[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Errors in compilation



I tried to add a subclass of queue called stfq (to implement start
time fair queuing). When I compiled it, it gave the following error:


stfq.o: In function `StfqClass type_info function':
/v/hank/v61/manisha/ns-2.1b4/stfq.cc(.text+0x14): undefined reference to `Stfq::Handler virtual table'
/v/hank/v61/manisha/ns-2.1b4/stfq.cc(.text+0x18): undefined reference to `Stfq::Handler virtual table'
/v/hank/v61/manisha/ns-2.1b4/stfq.cc(.text+0x20): undefined reference to `Stfq virtual table'
/v/hank/v61/manisha/ns-2.1b4/stfq.cc(.text+0x24): undefined reference to `Stfq virtual table'

Could someone tell me what is the error.

Thanks

--sudhir


The code is attached below:
-------------------------------------------------------------------------------
#include <stdlib.h>
#include <string.h>
#include "queue.h"

#define MAXFLOW 32

class Stfq : public Queue {
public: 
  Stfq();
  virtual int command(int argc, const char*const* argv);
  Packet *deque(void);
  void enque(Packet *pkt);
  void recv(Packet* p, Handler* h);
protected:
  struct flowState {
    Queue* q_;
    //    Packet* hol_;   /* head-of-line packet for each flow */
    double finishTag_; /* Stfq finish tag for hol packet */
    double startTag_; /* Stfq finish tag for hol packet */
    //Handler* handler_;
    double weight;// dunno why I keep this!!
  } fs_[MAXFLOW];
  int active;
  double  max_finish_tag;
};

static class StfqClass : public TclClass {
 public:
  StfqClass() : TclClass("Queue/STFQ") {}
  TclObject* create(int, const char*const*) {
    return (new Stfq);
  }
} class_stfq;

Stfq::Stfq()
{
  for (int i = 0; i < MAXFLOW; ++i) {
    fs_[i].q_ = 0;
    fs_[i].hol_ = 0;
    fs_[i].finishTag_ = 0.;
    fs_[i].startTag_ = 0.;
  }
  active = -1;
  max_finish_tag = 0;
}
/*
int Stfq::command(int argc, const char*const* argv) {
  if (argc == 3) {
    if (!strcmp(argv[1], "weight")) {
      wt_ = atoi(argv[2]);
      return (TCL_OK);
    }
  }
  return Queue::command(argc, argv);
}
*/

Packet* Stfq::deque(void){
    
  int packet_len;
  int i;

  for(i=0; i< MAXFLOW;i++){
    if(current == -1)
      fs_[i].start_tag = 0;
    else if(current == MAXFLOW)
      fs_[i].start_tag = max(max_finish_tag,fs_[i].finish_tag);
    else
      fs_[i].start_tag = max(fs_[i].finish_tag,fs_[current].start_tag);
    
    packet_len = fs_[i].q_->head_->datalen() + fs_[i].q_->head_->hdrlen_;

    fs_[i].finish_tag = fs_[i].start_tag + packet_len/fs_[i];
    
  }
   
  max_finish_tag = fs_[0].finish_tag;

  for(i=1;i<MAXFLOW;i++)
    if(fs_[i].finish_tag > max_finish_tag) max_finish_tag = fs_[i].finish_tag;
  
  int min_start_tag=fs_[0].start_tag;
  current = 0;

  for(i=1;i<MAXFLOW;i++)
    if(fs_[i].start_tag < min_start_tag){
      min_start_tag = fs_[i].start_tag;
      current = i;
    }

  return fs_[i].q_->deque();
}

void Stfq::enque(Packet*)
{
        /* should never be called because we override recv */
        abort();
}

   
void Stfq::recv(Packet* p, Handler* handler)
{
  hdr_ip* h = (hdr_ip*)p->access(off_ip_);
  int flowid = h->flowid();
  /* shouldn't be called when head-of-line is pending */
  if (flowid >= MAXFLOW || fs_[flowid].hol_ != 0)
    abort();
  
  /*
   * Put this packet at the head-of-line for its queue
   * and set up scheduling state according to the
   * standard fair-queueing "finish time" equation.
   */

  fs_[flowid].q_->enque();

  if (!blocked_) {
    /*
     * We're not blocked.  Get a packet and send it on.
     * We perform an extra check because the queue
     * might drop the packet even if it was
     * previously empty!  (e.g., RED can do this.)
     */
    p = deque();
    if (p != 0) {
      blocked_ = 1;
      target_->recv(p, &qh_);
    }
  }
}


----------------------------------------------------------------------------