Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

...

The program must follow the principle of least privilege while carefully separating the binding and bookkeeping tasks. To minimize the chance of a flaw in the program from compromising the superuser level account, it must drop superuser privileges as soon as the privileged operations are completed. In the code shown below, privileges are dropped permanently as soon as the bind() operation is carried out. This solution is in compliance with [FIO42-C. Ensure files are properly closed when they are no longer needed].

Code Block
bgColor#ccccff

/*  Code with elevated privileges  */

int establish() {
  struct sockaddr_in sa;              /*  This will store the listening socket's address  */
  int s;                              /*  This will hold the listening socket  */

  /* Fill up the structure with address and port number */

  sa.sin_port = htons(portnum);

  /* Other system calls like socket() */

  if (bind(s, (struct sockaddr *) &sa, sizeof(struct sockaddr_in)) < 0)  { 
    /* Perform cleanup */  
  }

  /* Return */  
}

int main(void) {
   int s = establish();

   if (setuid(getuid()) == -1) {   /* Drop privileges permanently */
      /*  Handle the error  */
   }

  /* Block with accept() until a client connects */
      
   switch(fork()) {
      case -1: /* Error, clean up and quit */
      case  0: /* Close all open file descriptors
                * This is the child, handle the client 
                */
      default: /* This is the parent, continue blocking */
   }
} 

...