Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/srv/net/tcp/rqueue.c

    r2f19103 r9520af7  
    3838#include <errno.h>
    3939#include <io/log.h>
     40#include <stdbool.h>
    4041#include <stdlib.h>
    4142#include <fibril.h>
     43#include <fibril_synch.h>
    4244#include "conn.h"
    43 #include "pdu.h"
    4445#include "rqueue.h"
    4546#include "segment.h"
     
    4748#include "ucall.h"
    4849
    49 /** Transcode bounced segments.
    50  *
    51  * If defined, segments bounced via the internal debugging loopback will
    52  * be encoded to a PDU and the decoded. Otherwise they will be bounced back
    53  * directly without passing the encoder-decoder.
    54  */
    55 #define BOUNCE_TRANSCODE
    56 
    5750static prodcons_t rqueue;
     51static bool fibril_active;
     52static fibril_mutex_t lock;
     53static fibril_condvar_t cv;
     54static tcp_rqueue_cb_t *rqueue_cb;
    5855
    5956/** Initialize segment receive queue. */
    60 void tcp_rqueue_init(void)
     57void tcp_rqueue_init(tcp_rqueue_cb_t *rcb)
    6158{
    6259        prodcons_initialize(&rqueue);
     60        fibril_mutex_initialize(&lock);
     61        fibril_condvar_initialize(&cv);
     62        fibril_active = false;
     63        rqueue_cb = rcb;
    6364}
    6465
    65 /** Bounce segment directy into receive queue without constructing the PDU.
    66  *
    67  * This is for testing purposes only.
    68  *
    69  * @param sp    Endpoint pair, oriented for transmission
    70  * @param seg   Segment
    71  */
    72 void tcp_rqueue_bounce_seg(inet_ep2_t *epp, tcp_segment_t *seg)
     66/** Finalize segment receive queue. */
     67void tcp_rqueue_fini(void)
    7368{
    74         inet_ep2_t rident;
     69        inet_ep2_t epp;
    7570
    76         log_msg(LOG_DEFAULT, LVL_DEBUG, "tcp_rqueue_bounce_seg()");
     71        inet_ep2_init(&epp);
     72        tcp_rqueue_insert_seg(&epp, NULL);
    7773
    78 #ifdef BOUNCE_TRANSCODE
    79         tcp_pdu_t *pdu;
    80         tcp_segment_t *dseg;
    81 
    82         if (tcp_pdu_encode(epp, seg, &pdu) != EOK) {
    83                 log_msg(LOG_DEFAULT, LVL_WARN, "Not enough memory. Segment dropped.");
    84                 return;
    85         }
    86 
    87         if (tcp_pdu_decode(pdu, &rident, &dseg) != EOK) {
    88                 log_msg(LOG_DEFAULT, LVL_WARN, "Not enough memory. Segment dropped.");
    89                 return;
    90         }
    91 
    92         tcp_pdu_delete(pdu);
    93 
    94         /** Insert decoded segment into rqueue */
    95         tcp_rqueue_insert_seg(&rident, dseg);
    96         tcp_segment_delete(seg);
    97 #else
    98         /* Reverse the identification */
    99         tcp_ep2_flipped(epp, &rident);
    100 
    101         /* Insert segment back into rqueue */
    102         tcp_rqueue_insert_seg(&rident, seg);
    103 #endif
     74        fibril_mutex_lock(&lock);
     75        while (fibril_active)
     76                fibril_condvar_wait(&cv, &lock);
     77        fibril_mutex_unlock(&lock);
    10478}
    10579
     
    10781 *
    10882 * @param epp   Endpoint pair, oriented for reception
    109  * @param seg   Segment
     83 * @param seg   Segment (ownership transferred to rqueue)
    11084 */
    11185void tcp_rqueue_insert_seg(inet_ep2_t *epp, tcp_segment_t *seg)
    11286{
    11387        tcp_rqueue_entry_t *rqe;
    114         log_msg(LOG_DEFAULT, LVL_DEBUG, "tcp_rqueue_insert_seg()");
    11588
    116         tcp_segment_dump(seg);
     89        log_msg(LOG_DEFAULT, LVL_DEBUG2, "tcp_rqueue_insert_seg()");
     90
     91        if (seg != NULL)
     92                tcp_segment_dump(seg);
    11793
    11894        rqe = calloc(1, sizeof(tcp_rqueue_entry_t));
     
    140116                rqe = list_get_instance(link, tcp_rqueue_entry_t, link);
    141117
    142                 tcp_as_segment_arrived(&rqe->epp, rqe->seg);
     118                if (rqe->seg == NULL) {
     119                        free(rqe);
     120                        break;
     121                }
     122
     123                rqueue_cb->seg_received(&rqe->epp, rqe->seg);
    143124                free(rqe);
    144125        }
    145126
    146         /* Not reached */
     127        log_msg(LOG_DEFAULT, LVL_DEBUG2, "tcp_rqueue_fibril() exiting");
     128
     129        /* Finished */
     130        fibril_mutex_lock(&lock);
     131        fibril_active = false;
     132        fibril_mutex_unlock(&lock);
     133        fibril_condvar_broadcast(&cv);
     134
    147135        return 0;
    148136}
     
    162150
    163151        fibril_add_ready(fid);
     152        fibril_active = true;
    164153}
    165154
Note: See TracChangeset for help on using the changeset viewer.