Merge branch 'mainstream'
authorGiuseppe Lettieri <g.lettieri@iet.unipi.it>
Tue, 5 Nov 2013 08:56:15 +0000 (09:56 +0100)
committerGiuseppe Lettieri <g.lettieri@iet.unipi.it>
Tue, 5 Nov 2013 08:56:15 +0000 (09:56 +0100)
1  2 
lib/dpif-netdev.c
lib/dpif.c

diff --combined lib/dpif-netdev.c
@@@ -125,7 -125,7 +125,7 @@@ struct dp_netdev_flow 
      long long int used;         /* Last used time, in monotonic msecs. */
      long long int packet_count; /* Number of packets matched. */
      long long int byte_count;   /* Number of bytes matched. */
-     uint8_t tcp_flags;          /* Bitwise-OR of seen tcp_flags values. */
+     uint16_t tcp_flags;         /* Bitwise-OR of seen tcp_flags values. */
  
      /* Actions. */
      struct nlattr *actions;
@@@ -201,17 -201,10 +201,17 @@@ dpif_netdev_class_is_dummy(const struc
      return class != &dpif_netdev_class;
  }
  
 +static bool
 +dpif_netdev_class_is_planetlab(const struct dpif_class *class)
 +{
 +    return class == &dpif_planetlab_class;
 +}
 +
  static const char *
  dpif_netdev_port_open_type(const struct dpif_class *class, const char *type)
  {
      return strcmp(type, "internal") ? type
 +                  : dpif_netdev_class_is_planetlab(class) ? "pltap"
                    : dpif_netdev_class_is_dummy(class) ? "dummy"
                    : "tap";
  }
@@@ -239,8 -232,7 +239,8 @@@ choose_port(struct dp_netdev *dp, cons
  {
      uint32_t port_no;
  
 -    if (dp->class != &dpif_netdev_class) {
 +    if (dp->class != &dpif_netdev_class && 
 +        dp->class != &dpif_planetlab_class) {
          const char *p;
          int start_no = 0;
  
@@@ -632,20 -624,20 +632,20 @@@ dpif_netdev_get_max_ports(const struct 
  }
  
  static void
- dp_netdev_free_flow(struct dp_netdev *dp, struct dp_netdev_flow *flow)
+ dp_netdev_free_flow(struct dp_netdev *dp, struct dp_netdev_flow *netdev_flow)
  {
-     hmap_remove(&dp->flow_table, &flow->node);
-     free(flow->actions);
-     free(flow);
+     hmap_remove(&dp->flow_table, &netdev_flow->node);
+     free(netdev_flow->actions);
+     free(netdev_flow);
  }
  
  static void
  dp_netdev_flow_flush(struct dp_netdev *dp)
  {
-     struct dp_netdev_flow *flow, *next;
+     struct dp_netdev_flow *netdev_flow, *next;
  
-     HMAP_FOR_EACH_SAFE (flow, next, node, &dp->flow_table) {
-         dp_netdev_free_flow(dp, flow);
+     HMAP_FOR_EACH_SAFE (netdev_flow, next, node, &dp->flow_table) {
+         dp_netdev_free_flow(dp, netdev_flow);
      }
  }
  
@@@ -744,23 -736,25 +744,25 @@@ dpif_netdev_port_poll_wait(const struc
  static struct dp_netdev_flow *
  dp_netdev_lookup_flow(const struct dp_netdev *dp, const struct flow *key)
  {
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
  
-     HMAP_FOR_EACH_WITH_HASH (flow, node, flow_hash(key, 0), &dp->flow_table) {
-         if (flow_equal(&flow->key, key)) {
-             return flow;
+     HMAP_FOR_EACH_WITH_HASH (netdev_flow, node, flow_hash(key, 0),
+                              &dp->flow_table) {
+         if (flow_equal(&netdev_flow->key, key)) {
+             return netdev_flow;
          }
      }
      return NULL;
  }
  
  static void
- get_dpif_flow_stats(struct dp_netdev_flow *flow, struct dpif_flow_stats *stats)
+ get_dpif_flow_stats(struct dp_netdev_flow *netdev_flow,
+                     struct dpif_flow_stats *stats)
  {
-     stats->n_packets = flow->packet_count;
-     stats->n_bytes = flow->byte_count;
-     stats->used = flow->used;
-     stats->tcp_flags = flow->tcp_flags;
+     stats->n_packets = netdev_flow->packet_count;
+     stats->n_bytes = netdev_flow->byte_count;
+     stats->used = netdev_flow->used;
+     stats->tcp_flags = netdev_flow->tcp_flags;
  }
  
  static int
@@@ -802,7 -796,7 +804,7 @@@ dpif_netdev_flow_get(const struct dpif 
                       struct ofpbuf **actionsp, struct dpif_flow_stats *stats)
  {
      struct dp_netdev *dp = get_dp_netdev(dpif);
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
      struct flow key;
      int error;
  
      }
  
      ovs_mutex_lock(&dp_netdev_mutex);
-     flow = dp_netdev_lookup_flow(dp, &key);
-     if (flow) {
+     netdev_flow = dp_netdev_lookup_flow(dp, &key);
+     if (netdev_flow) {
          if (stats) {
-             get_dpif_flow_stats(flow, stats);
+             get_dpif_flow_stats(netdev_flow, stats);
          }
          if (actionsp) {
-             *actionsp = ofpbuf_clone_data(flow->actions, flow->actions_len);
+             *actionsp = ofpbuf_clone_data(netdev_flow->actions,
+                                           netdev_flow->actions_len);
          }
      } else {
          error = ENOENT;
  }
  
  static int
- set_flow_actions(struct dp_netdev_flow *flow,
+ set_flow_actions(struct dp_netdev_flow *netdev_flow,
                   const struct nlattr *actions, size_t actions_len)
  {
-     flow->actions = xrealloc(flow->actions, actions_len);
-     flow->actions_len = actions_len;
-     memcpy(flow->actions, actions, actions_len);
+     netdev_flow->actions = xrealloc(netdev_flow->actions, actions_len);
+     netdev_flow->actions_len = actions_len;
+     memcpy(netdev_flow->actions, actions, actions_len);
      return 0;
  }
  
@@@ -842,36 -837,37 +845,37 @@@ static in
  dp_netdev_flow_add(struct dp_netdev *dp, const struct flow *key,
                     const struct nlattr *actions, size_t actions_len)
  {
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
      int error;
  
-     flow = xzalloc(sizeof *flow);
-     flow->key = *key;
+     netdev_flow = xzalloc(sizeof *netdev_flow);
+     netdev_flow->key = *key;
  
-     error = set_flow_actions(flow, actions, actions_len);
+     error = set_flow_actions(netdev_flow, actions, actions_len);
      if (error) {
-         free(flow);
+         free(netdev_flow);
          return error;
      }
  
-     hmap_insert(&dp->flow_table, &flow->node, flow_hash(&flow->key, 0));
+     hmap_insert(&dp->flow_table, &netdev_flow->node,
+                 flow_hash(&netdev_flow->key, 0));
      return 0;
  }
  
  static void
- clear_stats(struct dp_netdev_flow *flow)
+ clear_stats(struct dp_netdev_flow *netdev_flow)
  {
-     flow->used = 0;
-     flow->packet_count = 0;
-     flow->byte_count = 0;
-     flow->tcp_flags = 0;
+     netdev_flow->used = 0;
+     netdev_flow->packet_count = 0;
+     netdev_flow->byte_count = 0;
+     netdev_flow->tcp_flags = 0;
  }
  
  static int
  dpif_netdev_flow_put(struct dpif *dpif, const struct dpif_flow_put *put)
  {
      struct dp_netdev *dp = get_dp_netdev(dpif);
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
      struct flow key;
      int error;
  
      }
  
      ovs_mutex_lock(&dp_netdev_mutex);
-     flow = dp_netdev_lookup_flow(dp, &key);
-     if (!flow) {
+     netdev_flow = dp_netdev_lookup_flow(dp, &key);
+     if (!netdev_flow) {
          if (put->flags & DPIF_FP_CREATE) {
              if (hmap_count(&dp->flow_table) < MAX_FLOWS) {
                  if (put->stats) {
          }
      } else {
          if (put->flags & DPIF_FP_MODIFY) {
-             error = set_flow_actions(flow, put->actions, put->actions_len);
+             error = set_flow_actions(netdev_flow, put->actions,
+                                      put->actions_len);
              if (!error) {
                  if (put->stats) {
-                     get_dpif_flow_stats(flow, put->stats);
+                     get_dpif_flow_stats(netdev_flow, put->stats);
                  }
                  if (put->flags & DPIF_FP_ZERO_STATS) {
-                     clear_stats(flow);
+                     clear_stats(netdev_flow);
                  }
              }
          } else {
@@@ -920,7 -917,7 +925,7 @@@ static in
  dpif_netdev_flow_del(struct dpif *dpif, const struct dpif_flow_del *del)
  {
      struct dp_netdev *dp = get_dp_netdev(dpif);
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
      struct flow key;
      int error;
  
      }
  
      ovs_mutex_lock(&dp_netdev_mutex);
-     flow = dp_netdev_lookup_flow(dp, &key);
-     if (flow) {
+     netdev_flow = dp_netdev_lookup_flow(dp, &key);
+     if (netdev_flow) {
          if (del->stats) {
-             get_dpif_flow_stats(flow, del->stats);
+             get_dpif_flow_stats(netdev_flow, del->stats);
          }
-         dp_netdev_free_flow(dp, flow);
+         dp_netdev_free_flow(dp, netdev_flow);
      } else {
          error = ENOENT;
      }
@@@ -973,7 -970,7 +978,7 @@@ dpif_netdev_flow_dump_next(const struc
  {
      struct dp_netdev_flow_state *state = state_;
      struct dp_netdev *dp = get_dp_netdev(dpif);
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
      struct hmap_node *node;
  
      ovs_mutex_lock(&dp_netdev_mutex);
          return EOF;
      }
  
-     flow = CONTAINER_OF(node, struct dp_netdev_flow, node);
+     netdev_flow = CONTAINER_OF(node, struct dp_netdev_flow, node);
  
      if (key) {
          struct ofpbuf buf;
  
          ofpbuf_use_stack(&buf, &state->keybuf, sizeof state->keybuf);
-         odp_flow_key_from_flow(&buf, &flow->key, flow->key.in_port.odp_port);
+         odp_flow_key_from_flow(&buf, &netdev_flow->key,
+                                netdev_flow->key.in_port.odp_port);
  
          *key = buf.data;
          *key_len = buf.size;
  
      if (actions) {
          free(state->actions);
-         state->actions = xmemdup(flow->actions, flow->actions_len);
+         state->actions = xmemdup(netdev_flow->actions,
+                          netdev_flow->actions_len);
  
          *actions = state->actions;
-         *actions_len = flow->actions_len;
+         *actions_len = netdev_flow->actions_len;
      }
  
      if (stats) {
-         get_dpif_flow_stats(flow, &state->stats);
+         get_dpif_flow_stats(netdev_flow, &state->stats);
          *stats = &state->stats;
      }
  
@@@ -1141,12 -1140,13 +1148,13 @@@ dpif_netdev_recv_purge(struct dpif *dpi
  }
  \f
  static void
- dp_netdev_flow_used(struct dp_netdev_flow *flow, const struct ofpbuf *packet)
+ dp_netdev_flow_used(struct dp_netdev_flow *netdev_flow,
+                     const struct ofpbuf *packet)
  {
-     flow->used = time_msec();
-     flow->packet_count++;
-     flow->byte_count += packet->size;
-     flow->tcp_flags |= packet_get_tcp_flags(packet, &flow->key);
+     netdev_flow->used = time_msec();
+     netdev_flow->packet_count++;
+     netdev_flow->byte_count += packet->size;
+     netdev_flow->tcp_flags |= packet_get_tcp_flags(packet, &netdev_flow->key);
  }
  
  static void
@@@ -1154,7 -1154,7 +1162,7 @@@ dp_netdev_port_input(struct dp_netdev *
                       struct ofpbuf *packet, uint32_t skb_priority,
                       uint32_t pkt_mark, const struct flow_tnl *tnl)
  {
-     struct dp_netdev_flow *flow;
+     struct dp_netdev_flow *netdev_flow;
      struct flow key;
      union flow_in_port in_port_;
  
      }
      in_port_.odp_port = port->port_no;
      flow_extract(packet, skb_priority, pkt_mark, tnl, &in_port_, &key);
-     flow = dp_netdev_lookup_flow(dp, &key);
-     if (flow) {
-         dp_netdev_flow_used(flow, packet);
+     netdev_flow = dp_netdev_lookup_flow(dp, &key);
+     if (netdev_flow) {
+         dp_netdev_flow_used(netdev_flow, packet);
          dp_netdev_execute_actions(dp, packet, &key,
-                                   flow->actions, flow->actions_len);
+                                   netdev_flow->actions,
+                                   netdev_flow->actions_len);
          dp->n_hit++;
      } else {
          dp->n_missed++;
@@@ -1318,49 -1319,41 +1327,49 @@@ dp_netdev_execute_actions(struct dp_net
                          dp_netdev_output_port, dp_netdev_action_userspace);
  }
  
 +#define DPIF_NETDEV_CLASS_FUNCTIONS                   \
 +    dpif_netdev_enumerate,                            \
 +    dpif_netdev_port_open_type,                               \
 +    dpif_netdev_open,                                 \
 +    dpif_netdev_close,                                        \
 +    dpif_netdev_destroy,                              \
 +    dpif_netdev_run,                                  \
 +    dpif_netdev_wait,                                 \
 +    dpif_netdev_get_stats,                            \
 +    dpif_netdev_port_add,                             \
 +    dpif_netdev_port_del,                             \
 +    dpif_netdev_port_query_by_number,                 \
 +    dpif_netdev_port_query_by_name,                   \
 +    dpif_netdev_get_max_ports,                                \
 +    NULL,                       /* port_get_pid */    \
 +    dpif_netdev_port_dump_start,                      \
 +    dpif_netdev_port_dump_next,                               \
 +    dpif_netdev_port_dump_done,                               \
 +    dpif_netdev_port_poll,                            \
 +    dpif_netdev_port_poll_wait,                               \
 +    dpif_netdev_flow_get,                             \
 +    dpif_netdev_flow_put,                             \
 +    dpif_netdev_flow_del,                             \
 +    dpif_netdev_flow_flush,                           \
 +    dpif_netdev_flow_dump_start,                      \
 +    dpif_netdev_flow_dump_next,                               \
 +    dpif_netdev_flow_dump_done,                               \
 +    dpif_netdev_execute,                              \
 +    NULL,                       /* operate */         \
 +    dpif_netdev_recv_set,                             \
 +    dpif_netdev_queue_to_priority,                    \
 +    dpif_netdev_recv,                                 \
 +    dpif_netdev_recv_wait,                            \
 +    dpif_netdev_recv_purge,                           \
 +
  const struct dpif_class dpif_netdev_class = {
      "netdev",
 -    dpif_netdev_enumerate,
 -    dpif_netdev_port_open_type,
 -    dpif_netdev_open,
 -    dpif_netdev_close,
 -    dpif_netdev_destroy,
 -    dpif_netdev_run,
 -    dpif_netdev_wait,
 -    dpif_netdev_get_stats,
 -    dpif_netdev_port_add,
 -    dpif_netdev_port_del,
 -    dpif_netdev_port_query_by_number,
 -    dpif_netdev_port_query_by_name,
 -    dpif_netdev_get_max_ports,
 -    NULL,                       /* port_get_pid */
 -    dpif_netdev_port_dump_start,
 -    dpif_netdev_port_dump_next,
 -    dpif_netdev_port_dump_done,
 -    dpif_netdev_port_poll,
 -    dpif_netdev_port_poll_wait,
 -    dpif_netdev_flow_get,
 -    dpif_netdev_flow_put,
 -    dpif_netdev_flow_del,
 -    dpif_netdev_flow_flush,
 -    dpif_netdev_flow_dump_start,
 -    dpif_netdev_flow_dump_next,
 -    dpif_netdev_flow_dump_done,
 -    dpif_netdev_execute,
 -    NULL,                       /* operate */
 -    dpif_netdev_recv_set,
 -    dpif_netdev_queue_to_priority,
 -    dpif_netdev_recv,
 -    dpif_netdev_recv_wait,
 -    dpif_netdev_recv_purge,
 +    DPIF_NETDEV_CLASS_FUNCTIONS
 +};
 +
 +const struct dpif_class dpif_planetlab_class = {
 +    "planetlab",
 +    DPIF_NETDEV_CLASS_FUNCTIONS
  };
  
  static void
@@@ -1432,4 -1425,3 +1441,4 @@@ dpif_dummy_register(bool override
                               "DP PORT NEW-NUMBER",
                               3, 3, dpif_dummy_change_port_number, NULL);
  }
 +
diff --combined lib/dpif.c
@@@ -61,7 -61,6 +61,7 @@@ static const struct dpif_class *base_dp
      &dpif_linux_class,
  #endif
      &dpif_netdev_class,
 +    &dpif_planetlab_class,
  };
  
  struct registered_dpif_class {
@@@ -1184,6 -1183,8 +1184,8 @@@ dpif_execute__(struct dpif *dpif, cons
   * OVS_ACTION_ATTR_USERSPACE actions it passes the packet through to the dpif
   * implementation.
   *
+  * This works even if 'actions_len' is too long for a Netlink attribute.
+  *
   * Returns 0 if successful, otherwise a positive errno value. */
  int
  dpif_execute(struct dpif *dpif,
      execute.actions = actions;
      execute.actions_len = actions_len;
      execute.packet = buf;
-     execute.needs_help = needs_help;
+     execute.needs_help = needs_help || nl_attr_oversized(actions_len);
      return dpif_execute__(dpif, &execute);
  }