agent.cc
上传用户:rrhhcc
上传日期:2015-12-11
资源大小:54129k
文件大小:23k
源码类别:

通讯编程

开发平台:

Visual C++

  1. /*
  2.  * Copyright (c) 1997 University of Southern California.
  3.  * All rights reserved.
  4.  *
  5.  * Redistribution and use in source and binary forms, with or without
  6.  * modification, are permitted provided that the following conditions
  7.  * are met:
  8.  * 1. Redistributions of source code must retain the above copyright
  9.  *    notice, this list of conditions and the following disclaimer.
  10.  * 2. Redistributions in binary form must reproduce the above copyright
  11.  *    notice, this list of conditions and the following disclaimer in the
  12.  *    documentation and/or other materials provided with the distribution.
  13.  * 3. All advertising materials mentioning features or use of this software
  14.  *    must display the following acknowledgement:
  15.  *      This product includes software developed by the Information Sciences
  16.  *      Institute of the University of Southern California.
  17.  * 4. Neither the name of the University nor of the Institute may be used
  18.  *    to endorse or promote products derived from this software without
  19.  *    specific prior written permission.
  20.  *
  21.  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  22.  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  23.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  24.  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  25.  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  26.  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  27.  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  28.  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  29.  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  30.  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  31.  * SUCH DAMAGE.
  32.  *
  33.  * @(#) $Header: /cvsroot/nsnam/nam-1/agent.cc,v 1.39 2001/08/10 01:45:46 mehringe Exp $ (LBL)
  34.  */
  35. #include <stdlib.h>
  36. #ifdef WIN32
  37. #include <windows.h>
  38. #endif
  39. #include "netview.h"
  40. #include "psview.h"
  41. #include "node.h"
  42. #include "feature.h"
  43. #include "agent.h"
  44. #include "edge.h"
  45. #include "paint.h"
  46. #include "monitor.h"
  47. #include "sincos.h"
  48. static int g_agent_count = 1;  // Used to give unique id's to each agent
  49. //----------------------------------------------------------------------
  50. //  Wrapper for tcl creation of Agents 
  51. //----------------------------------------------------------------------
  52. static class AgentClass : public TclClass {
  53. public:
  54.   AgentClass() : TclClass("Agent") {} 
  55.   TclObject * create(int argc, const char*const* argv) {
  56.     Agent * agent;
  57.     const char * type;
  58.     int id;
  59.     double size;
  60.     type = argv[4];
  61.     id  = strtol(argv[5], NULL, 10);
  62.     size  = strtod(argv[6], NULL);
  63.     agent = new BoxAgent(type, id, size);
  64.     return agent;
  65.   }
  66. } class_agent;
  67. //----------------------------------------------------------------------
  68. //----------------------------------------------------------------------
  69. Agent::Agent(const char * type, int id, double _size) :
  70.   Animation(0, 0) {
  71.   setDefaults();
  72.   size(_size);
  73.   label_ = new char[strlen(type) + 1];
  74.   strcpy(label_, type);
  75.   number_ = id;
  76.   // Make sure new agents will have unique ids
  77.   if (g_agent_count <= id) {
  78.     g_agent_count = id + 1;
  79.   }
  80. }
  81. //----------------------------------------------------------------------
  82. // Agent::Agent(const char* name, double size)
  83. //----------------------------------------------------------------------
  84. Agent::Agent(const char* name, double _size) :
  85.   Animation(0, 0),
  86.   next_(0),
  87.   node_(0),
  88.   x_(0.0),
  89.   y_(0.0),
  90.   features_(NULL),
  91.   edge_(NULL),
  92.   angle_(NO_ANGLE),
  93.   anchor_(0),
  94.   mark_(0),
  95.   color_(0),
  96.   window_(20),
  97.   windowInit_(1),
  98.   maxcwnd_(0),
  99.   packetSize_(210),
  100.   interval_(0.0375),
  101.   tracevar_(0),
  102.   start_(0.0),
  103.   stop_(10.0),
  104.   produce_(0)
  105. {
  106.   size(_size);
  107.   AgentPartner_ = NULL;
  108.   flowcolor_ = NULL;
  109.   flowcolor("black");
  110.   number_ = g_agent_count;
  111.   g_agent_count++;
  112.   traffic_sources_ = NULL;
  113.   label_ = new char[strlen(name) + 1];
  114.   strcpy(label_, name);
  115.   paint_ = Paint::instance()->thin();
  116.   setDefaults();
  117. }
  118. //----------------------------------------------------------------------
  119. //----------------------------------------------------------------------
  120. void
  121. Agent::setDefaults() {
  122.   next_ = NULL;
  123.   node_ = NULL;
  124.   AgentPartner_ = NULL;
  125.   x_ = 0.0;
  126.   y_ = 0.0;
  127.   features_ = NULL;
  128.   edge_ = NULL;
  129.   angle_ = NO_ANGLE;
  130.   anchor_ = 0;
  131.   mark_ = 0;
  132.   color_ = NULL;
  133.   window_ = 20;
  134.   windowInit_ = 1;
  135.   maxcwnd_ = 0;
  136.   packetSize_ = 210;
  137.   interval_ = 0.0375;
  138.   tracevar_ = NULL;
  139.   start_ = 0.0;
  140.   stop_  = 1.0;
  141.   produce_ = 0;
  142.   flowcolor_ = NULL;
  143.   flowcolor("black");
  144.   traffic_sources_ = NULL;
  145.   paint_ = Paint::instance()->thin();
  146.   showLink();
  147. }
  148. float Agent::distance(float x, float y) const {
  149. return ((x_-x)*(x_-x) + (y_-y)*(y_-y));
  150. }
  151. void Agent::color(const char* name)
  152. {
  153.      if (name[0] == 0) {
  154.           if (color_) {
  155.        delete []color_;
  156.        color_ = 0;
  157.   }
  158.   return;
  159.      }
  160.      if (color_)
  161.        delete []color_;
  162.      color_ = new char[strlen(name) + 1];
  163.      strcpy(color_, name);
  164. }
  165. void Agent::size(double s)
  166. {
  167. size_ = s;
  168.   width_ = s;
  169.   height_ = s;
  170. update_bb();
  171. }
  172. void Agent::update_bb() {
  173. double off = 0.5 * size_;
  174. /*XXX*/
  175. bb_.xmin = x_ - off;
  176. bb_.ymin = y_ - off;
  177. bb_.xmax = x_ + off;
  178. bb_.ymax = y_ + off;
  179. }
  180. //----------------------------------------------------------------------
  181. // TrafficSource * 
  182. // TrafficSource::addTrafficSource(TrafficSource * ts)
  183. //   - Add traffic source to the trafficsources_ list
  184. //   - Returns the traffic source before the one just added
  185. //----------------------------------------------------------------------
  186. TrafficSource * 
  187. Agent::addTrafficSource(TrafficSource * ts) {
  188.   TrafficSource * run, * last;
  189.   run = traffic_sources_;
  190.   last = NULL;
  191.   // Find last traffic source on list
  192.   while (run) {
  193.     last = run;
  194.     run = run->next_;
  195.   }
  196.   // if it exists then add it to the list
  197.   if (last) {
  198.     last->next_ = ts;
  199.   } else {
  200.     traffic_sources_ = ts;
  201.   }  
  202.   return last;
  203. }
  204. //----------------------------------------------------------------------
  205. // TrafficSource *
  206. // Agent::removeTrafficSource(TrafficSource * ts) {
  207. //----------------------------------------------------------------------
  208. TrafficSource *
  209. Agent::removeTrafficSource(TrafficSource * ts) {
  210.   // ts->previous_ should be NULL for the first traffic source
  211.   // attached to this agent
  212.   if (ts->previous_) {
  213.     ts->previous_->next_ = ts->next_;
  214.   } else {
  215.     // I am the first traffic source so
  216.     // make agent point to my next_
  217.     traffic_sources_ = ts->next_;
  218.   }
  219.   if (ts->next_) {
  220.     ts->next_->previous_ = ts->previous_;
  221.   }
  222.   return ts;
  223. }
  224. void Agent::add_feature(Feature* f) {
  225.        f->next_ = features_;
  226.        features_ = f;
  227. }
  228. Feature *Agent::find_feature(char *name) const
  229. {
  230.   /*given a feature, remove it from an agent's feature list*/
  231.   Feature *ft;
  232.   ft=features_;
  233.   while (ft!=NULL)
  234.     {
  235.       if (strcmp(ft->name(), name)==0)
  236. return ft;
  237.       ft=ft->next();
  238.     }
  239.   return NULL;
  240. }
  241.  
  242.  
  243. void Agent::delete_feature(Feature* r)
  244. {
  245.   /*given a feature, remove it from an agent's feature list*/
  246.   Feature *f1, *f2;
  247.   f1=features_;
  248.   f2=features_;
  249.   while ((f1!=r)&&(f1!=NULL))
  250.     {
  251.       f2=f1;
  252.       f1=f1->next();
  253.     }
  254.   if (f1==r)
  255.     {
  256.       f2->next(f1->next());
  257.       if (f1==features_)
  258. features_=f1->next();
  259.     }
  260. }
  261.  
  262.  
  263. void Agent::label(const char* name, int anchor)
  264. {
  265. delete label_;
  266. label_ = new char[strlen(name) + 1];
  267. strcpy(label_, name);
  268. anchor_ = anchor;
  269. }
  270. void Agent::drawlabel(View* nv) const
  271. {
  272. /*XXX node number */
  273. if (label_ != 0)
  274. nv->string(x_, y_, size_, label_, anchor_);
  275. }
  276. /*
  277. void Agent::drawlabel(PSView* nv) const
  278. {
  279. if (label_ != 0)
  280. nv->string(x_, y_, size_, label_, anchor_);
  281. }
  282. */
  283. //----------------------------------------------------------------------
  284. // void
  285. // Agent::flowcolor(const char* color)
  286. //----------------------------------------------------------------------
  287. void
  288. Agent::flowcolor(const char* color) {
  289.  if (color[0] == 0) {
  290.    if (flowcolor_) {
  291.      delete []flowcolor_;
  292.      flowcolor_ = 0;
  293.    }
  294.    return;
  295.  }
  296.        
  297.  if (flowcolor_)
  298.    delete []flowcolor_;
  299.  flowcolor_ = new char[strlen(color) + 1];
  300.  strcpy(flowcolor_, color);
  301. }
  302. void Agent::tracevar(const char* var)
  303. {
  304.         if (var[0] == 0) {
  305.        if (tracevar_) {
  306.               delete []tracevar_;
  307.       tracevar_ = 0;
  308.        }
  309.        return;
  310. }
  311.         if (tracevar_)    delete []tracevar_;
  312. tracevar_ = new char[strlen(var) + 1];
  313. strcpy(tracevar_, var);
  314. }
  315. void Agent::reset(double)
  316. {
  317. paint_ = Paint::instance()->thick();
  318. }
  319. void Agent::place(double x, double y) { 
  320. x_ = x;
  321. y_ = y;
  322. mark_ = 1;
  323. update_bb();
  324. }
  325. const char* Agent::info() const {
  326.   static char text[128];
  327.   if(AgentPartner_!=NULL) {
  328.     sprintf(text, "Agent %s-%dnConnected to: %s on Node %d",
  329.                    name(), number(),
  330.                    AgentPartner_->name(),
  331.                    AgentPartner_->node_->num());
  332.   } else {
  333.     sprintf(text, "Agent: %s", label_);
  334.   }
  335.   return (text);
  336. }
  337. const char* Agent::getname() const
  338. {
  339.   static char text[128];
  340.   sprintf(text, "a %s", label_);
  341.   return (text);
  342. }
  343. void Agent::monitor(Monitor *m, double now, char *result, int len)
  344. {
  345.   char buf[256];
  346.   Feature *f;
  347.   monitor_=m;
  348.   sprintf(result, "Agent: %s", label_);
  349.   for(f=features_;f!=NULL;f=f->next()) {
  350.     strcat(result, "n");
  351.     f->monitor(now, buf, 255);
  352.     if (strlen(result)+strlen(buf)<(unsigned int)len)
  353.       strcat(result, buf);
  354.     else {
  355.       fprintf(stderr, "not enough space for monitor return stringn");
  356.       return;
  357.     }
  358.   }
  359. }
  360. //----------------------------------------------------------------------
  361. // BoxAgent::BoxAgent(const char * type, int id, double size);
  362. //----------------------------------------------------------------------
  363. BoxAgent::BoxAgent(const char * type, int id, double size) :
  364.   Agent(type,id,size) {
  365.   BoxAgent::size(size);
  366. }
  367. //----------------------------------------------------------------------
  368. // BoxAgent::BoxAgent(const char* name, double size)
  369. //----------------------------------------------------------------------
  370. BoxAgent::BoxAgent(const char* name, double size) :
  371.   Agent(name, size) {
  372.   BoxAgent::size(size);
  373. }
  374. //----------------------------------------------------------------------
  375. // void
  376. // BoxAgent::size(double s)
  377. //----------------------------------------------------------------------
  378. void
  379. BoxAgent::size(double s) {
  380. //  double delta = 0.5 * s;
  381.   
  382.   // Set size_ to s
  383.   Agent::size(s);
  384.  // x0_ = x_ - delta;
  385.  // y0_ = y_ - delta;
  386.  // x1_ = x_ + delta;
  387.  // y1_ = y_ + delta;
  388.  
  389.   x0_ = x_;
  390.   y0_ = y_;
  391. //  x1_ = x_ + s;
  392. //  y1_ = y_ + s*0.5;
  393.   width_ = s;
  394.   height_ = s*0.5;
  395.  update_bb();
  396. }
  397. void BoxAgent::update_bb() {
  398. bb_.xmin = x0_;
  399. bb_.ymin = y0_;
  400. bb_.xmax = x0_ + width_;
  401. bb_.ymax = y0_ + height_;
  402. }
  403. //----------------------------------------------------------------------
  404. //----------------------------------------------------------------------
  405. void 
  406. BoxAgent::findClosestCornertoPoint(double x, double y, double &corner_x,
  407.                                    double &corner_y) const {
  408.   double distance_0, distance_1;
  409.   // Calculate the difference
  410.   distance_0 = x0_ - x;
  411.   distance_1 = x0_ + width_ - x;
  412.   //We only want the magnitude
  413.   if (distance_0 < 0) {
  414.     distance_0 = -distance_0;
  415.   }
  416.   if (distance_1 < 0) {
  417.     distance_1 = -distance_1;
  418.   }
  419.   if (distance_0 < distance_1) {
  420.     corner_x = x0_;
  421.   } else {
  422.     corner_x = x0_ + width_;
  423.   }
  424.   // Do the same for the y values
  425.   distance_0 = y0_ - y;
  426.   distance_1 = y0_ + height_ - y;
  427.   if (distance_0 < 0) {
  428.     distance_0 = -distance_0;
  429.   }
  430.   if (distance_1 < 0) {
  431.     distance_1 = -distance_1;
  432.   }
  433.   if (distance_0 < distance_1) {
  434.     corner_y = y0_;
  435.   } else {
  436.     corner_y = y0_ + height_;
  437.   }
  438. }
  439. //----------------------------------------------------------------------
  440. //----------------------------------------------------------------------
  441. int 
  442. BoxAgent::inside(double, float px, float py) const {
  443. return (px >= x0_ && px <= (x0_ + width_) &&
  444.       py >= y0_ && py <= (y0_ + height_));
  445. }
  446. //----------------------------------------------------------------------
  447. // void 
  448. // BoxAgent::draw(View* nv, double ) const
  449. //   - Draw the agent label with a rectangle around it
  450. //   - Also draw monitors associated with it
  451. //----------------------------------------------------------------------
  452. void 
  453. BoxAgent::draw(View* nv, double time) {
  454.   double corner_x, corner_y, partner_corner_x, partner_corner_y;
  455.   double label_width, label_height, label_x, label_y;
  456.   char full_label[128];
  457.   // Draw line connecting this to its partner
  458.   if (AgentPartner_) {
  459.     if (draw_link_) {
  460.       AgentPartner_->findClosestCornertoPoint(x(), y(), 
  461.                                         partner_corner_x, partner_corner_y);
  462.       findClosestCornertoPoint(partner_corner_x, partner_corner_y,
  463.                                corner_x, corner_y);
  464.       nv->line(corner_x, corner_y, 
  465.                partner_corner_x, partner_corner_y,
  466.                paint_);
  467.     }
  468.   }
  469.     
  470.         
  471.   // Draw the label if it exists
  472.   if (label_ != 0) {
  473.     // Exapnd label to show partner id if connected
  474.     if (AgentPartner_) {
  475.       if (AgentRole_ == SOURCE) {
  476.         sprintf(full_label, "%s - %d", label_, number_);
  477.       } else {
  478.         sprintf(full_label, "%s - %d", label_, AgentPartner_->number());
  479.       }
  480.     } else {
  481.       sprintf(full_label, "%s", label_);
  482.     }
  483.     // We have to keep calculting the label width and height because
  484.     // we have no way of knowing if the user has zoomed in or out 
  485.     // on the current network view.
  486.     label_height = 0.9 * height_;
  487.     label_width = nv->getStringWidth(full_label, label_height);
  488.     // Add 10% of padding to width for the box
  489.     setWidth(1.1 * label_width);
  490.     place(x_,y_);
  491.     
  492.     // Center label in box
  493.     label_x = x0_ + (width_ - label_width);
  494.     label_y = y0_ + (height_ - label_height);
  495.     nv->string(full_label, label_x , label_y, label_height, NULL);
  496.     
  497.     update_bb();
  498.   }
  499.   
  500.   // Draw the rectangle 
  501.   nv->rect(x0_, y0_, x0_ + width_, y0_ + height_, paint_);
  502.   if (monitor_ != NULL) {
  503.     monitor_->draw(nv, (x0_ + x0_ + width_)/2, y0_ - height_);
  504.   }
  505. }
  506. /*
  507. void BoxAgent::draw(PSView* nv, double ) const
  508. {
  509.   nv->rect(x0_, y1_, x1_, y0_, paint_);
  510.   if (label_ != 0)
  511.     {
  512.       nv->string((x0_+x1_)/2, (y0_+y1_)/2, size_*0.75, label_, ANCHOR_CENTER);
  513.     }
  514. }
  515. */
  516. //----------------------------------------------------------------------
  517. // void 
  518. // BoxAgent::place(double x, double y) {
  519. //----------------------------------------------------------------------
  520. void 
  521. BoxAgent::place(double x, double y) {
  522.   double nsin, ncos;
  523.   Agent::place(x, y);  // Save original x,y values
  524.   SINCOSPI(angle_, &nsin, &ncos);
  525.   /*XXX should really use the X-display width*/
  526.   //width_ = strlen(label_)/2;
  527.   //width_ = strlen(label_) * 2.0;
  528.   
  529.   // on solaris, sin(M_PI) != 0 !!!
  530.   
  531.   // angle_ equals 0 or M_PI
  532.   if ((nsin < 1.0e-8) && (nsin > -1.0e-9)) {
  533.     y0_ = y_ - 0.5 * height_;
  534.     //y_ = y0_;
  535.   
  536.   // angle is in the first 2 quadrants
  537.   // i.e. between 0 and M_PI
  538.   } else if (nsin > 0) {
  539.     y0_ = y_;
  540.    
  541.   // angle_ is greater than M_PI but less than 2M_PI
  542.   } else {
  543.     // Move down twice as far to make room for traffic source labels
  544.     y0_ = y_ - 2*height_;
  545.     //y_ = y0_;
  546.   }
  547.   // angle equals M_PI/2 or 3M_PI/2 
  548.   if ((ncos < 1.0e-8) && (ncos > -1.0e-9)) {
  549.     x0_ = x_ - width_;
  550.     //x_ = x0_;
  551.   // angle is in 1st or 4th quadrant
  552.   } else if (ncos > 0) {
  553.     x0_ = x_;
  554.   
  555.   //  angle is in 2nd or 3rd quadrant
  556.   //  i.e. between M_PI/2 and 3M_PI/2
  557.   } else {
  558.     x0_ = x_ - width_;
  559.     //x_ = x0_;
  560.   }
  561.   update_bb();
  562. }
  563. //----------------------------------------------------------------------
  564. // int
  565. // Agent::writeNsDefinitionScript(FILE *file)
  566. //----------------------------------------------------------------------
  567. int
  568. Agent::writeNsDefinitionScript(FILE *file) {
  569.   TrafficSource * ts;
  570.   // Create agent definition
  571.   fprintf(file, "set agent(%d) [new Agent/%s]n", number_, label_);
  572.   // Attach it to it's parent node
  573.   fprintf(file, "$ns attach-agent $node(%d) $agent(%d)n",
  574.                 node_->num(), number_);
  575.   if (AgentRole_ == SOURCE) {
  576.     // Set flow color for agent
  577.     fprintf(file, "n$ns color %d "%s"n", number_, flowcolor_);
  578.     // flow id
  579.     fprintf(file, "$agent(%d) set fid_ %dn", number_, number_);
  580.     // Packet Size
  581.     fprintf(file, "$agent(%d) set packetSize_ %dn", number_, packetSize_);
  582.     if (strcmp(name(), "TCP") == 0) { 
  583.       // Maximum window size
  584.       fprintf(file, "$agent(%d) set window_ %dn", number_, window_);
  585.       // Initial reset of cwnd
  586.       fprintf(file, "$agent(%d) set windowInit_ %dn", number_, windowInit_);
  587.       fprintf(file, "$agent(%d) set maxcwnd_ %dn", number_, maxcwnd_);
  588.       if (tracevar_) {
  589.         if ((strcmp(tracevar_, "cwnd_") == 0) || 
  590.             (strcmp(tracevar_, "ssthresh_") == 0)) {
  591.           fprintf(file, "$ns add-agent-trace $agent(%d) tcpn", number_);
  592.           fprintf(file, "$ns monitor-agent-trace $agent(%d)n", number_);
  593.           fprintf(file, "$agent(%d) set tracevar_ %sn", number_, tracevar_);
  594.         }
  595.       }
  596.     } else if (strcmp(name(), "TCP/Reno") == 0) { 
  597.     } else if (strcmp(name(), "TCP/NewReno") == 0) { 
  598.     } else if (strcmp(name(), "TCP/Vegas") == 0) { 
  599.     } else if (strcmp(name(), "TCP/Sack1") == 0) { 
  600.     } else if (strcmp(name(), "TCP/Fack") == 0) { 
  601.     } else if (strcmp(name(), "UDP") == 0) { 
  602.     }
  603.   } else if (AgentRole_ == DESTINATION) {
  604.     // We have a sink
  605.     if (strcmp(name(), "TCPSink") == 0) { 
  606.       fprintf(file, "$agent(%d) set packetSize_ %dn", number_, packetSize_);
  607.     } else if (strcmp(name(), "TCPSink/DelAck") == 0) { 
  608.       fprintf(file, "$agent(%d) set packetSize_ %dn", number_, packetSize_);
  609.       fprintf(file, "$agent(%d) set interval_ %fn", number_, interval_);
  610.     } else if (strcmp(name(), "TCPSink/Sack1") == 0) {
  611.      // Ask about this one look at ns doc 29.2.3 for proper 
  612.      // syntax
  613.     }
  614.     // if it is NULL or anything else do nothing
  615.   }
  616.   
  617.    /*
  618.   // CBR source agents
  619.     } else if (strcmp(name(), "CBR")==0) {
  620.       fprintf(file, "n$ns color %d "%s"n",number_, flowcolor_);
  621.       fprintf(file, "set agent%d [new Agent/%s]n", number_, label_);
  622.       fprintf(file, "$ns attach-agent $n(%d) $agent%d n", node_->num(), number_);
  623.       fprintf(file, "$agent%d set fid_ %dn", number_, number_);
  624.       fprintf(file, "$agent%d set packetSize_ %dn", number_, packetSize_);
  625.       fprintf(file, "$agent%d set interval_ %fn", number_, interval_);
  626.   } else if (AgentRole_ == DESTINATION) {
  627.     // TCP/Full destination agents 
  628.     } else if (strcmp(name(), "TCP/FullTcp") == 0){
  629.       fprintf(file, "nset agent%d [new Agent/%s]n", number_, label_);
  630.       fprintf(file, "$ns attach-agent $node(%d) $agent%d n", node_->num(), number_);
  631.       fprintf(file, "$agent%d listenn", number_);
  632.     // all destination agents (NULL)
  633.     } else {
  634.       fprintf(file, "nset agent%d [new Agent/%s]n", number_, label_);
  635.       fprintf(file, "$ns attach-agent $node(%d) $agent%dn", node_->num(), number_);
  636.     }
  637.   }
  638. */
  639.   if (traffic_sources_) {
  640.       // # Create a CBR traffic source and attach it to udp0
  641.       // set cbr0 [new Application/Traffic/CBR]
  642.       // $cbr0 set packetSize_ 500
  643.       // $cbr0 set interval_ 0.005
  644.       // $cbr0 attach-agent $udp0
  645.     fprintf(file, "n# Create traffic sources and add them to the agent.n");
  646.     for (ts = traffic_sources_; ts; ts = ts->next_) {
  647.       ts->writeNsDefinitionScript(file);
  648.     }
  649.   }
  650.   return 0;
  651. }
  652. //----------------------------------------------------------------------
  653. // int
  654. // Agent::writeNsConnectionScript(FILE * file)
  655. //----------------------------------------------------------------------
  656. int
  657. Agent::writeNsConnectionScript(FILE * file) {
  658.   TrafficSource * ts;
  659.   if (AgentRole_ == SOURCE) {
  660.     fprintf(file, "$ns connect $agent(%d) $agent(%d)nn", 
  661.                   number_, AgentPartner_->number_);
  662.     fprintf(file, "n# Traffic Source actions.n");
  663.     for (ts = traffic_sources_; ts; ts = ts->next_) {
  664.       ts->writeNsActionScript(file);
  665.     }
  666.   }
  667.   return 0;
  668. }
  669. //----------------------------------------------------------------------
  670. //
  671. //----------------------------------------------------------------------
  672. int Agent::saveAsEnam(FILE *file) {
  673.   if ((AgentRole_ == 10)&&(strcmp(name(), "CBR")!=0)) {
  674.     if (AgentPartner_ != NULL) 
  675.       fprintf(file, "##g -t * -l %s -r %d -s %d -c %s -i %d -w %d -m %d -t %s -b %f -p %d -o %f -n %d -u %dn",
  676.           label_, AgentRole_, node_->num(), flowcolor_, windowInit_, window_, 
  677.           maxcwnd_, tracevar_, start_, produce_, stop_, number_, 
  678.           AgentPartner_->number_);
  679.     else 
  680.       fprintf(file, "##g -t * -l %s -r %d -s %d -c %s -i %d -w %d -m %d -t %s -b %f -p %d -o %f -n %dn",
  681.           label_, AgentRole_, node_->num(), flowcolor_, windowInit_, window_,
  682.           maxcwnd_, tracevar_, start_, produce_, stop_, number_);
  683.   } else if (((AgentRole_ == SOURCE) || 
  684.               (AgentRole_ == 10)) &&
  685.              (strcmp(name(), "CBR")==0)) {
  686.     if (AgentPartner_ != NULL)
  687.       fprintf(file, "##g -t * -l %s -r %d -s %d -c %s -k %d -v %f -b %f -o %f -n %d -u %d n",
  688.            label_, AgentRole_, node_->num(), flowcolor_, packetSize_, 
  689.            interval_, start_, stop_, number_, AgentPartner_->number_);
  690.     else 
  691.       fprintf(file, "##g -t * -l %s -r %d -s %d -c %s -k %d -v %f -b %f -o %f -n %dn",
  692.            label_, AgentRole_, node_->num(), flowcolor_, packetSize_,
  693.            interval_, start_, stop_, number_);
  694.   } else {
  695.     if (AgentPartner_ != NULL)
  696.       fprintf(file, "##g -t * -l %s -r %d -s %d -n %d -u %d n",
  697.                     label_, AgentRole_, node_->num(), number_,
  698.                     AgentPartner_->number_);
  699.     else 
  700.       fprintf(file, "##g -t * -l %s -r %d -s %d -n %dn",
  701.                     label_, AgentRole_, node_->num(), number_);
  702.   }
  703.   return(0);
  704. }
  705. //----------------------------------------------------------------------
  706. //----------------------------------------------------------------------
  707. const char* Agent::property() {
  708.   rgb *color;
  709.   color=Paint::instance()->paint_to_rgb(paint_);
  710.   static char text[256];
  711.   char * p;
  712.   // Header
  713.   p = text;
  714.   sprintf(text, "{"Agent: %s-%d" title title "Agent %d"} ",
  715.                 name(), number_, number_);
  716.   if (AgentRole_ == SOURCE) {
  717.     p = &text[strlen(text)];
  718.     sprintf(p, "{"Flow Color" flowcolor_ color %s} ", flowcolor_);
  719.     p = &text[strlen(text)];
  720.     sprintf(p, "{"Packet Size" packetSize_ text %d} ", packetSize_);
  721.     
  722.     //TCP source agents
  723.     if (strcmp(name(), "TCP") == 0) {
  724.       p = &text[strlen(text)];
  725.       sprintf(p, "{"Initial Window Size" windowInit_ text %d} ", windowInit_);
  726.       p = &text[strlen(text)];
  727.       sprintf(p, "{"Window" window_ text %d} ", window_); 
  728.       p = &text[strlen(text)];
  729.       sprintf(p, "{"Max Cwnd" maxcwnd_ text %d} ", maxcwnd_);
  730.     } 
  731.   } else if (AgentRole_ == DESTINATION) {
  732.     p = &text[strlen(text)];
  733.     sprintf(p, "{"Partner" partner_number text %d} ", AgentPartner_->num());
  734.   } else {
  735.     p = &text[strlen(text)];
  736.     sprintf(p, "{"To edit this agent's properties connect agent to it's partner." partner_number label  }");
  737.   }
  738.   return(text);
  739. }