Changeset - f6e991030a70
[Not reviewed]
default
0 1 0
Nathan Brink (binki) - 15 years ago 2010-07-31 00:56:13
ohnobinki@ohnopublishing.net
tabletennis_del_client() actually deletes the client if it's not at the front of one of the PING or PONG queues (fixing a segfault).
1 file changed with 1 insertions and 1 deletions:
0 comments (0 inline, 0 general)
src/server/tabletennis.c
Show inline comments
 
@@ -126,97 +126,97 @@ int tabletennis_serve(tabletennis_t tabl
 

	
 
	  q_enqueue(tabletennis->clients_to_ping, client, 0);
 
	}
 
    }
 

	
 
  /* for tabletennis_add_client() */
 
  memcpy(&tabletennis->time_last_check, &time_now, sizeof(struct timespec));
 

	
 
  return 0;
 
}
 

	
 
/**
 
 * helper for tabletennis_del_client() which just looks for a
 
 * particular pointer in the queue (a.k.a., list).
 
 */
 
static int tabletennis_del_client_traverse(void *trav_data, void *client)
 
{
 
  if(trav_data == client)
 
    return FALSE;
 

	
 
  return TRUE;
 
}
 

	
 
int tabletennis_del_client(tabletennis_t tabletennis, struct distrend_client *client)
 
{
 
  list_t thelist;
 

	
 
  thelist = NULL;
 
  switch(client->tabletennis_client.state)
 
    {
 
    case TABLETENNIS_NEED_PING:
 
      thelist = tabletennis->clients_to_ping;
 
      break;
 

	
 
    case TABLETENNIS_NEED_PONG:
 
    case TABLETENNIS_HAS_PONG:
 
      thelist = tabletennis->clients_need_pong;
 
      break;
 

	
 
    case TABLETENNIS_DELINQUENT:
 
      thelist = NULL;
 
      break;
 
    }
 

	
 
  if(!thelist)
 
    return 0;
 

	
 
  list_traverse(thelist, (void *)client, (list_traverse_func_t)&tabletennis_del_client_traverse,
 
		LIST_FORW | LIST_FRNT | LIST_SAVE);
 
		LIST_FORW | LIST_FRNT | LIST_ALTR);
 
  if(list_curr(thelist) == client)
 
    list_remove_curr(thelist);
 

	
 
  return 0;
 
}
 

	
 
void tabletennis_free(tabletennis_t tabletennis)
 
{
 
  q_free(tabletennis->clients_to_ping, LIST_NODEALLOC);
 
  q_free(tabletennis->clients_need_pong, LIST_NODEALLOC);
 

	
 
  free(tabletennis);
 
}
 

	
 
/* implementations of locals */
 

	
 
/**
 
 * Handles a DISTREN_REQUEST_PING from a client.
 
 *
 
 * @todo throttling?
 
 */
 
static int tabletennis_ping_request_handle(struct general_info *geninfo, struct distrend_client *client, struct distren_request *req, void *req_data)
 
{
 
  struct distren_request *pong_req;
 

	
 
  if(req->len > 32)
 
    distrend_send_disconnect(client, "You have tried to send a PING packet with a length longer than 32 bytes.");
 

	
 
  /**
 
      respond to the client using the data he sent in his PONG
 
      command.
 
   */
 
  distren_request_new(&pong_req, req->len, DISTREN_REQUEST_PONG);
 
  distrend_client_write_request(client, pong_req, req_data);
 
  distren_request_free(pong_req);
 

	
 
  return 0;
 
}
 

	
 
static int tabletennis_pong_request_handle(struct general_info *geninfo, struct distrend_client *client, struct distren_request *req, void *req_data)
 
{
 
  fprintf(stderr, "got pong\n");
 

	
 
  /*
 
   * The only place that sends PINGs from distrend is
 
   * tabletennis_serve() and it uses
 
   * client->tabletennis_client.time_next_check as the cookie.
 
   */
0 comments (0 inline, 0 general)