Süreçler(Process) arası iletişim-Linux Kernel IPC 1
Inter Process Commonication(IPC),bir veya birden fazla işlemin veya çalışmakta olan bir programdaki birden fazla iş parçacığı arasında veri alışverişi için kullanılır.
Yani bu yapı,bir programcının işletim sisteminde eş zamanlı olarak çalışan çeşitli program süreçleri arasındaki etkinlikleri koordine etmesine olanak tanıyan bir programlama arayüzü dür.
İlk atası “Signal”’dır. Signal Unix türevi sistemlerde en eski süreçler arası iletişim aracıdır. Ancak bu makalede SIGNAL işlenmeyecektir.
Aklımıza şöyle bir soru gelebilir.
Soru: Her sürecin kendi adres alanı ve benzersiz kullanıcı alanı varsa,süreçler birbirleriyle nasıl iletişim kuracak?
Cevap: Cevap Linux Kernel’dir. IPC de kernel seviyesinde bir yapıdır.
Böylelikle linux kernel,süreçler arasında iletişim kurmamız için gereken yapıyı bize IPC olarak sunuyor ve bunun korumasını sağlıyor.
Linux’a aşina olanlar bilirler ki linux’da her şey dosya dır.
Dolayısıyla IPC olarak işleyeceğimiz konular da dosya sistemi üzerinden yürütülecektir.Zaten aşağıda işleyeceğimiz örneklerde,işlemin dosya mantığında(dosyaya yaz,dosyadan oku) yapıldığını göreceğiz.
Bir sürecin aynı bilgisayarda veya aynı ağdaki farklı bir bilgisayarda başka işlemlerle iletişim kurmasına izin veren çeşitli IPC’ler vardır.
Bunlar başlık olarak şöyledir:
Pipes
Shared Memory
Message Queue
Semaphores
-Pipes:
Süreçlerin birbirleriyle mesaj alışverişi yaparak iletişim kurması ve yine farklı bilgisayar sistemlerinde çalışan işlemlerin ağ üzerinden iletişim kurması için bir yol sağlar.
-Shared Memory:
Bir işlem,diğer işlemin erişebileceği bir bellek bölümü oluşturur.Böylece paylaşılan bir bellek bölümü açılmış olur ve bu bölümde veri-değer değiş tokuş edilir.
NOT: Bu makalede “Shared Memory” işlenecektir.
-Message Queue:
Kernel mesaj kuyruklarının bir listesini tutar.
Mesaj kuyruğu kernel’da depolanan mesajların bağlantılı bir listesidir ve bir mesaj kuyruğu tanımlayıcısı ile tanımlanır.
-Semaphores:
Aynı kaynağa erişen süreçler için bir senkronizasyon mekanizması sağlar.
Dolayısıyla semafor ile veri aktarılmaz. Sadece paylaşılan kaynaklara erişimi koordine eder.
Son olarak Shared memory örneğine geçmeden evvel,linux sisteminde IPC komutlarını terminalde kullanarak bilgi edebilirsiniz.
Aşağıdaki komut ile sistemdeki IPC okuma erişimi olan kısımlarının genel dökümünü verecektir.
Örnek: ipcs -a
Paylaşılan bellek(Shared Memory) yoluyla IPC,iki veya daha fazla sürecin ortak belleğe erişebildiği bir kavramdır.Ve iletişim bir işlem tarafından yapılan değişikliklerin başka bir işlem tarafından görüntülenebildiği bu paylaşılan bellek aracılığıyla yapılır. Aşağıda Server ve Client mantığında iki ayrı örnek geliştireceğiz. Bunlardan Server olan örnek,bir dosya üzerinden bir paylaşım alanı oluşturacak ve bu dosyaya veri yazacaktır. Client olan örnek ise belirtilen bellek alanına erişecek ve oradan verileri okuyup ekrana yazdıracaktır.
Program örneğine geçmeden evvel,kullanacağımız api-fonksiyonları inceleyelim.Programlarda kullanılacak kütüphaneler ve Api-fonksiyonlar aşağıda yer almaktadır.
#include <sys/ipc.h>
#include <sys/shm.h>
-ftok(): Benzersiz(unique) anahtar oluşturmak için kullanılır.
-shmget(): Başarıyla tamamlandığında,paylaşılan bellek bölümü için bir tanımlayıcı döndürür.
Bu fonksiyonun aldığı parametre itibariyle yapısı şöyledir:
int shmget(key_t,size_tsize,intshmflg);
İlk parametresi ftok() ile elde edilen anahtar,ikinci paremetre ile boyutu,ve son parametre ise izin bilgisi verilmelidir.
-shmat(): Yukarıdaki fonksiyonla elde edilen bellek bölümünü kullanmadan önce bu fonksiyon kullanılarak ilgili bellek bölümünü bağlamamız gerekir.
Bu fonksiyonun aldığı parametre itibariyle yapısı şöyledir:
void *shmat(int shmid ,void *shmaddr ,int shmflg);
İlk parametre ile shmget() ile elde edilen tanımlayıcı,ikinci parametre ile belirli bir adres,ve son parametre bir bayrak değeri verilmelidir.
Biz örneklerimizde ikinci parametreye sıfır değeri vereceğiz. Böylelikle işletim sistemi otomatik olarak bir adres belirleyecektir.
-shmdt(): Paylaşılan bellek bölümü ile işimiz bittiğinde,bu fonksiyonu kullanarak program kendisini ilgili bölümden ayırır.
Bu fonksiyonun aldığı parametre itibariyle yapısı şöyledir:
int shmdt(void *shmaddr);
Aldığı parametre,paylaşılan bellek bölümünü işaret eder.
shmctl(): Paylaşılan bellek bölümünden programımızı ayırdığımızda ilgili bölüm yok edilmez. Ancak bu fonksiyonu kullanarak paylaşılan bellek bölümünü yok edebiliriz. Fonksiyonun yapısı şöyledir:
shmctl(int shmid,IPC_RMID,NULL);
İlk parametre,shmget() ile elde edilen bellek bölümü tanımlayıcısı verilir. İkinci parametre ise IPC’nin imha edilecek bölümü “IPC_RMID” anahtarıyla işaretlenir.
Örnek1 Paylaşılan bellek oluştur ve veri yaz:
#include <iostream>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <stdio.h>
using namespace std;
int main()
{
//ftok ile benzersiz bir anahtar oluştur:
key_t key = ftok("shared_memory_file",60);
// shmget paylaşılan bellek bölümü için bir tanımlayıcı döndür:
int shmid = shmget(key,1024,0666|IPC_CREAT);
//bellek bölümünü bağla:
char *str = (char*) shmat(shmid,(void*)0,0);
cout<<"Veri yaz:";
cin >> str;
printf("Paylaşılan belleğe yazılan veri: %s\n",str);
//Paylaşılan bellek bölümü ile işimiz bitti.Kendini ilgili bölümden ayırır:
shmdt(str);
return 0;
}
Örnek2 Paylaşılan bellek bölümünden veri oku:
#include <iostream>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <stdio.h>
using namespace std;int main()
{
//ftok ile benzersiz bir anahtar oluştur:
key_t key = ftok("shared_memory_file",60);// shmget paylaşılan bellek bölümü için bir tanımlayıcı döndür:
int shmid = shmget(key,1024,0666|IPC_CREAT);//bellek bölümünü bağla:
char *str = (char*) shmat(shmid,(void*)0,0);printf("Bellekten veri oku: %s\n",str);
//Paylaşılan bellek bölümü ile işimiz bitti.Kendini ilgili bölümden ayırır:
shmdt(str);
//Paylaşılan bellek bölümünü yok et:
shmctl(shmid,IPC_RMID,NULL);
return 0;
}
NOT: Dikkat ederseniz ilk örnekte “shmctl()” fonksiyonu kullanılmadı.
Çünkü paylaşılan alanda veri okunmadan ilgili bölümün yok edilmesini istemedik.
Inter Process Commonication(IPC) serisi devam edecektir.
end of