network.c 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192
  1. /* $Id: network.c,v 1.11 2001/04/28 15:29:25 kilobug Exp $ */
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <unistd.h>
  5. #include <server.h>
  6. #include <network.h>
  7. #include <pulsarnet.h>
  8. #include <general.h>
  9. #include <private.h>
  10. #include <action.h>
  11. void gfx_trash_client(net_type_t get, net_type_t wanted, void *data)
  12. {
  13. gfx_client_t *cl;
  14. cl = data;
  15. fprintf(stderr, "Network warning: reading %s, wanted %s.\n",
  16. net_type_name(get), net_type_name(wanted));
  17. close(cl->sock);
  18. cl->alive = False;
  19. }
  20. boolean_t gfx_get_ack(gfx_client_t *cl)
  21. {
  22. gfx_t *gfx;
  23. fflush(cl->wsock);
  24. gfx = gl_config->gfx_clients;
  25. if (!net_wait_ack(cl->sock))
  26. {
  27. gfx_trash_client(net_type_none, net_type_int, cl);
  28. return False;
  29. }
  30. return True;
  31. }
  32. void gfx_write_object(FILE *file, item_t *obj)
  33. {
  34. net_wr_float(file, obj->obj.x);
  35. net_wr_float(file, obj->obj.y);
  36. net_wr_int(file, obj->obj.team_id);
  37. if (obj->obj.type == obj_akx)
  38. {
  39. net_wr_int(file, obj->akx.action.type);
  40. switch (obj->akx.action.type)
  41. {
  42. case act_akx_move:
  43. break;
  44. case act_akx_pulse:
  45. net_wr_float(file, obj->akx.action.act.pulse.angle);
  46. net_wr_float(file, obj->akx.action.act.pulse.x);
  47. net_wr_float(file, obj->akx.action.act.pulse.y);
  48. break;
  49. case act_akx_link:
  50. net_wr_int(file, obj->akx.action.act.link.target_id);
  51. break;
  52. }
  53. }
  54. }
  55. static boolean_t gfx_do_send_updates(void *data, void *foo)
  56. {
  57. GSList *l;
  58. player_t *play;
  59. item_t *obj;
  60. int i;
  61. gfx_client_t *cl;
  62. cl = data;
  63. if (cl == NULL)
  64. {
  65. return True;
  66. }
  67. if (!cl->alive)
  68. {
  69. return True;
  70. }
  71. net_set_error_handler(gfx_trash_client, cl);
  72. net_wr_string(cl->wsock, "TRN");
  73. net_wr_int(cl->wsock, gl_config->turn_num);
  74. if (!gfx_get_ack(cl))
  75. {
  76. return False;
  77. }
  78. for (l = gl_config->players ; l != NULL ; l = l->next)
  79. {
  80. net_wr_string(cl->wsock, "UPL");
  81. play = l->data;
  82. net_wr_int(cl->wsock, play->team_id);
  83. net_wr_float(cl->wsock, play->score);
  84. }
  85. net_wr_string(cl->wsock, "END");
  86. if (!gfx_get_ack(cl))
  87. {
  88. return False;
  89. }
  90. for (i = 0 ; i < gl_config->nb_objects ; i++)
  91. {
  92. if (gl_objects[i].obj.change)
  93. {
  94. net_wr_string(cl->wsock, "UOB");
  95. obj = gl_objects + i;
  96. net_wr_int(cl->wsock, obj->obj.id);
  97. gfx_write_object(cl->wsock, obj);
  98. }
  99. }
  100. net_wr_string(cl->wsock, "END");
  101. if (!gfx_get_ack(cl))
  102. {
  103. return False;
  104. }
  105. return True;
  106. }
  107. static void gfx_send_updates(void *data, void *foo)
  108. {
  109. gfx_client_t *cl;
  110. if (!gfx_do_send_updates(data, foo))
  111. {
  112. cl = data;
  113. cl->alive = False;
  114. }
  115. }
  116. static void gfx_send_goodbye(void *data, void *foo)
  117. {
  118. gfx_client_t *cl;
  119. cl = data;
  120. net_wr_string(cl->wsock, "BYE");
  121. fflush(cl->wsock);
  122. net_wait_ack(cl->sock);
  123. }
  124. void gfx_client_new_turn(boolean_t last)
  125. {
  126. gfx_t *gfx;
  127. int i;
  128. if (!gl_config->gfx)
  129. {
  130. return;
  131. }
  132. gfx = gl_config->gfx_clients;
  133. i = net_chk_str_list(gfx->master, "GO", "END", NULL);
  134. if (i == -1)
  135. {
  136. fprintf(stderr, "Protocol error.\n");
  137. exit(0);
  138. }
  139. net_send_ack(gfx->wmaster);
  140. net_set_error_handler(NULL, NULL);
  141. if ((i == 0) && (!last))
  142. {
  143. while (gfx_new_client(gfx->sock, False))
  144. {
  145. }
  146. g_slist_foreach(gfx->clients, gfx_send_updates, NULL);
  147. }
  148. else
  149. {
  150. g_slist_foreach(gfx->clients, gfx_send_goodbye, NULL);
  151. exit(0);
  152. }
  153. }
  154. static void gfx_clean()
  155. {
  156. close(gl_config->gfx_clients->sock);
  157. }
  158. void gfx_init()
  159. {
  160. if (!gl_config->gfx)
  161. {
  162. return;
  163. gl_config->gfx_clients = NULL;
  164. }
  165. gl_config->gfx_clients = malloc(sizeof(*(gl_config->gfx_clients)));
  166. gl_config->gfx_clients->master = 0;
  167. gl_config->gfx_clients->wmaster = NULL;
  168. gl_config->gfx_clients->clients = NULL;
  169. gl_config->gfx_clients->sock = net_listen_at(gl_config->port, 15,
  170. NULL, 0);
  171. atexit(gfx_clean);
  172. while (!gfx_new_client(gl_config->gfx_clients->sock, True))
  173. {
  174. }
  175. }