source: npl/mediabox/lcdproc_edwin/src/server/clients.c @ c5c522c

gcc484ntopperl-5.22
Last change on this file since c5c522c was c5c522c, checked in by Edwin Eefting <edwin@datux.nl>, 8 years ago

initial commit, transferred from cleaned syn3 svn tree

  • Property mode set to 100644
File size: 5.0 KB
Line 
1/*
2
3  clients.c
4
5  Inits/shuts down client system,
6  creates/destroys individual clients,
7  enqueues/dequeues messages from clients,
8  and searches for clients in the list.
9
10  :)
11
12 */
13
14#include <stdio.h>
15#include <stdlib.h>
16#include <unistd.h>
17#include <string.h>
18
19#include "clients.h"
20#include "client_data.h"
21#include "../shared/debug.h"
22
23
24
25LL * clients;
26
27// Initialize and kill client list...
28int client_init()
29{
30   debug("client_init()\n");
31   
32   clients = LL_new();
33   if(!clients)
34   {
35      fprintf(stderr, "client_init:  Unable to create client list\n");
36      return -1;
37   }
38
39   return 0;
40}
41
42int client_shutdown()
43{
44   // TODO:  Close all connections first...
45   client *c;
46
47   debug("client_shutdown()\n");
48   
49   
50   // Free all client structures...
51   // Note that the regular list loop doesn't work here, because
52   // client_destroy() calls LL_Remove()
53   for(c = LL_Pop(clients);
54       c;
55       c = LL_Pop(clients))
56   {
57      debug("client_shutdown: ...\n");
58      if(c)
59      {
60         debug("client_shutdown: ... %i ...\n", c->sock);
61         if(0 != client_destroy(c))
62         {
63            fprintf(stderr, "client_shutdown: Error freeing client\n");
64         }
65         else
66         {
67            debug("client_shutdown: Freed client...\n");
68         }
69      }
70      else
71      {
72         debug("client_shutdown: No client!\n");
73      }
74   }
75
76   // Then, free the list...
77   LL_Destroy(clients);
78   
79   debug("client_shutdown: done\n");
80
81   return 0;
82}
83
84
85// Create and destroy clients....
86client * client_create(int sock)
87{
88   client *c;
89
90   debug("client_create(%i)\n", sock);
91
92   // Allocate new client...
93   c = malloc(sizeof(client));
94   if(!c)
95   {
96      fprintf(stderr, "client_create: error allocating new client\n");
97      return NULL;
98   }
99
100   // Init struct members
101   c->sock = 0;
102   c->data = NULL;
103   c->messages = NULL;
104
105
106   c->sock = sock;
107
108   // Set up message list...
109   c->messages = LL_new();
110   if(!c->messages)
111   {
112      fprintf(stderr, "client_create: error allocating message list\n");
113      free(c);
114      return NULL;
115   }
116
117   // TODO:  allocate and init client data...
118   c->data = malloc(sizeof(client_data));
119   if(!c->data)
120   {
121      fprintf(stderr, "client_create: error allocating client data\n");
122      free(c->messages);
123      free(c);
124      return NULL;
125   }
126   else if(client_data_init(c->data) < 0)
127   {
128      return NULL;
129   }
130   
131   // TODO:  Check for errors while adding the client to the list?
132   LL_Push(clients, (void *)c);
133   
134   return c;
135}
136int client_destroy(client *c)
137{
138   // TODO:  Close the socket connection here?
139   int err;
140   
141   char *str;
142
143   debug("client_destroy()\n");
144   
145   if(!c) return -1;
146
147   // Eat the rest of the incoming requests...
148   debug("client_destroy: get_messages\n");
149   while((str = client_get_message(c)))
150   {
151      if(str) {
152         debug("client_destroy: kill message %s\n", str);
153         free(str);
154      }
155   }
156
157   err = LL_Destroy(c->messages);
158
159   // Free client's other data
160   client_data_destroy(c->data);
161   
162/*
163   // FIXME?  Should the connection get closed here or elsewhere?
164   if(c->sock) close(c->sock);
165   c->sock = 0;
166*/
167   
168   // Remove the client from the clients list...
169   LL_Remove(clients, c);
170   
171   free(c);
172
173   return 0;
174}
175
176// Add and remove messages from the client's queue...
177int client_add_message(client *c, char *message)
178{
179   int err = 0;
180   char *dup;
181   char *str, *cp;
182   char delimiters[] = "\n\r\0";
183//   int len;
184
185   //debug("client_add_message(%s)\n", message);
186   
187   if(!c) return -1;
188   if(!message) return -1;
189
190//   len = strlen(message);
191//   if(len < 1) return 0;
192   
193   // Copy the string to avoid overwriting the original...
194   dup = strdup(message);
195   if(!dup)
196   {
197      fprintf(stderr, "client_add_message: Error allocating new string\n");
198      return -1;
199   }
200
201   // Now split the string into lines and enqueue each one...
202   for(str = strtok(dup, delimiters); str; str=strtok(NULL, delimiters))
203   {
204      cp = strdup(str);
205      debug("client_add_message: %s\n", cp);
206      err += LL_Enqueue(c->messages, (void *)cp);
207   }
208
209   //debug("client_add_message(%s): %i errors\n", message, err);
210   free(dup);  // Fixed memory leak...
211   
212   // Err is the number of errors encountered...
213   return err;
214   
215}
216// Woo-hoo!  A simple function.  :)
217char * client_get_message(client *c)
218{
219   char *str;
220
221   //debug("client_get_message()\n");
222
223   if(!c) return NULL;
224   
225   str = (char *)LL_Dequeue(c->messages);
226
227   //debug("client_get_message:  \"%s\"\n", str);
228   
229   return str;
230}
231
232// Get and set the client's data...
233int client_set(client *c, void *data)
234{
235   // You know, I really doubt this function will be useful...
236   return 0;
237}
238void * client_get(client *c)
239{
240   // But this one might be handy...
241
242   return NULL;
243}
244
245
246client * client_find_sock(int sock)
247{
248   client * c;
249
250//   debug("client_find_sock(%i)\n", sock);
251
252   LL_Rewind(clients);
253   do{
254      c = (client *)LL_Get(clients);
255//      debug("client_find_sock: ... %i ...\n", c->sock);
256      if(c->sock == sock)
257      {
258//       debug("client_find_sock: ..! %i !..\n", c->sock);
259         return c;
260      }
261   } while(LL_Next(clients) == 0);
262
263   debug("client_find_sock: failed\n");
264   
265   return NULL;
266}
Note: See TracBrowser for help on using the repository browser.