diff options
author | Ben Pfaff <blp@nicira.com> | 2011-05-12 12:05:42 -0700 |
---|---|---|
committer | Ben Pfaff <blp@nicira.com> | 2011-05-12 12:05:42 -0700 |
commit | 007948177581f3b3dad188221593d0e4bdca6ba0 (patch) | |
tree | f1acdac6058c28a0905f717612e3cb3c84fcea06 /lib | |
parent | fc08b7a2397ef0cf55014c1ee159599fb420b73e (diff) | |
parent | 2db65bf72c008cf7ee658d0b44744b39495ead14 (diff) | |
download | openvswitch-007948177581f3b3dad188221593d0e4bdca6ba0.tar.gz |
Merge 'master' into 'next'.
Diffstat (limited to 'lib')
-rw-r--r-- | lib/automake.mk | 3 | ||||
-rw-r--r-- | lib/bond.c | 44 | ||||
-rw-r--r-- | lib/bond.h | 3 | ||||
-rw-r--r-- | lib/dpif-linux.c | 36 | ||||
-rw-r--r-- | lib/dpif.c | 1 | ||||
-rw-r--r-- | lib/dpif.h | 3 | ||||
-rw-r--r-- | lib/flow.h | 2 | ||||
-rw-r--r-- | lib/lacp.c | 48 | ||||
-rw-r--r-- | lib/lacp.h | 3 | ||||
-rw-r--r-- | lib/learning-switch.c | 1 | ||||
-rw-r--r-- | lib/netdev-linux.c | 77 | ||||
-rw-r--r-- | lib/netdev-linux.h | 34 | ||||
-rw-r--r-- | lib/netdev-vport.c | 61 | ||||
-rw-r--r-- | lib/ofp-parse.c | 2 | ||||
-rw-r--r-- | lib/ofp-print.c | 22 | ||||
-rw-r--r-- | lib/ofp-util.c | 234 | ||||
-rw-r--r-- | lib/ofp-util.h | 23 | ||||
-rw-r--r-- | lib/stream-nossl.c | 76 | ||||
-rw-r--r-- | lib/stream-ssl.h | 26 |
19 files changed, 353 insertions, 346 deletions
diff --git a/lib/automake.mk b/lib/automake.mk index 878afe847..8c97100c7 100644 --- a/lib/automake.mk +++ b/lib/automake.mk @@ -200,6 +200,7 @@ lib_libopenvswitch_a_SOURCES += \ lib/dpif-linux.c \ lib/dpif-linux.h \ lib/netdev-linux.c \ + lib/netdev-linux.h \ lib/netdev-vport.c \ lib/netdev-vport.h \ lib/netlink-protocol.h \ @@ -223,6 +224,8 @@ lib/dhparams.c: lib/dh1024.pem lib/dh2048.pem lib/dh4096.pem openssl dhparam -C -in $(srcdir)/lib/dh4096.pem -noout) \ | sed 's/\(get_dh[0-9]*\)()/\1(void)/' > lib/dhparams.c.tmp mv lib/dhparams.c.tmp lib/dhparams.c +else +lib_libopenvswitch_a_SOURCES += lib/stream-nossl.c endif EXTRA_DIST += \ diff --git a/lib/bond.c b/lib/bond.c index 208310841..6f18824c4 100644 --- a/lib/bond.c +++ b/lib/bond.c @@ -74,7 +74,7 @@ struct bond_slave { uint64_t tx_bytes; /* Sum across 'tx_bytes' of entries. */ /* BM_STABLE specific bonding info. */ - uint16_t stb_id; /* ID used for 'stb_slaves' ordering. */ + uint32_t stb_id; /* ID used for 'stb_slaves' ordering. */ }; /* A bond, that is, a set of network devices grouped to improve performance or @@ -93,6 +93,7 @@ struct bond { int updelay, downdelay; /* Delay before slave goes up/down, in ms. */ bool lacp_negotiated; /* LACP negotiations were successful. */ bool bond_revalidate; /* True if flows need revalidation. */ + uint32_t basis; /* Basis for flow hash function. */ /* SLB specific bonding info. */ struct bond_entry *hash; /* An array of (BOND_MASK + 1) elements. */ @@ -129,8 +130,9 @@ static void bond_link_status_update(struct bond_slave *, struct tag_set *); static void bond_choose_active_slave(struct bond *, struct tag_set *); static bool bond_is_tcp_hash(const struct bond *); static unsigned int bond_hash_src(const uint8_t mac[ETH_ADDR_LEN], - uint16_t vlan); -static unsigned int bond_hash_tcp(const struct flow *, uint16_t vlan); + uint16_t vlan, uint32_t basis); +static unsigned int bond_hash_tcp(const struct flow *, uint16_t vlan, + uint32_t basis); static struct bond_entry *lookup_bond_entry(const struct bond *, const struct flow *, uint16_t vlan); @@ -291,6 +293,11 @@ bond_reconfigure(struct bond *bond, const struct bond_settings *s) revalidate = true; } + if (bond->basis != s->basis) { + bond->basis = s->basis; + revalidate = true; + } + if (bond->detect == BLSM_CARRIER) { struct bond_slave *slave; @@ -359,7 +366,7 @@ bond_slave_set_netdev__(struct bond *bond, struct bond_slave *slave, * 'slave_' or destroying 'bond'. */ void -bond_slave_register(struct bond *bond, void *slave_, uint16_t stb_id, +bond_slave_register(struct bond *bond, void *slave_, uint32_t stb_id, struct netdev *netdev) { struct bond_slave *slave = bond_slave_lookup(bond, slave_); @@ -999,6 +1006,8 @@ bond_unixctl_show(struct unixctl_conn *conn, bond_is_tcp_hash(bond) ? "balance-tcp" : "balance-slb"); } + ds_put_format(&ds, "bond-hash-basis: %"PRIu32"\n", bond->basis); + ds_put_format(&ds, "bond-detect-mode: %s\n", bond->monitor ? "carrier" : "miimon"); @@ -1227,11 +1236,13 @@ bond_unixctl_hash(struct unixctl_conn *conn, const char *args_, uint8_t hash; char *hash_cstr; unsigned int vlan; - char *mac_s, *vlan_s; + uint32_t basis; + char *mac_s, *vlan_s, *basis_s; char *save_ptr = NULL; mac_s = strtok_r(args, " ", &save_ptr); vlan_s = strtok_r(NULL, " ", &save_ptr); + basis_s = strtok_r(NULL, " ", &save_ptr); if (vlan_s) { if (sscanf(vlan_s, "%u", &vlan) != 1) { @@ -1242,9 +1253,18 @@ bond_unixctl_hash(struct unixctl_conn *conn, const char *args_, vlan = OFP_VLAN_NONE; } + if (basis_s) { + if (sscanf(basis_s, "%"PRIu32, &basis) != 1) { + unixctl_command_reply(conn, 501, "invalid basis"); + return; + } + } else { + basis = 0; + } + if (sscanf(mac_s, ETH_ADDR_SCAN_FMT, ETH_ADDR_SCAN_ARGS(mac)) == ETH_ADDR_SCAN_COUNT) { - hash = bond_hash_src(mac, vlan) & BOND_MASK; + hash = bond_hash_src(mac, vlan, basis) & BOND_MASK; hash_cstr = xasprintf("%u", hash); unixctl_command_reply(conn, 200, hash_cstr); @@ -1376,13 +1396,13 @@ bond_is_tcp_hash(const struct bond *bond) } static unsigned int -bond_hash_src(const uint8_t mac[ETH_ADDR_LEN], uint16_t vlan) +bond_hash_src(const uint8_t mac[ETH_ADDR_LEN], uint16_t vlan, uint32_t basis) { - return hash_bytes(mac, ETH_ADDR_LEN, vlan); + return hash_3words(hash_bytes(mac, ETH_ADDR_LEN, 0), vlan, basis); } static unsigned int -bond_hash_tcp(const struct flow *flow, uint16_t vlan) +bond_hash_tcp(const struct flow *flow, uint16_t vlan, uint32_t basis) { struct flow hash_flow = *flow; hash_flow.vlan_tci = vlan; @@ -1390,7 +1410,7 @@ bond_hash_tcp(const struct flow *flow, uint16_t vlan) /* The symmetric quality of this hash function is not required, but * flow_hash_symmetric_l4 already exists, and is sufficient for our * purposes, so we use it out of convenience. */ - return flow_hash_symmetric_l4(&hash_flow, 0); + return flow_hash_symmetric_l4(&hash_flow, basis); } static unsigned int @@ -1399,8 +1419,8 @@ bond_hash(const struct bond *bond, const struct flow *flow, uint16_t vlan) assert(bond->balance != BM_AB); return (bond_is_tcp_hash(bond) - ? bond_hash_tcp(flow, vlan) - : bond_hash_src(flow->dl_src, vlan)); + ? bond_hash_tcp(flow, vlan, bond->basis) + : bond_hash_src(flow->dl_src, vlan, bond->basis)); } static struct bond_entry * diff --git a/lib/bond.h b/lib/bond.h index 8736f4cd4..fe587928d 100644 --- a/lib/bond.h +++ b/lib/bond.h @@ -50,6 +50,7 @@ const char *bond_detect_mode_to_string(enum bond_detect_mode); /* Configuration for a bond as a whole. */ struct bond_settings { char *name; /* Bond's name, for log messages. */ + uint32_t basis; /* Flow hashing basis. */ /* Balancing configuration. */ enum bond_mode balance; @@ -74,7 +75,7 @@ void bond_destroy(struct bond *); bool bond_reconfigure(struct bond *, const struct bond_settings *); void bond_slave_register(struct bond *, void *slave_, - uint16_t stable_id, struct netdev *); + uint32_t stable_id, struct netdev *); void bond_slave_set_netdev(struct bond *, void *slave_, struct netdev *); void bond_slave_unregister(struct bond *, const void *slave); diff --git a/lib/dpif-linux.c b/lib/dpif-linux.c index e2c911cf9..7e6c49143 100644 --- a/lib/dpif-linux.c +++ b/lib/dpif-linux.c @@ -35,6 +35,7 @@ #include "bitmap.h" #include "dpif-provider.h" #include "netdev.h" +#include "netdev-linux.h" #include "netdev-vport.h" #include "netlink-socket.h" #include "netlink.h" @@ -431,6 +432,12 @@ dpif_linux_port_query__(const struct dpif *dpif, uint32_t port_no, dpif_port->name = xstrdup(reply.name); dpif_port->type = xstrdup(netdev_vport_get_netdev_type(&reply)); dpif_port->port_no = reply.port_no; + if (reply.stats) { + netdev_stats_from_rtnl_link_stats64(&dpif_port->stats, + reply.stats); + } else { + memset(&dpif_port->stats, 0xff, sizeof dpif_port->stats); + } ofpbuf_delete(buf); } return error; @@ -472,6 +479,8 @@ dpif_linux_flow_flush(struct dpif *dpif_) struct dpif_linux_port_state { struct nl_dump dump; + unsigned long *port_bitmap; /* Ports in the datapath. */ + bool complete; /* Dump completed without error. */ }; static int @@ -483,6 +492,8 @@ dpif_linux_port_dump_start(const struct dpif *dpif_, void **statep) struct ofpbuf *buf; *statep = state = xmalloc(sizeof *state); + state->port_bitmap = bitmap_allocate(LRU_MAX_PORTS); + state->complete = false; dpif_linux_vport_init(&request); request.cmd = ODP_DP_CMD_GET; @@ -506,6 +517,7 @@ dpif_linux_port_dump_next(const struct dpif *dpif OVS_UNUSED, void *state_, int error; if (!nl_dump_next(&state->dump, &buf)) { + state->complete = true; return EOF; } @@ -514,17 +526,39 @@ dpif_linux_port_dump_next(const struct dpif *dpif OVS_UNUSED, void *state_, return error; } + if (vport.port_no < LRU_MAX_PORTS) { + bitmap_set1(state->port_bitmap, vport.port_no); + } + dpif_port->name = (char *) vport.name; dpif_port->type = (char *) netdev_vport_get_netdev_type(&vport); dpif_port->port_no = vport.port_no; + if (vport.stats) { + netdev_stats_from_rtnl_link_stats64(&dpif_port->stats, vport.stats); + } else { + memset(&dpif_port->stats, 0xff, sizeof dpif_port->stats); + } return 0; } static int -dpif_linux_port_dump_done(const struct dpif *dpif OVS_UNUSED, void *state_) +dpif_linux_port_dump_done(const struct dpif *dpif_, void *state_) { + struct dpif_linux *dpif = dpif_linux_cast(dpif_); struct dpif_linux_port_state *state = state_; int error = nl_dump_done(&state->dump); + + if (state->complete) { + uint16_t i; + + for (i = 0; i < LRU_MAX_PORTS; i++) { + if (!bitmap_is_set(state->port_bitmap, i)) { + dpif_linux_push_port(dpif, i); + } + } + } + + free(state->port_bitmap); free(state); return error; } diff --git a/lib/dpif.c b/lib/dpif.c index 215ecfcd4..74e985698 100644 --- a/lib/dpif.c +++ b/lib/dpif.c @@ -469,6 +469,7 @@ dpif_port_clone(struct dpif_port *dst, const struct dpif_port *src) dst->name = xstrdup(src->name); dst->type = xstrdup(src->type); dst->port_no = src->port_no; + dst->stats = src->stats; } /* Frees memory allocated to members of 'dpif_port'. diff --git a/lib/dpif.h b/lib/dpif.h index 447ccd980..8452349b6 100644 --- a/lib/dpif.h +++ b/lib/dpif.h @@ -23,6 +23,7 @@ #include <stdint.h> #include "openflow/openflow.h" #include "openvswitch/datapath-protocol.h" +#include "netdev.h" #include "util.h" #ifdef __cplusplus @@ -31,7 +32,6 @@ extern "C" { struct dpif; struct ds; -struct netdev; struct nlattr; struct ofpbuf; struct sset; @@ -72,6 +72,7 @@ struct dpif_port { char *name; /* Network device name, e.g. "eth0". */ char *type; /* Network device type, e.g. "system". */ uint32_t port_no; /* Port number within datapath. */ + struct netdev_stats stats; /* Port statistics. */ }; void dpif_port_clone(struct dpif_port *, const struct dpif_port *); void dpif_port_destroy(struct dpif_port *); diff --git a/lib/flow.h b/lib/flow.h index f5f965c5b..6bd2c3d13 100644 --- a/lib/flow.h +++ b/lib/flow.h @@ -118,7 +118,7 @@ typedef unsigned int OVS_BITWISE flow_wildcards_t; #define FWW_TP_DST ((OVS_FORCE flow_wildcards_t) (1 << 7)) /* Same meanings as corresponding OFPFW_* bits, but differ in value. */ #define FWW_NW_TOS ((OVS_FORCE flow_wildcards_t) (1 << 1)) -/* No corresponding OFPFW_* or OVSFW_* bits. */ +/* No corresponding OFPFW_* bits. */ #define FWW_ETH_MCAST ((OVS_FORCE flow_wildcards_t) (1 << 8)) /* multicast bit only */ #define FWW_ARP_SHA ((OVS_FORCE flow_wildcards_t) (1 << 9)) diff --git a/lib/lacp.c b/lib/lacp.c index a7f66a24a..3fe5eff32 100644 --- a/lib/lacp.c +++ b/lib/lacp.c @@ -50,9 +50,9 @@ struct lacp { enum lacp_time lacp_time; /* Fast, Slow or Custom LACP time. */ long long int custom_time; /* LACP_TIME_CUSTOM transmission rate. */ - bool strict; /* True if in strict mode. */ bool negotiated; /* True if LACP negotiations were successful. */ bool update; /* True if lacp_update() needs to be called. */ + bool heartbeat; /* LACP heartbeat mode. */ }; struct slave { @@ -62,6 +62,7 @@ struct slave { struct lacp *lacp; /* LACP object containing this slave. */ uint16_t port_id; /* Port ID. */ uint16_t port_priority; /* Port Priority. */ + uint16_t key; /* Aggregation Key. 0 if default. */ char *name; /* Name of this slave. */ enum slave_status status; /* Slave status. */ @@ -181,10 +182,10 @@ lacp_configure(struct lacp *lacp, const struct lacp_settings *s) if (!eth_addr_equals(lacp->sys_id, s->id) || lacp->sys_priority != s->priority - || lacp->strict != s->strict) { + || lacp->heartbeat != s->heartbeat) { memcpy(lacp->sys_id, s->id, ETH_ADDR_LEN); lacp->sys_priority = s->priority; - lacp->strict = s->strict; + lacp->heartbeat = s->heartbeat; lacp->update = true; } @@ -272,9 +273,12 @@ lacp_slave_register(struct lacp *lacp, void *slave_, slave->name = xstrdup(s->name); } - if (slave->port_id != s->id || slave->port_priority != s->priority) { + if (slave->port_id != s->id + || slave->port_priority != s->priority + || slave->key != s->key) { slave->port_id = s->id; slave->port_priority = s->priority; + slave->key = s->key; lacp->update = true; @@ -425,6 +429,13 @@ lacp_update_attached(struct lacp *lacp) struct lacp_info lead_pri; static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 10); + if (lacp->heartbeat) { + HMAP_FOR_EACH (slave, node, &lacp->slaves) { + slave->attached = slave->status != LACP_DEFAULTED; + } + return; + } + lacp->update = false; lead = NULL; @@ -465,10 +476,6 @@ lacp_update_attached(struct lacp *lacp) slave->attached = false; } } - } else if (lacp->strict) { - HMAP_FOR_EACH (slave, node, &lacp->slaves) { - slave->attached = false; - } } } @@ -525,13 +532,15 @@ slave_set_expired(struct slave *slave) static void slave_get_actor(struct slave *slave, struct lacp_info *actor) { + struct lacp *lacp = slave->lacp; + uint16_t key; uint8_t state = 0; - if (slave->lacp->active) { + if (lacp->active) { state |= LACP_STATE_ACT; } - if (slave->lacp->lacp_time != LACP_TIME_SLOW) { + if (lacp->lacp_time != LACP_TIME_SLOW) { state |= LACP_STATE_TIME; } @@ -547,20 +556,25 @@ slave_get_actor(struct slave *slave, struct lacp_info *actor) state |= LACP_STATE_EXP; } - if (hmap_count(&slave->lacp->slaves) > 1) { + if (lacp->heartbeat || hmap_count(&lacp->slaves) > 1) { state |= LACP_STATE_AGG; } - if (slave->attached || !slave->lacp->negotiated) { + if (slave->attached || !lacp->negotiated) { state |= LACP_STATE_COL | LACP_STATE_DIST; } + key = lacp->key_slave->key; + if (!key) { + key = lacp->key_slave->port_id; + } + actor->state = state; - actor->key = htons(slave->lacp->key_slave->port_id); + actor->key = htons(key); actor->port_priority = htons(slave->port_priority); actor->port_id = htons(slave->port_id); - actor->sys_priority = htons(slave->lacp->sys_priority); - memcpy(&actor->sys_id, slave->lacp->sys_id, ETH_ADDR_LEN); + actor->sys_priority = htons(lacp->sys_priority); + memcpy(&actor->sys_id, lacp->sys_id, ETH_ADDR_LEN); } /* Given 'slave', populates 'priority' with data representing its LACP link @@ -702,8 +716,8 @@ lacp_unixctl_show(struct unixctl_conn *conn, ds_put_format(&ds, "lacp: %s\n", lacp->name); ds_put_format(&ds, "\tstatus: %s", lacp->active ? "active" : "passive"); - if (lacp->strict) { - ds_put_cstr(&ds, " strict"); + if (lacp->heartbeat) { + ds_put_cstr(&ds, " heartbeat"); } if (lacp->negotiated) { ds_put_cstr(&ds, " negotiated"); diff --git a/lib/lacp.h b/lib/lacp.h index 396569205..0fb797e89 100644 --- a/lib/lacp.h +++ b/lib/lacp.h @@ -88,7 +88,7 @@ struct lacp_settings { bool active; enum lacp_time lacp_time; long long int custom_time; - bool strict; + bool heartbeat; }; void lacp_init(void); @@ -106,6 +106,7 @@ struct lacp_slave_settings { char *name; uint16_t id; uint16_t priority; + uint16_t key; }; void lacp_slave_register(struct lacp *, void *slave_, diff --git a/lib/learning-switch.c b/lib/learning-switch.c index 75e04df62..6bd228623 100644 --- a/lib/learning-switch.c +++ b/lib/learning-switch.c @@ -238,7 +238,6 @@ lswitch_process_packet(struct lswitch *sw, struct rconn *rconn, case OFPUTIL_OFPST_PORT_REPLY: case OFPUTIL_OFPST_TABLE_REPLY: case OFPUTIL_OFPST_AGGREGATE_REPLY: - case OFPUTIL_NXT_TUN_ID_FROM_COOKIE: case OFPUTIL_NXT_ROLE_REQUEST: case OFPUTIL_NXT_ROLE_REPLY: case OFPUTIL_NXT_FLOW_MOD_TABLE_ID: diff --git a/lib/netdev-linux.c b/lib/netdev-linux.c index 6b1124fe5..5f13f18a4 100644 --- a/lib/netdev-linux.c +++ b/lib/netdev-linux.c @@ -15,6 +15,9 @@ */ #include <config.h> + +#include "netdev-linux.h" + #include <assert.h> #include <errno.h> #include <fcntl.h> @@ -3925,7 +3928,55 @@ tc_calc_buffer(unsigned int Bps, int mtu, uint64_t burst_bytes) unsigned int min_burst = tc_buffer_per_jiffy(Bps) + mtu; return tc_bytes_to_ticks(Bps, MAX(burst_bytes, min_burst)); } - + +/* Public utility functions. */ + +#define COPY_NETDEV_STATS \ + dst->rx_packets = src->rx_packets; \ + dst->tx_packets = src->tx_packets; \ + dst->rx_bytes = src->rx_bytes; \ + dst->tx_bytes = src->tx_bytes; \ + dst->rx_errors = src->rx_errors; \ + dst->tx_errors = src->tx_errors; \ + dst->rx_dropped = src->rx_dropped; \ + dst->tx_dropped = src->tx_dropped; \ + dst->multicast = src->multicast; \ + dst->collisions = src->collisions; \ + dst->rx_length_errors = src->rx_length_errors; \ + dst->rx_over_errors = src->rx_over_errors; \ + dst->rx_crc_errors = src->rx_crc_errors; \ + dst->rx_frame_errors = src->rx_frame_errors; \ + dst->rx_fifo_errors = src->rx_fifo_errors; \ + dst->rx_missed_errors = src->rx_missed_errors; \ + dst->tx_aborted_errors = src->tx_aborted_errors; \ + dst->tx_carrier_errors = src->tx_carrier_errors; \ + dst->tx_fifo_errors = src->tx_fifo_errors; \ + dst->tx_heartbeat_errors = src->tx_heartbeat_errors; \ + dst->tx_window_errors = src->tx_window_errors + +/* Copies 'src' into 'dst', performing format conversion in the process. */ +void +netdev_stats_from_rtnl_link_stats(struct netdev_stats *dst, + const struct rtnl_link_stats *src) +{ + COPY_NETDEV_STATS; +} + +/* Copies 'src' into 'dst', performing format conversion in the process. */ +void +netdev_stats_from_rtnl_link_stats64(struct netdev_stats *dst, + const struct rtnl_link_stats64 *src) +{ + COPY_NETDEV_STATS; +} + +/* Copies 'src' into 'dst', performing format conversion in the process. */ +void +netdev_stats_to_rtnl_link_stats64(struct rtnl_link_stats64 *dst, + const struct netdev_stats *src) +{ + COPY_NETDEV_STATS; +} /* Utility functions. */ @@ -3945,7 +3996,6 @@ get_stats_via_netlink(int ifindex, struct netdev_stats *stats) struct ofpbuf request; struct ofpbuf *reply; struct ifinfomsg *ifi; - const struct rtnl_link_stats *rtnl_stats; struct nlattr *attrs[ARRAY_SIZE(rtnlgrp_link_policy)]; int error; @@ -3973,28 +4023,7 @@ get_stats_via_netlink(int ifindex, struct netdev_stats *stats) return EPROTO; } - rtnl_stats = nl_attr_get(attrs[IFLA_STATS]); - stats->rx_packets = rtnl_stats->rx_packets; - stats->tx_packets = rtnl_stats->tx_packets; - stats->rx_bytes = rtnl_stats->rx_bytes; - stats->tx_bytes = rtnl_stats->tx_bytes; - stats->rx_errors = rtnl_stats->rx_errors; - stats->tx_errors = rtnl_stats->tx_errors; - stats->rx_dropped = rtnl_stats->rx_dropped; - stats->tx_dropped = rtnl_stats->tx_dropped; - stats->multicast = rtnl_stats->multicast; - stats->collisions = rtnl_stats->collisions; - stats->rx_length_errors = rtnl_stats->rx_length_errors; - stats->rx_over_errors = rtnl_stats->rx_over_errors; - stats->rx_crc_errors = rtnl_stats->rx_crc_errors; - stats->rx_frame_errors = rtnl_stats->rx_frame_errors; - stats->rx_fifo_errors = rtnl_stats->rx_fifo_errors; - stats->rx_missed_errors = rtnl_stats->rx_missed_errors; - stats->tx_aborted_errors = rtnl_stats->tx_aborted_errors; - stats->tx_carrier_errors = rtnl_stats->tx_carrier_errors; - stats->tx_fifo_errors = rtnl_stats->tx_fifo_errors; - stats->tx_heartbeat_errors = rtnl_stats->tx_heartbeat_errors; - stats->tx_window_errors = rtnl_stats->tx_window_errors; + netdev_stats_from_rtnl_link_stats(stats, nl_attr_get(attrs[IFLA_STATS])); ofpbuf_delete(reply); diff --git a/lib/netdev-linux.h b/lib/netdev-linux.h new file mode 100644 index 000000000..7a112049b --- /dev/null +++ b/lib/netdev-linux.h @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2011 Nicira Networks. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef NETDEV_LINUX_H +#define NETDEV_LINUX_H 1 + +/* These functions are Linux specific, so they should be used directly only by + * Linux-specific code. */ + +struct netdev_stats; +struct rtnl_link_stats; +struct rtnl_link_stats64; + +void netdev_stats_from_rtnl_link_stats(struct netdev_stats *dst, + const struct rtnl_link_stats *src); +void netdev_stats_from_rtnl_link_stats64(struct netdev_stats *dst, + const struct rtnl_link_stats64 *src); +void netdev_stats_to_rtnl_link_stats64(struct rtnl_link_stats64 *dst, + const struct netdev_stats *src); + +#endif /* netdev-linux.h */ diff --git a/lib/netdev-vport.c b/lib/netdev-vport.c index be2694159..e11cb2a8d 100644 --- a/lib/netdev-vport.c +++ b/lib/netdev-vport.c @@ -32,6 +32,7 @@ #include "hash.h" #include "hmap.h" #include "list.h" +#include "netdev-linux.h" #include "netdev-provider.h" #include "netlink.h" #include "netlink-socket.h" @@ -416,27 +417,7 @@ netdev_vport_get_stats(const struct netdev *netdev, struct netdev_stats *stats) return EOPNOTSUPP; } - stats->rx_packets = reply.stats->rx_packets; - stats->tx_packets = reply.stats->tx_packets; - stats->rx_bytes = reply.stats->rx_bytes; - stats->tx_bytes = reply.stats->tx_bytes; - stats->rx_errors = reply.stats->rx_errors; - stats->tx_errors = reply.stats->tx_errors; - stats->rx_dropped = reply.stats->rx_dropped; - stats->tx_dropped = reply.stats->tx_dropped; - stats->multicast = reply.stats->multicast; - stats->collisions = reply.stats->collisions; - stats->rx_length_errors = reply.stats->rx_length_errors; - stats->rx_over_errors = reply.stats->rx_over_errors; - stats->rx_crc_errors = reply.stats->rx_crc_errors; - stats->rx_frame_errors = reply.stats->rx_frame_errors; - stats->rx_fifo_errors = reply.stats->rx_fifo_errors; - stats->rx_missed_errors = reply.stats->rx_missed_errors; - stats->tx_aborted_errors = reply.stats->tx_aborted_errors; - stats->tx_carrier_errors = reply.stats->tx_carrier_errors; - stats->tx_fifo_errors = reply.stats->tx_fifo_errors; - stats->tx_heartbeat_errors = reply.stats->tx_heartbeat_errors; - stats->tx_window_errors = reply.stats->tx_window_errors; + netdev_stats_from_rtnl_link_stats64(stats, reply.stats); ofpbuf_delete(buf); @@ -450,27 +431,7 @@ netdev_vport_set_stats(struct netdev *netdev, const struct netdev_stats *stats) struct dpif_linux_vport vport; int err; - rtnl_stats.rx_packets = stats->rx_packets; - rtnl_stats.tx_packets = stats->tx_packets; - rtnl_stats.rx_bytes = stats->rx_bytes; - rtnl_stats.tx_bytes = stats->tx_bytes; - rtnl_stats.rx_errors = stats->rx_errors; - rtnl_stats.tx_errors = stats->tx_errors; - rtnl_stats.rx_dropped = stats->rx_dropped; - rtnl_stats.tx_dropped = stats->tx_dropped; - rtnl_stats.multicast = stats->multicast; - rtnl_stats.collisions = stats->collisions; - rtnl_stats.rx_length_errors = stats->rx_length_errors; - rtnl_stats.rx_over_errors = stats->rx_over_errors; - rtnl_stats.rx_crc_errors = stats->rx_crc_errors; - rtnl_stats.rx_frame_errors = stats->rx_frame_errors; - rtnl_stats.rx_fifo_errors = stats->rx_fifo_errors; - rtnl_stats.rx_missed_errors = stats->rx_missed_errors; - rtnl_stats.tx_aborted_errors = stats->tx_aborted_errors; - rtnl_stats.tx_carrier_errors = stats->tx_carrier_errors; - rtnl_stats.tx_fifo_errors = stats->tx_fifo_errors; - rtnl_stats.tx_heartbeat_errors = stats->tx_heartbeat_errors; - rtnl_stats.tx_window_errors = stats->tx_window_errors; + netdev_stats_to_rtnl_link_stats64(&rtnl_stats, stats); dpif_linux_vport_init(&vport); vport.cmd = ODP_VPORT_CMD_SET; @@ -667,7 +628,7 @@ parse_tunnel_config(const char *name, const char *type, ovs_be32 daddr = htonl(0); uint32_t flags; - flags = TNL_F_PMTUD | TNL_F_HDR_CACHE; + flags = TNL_F_DF_DEFAULT | TNL_F_PMTUD | TNL_F_HDR_CACHE; if (!strcmp(type, "gre")) { is_gre = true; } else if (!strcmp(type, "ipsec_gre")) { @@ -709,6 +670,14 @@ parse_tunnel_config(const char *name, const char *type, if (!strcmp(node->data, "true")) { flags |= TNL_F_CSUM; } + } else if (!strcmp(node->name, "df_inherit")) { + if (!strcmp(node->data, "true")) { + flags |= TNL_F_DF_INHERIT; + } + } else if (!strcmp(node->name, "df_default")) { + if (!strcmp(node->data, "false")) { + flags &= ~TNL_F_DF_DEFAULT; + } } else if (!strcmp(node->name, "pmtud")) { if (!strcmp(node->data, "false")) { flags &= ~TNL_F_PMTUD; @@ -891,6 +860,12 @@ unparse_tunnel_config(const char *name OVS_UNUSED, const char *type OVS_UNUSED, if (flags & TNL_F_CSUM) { smap_add(args, "csum", "true"); } + if (flags & TNL_F_DF_INHERIT) { + smap_add(args, "df_inherit", "true"); + } + if (!(flags & TNL_F_DF_DEFAULT)) { + smap_add(args, "df_default", "false"); + } if (!(flags & TNL_F_PMTUD)) { smap_add(args, "pmtud", "false"); } diff --git a/lib/ofp-parse.c b/lib/ofp-parse.c index c7ff4c323..29137ac9d 100644 --- a/lib/ofp-parse.c +++ b/lib/ofp-parse.c @@ -853,7 +853,7 @@ parse_ofp_flow_mod_str(struct list *packets, enum nx_flow_format *cur_format, parse_ofp_str(&fm, is_del ? NULL : &actions, string); fm.command = command; - min_format = ofputil_min_flow_format(&fm.cr, true, fm.cookie); + min_format = ofputil_min_flow_format(&fm.cr); next_format = MAX(*cur_format, min_format); if (next_format != *cur_format) { struct ofpbuf *sff = ofputil_make_set_flow_format(next_format); diff --git a/lib/ofp-print.c b/lib/ofp-print.c index 5b04d1923..cbac1e44a 100644 --- a/lib/ofp-print.c +++ b/lib/ofp-print.c @@ -780,9 +780,6 @@ ofp_match_to_string(const struct ofp_match *om, int verbosity) skip_type = false; } } - if (w & NXFW_TUN_ID) { - ds_put_cstr(&f, "tun_id_wild,"); - } print_wild(&f, "in_port=", w & OFPFW_IN_PORT, verbosity, "%d", ntohs(om->in_port)); print_wild(&f, "dl_vlan=", w & OFPFW_DL_VLAN, verbosity, @@ -837,7 +834,7 @@ ofp_print_flow_mod(struct ds *s, const struct ofp_header *oh, bool need_priority; int error; - error = ofputil_decode_flow_mod(&fm, oh, NXFF_OPENFLOW10, true); + error = ofputil_decode_flow_mod(&fm, oh, true); if (error) { ofp_print_error(s, error); return; @@ -937,7 +934,7 @@ ofp_print_flow_removed(struct ds *string, const struct ofp_header *oh) struct ofputil_flow_removed fr; int error; - error = ofputil_decode_flow_removed(&fr, oh, NXFF_OPENFLOW10); + error = ofputil_decode_flow_removed(&fr, oh); if (error) { ofp_print_error(string, error); return; @@ -1073,7 +1070,7 @@ ofp_print_flow_stats_request(struct ds *string, const struct ofp_header *oh) struct flow_stats_request fsr; int error; - error = ofputil_decode_flow_stats_request(&fsr, oh, NXFF_OPENFLOW10); + error = ofputil_decode_flow_stats_request(&fsr, oh); if (error) { ofp_print_error(string, error); return; @@ -1106,7 +1103,7 @@ ofp_print_flow_stats_reply(struct ds *string, const struct ofp_header *oh) struct ofputil_flow_stats fs; int retval; - retval = ofputil_decode_flow_stats_reply(&fs, &b, NXFF_OPENFLOW10); + retval = ofputil_decode_flow_stats_reply(&fs, &b); if (retval) { if (retval != EOF) { ds_put_cstr(string, " ***parse error***"); @@ -1335,13 +1332,6 @@ ofp_print_echo(struct ds *string, const struct ofp_header *oh, int verbosity) } static void -ofp_print_nxt_tun_id_from_cookie(struct ds *string, - const struct nxt_tun_id_cookie *ntic) -{ - ds_put_format(string, " set=%"PRIu8, ntic->set); -} - -static void ofp_print_nxt_role_message(struct ds *string, const struct nx_role_request *nrr) { @@ -1517,10 +1507,6 @@ ofp_to_string__(const struct ofp_header *oh, ofp_print_ofpst_aggregate_reply(string, oh); break; - case OFPUTIL_NXT_TUN_ID_FROM_COOKIE: - ofp_print_nxt_tun_id_from_cookie(string, msg); - break; - case OFPUTIL_NXT_ROLE_REQUEST: case OFPUTIL_NXT_ROLE_REPLY: ofp_print_nxt_role_message(string, msg); diff --git a/lib/ofp-util.c b/lib/ofp-util.c index 962727cc9..3487cbac1 100644 --- a/lib/ofp-util.c +++ b/lib/ofp-util.c @@ -102,25 +102,17 @@ enum { }; /* Converts the ofp_match in 'match' into a cls_rule in 'rule', with the given - * 'priority'. - * - * 'flow_format' must either NXFF_OPENFLOW10 or NXFF_TUN_ID_FROM_COOKIE. In - * the latter case only, 'flow''s tun_id field will be taken from the high bits - * of 'cookie', if 'match''s wildcards do not indicate that tun_id is - * wildcarded. */ + * 'priority'. */ void ofputil_cls_rule_from_match(const struct ofp_match *match, - unsigned int priority, - enum nx_flow_format flow_format, - ovs_be64 cookie, struct cls_rule *rule) + unsigned int priority, struct cls_rule *rule) { struct flow_wildcards *wc = &rule->wc; unsigned int ofpfw; ovs_be16 vid, pcp; /* Initialize rule->priority. */ - ofpfw = ntohl(match->wildcards); - ofpfw &= flow_format == NXFF_TUN_ID_FROM_COOKIE ? OVSFW_ALL : OFPFW_ALL; + ofpfw = ntohl(match->wildcards) & OFPFW_ALL; rule->priority = !ofpfw ? UINT16_MAX : priority; /* Initialize most of rule->wc. */ @@ -136,10 +128,6 @@ ofputil_cls_rule_from_match(const struct ofp_match *match, wc->nw_src_mask = ofputil_wcbits_to_netmask(ofpfw >> OFPFW_NW_SRC_SHIFT); wc->nw_dst_mask = ofputil_wcbits_to_netmask(ofpfw >> OFPFW_NW_DST_SHIFT); - if (flow_format == NXFF_TUN_ID_FROM_COOKIE && !(ofpfw & NXFW_TUN_ID)) { - cls_rule_set_tun_id(rule, htonll(ntohll(cookie) >> 32)); - } - if (ofpfw & OFPFW_DL_DST) { /* OpenFlow 1.0 OFPFW_DL_DST covers the whole Ethernet destination, but * Open vSwitch breaks the Ethernet destination into bits as FWW_DL_DST @@ -206,21 +194,9 @@ ofputil_cls_rule_from_match(const struct ofp_match *match, cls_rule_zero_wildcarded_fields(rule); } -/* Convert 'rule' into the OpenFlow match structure 'match'. 'flow_format' - * must either NXFF_OPENFLOW10 or NXFF_TUN_ID_FROM_COOKIE. - * - * The NXFF_TUN_ID_FROM_COOKIE flow format requires modifying the flow cookie. - * This function can help with that, if 'cookie_out' is nonnull. For - * NXFF_OPENFLOW10, or if the tunnel ID is wildcarded, 'cookie_in' will be - * copied directly to '*cookie_out'. For NXFF_TUN_ID_FROM_COOKIE when tunnel - * ID is matched, 'cookie_in' will be modified appropriately before setting - * '*cookie_out'. - */ +/* Convert 'rule' into the OpenFlow match structure 'match'. */ void -ofputil_cls_rule_to_match(const struct cls_rule *rule, - enum nx_flow_format flow_format, - struct ofp_match *match, - ovs_be64 cookie_in, ovs_be64 *cookie_out) +ofputil_cls_rule_to_match(const struct cls_rule *rule, struct ofp_match *match) { const struct flow_wildcards *wc = &rule->wc; unsigned int ofpfw; @@ -233,20 +209,6 @@ ofputil_cls_rule_to_match(const struct cls_rule *rule, ofpfw |= OFPFW_NW_TOS; } - /* Tunnel ID. */ - if (flow_format == NXFF_TUN_ID_FROM_COOKIE) { - if (wc->tun_id_mask == htonll(0)) { - ofpfw |= NXFW_TUN_ID; - } else { - uint32_t cookie_lo = ntohll(cookie_in); - uint32_t cookie_hi = ntohll(rule->flow.tun_id); - cookie_in = htonll(cookie_lo | ((uint64_t) cookie_hi << 32)); - } - } - if (cookie_out) { - *cookie_out = cookie_in; - } - /* Translate VLANs. */ match->dl_vlan = htons(0); match->dl_vlan_pcp = 0; @@ -412,10 +374,6 @@ ofputil_decode_vendor(const struct ofp_header *oh, != sizeof(struct nxt_flow_mod_table_id)); static const struct ofputil_msg_type nxt_messages[] = { - { OFPUTIL_NXT_TUN_ID_FROM_COOKIE, - NXT_TUN_ID_FROM_COOKIE, "NXT_TUN_ID_FROM_COOKIE", - sizeof(struct nxt_tun_id_cookie), 0 }, - { OFPUTIL_NXT_ROLE_REQUEST, NXT_ROLE_REQUEST, "NXT_ROLE_REQUEST", sizeof(struct nx_role_request), 0 }, @@ -816,7 +774,6 @@ ofputil_flow_format_is_valid(enum nx_flow_format flow_format) { switch (flow_format) { case NXFF_OPENFLOW10: - case NXFF_TUN_ID_FROM_COOKIE: case NXFF_NXM: return true; } @@ -830,8 +787,6 @@ ofputil_flow_format_to_string(enum nx_flow_format flow_format) switch (flow_format) { case NXFF_OPENFLOW10: return "openflow10"; - case NXFF_TUN_ID_FROM_COOKIE: - return "tun_id_from_cookie"; case NXFF_NXM: return "nxm"; default: @@ -843,7 +798,6 @@ int ofputil_flow_format_from_string(const char *s) { return (!strcmp(s, "openflow10") ? NXFF_OPENFLOW10 - : !strcmp(s, "tun_id_from_cookie") ? NXFF_TUN_ID_FROM_COOKIE : !strcmp(s, "nxm") ? NXFF_NXM : -1); } @@ -861,100 +815,43 @@ regs_fully_wildcarded(const struct flow_wildcards *wc) return true; } -static inline bool -is_nxm_required(const struct cls_rule *rule, bool cookie_support, - ovs_be64 cookie) +/* Returns the minimum nx_flow_format to use for sending 'rule' to a switch + * (e.g. to add or remove a flow). Only NXM can handle tunnel IDs, registers, + * or fixing the Ethernet multicast bit. Otherwise, it's better to use + * NXFF_OPENFLOW10 for backward compatibility. */ +enum nx_flow_format +ofputil_min_flow_format(const struct cls_rule *rule) { const struct flow_wildcards *wc = &rule->wc; - uint32_t cookie_hi; - uint64_t tun_id; /* Only NXM supports separately wildcards the Ethernet multicast bit. */ if (!(wc->wildcards & FWW_DL_DST) != !(wc->wildcards & FWW_ETH_MCAST)) { - return true; + return NXFF_NXM; } /* Only NXM supports matching ARP hardware addresses. */ if (!(wc->wildcards & FWW_ARP_SHA) || !(wc->wildcards & FWW_ARP_THA)) { - return true; + return NXFF_NXM; } /* Only NXM supports matching IPv6 traffic. */ if (!(wc->wildcards & FWW_DL_TYPE) && (rule->flow.dl_type == htons(ETH_TYPE_IPV6))) { - return true; + return NXFF_NXM; } /* Only NXM supports matching registers. */ if (!regs_fully_wildcarded(wc)) { - return true; + return NXFF_NXM; } - switch (wc->tun_id_mask) { - case CONSTANT_HTONLL(0): - /* Other formats can fully wildcard tun_id. */ - break; - - case CONSTANT_HTONLL(UINT64_MAX): - /* Only NXM supports tunnel ID matching without a cookie. */ - if (!cookie_support) { - return true; - } - - /* Only NXM supports 64-bit tunnel IDs. */ - tun_id = ntohll(rule->flow.tun_id); - if (tun_id > UINT32_MAX) { - return true; - } - - /* Only NXM supports a cookie whose top 32 bits conflict with the - * tunnel ID. */ - cookie_hi = ntohll(cookie) >> 32; - if (cookie_hi && cookie_hi != tun_id) { - return true; - } - break; - - default: - /* Only NXM supports partial matches on tunnel ID. */ - return true; + /* Only NXM supports matching tun_id. */ + if (wc->tun_id_mask != htonll(0)) { + return NXFF_NXM; } /* Other formats can express this rule. */ - return false; -} - -/* Returns the minimum nx_flow_format to use for sending 'rule' to a switch - * (e.g. to add or remove a flow). 'cookie_support' should be true if the - * command to be sent includes a flow cookie (as OFPT_FLOW_MOD does, for - * example) or false if the command does not (OFPST_FLOW and OFPST_AGGREGATE do - * not, for example). If 'cookie_support' is true, then 'cookie' should be the - * cookie to be sent; otherwise its value is ignored. - * - * The "best" flow format is chosen on this basis: - * - * - It must be capable of expressing the rule. NXFF_OPENFLOW10 flows can't - * handle tunnel IDs. NXFF_TUN_ID_FROM_COOKIE flows can't handle registers - * or fixing the Ethernet multicast bit, and can't handle tunnel IDs that - * conflict with the high 32 bits of the cookie or commands that don't - * support cookies. - * - * - Otherwise, the chosen format should be as backward compatible as - * possible. (NXFF_OPENFLOW10 is more backward compatible than - * NXFF_TUN_ID_FROM_COOKIE, which is more backward compatible than - * NXFF_NXM.) - */ -enum nx_flow_format -ofputil_min_flow_format(const struct cls_rule *rule, bool cookie_support, - ovs_be64 cookie) -{ - if (is_nxm_required(rule, cookie_support, cookie)) { - return NXFF_NXM; - } else if (rule->wc.tun_id_mask != htonll(0)) { - return NXFF_TUN_ID_FROM_COOKIE; - } else { - return NXFF_OPENFLOW10; - } + return NXFF_OPENFLOW10; } /* Returns an OpenFlow message that can be used to set the flow format to @@ -962,20 +859,11 @@ ofputil_min_flow_format(const struct cls_rule *rule, bool cookie_support, struct ofpbuf * ofputil_make_set_flow_format(enum nx_flow_format flow_format) { + struct nxt_set_flow_format *sff; struct ofpbuf *msg; - if (flow_format == NXFF_OPENFLOW10 - || flow_format == NXFF_TUN_ID_FROM_COOKIE) { - struct nxt_tun_id_cookie *tic; - - tic = make_nxmsg(sizeof *tic, NXT_TUN_ID_FROM_COOKIE, &msg); - tic->set = flow_format == NXFF_TUN_ID_FROM_COOKIE; - } else { - struct nxt_set_flow_format *sff; - - sff = make_nxmsg(sizeof *sff, NXT_SET_FLOW_FORMAT, &msg); - sff->format = htonl(flow_format); - } + sff = make_nxmsg(sizeof *sff, NXT_SET_FLOW_FORMAT, &msg); + sff->format = htonl(flow_format); return msg; } @@ -997,17 +885,12 @@ ofputil_make_flow_mod_table_id(bool flow_mod_table_id) * flow_mod in 'fm'. Returns 0 if successful, otherwise an OpenFlow error * code. * - * For OFPT_FLOW_MOD messages, 'flow_format' should be the current flow format - * at the time when the message was received. Otherwise 'flow_format' is - * ignored. - * * 'flow_mod_table_id' should be true if the NXT_FLOW_MOD_TABLE_ID extension is * enabled, false otherwise. * * Does not validate the flow_mod actions. */ int ofputil_decode_flow_mod(struct flow_mod *fm, const struct ofp_header *oh, - enum nx_flow_format flow_format, bool flow_mod_table_id) { const struct ofputil_msg_type *type; @@ -1049,8 +932,7 @@ ofputil_decode_flow_mod(struct flow_mod *fm, const struct ofp_header *oh, } /* Translate the message. */ - ofputil_cls_rule_from_match(&match, ntohs(ofm->priority), flow_format, - ofm->cookie, &fm->cr); + ofputil_cls_rule_from_match(&match, ntohs(ofm->priority), &fm->cr); fm->cookie = ofm->cookie; command = ntohs(ofm->command); fm->idle_timeout = ntohs(ofm->idle_timeout); @@ -1116,15 +998,13 @@ ofputil_encode_flow_mod(const struct flow_mod *fm, ? (fm->command & 0xff) | (fm->table_id << 8) : fm->command); - if (flow_format == NXFF_OPENFLOW10 - || flow_format == NXFF_TUN_ID_FROM_COOKIE) { + if (flow_format == NXFF_OPENFLOW10) { struct ofp_flow_mod *ofm; msg = ofpbuf_new(sizeof *ofm + actions_len); ofm = put_openflow(sizeof *ofm, OFPT_FLOW_MOD, msg); - ofputil_cls_rule_to_match(&fm->cr, flow_format, &ofm->match, - fm->cookie, &ofm->cookie); - ofm->command = htons(command); + ofputil_cls_rule_to_match(&fm->cr, &ofm->match); + ofm->command = htons(fm->command); ofm->idle_timeout = htons(fm->idle_timeout); ofm->hard_timeout = htons(fm->hard_timeout); ofm->priority = htons(fm->cr.priority); @@ -1161,13 +1041,12 @@ ofputil_encode_flow_mod(const struct flow_mod *fm, static int ofputil_decode_ofpst_flow_request(struct flow_stats_request *fsr, const struct ofp_header *oh, - enum nx_flow_format flow_format, bool aggregate) { const struct ofp_flow_stats_request *ofsr = ofputil_stats_body(oh); fsr->aggregate = aggregate; - ofputil_cls_rule_from_match(&ofsr->match, 0, flow_format, 0, &fsr->match); + ofputil_cls_rule_from_match(&ofsr->match, 0, &fsr->match); fsr->out_port = ntohs(ofsr->out_port); fsr->table_id = ofsr->table_id; @@ -1202,17 +1081,11 @@ ofputil_decode_nxst_flow_request(struct flow_stats_request *fsr, } /* Converts an OFPST_FLOW, OFPST_AGGREGATE, NXST_FLOW, or NXST_AGGREGATE - * request 'oh', received when the current flow format was 'flow_format', into - * an abstract flow_stats_request in 'fsr'. Returns 0 if successful, otherwise - * an OpenFlow error code. - * - * For OFPST_FLOW and OFPST_AGGREGATE messages, 'flow_format' should be the - * current flow format at the time when the message was received. Otherwise - * 'flow_format' is ignored. */ + * request 'oh', into an abstract flow_stats_request in 'fsr'. Returns 0 if + * successful, otherwise an OpenFlow error code. */ int ofputil_decode_flow_stats_request(struct flow_stats_request *fsr, - const struct ofp_header *oh, - enum nx_flow_format flow_format) + const struct ofp_header *oh) { const struct ofputil_msg_type *type; struct ofpbuf b; @@ -1224,10 +1097,10 @@ ofputil_decode_flow_stats_request(struct flow_stats_request *fsr, code = ofputil_msg_type_code(type); switch (code) { case OFPUTIL_OFPST_FLOW_REQUEST: - return ofputil_decode_ofpst_flow_request(fsr, oh, flow_format, false); + return ofputil_decode_ofpst_flow_request(fsr, oh, false); case OFPUTIL_OFPST_AGGREGATE_REQUEST: - return ofputil_decode_ofpst_flow_request(fsr, oh, flow_format, true); + return ofputil_decode_ofpst_flow_request(fsr, oh, true); case OFPUTIL_NXST_FLOW_REQUEST: return ofputil_decode_nxst_flow_request(fsr, oh, false); @@ -1250,8 +1123,7 @@ ofputil_encode_flow_stats_request(const struct flow_stats_request *fsr, { struct ofpbuf *msg; - if (flow_format == NXFF_OPENFLOW10 - || flow_format == NXFF_TUN_ID_FROM_COOKIE) { + if (flow_format == NXFF_OPENFLOW10) { struct ofp_flow_stats_request *ofsr; int type; @@ -1260,8 +1132,7 @@ ofputil_encode_flow_stats_request(const struct flow_stats_request *fsr, type = fsr->aggregate ? OFPST_AGGREGATE : OFPST_FLOW; ofsr = ofputil_make_stats_request(sizeof *ofsr, type, &msg); - ofputil_cls_rule_to_match(&fsr->match, flow_format, &ofsr->match, - 0, NULL); + ofputil_cls_rule_to_match(&fsr->match, &ofsr->match); ofsr->table_id = fsr->table_id; ofsr->out_port = htons(fsr->out_port); } else if (flow_format == NXFF_NXM) { @@ -1285,9 +1156,7 @@ ofputil_encode_flow_stats_request(const struct flow_stats_request *fsr, } /* Converts an OFPST_FLOW or NXST_FLOW reply in 'msg' into an abstract - * ofputil_flow_stats in 'fs'. For OFPST_FLOW messages, 'flow_format' should - * be the current flow format at the time when the request corresponding to the - * reply in 'msg' was sent. Otherwise 'flow_format' is ignored. + * ofputil_flow_stats in 'fs'. * * Multiple OFPST_FLOW or NXST_FLOW replies can be packed into a single * OpenFlow message. Calling this function multiple times for a single 'msg' @@ -1298,8 +1167,7 @@ ofputil_encode_flow_stats_request(const struct flow_stats_request *fsr, * otherwise a positive errno value. */ int ofputil_decode_flow_stats_reply(struct ofputil_flow_stats *fs, - struct ofpbuf *msg, - enum nx_flow_format flow_format) + struct ofpbuf *msg) { const struct ofputil_msg_type *type; int code; @@ -1344,7 +1212,7 @@ ofputil_decode_flow_stats_reply(struct ofputil_flow_stats *fs, fs->cookie = get_32aligned_be64(&ofs->cookie); ofputil_cls_rule_from_match(&ofs->match, ntohs(ofs->priority), - flow_format, fs->cookie, &fs->rule); + &fs->rule); fs->table_id = ofs->table_id; fs->duration_sec = ntohl(ofs->duration_sec); fs->duration_nsec = ntohl(ofs->duration_nsec); @@ -1395,18 +1263,12 @@ ofputil_decode_flow_stats_reply(struct ofputil_flow_stats *fs, return 0; } -/* Converts an OFPT_FLOW_REMOVED or NXT_FLOW_REMOVED message 'oh', received - * when the current flow format was 'flow_format', into an abstract - * ofputil_flow_removed in 'fr'. Returns 0 if successful, otherwise an - * OpenFlow error code. - * - * For OFPT_FLOW_REMOVED messages, 'flow_format' should be the current flow - * format at the time when the message was received. Otherwise 'flow_format' - * is ignored. */ +/* Converts an OFPT_FLOW_REMOVED or NXT_FLOW_REMOVED message 'oh' into an + * abstract ofputil_flow_removed in 'fr'. Returns 0 if successful, otherwise + * an OpenFlow error code. */ int ofputil_decode_flow_removed(struct ofputil_flow_removed *fr, - const struct ofp_header *oh, - enum nx_flow_format flow_format) + const struct ofp_header *oh) { const struct ofputil_msg_type *type; enum ofputil_msg_code code; @@ -1418,7 +1280,7 @@ ofputil_decode_flow_removed(struct ofputil_flow_removed *fr, ofr = (const struct ofp_flow_removed *) oh; ofputil_cls_rule_from_match(&ofr->match, ntohs(ofr->priority), - flow_format, ofr->cookie, &fr->rule); + &fr->rule); fr->cookie = ofr->cookie; fr->reason = ofr->reason; fr->duration_sec = ntohl(ofr->duration_sec); @@ -1466,14 +1328,12 @@ ofputil_encode_flow_removed(const struct ofputil_flow_removed *fr, { struct ofpbuf *msg; - if (flow_format == NXFF_OPENFLOW10 - || flow_format == NXFF_TUN_ID_FROM_COOKIE) { + if (flow_format == NXFF_OPENFLOW10) { struct ofp_flow_removed *ofr; ofr = make_openflow_xid(sizeof *ofr, OFPT_FLOW_REMOVED, htonl(0), &msg); - ofputil_cls_rule_to_match(&fr->rule, flow_format, &ofr->match, - fr->cookie, &ofr->cookie); + ofputil_cls_rule_to_match(&fr->rule, &ofr->match); ofr->priority = htons(fr->rule.priority); ofr->reason = fr->reason; ofr->duration_sec = htonl(fr->duration_sec); @@ -1768,7 +1628,7 @@ make_flow_mod(uint16_t command, const struct cls_rule *rule, ofm->header.length = htons(size); ofm->cookie = 0; ofm->priority = htons(MIN(rule->priority, UINT16_MAX)); - ofputil_cls_rule_to_match(rule, NXFF_OPENFLOW10, &ofm->match, 0, NULL); + ofputil_cls_rule_to_match(rule, &ofm->match); ofm->command = htons(command); return out; } @@ -2099,7 +1959,7 @@ check_action(const union ofp_action *a, unsigned int len, if (error) { return error; } - if (a->vlan_vid.vlan_vid & ~7) { + if (a->vlan_pcp.vlan_pcp & ~7) { return ofp_mkerr(OFPET_BAD_ACTION, OFPBAC_BAD_ARGUMENT); } return 0; @@ -2212,7 +2072,7 @@ normalize_match(struct ofp_match *m) enum { OFPFW_TP = OFPFW_TP_SRC | OFPFW_TP_DST }; uint32_t wc; - wc = ntohl(m->wildcards) & OVSFW_ALL; + wc = ntohl(m->wildcards) & OFPFW_ALL; if (wc & OFPFW_DL_TYPE) { m->dl_type = 0; diff --git a/lib/ofp-util.h b/lib/ofp-util.h index 55c2c5889..c87b04b74 100644 --- a/lib/ofp-util.h +++ b/lib/ofp-util.h @@ -71,7 +71,6 @@ enum ofputil_msg_code { OFPUTIL_OFPST_AGGREGATE_REPLY, /* NXT_* messages. */ - OFPUTIL_NXT_TUN_ID_FROM_COOKIE, OFPUTIL_NXT_ROLE_REQUEST, OFPUTIL_NXT_ROLE_REPLY, OFPUTIL_NXT_SET_FLOW_FORMAT, @@ -101,11 +100,8 @@ int ofputil_netmask_to_wcbits(ovs_be32 netmask); /* Work with OpenFlow 1.0 ofp_match. */ void ofputil_cls_rule_from_match(const struct ofp_match *, - unsigned int priority, enum nx_flow_format, - ovs_be64 cookie, struct cls_rule *); -void ofputil_cls_rule_to_match(const struct cls_rule *, enum nx_flow_format, - struct ofp_match *, - ovs_be64 cookie_in, ovs_be64 *cookie_out); + unsigned int priority, struct cls_rule *); +void ofputil_cls_rule_to_match(const struct cls_rule *, struct ofp_match *); void normalize_match(struct ofp_match *); char *ofp_match_to_literal_string(const struct ofp_match *match); @@ -117,9 +113,7 @@ ovs_be16 ofputil_dl_type_from_openflow(ovs_be16 ofp_dl_type); bool ofputil_flow_format_is_valid(enum nx_flow_format); const char *ofputil_flow_format_to_string(enum nx_flow_format); int ofputil_flow_format_from_string(const char *); -enum nx_flow_format ofputil_min_flow_format(const struct cls_rule *, - bool cookie_support, - ovs_be64 cookie); +enum nx_flow_format ofputil_min_flow_format(const struct cls_rule *); struct ofpbuf *ofputil_make_set_flow_format(enum nx_flow_format); @@ -142,7 +136,7 @@ struct flow_mod { }; int ofputil_decode_flow_mod(struct flow_mod *, const struct ofp_header *, - enum nx_flow_format, bool flow_mod_table_id); + bool flow_mod_table_id); struct ofpbuf *ofputil_encode_flow_mod(const struct flow_mod *, enum nx_flow_format, bool flow_mod_table_id); @@ -156,8 +150,7 @@ struct flow_stats_request { }; int ofputil_decode_flow_stats_request(struct flow_stats_request *, - const struct ofp_header *, - enum nx_flow_format); + const struct ofp_header *); struct ofpbuf *ofputil_encode_flow_stats_request( const struct flow_stats_request *, enum nx_flow_format); @@ -177,8 +170,7 @@ struct ofputil_flow_stats { }; int ofputil_decode_flow_stats_reply(struct ofputil_flow_stats *, - struct ofpbuf *msg, - enum nx_flow_format); + struct ofpbuf *msg); /* Flow removed message, independent of flow format. */ struct ofputil_flow_removed { @@ -193,8 +185,7 @@ struct ofputil_flow_removed { }; int ofputil_decode_flow_removed(struct ofputil_flow_removed *, - const struct ofp_header *, - enum nx_flow_format); + const struct ofp_header *); struct ofpbuf *ofputil_encode_flow_removed(const struct ofputil_flow_removed *, enum nx_flow_format); diff --git a/lib/stream-nossl.c b/lib/stream-nossl.c new file mode 100644 index 000000000..cdbbf5d7a --- /dev/null +++ b/lib/stream-nossl.c @@ -0,0 +1,76 @@ +/* + * Copyright (c) 2011 Nicira Networks. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include <config.h> +#include "stream-ssl.h" +#include "vlog.h" + +VLOG_DEFINE_THIS_MODULE(stream_nossl); + +/* Dummy function definitions, used when OVS is built without OpenSSL. */ + +bool +stream_ssl_is_configured(void) +{ + return false; +} + +static void NO_RETURN +nossl_option(const char *detail) +{ + VLOG_FATAL("%s specified but Open vSwitch was built without SSL support", + detail); +} + +void +stream_ssl_set_private_key_file(const char *file_name) +{ + if (file_name != NULL) { + nossl_option("Private key"); + } +} + +void +stream_ssl_set_certificate_file(const char *file_name) +{ + if (file_name != NULL) { + nossl_option("Certificate"); + } +} + +void +stream_ssl_set_ca_cert_file(const char *file_name, bool bootstrap OVS_UNUSED) +{ + if (file_name != NULL) { + nossl_option("CA certificate"); + } +} + +void +stream_ssl_set_peer_ca_cert_file(const char *file_name) +{ + if (file_name != NULL) { + nossl_option("Peer CA certificate"); + } +} + +void +stream_ssl_set_key_and_cert(const char *private_key_file, + const char *certificate_file) +{ + stream_ssl_set_private_key_file(private_key_file); + stream_ssl_set_certificate_file(certificate_file); +} diff --git a/lib/stream-ssl.h b/lib/stream-ssl.h index 6bea577d3..29c3120fd 100644 --- a/lib/stream-ssl.h +++ b/lib/stream-ssl.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2008, 2009, 2010 Nicira Networks. + * Copyright (c) 2008, 2009, 2010, 2011 Nicira Networks. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,28 +18,18 @@ #include <stdbool.h> -#ifdef HAVE_OPENSSL bool stream_ssl_is_configured(void); - void stream_ssl_set_private_key_file(const char *file_name); void stream_ssl_set_certificate_file(const char *file_name); void stream_ssl_set_ca_cert_file(const char *file_name, bool bootstrap); - +void stream_ssl_set_peer_ca_cert_file(const char *file_name); void stream_ssl_set_key_and_cert(const char *private_key_file, const char *certificate_file); - -void stream_ssl_set_peer_ca_cert_file(const char *file_name); - -/* Define the long options for SSL support. - * - * Note that the definition includes a final comma, and therefore a comma - * must not be supplied when using the definition. This is done so that - * compilation succeeds whether or not HAVE_OPENSSL is defined. */ -#define STREAM_SSL_LONG_OPTIONS \ +#define STREAM_SSL_LONG_OPTIONS \ {"private-key", required_argument, 0, 'p'}, \ {"certificate", required_argument, 0, 'c'}, \ - {"ca-cert", required_argument, 0, 'C'}, + {"ca-cert", required_argument, 0, 'C'} #define STREAM_SSL_OPTION_HANDLERS \ case 'p': \ @@ -53,13 +43,5 @@ void stream_ssl_set_peer_ca_cert_file(const char *file_name); case 'C': \ stream_ssl_set_ca_cert_file(optarg, false); \ break; -#else /* !HAVE_OPENSSL */ -static inline bool stream_ssl_is_configured(void) -{ - return false; -} -#define STREAM_SSL_LONG_OPTIONS -#define STREAM_SSL_OPTION_HANDLERS -#endif /* !HAVE_OPENSSL */ #endif /* stream-ssl.h */ |