Annotation of Amaya/amaya/AHTBridge.c, revision 1.99
1.9 cvs 1: /*
2: *
1.93 vatton 3: * (c) COPYRIGHT INRIA and W3C, 1996-2004
1.9 cvs 4: * Please first read the full copyright statement in file COPYRIGHT.
5: *
6: */
1.75 cvs 7:
1.14 cvs 8: /*
9: * AHTBridge.c : This module implements the callback setup and
10: * handlers between the Xt, libwww, and Amaya procedures. It's responsible
11: * for assigning, modifying, and supressing Xt events to the active
12: * requests.
13: *
14: * Author: J Kahan
1.67 cvs 15: * J. K./R. Guetari. Windows NT/95 routines
1.79 cvs 16: * J. K./S. Gully GTK routines
1.14 cvs 17: *
18: */
1.94 gully 19:
20: #if defined(_GTK)
1.85 gully 21: #include <glib.h>
1.68 cvs 22: #endif /* _GTK */
23:
1.94 gully 24: #ifdef _WX
25: #include "wxAmayaTimer.h"
26: #include "wxAmayaSocketEvent.h"
27: #endif /* _WX */
28:
1.16 cvs 29: #define THOT_EXPORT extern
1.4 cvs 30: #include "amaya.h"
1.10 cvs 31: #include "AHTBridge_f.h"
32: #include "AHTFWrite_f.h"
33: #include "query_f.h"
34: #include "answer_f.h"
1.64 cvs 35: #include "HTEvtLst.h"
1.4 cvs 36:
1.58 cvs 37: #if 0
38: #define DEBUG_LIBWWW
39: #define THD_TRACE 1
40: #endif
41:
1.96 vatton 42: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.85 gully 43: /* Private functions */
44: static void RequestRegisterReadXtevent (SOCKET);
45: static void RequestKillReadXtevent (SOCKET);
46: static void RequestRegisterWriteXtevent ( SOCKET);
47: static void RequestKillWriteXtevent (SOCKET);
48: static void RequestRegisterExceptXtevent ( SOCKET);
49: static void RequestKillExceptXtevent (SOCKET);
1.96 vatton 50: #endif /* #if defined(_GTK) */
1.24 cvs 51:
1.32 cvs 52: /* Private variables */
1.4 cvs 53:
54: /*
1.58 cvs 55: * this set of HTEventType map our WinSock "socket event HTEventType" into
1.4 cvs 56: * our read and write sets. Note that under the canonical Unix model,
57: * a non-blocking socket passed to an accept() call will appear as readable,
58: * whilst a non-blocking call to connect() will appear as writeable. In add.
59: * if the connection has been closed, the socket will appear readable under
60: * BSD Unix semantics
61: */
1.32 cvs 62:
1.91 gully 63: static const HTEventType ReadBits = (HTEventType)(HTEvent_READ | HTEvent_ACCEPT | HTEvent_CLOSE);
64: static const HTEventType WriteBits = (HTEventType)(HTEvent_WRITE | HTEvent_CONNECT);
65: static const HTEventType ExceptBits = (HTEventType)HTEvent_OOB;
1.58 cvs 66:
1.94 gully 67: #if defined(_GTK)
1.85 gully 68: typedef struct sStatus {
69: gint read; /* the different GTK Id's */
70: gint write;
71: gint except;
72: } SocketStatus;
1.79 cvs 73: #endif /* _GTK */
1.94 gully 74: #if defined(_WX)
75: typedef struct sStatus {
76: int read;
77: int write;
78: int except;
79: } SocketStatus;
80: #endif /* _WX */
81: #if defined(_NOGUI)
1.85 gully 82: typedef struct sStatus {
83: int read;
84: int write;
85: int except;
86: } SocketStatus;
1.88 cvs 87: #endif /* #ifdef _NOGUI */
1.96 vatton 88: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.89 cvs 89: #define SOCK_TABLE_SIZE 67
90: #define HASH(s) ((s) % SOCK_TABLE_SIZE)
91: static SocketStatus persSockets[SOCK_TABLE_SIZE];
1.96 vatton 92: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.4 cvs 93:
1.10 cvs 94: /*--------------------------------------------------------------------
95: AHTCallback_bridge
1.11 cvs 96: this function acts as a bridge between Xt and libwww. From the Xt
97: point of view, this function is the callback handler whenever there's
98: any activity on the sockets associated with the active requests. From
99: the libwww point of view, this is the function that takes the initiative
100: to invoke the callback function associated with an active request,
101: whenever there's an activity in the socket associated to it.
102: In this latter aspect, this function is similar to the library's
103: own __DoCallback() function.
104: Upon activation, the function looks up the request associated with the
105: active socket and then looks up the cbf associated with that request.
106: Upon completion of the execution of the request's cbf, it verifies
107: the state of the request and, if it's an asynchronous request, deletes
108: the memory allocated to it.
1.10 cvs 109: -------------------------------------------------------------------*/
1.80 kahan 110: void *AHTCallback_bridge (caddr_t cd, int *s, XtInputId * id)
1.4 cvs 111: {
1.96 vatton 112: return (0);
1.4 cvs 113: }
1.85 gully 114:
1.94 gully 115: #if defined(_GTK)
1.79 cvs 116: static void AHTCallback_bridgeGTK (gpointer data, gint source, GdkInputCondition condition)
117: {
118: int status; /* the status result of the libwwww call */
119: HTEventType type = HTEvent_ALL;
120: int v;
121: int socket;
122: ms_t now = HTGetTimeInMillis();
123:
124: socket = (SOCKET) data;
125: v = HASH (socket);
126:
127: /* convert the FD into an HTEventType which will allow us to find the
128: request associated with the socket */
129:
130: /* I could send some other data here, like the event itself, right */
131: switch (condition)
132: {
133: case GDK_INPUT_READ:
134: type = HTEvent_READ;
135: break;
136: case GDK_INPUT_WRITE:
137: type = HTEvent_WRITE;
138: break;
139: case GDK_INPUT_EXCEPTION:
140: type = HTEvent_OOB;
141: break;
142: default:
143: type = HTEvent_ALL;
144: break;
145: } /* switch */
146:
147: /* Invokes the callback associated to the requests */
148:
149: /** CanDoStop_set (FALSE); **/
150: if ((status = HTEventList_dispatch (socket, type, now)) != HT_OK)
151: {
152: #ifdef DEBUG_LIBWWW
153: HTTrace ("Callback.... returned a value != HT_OK");
154: #endif
155: }
156: /*** CanDoStop_set (TRUE); **/
157: }
1.94 gully 158: #endif /* _GTK */
159:
160:
161: #if defined(_WX)
162: static void AHTCallback_bridgeWX ( int register_id, int socket, wxAmayaSocketCondition condition)
163: {
164: int status; /* the status result of the libwwww call */
165: HTEventType type = HTEvent_ALL;
166: int v;
167: ms_t now = HTGetTimeInMillis();
168:
169: v = HASH (socket);
170:
171: /* convert the FD into an HTEventType which will allow us to find the
172: request associated with the socket */
173:
174: /* I could send some other data here, like the event itself, right */
175: switch (condition)
176: {
177: case WXAMAYASOCKET_READ:
178: type = HTEvent_READ;
179: break;
180: case WXAMAYASOCKET_WRITE:
181: type = HTEvent_WRITE;
182: break;
183: case WXAMAYASOCKET_EXCEPTION:
184: type = HTEvent_OOB;
185: break;
186: default:
187: type = HTEvent_ALL;
188: break;
189: } /* switch */
190:
191: /* Invokes the callback associated to the requests */
192:
193: /** CanDoStop_set (FALSE); **/
194: if ((status = HTEventList_dispatch (socket, type, now)) != HT_OK)
195: {
196: #ifdef DEBUG_LIBWWW
197: HTTrace ("Callback.... returned a value != HT_OK");
198: #endif
199: }
200: /*** CanDoStop_set (TRUE); **/
201: }
202: #endif /* _WX */
1.41 cvs 203:
204: /*--------------------------------------------------------------------
205: ProcessTerminateRequest
206: This function is called whenever a request has ended. If the requested
207: ended normally, the function will call any callback associated to the
208: request. Otherwise, it will just mark the request as over.
209: -------------------------------------------------------------------*/
1.82 vatton 210: void ProcessTerminateRequest (HTRequest *request, HTResponse *response,
211: void *param, int status)
1.41 cvs 212: {
1.91 gully 213: AHTReqContext *me = (AHTReqContext *)HTRequest_context (request);
1.56 cvs 214:
1.58 cvs 215: /* choose a correct treatment in function of the request's
1.41 cvs 216: being associated with an error, with an interruption, or with a
217: succesful completion */
1.64 cvs 218:
219: #ifdef DEBUG_LIBWWW
220: if (THD_TRACE)
1.82 vatton 221: fprintf (stderr,"ProcessTerminateRequest: processing req %p, url %s,\
222: status %d\n", me, me->urlName, me->reqStatus);
1.64 cvs 223: #endif /* DEBUG_LIBWWW */
1.83 kahan 224: if (me->reqStatus == HT_END)
1.41 cvs 225: {
1.58 cvs 226: if (AmayaIsAlive () && me->terminate_cbf)
1.82 vatton 227: (*me->terminate_cbf) (me->docid, 0, me->urlName, me->outputfile,
228: &(me->http_headers), me->context_tcbf);
1.58 cvs 229:
1.41 cvs 230: }
1.42 cvs 231: else if (me->reqStatus == HT_ABORT)
1.41 cvs 232: /* either the application ended or the user pressed the stop
233: button. We erase the incoming file, if it exists */
234: {
1.52 cvs 235: if (AmayaIsAlive () && me->terminate_cbf)
1.82 vatton 236: (*me->terminate_cbf) (me->docid, -1, me->urlName, me->outputfile,
237: &(me->http_headers), me->context_tcbf);
1.78 cvs 238: if (me->outputfile && me->outputfile[0] != EOS)
1.41 cvs 239: {
1.70 cvs 240: TtaFileUnlink (me->outputfile);
1.78 cvs 241: me->outputfile[0] = EOS;
1.70 cvs 242: }
1.41 cvs 243: }
1.83 kahan 244: else if (me->reqStatus == HT_ERR)
1.41 cvs 245: {
246: /* there was an error */
1.90 gully 247: if (AmayaIsAlive () && me->terminate_cbf)
1.82 vatton 248: (*me->terminate_cbf) (me->docid, -2, me->urlName, me->outputfile,
249: &(me->http_headers), me->context_tcbf);
1.41 cvs 250:
1.78 cvs 251: if (me->outputfile && me->outputfile[0] != EOS)
1.41 cvs 252: {
1.70 cvs 253: TtaFileUnlink (me->outputfile);
1.78 cvs 254: me->outputfile[0] = EOS;
1.41 cvs 255: }
256: }
1.58 cvs 257:
1.41 cvs 258: /* we erase the context if we're dealing with an asynchronous request */
1.61 cvs 259: if ((me->mode & AMAYA_ASYNC)
260: || (me->mode & AMAYA_IASYNC))
1.58 cvs 261: {
1.63 cvs 262: Document doc = me->docid;
1.58 cvs 263: me->reqStatus = HT_END;
264: /*** @@@ do we need this? yes!! **/
265: AHTLoadTerminate_handler (request, response, param, status);
266: AHTReqContext_delete (me);
1.63 cvs 267: AHTPrintPendingRequestStatus (doc, YES);
1.58 cvs 268: }
269: }
1.4 cvs 270:
1.92 cvs 271: #ifdef _WINGUI
1.29 cvs 272: /*----------------------------------------------------------------
1.32 cvs 273: WIN_Activate_Request
1.29 cvs 274: when there are more open requests than available sockets, the
275: requests are put in a "pending state." When a socket becomes
276: available, libwww associates it with a pending request and then
277: calls this callback function. This function is responsible for
278: opening the temporary file where the GET and POST results
279: will be stored. The function is also responsible for
280: registering the socket with the Xt event loop.
281: Consult the libwww manual for more details on the signature
282: of this function.
283: ----------------------------------------------------------------*/
1.97 vatton 284: int WIN_Activate_Request (HTRequest * request, HTAlertOpcode op,
285: int msgnum, const char *dfault, void *input,
286: HTAlertPar * reply)
1.29 cvs 287: {
288: AHTReqContext *me = HTRequest_context (request);
289:
1.58 cvs 290: if (me->reqStatus == HT_NEW)
291: {
292: if (!(me->output)
293: && (me->output != stdout)
294: && me->outputfile
1.99 ! cvs 295: && ((me->output = TtaWriteOpen (me->outputfile)) == NULL))
1.97 vatton 296: {
1.58 cvs 297: /* the request is associated with a file */
1.78 cvs 298: me->outputfile[0] = EOS; /* file could not be opened */
1.97 vatton 299: TtaSetStatus (me->docid, 1,
300: TtaGetMessage (AMAYA, AM_CANNOT_CREATE_FILE), me->outputfile);
1.58 cvs 301: me->reqStatus = HT_ERR;
302:
303: if (me->error_html)
1.97 vatton 304: /* so we can show the error message */
305: DocNetworkStatus[me->docid] |= AMAYA_NET_ERROR;
1.58 cvs 306: }
307: else
308: {
309: #ifdef DEBUG_LIBWWW
310: if (THD_TRACE)
311: fprintf (stderr, "WIN_Activate_Request: Activating pending %s. "
312: "Open fd %d\n", me->urlName, (int) me->output);
313: #endif /* DEBUG_LIBWWW */
1.97 vatton 314: HTRequest_setOutputStream (me->request,
315: AHTFWriter_new (me->request, me->output, YES));
1.58 cvs 316: /*change the status of the request */
317: me->reqStatus = HT_WAITING;
318: }
319: }
320: else if (me->reqStatus == HT_WAITING)
321: {
322: /*change the status of the request */
323: rewind (me->output);
324: if (HTRequest_outputStream (me->request) == NULL)
325: HTRequest_setOutputStream (me->request, AHTFWriter_new (me->request, me->output, YES));
326: }
1.32 cvs 327: else {
1.36 cvs 328: me->reqStatus = HT_ERR;
1.32 cvs 329: }
330:
1.36 cvs 331: return ((me->reqStatus != HT_ERR) ? HT_OK : HT_ERROR);
1.32 cvs 332: }
333:
1.92 cvs 334: #endif /* _WINGUI */
1.60 cvs 335:
1.11 cvs 336: /*----------------------------------------------------------------------
337: AHTEvent_register
338: callback called by libwww whenever a socket is open and associated
339: to a request. It sets the pertinent Xt events so that the Xt Event
340: loops gets an interruption whenever there's action of the socket.
341: In addition, it registers the request with libwww.
342: ----------------------------------------------------------------------*/
1.58 cvs 343: int AHTEvent_register (SOCKET sock, HTEventType type, HTEvent *event)
1.4 cvs 344: {
1.85 gully 345: int status = 0;
1.7 cvs 346:
1.40 cvs 347: if (sock == INVSOC)
348: {
1.36 cvs 349: #ifdef DEBUG_LIBWWW
1.58 cvs 350: fprintf(stderr, "AHTEvent_register: sock = INVSOC\n");
1.37 cvs 351: #endif /* DEBUG_LIBWWW */
1.58 cvs 352: return (0);
353: }
1.43 cvs 354:
1.96 vatton 355: #if defined(_GTK) || defined(_WX)
1.94 gully 356: /* need something special for HTEvent_CLOSE */
1.58 cvs 357: if (type & ReadBits)
358: RequestRegisterReadXtevent (sock);
359:
360: if (type & WriteBits)
361: RequestRegisterWriteXtevent (sock);
362:
363: if (type & ExceptBits)
364: RequestRegisterExceptXtevent (sock);
1.96 vatton 365: #endif /* defined(_GTK) || defined(_WX) */
1.94 gully 366: #ifdef _WINDOWS
1.50 cvs 367: /* under windows, libwww requires an explicit FD_CLOSE registration
1.58 cvs 368: to detect HTTP responses not having a Content-Length header */
1.95 cvs 369: status = HTEventList_register (sock, (HTEventType)(type | HTEvent_CLOSE) , event);
1.94 gully 370: #endif /* _WINDOWS */
371: #if defined(_UNIX)
1.58 cvs 372: status = HTEventList_register (sock, type, event);
1.94 gully 373: #endif /* #if defined(_UNIX) */
1.96 vatton 374:
1.58 cvs 375: return (status);
376: }
1.50 cvs 377:
1.34 cvs 378: /*----------------------------------------------------------------------
379: AHTEvent_unregister
380: callback called by libwww each time a request is unregistered. This
381: function takes care of unregistering the pertinent Xt events
382: associated with the request's socket. In addition, it unregisters
383: the request from libwww.
384: ----------------------------------------------------------------------*/
1.58 cvs 385: int AHTEvent_unregister (SOCKET sock, HTEventType type)
1.34 cvs 386: {
1.58 cvs 387: int status;
1.76 kahan 388:
389: if (sock == INVSOC)
390: return HT_OK;
1.38 cvs 391:
1.96 vatton 392: #if defined(_GTK) || defined(_WX)
1.58 cvs 393: /* remove the Xt event hooks */
394: if (type & ReadBits)
395: RequestKillReadXtevent (sock);
396:
397: if (type & WriteBits)
398: RequestKillWriteXtevent (sock);
399:
400: if (type & ExceptBits)
401: RequestKillExceptXtevent (sock);
1.96 vatton 402: #endif /* #if defined(_GTK) || defined(_WX) */
1.35 cvs 403:
1.58 cvs 404: /* @@@ if this is the default for windows, no need to have AHTEvent_..
405: in windows!! */
406: /* call libwww's default routine */
407: status = HTEventList_unregister (sock, type);
1.7 cvs 408: return (status);
1.4 cvs 409: }
1.35 cvs 410:
1.58 cvs 411: /* Private functions */
412:
1.11 cvs 413: /*----------------------------------------------------------------------
414: RequestKillAllXtevents
415: front-end for kill all Xt events associated with the request pointed
416: to by "me".
417: ----------------------------------------------------------------------*/
1.79 cvs 418: void RequestKillAllXtevents (AHTReqContext * me)
1.4 cvs 419: {
1.96 vatton 420: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 421: int sock = INVSOC;
422:
423: return;
424: /* @@@ what to do with this one? @@@ */
425: if (me->read_sock != INVSOC)
426: sock = me->read_sock;
427: else
428: if (me->write_sock != INVSOC)
429: sock = me->write_sock;
430: else
431: if (me->except_sock != INVSOC)
432: sock = me->except_sock;
433:
434: #ifdef DEBUG_LIBWWW
1.7 cvs 435: if (THD_TRACE)
1.58 cvs 436: fprintf (stderr, "RequestKillAllXtEvents: Clearing XtInputs\n");
437: #endif /* DEBUG_LIBWWW */
1.4 cvs 438:
1.58 cvs 439: RequestKillReadXtevent (sock);
440: RequestKillWriteXtevent (sock);
441: RequestKillExceptXtevent (sock);
1.96 vatton 442: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.4 cvs 443: }
444:
1.11 cvs 445: /*----------------------------------------------------------------------
1.18 cvs 446: RequestRegisterReadXtevent
447: Registers with Xt the read events associated with socket sock
448: ----------------------------------------------------------------------*/
1.79 cvs 449: static void RequestRegisterReadXtevent (SOCKET sock)
1.18 cvs 450: {
1.96 vatton 451: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 452: int v;
453:
454: v = HASH (sock);
455: if (!persSockets[v].read)
1.18 cvs 456: {
1.94 gully 457: #if defined(_GTK)
1.96 vatton 458: persSockets[v].read = gdk_input_add ((gint) sock,
459: GDK_INPUT_READ,
460: AHTCallback_bridgeGTK,
461: (gpointer) sock);
1.94 gully 462: #endif /* _GTK */
463: #if defined(_WX)
1.96 vatton 464: persSockets[v].read = wxAmayaSocketEvent::RegisterSocket( sock,
1.94 gully 465: WXAMAYASOCKET_READ,
466: AHTCallback_bridgeWX );
467: #endif /* _WX */
1.79 cvs 468:
1.58 cvs 469: #ifdef DEBUG_LIBWWW
1.18 cvs 470: if (THD_TRACE)
1.58 cvs 471: fprintf (stderr, "RegisterReadXtEvent: adding XtInput %lu Socket %d\n",
472: persSockets[v].read, sock);
473: #endif /* DEBUG_LIBWWW */
1.18 cvs 474: }
1.96 vatton 475: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.18 cvs 476: }
477:
478: /*----------------------------------------------------------------------
1.11 cvs 479: RequestKillReadXtevent
480: kills any read Xt event associated with the request pointed to by "me".
481: ----------------------------------------------------------------------*/
1.79 cvs 482: static void RequestKillReadXtevent (SOCKET sock)
1.4 cvs 483: {
1.96 vatton 484: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 485: int v;
486:
487: v = HASH (sock);
488: if (persSockets[v].read)
489: {
490: #ifdef DEBUG_LIBWWW
491: if (THD_TRACE)
492: fprintf (stderr, "UnregisterReadXtEvent: Clearing XtInput %lu\n",
493: persSockets[v].read);
494: #endif /* DEBUG_LIBWWW */
1.85 gully 495:
1.94 gully 496: #if defined(_GTK)
1.79 cvs 497: gdk_input_remove (persSockets[v].read);
498: persSockets[v].read = (gint) 0;
499: #endif /* !_GTK */
1.94 gully 500: #if defined(_WX)
501: wxAmayaSocketEvent::UnregisterSocket( persSockets[v].read );
502: persSockets[v].read = 0;
503: #endif /* _WX */
504:
1.58 cvs 505: }
1.96 vatton 506: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.18 cvs 507: }
508:
509: /*----------------------------------------------------------------------
510: RequestRegisterWriteXtevent
511: Registers with Xt the write events associated with socket sock
512: ----------------------------------------------------------------------*/
1.79 cvs 513: static void RequestRegisterWriteXtevent (SOCKET sock)
1.18 cvs 514: {
1.96 vatton 515: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 516: int v;
1.96 vatton 517:
1.58 cvs 518: v = HASH (sock);
519: if (!persSockets[v].write)
520: {
1.94 gully 521: #if defined(_GTK)
1.96 vatton 522: persSockets[v].write = gdk_input_add ((gint) sock,
523: GDK_INPUT_WRITE,
524: AHTCallback_bridgeGTK,
525: (gpointer) sock);
1.94 gully 526: #endif /* _GTK */
527: #if defined(_WX)
1.96 vatton 528: persSockets[v].write = wxAmayaSocketEvent::RegisterSocket( sock,
1.94 gully 529: WXAMAYASOCKET_WRITE,
530: AHTCallback_bridgeWX );
531: #endif /* _WX */
1.79 cvs 532:
1.58 cvs 533: #ifdef DEBUG_LIBWWW
1.18 cvs 534: if (THD_TRACE)
1.58 cvs 535: fprintf (stderr, "RegisterWriteXtEvent: Adding XtInput %lu Socket %d\n",
536: persSockets[v].write, sock);
537: #endif /* DEBUG_LIBWWW */
538:
539: }
1.96 vatton 540: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.4 cvs 541: }
542:
1.11 cvs 543: /*----------------------------------------------------------------------
544: RequestKillWriteXtevent
545: kills any write Xt event associated with the request pointed to
546: by "me".
547: ----------------------------------------------------------------------*/
1.79 cvs 548: static void RequestKillWriteXtevent (SOCKET sock)
1.4 cvs 549: {
1.96 vatton 550: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 551: int v;
552:
553: v = HASH (sock);
554: if (persSockets[v].write)
555: {
556: #ifdef DEBUG_LIBWWW
557: if (THD_TRACE)
558: fprintf (stderr, "UnRegisterWriteXtEvent: Clearing Write XtInputs "
559: "%lu\n",
560: persSockets[v].write);
561: #endif /* DEBUG_LIBWWW */
1.85 gully 562:
1.94 gully 563: #if defined(_GTK)
1.79 cvs 564: gdk_input_remove (persSockets[v].write);
565: persSockets[v].write = (gint) 0;
1.85 gully 566: #endif /* _GTK */
1.94 gully 567: #if defined(_WX)
568: wxAmayaSocketEvent::UnregisterSocket( persSockets[v].write );
569: persSockets[v].write = 0;
570: #endif /* _WX */
571:
1.58 cvs 572: }
1.96 vatton 573: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.18 cvs 574: }
575:
576: /*----------------------------------------------------------------------
577: RequestRegisterExceptXtevent
578: Registers with Xt the except events associated with socket sock
579: ----------------------------------------------------------------------*/
1.79 cvs 580: static void RequestRegisterExceptXtevent (SOCKET sock)
1.18 cvs 581: {
1.96 vatton 582: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 583: int v;
584:
585: v = HASH (sock);
586: if (!persSockets[v].except)
1.18 cvs 587: {
1.94 gully 588: #if defined(_GTK)
1.96 vatton 589: persSockets[v].except = gdk_input_add ((gint) sock,
590: GDK_INPUT_EXCEPTION,
591: AHTCallback_bridgeGTK,
592: (gpointer) sock);
1.85 gully 593: #endif /* _GTK */
1.94 gully 594: #if defined(_WX)
595: persSockets[v].except =
596: wxAmayaSocketEvent::RegisterSocket( sock,
597: WXAMAYASOCKET_EXCEPTION,
598: AHTCallback_bridgeWX );
599: #endif /* _WX */
600:
601: #ifdef DEBUG_LIBWWW
1.58 cvs 602: if (THD_TRACE)
603: fprintf (stderr, "RegisterExceptXtEvent: adding XtInput %lu Socket %d\n",
604: persSockets[v].except, sock);
605: #endif /* DEBUG_LIBWWW */
1.18 cvs 606: }
1.96 vatton 607: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.4 cvs 608: }
609:
1.11 cvs 610: /*----------------------------------------------------------------------
611: RequestKillExceptXtevent
612: kills any exception Xt event associated with the request pointed to
613: by "me".
614: ----------------------------------------------------------------------*/
1.79 cvs 615: static void RequestKillExceptXtevent (SOCKET sock)
1.4 cvs 616: {
1.96 vatton 617: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 618: int v;
619:
620: v = HASH (sock);
621: if (persSockets[v].except)
622: {
623: #ifdef DEBUG_LIBWWW
624: if (THD_TRACE)
625: fprintf (stderr, "UnregisterExceptXtEvent: Clearing Except XtInputs "
626: "%lu\n", persSockets[v].except);
627: #endif /* DEBUG_LIBWWW */
1.85 gully 628:
1.94 gully 629: #if defined(_GTK)
1.79 cvs 630: gdk_input_remove (persSockets[v].except);
631: persSockets[v].except = (gint) 0;
1.85 gully 632: #endif /* _GTK */
1.94 gully 633: #if defined(_WX)
634: wxAmayaSocketEvent::UnregisterSocket( persSockets[v].except );
635: persSockets[v].except = 0;
636: #endif /* _WX */
1.58 cvs 637: }
1.96 vatton 638: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.58 cvs 639: }
640:
641: /*----------------------------------------------------------------------
642: Xt Timer functions
643: ----------------------------------------------------------------------*/
644:
645: struct _HTTimer {
1.96 vatton 646: ms_t millis; /* Relative value in millis */
647: ms_t expires; /* Absolute value in millis */
648: BOOL relative;
649: BOOL repetitive;
650: void * param; /* Client supplied context */
651: HTTimerCallback * cbf;
1.58 cvs 652: };
653:
654: struct _AmayaTimer {
655: HTTimer *libwww_timer;
1.85 gully 656: #ifdef _GTK
1.79 cvs 657: guint xt_timer;
1.85 gully 658: #endif /* _GTK */
1.94 gully 659: #ifdef _WX
660: wxAmayaTimer * xt_timer;
661: #endif /* _WX */
1.85 gully 662: #ifdef _NOGUI
663: unsigned int xt_timer;
664: #endif /* #ifdef _NOGUI */
1.58 cvs 665: };
666: typedef struct _AmayaTimer AmayaTimer;
667:
668: static HTList *Timers = NULL;
669:
670: /*----------------------------------------------------------------------
1.79 cvs 671: TimerCallback
672: called by the system event loop. Timers shouldn't be restarted
673: on exiting.
1.58 cvs 674: ----------------------------------------------------------------------*/
675: void *TimerCallback (XtPointer cdata, XtIntervalId *id)
676: {
677: return (0);
678: }
1.86 gully 679:
1.85 gully 680: #ifdef _GTK
1.79 cvs 681: /*----------------------------------------------------------------------
682: TimerCallbackGTK
1.81 kahan 683: The callback returns FALSE to destroy the timer that called it.
1.79 cvs 684: ----------------------------------------------------------------------*/
685: gboolean TimerCallbackGTK (gpointer id)
686: {
687: HTList *cur, *last;
688: AmayaTimer *me;
689: HTTimer *libwww_timer;
690: AmayaTimer *data;
691:
692: data = (AmayaTimer *) id;
693:
694: if (!AmayaIsAlive ()
695: || Timers == NULL)
1.81 kahan 696: return (FALSE);
1.79 cvs 697:
698: /* find the timer from the uid */
699: last = cur = Timers;
700: while ((me = (AmayaTimer * ) HTList_nextObject (cur)))
701: {
702: if (me == data)
703: break;
704: last = cur;
705: }
706:
707: if (me)
708: {
709: libwww_timer = me->libwww_timer;
710: /* remove the element from the list @@@ can be optimized later */
711: HTList_quickRemoveElement(cur, last);
712: TtaFreeMemory (me);
713: HTTimer_dispatch (libwww_timer);
714: }
715: return (FALSE);
716: }
1.85 gully 717: #endif /* _GTK */
1.79 cvs 718:
1.58 cvs 719: /*----------------------------------------------------------------------
1.94 gully 720: TimerCallbackWX
721: called when a timer is throw
722: ----------------------------------------------------------------------*/
723: void TimerCallbackWX( void * p_context )
724: {
725: #ifdef _WX
726: HTList *cur, *last;
727: AmayaTimer *me;
728: HTTimer *libwww_timer;
729: AmayaTimer *data;
730:
731: data = (AmayaTimer *)p_context;
732:
733: if (!AmayaIsAlive ()
734: || Timers == NULL)
735: return;
736:
737: /* find the timer from the uid */
738: last = cur = Timers;
739: while ((me = (AmayaTimer * ) HTList_nextObject (cur)))
740: {
741: if (me == data)
742: break;
743: last = cur;
744: }
745:
746: if (me)
747: {
748: libwww_timer = me->libwww_timer;
749: /* remove the element from the list @@@ can be optimized later */
750: HTList_quickRemoveElement(cur, last);
751:
752: /* delete explicitely the AmayaTimer */
753: delete wxDynamicCast(me->xt_timer, wxAmayaTimer);
754:
755: TtaFreeMemory (me);
756: HTTimer_dispatch (libwww_timer);
757: }
758: #endif /* _WX */
759: }
760:
761: /*----------------------------------------------------------------------
1.59 cvs 762: KillAllTimers
1.58 cvs 763: ----------------------------------------------------------------------*/
1.59 cvs 764: void KillAllTimers (void)
1.58 cvs 765: {
1.96 vatton 766: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 767: /* @@@ maybe add something else to kill the Xt things */
768: if (Timers)
769: HTList_delete (Timers);
1.65 cvs 770: Timers = NULL;
1.96 vatton 771: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.58 cvs 772: }
773:
774: /*----------------------------------------------------------------------
1.59 cvs 775: AMAYA_SetTimer
776: ----------------------------------------------------------------------*/
777: void AMAYA_SetTimer (HTTimer *libwww_timer)
1.58 cvs 778: {
1.96 vatton 779: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 780: HTList *cur, *last;
781: AmayaTimer *me;
782:
1.90 gully 783: if (!AmayaIsAlive ()
1.58 cvs 784: || libwww_timer == NULL
785: || libwww_timer->expires == 0)
786: return;
787:
788: if (Timers == NULL)
789: Timers = HTList_new ();
790:
791: /* see if this timer existed already */
792: last = cur = Timers;
793: while ((me = (AmayaTimer * ) HTList_nextObject (cur)))
794: {
795: if (me->libwww_timer == libwww_timer)
796: break;
797: last = cur;
798: }
799:
800: if (me)
801: {
802: /* remove the old timer */
803: if (me->xt_timer)
804: {
1.85 gully 805: #ifdef _GTK
1.79 cvs 806: gtk_timeout_remove (me->xt_timer);
807: me->xt_timer = (guint) 0;
808: #endif /* !_GTK */
1.94 gully 809: #ifdef _WX
810: delete wxDynamicCast(me->xt_timer, wxTimer);
811: me->xt_timer = NULL;
812: #endif /* _WX */
813: }
1.58 cvs 814: }
815: else
816: {
817: /* create a new element */
1.91 gully 818: me = (AmayaTimer*)TtaGetMemory (sizeof (AmayaTimer));
1.58 cvs 819: /* and add it to the list */
820: HTList_addObject(last, (void *) me);
821: me->libwww_timer = libwww_timer;
822: }
823:
824: /* add a new time out */
1.85 gully 825: #ifdef _GTK
1.79 cvs 826: me->xt_timer = gtk_timeout_add ((guint32) me->libwww_timer->millis,
827: (GtkFunction) TimerCallbackGTK,
828: (gpointer) me);
1.85 gully 829: #endif /* _GTK */
1.94 gully 830: #ifdef _WX
831: me->xt_timer = new wxAmayaTimer( TimerCallbackWX, me);
832: /* start a one shot timer */
833: me->xt_timer->Start( me->libwww_timer->millis, TRUE );
834: #endif /* _WX */
835:
1.96 vatton 836: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.58 cvs 837: }
838:
839: /*----------------------------------------------------------------------
1.59 cvs 840: AMAYA_DeleteTimer
1.58 cvs 841: ----------------------------------------------------------------------*/
1.59 cvs 842: void AMAYA_DeleteTimer (HTTimer *libwww_timer)
1.58 cvs 843: {
1.96 vatton 844: #if defined(_GTK) || defined(_WX) || defined(_NOGUI)
1.58 cvs 845: HTList *cur, *last;
846: AmayaTimer *me;
847:
1.59 cvs 848: if (Timers == NULL || libwww_timer == NULL)
1.58 cvs 849: return;
850:
851: /* find the id */
852: last = cur = Timers;
853: while ((me = (AmayaTimer * ) HTList_nextObject (cur)))
854: {
1.59 cvs 855: if (me->libwww_timer == libwww_timer)
1.58 cvs 856: break;
857: last = cur;
858: }
859:
860: if (me)
861: {
862: /* remove the Xt timer */
1.85 gully 863: #ifdef _GTK
1.79 cvs 864: gtk_timeout_remove (me->xt_timer);
1.85 gully 865: #endif /* _GTK */
1.94 gully 866: #ifdef _WX
867: delete wxDynamicCast(me->xt_timer, wxTimer);
868: #endif /* _WX */
869:
1.58 cvs 870: /* and the element from the list */
1.65 cvs 871: HTList_removeObject (Timers, me);
1.58 cvs 872: TtaFreeMemory (me);
873: }
1.96 vatton 874: #endif /* #if defined(_GTK) || defined(_WX) || defined(_NOGUI) */
1.31 cvs 875: }
1.86 gully 876:
Webmaster