void
ofputil_wildcard_from_ofpfw10(uint32_t ofpfw, struct flow_wildcards *wc)
{
- BUILD_ASSERT_DECL(FLOW_WC_SEQ == 25);
+ BUILD_ASSERT_DECL(FLOW_WC_SEQ == 26);
/* Initialize most of wc. */
flow_wildcards_init_catchall(wc);
enum ofperr err;
/* Pull OpenFlow headers for the first call. */
- if (!msg->l2) {
+ if (!msg->frame) {
ofpraw_pull_assert(msg);
}
enum ofperr err;
/* Pull OpenFlow headers for the first call. */
- if (!msg->l2) {
+ if (!msg->frame) {
ofpraw_pull_assert(msg);
}
queue->min_rate = UINT16_MAX;
queue->max_rate = UINT16_MAX;
- oh = reply->l2;
+ oh = reply->frame;
if (oh->version < OFP12_VERSION) {
const struct ofp10_packet_queue *opq10;
enum ofperr error;
enum ofpraw raw;
- error = (msg->l2
- ? ofpraw_decode(&raw, msg->l2)
+ error = (msg->frame
+ ? ofpraw_decode(&raw, msg->frame)
: ofpraw_pull(&raw, msg));
if (error) {
return error;
}
- oh = msg->l2;
+ oh = msg->frame;
if (!ofpbuf_size(msg)) {
return EOF;
struct ofp13_table_features *otf;
unsigned int len;
- if (!msg->l2) {
- msg->l2 = ofpbuf_data(msg);
+ if (!msg->frame) {
ofpraw_pull_assert(msg);
}
struct nx_flow_monitor_request *nfmr;
uint16_t flags;
- if (!msg->l2) {
- msg->l2 = ofpbuf_data(msg);
+ if (!msg->frame) {
ofpraw_pull_assert(msg);
}
unsigned int length;
struct ofp_header *oh;
- if (!msg->l2) {
- msg->l2 = ofpbuf_data(msg);
+ if (!msg->frame) {
ofpraw_pull_assert(msg);
}
goto bad_len;
}
- oh = msg->l2;
+ oh = msg->frame;
nfuh = ofpbuf_data(msg);
update->event = ntohs(nfuh->event);
msg = ofpbuf_from_list(list_back(replies));
start_ofs = ofpbuf_size(msg);
- version = ((struct ofp_header *)msg->l2)->version;
+ version = ((struct ofp_header *)msg->frame)->version;
if (update->event == NXFME_ABBREV) {
struct nx_flow_update_abbrev *nfua;
bool
ofputil_port_from_string(const char *s, ofp_port_t *portp)
{
- uint32_t port32;
+ unsigned int port32; /* int is at least 32 bits wide. */
+ if (*s == '-') {
+ VLOG_WARN("Negative value %s is not a valid port number.", s);
+ return false;
+ }
*portp = 0;
if (str_to_uint(s, 10, &port32)) {
if (port32 < ofp_to_u16(OFPP_MAX)) {
enum ofperr error;
enum ofpraw raw;
- error = (msg->l2
- ? ofpraw_decode(&raw, msg->l2)
+ error = (msg->frame
+ ? ofpraw_decode(&raw, msg->frame)
: ofpraw_pull(&raw, msg));
if (error) {
return error;
return request;
}
-static void *
-ofputil_group_stats_to_ofp11(const struct ofputil_group_stats *ogs,
- size_t base_len, struct list *replies)
+static void
+ofputil_group_stats_to_ofp11__(const struct ofputil_group_stats *gs,
+ struct ofp11_group_stats *gs11, size_t length,
+ struct ofp11_bucket_counter bucket_cnts[])
{
- struct ofp11_bucket_counter *bc11;
- struct ofp11_group_stats *gs11;
- size_t length;
int i;
- length = base_len + sizeof(struct ofp11_bucket_counter) * ogs->n_buckets;
-
- gs11 = ofpmp_append(replies, length);
- memset(gs11, 0, base_len);
+ memset(gs11, 0, length);
gs11->length = htons(length);
- gs11->group_id = htonl(ogs->group_id);
- gs11->ref_count = htonl(ogs->ref_count);
- gs11->packet_count = htonll(ogs->packet_count);
- gs11->byte_count = htonll(ogs->byte_count);
+ gs11->group_id = htonl(gs->group_id);
+ gs11->ref_count = htonl(gs->ref_count);
+ gs11->packet_count = htonll(gs->packet_count);
+ gs11->byte_count = htonll(gs->byte_count);
- bc11 = (void *) (((uint8_t *) gs11) + base_len);
- for (i = 0; i < ogs->n_buckets; i++) {
- const struct bucket_counter *obc = &ogs->bucket_stats[i];
-
- bc11[i].packet_count = htonll(obc->packet_count);
- bc11[i].byte_count = htonll(obc->byte_count);
+ for (i = 0; i < gs->n_buckets; i++) {
+ bucket_cnts[i].packet_count = htonll(gs->bucket_stats[i].packet_count);
+ bucket_cnts[i].byte_count = htonll(gs->bucket_stats[i].byte_count);
}
-
- return gs11;
}
static void
-ofputil_append_of13_group_stats(const struct ofputil_group_stats *ogs,
- struct list *replies)
+ofputil_group_stats_to_ofp11(const struct ofputil_group_stats *gs,
+ struct ofp11_group_stats *gs11, size_t length)
{
- struct ofp13_group_stats *gs13;
+ ofputil_group_stats_to_ofp11__(gs, gs11, length, gs11->bucket_stats);
+}
- gs13 = ofputil_group_stats_to_ofp11(ogs, sizeof *gs13, replies);
- gs13->duration_sec = htonl(ogs->duration_sec);
- gs13->duration_nsec = htonl(ogs->duration_nsec);
+static void
+ofputil_group_stats_to_ofp13(const struct ofputil_group_stats *gs,
+ struct ofp13_group_stats *gs13, size_t length)
+{
+ ofputil_group_stats_to_ofp11__(gs, &gs13->gs, length, gs13->bucket_stats);
+ gs13->duration_sec = htonl(gs->duration_sec);
+ gs13->duration_nsec = htonl(gs->duration_nsec);
}
-/* Encodes 'ogs' properly for the format of the list of group statistics
+/* Encodes 'gs' properly for the format of the list of group statistics
* replies already begun in 'replies' and appends it to the list. 'replies'
* must have originally been initialized with ofpmp_init(). */
void
ofputil_append_group_stats(struct list *replies,
- const struct ofputil_group_stats *ogs)
+ const struct ofputil_group_stats *gs)
{
struct ofpbuf *msg = ofpbuf_from_list(list_back(replies));
struct ofp_header *oh = ofpbuf_data(msg);
+ size_t length;
- switch ((enum ofp_version)oh->version) {
+ switch ((enum ofp_version) oh->version) {
case OFP11_VERSION:
- case OFP12_VERSION:
- ofputil_group_stats_to_ofp11(ogs, sizeof(struct ofp11_group_stats),
- replies);
- break;
+ case OFP12_VERSION:{
+ struct ofp11_group_stats *reply;
+
+ length = gs->n_buckets * sizeof reply->bucket_stats[0]
+ + sizeof *reply;
+ reply = ofpmp_append(replies, length);
+ ofputil_group_stats_to_ofp11(gs, reply, length);
+ break;
+ }
case OFP13_VERSION:
- ofputil_append_of13_group_stats(ogs, replies);
- break;
+ case OFP14_VERSION:{
+ struct ofp13_group_stats *reply;
- case OFP14_VERSION:
- OVS_NOT_REACHED();
- break;
+ length = gs->n_buckets * sizeof reply->bucket_stats[0]
+ + sizeof *reply;
+ reply = ofpmp_append(replies, length);
+ ofputil_group_stats_to_ofp13(gs, reply, length);
+ break;
+ }
case OFP10_VERSION:
default:
OVS_NOT_REACHED();
}
}
-
/* Returns an OpenFlow group features request for OpenFlow version
* 'ofp_version'. */
struct ofpbuf *
size_t i;
gs->bucket_stats = NULL;
- error = (msg->l2
- ? ofpraw_decode(&raw, msg->l2)
+ error = (msg->frame
+ ? ofpraw_decode(&raw, msg->frame)
: ofpraw_pull(&raw, msg));
if (error) {
return error;
struct ofp11_group_desc_stats *ogds;
size_t length;
- if (!msg->l2) {
+ if (!msg->frame) {
ofpraw_pull_assert(msg);
}
enum ofperr error;
enum ofpraw raw;
- error = (msg->l2
- ? ofpraw_decode(&raw, msg->l2)
+ error = (msg->frame
+ ? ofpraw_decode(&raw, msg->frame)
: ofpraw_pull(&raw, msg));
if (error) {
return error;
OVS_NOT_REACHED();
}
}
+
+enum ofperr
+ofputil_decode_bundle_ctrl(const struct ofp_header *oh,
+ struct ofputil_bundle_ctrl_msg *msg)
+{
+ struct ofpbuf b;
+ enum ofpraw raw;
+ const struct ofp14_bundle_ctrl_msg *m;
+
+ ofpbuf_use_const(&b, oh, ntohs(oh->length));
+ raw = ofpraw_pull_assert(&b);
+ ovs_assert(raw == OFPRAW_OFPT14_BUNDLE_CONTROL);
+
+ m = ofpbuf_l3(&b);
+ msg->bundle_id = ntohl(m->bundle_id);
+ msg->type = ntohs(m->type);
+ msg->flags = ntohs(m->flags);
+
+ return 0;
+}
+
+struct ofpbuf *
+ofputil_encode_bundle_ctrl_reply(const struct ofp_header *oh,
+ struct ofputil_bundle_ctrl_msg *msg)
+{
+ struct ofpbuf *buf;
+ struct ofp14_bundle_ctrl_msg *m;
+
+ buf = ofpraw_alloc_reply(OFPRAW_OFPT14_BUNDLE_CONTROL, oh, 0);
+ m = ofpbuf_put_zeros(buf, sizeof *m);
+
+ m->bundle_id = htonl(msg->bundle_id);
+ m->type = htons(msg->type);
+ m->flags = htons(msg->flags);
+
+ return buf;
+}
+
+enum ofperr
+ofputil_decode_bundle_add(const struct ofp_header *oh,
+ struct ofputil_bundle_add_msg *msg)
+{
+ const struct ofp14_bundle_ctrl_msg *m;
+ struct ofpbuf b;
+ enum ofpraw raw;
+ size_t inner_len;
+
+ ofpbuf_use_const(&b, oh, ntohs(oh->length));
+ raw = ofpraw_pull_assert(&b);
+ ovs_assert(raw == OFPRAW_OFPT14_BUNDLE_ADD_MESSAGE);
+
+ m = ofpbuf_pull(&b, sizeof *m);
+ msg->bundle_id = ntohl(m->bundle_id);
+ msg->flags = ntohs(m->flags);
+
+ msg->msg = ofpbuf_data(&b);
+ inner_len = ntohs(msg->msg->length);
+ if (inner_len < sizeof(struct ofp_header) || inner_len > ofpbuf_size(&b)) {
+ return OFPERR_OFPBFC_MSG_BAD_LEN;
+ }
+
+ return 0;
+}
+
+struct ofpbuf *
+ofputil_encode_bundle_add(enum ofp_version ofp_version,
+ struct ofputil_bundle_add_msg *msg)
+{
+ struct ofpbuf *request;
+ struct ofp14_bundle_ctrl_msg *m;
+
+ request = ofpraw_alloc(OFPRAW_OFPT14_BUNDLE_ADD_MESSAGE, ofp_version, 0);
+ m = ofpbuf_put_zeros(request, sizeof *m);
+
+ m->bundle_id = htonl(msg->bundle_id);
+ m->flags = htons(msg->flags);
+ ofpbuf_put(request, msg->msg, ntohs(msg->msg->length));
+
+ return request;
+}