1. Write a program named <print_num.c>, which should take one command-line argument called maxnum. Print_num should fork a child process, which prints the odd integers up to maxnum (inclusive), with space separating the numbers. At the same time, the parent process should print the even integers from 0 to maxnum (inclusive), with space separating the numbers. The parent process should wait for the child process to terminate before exiting.
Source code:
#include<sys/types.h>
#include<stdio.h>
#include<unistd.h>
int main(int argc, char *argv[])
{
pid_t pid;
/*Command line arguments are strings so convert to int*/
if (argc != 2) {
printf(“Usage: %s max_num (must be an integer)n”, argv[0]);
return 1;
}
int maxnum = atoi(argv[1]);
/*fork a child process*/
pid = fork();
if(pid < 0)/*error occured*/
{
fprintf(stderr, “Fork Failed”);
return 1;
}
else if(pid == 0)/*child process*/
{
int i = 1;
while(i <= maxnum)
{
printf(“%i “, i);
i+=2;
}
}
else /*parent process*/
{
int i = 0;
while(i <= maxnum)
{
printf(“%i “, i);
i+=2;
}
/*parent will wait for the child to complete*/
wait(NULL);
printf(“n”);
}
return 0;
}
Screenshots:
2. Use “ps” to find out the process IDs’ of the parent process and the child process. Take a screenshot of your ps output and point out which is the parent process and which is the child process. [Note: you may need to use “sleep()” function to pause the execution so you can see the process IDs. If so, explain where you add the line(s).]
Source Code:
#include<sys/types.h>
#include<stdio.h>
#include<unistd.h>
int main(int argc, char *argv[])
{
pid_t pid;
/*Command line arguments are strings so convert to int*/
if (argc != 2) {
printf(“Usage: %s max_num (must be an integer)n”, argv[0]);
return 1;
}
int maxnum = atoi(argv[1]);
/*fork a child process*/
pid = fork();
if(pid < 0)/*error occured*/
{
fprintf(stderr, “Fork Failed”);
return 1;
}
else if(pid == 0)/*child process*/
{
int i = 1;
while(i <= maxnum)
{
printf(“%i “, i);
i+=2;
}
}
else /*parent process*/
{
int i = 0;
while(i <= maxnum)
{
printf(“%i “, i);
i+=2;
}
/*parent will wait for the child to complete*/
wait(NULL);
printf(“n”);
}
//both processes will sleep for 10 seconds before exiting
// since parent process waits for child process, it waits for 20 seconds.
sleep(10);
return 0;
}
Screenshots:
Process 608 and 609 are the pid’s of child and parent. Since the parent process will stay alive longer than the child process, 608 is the parent process and 609 is the child process. Actually, 609 is larger than 608 (created by 608).
Note that we ran a.out with “&” at the end. That ran it in background. You could use dual windows.
3. You will notice that most likely the output are not strictly sequential, i.e., not in the sequence of 0, 1, 2, 3, 4, …, maxnum. Rewrite your code above to generate an output as 0 1 2 3 … maxnum. The only requirement is that odd integers must be printed by the child process and even numbers must be printed out by the parent process.
The following is a hack. Increase delay to have a higher confidence that the results are correct.
Source Code:
#include<sys/types.h>
#include<stdio.h>
#include<unistd.h>
int main(int argc, char *argv[])
{
pid_t pid;
/*Command line arguments are strings so convert to int*/
if (argc != 2) {
printf(“Usage: %s max_num (must be an integer)n”, argv[0]);
return 1;
}
int maxnum = atoi(argv[1]);
double delay=1; //second
/*fork a child process*/
pid = fork();
if(pid < 0)/*error occured*/
{
fprintf(stderr, “Fork Failed”);
return 1;
}
else if(pid == 0)/*child process*/
{
int i = 1;
sleep(delay/2); //sleep a half delay
while(i <= maxnum)
{
sleep(delay); //sleep
printf(“%i “, i);
fflush(stdout); //send output
i+=2;
}
}
else /*parent process*/
{
int i = 0;
while(i <= maxnum)
{
sleep(delay); //sleep
printf(“%i “, i);
fflush(stdout); //send output
i+=2;
}
/*parent will wait for the child to complete*/
wait(NULL);
printf(“n”);
}
//both processes will sleep for 10 seconds before exiting
// both since parent process waits for child process, it waits for 20 seconds.
//sleep(10);
return 0;
}
Screenshots:
4. Fibonacci sequence, Child Process, and Shared memory, textbook page 145-146, problem 3.19. Please use C and the shared memory code sample on page 125 of textbook.
Source Code:
#include <sys/shm.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#define MAX_SEQUENCE 100
/*struct for shared data segment, per page 125*/
typedef struct{
long fib_sequence[MAX_SEQUENCE];
int sequence_size;
} shared_data;
int main()
{
/*fib number input by user*/
int fib;
/*identifier for the shared memory segment*/
int segment_id;
/*pointer to the shared segment*/
shared_data *shared_mem;
/*process id*/
pid_t pid;
/*read input from command line*/
printf(“Please input a number for the fibonacci sequence: “);
scanf(“%d”, &fib);
/*bounds check*/
if(fib > MAX_SEQUENCE){
printf(“Max Input Size: %dn”, MAX_SEQUENCE);
exit(1);
}
/*allocate shared memory segment*/
segment_id = shmget(IPC_PRIVATE, sizeof(shared_data), S_IRUSR | S_IWUSR);
/*attach shared memory segment*/
shared_mem = (shared_data*)shmat(segment_id, NULL, 0);
/*size of sequence to arg input on command line*/
shared_mem -> sequence_size = fib;
/*fork a child process*/
pid = fork();
/*check for successful fork*/
if(pid < 0){
fprintf(stderr, “Fork failedn”);
return 1;
}
/*if equal to zero, child process successful*/
else if(pid == 0){
int counter = 0;
/*fibonacci sequence formula is = fib(n-1)+fib(n-2), always starting with zero and one*/
while(counter < shared_mem -> sequence_size){
if(counter == 0){
shared_mem -> fib_sequence[counter] = 0;
}
else if(counter == 1){
shared_mem -> fib_sequence[counter] = 1;
}
else{
shared_mem -> fib_sequence[counter] = shared_mem -> fib_sequence[counter-1]+shared_mem -> fib_sequence[counter-2];
}
counter++;
}
}
/*into the parent process*/
else{
/*wait for child to complete*/
wait(NULL);
int count = 0;
/*print the fibonacci sequence to screen*/
while(count < shared_mem -> sequence_size){
printf(“%li “, shared_mem -> fib_sequence[count]);
count++;
}
printf(“n”);
/*now detach shared memory segment*/
shmdt(shared_mem);
/*now remove shared memory segment*/
shmctl(segment_id, IPC_RMID, NULL);
}
return 0;
}