Bryan Tan
Bryan Tan

Reputation: 293

Is it possible for a child process to get the PID of its siblings?

The child process is another C program run with execlp. The machine is Unix. I know the child process can access the process table with execlp("ps", "ps", NULL) but I can't figure out how it can determine its sibling.

Even though the processes are asynchronous, I know that the sibling process will be running.

Upvotes: 0

Views: 929

Answers (2)

karan patel
karan patel

Reputation: 61

yes, it is possible. I am attaching c code for this. Here I have taken 4 children and all are sharing their pid's.

#include <stdio.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>

#define NUM_CHILDREN 4

/* Entry point for the child processes */
int child_main(int pipe_read_end) {
  pid_t my_pid = getpid();

  /* Read child pids from pipe */
  int child_pids[NUM_CHILDREN];
  unsigned int bytes_read = 0;
  while (bytes_read < sizeof(child_pids)) {
    ssize_t result = read(pipe_read_end, ((unsigned char *) child_pids) + bytes_read, sizeof(child_pids) - bytes_read);
    if (result < 0) {
      perror("error reading from pipe");
      return 1;
    } else if (result == 0) {
      fprintf(stderr, "unexpected end of file\n");
      return 1;
    } else {
      bytes_read += result;
    }
  }
  close(pipe_read_end);

  /* Do something useful with these child pids */
  for (int i = 0; i < NUM_CHILDREN; i++) {
    printf("Child %d received sibling pid %d\n", my_pid, child_pids[i]);
  }

  return 0;
}

/* Entry point for the parent process. */
int main() {
  int child_pids[NUM_CHILDREN];
  int pipe_write_ends[NUM_CHILDREN];
  for (int i = 0; i < NUM_CHILDREN; i++) {
    /* Create the pipe for child i */
    int pipefd[2];
    if (pipe(pipefd)) {
      perror("error creating pipe");
      return 1;
    }
    int pipe_read_end = pipefd[0];
    int pipe_write_end = pipefd[1];

    /* Fork child i */
    pid_t child_pid = fork();
    if (child_pid < 0) {
      perror("error forking");
      return 1;
    } else if (child_pid == 0) {
      printf("Child %d was forked\n", getpid());
      close(pipe_write_end);
      return child_main(pipe_read_end);
    } else {
      printf("Parent forked child %d\n", child_pid);
      close(pipe_read_end);
      pipe_write_ends[i] = pipe_write_end;
      child_pids[i] = child_pid;
    }
  }

  /* Send pids down the pipes for each child */
  for (int i = 0; i < NUM_CHILDREN; i++) {
    unsigned int bytes_written = 0;
    while (bytes_written < sizeof(child_pids)) {
      ssize_t result = write(pipe_write_ends[i], ((unsigned char *) child_pids) + bytes_written, sizeof(child_pids) - bytes_written);
      if (result < 0) {
        perror("error writing to pipe");
        return 1;
      } else {
        bytes_written += result;
      }
    }
    close(pipe_write_ends[i]);
  }

  /* Wait for children to exit */
  for (int i = 0; i < NUM_CHILDREN; i++) {
    if (waitpid(child_pids[i], 0, 0) < 0) {
      perror("error waiting for child");
      return 1;
    }
  }
  }

Upvotes: 0

alk
alk

Reputation: 70883

Is it possible for a child process to get the PID of its siblings?

Without talking with the parent using sort of a protocol, this is not possible in a portable manner. On some systems it might not even be possible at all.

Upvotes: 1

Related Questions