Lecture No. 08
Dated: 11-05-2025
Inter Process Communication
It provides a mechanism for processes
to communicate and synchronize their actions without sharing the same address space
.
Message Passing System
This allows processes
to communicate without shared data. Messages
sent by a process
may be of either fixed or variable length.
There are several methods for logically implementing a link for the processes
to communicate.
Direct Communication
Primitives
Send(P, message)
Sends a message
to process
P
.
Receive(Q, message)
Receive a message
from process
Q
.
Properties
- Only 1
link
can exist between exactly 2processes
. Processes
need to know each other'sID
to be able to communicate.
Indirect Communication
Primitives
Send(A, message)
Send a message
to mailbox A
.
Receive(A, message)
Receive a message
from mailbox A
.
Properties
- A
link
between multipleprocesses
will only exist if they share the samemailbox
. - Multiple
links
can exist but each will be associated with a certainmailbox
.
Synchronization
Primitives
Blocking Send
The sending process
is blocked until the message
is received.
Non Blocking Send
The sending process
sends the message
and resumes operation.
Blocking Receive
The receiver
blocks until a message
is available.
Non Blocking Receiver
The receiver
receives either a valid message
or a null
.
Buffering
Messages
exchanged by the processes
reside in a temporary queue
.
Zero Capacity
- Has zero length.
Message
cannot wait.Sender
must blockreceiver
.
Bounded Capacity
- Has \(n\) size.
Sender
blocksreceiver
until there is space inqueue
.
Unbounded Capacity
- Has \(\infty\) size.
Sender
never blocksreceiver
.
Unix / Linux IPC Tools
- Pipe
- Named pipe (FIFO)
- BSD Socket
- TLI
- Message queue
- Shared memory
read()
#include <unistd.h>
ssize_t read(int file_descriptor, void* buf, size_t count);
if count
is
- \(= 0\) then
read()
returns \(0\). - \(>\)
SSIZE_MAX
, the result is unspecified.
On success, read()
returns number of bytes
read and 0
indicates EOF
.
It also advances the file position pointer
.
write()
#include <unistd.h>
ssize_t write(int file_descriptor, const void* buf, size_t count);
close()
#include <unistd.h>
int close(int file_descriptor);
pipe()
#include <unistd.h>
int pipe(int file_descriptor[2]);
- For reading
- For writing
A pipe
is bounded buffer and the maximum data which can be written, is PIPE_BUF
.
Defined:
- as \(5120\) in
"sys/param.h"
- as \(4096\) in
"linux/param.h"
Example
/* Parent creates pipe, forks a child, child writes into
pipe, and parent reads from pipe */
#include <stdio.h>
#include <stdlib.h> // For exit()
#include <string.h> // For strlen()
#include <unistd.h> // For pipe(), fork(), read(), write(), close()
#include <sys/types.h> // For pid_t
#include <sys/wait.h> // For wait()
int main() {
int pipefd[2], pid, n, rc, nr, status;
char *testString = "Hello, world!\n";
char buf[1024];
rc = pipe(pipefd);
if (rc < 0) {
perror("pipe");
exit(1);
}
pid = fork();
if (pid < 0) {
perror("fork");
exit(1);
}
if (pid == 0) { /* Child’s Code */
close(pipefd[0]); // Close read end
write(pipefd[1], testString, strlen(testString));
close(pipefd[1]);
exit(0);
}
/* Parent’s Code */
close(pipefd[1]); // Close write end
n = strlen(testString);
nr = read(pipefd[0], buf, n);
rc = write(1, buf, nr);
wait(&status);
printf("Good work child!\n");
return 0;
}