檔案:
課程介紹 · 6.S081 All-In-One (dgs.zone)
網課:6.S081 / Fall 2020 [麻省理工作業系統 - 2020 年秋季][中英文字幕]_嗶哩嗶哩_bilibili
1.sleep
main的第一個引數一般是函式名,第二個才是引數
而輸入的引數是Ascii碼,系統呼叫sleep需要的是數值,因此需要轉換
#include "kernel/types.h"
#include "kernel/stat.h"
#include "user/user.h"
int
main(int argc, char *argv[])
{
if (argc != 2) {
fprintf(2, "Usage: sleep <number>\n");
exit(1);
}
int i = *argv[1] - '1';
sleep(i);
exit(0);
}

2.pingpong
考驗對管道的理解
錯誤:第一次寫的時候,不知道pipe(p1)后,p1[0]為讀入端,p1[1]為寫入端,也就是說p1[0]、p1[1]的分工是被定死了的
這里close是一種習慣,當一個行程有太多管道的時候,可能會爆掉,比如xv6的每個行程最多只能打開16個檔案描述符
read(p1[0], buf, n) 是從管道p1[0]中讀取n個位元組到buf,并回傳實際讀取的位元組數,
因此可以使用 read(p1[0], buf, n) == n 來判斷是否順利讀入
write(p1[1], buf, n) 同理
#include "kernel/types.h" #include "kernel/stat.h" #include "user/user.h" int main(int argc, char *argv[]){ if(argc > 1){ fprintf(2, "Usage: pingpong\n"); exit(1); } int p1[2], p2[2]; pipe(p1); pipe(p2); char buf[1]; if(fork() == 0){ //son should read buf[0] = '0'; close(p1[0]); close(p2[1]); if(read(p2[0], buf, 1) == 1){ close(p2[0]); printf("%d: received pong\n", getpid()); } write(p1[1], buf, 1); close(p1[1]); } else{ buf[0] = '1'; close(p1[1]); close(p2[0]); write(p2[1], buf, 1); close(p2[1]); if(read(p1[0], buf, 1) == 1){ close(p1[0]); printf("%d: received ping\n",getpid()); } } exit(0); }


3. primes
錯誤:把函式定義在main()之后,導致編譯出錯
main()函式進行第一次fork,父行程通過管道向子行程傳遞2~35,子行程呼叫遞回,
遞回的第一件事是檢查其父行程是否通過管道傳遞數字,如果沒有,說明遞回結束,
如果有,那么傳遞的第一個數字i一定是質數(這些數都是不能被比它小的數字整除的),將其列印,
然后進行fork(),本行程進行篩選,將不能被i整除的數字傳遞給子行程,子行程呼叫遞回
行程1->行程2: 傳遞 2~35
行程2:列印2,行程2->行程3 傳遞: 3~35 篩掉能被2整除的數,傳遞給行程3
行程3:列印3,行程3->行程4 傳遞: 5~35(不能被2、3整除) 篩掉能被3整除的數,傳遞給4
#include "kernel/types.h"
#include "kernel/stat.h"
#include "user/user.h"
void ff(int p[]){
close(p[1]);
int i;
// finish 2~35
if(read(p[0], &i, sizeof(i)) == 0){
close(p[0]);
exit(0);
}
printf("prime %d\n",i);
int num, newp[2];
pipe(newp);
//son recursion
if(fork() == 0){
close(p[0]);
close(newp[1]);
ff(newp);
}
//parent output for son
else{
close(newp[0]);
// get digit from its parent
while(read(p[0], &num, sizeof(num)) != 0){
//sift digit, and send to son
if(num % i != 0)
write(newp[1], &num, sizeof(num));
}
close(p[0]);
close(newp[1]);
wait(0);
}
exit(0);
}
int main(int argc, char *argv[]){
//need not input
if(argc > 1){
fprintf(2, "Usage: primes\n");
exit(1);
}
int p[2];
pipe(p);
//son
if(fork() == 0){
close(p[1]);
ff(p);
}
//parent
else{
close(p[0]);
for(int i = 2; i <= 35; i++){
write(p[1], &i, sizeof(i));
}
close(p[1]);
wait(0);
}
exit(0);
}

轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/395000.html
標籤:其他
上一篇:配接器模式改造Servlet(GenericServlet)
下一篇:Linux系統配置(服務控制)
