title: c - creating threads & joining them in a for loop
body: <p>So basically I'm making a simulator in c for vehicles entering in and out of cell phone tower zones. I'm trying to add code in simulator.c that makes the function spawn a new thread for each cell tower as well as one thread to handle the display. The simulator program should continue up until all 7 cell tower threads have completed, and the cell tower threads should continue until they receive a shutdown request. The display thread runs indefinitely but gets killed when the simulator process completes. I'm having trouble understanding what parameters I'm supposed to use to create and join the threads. I posted below what I have so far in the simulator.c program. My attempt is trying to loop the statements to make 7 threads for 7 cell towers. I'm not sure if my first parameter for pthread_create is correct and I'm not really sure what my 4th parameter is supposed to be. I know I'm supposed to pass in some sort of argument but I'm not sure what. Also I'm not too sure what the requirements mean for "the cell tower threads should continue until they receive a shutdown request." Each cell tower thread is supposed to call handleIncomingRequests() from cellTower.c and the display thread should call showSimulation() from display.c</p>
  
  <p>Any help would be really appreciated. I watched some videos online about threading in c but I'm still a little confused as to how they work. I posted below the files I felt were only related to this question, but if anyone wants me to post every file for this entire program I don't mind.</p>
  
  <p>simulator.c: </p>
  
  <pre><code>#include &lt;stdio.h&gt;
  #include &lt;stdlib.h&gt;
  #include &lt;pthread.h&gt;
  #include "simulator.h"
  
  #include "display.c"
  #include "cellTower.c"
  
  int main() {
    City     ottawa;
  
    // Cell tower data
    short    xLocations[7] = {100, 400, 650, 640, 400, 120, 200};
    short    yLocations[7] = {100, 200, 150, 450, 500, 350, 500};
    short     cellRadii[7] = {110, 200, 150, 180, 160, 120, 100};
    int      cellColors[7] = {0xFF8822 /*Orange*/, 0xFF2222 /*Red*/, 0xFFFF44 /*Yellow*/,
                  0x22FF22 /*Green*/, 0xAA66FF /*Purple*/, 0x0099FF /*Blue*/,
                  0x999999 /*LightGray*/};
  
    // Set up the Cell Towers with the above data ... and no connected vehicles to begin
    ottawa.numTowers = 7;
    for (int i=0; i&lt;ottawa.numTowers; i++) {
      ottawa.towers[i].online = 1;
      ottawa.towers[i].id = (unsigned char)i;
      ottawa.towers[i].x = xLocations[i];
      ottawa.towers[i].y = yLocations[i];
      ottawa.towers[i].radius = cellRadii[i];
      ottawa.towers[i].color = cellColors[i];
      ottawa.towers[i].numConnectedVehicles = 0;
      for (int j=0; j&lt;MAX_CONNECTIONS; j++)
        ottawa.towers[i].connectedVehicles[j].connected = 0;
    }
  
    // Remove the line of code below.  Add code to spawn the necessary threads and
    // wait for their completion before exiting gracefully with some kind of message
      pthread_t cellTowers[ottawa.numTowers];
      int i;
      for(i = 0; i &lt; ottawa.numTowers; i++){
          pthread_create(cellTowers[i], NULL, handleIncomingRequests, "");
          pthread_join(cellTowers[i], NULL);
      }
  
      pthread_t displayTower;
      pthread_create(&amp;displayTower, NULL, showSimulation, "");
  
  
  
  }
  </code></pre>
  
  <p>simulator.h:</p>
  
  <pre><code>#define VEHICLE_SPEED           3   // Forward pixels per movement
  #define VEHICLE_TURN_ANGLE      5   // degrees to turn for each vehicle movement
  
  #define NUM_TOWERS              7   // Number of cell towers within the city borders
  
  #define SERVER_IP     "127.0.0.1"   // IP address of simulator server
  #define SERVER_PORT          6000   // PORT of the simulator server
  
  // Command codes sent from client to server
  #define SHUTDOWN           1
  #define CONNECT            2
  #define UPDATE             3
  
  // Command codes sent from server to client
  #define YES                5
  #define NO                 6
  #define NOT_OK_BOUNDARY    7
  #define NOT_OK_COLLIDE     8
  
  
  typedef struct {
    int   x;
    int   y;
    int   direction;
    char  towerID;
  } Vehicle;
  
  typedef struct {
    int   x;
    int   y;
    char  connected;
  } ConnectedVehicle;
  
  
  typedef struct {
    char               online; // 0 = no, 1 = yes
    char               id;
    short              x;
    short              y;
    short              radius;
    int                color;
    ConnectedVehicle   connectedVehicles[MAX_CONNECTIONS];
    short              numConnectedVehicles;
  } CellTower;
  
  typedef struct {
    CellTower towers[NUM_TOWERS];
    short     numTowers;
  } City;
  </code></pre>
  
  <p>cellTower.c:</p>
  
  <pre><code>#include &lt;string.h&gt;
  #include &lt;sys/socket.h&gt;
  #include &lt;netinet/in.h&gt;
  
  
  void *handleIncomingRequests(void *ct) {
    CellTower       *tower = ct;
  }
  </code></pre>
  
  <p>display.c:</p>
  
  <pre><code>#include &lt;unistd.h&gt;
  #include &lt;X11/Xlib.h&gt;
  
  //Display-related variables
  Display *display;
  Window   win;
  GC       gc;
  
  
  // Initialize and open the simulator window with size CITY_WIDTH x CITY_HEIGHT.
  void initializeWindow() {
    // Open connection to X server
    display = XOpenDisplay(NULL);
  
    // Create a simple window, set the title and get the graphics context then
    // make is visible and get ready to draw
    win = XCreateSimpleWindow(display,  RootWindow(display, 0), 0, 0,
                  CITY_WIDTH, CITY_HEIGHT, 0, 0x000000, 0xFFFFFF);
    XStoreName(display, win, "Vehicle Simulator");
    gc = XCreateGC(display, win, 0, NULL);
    XMapWindow(display, win);
    XFlush(display);
    usleep(20000);  // sleep for 20 milliseconds.
  }
  
  // Close the display window
  void closeWindow() {
    XFreeGC(display, gc);
    XUnmapWindow(display, win);
    XDestroyWindow(display, win);
    XCloseDisplay(display);
  }
  
  
  // Redraw all the cell towers and all the vehicles that are connected to towers.
  // This code should run in an infinite loop continuously drawing the city.
  // Vehicles are drawn as circles with radius VEHICLE_RADIUS.
  void *showSimulation(void *c) {
    City  *city = c;
  
    // Open the window
    initializeWindow();
  
    // Now keep redrawing until someone kills the thread
    while(1) {
      // Erase the background 
      XSetForeground(display, gc, 0xFFFFFF);
      XFillRectangle(display, win, gc, 0, 0, CITY_WIDTH, CITY_HEIGHT);
  
      // Draw all the cell towers
      for (int i=0; i&lt;city-&gt;numTowers; i++) {
        short r = city-&gt;towers[i].radius;
        XSetForeground(display, gc, city-&gt;towers[i].color);
        for (int b=-3;b&lt;=3; b++)
      XDrawArc(display, win, gc,
           city-&gt;towers[i].x-r+b, city-&gt;towers[i].y-r+b,
           2*(r-b), 2*(r-b), 0, 360*64);
      }
  
      // Draw all the vehicles within each cell tower's range 
      for (int t=0; t&lt;city-&gt;numTowers; t++) {
        for (int i=0; i&lt;MAX_CONNECTIONS; i++) {
      if (city-&gt;towers[t].connectedVehicles[i].connected) {
        XSetForeground(display, gc, city-&gt;towers[t].color);
        XFillArc(display, win, gc,
             city-&gt;towers[t].connectedVehicles[i].x-VEHICLE_RADIUS,
             city-&gt;towers[t].connectedVehicles[i].y-VEHICLE_RADIUS,
             2*VEHICLE_RADIUS, 2*VEHICLE_RADIUS, 0, 360*64);
        XSetForeground(display, gc, 0x000000); // draw a black border
        XDrawArc(display, win, gc,
             city-&gt;towers[t].connectedVehicles[i].x-VEHICLE_RADIUS,
             city-&gt;towers[t].connectedVehicles[i].y-VEHICLE_RADIUS,
             2*VEHICLE_RADIUS, 2*VEHICLE_RADIUS, 0, 360*64);
      }
        }
      }
      XFlush(display);
      usleep(2000);
    }
  
    closeWindow();
    pthread_exit(NULL);
  }
  </code></pre>
  
  <p>Also if anyone has some useful resources for threading, that would also be appreciated!!!</p>