Changeset 862371b for libfaim/rxqueue.c


Ignore:
Timestamp:
Jun 29, 2003, 1:47:04 PM (21 years ago)
Author:
James M. Kretchmar <kretch@mit.edu>
Branches:
master, barnowl_perlaim, debian, owl, release-1.10, release-1.4, release-1.5, release-1.6, release-1.7, release-1.8, release-1.9
Children:
e016fc2
Parents:
03ad7b2
Message:
*** empty log message ***
File:
1 edited

Legend:

Unmodified
Added
Removed
  • libfaim/rxqueue.c

    r5e53c4a r862371b  
    11/*
    2  *  aim_rxqueue.c
     2 * rxqueue.c
    33 *
    44 * This file contains the management routines for the receive
     
    6464}
    6565
    66 faim_internal int aim_bstream_init(aim_bstream_t *bs, fu8_t *data, int len)
    67 {
    68        
    69         if (!bs)
    70                 return -1;
    71 
    72         bs->data = data;
    73         bs->len = len;
    74         bs->offset = 0;
    75 
    76         return 0;
    77 }
    78 
    79 faim_internal int aim_bstream_empty(aim_bstream_t *bs)
    80 {
    81         return bs->len - bs->offset;
    82 }
    83 
    84 faim_internal int aim_bstream_curpos(aim_bstream_t *bs)
    85 {
    86         return bs->offset;
    87 }
    88 
    89 faim_internal int aim_bstream_setpos(aim_bstream_t *bs, int off)
    90 {
    91 
    92         if (off > bs->len)
    93                 return -1;
    94 
    95         bs->offset = off;
    96 
    97         return off;
    98 }
    99 
    100 faim_internal void aim_bstream_rewind(aim_bstream_t *bs)
    101 {
    102 
    103         aim_bstream_setpos(bs, 0);
     66/**
     67 * aim_frame_destroy - free aim_frame_t
     68 * @frame: the frame to free
     69 *
     70 * returns -1 on error; 0 on success.
     71 *
     72 */
     73faim_internal void aim_frame_destroy(aim_frame_t *frame)
     74{
     75
     76        free(frame->data.data); /* XXX aim_bstream_free */
     77        free(frame);
    10478
    10579        return;
    10680}
    10781
    108 faim_internal int aim_bstream_advance(aim_bstream_t *bs, int n)
    109 {
    110 
    111         if (aim_bstream_empty(bs) < n)
    112                 return 0; /* XXX throw an exception */
    113 
    114         bs->offset += n;
    115 
    116         return n;
    117 }
    118 
    119 faim_internal fu8_t aimbs_get8(aim_bstream_t *bs)
    120 {
    121        
    122         if (aim_bstream_empty(bs) < 1)
    123                 return 0; /* XXX throw an exception */
    124        
    125         bs->offset++;
    126        
    127         return aimutil_get8(bs->data + bs->offset - 1);
    128 }
    129 
    130 faim_internal fu16_t aimbs_get16(aim_bstream_t *bs)
    131 {
    132        
    133         if (aim_bstream_empty(bs) < 2)
    134                 return 0; /* XXX throw an exception */
    135        
    136         bs->offset += 2;
    137        
    138         return aimutil_get16(bs->data + bs->offset - 2);
    139 }
    140 
    141 faim_internal fu32_t aimbs_get32(aim_bstream_t *bs)
    142 {
    143        
    144         if (aim_bstream_empty(bs) < 4)
    145                 return 0; /* XXX throw an exception */
    146        
    147         bs->offset += 4;
    148        
    149         return aimutil_get32(bs->data + bs->offset - 4);
    150 }
    151 
    152 faim_internal fu8_t aimbs_getle8(aim_bstream_t *bs)
    153 {
    154        
    155         if (aim_bstream_empty(bs) < 1)
    156                 return 0; /* XXX throw an exception */
    157        
    158         bs->offset++;
    159        
    160         return aimutil_getle8(bs->data + bs->offset - 1);
    161 }
    162 
    163 faim_internal fu16_t aimbs_getle16(aim_bstream_t *bs)
    164 {
    165        
    166         if (aim_bstream_empty(bs) < 2)
    167                 return 0; /* XXX throw an exception */
    168        
    169         bs->offset += 2;
    170        
    171         return aimutil_getle16(bs->data + bs->offset - 2);
    172 }
    173 
    174 faim_internal fu32_t aimbs_getle32(aim_bstream_t *bs)
    175 {
    176        
    177         if (aim_bstream_empty(bs) < 4)
    178                 return 0; /* XXX throw an exception */
    179        
    180         bs->offset += 4;
    181        
    182         return aimutil_getle32(bs->data + bs->offset - 4);
    183 }
    184 
    185 faim_internal int aimbs_put8(aim_bstream_t *bs, fu8_t v)
    186 {
    187 
    188         if (aim_bstream_empty(bs) < 1)
    189                 return 0; /* XXX throw an exception */
    190 
    191         bs->offset += aimutil_put8(bs->data + bs->offset, v);
    192 
    193         return 1;
    194 }
    195 
    196 faim_internal int aimbs_put16(aim_bstream_t *bs, fu16_t v)
    197 {
    198 
    199         if (aim_bstream_empty(bs) < 2)
    200                 return 0; /* XXX throw an exception */
    201 
    202         bs->offset += aimutil_put16(bs->data + bs->offset, v);
    203 
    204         return 2;
    205 }
    206 
    207 faim_internal int aimbs_put32(aim_bstream_t *bs, fu32_t v)
    208 {
    209 
    210         if (aim_bstream_empty(bs) < 4)
    211                 return 0; /* XXX throw an exception */
    212 
    213         bs->offset += aimutil_put32(bs->data + bs->offset, v);
    214 
    215         return 1;
    216 }
    217 
    218 faim_internal int aimbs_putle8(aim_bstream_t *bs, fu8_t v)
    219 {
    220 
    221         if (aim_bstream_empty(bs) < 1)
    222                 return 0; /* XXX throw an exception */
    223 
    224         bs->offset += aimutil_putle8(bs->data + bs->offset, v);
    225 
    226         return 1;
    227 }
    228 
    229 faim_internal int aimbs_putle16(aim_bstream_t *bs, fu16_t v)
    230 {
    231 
    232         if (aim_bstream_empty(bs) < 2)
    233                 return 0; /* XXX throw an exception */
    234 
    235         bs->offset += aimutil_putle16(bs->data + bs->offset, v);
    236 
    237         return 2;
    238 }
    239 
    240 faim_internal int aimbs_putle32(aim_bstream_t *bs, fu32_t v)
    241 {
    242 
    243         if (aim_bstream_empty(bs) < 4)
    244                 return 0; /* XXX throw an exception */
    245 
    246         bs->offset += aimutil_putle32(bs->data + bs->offset, v);
    247 
    248         return 1;
    249 }
    250 
    251 faim_internal int aimbs_getrawbuf(aim_bstream_t *bs, fu8_t *buf, int len)
    252 {
    253 
    254         if (aim_bstream_empty(bs) < len)
    255                 return 0;
    256 
    257         memcpy(buf, bs->data + bs->offset, len);
    258         bs->offset += len;
    259 
    260         return len;
    261 }
    262 
    263 faim_internal fu8_t *aimbs_getraw(aim_bstream_t *bs, int len)
    264 {
    265         fu8_t *ob;
    266 
    267         if (!(ob = malloc(len)))
    268                 return NULL;
    269 
    270         if (aimbs_getrawbuf(bs, ob, len) < len) {
    271                 free(ob);
    272                 return NULL;
    273         }
    274 
    275         return ob;
    276 }
    277 
    278 faim_internal char *aimbs_getstr(aim_bstream_t *bs, int len)
    279 {
    280         char *ob;
    281 
    282         if (!(ob = malloc(len+1)))
    283                 return NULL;
    284 
    285         if (aimbs_getrawbuf(bs, ob, len) < len) {
    286                 free(ob);
    287                 return NULL;
    288         }
    289        
    290         ob[len] = '\0';
    291 
    292         return ob;
    293 }
    294 
    295 faim_internal int aimbs_putraw(aim_bstream_t *bs, const fu8_t *v, int len)
    296 {
    297 
    298         if (aim_bstream_empty(bs) < len)
    299                 return 0; /* XXX throw an exception */
    300 
    301         memcpy(bs->data + bs->offset, v, len);
    302         bs->offset += len;
    303 
    304         return len;
    305 }
    306 
    307 faim_internal int aimbs_putbs(aim_bstream_t *bs, aim_bstream_t *srcbs, int len)
    308 {
    309 
    310         if (aim_bstream_empty(srcbs) < len)
    311                 return 0; /* XXX throw exception (underrun) */
    312 
    313         if (aim_bstream_empty(bs) < len)
    314                 return 0; /* XXX throw exception (overflow) */
    315 
    316         memcpy(bs->data + bs->offset, srcbs->data + srcbs->offset, len);
    317         bs->offset += len;
    318         srcbs->offset += len;
    319 
    320         return len;
    321 }
    322 
    323 /**
    324  * aim_frame_destroy - free aim_frame_t
    325  * @frame: the frame to free 
    326  *
    327  * returns -1 on error; 0 on success. 
    328  *
    329  */
    330 faim_internal void aim_frame_destroy(aim_frame_t *frame)
    331 {
    332 
    333         free(frame->data.data); /* XXX aim_bstream_free */
    334 
    335         if (frame->hdrtype == AIM_FRAMETYPE_OFT)
    336                 free(frame->hdr.oft.hdr2);
    337         free(frame);
    338        
    339         return;
    340 }
    341 
    342 
    343 /*
    344  * Grab a single command sequence off the socket, and enqueue
    345  * it in the incoming event queue in a seperate struct.
    346  */
    347 faim_export int aim_get_command(aim_session_t *sess, aim_conn_t *conn)
     82/*
     83 * Read a FLAP header from conn into fr, and return the number of bytes in the payload.
     84 */
     85static faim_shortfunc int aim_get_command_flap(aim_session_t *sess, aim_conn_t *conn, aim_frame_t *fr)
    34886{
    34987        fu8_t flaphdr_raw[6];
    35088        aim_bstream_t flaphdr;
    351         aim_frame_t *newrx;
    35289        fu16_t payloadlen;
    35390       
    354         if (!sess || !conn)
    355                 return 0;
    356 
    357         if (conn->fd == -1)
    358                 return -1; /* its a aim_conn_close()'d connection */
    359 
    360         if (conn->fd < 3)  /* can happen when people abuse the interface */
    361                 return 0;
    362 
    363         if (conn->status & AIM_CONN_STATUS_INPROGRESS)
    364                 return aim_conn_completeconnect(sess, conn);
    365 
    366         /*
    367          * Rendezvous (client-client) connections do not speak
    368          * FLAP, so this function will break on them.
    369          */
    370         if (conn->type == AIM_CONN_TYPE_RENDEZVOUS)
    371                 return aim_get_command_rendezvous(sess, conn);
    372         else if (conn->type == AIM_CONN_TYPE_RENDEZVOUS_OUT) {
    373                 faimdprintf(sess, 0, "AIM_CONN_TYPE_RENDEZVOUS_OUT on fd %d\n", conn->fd);
    374                 return 0;
    375         }
    376 
    37791        aim_bstream_init(&flaphdr, flaphdr_raw, sizeof(flaphdr_raw));
    37892
    37993        /*
    38094         * Read FLAP header.  Six bytes:
    381          *   
    38295         *   0 char  -- Always 0x2a
    38396         *   1 char  -- Channel ID.  Usually 2 -- 1 and 4 are used during login.
    384          *   2 short -- Sequence number 
     97         *   2 short -- Sequence number
    38598         *   4 short -- Number of data bytes that follow.
    38699         */
     
    406119        }       
    407120
    408         /* allocate a new struct */
    409         if (!(newrx = (aim_frame_t *)malloc(sizeof(aim_frame_t))))
    410                 return -1;
    411         memset(newrx, 0, sizeof(aim_frame_t));
    412 
    413121        /* we're doing FLAP if we're here */
    414         newrx->hdrtype = AIM_FRAMETYPE_FLAP;
    415        
    416         newrx->hdr.flap.type = aimbs_get8(&flaphdr);
    417         newrx->hdr.flap.seqnum = aimbs_get16(&flaphdr);
    418         payloadlen = aimbs_get16(&flaphdr);
     122        fr->hdrtype = AIM_FRAMETYPE_FLAP;
     123
     124        fr->hdr.flap.type = aimbs_get8(&flaphdr);
     125        fr->hdr.flap.seqnum = aimbs_get16(&flaphdr);
     126        payloadlen = aimbs_get16(&flaphdr); /* length of payload */
     127
     128        return payloadlen;
     129}
     130
     131/*
     132 * Read a rendezvous header from conn into fr, and return the number of bytes in the payload.
     133 */
     134static int aim_get_command_rendezvous(aim_session_t *sess, aim_conn_t *conn, aim_frame_t *fr)
     135{
     136        fu8_t rendhdr_raw[8];
     137        aim_bstream_t rendhdr;
     138
     139        aim_bstream_init(&rendhdr, rendhdr_raw, sizeof(rendhdr_raw));
     140
     141        if (aim_bstream_recv(&rendhdr, conn->fd, 8) < 8) {
     142                aim_conn_close(conn);
     143                return -1;
     144        }
     145
     146        aim_bstream_rewind(&rendhdr);
     147
     148        fr->hdrtype = AIM_FRAMETYPE_OFT; /* a misnomer--rendezvous */
     149
     150        aimbs_getrawbuf(&rendhdr, fr->hdr.rend.magic, 4);
     151        fr->hdr.rend.hdrlen = aimbs_get16(&rendhdr) - 8;
     152        fr->hdr.rend.type = aimbs_get16(&rendhdr);
     153
     154        return fr->hdr.rend.hdrlen;
     155}
     156
     157/*
     158 * Grab a single command sequence off the socket, and enqueue it in the incoming event queue
     159 * in a separate struct.
     160 */
     161faim_export int aim_get_command(aim_session_t *sess, aim_conn_t *conn)
     162{
     163        aim_frame_t *newrx;
     164        fu16_t payloadlen;
     165
     166        if (!sess || !conn)
     167                return -1;
     168
     169        if (conn->fd == -1)
     170                return -1; /* it's an aim_conn_close()'d connection */
     171
     172        if (conn->fd < 3) /* can happen when people abuse the interface */
     173                return -1;
     174
     175        if (conn->status & AIM_CONN_STATUS_INPROGRESS)
     176                return aim_conn_completeconnect(sess, conn);
     177
     178        if (!(newrx = (aim_frame_t *)calloc(sizeof(aim_frame_t), 1)))
     179                return -1;
     180
     181        /*
     182         * Rendezvous (client to client) connections do not speak FLAP, so this
     183         * function will break on them.
     184         */
     185        if (conn->type == AIM_CONN_TYPE_RENDEZVOUS)
     186                payloadlen = aim_get_command_rendezvous(sess, conn, newrx);
     187        else if (conn->type == AIM_CONN_TYPE_RENDEZVOUS_OUT) {
     188                faimdprintf(sess, 0, "AIM_CONN_TYPE_RENDEZVOUS_OUT on fd %d\n", conn->fd);
     189                free(newrx);
     190                return -1;
     191        } else
     192                payloadlen = aim_get_command_flap(sess, conn, newrx);
    419193
    420194        newrx->nofree = 0; /* free by default */
     
    508282        return;
    509283}
    510 
Note: See TracChangeset for help on using the changeset viewer.