#include #include "cpuqueue.hh" #include #include CPUQueue::CPUQueue() : _last(0), _drops(0) { memset(&_q, 0, sizeof(_q)); } CPUQueue::~CPUQueue() { } int CPUQueue::configure(Vector &conf, ErrorHandler *errh) { unsigned new_capacity = 128; if (cp_va_parse(conf, this, errh, cpOptional, cpUnsigned, "maximum queue length", &new_capacity, cpEnd) < 0) return -1; _capacity = new_capacity; return 0; } int CPUQueue::initialize(ErrorHandler *errh) { for (int i=0; ierror("out of memory!"); _drops = 0; _last = 0; return 0; } void CPUQueue::cleanup(CleanupStage) { for (int i=0; ikill(); delete[] _q[i]._q; _q[i]._q = 0; } } inline Packet * CPUQueue::deq(int n) { if (_q[n]._head != _q[n]._tail) { Packet *p = _q[n]._q[_q[n]._head]; _q[n]._head = next_i(_q[n]._head); return p; } else return 0; } void CPUQueue::push(int, Packet *p) { int n = click_current_processor(); int next = next_i(_q[n]._tail); if (next != _q[n]._head) { _q[n]._q[_q[n]._tail] = p; _q[n]._tail = next; } else { p->kill(); _drops++; } } Packet * CPUQueue::pull(int port) { int n = _last; Packet *p = 0; for (int i = 0; i < NUM_CLICK_CPUS; i++) { p = deq(n); n++; if (n == NUM_CLICK_CPUS) n = 0; if (p) { _last = n; return p; } } return 0; } String CPUQueue::read_handler(Element *e, void *thunk) { CPUQueue *q = static_cast(e); switch (reinterpret_cast(thunk)) { case 0: return String(q->capacity()); case 1: return String(q->drops()); default: return ""; } } void CPUQueue::add_handlers() { add_read_handler("capacity", read_handler, (void *)0); add_read_handler("drops", read_handler, (void *)1); } ELEMENT_REQUIRES(linuxmodule) EXPORT_ELEMENT(CPUQueue) ELEMENT_MT_SAFE(CPUQueue)