src/irc_queue.c
author Tero Marttila <terom@fixme.fi>
Thu, 23 Apr 2009 17:17:33 +0300
changeset 147 fd97eb3c183a
parent 102 af4190b743a5
child 151 b0b01420b99d
permissions -rw-r--r--
fix bug with irc_net_destroy/users
90
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     1
#include "irc_queue.h"
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     2
#include "log.h"
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     3
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     4
// XXX: for ev_base
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     5
#include "sock_internal.h"
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     6
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     7
#include <stdlib.h>
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     8
#include <string.h>
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     9
#include <time.h>
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    10
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    11
/**
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    12
 * Send a formatted line on the line_proto, and apply the IRC_QUEUE_PENALTY to the timer, resetting it to the current
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    13
 * time if it's fallen behind.
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    14
 */
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    15
static err_t irc_queue_send_buf (struct irc_queue *queue, const char *line_buf)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    16
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    17
    time_t now = time(NULL);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    18
    err_t err;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    19
    int ret;
102
af4190b743a5 log outoing messages from irc_queue
Tero Marttila <terom@fixme.fi>
parents: 91
diff changeset
    20
af4190b743a5 log outoing messages from irc_queue
Tero Marttila <terom@fixme.fi>
parents: 91
diff changeset
    21
    log_debug("%s", line_buf);
90
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    22
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    23
    // XXX: output buffering?
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    24
    if ((ret = line_proto_send(queue->lp, line_buf)) < 0)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    25
        return (err = -ret);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    26
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    27
    // reset timer to current time if it's fallen behind
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    28
    if (queue->timer < now)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    29
        queue->timer = now;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    30
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    31
    // apply penalty
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    32
    queue->timer += IRC_QUEUE_PENALTY;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    33
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    34
    // ok
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    35
    return SUCCESS;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    36
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    37
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    38
/**
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    39
 * Pump the queue, sending the next message. If it is given explicitly, then the given message is "pumped", and it is
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    40
 * assumed to not be in the queue_list. Otherwise, the next entry is taken from the queue.
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    41
 *
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    42
 * If the queue is empty and no entry is given, does nothing.
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    43
 */
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    44
static err_t irc_queue_pump (struct irc_queue *queue, struct irc_queue_entry *next)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    45
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    46
    err_t err;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    47
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    48
    // pop the next entry?
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    49
    if (next == NULL) {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    50
        // take it from the head of the list
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    51
        next = TAILQ_FIRST(&queue->list);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    52
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    53
        // nothing to do?
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    54
        if (!next)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    55
            return SUCCESS;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    56
        
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    57
        // and then remove it
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    58
        TAILQ_REMOVE(&queue->list, next, queue_list);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    59
    }
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    60
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    61
    // send it
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    62
    if ((err = irc_queue_send_buf(queue, next->line_buf)))
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    63
        goto error;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    64
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    65
    // ok, release it
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    66
    free(next);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    67
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    68
    // done
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    69
    return SUCCESS;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    70
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    71
error:
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    72
    // hmm... re-insert and return error, we can try again later
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    73
    TAILQ_INSERT_HEAD(&queue->list, next, queue_list);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    74
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    75
    return err;    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    76
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    77
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    78
/**
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    79
 * Schedule the queue's timer for execution once the timer has expired, or immediately if it's not full. If next is
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    80
 * given, it should be the next entry to send, and not part of the queue_list.
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    81
 */
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    82
static err_t irc_queue_schedule (struct irc_queue *queue)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    83
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    84
    time_t now = time(NULL);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    85
    struct timeval tv;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    86
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    87
    // calculate the timeout
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    88
    int timeout = (queue->timer - (now + IRC_QUEUE_WINDOW));
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    89
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    90
    // setup the timeout, zero if we don't actually need to wait...
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    91
    tv.tv_sec = timeout > 0 ? timeout : 0;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    92
    tv.tv_usec = 0;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    93
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    94
    // setup the timer event
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    95
    if (evtimer_add(queue->ev, &tv))
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    96
        return ERR_EVENT_ADD;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    97
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    98
    // ok
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    99
    return SUCCESS;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   100
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   101
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   102
/**
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   103
 * Our timer callback
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   104
 */
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   105
static void irc_queue_timer (int fd, short what, void *arg)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   106
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   107
    time_t now = time(NULL);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   108
    struct irc_queue *queue = arg;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   109
    err_t err;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   110
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   111
    (void) fd;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   112
    (void) what;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   113
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   114
    // pump the queue until our timer is full again, or the queue is empty
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   115
    while (queue->timer <= now + IRC_QUEUE_WINDOW && !TAILQ_EMPTY(&queue->list)) {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   116
        if ((err = irc_queue_pump(queue, NULL))) {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   117
            log_warn("irc_queue_pump: %s", error_name(err));
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   118
            break;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   119
        }
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   120
    }
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   121
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   122
    // reschedule if needed
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   123
    if (!TAILQ_EMPTY(&queue->list)) {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   124
        if ((err = irc_queue_schedule(queue))) {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   125
            log_err(err, "irc_queue_scheulde");
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   126
        }
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   127
    }
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   128
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   129
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   130
err_t irc_queue_create (struct irc_queue **queue_ptr, struct line_proto *lp, struct error_info *err)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   131
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   132
    struct irc_queue *queue;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   133
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   134
    // alloc
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   135
    if ((queue = calloc(1, sizeof(*queue))) == NULL)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   136
        return SET_ERROR(err, ERR_CALLOC);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   137
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   138
    // create the timer event
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   139
    // XXX: using the sock module ev_base
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   140
    if ((queue->ev = evtimer_new(_sock_stream_ctx.ev_base, &irc_queue_timer, queue)) == NULL)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   141
        JUMP_SET_ERROR(err, ERR_EVENT_NEW);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   142
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   143
    // initialize
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   144
    queue->lp = lp;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   145
    queue->timer = time(NULL);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   146
    TAILQ_INIT(&queue->list); 
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   147
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   148
    // ok
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   149
    *queue_ptr = queue;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   150
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   151
    return SUCCESS;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   152
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   153
error:
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   154
    // cleanup
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   155
    free(queue);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   156
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   157
    return ERROR_CODE(err);    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   158
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   159
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   160
/**
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   161
 * Attempt to send a irc_line directly on the queue's line_proto, otherwise enqueueing it for later transmission.
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   162
 */
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   163
static err_t irc_queue_send_direct (struct irc_queue *queue, const struct irc_line *line)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   164
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   165
    char line_buf[IRC_LINE_MAX + 2];
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   166
    err_t err;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   167
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   168
    // format
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   169
    if ((err = irc_line_build(line, line_buf)))
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   170
        return err;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   171
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   172
    // add CRLF
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   173
    strcat(line_buf, "\r\n");
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   174
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   175
    // send
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   176
    // XXX: handle send-buffer-full by enqueuing it after all
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   177
    return irc_queue_send_buf(queue, line_buf);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   178
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   179
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   180
/**
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   181
 * Enqueue a irc_line onto the queue's list, and schedule the timer for execution
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   182
 */
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   183
static err_t irc_queue_put (struct irc_queue *queue, const struct irc_line *line)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   184
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   185
    struct irc_queue_entry *entry;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   186
    err_t err;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   187
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   188
    // alloc
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   189
    if ((entry = calloc(1, sizeof(*entry))) == NULL)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   190
        return ERR_CALLOC;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   191
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   192
    // format
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   193
    if ((err = irc_line_build(line, entry->line_buf)))
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   194
        goto error;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   195
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   196
    // add CRLF
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   197
    strcat(entry->line_buf, "\r\n");
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   198
   
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   199
    // then re-schedule the queue
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   200
    if ((err = irc_queue_schedule(queue)))
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   201
        goto error;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   202
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   203
    // append to end of list
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   204
    TAILQ_INSERT_TAIL(&queue->list, entry, queue_list);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   205
 
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   206
    // ok
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   207
    return SUCCESS;
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   208
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   209
error:
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   210
    // cleanup
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   211
    free(entry);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   212
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   213
    return err;    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   214
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   215
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   216
err_t irc_queue_process (struct irc_queue *queue, const struct irc_line *line)
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   217
{
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   218
    // current time
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   219
    time_t now = time(NULL);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   220
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   221
    if (queue->timer < now + IRC_QUEUE_WINDOW) {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   222
        // timer is OK, send directly
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   223
        return irc_queue_send_direct(queue, line);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   224
    
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   225
    } else {
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   226
        // enqueue for later transmission
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   227
        return irc_queue_put(queue, line);
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   228
    }
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   229
}
9d489b1039b2 implement irc_queue, with some basic functionality tests
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
   230
91
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   231
void irc_queue_destroy (struct irc_queue *queue)
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   232
{
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   233
    struct irc_queue_entry *entry, *next;
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   234
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   235
    // free all entries
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   236
    for (entry = TAILQ_FIRST(&queue->list); entry; entry = next) {
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   237
        next = TAILQ_NEXT(entry, queue_list);
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   238
        free(entry);
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   239
    }
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   240
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   241
    // the event
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   242
    event_free(queue->ev);
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   243
    
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   244
    // the queue itself
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   245
    free(queue);
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   246
}
bca23cbe1dce implement irc_queue for irc_conn, and add missing irc_queue_destroy, fix irc_conn_destroy
Tero Marttila <terom@fixme.fi>
parents: 90
diff changeset
   247