C'de Çatal Sistem Çağrısı

Fork System Call C



fork() sistem çağrısı, bir C programında alt süreçler oluşturmak için kullanılır. fork(), uygulamanızda paralel işlemenin gerekli olduğu yerlerde kullanılır. fork() sistem işlevi başlıklarda tanımlanmıştır. sys/types.h ve unistd.h . Fork kullandığınız bir programda wait() sistem çağrısını da kullanmanız gerekir. wait() sistem çağrısı, ana süreçte alt sürecin bitmesini beklemek için kullanılır. Bir alt işlemi bitirmek için, alt işlemde çıkış() sistem çağrısı kullanılır. wait() işlevi başlıkta tanımlanır sistem/bekle.h ve çıkış() işlevi başlıkta tanımlanır stdlib.h .

Şekil 1: Temel çatal() iş akışı

Şekil 1: Temel çatal() iş akışı







Bu yazıda size C'de alt süreçler oluşturmak için fork() sistem çağrısının nasıl kullanılacağını göstereceğim. Haydi başlayalım.



fork() Sözdizimi ve Dönüş Değeri:

fork() sistem işlevinin sözdizimi aşağıdaki gibidir:



pid_t çatalı(geçersiz);

fork() sistem işlevi herhangi bir bağımsız değişkeni kabul etmez. Türün bir tamsayısını döndürür pid_t .





Başarılı olduğunda, fork(), 0'dan büyük olan alt sürecin PID'sini döndürür. Alt sürecin içinde, dönüş değeri 0'dır. Fork() başarısız olursa, -1 döndürür.

Basit çatal() Örnek:

Basit bir çatal() örneği aşağıda verilmiştir:



#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek

intana(geçersiz) {
pid_t pid=çatal();

Eğer(pid== 0) {
baskı ('Alt => PPID: %d PID: %d ',getppid(),getpid());
çıkış (EXIT_SUCCESS);
}
Başka Eğer(pid> 0) {
baskı ('Üst => PID: %d ',getpid());
baskı ('Çocuk sürecinin bitmesini bekliyorum. ');
Bekle(BOŞ);
baskı ('Çocuk süreci bitti. ');
}
Başka {
baskı ('Alt süreç oluşturulamıyor. ');
}

dönüşEXIT_SUCCESS;
}

Burada, ana/ana süreçten bir alt süreç oluşturmak için fork() kullandım. Ardından, alt ve üst süreçten PID (İşlem Kimliği) ve PPID'yi (Üst İşlem Kimliği) yazdırdım. Ana süreçte wait(NULL) alt sürecin bitmesini beklemek için kullanılır. Alt süreçte, alt işlemi bitirmek için çıkış() kullanılır. Gördüğünüz gibi, ana sürecin PID'si, alt sürecin PPID'sidir. Yani çocuk süreci 24738 ana sürece aittir 24731 .

Programınızı daha modüler hale getirmek için işlevleri de kullanabilirsiniz. İşte, kullandım süreçGörevi() ve ebeveynGörev() sırasıyla çocuk ve ebeveyn süreçleri için işlevler. fork() aslında bu şekilde kullanılır.

#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek

geçersizçocukgörev() {
baskı ('Selam Dünya ');
}

geçersizebeveyngörevi() {
baskı ('Ana görev. ');
}

intana(geçersiz) {
pid_t pid=çatal();

Eğer(pid== 0) {
çocukgörev();
çıkış (EXIT_SUCCESS);
}
Başka Eğer(pid> 0) {
Bekle(BOŞ);
ebeveyngörevi();
}
Başka {
baskı ('Alt süreç oluşturulamıyor.');
}

dönüşEXIT_SUCCESS;
}

Yukarıdaki programın çıktısı:

fork() ve Loop kullanarak Çoklu Alt İşlemleri Çalıştırma:

İhtiyaç duyduğunuz kadar çok sayıda alt süreç oluşturmak için döngüyü de kullanabilirsiniz. Aşağıdaki örnekte for döngüsü kullanarak 5 alt süreç oluşturdum. Ayrıca alt süreçlerden PID ve PPID'yi yazdırdım.

#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek

intana(geçersiz) {
için(intben= 1;ben<= 5;ben++) {
pid_t pid=çatal();

Eğer(pid== 0) {
baskı ('Alt süreç => PPID=%d, PID=%d ',getppid(),getpid());
çıkış (0);
}
Başka {
baskı ('Üst süreç => PID=%d ',getpid());
baskı ('Alt süreçlerin bitmesi bekleniyor... ');
Bekle(BOŞ);
baskı ('çocuk süreci bitti. ');
}
}

dönüşEXIT_SUCCESS;
}

Gördüğünüz gibi, Ana işlem kimliği tüm alt işlemlerde aynıdır. Yani, hepsi aynı ebeveyne aittir. Ayrıca doğrusal bir şekilde yürütülürler. Birbiri ardına. Alt süreçleri kontrol etmek karmaşık bir iştir. Linux sistem programlaması ve nasıl çalıştığı hakkında daha fazla bilgi edinirseniz, bu süreçlerin akışını istediğiniz gibi kontrol edebileceksiniz.

Gerçek Hayat Örneği:

md5, sha256 vb. karma oluşturma gibi farklı karmaşık matematiksel hesaplamalar çok fazla işlem gücü gerektirir. Bunun gibi şeyleri ana programla aynı süreçte hesaplamak yerine, bir alt süreçteki hash'i hesaplayabilir ve hash'i ana prosese geri döndürebilirsiniz.

Aşağıdaki örnekte, bir alt süreçte 4 haneli bir PIN kodu oluşturdum ve bunu ana program olan üst sürece gönderdim. Sonra oradan PIN kodunu yazdırdım.

#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek
#Dahil etmek

intalPIN() {
// tohum olarak PPID ve PID kullanın
srand (getpid() +getppid());
intgizli= 1000 + sıra () % 9000;
dönüşgizli;
}

intana(geçersiz) {
intfd[2];
boru(fd);
pid_t pid=çatal();

Eğer(pid> 0) {
kapat(0);
kapat(fd[1]);
sonrasında(fd[0]);

intgizli numara;
size_tokuma baytları=okuman(fd[0], &gizli numara, boyutu(gizli numara));

baskı ('PIN bekleniyor... ');
Bekle(BOŞ);
baskı ('Bayt okuma: %ld ',okuma baytları);
baskı ('PIN: %d ',gizli numara);
}
Başka Eğer(pid== 0) {
kapat(1);
kapat(fd[0]);
sonrasında(fd[1]);

intgizli=alPIN();
yazı yazmak(fd[1], &gizli, boyutu(gizli));
çıkış (EXIT_SUCCESS);
}

dönüşEXIT_SUCCESS;
}

Gördüğünüz gibi programı her çalıştırdığımda 4 haneli farklı bir PIN kodu alıyorum.

Linux'ta fork() sistem çağrısını temel olarak bu şekilde kullanırsınız. Bu makaleyi okuduğunuz için teşekkürler.