]> andersk Git - moira.git/blob - gdb/gdb_ops.c
lint
[moira.git] / gdb / gdb_ops.c
1 /*
2  *      $Source$
3  *      $Header$
4  */
5
6 #ifndef lint
7 static char *rcsid_gdb_ops_c = "$Header$";
8 #endif  lint
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30 /************************************************************************/
31 /*      
32 /*                         gdb_ops.c
33 /*      
34 /*            GDB - Asynchronous Operations and Their Synchronous
35 /*                  Counterparts
36 /*      
37 /*      Author: Noah Mendelsohn
38 /*      Copyright: 1986 MIT Project Athena 
39 /*              For copying and distribution information, please see
40 /*              the file <mit-copyright.h>.
41 /*      
42 /*      These routines provide a suite of asynchronous operations 
43 /*      on connections.
44 /*      
45 /************************************************************************/
46
47 #include <mit-copyright.h>
48 #include <stdio.h>
49 #include "gdb.h"
50 #include <netinet/in.h>
51 #include <sys/ioctl.h>
52 #ifdef vax
53 extern u_long htonl();
54 #endif vax
55 \f
56 /************************************************************************/
57 /*      
58 /*                      send_object (send_object)
59 /*      
60 /*      Synchronous form of start_sending_object.  Returns either
61 /*      OP_CANCELLED, or OP_RESULT(op).
62 /*      
63 /************************************************************************/
64
65 int
66 send_object(con, objp, type)
67 CONNECTION con;
68 char *objp;
69 int type;
70 {
71         register OPERATION op;
72         register int retval;
73
74
75         op = create_operation();
76         start_sending_object(op, con, objp, type);
77         (void) complete_operation(op);
78         if (OP_STATUS(op) == OP_COMPLETE)
79                 retval =  OP_RESULT(op);
80         else
81                 retval = OP_STATUS(op);
82         delete_operation(op);
83         return retval;
84 }
85 \f
86 /************************************************************************/
87 /*      
88 /*                      start_send_object (g_snobj)
89 /*      
90 /*      Start the asynchronous transmission of a gdb object.
91 /*      Note that this routine must be passed the address of the object,
92 /*      not the object itself.
93 /*      
94 /*      The following three routines work together, and may be considered
95 /*      as a single entity implementing the operation.  The first merely
96 /*      saves away its arguments and queues the operation on the designated
97 /*      connection.  These stay there until they percolate to the head of
98 /*      the queue.  The second is the initialization routine, which is
99 /*      called by the connection maintenance logic when the operation
100 /*      first reaches the head of the queue.  This routine encodes
101 /*      the supplied data for transmission, and then sends it.  If the
102 /*      transmission executes synchronously, then the third routine is
103 /*      called immediately to clean up.  If not, the third routine is
104 /*      marked as the 'continuation' routine, which will cause its 
105 /*      invocation when the transmission completes.
106 /*      
107 /*      The data is preceded by its length expressed as a long in 
108 /*      network byte order.
109 /*      
110 /************************************************************************/
111
112 struct obj_data {
113         char    *objp;                          /* address of the object to */
114                                                 /* be sent */
115         int     type;                           /* type code for the object */
116                                                 /* to be sent*/
117         char    *flattened;                     /* address of first byte */
118                                                 /* of flattened data */
119         int     len;                            /* length of the flattened */
120                                                 /* data */
121 };
122
123 int g_isnobj();
124 int g_csnobj();
125
126 int
127 start_sending_object(op, con, objp, type)
128 OPERATION op;
129 CONNECTION con;
130 char *objp;
131 int type;
132 {
133         struct obj_data *arg;
134
135        /*
136         * Make sure the supplied connection is a legal one
137         */
138         GDB_CHECK_CON(con, "start_sending_object")
139         GDB_CHECK_OP(op, "start_sending_object")
140
141         arg = (struct obj_data *)db_alloc(sizeof(struct obj_data));
142
143         arg->objp = objp;
144         arg->type = type;
145         initialize_operation(op, g_isnobj, (char *)arg, (int (*)())NULL);
146         (void) queue_operation(con, CON_OUTPUT, op);
147 }
148
149         /*----------------------------------------------------------*/
150         /*      
151         /*                      g_isnobj
152         /*      
153         /*      Init routine for sending an object.  This routine is 
154         /*      called by the connection management logic when the send
155         /*      request percolates to the top of the queue.  This routine
156         /*      reformats the data into an appropriate form for transmission.
157         /*      The format used is a length, represented as a long in 
158         /*      network byte order, followed by the data itself.  The
159         /*      continuation routine below is called, either synchronously 
160         /*      or asynchronously, once the transmission is complete.
161         /*      
162         /*----------------------------------------------------------*/
163
164 int
165 g_isnobj(op, hcon, arg)
166 OPERATION op;
167 HALF_CONNECTION hcon;
168 struct obj_data *arg;
169 {
170        /*
171         * Find out the encoded length of the data
172         */
173         arg->len = FCN_PROPERTY(arg->type, CODED_LENGTH_PROPERTY)
174                                (arg->objp, hcon);
175
176        /*
177         * Allocate space and flatten (encode) the data
178         */
179         arg->flattened = db_alloc(arg->len+sizeof(long));
180         *(u_long *)arg->flattened = htonl((u_long)arg->len);
181
182         FCN_PROPERTY(arg->type, ENCODE_PROPERTY)
183                                (arg->objp, hcon, arg->flattened+sizeof(long));
184
185        /*
186         * Set up continuation routine in case it's needed after the return
187         */
188         op->fcn.cont = g_csnobj;
189
190        /*
191         * Start sending the data, maybe even complete
192         */
193         if (gdb_send_data(hcon, arg->flattened, arg->len + sizeof(long)) == 
194             OP_COMPLETE) {              
195                 return g_csnobj(op, hcon, arg)  ;/* this return is a little */
196                                                 /* subtle.  As continuation */
197                                                 /* routines call each other */
198                                                 /* synchronously, the last */
199                                                 /* one determines whether we */
200                                                 /* completed or are still */
201                                                 /* running.  That status */
202                                                 /* percolates back through */
203                                                 /* the entire call chain. */
204         } else {
205                 return OP_RUNNING;
206         }
207 }
208
209
210         
211
212         
213         
214         /*----------------------------------------------------------*/
215         /*      
216         /*                       g_csnobj
217         /*      
218         /*      Continuation routine for sending an object.  Since there is
219         /*      only one transmission, started by the init routine, this is
220         /*      called when that transmission is done, and it does all the
221         /*      associated clean up.
222         /*      
223         /*----------------------------------------------------------*/
224
225 /*ARGSUSED*/
226 int
227 g_csnobj(op, hcon, arg)
228 OPERATION op;
229 HALF_CONNECTION hcon;
230 struct obj_data *arg;
231 {
232         op->result = OP_SUCCESS;                
233         db_free((char *)arg->flattened, arg->len + sizeof(long));
234                                                 /* free the sent data */
235         db_free((char *)arg, sizeof(struct obj_data));  /* free the state structure */
236         return OP_COMPLETE;
237 }
238
239 \f
240 /************************************************************************/
241 /*      
242 /*                      receive_object (receive_object)
243 /*      
244 /*      Synchronous form of start_receiving_object.  Returns either
245 /*      OP_CANCELLED, or OP_RESULT(op).
246 /*      
247 /************************************************************************/
248
249 int
250 receive_object(con, objp, type)
251 CONNECTION con;
252 char *objp;
253 int type;
254 {
255         register OPERATION op;
256         register int retval;
257
258         op = create_operation();
259         start_receiving_object(op, con, objp, type);
260         (void) complete_operation(op);
261         if (OP_STATUS(op) == OP_COMPLETE)
262                 retval =  OP_RESULT(op);
263         else
264                 retval = OP_STATUS(op);
265         delete_operation(op);
266         return retval;
267 }
268 \f
269 /************************************************************************/
270 /*      
271 /*                      start_receiving_object (g_rcobj)
272 /*      
273 /*      Start the asynchronous receipt of a gdb object.  Note that this
274 /*      routine must be passed the address of the object, not the object
275 /*      itself.  In the case of structured objects, this routine may 
276 /*      allocate the necessary storage.  The work to build the object is
277 /*      done by the object's decode routine.
278 /*      
279 /*      The following three routines work together, and may be considered
280 /*      as a single entity implementing the operation.  The first merely
281 /*      saves away its arguments and queues the operation on the designated
282 /*      connection.  These stay there until they percolate to the head of
283 /*      the queue.  The second is the initialization routine, which is
284 /*      called by the connection maintenance logic when the operation
285 /*      first reaches the head of the queue.  This routine initiates a read
286 /*      for the length of the object, and sets up a continuation routine
287 /*      to read the object itself.  When the object itself has been read, it 
288 /*      is decoded and the operation completes.
289 /*      
290 /*      The data is preceded by its length expressed as a long in 
291 /*      network byte order.
292 /*      
293 /*                      preempt_and_start_receiving_object (g_prcobj)
294 /*      
295 /*      Similar to above, but may be called only from an active operation
296 /*      (i.e. an init or continue routine) on an inbound half connection.
297 /*      The receive effectively pre-empts the old operation, which wil
298 /*      continue after the receive is done.
299 /*      
300 /*      
301 /************************************************************************/
302
303 struct robj_data {
304         char    *objp;                          /* address of the object to */
305                                                 /* be received */
306         int     type;                           /* type code for the object */
307                                                 /* to be received */
308         char    *flattened;                     /* address of first byte */
309                                                 /* of flattened data */
310         int     len;                            /* length of the flattened */
311                                                 /* data */
312 };
313
314 int g_ircobj();
315 int g_c1rcobj();
316 int g_c2rcobj();
317
318         /*----------------------------------------------------------*/
319         /*      
320         /*              start_receiving_object
321         /*      
322         /*----------------------------------------------------------*/
323
324 int
325 start_receiving_object(op, con, objp, type)
326 OPERATION op;
327 CONNECTION con;
328 char *objp;
329 int type;
330 {
331         struct robj_data *arg;
332
333        /*
334         * Make sure the supplied connection is a legal one
335         */
336         GDB_CHECK_CON(con, "start_receiving_object")
337         GDB_CHECK_OP(op, "start_receiving_object")
338
339         arg = (struct robj_data *)db_alloc(sizeof(struct robj_data));
340
341         arg->objp = objp;
342         arg->type = type;
343         initialize_operation(op, g_ircobj, (char *)arg, (int (*)())NULL);
344         (void) queue_operation(con, CON_INPUT, op);
345 }
346
347         /*----------------------------------------------------------*/
348         /*      
349         /*              preempt_and_start_receiving_object
350         /*      
351         /*----------------------------------------------------------*/
352
353 int
354 preempt_and_start_receiving_object(op, oldop, objp, type)
355 OPERATION op;
356 OPERATION oldop;
357 char *objp;
358 int type;
359 {
360         struct robj_data *arg;
361
362        /*
363         * Make sure the supplied connection is a legal one
364         */
365         GDB_CHECK_OP(op, "preempt_and_start_receiving_object")
366         GDB_CHECK_OP(oldop, "preempt_and_start_receiving_object")
367
368         arg = (struct robj_data *)db_alloc(sizeof(struct robj_data));
369
370         arg->objp = objp;
371         arg->type = type;
372         initialize_operation(op, g_ircobj, (char *)arg, (int (*)())NULL);
373         (void) g_preempt_me(oldop, op);
374 }
375
376         /*----------------------------------------------------------*/
377         /*      
378         /*                      g_ircobj
379         /*      
380         /*      Initialization routine for receiving an object.  
381         /*      Called when the receive operation percolates to the
382         /*      top of the queue.  First, we must receive the single
383         /*      'long' which carries the length of the rest of the data.
384         /*      We do that now, either synchronously or asynchronously.
385         /*      
386         /*----------------------------------------------------------*/
387
388 int
389 g_ircobj(op, hcon, arg)
390 OPERATION op;
391 HALF_CONNECTION hcon;
392 struct robj_data *arg;
393 {
394         op->fcn.cont = g_c1rcobj;
395         if(gdb_receive_data(hcon, (char *)&(arg->len), sizeof(long)) == OP_COMPLETE) {
396                 return g_c1rcobj(op, hcon, arg);/* this return is a little */
397                                                 /* subtle.  As continuation */
398                                                 /* routines call each other */
399                                                 /* synchronously, the last */
400                                                 /* one determines whether we */
401                                                 /* completed or are still */
402                                                 /* running.  That status */
403                                                 /* percolates back through */
404                                                 /* the entire call chain. */
405         } else {
406                 return OP_RUNNING;
407         }
408 }
409
410         /*----------------------------------------------------------*/
411         /*      
412         /*                      g_c1rcobj
413         /*      
414         /*      At this point, we have received the length.  Now, allocate
415         /*      the space for the rest of the data, and start receiving
416         /*      it.
417         /*      
418         /*----------------------------------------------------------*/
419
420 int
421 g_c1rcobj(op, hcon, arg)
422 OPERATION op;
423 HALF_CONNECTION hcon;
424 struct robj_data *arg;
425 {
426 #ifdef  vax
427         extern u_long ntohl();
428 #endif  vax
429         
430        /*
431         * Now we know the length of the encoded data, convert the length
432         * to local byte order, and allocate the space for the receive.
433         */
434         arg->len = (int) ntohl((u_long)arg->len);
435         if (arg->len > 65536)
436           return OP_CANCELLED;
437
438         arg->flattened = db_alloc(arg->len);
439         if (arg->flattened == NULL)
440           return OP_CANCELLED;
441        /*
442         * Now start receiving the encoded object itself.  If it all comes in
443         * synchronously, then just go on to the c2 routine to decode it and
444         * finish up.  Else return OP_RUNNING, so the rest of the system 
445         * can get some work done while we wait.
446         */
447         op->fcn.cont = g_c2rcobj;
448         if(gdb_receive_data(hcon, arg->flattened, arg->len ) == OP_COMPLETE) {
449                 return g_c2rcobj(op, hcon, arg);
450         } else {
451                 return OP_RUNNING;
452         }
453 }
454
455         /*----------------------------------------------------------*/
456         /*      
457         /*                    g_c2rcobj
458         /*      
459         /*      At this point, all the data has been received.  Decode
460         /*      it into the place provided by the caller, free all
461         /*      temporarily allocated memory, and return.
462         /*      
463         /*----------------------------------------------------------*/
464
465 int
466 g_c2rcobj(op, hcon, arg)
467 OPERATION op;
468 HALF_CONNECTION hcon;
469 struct robj_data *arg;
470 {
471        /*
472         * Decode the received data into local representation.
473         */
474         FCN_PROPERTY(arg->type, DECODE_PROPERTY)
475                           (arg->objp, hcon, arg->flattened);
476         op->result = OP_SUCCESS;
477         db_free(arg->flattened, arg->len);      /* free the received data */
478         db_free((char *)arg, sizeof(struct robj_data)); /* free the state structure */
479         return OP_COMPLETE;
480 }
481 \f
482 /************************************************************************/
483 /*      
484 /*                      complete_operation(complete_operation)
485 /*      
486 /*      Wait for a given operation to complete, allowing everything
487 /*      to progress in the meantime.  Returns the last known status
488 /*      of the operation, which in general will be OP_COMPLETE unless
489 /*      errors were encountered (and this version of the code doesn't
490 /*      do error handing right anyway!)
491 /*      
492 /*      We do this by (1) calling gdb_progress to assure that all
493 /*      possible progress has been made, which is always a good thing
494 /*      to do when we get the chance and (2) looping on calls to 
495 /*      con_select, which will make all possible future progress, 
496 /*      but without burning cycles unnecessarily in the process.
497 /*      
498 /************************************************************************/
499
500 int
501 complete_operation(op)
502 OPERATION op;
503 {
504         (void) gdb_progress();
505
506         while(op->status != OP_COMPLETE && op->status != OP_CANCELLED)
507                 (void) con_select(0, (fd_set *)NULL, (fd_set *)NULL,
508                            (fd_set *)NULL, (struct timeval *)NULL);
509
510         return op->status;
511
512 }
513
514 \f
515 /************************************************************************/
516 /*      
517 /*                      cancel_operation(cancel_operation)
518 /*      
519 /*      Attempts to cancel an operation.  
520 /*      
521 /************************************************************************/
522
523 int
524 cancel_operation(op)
525 OPERATION op;
526 {
527         register HALF_CONNECTION hcon = op->halfcon;
528
529         if (op->status != OP_RUNNING && op->status != OP_QUEUED)
530                 return op->status; 
531
532         if (hcon == NULL)
533                 GDB_GIVEUP("cancel_operation: operation is queued but half connection is unknown")
534
535        /*
536         * If we're at the head of the queue and running, then we have to
537         * call the cancelation routine for this particular operation so
538         * it can clean up.
539         */
540         if (op->prev == (OPERATION)hcon) {
541                 if (op->status == OP_RUNNING && op->cancel != NULL)
542                         (*op->cancel)(op->halfcon, op->arg);
543         }
544
545        /*
546         * Looks safe, now cancel it.
547         */
548         op->next->prev = op->prev;              /* de-q it */
549         op->prev->next = op->next;              /* "  "  " */
550         op->status = OP_CANCELLED;
551         op->halfcon = NULL;
552
553         return OP_CANCELLED;
554 }
555 \f
556 /************************************************************************/
557 /*      
558 /*                      start_listening
559 /*      
560 /*      Start the asynchronous acquisition of a connection.  This
561 /*      results in the queuing of a GDB "OPERATION" to do the
562 /*      requested listening.
563 /*      
564 /************************************************************************/
565
566 struct lis_data {
567         char    *otherside;                     /* data returned from an */
568                                                 /* accept */
569         int     *otherlen;                      /* length of the otherside */
570                                                 /* field */
571         int     *fdp;                           /* ptr to the fd of the */
572                                                 /* newly accepted */
573                                                 /* connection */
574 };
575
576 int g_ilis();
577 int g_clis();
578
579 void
580 gdb_start_listening(op, con, otherside, lenp, fdp)
581 OPERATION op;
582 CONNECTION con;
583 char *otherside;
584 int  *lenp;
585 int  *fdp;
586 {
587         struct lis_data *arg;
588
589         GDB_INIT_CHECK
590
591        /*
592         * Make sure the supplied connection is a legal one
593         */
594         GDB_CHECK_CON(con, "start_listening")
595         GDB_CHECK_OP(op, "start_listening")
596
597         arg = (struct lis_data *)db_alloc(sizeof(struct lis_data));
598
599         arg->otherside = otherside;
600         arg->otherlen = lenp;
601         arg->fdp = fdp;
602         initialize_operation(op, g_ilis, (char *)arg, (int (*)())NULL);
603         (void) queue_operation(con, CON_INPUT, op);
604 }
605
606         /*----------------------------------------------------------*/
607         /*      
608         /*                      g_ilis
609         /*      
610         /*      Init routine for doing a listen.
611         /*      
612         /*----------------------------------------------------------*/
613
614 int
615 g_ilis(op, hcon, arg)
616 OPERATION op;
617 HALF_CONNECTION hcon;
618 struct lis_data *arg;
619 {
620         int rc;
621
622        /*
623         * Set up continuation routine in case it's needed after the return
624         */
625         op->fcn.cont = g_clis;
626
627        /*
628         * Try doing the listen now, and then decide whether to go
629         * right on to the continuation routine or to let things hang
630         * for the moment.
631         */
632         rc = gdb_start_a_listen(hcon, arg->otherside, arg->otherlen, arg->fdp);
633         if (rc==OP_COMPLETE) {          
634                 return g_clis(op, hcon, arg);   /* this return is a little */
635                                                 /* subtle.  As continuation */
636                                                 /* routines call each other */
637                                                 /* synchronously, the last */
638                                                 /* one determines whether we */
639                                                 /* completed or are still */
640                                                 /* running.  That status */
641                                                 /* percolates back through */
642                                                 /* the entire call chain. */
643         } else {
644                 return OP_RUNNING;
645         }
646 }
647
648
649         
650         /*----------------------------------------------------------*/
651         /*      
652         /*                       g_clis
653         /*      
654         /*      Continuation routine for accepting a connection.
655         /*
656         /*      At this point, the fd has been accepted and all
657         /*      the necessary information given back to the caller.
658         /*      
659         /*----------------------------------------------------------*/
660
661 /*ARGSUSED*/
662 int
663 g_clis(op, hcon, arg)
664 OPERATION op;
665 HALF_CONNECTION hcon;
666 struct lis_data *arg;
667 {
668         op->result = OP_SUCCESS;                
669         db_free((char *)arg, sizeof(struct lis_data));  
670                                                 /* free the state structure */
671         return OP_COMPLETE;
672 }
673
674 \f
675 /************************************************************************/
676 /*      
677 /*                      start_accepting_client
678 /*      
679 /*      Start the asynchronous acquisition of a client.  This queueable
680 /*      operation first tries to accept a connection.  On this connection,
681 /*      it reads a startup string from the client, and then completes.
682 /*      
683 /*      The return values from this are not quite what you might expect.
684 /*      In general, the operation will show complete, rather than cancelled,
685 /*      if it gets as far as creating the new connection at all.  If
686 /*      subsequent activities result in errors from system calls, then
687 /*      this operation will complete with a status of OP_COMPLETE and a 
688 /*      result of OP_CANCELLED.  In this case, the applications IS given
689 /*      a connection descriptor for the new connection, and that descriptor
690 /*      has an errno value indicating why the failure occurred.  The 
691 /*      caller must then sever this connection to free the descriptor.
692 /*      
693 /************************************************************************/
694
695 struct acc_data {
696         char    *otherside;                     /* data returned from an */
697                                                 /* accept */
698         int     *otherlen;                      /* length of the otherside */
699                                                 /* field */
700         OPERATION listenop;                     /* used to listen for */
701                                                 /* the fd */
702         OPERATION receiveop;                    /* used when receiving */
703                                                 /* tuple from the client */
704         CONNECTION con;                         /* the connection we're */
705                                                 /* trying to create */
706         CONNECTION *conp;                       /* this is where the caller */
707                                                 /* wants the connection */
708                                                 /* returned */
709         TUPLE *tuplep;                          /* pointer to tuple we */
710                                                 /* are going to receive */
711                                                 /* from new client */
712 };
713
714 int g_iacc();
715 int g_i2acc();
716
717 void
718 start_accepting_client(listencon, op, conp, otherside, lenp, tuplep)
719 CONNECTION listencon;
720 OPERATION op;
721 CONNECTION *conp;
722 char *otherside;
723 int  *lenp;
724 TUPLE *tuplep;
725 {
726         struct acc_data *arg;
727
728         GDB_INIT_CHECK
729
730        /*
731         * Make sure the supplied connection and operation are legal
732         */
733         GDB_CHECK_CON(listencon, "start_accepting_client")
734         GDB_CHECK_OP(op, "start_accepting_client")
735
736         arg = (struct acc_data *)db_alloc(sizeof(struct acc_data));
737
738         arg->otherside = otherside;
739         arg->otherlen = lenp;
740         arg->conp = conp;
741         *conp = NULL;                           /* in case we fail */
742         arg->listenop = create_operation();
743         arg->receiveop = create_operation();
744         arg->con = g_make_con();
745         arg->tuplep = tuplep;
746         *tuplep = NULL;                         /* in case we fail */
747
748        /*
749         * Queue an operation ahead of us which will accept an fd and
750         * put it in arg->con->in.  As a byproduct, pick up the from
751         * information that we return to the caller.
752         */
753         gdb_start_listening(arg->listenop, listencon,
754                             arg->otherside, 
755                             arg->otherlen, &(arg->con->in.fd));
756         
757        /*
758         * Now queue us behind it.  By the time we run our init routine,
759         * a connection should have been acquired.
760         */
761         initialize_operation(op, g_iacc, (char *)arg, (int (*)())NULL);
762         (void) queue_operation(listencon, CON_INPUT, op);
763 }
764
765         /*----------------------------------------------------------*/
766         /*      
767         /*                      g_iacc
768         /*      
769         /*      Init routine for accepting a connection.  By the 
770         /*      time this runs, the listen has been done, the 
771         /*      'from' data put in position for the caller, and
772         /*      the fd plugged into the connection descriptor.
773         /*      If all went well, fill out the connection descriptor
774         /*      and then requeue us on that to do the receive of
775         /*      the requested tuple.
776         /*      
777         /*----------------------------------------------------------*/
778
779 /*ARGSUSED*/
780 int
781 g_iacc(op, hcon, arg)
782 OPERATION op;
783 HALF_CONNECTION hcon;
784 struct acc_data *arg;
785 {
786         register CONNECTION con = arg->con;
787
788        /*
789         * Set up 2nd init routine for after we re-queue ourselves
790         */
791         op->fcn.cont = g_i2acc;
792        /*
793         * See whether we successfully accepted a connection.  If
794         * not, we just cancel ourselves.  If so, fill out the
795         * connection descriptor and related data structures properly,
796         * then requeue ourselves on the new connection.
797         */
798         if (OP_STATUS(arg->listenop) != OP_COMPLETE ||
799             OP_RESULT(arg->listenop) != OP_SUCCESS ||
800             con->in.fd <=0) {
801                     (void) sever_connection(con);
802                     g_clnup_accept(arg);
803                     op->result = OP_CANCELLED;
804                     return OP_CANCELLED;
805         }
806
807        /*
808         * OK, we got an fd, but the connection and related structures 
809         * aren't really set up straight, and the fd must be put
810         * into non-blocking mode.  There really should be a common
811         * routine for this, since some of the logic exists in 2
812         * or 3 places.
813         */
814         con->status = CON_STARTING;
815         con->out.fd = con->in.fd;
816         g_ver_iprotocol(con);                   /* make sure we're at */
817                                                 /* same level of protocol */
818         if (con->status == CON_UP) {
819                /*
820                 * We've successfully started the connection, now mark
821                 * it for non-blocking I/O.  Also, update the high water
822                 * mark of fd's controlled by our system.
823                 */
824                 int nb = 1;
825                 if(ioctl(con->in.fd, FIONBIO, (char *)&nb)== (-1)) {
826                         g_stop_with_errno(con);
827                         *arg->conp = con;       /* give failed con to */
828                                                 /* caller so he can find */
829                                                 /* errno */
830                         gdb_perror("gdb: ioctl for non-block failed");
831                         g_clnup_accept(arg);
832                         op->result = OP_CANCELLED; /* we didn't really, but */
833                                                  /* we want caller to look */
834                                                  /* at the connection so he */
835                                                  /* can find errno*/
836                         return OP_COMPLETE;
837                 }
838                 if (con->in.fd +1 > gdb_mfd) 
839                         gdb_mfd = con->in.fd + 1;
840                /*
841                 * Allocate a buffer, if necessary, and reset buffer pointers
842                 * so first request will result in a long read into the buffer
843                 */
844                 g_allocate_connection_buffers(con);
845
846         } else {
847                 *arg->conp = con;               /* give failed con to */
848                                                 /* caller so he can find */
849                                                 /* errno */
850                 g_clnup_accept(arg);
851                 op->result = OP_CANCELLED;
852                 return OP_COMPLETE;
853         }
854
855        /*
856         * Before we requeue ourselves on the new connection, queue
857         * up a receive for the expected tuple.  Then we'll be 
858         * sure that it's there by the time we run.
859         */
860         start_receiving_object(arg->receiveop, con, (char *)(arg->tuplep),
861                                TUPLE_T);
862        /*
863         * Requeue ourselves behind the receive operation.
864         */
865
866         (void) requeue_operation(con, CON_INPUT, op);
867         return OP_REQUEUED;
868 }
869
870
871         
872         /*----------------------------------------------------------*/
873         /*      
874         /*                      g_i2acc
875         /*      
876         /*      Second init routine for accepting a connection. 
877         /*      This one is run after the operation is requeued on
878         /*      the new connection.  By the time we run here, the
879         /*      attempt to receive the tuple has already been made.
880         /*      We just check on status and clean-up.
881         /*      
882         /*----------------------------------------------------------*/
883
884 /*ARGSUSED*/
885 int
886 g_i2acc(op, hcon, arg)
887 OPERATION op;
888 HALF_CONNECTION hcon;
889 struct acc_data *arg;
890 {
891         int rc;
892
893         rc = OP_STATUS(arg->receiveop);         /* if it completes, then */
894                                                 /* so do we! */
895         *arg->conp = arg->con;                  /* give caller the new con */
896         if (rc != OP_COMPLETE) 
897                 (void) g_stop_connection(arg->con);
898        /*
899         * Release all transient data structures.
900         */
901         g_clnup_accept(arg);
902         
903         return OP_COMPLETE;
904 }
905
906         /*----------------------------------------------------------*/
907         /*      
908         /*                      g_clnup_accept
909         /*      
910         /*      Free all data structures used by start_accepting_client.
911         /*      
912         /*----------------------------------------------------------*/
913
914 int
915 g_clnup_accept(arg)
916 struct acc_data *arg;
917 {
918         delete_operation(arg->listenop);
919         delete_operation(arg->receiveop);
920         db_free((char *)arg, sizeof(struct acc_data));  
921 }
This page took 0.110105 seconds and 5 git commands to generate.