Introduction to DIPC

DIPC (Distributd Inter-Process Communication) is a software-only solution for distributed data exchange on a network on Linux computers. It operates at the kernel level, and allows the programmer to use System V semaphores, message queues, and shared memory segments over the network with minimal change at the source code level.

To use it, one must patch the Linux kernel and the compile and install the modified kernel. After that, using the system is very easy for the programmer. For example, the program may send a few bytes to a message queue with a given number, except that now, a process running in another machine, and reading from a message queue with the same number, will receive the message. As simple as that.

The code at the end of this page shows a very simple programme that uses DIPC to exchange a message over the network. This source code is mainly System V IPC programming. The addition required by DIPC is highlighted in bold.

To read papers on DIPC please click here.

To download DIPC please click here and select the download tab. The DIPC package contains indformation about the system, as well as examples and the complete source code.

Kamran Karimi can be contacted at kamkar@users.sourceforge.net.



The sample program the follows sends 512 bytes (containing a message) from one process to another via a message queue. If run on a cluster with DIPC properly installed, the message will traverse the network.

A few notes about DIPC programs: They can be run on computers with no support for DIPC in the kernel, though in this case all the processes should run in the same machine. DIPC does not distributed any code accross the network, so the user must start each process remotely as appropriate (maybe via 'rsh' or similar methods).

/*
* hello.h
*
* Header file for hello1.c and hello2.c
*
* By Kamran Karimi
*/

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#include <errno.h>
#include <linux/dipc.h>
#include <string.h>


#ifdef __GLIBC__
#define IPC_DIPC 00010000 /* make it distributed */
#endif


#define MSG_KEY 40
#define MSG_MODE (IPC_DIPC | IPC_EXCL | 0777)
/* use of 'IPC_DIPC' is the ONLY thing that makes this program a distributed
   one. Everything else is normal System V IPC programming */
#define MSG_TYPE 10
#define MSG_SIZE 512

struct message
{
   long mtype;
   char mtext[MSG_SIZE];
};



/*
* hello1.c
*
* It initializes a message structure and waits to receive a message.
* After running hello1, you should run hello2 on a remote machine.
*
* By Kamran Karimi
*/

#include "hello.h"

int main()
{
  int msgid;
  struct message mess;

  /* create the message queue. The other process will access it later */
  msgid = msgget(MSG_KEY, MSG_MODE | IPC_CREAT);
  if(msgid < 0)
  {
   fprintf(stderr,"Hello1: msgget() failed BECAUSE %s\n", strerror(errno));
   exit(20);
  }
  fprintf(stderr,"Hello1: waiting to receive a message...\n");
  if(msgrcv(msgid, (struct msgbuf *)&mess, sizeof(mess.mtext), 0, 0) < 0)
   fprintf(stderr,"Hello1: msgrcv() failed BECAUSE %s\n", strerror(errno));
  else
   fprintf(stderr,"Hello1: Received '%s'\n",mess.mtext);
  msgctl(msgid,IPC_RMID,NULL);
  exit(0);
}



/*
* hello2.c
*
* This program sends a message to hello1 process.
* You should first run hello1, and then hello2 on a machine in the
* same cluster
*
* By Kamran Karimi
*/

#include "hello.h"

int main()
{
  int msgid;
  struct message mess;

  /* gain access to the message queue that was created by hello1 */
  msgid = msgget(MSG_KEY, MSG_MODE);
  if(msgid < 0)
  {
   fprintf(stderr,"Hello2: msgget() failed BECAUSE %s\n",strerror(errno));
   exit(20);
  }
  mess.mtype = MSG_TYPE; /* not necessary here */
  strcpy(mess.mtext,"Hello, Distributed Programming!");
  /* now send the message. This will traverse the network if hello1 and
    hello2 programs are in different computers and DIPC is properly
    installed */
  if(msgsnd(msgid, (struct msgbuf *)&mess, sizeof(mess.mtext), 0) < 0)
  {
   fprintf(stderr,"Hello2: msgsnd() failed BECAUSE %s\n", strerror(errno));
   exit(20);
  }
  exit(0);
}