Linux下進程代碼調試與理解


Linux下進程代碼調試與理解

創建進程代碼1:

#include <stdio.h>
void main( ) {
	int p1,p2;
	while((p1=fork())==-1);        /*創建子進程p1*/
	if (p1==0)  putchar('b');
	else {
		while((p2=fork())==-1);   /*創建子進程p2*/
		if(p2==0)  putchar('c');
		else  putchar('a');
	}
}

調試結果:

1587797903776

分析:這里的if和else不是以前理解的選擇分支。fork后產生的子進程和父進程並行運行的.這種理解是不正確的。if 和 else 還是選擇分支。 主要的原因是,fork() 函數調用一次,返回兩次。兩次返回的區別是:子進程的返回值是0,父進程返回值為新子進程的進程ID,至於abc順序為什么先后,偶也是懵的,只知道是隨機的。

創建進程代碼2:

#include <stdio.h>
void main( ) {
	int p1,p2,i;
	while((p1=fork())== -1);          /*創建子進程p1*/
	if (p1==0)
		for(i=0; i<10; i++)
			printf("daughter  %d\n",i);
	else {
		while((p2=fork())== -1);   /*創建子進程p2*/
		if(p2==0)
			for(i=0; i<10; i++)
				printf("son  %d\n",i);
		else
			for(i=0; i<10; i++)
				printf("parent  %d\n",i);
	}
}

調試結果:

1587798181254

創建進程代碼3(在2上加上sleep):

#include <stdio.h>
void main( ) {
	int p1,p2,i;
	while((p1=fork())== -1);          /*創建子進程p1*/
	if (p1==0)
		for(i=0; i<10; i++) {
			printf("daughter  %d\n",i);
			sleep(1);
		}

	else {
		while((p2=fork())== -1);   /*創建子進程p2*/
		if(p2==0)
			for(i=0; i<10; i++) {
				printf("son  %d\n",i);
				sleep(1);
			}

		else
			for(i=0; i<10; i++) {
				printf("parent  %d\n",i);
				sleep(1);
			}

	}
}

調試結果:

1587798393483

創建進程代碼4(在1上加上i觀察結果):

#include <stdio.h>
void main( ) {
	int p1,p2;
	int i;
	while((p1=fork())==-1);        /*創建子進程p1*/
	if (p1==0)  putchar('b');
	else {
		while((p2=fork())==-1);   /*創建子進程p2*/
		if(p2==0)  putchar('c');
		else  putchar('a');
	}
	i++;
	printf("i=%d\n",i);
}

調試結果:

1587798569866

可以觀察得出不同進程的i的值不同。

管理進程代碼:

#include<stdio.h>
#include <stdlib.h>
#include<unistd.h>
void main( )
{      
        int pid;    
        pid=fork( );         /*創建子進程*/
switch(pid) 
{
               case  -1:                          /*創建失敗*/
                       printf("fork fail!\n");
                       exit(1);
               case  0:                                 /*子進程*/
                       execl("/bin/ls","ls","-1","-color",NULL);  
                       printf("exec fail!\n");
                       exit(1);
               default:                                 /*父進程*/
                       wait(NULL);                  /*同步*/
                       printf("ls completed !\n");
                       exit(0);
          }
}
調試結果:

1587799195418

如果缺少wait:

1587799377059

分析:少了個wait就會先是父進程執行completed后,子進程才把ls打印出來

如果目錄寫錯:

1587799424111

分析:父進程未出現錯誤仍正常運行,子進程報錯。

互斥程序代碼(加鎖):

#include <stdio.h>
#include <unistd.h>
void main() {
	int p1,p2,i;
	while((p1=fork( ))== -1);       /*創建子進程p1*/
	if (p1==0) {
		lockf(1,1,0);          /*加鎖,這里第一個參數為stdout(標准輸出設備的描述符)*/
		for(i=0; i<10; i++)
			printf("daughter %d\n",i);
		lockf(1,0,0);                     /*解鎖*/
	} else {
		while((p2=fork( ))==-1);  /*創建子進程p2*/
		if (p2==0) {
			lockf(1,1,0);        /*加鎖*/
			for(i=0; i<10; i++)
				printf("son %d\n",i);
			lockf(1,0,0);            /*解鎖*/
		} else {
			lockf(1,1,0);         /*加鎖*/
			for(i=0; i<10; i++)
				printf(" parent %d\n",i);
			lockf(1,0,0);         /*解鎖*/
		}
	}
}

互斥程序調試結果:

1587799743277

分析:lockf(1,1,0)是鎖定屏幕輸出,不讓其他進程可以輸出到屏幕,lockf(1,0,0)則是解鎖,所以拿到鎖的那個進程能夠在屏幕上一直輸出。

互斥程序代碼(未加鎖):

#include <stdio.h>
#include <unistd.h>
void main() {
	int p1,p2,i;
	while((p1=fork( ))== -1);       /*創建子進程p1*/
	if (p1==0) {
		//lockf(1,1,0);          /*加鎖,這里第一個參數為stdout(標准輸出設備的描述符)*/
		for(i=0; i<10; i++)
			printf("daughter %d\n",i);
		//lockf(1,0,0);                     /*解鎖*/
	} else {
		while((p2=fork( ))==-1);  /*創建子進程p2*/
		if (p2==0) {
			//lockf(1,1,0);        /*加鎖*/
			for(i=0; i<10; i++)
				printf("son %d\n",i);
			//lockf(1,0,0);            /*解鎖*/
		} else {
			//lockf(1,1,0);         /*加鎖*/
			for(i=0; i<10; i++)
				printf(" parent %d\n",i);
			//lockf(1,0,0);         /*解鎖*/c
		}
	}
}

運行結果:

1587801839632

分析:沒有鎖,他們是同步運行,順序不分先后。

互斥程序代碼(加鎖+sleep):

#include <stdio.h>
#include <unistd.h>
void main() {
	int p1,p2,i;
	while((p1=fork( ))== -1);       /*創建子進程p1*/
	if (p1==0) {
		lockf(1,1,0);          /*加鎖,這里第一個參數為stdout(標准輸出設備的描述符)*/
		for(i=0; i<10; i++){
			printf("daughter %d\n",i);
			sleep(1);
		}
			
		lockf(1,0,0);                     /*解鎖*/
	} else {
		while((p2=fork( ))==-1);  /*創建子進程p2*/
		if (p2==0) {
			lockf(1,1,0);        /*加鎖*/
			for(i=0; i<10; i++){
				printf("son %d\n",i);
				sleep(1);
			}
				
			lockf(1,0,0);            /*解鎖*/
		} else {
			lockf(1,1,0);         /*加鎖*/
			for(i=0; i<10; i++){
				printf(" parent %d\n",i);
				sleep(1);
			}
				printf(" parent %d\n",i);
			lockf(1,0,0);         /*解鎖*/
		}
	}
}

運行結果:

1587802099447

分析:加上sleep也是一樣的,他們是同步運行的。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM