Example #1
0
int
MAIN(int argc, char *argv[]) {
  struct datapath_arg dparg;
  struct dpmgr *dpmgr;
  lagopus_thread_t *datapath;
  struct bridge *bridge;
  int portid;
  void *rv;
  int ret;

  dpmgr = dpmgr_alloc();
  if (dpmgr == NULL) {
    rte_exit(EXIT_FAILURE, "failed to initialize datapath manager.\n");
  }

  /* Create default bridge. */
  ret = dpmgr_bridge_add(dpmgr, "br0", 0);
  if (ret < 0) {
    rte_exit(EXIT_FAILURE, "Adding br0 failed\n");
  }

  /* register flow entries */
  bridge = dpmgr_bridge_lookup(dpmgr, "br0");
  register_flow(bridge->flowdb, 100000);
  flowdb_switch_mode_set(bridge->flowdb, SWITCH_MODE_OPENFLOW);

  /* Start datapath. */
  dparg.dpmgr = dpmgr;
  dparg.argc = argc;
  dparg.argv = argv;
  datapath_initialize(&dparg, &datapath);

  /* register all physical ports */
  for (portid = 0; portid < nb_ports; portid++) {
    if (lagopus_is_portid_enabled(portid) == true) {
      struct port nport;

      /* New port API. */
      nport.ofp_port.port_no = (uint32_t)portid + 1;
      nport.ifindex = (uint32_t)portid;
      printf("port id %u\n", nport.ofp_port.port_no);

      snprintf(nport.ofp_port.name , sizeof(nport.ofp_port.name),
               "eth%d", portid);
      dpmgr_port_add(dpmgr, &nport);
    }
  }

  /* assign all ports to br0 */
  for (portid = 0; portid < nb_ports; portid++) {
    dpmgr_bridge_port_add(dpmgr, "br0", (uint32_t)portid + 1);
  }
  datapath_start();

  while (lagopus_thread_wait(datapath, 1000000) == LAGOPUS_RESULT_TIMEDOUT) {
    sleep(1);
  }

  return 0;
}
Example #2
0
void
test_group_table_lookup(void) {
  struct dpmgr *dpmgr;
  struct bridge *bridge;
  struct group_table *group_table;
  struct group *group, *gl;
  struct ofp_group_mod group_mod;
  struct bucket_list bucket_list;
  struct ofp_error error;
  lagopus_result_t ret;

  dpmgr = dpmgr_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(dpmgr, "dpmgr alloc error.");
  ret = dpmgr_bridge_add(dpmgr, "br0", 0);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "bridge add error");
  bridge = dpmgr_bridge_lookup(dpmgr, "br0");
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "bridge alloc error.");
  TAILQ_INIT(&bucket_list);
  group_table = group_table_alloc(bridge);
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "group_table alloc error.");
  bridge->group_table = group_table;
  group_mod.group_id = 1;
  group_mod.type = OFPGT_ALL;
  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");
  gl = group_table_lookup(group_table, 0);
  TEST_ASSERT_NULL_MESSAGE(gl, "invalid group found error");
  gl = group_table_lookup(group_table, 1);
  TEST_ASSERT_EQUAL_MESSAGE(gl, group,
                            "invalid group found error");
}
Example #3
0
void
test_lagopus_receive_packet(void) {
  struct lagopus_packet pkt;
  struct dpmgr *my_dpmgr;
  struct port nport, *port;
  struct bridge *bridge;
  OS_MBUF *m;
  lagopus_result_t rv;

  my_dpmgr = dpmgr_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(my_dpmgr, "alloc error");
  rv = dpmgr_bridge_add(my_dpmgr, "br0", 0);
  TEST_ASSERT_EQUAL_MESSAGE(rv, LAGOPUS_RESULT_OK, "bridge add error\n");

  nport.type = LAGOPUS_PORT_TYPE_NULL; /* for test */
  nport.ifindex = 0;
  nport.ofp_port.hw_addr[0] = 1;
  dpmgr_port_add(my_dpmgr, &nport);
  nport.ifindex = 1;
  dpmgr_port_add(my_dpmgr, &nport);

  rv = dpmgr_bridge_port_add(my_dpmgr, "br0", 0, 1);
  TEST_ASSERT_EQUAL(rv, LAGOPUS_RESULT_OK);
  rv = dpmgr_bridge_port_add(my_dpmgr, "br0", 1, 2);
  TEST_ASSERT_EQUAL(rv, LAGOPUS_RESULT_OK);

  bridge = dpmgr_bridge_lookup(my_dpmgr, "br0");
  TEST_ASSERT_NOT_NULL(bridge);

  /* prepare packet */
  m = calloc(1, sizeof(*m));
  TEST_ASSERT_NOT_NULL_MESSAGE(m, "m: calloc error.");
  m->data = &m->dat[128];

  m->data[12] = 0x08;
  m->data[13] = 0x00;
  m->data[14] = 0x45;
  m->data[23] = IPPROTO_TCP;
  m->refcnt = 2;

  pkt.cache = NULL;
  pkt.table_id = 0;
  pkt.flags = 0;

  port = port_lookup(bridge->ports, 1);
  TEST_ASSERT_NOT_NULL_MESSAGE(port, "port lookup error.");
  lagopus_set_in_port(&pkt, port);
  TEST_ASSERT_EQUAL_MESSAGE(pkt.in_port, port, "port error.");
  TEST_ASSERT_EQUAL(pkt.in_port->bridge, bridge);

  lagopus_packet_init(&pkt, m);
  lagopus_receive_packet(port, &pkt);
  TEST_ASSERT_NOT_EQUAL_MESSAGE(pkt.in_port, NULL,
                                "port error.");
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "m->refcnt error.");
  dpmgr_free(my_dpmgr);
}
Example #4
0
void
test_lagopus_match_and_action(void) {
  struct action_list action_list;
  struct dpmgr *my_dpmgr;
  struct bridge *bridge;
  struct table *table;
  struct action *action;
  struct ofp_action_output *action_set;
  struct port nport, *port;
  struct lagopus_packet pkt;
  OS_MBUF *m;

  /* setup bridge and port */
  my_dpmgr = dpmgr_alloc();
  dpmgr_bridge_add(my_dpmgr, "br0", 0);

  nport.type = LAGOPUS_PORT_TYPE_NULL; /* for test */
  nport.ifindex = 0;
  nport.ofp_port.hw_addr[0] = 1;
  dpmgr_port_add(my_dpmgr, &nport);
  nport.ifindex = 1;
  dpmgr_port_add(my_dpmgr, &nport);

  dpmgr_bridge_port_add(my_dpmgr, "br0", 0, 1);
  dpmgr_bridge_port_add(my_dpmgr, "br0", 1, 2);

  bridge = dpmgr_bridge_lookup(my_dpmgr, "br0");
  TEST_ASSERT_NOT_NULL(bridge);

  flowdb_switch_mode_set(bridge->flowdb, SWITCH_MODE_OPENFLOW);
  table = table_get(bridge->flowdb, 0);
  table->userdata = new_flowinfo_eth_type();

  TAILQ_INIT(&action_list);
  action = calloc(1, sizeof(*action) + 64);
  action_set = (struct ofp_action_output *)&action->ofpat;
  action_set->type = OFPAT_OUTPUT;
  lagopus_set_action_function(action);
  TAILQ_INSERT_TAIL(&action_list, action, entry);

  m = calloc(1, sizeof(*m));
  TEST_ASSERT_NOT_NULL_MESSAGE(m, "calloc error.");
  m->data = &m->dat[128];
  m->refcnt = 2;

  port = port_lookup(bridge->ports, 1);
  TEST_ASSERT_NOT_NULL(port);
  lagopus_set_in_port(&pkt, port);
  TEST_ASSERT_EQUAL(pkt.in_port, port);
  TEST_ASSERT_EQUAL(pkt.in_port->bridge, bridge);
  pkt.table_id = 0;
  lagopus_packet_init(&pkt, m);
  lagopus_match_and_action(&pkt);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "match_and_action refcnt error.");
  free(m);
  dpmgr_free(my_dpmgr);
}
Example #5
0
void
setUp(void) {
  TEST_ASSERT_NULL(dpmgr);
  TEST_ASSERT_NULL(bridge);
  TEST_ASSERT_NOT_NULL(dpmgr = dpmgr_alloc());
  TEST_ASSERT_TRUE(LAGOPUS_RESULT_OK == dpmgr_bridge_add(dpmgr, bridge_name,
                   dpid));
  TEST_ASSERT_NOT_NULL(bridge = dpmgr_bridge_lookup(dpmgr, bridge_name));
}
Example #6
0
void
test_group_desc(void) {
  struct dpmgr *dpmgr;
  struct bridge *bridge;
  struct group_table *group_table;
  struct group *group;
  struct ofp_group_mod group_mod;
  struct bucket_list bucket_list;
  struct group_desc_list group_desc_list;
  struct group_desc *desc;
  struct ofp_error error;
  lagopus_result_t ret;

  dpmgr = dpmgr_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(dpmgr, "dpmgr alloc error.");
  ret = dpmgr_bridge_add(dpmgr, "br0", 0);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "bridge add error");
  bridge = dpmgr_bridge_lookup(dpmgr, "br0");
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "bridge alloc error.");
  TAILQ_INIT(&bucket_list);
  group_table = group_table_alloc(bridge);
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "group_table alloc error.");
  bridge->group_table = group_table;

  group_mod.group_id = 1;
  group_mod.type = OFPGT_ALL;
  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");

  group_mod.group_id = 1000000;
  group_mod.type = OFPGT_SELECT;
  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");

  TAILQ_INIT(&group_desc_list);
  ret = group_descs(group_table, &group_desc_list, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "get desc error");
  desc = TAILQ_FIRST(&group_desc_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(desc, "group not found");
  TEST_ASSERT_EQUAL_MESSAGE(desc->ofp.group_id, 1,
                            "group id error");
  TEST_ASSERT_EQUAL_MESSAGE(desc->ofp.type, OFPGT_ALL,
                            "group type error");
  desc = TAILQ_NEXT(desc, entry);
  TEST_ASSERT_NOT_NULL_MESSAGE(desc, "number of groups error");
  TEST_ASSERT_EQUAL_MESSAGE(desc->ofp.group_id, 1000000,
                            "group id error");
  TEST_ASSERT_EQUAL_MESSAGE(desc->ofp.type, OFPGT_SELECT,
                            "group type error");
}
Example #7
0
void
setUp(void) {
  if (dpmgr != NULL) {
    return;
  }

  /* Datapath manager alloc. */
  dpmgr = dpmgr_alloc();
  if (dpmgr == NULL) {
    fprintf(stderr, "Datapath manager allocation failed\n");
    exit(-1);
  }
  (void)global_state_set(GLOBAL_STATE_STARTED);
}
Example #8
0
void
setUp(void) {
  TEST_ASSERT_NULL(dpmgr);
  TEST_ASSERT_NULL(bridge);
  TEST_ASSERT_NULL(flowdb);
  TEST_ASSERT_NULL(ports);
  TEST_ASSERT_NULL(group_table);

  TEST_ASSERT_NOT_NULL(dpmgr = dpmgr_alloc());
  TEST_ASSERT_TRUE(LAGOPUS_RESULT_OK == dpmgr_bridge_add(dpmgr, bridge_name,
                   dpid));
  TEST_ASSERT_NOT_NULL(bridge = dpmgr_bridge_lookup(dpmgr, bridge_name));
  TEST_ASSERT_NOT_NULL(flowdb = bridge->flowdb);
  TEST_ASSERT_NOT_NULL(ports = ports_alloc());
  TEST_ASSERT_NOT_NULL(group_table = group_table_alloc(bridge));
}
Example #9
0
void
test_group_table_alloc(void) {
  struct dpmgr *dpmgr;
  struct bridge *bridge;
  struct group_table *group_table;
  lagopus_result_t rv;

  dpmgr = dpmgr_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(dpmgr, "dpmgr alloc error.");
  rv = dpmgr_bridge_add(dpmgr, "br0", 0);
  TEST_ASSERT_EQUAL_MESSAGE(rv, LAGOPUS_RESULT_OK,
                            "bridge add error");
  bridge = dpmgr_bridge_lookup(dpmgr, "br0");
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "bridge alloc error.");
  group_table = group_table_alloc(bridge);
  TEST_ASSERT_NOT_NULL_MESSAGE(group_table, "alloc error");
}
Example #10
0
struct channel *
create_data_channel(void) {
  static uint8_t cnt;
  char buf[256];
  struct channel *channel;
  struct session *session;
  struct addrunion addr;
  struct port port;
  uint64_t dpid = 0xabc;
  uint8_t port_hw_addr[OFP_ETH_ALEN] = {0xff, 0xff, 0xff,
                                        0xff, 0xff, 0xff
                                       };

  if (s_dpmgr == NULL) {
    s_dpmgr = dpmgr_alloc();
    dpmgr_bridge_add(s_dpmgr, "br0", dpid);
    dpmgr_controller_add(s_dpmgr, "br0", "127.0.0.1");
    port.ofp_port.port_no = 0;
    memcpy(port.ofp_port.hw_addr, port_hw_addr, OFP_ETH_ALEN);
    port.ifindex = 0;
    dpmgr_port_add(s_dpmgr, &port);
    dpmgr_bridge_port_add(s_dpmgr, "br0", 0, 0);
  }
  if (s_bridge == NULL) {
    s_bridge = dpmgr_bridge_lookup(s_dpmgr, "br0");
  }
  if (s_event_manager == NULL) {
    s_event_manager = event_manager_alloc();
    channel_mgr_initialize(s_event_manager);
  }

  snprintf(buf, sizeof(buf), "127.0.0.%u", cnt++);//XXX
  addrunion_ipv4_set(&addr, buf);
  channel_mgr_channel_add(s_bridge, dpid, &addr);
  channel_mgr_channel_lookup(s_bridge, &addr, &channel);


  session = channel_session_get(channel);
  session_write_set(session, s_write_tcp);
  session_sockfd_set(session, 3);

  channel_version_set(channel, 0x04);
  channel_xid_set(channel, s_xid);

  return channel;
}
void
setUp(void) {
  struct ofp_error err;

  TEST_ASSERT_NULL(dpmgr);
  TEST_ASSERT_NULL(bridge);
  TEST_ASSERT_NULL(flowdb);

  TEST_ASSERT_NOT_NULL(dpmgr = dpmgr_alloc());
  TEST_ASSERT_TRUE(LAGOPUS_RESULT_OK == dpmgr_bridge_add(dpmgr, bridge_name,
                   dpid));
  TEST_ASSERT_NOT_NULL(bridge = dpmgr_bridge_lookup(dpmgr, bridge_name));
  TEST_ASSERT_NOT_NULL(flowdb = bridge->flowdb);

  TAILQ_INIT(&features_list);
  memset(&err, 0, sizeof(err));
  TEST_ASSERT_TRUE(LAGOPUS_RESULT_OK == flowdb_get_table_features(flowdb,
                   &features_list, &err));
}
Example #12
0
void
test_group_table_add(void) {
  struct dpmgr *dpmgr;
  struct bridge *bridge;
  struct group_table *group_table;
  struct group *group;
  struct ofp_group_mod group_mod;
  struct bucket_list bucket_list;
  struct bucket *bucket;
  struct action *action;
  struct ofp_error error;
  lagopus_result_t ret;

  dpmgr = dpmgr_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(dpmgr, "dpmgr alloc error.");
  ret = dpmgr_bridge_add(dpmgr, "br0", 0);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "bridge add error");
  bridge = dpmgr_bridge_lookup(dpmgr, "br0");
  group_table = group_table_alloc(bridge);
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "group_table alloc error.");
  bridge->group_table = group_table;
  group_mod.group_id = 1;
  group_mod.type = OFPGT_ALL;
  TAILQ_INIT(&bucket_list);
  group = group_alloc(&group_mod, &bucket_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(group, "group_alloc error");
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");

  group_mod.group_id = 2;
  group_mod.type = OFPGT_ALL;
  TAILQ_INIT(&bucket_list);

  action = action_alloc(sizeof(uint32_t));
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action alloc error");
  action->ofpat.type = OFPAT_GROUP;
  bucket = calloc(1, sizeof(struct bucket));
  TEST_ASSERT_NOT_NULL_MESSAGE(bucket, "bucket alloc error");
  TAILQ_INIT(&bucket->action_list);
  ((struct ofp_action_group *)&action->ofpat)->group_id = 3;
  ((struct ofp_action_group *)&action->ofpat)->len =
    sizeof(struct ofp_action_header) + sizeof(uint32_t);
  TAILQ_INSERT_TAIL(&bucket->action_list, action, entry);
  TAILQ_INSERT_TAIL(&bucket_list, bucket, entry);

  action = action_alloc(sizeof(uint32_t));
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action alloc error");
  action->ofpat.type = OFPAT_OUTPUT;
  bucket = calloc(1, sizeof(struct bucket));
  TEST_ASSERT_NOT_NULL_MESSAGE(bucket, "bucket alloc error");
  TAILQ_INIT(&bucket->action_list);
  ((struct ofp_action_output *)&action->ofpat)->port = 3;
  ((struct ofp_action_output *)&action->ofpat)->len =
    sizeof(struct ofp_action_header) + sizeof(uint32_t);
  TAILQ_INSERT_TAIL(&bucket->action_list, action, entry);
  TAILQ_INSERT_TAIL(&bucket_list, bucket, entry);

  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");
  bucket = TAILQ_FIRST(&group->bucket_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(bucket, "bucket copy error");
  action = TAILQ_FIRST(&bucket->action_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action copy error");
  TEST_ASSERT_EQUAL_MESSAGE(action->ofpat.type, OFPAT_GROUP,
                            "action copy error");
  bucket = TAILQ_NEXT(bucket, entry);
  TEST_ASSERT_NOT_NULL_MESSAGE(bucket, "bucket copy error");
  action = TAILQ_FIRST(&bucket->action_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action copy error");
  TEST_ASSERT_EQUAL_MESSAGE(action->ofpat.type, OFPAT_OUTPUT,
                            "action copy error");
  TEST_ASSERT_EQUAL_MESSAGE(
    ((struct ofp_action_output *)&action->ofpat)->port, 3,
    "action copy error");

  group_mod.group_id = 3;
  group_mod.type = OFPGT_ALL;
  action = action_alloc(sizeof(uint32_t));
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action alloc error");
  action->ofpat.type = OFPAT_GROUP;
  ((struct ofp_action_group *)&action->ofpat)->group_id = 2;
  ((struct ofp_action_group *)&action->ofpat)->len =
    sizeof(struct ofp_action_header) + sizeof(uint32_t);
  bucket = calloc(1, sizeof(struct bucket));
  TAILQ_INIT(&bucket->action_list);
  TAILQ_INSERT_TAIL(&bucket->action_list, action, entry);
  TAILQ_INIT(&bucket_list);
  TAILQ_INSERT_TAIL(&bucket_list, bucket, entry);
  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OFP_ERROR,
                            "group_table_add loop error");
  TEST_ASSERT_EQUAL_MESSAGE(error.code, OFPGMFC_LOOP,
                            "loop error detection failed");
}
Example #13
0
void
test_group_stats(void) {
  struct dpmgr *dpmgr;
  struct bridge *bridge;
  struct group_table *group_table;
  struct group *group;
  struct ofp_group_mod group_mod;
  struct bucket_list bucket_list;
  struct ofp_group_stats_request request;
  struct group_stats_list group_stats_list;
  struct group_stats *stats;
  struct ofp_error error;
  struct ofp_flow_mod flow_mod;
  struct match_list match_list;
  struct instruction_list instruction_list;
  struct instruction *instruction;
  struct action *action;
  lagopus_result_t ret;

  dpmgr = dpmgr_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(dpmgr, "dpmgr alloc error.");
  ret = dpmgr_bridge_add(dpmgr, "br0", 0);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "bridge add error");
  bridge = dpmgr_bridge_lookup(dpmgr, "br0");
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "bridge alloc error.");
  TAILQ_INIT(&bucket_list);
  group_table = group_table_alloc(bridge);
  TEST_ASSERT_NOT_NULL_MESSAGE(bridge, "group_table alloc error.");
  bridge->group_table = group_table;

  group_mod.group_id = 1;
  group_mod.type = OFPGT_ALL;
  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");

  group_mod.group_id = 1000000;
  group_mod.type = OFPGT_ALL;
  group = group_alloc(&group_mod, &bucket_list);
  ret = group_table_add(group_table, group, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "group_table_add error");

  request.group_id = 1;
  TAILQ_INIT(&group_stats_list);
  ret = group_stats(group_table, &request, &group_stats_list, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "get stats error");
  stats = TAILQ_FIRST(&group_stats_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(stats, "group not found");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.group_id, 1,
                            "group id error");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.duration_sec, 0,
                            "duration sec error");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.ref_count, 0,
                            "ref_count error");
  stats = TAILQ_NEXT(stats, entry);
  TEST_ASSERT_NULL_MESSAGE(stats, "number of groups error");

  TAILQ_INIT(&match_list);
  TAILQ_INIT(&instruction_list);
  instruction = instruction_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(instruction, "instruction alloc error.");
  instruction->ofpit.type = OFPIT_APPLY_ACTIONS;
  TAILQ_INIT(&instruction->action_list);
  action = action_alloc(sizeof(struct ofp_action_group));
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action alloc error.");
  action->ofpat.type = OFPAT_GROUP;
  ((struct ofp_action_group *)&action->ofpat)->group_id = 5;
  TAILQ_INSERT_TAIL(&instruction->action_list, action, entry);
  TAILQ_INSERT_TAIL(&instruction_list, instruction, entry);
  flow_mod.table_id = 0;
  flow_mod.priority = 1;
  flow_mod.flags = 0;
  flow_mod.cookie = 0;
  ret = flowdb_flow_add(bridge, &flow_mod, &match_list,
                        &instruction_list, &error);
  TEST_ASSERT_NOT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                                "flowdb_flow_add: group check error");
  TAILQ_INIT(&match_list);
  TAILQ_INIT(&instruction_list);
  instruction = instruction_alloc();
  TEST_ASSERT_NOT_NULL_MESSAGE(instruction, "instruction alloc error.");
  instruction->ofpit.type = OFPIT_APPLY_ACTIONS;
  TAILQ_INIT(&instruction->action_list);
  action = action_alloc(sizeof(struct ofp_action_group));
  TEST_ASSERT_NOT_NULL_MESSAGE(action, "action alloc error.");
  action->ofpat.type = OFPAT_GROUP;
  ((struct ofp_action_group *)&action->ofpat)->group_id = 1;
  TAILQ_INSERT_TAIL(&instruction->action_list, action, entry);
  TAILQ_INSERT_TAIL(&instruction_list, instruction, entry);
  ret = flowdb_flow_add(bridge, &flow_mod, &match_list,
                        &instruction_list, &error);
  printf("%d.%d\n", error.type, error.code);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "flowdb_flow_add: add to empty table error");

  request.group_id = 1;
  TAILQ_INIT(&group_stats_list);
  ret = group_stats(group_table, &request, &group_stats_list, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "get stats error");
  stats = TAILQ_FIRST(&group_stats_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(stats, "group not found");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.group_id, 1,
                            "group id error");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.duration_sec, 0,
                            "duration sec error");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.ref_count, 1,
                            "ref_count error");
  stats = TAILQ_NEXT(stats, entry);
  TEST_ASSERT_NULL_MESSAGE(stats, "number of groups error");

  request.group_id = OFPG_ALL;
  TAILQ_INIT(&group_stats_list);
  ret = group_stats(group_table, &request, &group_stats_list, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "get stats error");
  stats = TAILQ_FIRST(&group_stats_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(stats, "group not found");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.group_id, 1,
                            "group id error");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.duration_sec, 0,
                            "duration sec error");
  stats = TAILQ_NEXT(stats, entry);
  TEST_ASSERT_NOT_NULL_MESSAGE(stats, "group not found");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.group_id, 1000000,
                            "group id error");
  stats = TAILQ_NEXT(stats, entry);
  TEST_ASSERT_NULL_MESSAGE(stats, "number of groups error");

  sleep(1);
  TAILQ_INIT(&group_stats_list);
  ret = group_stats(group_table, &request, &group_stats_list, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "get stats error");
  stats = TAILQ_FIRST(&group_stats_list);
  TEST_ASSERT_NOT_NULL_MESSAGE(stats, "group not found");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.group_id, 1,
                            "group id error");
  TEST_ASSERT_EQUAL_MESSAGE(stats->ofp.duration_sec, 1,
                            "duration sec error");

  request.group_id = 20;
  TAILQ_INIT(&group_stats_list);
  ret = group_stats(group_table, &request, &group_stats_list, &error);
  TEST_ASSERT_EQUAL_MESSAGE(ret, LAGOPUS_RESULT_OK,
                            "get stats error");
  stats = TAILQ_FIRST(&group_stats_list);
  TEST_ASSERT_NULL_MESSAGE(stats, "stats is not empry");
}
Example #14
0
void
test_action_OUTPUT(void) {
  struct action_list action_list;
  struct dpmgr *my_dpmgr;
  struct bridge *bridge;
  struct port *port;
  struct action *action;
  struct ofp_action_output *action_set;
  struct port nport;
  struct lagopus_packet pkt;
  OS_MBUF *m;

  /* setup bridge and port */
  my_dpmgr = dpmgr_alloc();
  dpmgr_bridge_add(my_dpmgr, "br0", 0);
  nport.type = LAGOPUS_PORT_TYPE_NULL; /* for test */
  nport.ofp_port.port_no = 1;
  nport.ifindex = 0;
  nport.ofp_port.hw_addr[0] = 1;
  dpmgr_port_add(my_dpmgr, &nport);
  port = port_lookup(my_dpmgr->ports, 0);
  TEST_ASSERT_NOT_NULL(port);
  port->ofp_port.hw_addr[0] = 0xff;
  nport.ofp_port.port_no = 2;
  nport.ifindex = 1;
  dpmgr_port_add(my_dpmgr, &nport);
  port = port_lookup(my_dpmgr->ports, 1);
  TEST_ASSERT_NOT_NULL(port);
  port->ofp_port.hw_addr[0] = 0xff;
  dpmgr_bridge_port_add(my_dpmgr, "br0", 0, 1);
  dpmgr_bridge_port_add(my_dpmgr, "br0", 1, 2);

  TAILQ_INIT(&action_list);
  action = calloc(1, sizeof(*action) + 64);
  action_set = (struct ofp_action_output *)&action->ofpat;
  action_set->type = OFPAT_OUTPUT;
  lagopus_set_action_function(action);
  TAILQ_INSERT_TAIL(&action_list, action, entry);

  memset(&pkt, 0, sizeof(pkt));

  m = calloc(1, sizeof(*m));
  TEST_ASSERT_NOT_NULL_MESSAGE(m, "calloc error.");
  m->data = &m->dat[128];

  bridge = dpmgr_bridge_lookup(my_dpmgr, "br0");
  TEST_ASSERT_NOT_NULL(bridge);
  lagopus_set_in_port(&pkt, port_lookup(bridge->ports, 1));
  TEST_ASSERT_NOT_NULL(pkt.in_port);
  lagopus_packet_init(&pkt, m);

  /* output action always decrement reference count. */
  m->refcnt = 2;
  action_set->port = 1;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = 2;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = OFPP_ALL;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = OFPP_NORMAL;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = OFPP_IN_PORT;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = OFPP_CONTROLLER;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = OFPP_FLOOD;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = OFPP_LOCAL;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");

  m->refcnt = 2;
  action_set->port = 0;
  execute_action(&pkt, &action_list);
  TEST_ASSERT_EQUAL_MESSAGE(m->refcnt, 1,
                            "OUTPUT refcnt error.");
  free(m);
  dpmgr_free(my_dpmgr);
}