2 * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014 Nicira, Inc.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at:
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
18 #include "ofp-print.h"
22 #include <sys/types.h>
23 #include <netinet/in.h>
30 #include "byte-order.h"
32 #include "dynamic-string.h"
35 #include "multipath.h"
36 #include "meta-flow.h"
39 #include "ofp-actions.h"
40 #include "ofp-errors.h"
44 #include "openflow/openflow.h"
45 #include "openflow/nicira-ext.h"
47 #include "type-props.h"
48 #include "unaligned.h"
52 static void ofp_print_queue_name(struct ds
*string
, uint32_t port
);
53 static void ofp_print_error(struct ds
*, enum ofperr
);
54 static void ofp_print_table_features(struct ds
*,
55 const struct ofputil_table_features
*,
56 const struct ofputil_table_stats
*);
58 /* Returns a string that represents the contents of the Ethernet frame in the
59 * 'len' bytes starting at 'data'. The caller must free the returned string.*/
61 ofp_packet_to_string(const void *data
, size_t len
)
63 struct ds ds
= DS_EMPTY_INITIALIZER
;
64 const struct pkt_metadata md
= PKT_METADATA_INITIALIZER(0);
69 ofpbuf_use_const(&buf
, data
, len
);
70 flow_extract(&buf
, &md
, &flow
);
71 flow_format(&ds
, &flow
);
73 l4_size
= ofpbuf_l4_size(&buf
);
75 if (flow
.nw_proto
== IPPROTO_TCP
&& l4_size
>= TCP_HEADER_LEN
) {
76 struct tcp_header
*th
= ofpbuf_l4(&buf
);
77 ds_put_format(&ds
, " tcp_csum:%"PRIx16
, ntohs(th
->tcp_csum
));
78 } else if (flow
.nw_proto
== IPPROTO_UDP
&& l4_size
>= UDP_HEADER_LEN
) {
79 struct udp_header
*uh
= ofpbuf_l4(&buf
);
80 ds_put_format(&ds
, " udp_csum:%"PRIx16
, ntohs(uh
->udp_csum
));
81 } else if (flow
.nw_proto
== IPPROTO_SCTP
&& l4_size
>= SCTP_HEADER_LEN
) {
82 struct sctp_header
*sh
= ofpbuf_l4(&buf
);
83 ds_put_format(&ds
, " sctp_csum:%"PRIx32
,
84 ntohl(get_16aligned_be32(&sh
->sctp_csum
)));
87 ds_put_char(&ds
, '\n');
93 ofp_print_packet_in(struct ds
*string
, const struct ofp_header
*oh
,
96 char reasonbuf
[OFPUTIL_PACKET_IN_REASON_BUFSIZE
];
97 struct ofputil_packet_in pin
;
101 error
= ofputil_decode_packet_in(&pin
, oh
);
103 ofp_print_error(string
, error
);
108 ds_put_format(string
, " table_id=%"PRIu8
, pin
.table_id
);
111 if (pin
.cookie
!= OVS_BE64_MAX
) {
112 ds_put_format(string
, " cookie=0x%"PRIx64
, ntohll(pin
.cookie
));
115 ds_put_format(string
, " total_len=%"PRIuSIZE
" in_port=", pin
.total_len
);
116 ofputil_format_port(pin
.fmd
.in_port
, string
);
118 if (pin
.fmd
.tun_id
!= htonll(0)) {
119 ds_put_format(string
, " tun_id=0x%"PRIx64
, ntohll(pin
.fmd
.tun_id
));
122 if (pin
.fmd
.tun_src
!= htonl(0)) {
123 ds_put_format(string
, " tun_src="IP_FMT
, IP_ARGS(pin
.fmd
.tun_src
));
126 if (pin
.fmd
.tun_dst
!= htonl(0)) {
127 ds_put_format(string
, " tun_dst="IP_FMT
, IP_ARGS(pin
.fmd
.tun_dst
));
130 if (pin
.fmd
.metadata
!= htonll(0)) {
131 ds_put_format(string
, " metadata=0x%"PRIx64
, ntohll(pin
.fmd
.metadata
));
134 for (i
= 0; i
< FLOW_N_REGS
; i
++) {
135 if (pin
.fmd
.regs
[i
]) {
136 ds_put_format(string
, " reg%d=0x%"PRIx32
, i
, pin
.fmd
.regs
[i
]);
140 if (pin
.fmd
.pkt_mark
!= 0) {
141 ds_put_format(string
, " pkt_mark=0x%"PRIx32
, pin
.fmd
.pkt_mark
);
144 ds_put_format(string
, " (via %s)",
145 ofputil_packet_in_reason_to_string(pin
.reason
, reasonbuf
,
148 ds_put_format(string
, " data_len=%"PRIuSIZE
, pin
.packet_len
);
149 if (pin
.buffer_id
== UINT32_MAX
) {
150 ds_put_format(string
, " (unbuffered)");
151 if (pin
.total_len
!= pin
.packet_len
) {
152 ds_put_format(string
, " (***total_len != data_len***)");
155 ds_put_format(string
, " buffer=0x%08"PRIx32
, pin
.buffer_id
);
156 if (pin
.total_len
< pin
.packet_len
) {
157 ds_put_format(string
, " (***total_len < data_len***)");
160 ds_put_char(string
, '\n');
163 char *packet
= ofp_packet_to_string(pin
.packet
, pin
.packet_len
);
164 ds_put_cstr(string
, packet
);
168 ds_put_hex_dump(string
, pin
.packet
, pin
.packet_len
, 0, false);
173 ofp_print_packet_out(struct ds
*string
, const struct ofp_header
*oh
,
176 struct ofputil_packet_out po
;
177 struct ofpbuf ofpacts
;
180 ofpbuf_init(&ofpacts
, 64);
181 error
= ofputil_decode_packet_out(&po
, oh
, &ofpacts
);
183 ofpbuf_uninit(&ofpacts
);
184 ofp_print_error(string
, error
);
188 ds_put_cstr(string
, " in_port=");
189 ofputil_format_port(po
.in_port
, string
);
191 ds_put_cstr(string
, " actions=");
192 ofpacts_format(po
.ofpacts
, po
.ofpacts_len
, string
);
194 if (po
.buffer_id
== UINT32_MAX
) {
195 ds_put_format(string
, " data_len=%"PRIuSIZE
, po
.packet_len
);
196 if (verbosity
> 0 && po
.packet_len
> 0) {
197 char *packet
= ofp_packet_to_string(po
.packet
, po
.packet_len
);
198 ds_put_char(string
, '\n');
199 ds_put_cstr(string
, packet
);
203 ds_put_hex_dump(string
, po
.packet
, po
.packet_len
, 0, false);
206 ds_put_format(string
, " buffer=0x%08"PRIx32
, po
.buffer_id
);
209 ofpbuf_uninit(&ofpacts
);
212 /* qsort comparison function. */
214 compare_ports(const void *a_
, const void *b_
)
216 const struct ofputil_phy_port
*a
= a_
;
217 const struct ofputil_phy_port
*b
= b_
;
218 uint16_t ap
= ofp_to_u16(a
->port_no
);
219 uint16_t bp
= ofp_to_u16(b
->port_no
);
221 return ap
< bp
? -1 : ap
> bp
;
225 ofp_print_bit_names(struct ds
*string
, uint32_t bits
,
226 const char *(*bit_to_name
)(uint32_t bit
),
233 ds_put_cstr(string
, "0");
237 for (i
= 0; i
< 32; i
++) {
238 uint32_t bit
= UINT32_C(1) << i
;
241 const char *name
= bit_to_name(bit
);
244 ds_put_char(string
, separator
);
246 ds_put_cstr(string
, name
);
254 ds_put_char(string
, separator
);
256 ds_put_format(string
, "0x%"PRIx32
, bits
);
261 netdev_feature_to_name(uint32_t bit
)
263 enum netdev_features f
= bit
;
266 case NETDEV_F_10MB_HD
: return "10MB-HD";
267 case NETDEV_F_10MB_FD
: return "10MB-FD";
268 case NETDEV_F_100MB_HD
: return "100MB-HD";
269 case NETDEV_F_100MB_FD
: return "100MB-FD";
270 case NETDEV_F_1GB_HD
: return "1GB-HD";
271 case NETDEV_F_1GB_FD
: return "1GB-FD";
272 case NETDEV_F_10GB_FD
: return "10GB-FD";
273 case NETDEV_F_40GB_FD
: return "40GB-FD";
274 case NETDEV_F_100GB_FD
: return "100GB-FD";
275 case NETDEV_F_1TB_FD
: return "1TB-FD";
276 case NETDEV_F_OTHER
: return "OTHER";
277 case NETDEV_F_COPPER
: return "COPPER";
278 case NETDEV_F_FIBER
: return "FIBER";
279 case NETDEV_F_AUTONEG
: return "AUTO_NEG";
280 case NETDEV_F_PAUSE
: return "AUTO_PAUSE";
281 case NETDEV_F_PAUSE_ASYM
: return "AUTO_PAUSE_ASYM";
288 ofp_print_port_features(struct ds
*string
, enum netdev_features features
)
290 ofp_print_bit_names(string
, features
, netdev_feature_to_name
, ' ');
291 ds_put_char(string
, '\n');
295 ofputil_port_config_to_name(uint32_t bit
)
297 enum ofputil_port_config pc
= bit
;
300 case OFPUTIL_PC_PORT_DOWN
: return "PORT_DOWN";
301 case OFPUTIL_PC_NO_STP
: return "NO_STP";
302 case OFPUTIL_PC_NO_RECV
: return "NO_RECV";
303 case OFPUTIL_PC_NO_RECV_STP
: return "NO_RECV_STP";
304 case OFPUTIL_PC_NO_FLOOD
: return "NO_FLOOD";
305 case OFPUTIL_PC_NO_FWD
: return "NO_FWD";
306 case OFPUTIL_PC_NO_PACKET_IN
: return "NO_PACKET_IN";
313 ofp_print_port_config(struct ds
*string
, enum ofputil_port_config config
)
315 ofp_print_bit_names(string
, config
, ofputil_port_config_to_name
, ' ');
316 ds_put_char(string
, '\n');
320 ofputil_port_state_to_name(uint32_t bit
)
322 enum ofputil_port_state ps
= bit
;
325 case OFPUTIL_PS_LINK_DOWN
: return "LINK_DOWN";
326 case OFPUTIL_PS_BLOCKED
: return "BLOCKED";
327 case OFPUTIL_PS_LIVE
: return "LIVE";
329 case OFPUTIL_PS_STP_LISTEN
:
330 case OFPUTIL_PS_STP_LEARN
:
331 case OFPUTIL_PS_STP_FORWARD
:
332 case OFPUTIL_PS_STP_BLOCK
:
333 /* Handled elsewhere. */
341 ofp_print_port_state(struct ds
*string
, enum ofputil_port_state state
)
343 enum ofputil_port_state stp_state
;
345 /* The STP state is a 2-bit field so it doesn't fit in with the bitmask
346 * pattern. We have to special case it.
348 * OVS doesn't support STP, so this field will always be 0 if we are
349 * talking to OVS, so we'd always print STP_LISTEN in that case.
350 * Therefore, we don't print anything at all if the value is STP_LISTEN, to
351 * avoid confusing users. */
352 stp_state
= state
& OFPUTIL_PS_STP_MASK
;
355 (stp_state
== OFPUTIL_PS_STP_LEARN
? "STP_LEARN"
356 : stp_state
== OFPUTIL_PS_STP_FORWARD
? "STP_FORWARD"
358 state
&= ~OFPUTIL_PS_STP_MASK
;
360 ofp_print_bit_names(string
, state
, ofputil_port_state_to_name
,
364 ofp_print_bit_names(string
, state
, ofputil_port_state_to_name
, ' ');
366 ds_put_char(string
, '\n');
370 ofp_print_phy_port(struct ds
*string
, const struct ofputil_phy_port
*port
)
372 char name
[sizeof port
->name
];
375 memcpy(name
, port
->name
, sizeof name
);
376 for (j
= 0; j
< sizeof name
- 1; j
++) {
377 if (!isprint((unsigned char) name
[j
])) {
383 ds_put_char(string
, ' ');
384 ofputil_format_port(port
->port_no
, string
);
385 ds_put_format(string
, "(%s): addr:"ETH_ADDR_FMT
"\n",
386 name
, ETH_ADDR_ARGS(port
->hw_addr
));
388 ds_put_cstr(string
, " config: ");
389 ofp_print_port_config(string
, port
->config
);
391 ds_put_cstr(string
, " state: ");
392 ofp_print_port_state(string
, port
->state
);
395 ds_put_format(string
, " current: ");
396 ofp_print_port_features(string
, port
->curr
);
398 if (port
->advertised
) {
399 ds_put_format(string
, " advertised: ");
400 ofp_print_port_features(string
, port
->advertised
);
402 if (port
->supported
) {
403 ds_put_format(string
, " supported: ");
404 ofp_print_port_features(string
, port
->supported
);
407 ds_put_format(string
, " peer: ");
408 ofp_print_port_features(string
, port
->peer
);
410 ds_put_format(string
, " speed: %"PRIu32
" Mbps now, "
411 "%"PRIu32
" Mbps max\n",
412 port
->curr_speed
/ UINT32_C(1000),
413 port
->max_speed
/ UINT32_C(1000));
416 /* Given a buffer 'b' that contains an array of OpenFlow ports of type
417 * 'ofp_version', writes a detailed description of each port into
420 ofp_print_phy_ports(struct ds
*string
, uint8_t ofp_version
,
423 struct ofputil_phy_port
*ports
;
424 size_t allocated_ports
, n_ports
;
430 for (n_ports
= 0; ; n_ports
++) {
431 if (n_ports
>= allocated_ports
) {
432 ports
= x2nrealloc(ports
, &allocated_ports
, sizeof *ports
);
435 retval
= ofputil_pull_phy_port(ofp_version
, b
, &ports
[n_ports
]);
441 qsort(ports
, n_ports
, sizeof *ports
, compare_ports
);
442 for (i
= 0; i
< n_ports
; i
++) {
443 ofp_print_phy_port(string
, &ports
[i
]);
448 ofp_print_error(string
, retval
);
453 ofputil_capabilities_to_name(uint32_t bit
)
455 enum ofputil_capabilities capabilities
= bit
;
457 switch (capabilities
) {
458 case OFPUTIL_C_FLOW_STATS
: return "FLOW_STATS";
459 case OFPUTIL_C_TABLE_STATS
: return "TABLE_STATS";
460 case OFPUTIL_C_PORT_STATS
: return "PORT_STATS";
461 case OFPUTIL_C_IP_REASM
: return "IP_REASM";
462 case OFPUTIL_C_QUEUE_STATS
: return "QUEUE_STATS";
463 case OFPUTIL_C_ARP_MATCH_IP
: return "ARP_MATCH_IP";
464 case OFPUTIL_C_STP
: return "STP";
465 case OFPUTIL_C_GROUP_STATS
: return "GROUP_STATS";
466 case OFPUTIL_C_PORT_BLOCKED
: return "PORT_BLOCKED";
473 ofp_print_switch_features(struct ds
*string
, const struct ofp_header
*oh
)
475 struct ofputil_switch_features features
;
479 error
= ofputil_decode_switch_features(oh
, &features
, &b
);
481 ofp_print_error(string
, error
);
485 ds_put_format(string
, " dpid:%016"PRIx64
"\n", features
.datapath_id
);
487 ds_put_format(string
, "n_tables:%"PRIu8
", n_buffers:%"PRIu32
,
488 features
.n_tables
, features
.n_buffers
);
489 if (features
.auxiliary_id
) {
490 ds_put_format(string
, ", auxiliary_id:%"PRIu8
, features
.auxiliary_id
);
492 ds_put_char(string
, '\n');
494 ds_put_cstr(string
, "capabilities: ");
495 ofp_print_bit_names(string
, features
.capabilities
,
496 ofputil_capabilities_to_name
, ' ');
497 ds_put_char(string
, '\n');
499 switch ((enum ofp_version
)oh
->version
) {
501 ds_put_cstr(string
, "actions: ");
502 ofpact_bitmap_format(features
.ofpacts
, string
);
503 ds_put_char(string
, '\n');
511 return; /* no ports in ofp13_switch_features */
516 ofp_print_phy_ports(string
, oh
->version
, &b
);
520 ofp_print_switch_config(struct ds
*string
, const struct ofp_switch_config
*osc
)
522 enum ofp_config_flags flags
;
524 flags
= ntohs(osc
->flags
);
526 ds_put_format(string
, " frags=%s", ofputil_frag_handling_to_string(flags
));
527 flags
&= ~OFPC_FRAG_MASK
;
529 if (flags
& OFPC_INVALID_TTL_TO_CONTROLLER
) {
530 ds_put_format(string
, " invalid_ttl_to_controller");
531 flags
&= ~OFPC_INVALID_TTL_TO_CONTROLLER
;
535 ds_put_format(string
, " ***unknown flags 0x%04"PRIx16
"***", flags
);
538 ds_put_format(string
, " miss_send_len=%"PRIu16
"\n", ntohs(osc
->miss_send_len
));
541 static void print_wild(struct ds
*string
, const char *leader
, int is_wild
,
542 int verbosity
, const char *format
, ...)
545 static void print_wild(struct ds
*string
, const char *leader
, int is_wild
,
546 int verbosity
, const char *format
, ...)
548 if (is_wild
&& verbosity
< 2) {
551 ds_put_cstr(string
, leader
);
555 va_start(args
, format
);
556 ds_put_format_valist(string
, format
, args
);
559 ds_put_char(string
, '*');
561 ds_put_char(string
, ',');
565 print_wild_port(struct ds
*string
, const char *leader
, int is_wild
,
566 int verbosity
, ofp_port_t port
)
568 if (is_wild
&& verbosity
< 2) {
571 ds_put_cstr(string
, leader
);
573 ofputil_format_port(port
, string
);
575 ds_put_char(string
, '*');
577 ds_put_char(string
, ',');
581 print_ip_netmask(struct ds
*string
, const char *leader
, ovs_be32 ip
,
582 uint32_t wild_bits
, int verbosity
)
584 if (wild_bits
>= 32 && verbosity
< 2) {
587 ds_put_cstr(string
, leader
);
588 if (wild_bits
< 32) {
589 ds_put_format(string
, IP_FMT
, IP_ARGS(ip
));
591 ds_put_format(string
, "/%d", 32 - wild_bits
);
594 ds_put_char(string
, '*');
596 ds_put_char(string
, ',');
600 ofp10_match_print(struct ds
*f
, const struct ofp10_match
*om
, int verbosity
)
602 char *s
= ofp10_match_to_string(om
, verbosity
);
608 ofp10_match_to_string(const struct ofp10_match
*om
, int verbosity
)
610 struct ds f
= DS_EMPTY_INITIALIZER
;
611 uint32_t w
= ntohl(om
->wildcards
);
612 bool skip_type
= false;
613 bool skip_proto
= false;
615 if (!(w
& OFPFW10_DL_TYPE
)) {
617 if (om
->dl_type
== htons(ETH_TYPE_IP
)) {
618 if (!(w
& OFPFW10_NW_PROTO
)) {
620 if (om
->nw_proto
== IPPROTO_ICMP
) {
621 ds_put_cstr(&f
, "icmp,");
622 } else if (om
->nw_proto
== IPPROTO_TCP
) {
623 ds_put_cstr(&f
, "tcp,");
624 } else if (om
->nw_proto
== IPPROTO_UDP
) {
625 ds_put_cstr(&f
, "udp,");
626 } else if (om
->nw_proto
== IPPROTO_SCTP
) {
627 ds_put_cstr(&f
, "sctp,");
629 ds_put_cstr(&f
, "ip,");
633 ds_put_cstr(&f
, "ip,");
635 } else if (om
->dl_type
== htons(ETH_TYPE_ARP
)) {
636 ds_put_cstr(&f
, "arp,");
637 } else if (om
->dl_type
== htons(ETH_TYPE_RARP
)){
638 ds_put_cstr(&f
, "rarp,");
639 } else if (om
->dl_type
== htons(ETH_TYPE_MPLS
)) {
640 ds_put_cstr(&f
, "mpls,");
641 } else if (om
->dl_type
== htons(ETH_TYPE_MPLS_MCAST
)) {
642 ds_put_cstr(&f
, "mplsm,");
647 print_wild_port(&f
, "in_port=", w
& OFPFW10_IN_PORT
, verbosity
,
648 u16_to_ofp(ntohs(om
->in_port
)));
649 print_wild(&f
, "dl_vlan=", w
& OFPFW10_DL_VLAN
, verbosity
,
650 "%d", ntohs(om
->dl_vlan
));
651 print_wild(&f
, "dl_vlan_pcp=", w
& OFPFW10_DL_VLAN_PCP
, verbosity
,
652 "%d", om
->dl_vlan_pcp
);
653 print_wild(&f
, "dl_src=", w
& OFPFW10_DL_SRC
, verbosity
,
654 ETH_ADDR_FMT
, ETH_ADDR_ARGS(om
->dl_src
));
655 print_wild(&f
, "dl_dst=", w
& OFPFW10_DL_DST
, verbosity
,
656 ETH_ADDR_FMT
, ETH_ADDR_ARGS(om
->dl_dst
));
658 print_wild(&f
, "dl_type=", w
& OFPFW10_DL_TYPE
, verbosity
,
659 "0x%04x", ntohs(om
->dl_type
));
661 print_ip_netmask(&f
, "nw_src=", om
->nw_src
,
662 (w
& OFPFW10_NW_SRC_MASK
) >> OFPFW10_NW_SRC_SHIFT
,
664 print_ip_netmask(&f
, "nw_dst=", om
->nw_dst
,
665 (w
& OFPFW10_NW_DST_MASK
) >> OFPFW10_NW_DST_SHIFT
,
668 if (om
->dl_type
== htons(ETH_TYPE_ARP
) ||
669 om
->dl_type
== htons(ETH_TYPE_RARP
)) {
670 print_wild(&f
, "arp_op=", w
& OFPFW10_NW_PROTO
, verbosity
,
673 print_wild(&f
, "nw_proto=", w
& OFPFW10_NW_PROTO
, verbosity
,
677 print_wild(&f
, "nw_tos=", w
& OFPFW10_NW_TOS
, verbosity
,
679 if (om
->nw_proto
== IPPROTO_ICMP
) {
680 print_wild(&f
, "icmp_type=", w
& OFPFW10_ICMP_TYPE
, verbosity
,
681 "%d", ntohs(om
->tp_src
));
682 print_wild(&f
, "icmp_code=", w
& OFPFW10_ICMP_CODE
, verbosity
,
683 "%d", ntohs(om
->tp_dst
));
685 print_wild(&f
, "tp_src=", w
& OFPFW10_TP_SRC
, verbosity
,
686 "%d", ntohs(om
->tp_src
));
687 print_wild(&f
, "tp_dst=", w
& OFPFW10_TP_DST
, verbosity
,
688 "%d", ntohs(om
->tp_dst
));
690 if (ds_last(&f
) == ',') {
697 ofp_print_flow_flags(struct ds
*s
, enum ofputil_flow_mod_flags flags
)
699 if (flags
& OFPUTIL_FF_SEND_FLOW_REM
) {
700 ds_put_cstr(s
, "send_flow_rem ");
702 if (flags
& OFPUTIL_FF_CHECK_OVERLAP
) {
703 ds_put_cstr(s
, "check_overlap ");
705 if (flags
& OFPUTIL_FF_RESET_COUNTS
) {
706 ds_put_cstr(s
, "reset_counts ");
708 if (flags
& OFPUTIL_FF_NO_PKT_COUNTS
) {
709 ds_put_cstr(s
, "no_packet_counts ");
711 if (flags
& OFPUTIL_FF_NO_BYT_COUNTS
) {
712 ds_put_cstr(s
, "no_byte_counts ");
714 if (flags
& OFPUTIL_FF_HIDDEN_FIELDS
) {
715 ds_put_cstr(s
, "allow_hidden_fields ");
717 if (flags
& OFPUTIL_FF_NO_READONLY
) {
718 ds_put_cstr(s
, "no_readonly_table ");
723 ofp_print_flow_mod(struct ds
*s
, const struct ofp_header
*oh
, int verbosity
)
725 struct ofputil_flow_mod fm
;
726 struct ofpbuf ofpacts
;
730 enum ofputil_protocol protocol
;
732 protocol
= ofputil_protocol_from_ofp_version(oh
->version
);
733 protocol
= ofputil_protocol_set_tid(protocol
, true);
735 ofpbuf_init(&ofpacts
, 64);
736 error
= ofputil_decode_flow_mod(&fm
, oh
, protocol
, &ofpacts
,
739 ofpbuf_uninit(&ofpacts
);
740 ofp_print_error(s
, error
);
745 switch (fm
.command
) {
747 ds_put_cstr(s
, "ADD");
750 ds_put_cstr(s
, "MOD");
752 case OFPFC_MODIFY_STRICT
:
753 ds_put_cstr(s
, "MOD_STRICT");
756 ds_put_cstr(s
, "DEL");
758 case OFPFC_DELETE_STRICT
:
759 ds_put_cstr(s
, "DEL_STRICT");
762 ds_put_format(s
, "cmd:%d", fm
.command
);
764 if (fm
.table_id
!= 0) {
765 ds_put_format(s
, " table:%d", fm
.table_id
);
769 ofpraw_decode(&raw
, oh
);
770 if (verbosity
>= 3 && raw
== OFPRAW_OFPT10_FLOW_MOD
) {
771 const struct ofp10_flow_mod
*ofm
= ofpmsg_body(oh
);
772 ofp10_match_print(s
, &ofm
->match
, verbosity
);
774 /* ofp_print_match() doesn't print priority. */
775 need_priority
= true;
776 } else if (verbosity
>= 3 && raw
== OFPRAW_NXT_FLOW_MOD
) {
777 const struct nx_flow_mod
*nfm
= ofpmsg_body(oh
);
778 const void *nxm
= nfm
+ 1;
781 nxm_s
= nx_match_to_string(nxm
, ntohs(nfm
->match_len
));
782 ds_put_cstr(s
, nxm_s
);
785 /* nx_match_to_string() doesn't print priority. */
786 need_priority
= true;
788 match_format(&fm
.match
, s
, fm
.priority
);
790 /* match_format() does print priority. */
791 need_priority
= false;
794 if (ds_last(s
) != ' ') {
797 if (fm
.new_cookie
!= htonll(0) && fm
.new_cookie
!= OVS_BE64_MAX
) {
798 ds_put_format(s
, "cookie:0x%"PRIx64
" ", ntohll(fm
.new_cookie
));
800 if (fm
.cookie_mask
!= htonll(0)) {
801 ds_put_format(s
, "cookie:0x%"PRIx64
"/0x%"PRIx64
" ",
802 ntohll(fm
.cookie
), ntohll(fm
.cookie_mask
));
804 if (fm
.idle_timeout
!= OFP_FLOW_PERMANENT
) {
805 ds_put_format(s
, "idle:%"PRIu16
" ", fm
.idle_timeout
);
807 if (fm
.hard_timeout
!= OFP_FLOW_PERMANENT
) {
808 ds_put_format(s
, "hard:%"PRIu16
" ", fm
.hard_timeout
);
810 if (fm
.priority
!= OFP_DEFAULT_PRIORITY
&& need_priority
) {
811 ds_put_format(s
, "pri:%"PRIu16
" ", fm
.priority
);
813 if (fm
.buffer_id
!= UINT32_MAX
) {
814 ds_put_format(s
, "buf:0x%"PRIx32
" ", fm
.buffer_id
);
816 if (fm
.out_port
!= OFPP_ANY
) {
817 ds_put_format(s
, "out_port:");
818 ofputil_format_port(fm
.out_port
, s
);
822 if (oh
->version
== OFP10_VERSION
|| oh
->version
== OFP11_VERSION
) {
823 /* Don't print the reset_counts flag for OF1.0 and OF1.1 because those
824 * versions don't really have such a flag and printing one is likely to
826 fm
.flags
&= ~OFPUTIL_FF_RESET_COUNTS
;
828 ofp_print_flow_flags(s
, fm
.flags
);
830 ds_put_cstr(s
, "actions=");
831 ofpacts_format(fm
.ofpacts
, fm
.ofpacts_len
, s
);
832 ofpbuf_uninit(&ofpacts
);
836 ofp_print_duration(struct ds
*string
, unsigned int sec
, unsigned int nsec
)
838 ds_put_format(string
, "%u", sec
);
840 /* If there are no fractional seconds, don't print any decimals.
842 * If the fractional seconds can be expressed exactly as milliseconds,
843 * print 3 decimals. Open vSwitch provides millisecond precision for most
844 * time measurements, so printing 3 decimals every time makes it easier to
845 * spot real changes in flow dumps that refresh themselves quickly.
847 * If the fractional seconds are more precise than milliseconds, print the
848 * number of decimals needed to express them exactly.
851 unsigned int msec
= nsec
/ 1000000;
852 if (msec
* 1000000 == nsec
) {
853 ds_put_format(string
, ".%03u", msec
);
855 ds_put_format(string
, ".%09u", nsec
);
856 while (string
->string
[string
->length
- 1] == '0') {
861 ds_put_char(string
, 's');
864 /* Returns a string form of 'reason'. The return value is either a statically
865 * allocated constant string or the 'bufsize'-byte buffer 'reasonbuf'.
866 * 'bufsize' should be at least OFP_FLOW_REMOVED_REASON_BUFSIZE. */
867 #define OFP_FLOW_REMOVED_REASON_BUFSIZE (INT_STRLEN(int) + 1)
869 ofp_flow_removed_reason_to_string(enum ofp_flow_removed_reason reason
,
870 char *reasonbuf
, size_t bufsize
)
873 case OFPRR_IDLE_TIMEOUT
:
875 case OFPRR_HARD_TIMEOUT
:
879 case OFPRR_GROUP_DELETE
:
880 return "group_delete";
883 case OFPRR_METER_DELETE
:
884 return "meter_delete";
886 snprintf(reasonbuf
, bufsize
, "%d", (int) reason
);
892 ofp_print_flow_removed(struct ds
*string
, const struct ofp_header
*oh
)
894 char reasonbuf
[OFP_FLOW_REMOVED_REASON_BUFSIZE
];
895 struct ofputil_flow_removed fr
;
898 error
= ofputil_decode_flow_removed(&fr
, oh
);
900 ofp_print_error(string
, error
);
904 ds_put_char(string
, ' ');
905 match_format(&fr
.match
, string
, fr
.priority
);
907 ds_put_format(string
, " reason=%s",
908 ofp_flow_removed_reason_to_string(fr
.reason
, reasonbuf
,
911 if (fr
.table_id
!= 255) {
912 ds_put_format(string
, " table_id=%"PRIu8
, fr
.table_id
);
915 if (fr
.cookie
!= htonll(0)) {
916 ds_put_format(string
, " cookie:0x%"PRIx64
, ntohll(fr
.cookie
));
918 ds_put_cstr(string
, " duration");
919 ofp_print_duration(string
, fr
.duration_sec
, fr
.duration_nsec
);
920 ds_put_format(string
, " idle%"PRIu16
, fr
.idle_timeout
);
921 if (fr
.hard_timeout
) {
922 /* The hard timeout was only added in OF1.2, so only print it if it is
923 * actually in use to avoid gratuitous change to the formatting. */
924 ds_put_format(string
, " hard%"PRIu16
, fr
.hard_timeout
);
926 ds_put_format(string
, " pkts%"PRIu64
" bytes%"PRIu64
"\n",
927 fr
.packet_count
, fr
.byte_count
);
931 ofp_print_port_mod(struct ds
*string
, const struct ofp_header
*oh
)
933 struct ofputil_port_mod pm
;
936 error
= ofputil_decode_port_mod(oh
, &pm
, true);
938 ofp_print_error(string
, error
);
942 ds_put_cstr(string
, "port: ");
943 ofputil_format_port(pm
.port_no
, string
);
944 ds_put_format(string
, ": addr:"ETH_ADDR_FMT
"\n",
945 ETH_ADDR_ARGS(pm
.hw_addr
));
947 ds_put_cstr(string
, " config: ");
948 ofp_print_port_config(string
, pm
.config
);
950 ds_put_cstr(string
, " mask: ");
951 ofp_print_port_config(string
, pm
.mask
);
953 ds_put_cstr(string
, " advertise: ");
955 ofp_print_port_features(string
, pm
.advertise
);
957 ds_put_cstr(string
, "UNCHANGED\n");
962 ofp_print_table_miss_config(struct ds
*string
, enum ofputil_table_miss miss
)
965 case OFPUTIL_TABLE_MISS_CONTROLLER
:
966 ds_put_cstr(string
, "controller\n");
968 case OFPUTIL_TABLE_MISS_CONTINUE
:
969 ds_put_cstr(string
, "continue\n");
971 case OFPUTIL_TABLE_MISS_DROP
:
972 ds_put_cstr(string
, "drop\n");
974 case OFPUTIL_TABLE_MISS_DEFAULT
:
976 ds_put_format(string
, "Unknown (%d)\n", miss
);
982 ofp_print_table_mod(struct ds
*string
, const struct ofp_header
*oh
)
984 struct ofputil_table_mod pm
;
987 error
= ofputil_decode_table_mod(oh
, &pm
);
989 ofp_print_error(string
, error
);
993 if (pm
.table_id
== 0xff) {
994 ds_put_cstr(string
, " table_id: ALL_TABLES");
996 ds_put_format(string
, " table_id=%"PRIu8
, pm
.table_id
);
999 if (pm
.miss_config
!= OFPUTIL_TABLE_MISS_DEFAULT
) {
1000 ds_put_cstr(string
, ", flow_miss_config=");
1001 ofp_print_table_miss_config(string
, pm
.miss_config
);
1006 ofp_print_queue_get_config_request(struct ds
*string
,
1007 const struct ofp_header
*oh
)
1012 error
= ofputil_decode_queue_get_config_request(oh
, &port
);
1014 ofp_print_error(string
, error
);
1018 ds_put_cstr(string
, " port=");
1019 ofputil_format_port(port
, string
);
1023 print_queue_rate(struct ds
*string
, const char *name
, unsigned int rate
)
1026 ds_put_format(string
, " %s:%u.%u%%", name
, rate
/ 10, rate
% 10);
1027 } else if (rate
< UINT16_MAX
) {
1028 ds_put_format(string
, " %s:(disabled)", name
);
1033 ofp_print_queue_get_config_reply(struct ds
*string
,
1034 const struct ofp_header
*oh
)
1040 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1041 error
= ofputil_decode_queue_get_config_reply(&b
, &port
);
1043 ofp_print_error(string
, error
);
1047 ds_put_cstr(string
, " port=");
1048 ofputil_format_port(port
, string
);
1049 ds_put_char(string
, '\n');
1052 struct ofputil_queue_config queue
;
1055 retval
= ofputil_pull_queue_get_config_reply(&b
, &queue
);
1057 if (retval
!= EOF
) {
1058 ofp_print_error(string
, retval
);
1063 ds_put_format(string
, "queue %"PRIu32
":", queue
.queue_id
);
1064 print_queue_rate(string
, "min_rate", queue
.min_rate
);
1065 print_queue_rate(string
, "max_rate", queue
.max_rate
);
1066 ds_put_char(string
, '\n');
1071 ofp_print_meter_flags(struct ds
*s
, uint16_t flags
)
1073 if (flags
& OFPMF13_KBPS
) {
1074 ds_put_cstr(s
, "kbps ");
1076 if (flags
& OFPMF13_PKTPS
) {
1077 ds_put_cstr(s
, "pktps ");
1079 if (flags
& OFPMF13_BURST
) {
1080 ds_put_cstr(s
, "burst ");
1082 if (flags
& OFPMF13_STATS
) {
1083 ds_put_cstr(s
, "stats ");
1086 flags
&= ~(OFPMF13_KBPS
| OFPMF13_PKTPS
| OFPMF13_BURST
| OFPMF13_STATS
);
1088 ds_put_format(s
, "flags:0x%"PRIx16
" ", flags
);
1093 ofp_print_meter_band(struct ds
*s
, uint16_t flags
,
1094 const struct ofputil_meter_band
*mb
)
1096 ds_put_cstr(s
, "\ntype=");
1099 ds_put_cstr(s
, "drop");
1101 case OFPMBT13_DSCP_REMARK
:
1102 ds_put_cstr(s
, "dscp_remark");
1105 ds_put_format(s
, "%u", mb
->type
);
1108 ds_put_format(s
, " rate=%"PRIu32
, mb
->rate
);
1110 if (flags
& OFPMF13_BURST
) {
1111 ds_put_format(s
, " burst_size=%"PRIu32
, mb
->burst_size
);
1113 if (mb
->type
== OFPMBT13_DSCP_REMARK
) {
1114 ds_put_format(s
, " prec_level=%"PRIu8
, mb
->prec_level
);
1119 ofp_print_meter_stats(struct ds
*s
, const struct ofputil_meter_stats
*ms
)
1123 ds_put_format(s
, "meter:%"PRIu32
" ", ms
->meter_id
);
1124 ds_put_format(s
, "flow_count:%"PRIu32
" ", ms
->flow_count
);
1125 ds_put_format(s
, "packet_in_count:%"PRIu64
" ", ms
->packet_in_count
);
1126 ds_put_format(s
, "byte_in_count:%"PRIu64
" ", ms
->byte_in_count
);
1127 ds_put_cstr(s
, "duration:");
1128 ofp_print_duration(s
, ms
->duration_sec
, ms
->duration_nsec
);
1129 ds_put_char(s
, ' ');
1131 ds_put_cstr(s
, "bands:\n");
1132 for (i
= 0; i
< ms
->n_bands
; ++i
) {
1133 ds_put_format(s
, "%d: ", i
);
1134 ds_put_format(s
, "packet_count:%"PRIu64
" ", ms
->bands
[i
].packet_count
);
1135 ds_put_format(s
, "byte_count:%"PRIu64
"\n", ms
->bands
[i
].byte_count
);
1140 ofp_print_meter_config(struct ds
*s
, const struct ofputil_meter_config
*mc
)
1144 ds_put_format(s
, "meter=%"PRIu32
" ", mc
->meter_id
);
1146 ofp_print_meter_flags(s
, mc
->flags
);
1148 ds_put_cstr(s
, "bands=");
1149 for (i
= 0; i
< mc
->n_bands
; ++i
) {
1150 ofp_print_meter_band(s
, mc
->flags
, &mc
->bands
[i
]);
1152 ds_put_char(s
, '\n');
1156 ofp_print_meter_mod(struct ds
*s
, const struct ofp_header
*oh
)
1158 struct ofputil_meter_mod mm
;
1159 struct ofpbuf bands
;
1162 ofpbuf_init(&bands
, 64);
1163 error
= ofputil_decode_meter_mod(oh
, &mm
, &bands
);
1165 ofpbuf_uninit(&bands
);
1166 ofp_print_error(s
, error
);
1170 switch (mm
.command
) {
1172 ds_put_cstr(s
, " ADD ");
1174 case OFPMC13_MODIFY
:
1175 ds_put_cstr(s
, " MOD ");
1177 case OFPMC13_DELETE
:
1178 ds_put_cstr(s
, " DEL ");
1181 ds_put_format(s
, " cmd:%d ", mm
.command
);
1184 ofp_print_meter_config(s
, &mm
.meter
);
1185 ofpbuf_uninit(&bands
);
1189 ofp_print_meter_stats_request(struct ds
*s
, const struct ofp_header
*oh
)
1193 ofputil_decode_meter_request(oh
, &meter_id
);
1195 ds_put_format(s
, " meter=%"PRIu32
, meter_id
);
1199 ofputil_meter_capabilities_to_name(uint32_t bit
)
1201 enum ofp13_meter_flags flag
= bit
;
1204 case OFPMF13_KBPS
: return "kbps";
1205 case OFPMF13_PKTPS
: return "pktps";
1206 case OFPMF13_BURST
: return "burst";
1207 case OFPMF13_STATS
: return "stats";
1214 ofputil_meter_band_types_to_name(uint32_t bit
)
1217 case 1 << OFPMBT13_DROP
: return "drop";
1218 case 1 << OFPMBT13_DSCP_REMARK
: return "dscp_remark";
1225 ofp_print_meter_features_reply(struct ds
*s
, const struct ofp_header
*oh
)
1227 struct ofputil_meter_features mf
;
1229 ofputil_decode_meter_features(oh
, &mf
);
1231 ds_put_format(s
, "\nmax_meter:%"PRIu32
, mf
.max_meters
);
1232 ds_put_format(s
, " max_bands:%"PRIu8
, mf
.max_bands
);
1233 ds_put_format(s
, " max_color:%"PRIu8
"\n", mf
.max_color
);
1235 ds_put_cstr(s
, "band_types: ");
1236 ofp_print_bit_names(s
, mf
.band_types
,
1237 ofputil_meter_band_types_to_name
, ' ');
1238 ds_put_char(s
, '\n');
1240 ds_put_cstr(s
, "capabilities: ");
1241 ofp_print_bit_names(s
, mf
.capabilities
,
1242 ofputil_meter_capabilities_to_name
, ' ');
1243 ds_put_char(s
, '\n');
1247 ofp_print_meter_config_reply(struct ds
*s
, const struct ofp_header
*oh
)
1249 struct ofpbuf bands
;
1252 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1253 ofpbuf_init(&bands
, 64);
1255 struct ofputil_meter_config mc
;
1258 retval
= ofputil_decode_meter_config(&b
, &mc
, &bands
);
1260 if (retval
!= EOF
) {
1261 ofp_print_error(s
, retval
);
1265 ds_put_char(s
, '\n');
1266 ofp_print_meter_config(s
, &mc
);
1268 ofpbuf_uninit(&bands
);
1272 ofp_print_meter_stats_reply(struct ds
*s
, const struct ofp_header
*oh
)
1274 struct ofpbuf bands
;
1277 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1278 ofpbuf_init(&bands
, 64);
1280 struct ofputil_meter_stats ms
;
1283 retval
= ofputil_decode_meter_stats(&b
, &ms
, &bands
);
1285 if (retval
!= EOF
) {
1286 ofp_print_error(s
, retval
);
1290 ds_put_char(s
, '\n');
1291 ofp_print_meter_stats(s
, &ms
);
1293 ofpbuf_uninit(&bands
);
1297 ofp_print_error(struct ds
*string
, enum ofperr error
)
1299 if (string
->length
) {
1300 ds_put_char(string
, ' ');
1302 ds_put_format(string
, "***decode error: %s***\n", ofperr_get_name(error
));
1306 ofp_print_hello(struct ds
*string
, const struct ofp_header
*oh
)
1308 uint32_t allowed_versions
;
1311 ok
= ofputil_decode_hello(oh
, &allowed_versions
);
1313 ds_put_cstr(string
, "\n version bitmap: ");
1314 ofputil_format_version_bitmap(string
, allowed_versions
);
1317 ds_put_cstr(string
, "\n unknown data in hello:\n");
1318 ds_put_hex_dump(string
, oh
, ntohs(oh
->length
), 0, true);
1323 ofp_print_error_msg(struct ds
*string
, const struct ofp_header
*oh
)
1325 size_t len
= ntohs(oh
->length
);
1326 struct ofpbuf payload
;
1330 error
= ofperr_decode_msg(oh
, &payload
);
1332 ds_put_cstr(string
, "***decode error***");
1333 ds_put_hex_dump(string
, oh
+ 1, len
- sizeof *oh
, 0, true);
1337 ds_put_format(string
, " %s\n", ofperr_get_name(error
));
1339 if (error
== OFPERR_OFPHFC_INCOMPATIBLE
|| error
== OFPERR_OFPHFC_EPERM
) {
1340 ds_put_printable(string
, ofpbuf_data(&payload
), ofpbuf_size(&payload
));
1342 s
= ofp_to_string(ofpbuf_data(&payload
), ofpbuf_size(&payload
), 1);
1343 ds_put_cstr(string
, s
);
1346 ofpbuf_uninit(&payload
);
1350 ofp_print_port_status(struct ds
*string
, const struct ofp_header
*oh
)
1352 struct ofputil_port_status ps
;
1355 error
= ofputil_decode_port_status(oh
, &ps
);
1357 ofp_print_error(string
, error
);
1361 if (ps
.reason
== OFPPR_ADD
) {
1362 ds_put_format(string
, " ADD:");
1363 } else if (ps
.reason
== OFPPR_DELETE
) {
1364 ds_put_format(string
, " DEL:");
1365 } else if (ps
.reason
== OFPPR_MODIFY
) {
1366 ds_put_format(string
, " MOD:");
1369 ofp_print_phy_port(string
, &ps
.desc
);
1373 ofp_print_ofpst_desc_reply(struct ds
*string
, const struct ofp_header
*oh
)
1375 const struct ofp_desc_stats
*ods
= ofpmsg_body(oh
);
1377 ds_put_char(string
, '\n');
1378 ds_put_format(string
, "Manufacturer: %.*s\n",
1379 (int) sizeof ods
->mfr_desc
, ods
->mfr_desc
);
1380 ds_put_format(string
, "Hardware: %.*s\n",
1381 (int) sizeof ods
->hw_desc
, ods
->hw_desc
);
1382 ds_put_format(string
, "Software: %.*s\n",
1383 (int) sizeof ods
->sw_desc
, ods
->sw_desc
);
1384 ds_put_format(string
, "Serial Num: %.*s\n",
1385 (int) sizeof ods
->serial_num
, ods
->serial_num
);
1386 ds_put_format(string
, "DP Description: %.*s\n",
1387 (int) sizeof ods
->dp_desc
, ods
->dp_desc
);
1391 ofp_print_flow_stats_request(struct ds
*string
, const struct ofp_header
*oh
)
1393 struct ofputil_flow_stats_request fsr
;
1396 error
= ofputil_decode_flow_stats_request(&fsr
, oh
);
1398 ofp_print_error(string
, error
);
1402 if (fsr
.table_id
!= 0xff) {
1403 ds_put_format(string
, " table=%"PRIu8
, fsr
.table_id
);
1406 if (fsr
.out_port
!= OFPP_ANY
) {
1407 ds_put_cstr(string
, " out_port=");
1408 ofputil_format_port(fsr
.out_port
, string
);
1411 ds_put_char(string
, ' ');
1412 match_format(&fsr
.match
, string
, OFP_DEFAULT_PRIORITY
);
1416 ofp_print_flow_stats(struct ds
*string
, struct ofputil_flow_stats
*fs
)
1418 ds_put_format(string
, " cookie=0x%"PRIx64
", duration=",
1419 ntohll(fs
->cookie
));
1421 ofp_print_duration(string
, fs
->duration_sec
, fs
->duration_nsec
);
1422 ds_put_format(string
, ", table=%"PRIu8
", ", fs
->table_id
);
1423 ds_put_format(string
, "n_packets=%"PRIu64
", ", fs
->packet_count
);
1424 ds_put_format(string
, "n_bytes=%"PRIu64
", ", fs
->byte_count
);
1425 if (fs
->idle_timeout
!= OFP_FLOW_PERMANENT
) {
1426 ds_put_format(string
, "idle_timeout=%"PRIu16
", ", fs
->idle_timeout
);
1428 if (fs
->hard_timeout
!= OFP_FLOW_PERMANENT
) {
1429 ds_put_format(string
, "hard_timeout=%"PRIu16
", ", fs
->hard_timeout
);
1432 ofp_print_flow_flags(string
, fs
->flags
);
1434 if (fs
->idle_age
>= 0) {
1435 ds_put_format(string
, "idle_age=%d, ", fs
->idle_age
);
1437 if (fs
->hard_age
>= 0 && fs
->hard_age
!= fs
->duration_sec
) {
1438 ds_put_format(string
, "hard_age=%d, ", fs
->hard_age
);
1441 match_format(&fs
->match
, string
, fs
->priority
);
1442 if (string
->string
[string
->length
- 1] != ' ') {
1443 ds_put_char(string
, ' ');
1446 ds_put_cstr(string
, "actions=");
1447 ofpacts_format(fs
->ofpacts
, fs
->ofpacts_len
, string
);
1451 ofp_print_flow_stats_reply(struct ds
*string
, const struct ofp_header
*oh
)
1453 struct ofpbuf ofpacts
;
1456 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1457 ofpbuf_init(&ofpacts
, 64);
1459 struct ofputil_flow_stats fs
;
1462 retval
= ofputil_decode_flow_stats_reply(&fs
, &b
, true, &ofpacts
);
1464 if (retval
!= EOF
) {
1465 ds_put_cstr(string
, " ***parse error***");
1469 ds_put_char(string
, '\n');
1470 ofp_print_flow_stats(string
, &fs
);
1472 ofpbuf_uninit(&ofpacts
);
1476 ofp_print_aggregate_stats_reply(struct ds
*string
, const struct ofp_header
*oh
)
1478 struct ofputil_aggregate_stats as
;
1481 error
= ofputil_decode_aggregate_stats_reply(&as
, oh
);
1483 ofp_print_error(string
, error
);
1487 ds_put_format(string
, " packet_count=%"PRIu64
, as
.packet_count
);
1488 ds_put_format(string
, " byte_count=%"PRIu64
, as
.byte_count
);
1489 ds_put_format(string
, " flow_count=%"PRIu32
, as
.flow_count
);
1493 print_port_stat(struct ds
*string
, const char *leader
, uint64_t stat
, int more
)
1495 ds_put_cstr(string
, leader
);
1496 if (stat
!= UINT64_MAX
) {
1497 ds_put_format(string
, "%"PRIu64
, stat
);
1499 ds_put_char(string
, '?');
1502 ds_put_cstr(string
, ", ");
1504 ds_put_cstr(string
, "\n");
1509 ofp_print_ofpst_port_request(struct ds
*string
, const struct ofp_header
*oh
)
1511 ofp_port_t ofp10_port
;
1514 error
= ofputil_decode_port_stats_request(oh
, &ofp10_port
);
1516 ofp_print_error(string
, error
);
1520 ds_put_cstr(string
, " port_no=");
1521 ofputil_format_port(ofp10_port
, string
);
1525 ofp_print_ofpst_port_reply(struct ds
*string
, const struct ofp_header
*oh
,
1530 ds_put_format(string
, " %"PRIuSIZE
" ports\n", ofputil_count_port_stats(oh
));
1531 if (verbosity
< 1) {
1535 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1537 struct ofputil_port_stats ps
;
1540 retval
= ofputil_decode_port_stats(&ps
, &b
);
1542 if (retval
!= EOF
) {
1543 ds_put_cstr(string
, " ***parse error***");
1548 ds_put_cstr(string
, " port ");
1549 if (ofp_to_u16(ps
.port_no
) < 10) {
1550 ds_put_char(string
, ' ');
1552 ofputil_format_port(ps
.port_no
, string
);
1554 ds_put_cstr(string
, ": rx ");
1555 print_port_stat(string
, "pkts=", ps
.stats
.rx_packets
, 1);
1556 print_port_stat(string
, "bytes=", ps
.stats
.rx_bytes
, 1);
1557 print_port_stat(string
, "drop=", ps
.stats
.rx_dropped
, 1);
1558 print_port_stat(string
, "errs=", ps
.stats
.rx_errors
, 1);
1559 print_port_stat(string
, "frame=", ps
.stats
.rx_frame_errors
, 1);
1560 print_port_stat(string
, "over=", ps
.stats
.rx_over_errors
, 1);
1561 print_port_stat(string
, "crc=", ps
.stats
.rx_crc_errors
, 0);
1563 ds_put_cstr(string
, " tx ");
1564 print_port_stat(string
, "pkts=", ps
.stats
.tx_packets
, 1);
1565 print_port_stat(string
, "bytes=", ps
.stats
.tx_bytes
, 1);
1566 print_port_stat(string
, "drop=", ps
.stats
.tx_dropped
, 1);
1567 print_port_stat(string
, "errs=", ps
.stats
.tx_errors
, 1);
1568 print_port_stat(string
, "coll=", ps
.stats
.collisions
, 0);
1570 if (ps
.duration_sec
!= UINT32_MAX
) {
1571 ds_put_cstr(string
, " duration=");
1572 ofp_print_duration(string
, ps
.duration_sec
, ps
.duration_nsec
);
1573 ds_put_char(string
, '\n');
1579 ofp_print_table_stats_reply(struct ds
*string
, const struct ofp_header
*oh
)
1583 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1584 ofpraw_pull_assert(&b
);
1587 struct ofputil_table_features features
;
1588 struct ofputil_table_stats stats
;
1591 retval
= ofputil_decode_table_stats_reply(&b
, &stats
, &features
);
1593 if (retval
!= EOF
) {
1594 ofp_print_error(string
, retval
);
1599 ofp_print_table_features(string
, &features
, &stats
);
1604 ofp_print_queue_name(struct ds
*string
, uint32_t queue_id
)
1606 if (queue_id
== OFPQ_ALL
) {
1607 ds_put_cstr(string
, "ALL");
1609 ds_put_format(string
, "%"PRIu32
, queue_id
);
1614 ofp_print_ofpst_queue_request(struct ds
*string
, const struct ofp_header
*oh
)
1616 struct ofputil_queue_stats_request oqsr
;
1619 error
= ofputil_decode_queue_stats_request(oh
, &oqsr
);
1621 ds_put_format(string
, "***decode error: %s***\n", ofperr_get_name(error
));
1625 ds_put_cstr(string
, "port=");
1626 ofputil_format_port(oqsr
.port_no
, string
);
1628 ds_put_cstr(string
, " queue=");
1629 ofp_print_queue_name(string
, oqsr
.queue_id
);
1633 ofp_print_ofpst_queue_reply(struct ds
*string
, const struct ofp_header
*oh
,
1638 ds_put_format(string
, " %"PRIuSIZE
" queues\n", ofputil_count_queue_stats(oh
));
1639 if (verbosity
< 1) {
1643 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1645 struct ofputil_queue_stats qs
;
1648 retval
= ofputil_decode_queue_stats(&qs
, &b
);
1650 if (retval
!= EOF
) {
1651 ds_put_cstr(string
, " ***parse error***");
1656 ds_put_cstr(string
, " port ");
1657 ofputil_format_port(qs
.port_no
, string
);
1658 ds_put_cstr(string
, " queue ");
1659 ofp_print_queue_name(string
, qs
.queue_id
);
1660 ds_put_cstr(string
, ": ");
1662 print_port_stat(string
, "bytes=", qs
.tx_bytes
, 1);
1663 print_port_stat(string
, "pkts=", qs
.tx_packets
, 1);
1664 print_port_stat(string
, "errors=", qs
.tx_errors
, 1);
1666 ds_put_cstr(string
, "duration=");
1667 if (qs
.duration_sec
!= UINT32_MAX
) {
1668 ofp_print_duration(string
, qs
.duration_sec
, qs
.duration_nsec
);
1670 ds_put_char(string
, '?');
1672 ds_put_char(string
, '\n');
1677 ofp_print_ofpst_port_desc_request(struct ds
*string
,
1678 const struct ofp_header
*oh
)
1683 error
= ofputil_decode_port_desc_stats_request(oh
, &port
);
1685 ofp_print_error(string
, error
);
1689 ds_put_cstr(string
, " port=");
1690 ofputil_format_port(port
, string
);
1694 ofp_print_ofpst_port_desc_reply(struct ds
*string
,
1695 const struct ofp_header
*oh
)
1699 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1700 ofpraw_pull_assert(&b
);
1701 ds_put_char(string
, '\n');
1702 ofp_print_phy_ports(string
, oh
->version
, &b
);
1706 ofp_print_stats(struct ds
*string
, const struct ofp_header
*oh
)
1708 uint16_t flags
= ofpmp_flags(oh
);
1711 ds_put_cstr(string
, " flags=");
1712 if ((!ofpmsg_is_stat_request(oh
) || oh
->version
>= OFP13_VERSION
)
1713 && (flags
& OFPSF_REPLY_MORE
)) {
1714 ds_put_cstr(string
, "[more]");
1715 flags
&= ~OFPSF_REPLY_MORE
;
1718 ds_put_format(string
, "[***unknown flags 0x%04"PRIx16
"***]",
1725 ofp_print_echo(struct ds
*string
, const struct ofp_header
*oh
, int verbosity
)
1727 size_t len
= ntohs(oh
->length
);
1729 ds_put_format(string
, " %"PRIuSIZE
" bytes of payload\n", len
- sizeof *oh
);
1730 if (verbosity
> 1) {
1731 ds_put_hex_dump(string
, oh
+ 1, len
- sizeof *oh
, 0, true);
1736 ofp_print_role_generic(struct ds
*string
, enum ofp12_controller_role role
,
1737 uint64_t generation_id
)
1739 ds_put_cstr(string
, " role=");
1742 case OFPCR12_ROLE_NOCHANGE
:
1743 ds_put_cstr(string
, "nochange");
1745 case OFPCR12_ROLE_EQUAL
:
1746 ds_put_cstr(string
, "equal"); /* OF 1.2 wording */
1748 case OFPCR12_ROLE_MASTER
:
1749 ds_put_cstr(string
, "master");
1751 case OFPCR12_ROLE_SLAVE
:
1752 ds_put_cstr(string
, "slave");
1758 if (generation_id
!= UINT64_MAX
) {
1759 ds_put_format(string
, " generation_id=%"PRIu64
, generation_id
);
1764 ofp_print_role_message(struct ds
*string
, const struct ofp_header
*oh
)
1766 struct ofputil_role_request rr
;
1769 error
= ofputil_decode_role_message(oh
, &rr
);
1771 ofp_print_error(string
, error
);
1775 ofp_print_role_generic(string
, rr
.role
, rr
.have_generation_id
? rr
.generation_id
: UINT64_MAX
);
1779 ofp_print_role_status_message(struct ds
*string
, const struct ofp_header
*oh
)
1781 struct ofputil_role_status rs
;
1784 error
= ofputil_decode_role_status(oh
, &rs
);
1786 ofp_print_error(string
, error
);
1790 ofp_print_role_generic(string
, rs
.role
, rs
.generation_id
);
1792 ds_put_cstr(string
, " reason=");
1794 switch (rs
.reason
) {
1795 case OFPCRR_MASTER_REQUEST
:
1796 ds_put_cstr(string
, "master_request");
1799 ds_put_cstr(string
, "configuration_changed");
1801 case OFPCRR_EXPERIMENTER
:
1802 ds_put_cstr(string
, "experimenter_data_changed");
1810 ofp_print_nxt_flow_mod_table_id(struct ds
*string
,
1811 const struct nx_flow_mod_table_id
*nfmti
)
1813 ds_put_format(string
, " %s", nfmti
->set
? "enable" : "disable");
1817 ofp_print_nxt_set_flow_format(struct ds
*string
,
1818 const struct nx_set_flow_format
*nsff
)
1820 uint32_t format
= ntohl(nsff
->format
);
1822 ds_put_cstr(string
, " format=");
1823 if (ofputil_nx_flow_format_is_valid(format
)) {
1824 ds_put_cstr(string
, ofputil_nx_flow_format_to_string(format
));
1826 ds_put_format(string
, "%"PRIu32
, format
);
1831 ofp_print_nxt_set_packet_in_format(struct ds
*string
,
1832 const struct nx_set_packet_in_format
*nspf
)
1834 uint32_t format
= ntohl(nspf
->format
);
1836 ds_put_cstr(string
, " format=");
1837 if (ofputil_packet_in_format_is_valid(format
)) {
1838 ds_put_cstr(string
, ofputil_packet_in_format_to_string(format
));
1840 ds_put_format(string
, "%"PRIu32
, format
);
1844 /* Returns a string form of 'reason'. The return value is either a statically
1845 * allocated constant string or the 'bufsize'-byte buffer 'reasonbuf'.
1846 * 'bufsize' should be at least OFP_PORT_REASON_BUFSIZE. */
1847 #define OFP_PORT_REASON_BUFSIZE (INT_STRLEN(int) + 1)
1849 ofp_port_reason_to_string(enum ofp_port_reason reason
,
1850 char *reasonbuf
, size_t bufsize
)
1863 snprintf(reasonbuf
, bufsize
, "%d", (int) reason
);
1869 ofp_print_nxt_set_async_config(struct ds
*string
,
1870 const struct nx_async_config
*nac
)
1874 for (i
= 0; i
< 2; i
++) {
1877 ds_put_format(string
, "\n %s:\n", i
== 0 ? "master" : "slave");
1879 ds_put_cstr(string
, " PACKET_IN:");
1880 for (j
= 0; j
< 32; j
++) {
1881 if (nac
->packet_in_mask
[i
] & htonl(1u << j
)) {
1882 char reasonbuf
[OFPUTIL_PACKET_IN_REASON_BUFSIZE
];
1885 reason
= ofputil_packet_in_reason_to_string(j
, reasonbuf
,
1887 ds_put_format(string
, " %s", reason
);
1890 if (!nac
->packet_in_mask
[i
]) {
1891 ds_put_cstr(string
, " (off)");
1893 ds_put_char(string
, '\n');
1895 ds_put_cstr(string
, " PORT_STATUS:");
1896 for (j
= 0; j
< 32; j
++) {
1897 if (nac
->port_status_mask
[i
] & htonl(1u << j
)) {
1898 char reasonbuf
[OFP_PORT_REASON_BUFSIZE
];
1901 reason
= ofp_port_reason_to_string(j
, reasonbuf
,
1903 ds_put_format(string
, " %s", reason
);
1906 if (!nac
->port_status_mask
[i
]) {
1907 ds_put_cstr(string
, " (off)");
1909 ds_put_char(string
, '\n');
1911 ds_put_cstr(string
, " FLOW_REMOVED:");
1912 for (j
= 0; j
< 32; j
++) {
1913 if (nac
->flow_removed_mask
[i
] & htonl(1u << j
)) {
1914 char reasonbuf
[OFP_FLOW_REMOVED_REASON_BUFSIZE
];
1917 reason
= ofp_flow_removed_reason_to_string(j
, reasonbuf
,
1919 ds_put_format(string
, " %s", reason
);
1922 if (!nac
->flow_removed_mask
[i
]) {
1923 ds_put_cstr(string
, " (off)");
1925 ds_put_char(string
, '\n');
1930 ofp_print_nxt_set_controller_id(struct ds
*string
,
1931 const struct nx_controller_id
*nci
)
1933 ds_put_format(string
, " id=%"PRIu16
, ntohs(nci
->controller_id
));
1937 ofp_print_nxt_flow_monitor_cancel(struct ds
*string
,
1938 const struct ofp_header
*oh
)
1940 ds_put_format(string
, " id=%"PRIu32
,
1941 ofputil_decode_flow_monitor_cancel(oh
));
1945 nx_flow_monitor_flags_to_name(uint32_t bit
)
1947 enum nx_flow_monitor_flags fmf
= bit
;
1950 case NXFMF_INITIAL
: return "initial";
1951 case NXFMF_ADD
: return "add";
1952 case NXFMF_DELETE
: return "delete";
1953 case NXFMF_MODIFY
: return "modify";
1954 case NXFMF_ACTIONS
: return "actions";
1955 case NXFMF_OWN
: return "own";
1962 ofp_print_nxst_flow_monitor_request(struct ds
*string
,
1963 const struct ofp_header
*oh
)
1967 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
1969 struct ofputil_flow_monitor_request request
;
1972 retval
= ofputil_decode_flow_monitor_request(&request
, &b
);
1974 if (retval
!= EOF
) {
1975 ofp_print_error(string
, retval
);
1980 ds_put_format(string
, "\n id=%"PRIu32
" flags=", request
.id
);
1981 ofp_print_bit_names(string
, request
.flags
,
1982 nx_flow_monitor_flags_to_name
, ',');
1984 if (request
.out_port
!= OFPP_NONE
) {
1985 ds_put_cstr(string
, " out_port=");
1986 ofputil_format_port(request
.out_port
, string
);
1989 if (request
.table_id
!= 0xff) {
1990 ds_put_format(string
, " table=%"PRIu8
, request
.table_id
);
1993 ds_put_char(string
, ' ');
1994 match_format(&request
.match
, string
, OFP_DEFAULT_PRIORITY
);
1995 ds_chomp(string
, ' ');
2000 ofp_print_nxst_flow_monitor_reply(struct ds
*string
,
2001 const struct ofp_header
*oh
)
2003 uint64_t ofpacts_stub
[1024 / 8];
2004 struct ofpbuf ofpacts
;
2007 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
2008 ofpbuf_use_stub(&ofpacts
, ofpacts_stub
, sizeof ofpacts_stub
);
2010 char reasonbuf
[OFP_FLOW_REMOVED_REASON_BUFSIZE
];
2011 struct ofputil_flow_update update
;
2015 update
.match
= &match
;
2016 retval
= ofputil_decode_flow_update(&update
, &b
, &ofpacts
);
2018 if (retval
!= EOF
) {
2019 ofp_print_error(string
, retval
);
2021 ofpbuf_uninit(&ofpacts
);
2025 ds_put_cstr(string
, "\n event=");
2026 switch (update
.event
) {
2028 ds_put_cstr(string
, "ADDED");
2032 ds_put_format(string
, "DELETED reason=%s",
2033 ofp_flow_removed_reason_to_string(update
.reason
,
2038 case NXFME_MODIFIED
:
2039 ds_put_cstr(string
, "MODIFIED");
2043 ds_put_format(string
, "ABBREV xid=0x%"PRIx32
, ntohl(update
.xid
));
2047 ds_put_format(string
, " table=%"PRIu8
, update
.table_id
);
2048 if (update
.idle_timeout
!= OFP_FLOW_PERMANENT
) {
2049 ds_put_format(string
, " idle_timeout=%"PRIu16
,
2050 update
.idle_timeout
);
2052 if (update
.hard_timeout
!= OFP_FLOW_PERMANENT
) {
2053 ds_put_format(string
, " hard_timeout=%"PRIu16
,
2054 update
.hard_timeout
);
2056 ds_put_format(string
, " cookie=%#"PRIx64
, ntohll(update
.cookie
));
2058 ds_put_char(string
, ' ');
2059 match_format(update
.match
, string
, OFP_DEFAULT_PRIORITY
);
2061 if (update
.ofpacts_len
) {
2062 if (string
->string
[string
->length
- 1] != ' ') {
2063 ds_put_char(string
, ' ');
2065 ds_put_cstr(string
, "actions=");
2066 ofpacts_format(update
.ofpacts
, update
.ofpacts_len
, string
);
2072 ofp_print_version(const struct ofp_header
*oh
,
2075 switch (oh
->version
) {
2079 ds_put_cstr(string
, " (OF1.1)");
2082 ds_put_cstr(string
, " (OF1.2)");
2085 ds_put_cstr(string
, " (OF1.3)");
2088 ds_put_cstr(string
, " (OF1.4)");
2091 ds_put_cstr(string
, " (OF1.5)");
2094 ds_put_format(string
, " (OF 0x%02"PRIx8
")", oh
->version
);
2097 ds_put_format(string
, " (xid=0x%"PRIx32
"):", ntohl(oh
->xid
));
2101 ofp_header_to_string__(const struct ofp_header
*oh
, enum ofpraw raw
,
2104 ds_put_cstr(string
, ofpraw_get_name(raw
));
2105 ofp_print_version(oh
, string
);
2109 ofp_print_group(struct ds
*s
, uint32_t group_id
, uint8_t type
,
2110 struct list
*p_buckets
)
2112 static const char *type_str
[] = { "all", "select", "indirect",
2114 struct ofputil_bucket
*bucket
;
2116 ds_put_format(s
, "group_id=%"PRIu32
",type=%s",
2117 group_id
, type_str
[type
> 4 ? 4 : type
]);
2122 LIST_FOR_EACH (bucket
, list_node
, p_buckets
) {
2123 ds_put_cstr(s
, ",bucket=");
2125 if (bucket
->weight
!= 1) {
2126 ds_put_format(s
, "weight:%"PRIu16
",", bucket
->weight
);
2128 if (bucket
->watch_port
!= OFPP_NONE
) {
2129 ds_put_format(s
, "watch_port:%"PRIu32
",", bucket
->watch_port
);
2131 if (bucket
->watch_group
!= OFPG11_ANY
) {
2132 ds_put_format(s
, "watch_group:%"PRIu32
",", bucket
->watch_group
);
2135 ds_put_cstr(s
, "actions=");
2136 ofpacts_format(bucket
->ofpacts
, bucket
->ofpacts_len
, s
);
2141 ofp_print_ofpst_group_desc_request(struct ds
*string
,
2142 const struct ofp_header
*oh
)
2144 uint32_t group_id
= ofputil_decode_group_desc_request(oh
);
2145 ds_put_cstr(string
, " group_id=");
2146 ofputil_format_group(group_id
, string
);
2150 ofp_print_group_desc(struct ds
*s
, const struct ofp_header
*oh
)
2154 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
2156 struct ofputil_group_desc gd
;
2159 retval
= ofputil_decode_group_desc_reply(&gd
, &b
, oh
->version
);
2161 if (retval
!= EOF
) {
2162 ds_put_cstr(s
, " ***parse error***");
2167 ds_put_char(s
, '\n');
2168 ds_put_char(s
, ' ');
2169 ofp_print_group(s
, gd
.group_id
, gd
.type
, &gd
.buckets
);
2170 ofputil_bucket_list_destroy(&gd
.buckets
);
2175 ofp_print_ofpst_group_request(struct ds
*string
, const struct ofp_header
*oh
)
2180 error
= ofputil_decode_group_stats_request(oh
, &group_id
);
2182 ofp_print_error(string
, error
);
2186 ds_put_cstr(string
, " group_id=");
2187 ofputil_format_group(group_id
, string
);
2191 ofp_print_group_stats(struct ds
*s
, const struct ofp_header
*oh
)
2196 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
2199 struct ofputil_group_stats gs
;
2202 retval
= ofputil_decode_group_stats_reply(&b
, &gs
);
2204 if (retval
!= EOF
) {
2205 ds_put_cstr(s
, " ***parse error***");
2210 ds_put_char(s
, '\n');
2212 ds_put_char(s
, ' ');
2213 ds_put_format(s
, "group_id=%"PRIu32
",", gs
.group_id
);
2215 if (gs
.duration_sec
!= UINT32_MAX
) {
2216 ds_put_cstr(s
, "duration=");
2217 ofp_print_duration(s
, gs
.duration_sec
, gs
.duration_nsec
);
2218 ds_put_char(s
, ',');
2220 ds_put_format(s
, "ref_count=%"PRIu32
",", gs
.ref_count
);
2221 ds_put_format(s
, "packet_count=%"PRIu64
",", gs
.packet_count
);
2222 ds_put_format(s
, "byte_count=%"PRIu64
"", gs
.byte_count
);
2224 for (bucket_i
= 0; bucket_i
< gs
.n_buckets
; bucket_i
++) {
2225 if (gs
.bucket_stats
[bucket_i
].packet_count
!= UINT64_MAX
) {
2226 ds_put_format(s
, ",bucket%"PRIu32
":", bucket_i
);
2227 ds_put_format(s
, "packet_count=%"PRIu64
",", gs
.bucket_stats
[bucket_i
].packet_count
);
2228 ds_put_format(s
, "byte_count=%"PRIu64
"", gs
.bucket_stats
[bucket_i
].byte_count
);
2232 free(gs
.bucket_stats
);
2237 group_type_to_string(enum ofp11_group_type type
)
2240 case OFPGT11_ALL
: return "all";
2241 case OFPGT11_SELECT
: return "select";
2242 case OFPGT11_INDIRECT
: return "indirect";
2243 case OFPGT11_FF
: return "fast failover";
2244 default: OVS_NOT_REACHED();
2249 ofp_print_group_features(struct ds
*string
, const struct ofp_header
*oh
)
2251 struct ofputil_group_features features
;
2254 ofputil_decode_group_features_reply(oh
, &features
);
2256 ds_put_format(string
, "\n Group table:\n");
2257 ds_put_format(string
, " Types: 0x%"PRIx32
"\n", features
.types
);
2258 ds_put_format(string
, " Capabilities: 0x%"PRIx32
"\n",
2259 features
.capabilities
);
2261 for (i
= 0; i
< OFPGT12_N_TYPES
; i
++) {
2262 if (features
.types
& (1u << i
)) {
2263 ds_put_format(string
, " %s group:\n", group_type_to_string(i
));
2264 ds_put_format(string
, " max_groups=%#"PRIx32
"\n",
2265 features
.max_groups
[i
]);
2266 ds_put_format(string
, " actions: ");
2267 ofpact_bitmap_format(features
.ofpacts
[i
], string
);
2268 ds_put_char(string
, '\n');
2274 ofp_print_group_mod(struct ds
*s
, const struct ofp_header
*oh
)
2276 struct ofputil_group_mod gm
;
2279 error
= ofputil_decode_group_mod(oh
, &gm
);
2281 ofp_print_error(s
, error
);
2285 ds_put_char(s
, '\n');
2287 ds_put_char(s
, ' ');
2288 switch (gm
.command
) {
2290 ds_put_cstr(s
, "ADD");
2293 case OFPGC11_MODIFY
:
2294 ds_put_cstr(s
, "MOD");
2297 case OFPGC11_DELETE
:
2298 ds_put_cstr(s
, "DEL");
2302 ds_put_format(s
, "cmd:%"PRIu16
"", gm
.command
);
2304 ds_put_char(s
, ' ');
2306 ofp_print_group(s
, gm
.group_id
, gm
.type
, &gm
.buckets
);
2307 ofputil_bucket_list_destroy(&gm
.buckets
);
2311 print_table_action_features(struct ds
*s
,
2312 const struct ofputil_table_action_features
*taf
)
2315 ds_put_cstr(s
, " actions: ");
2316 ofpact_bitmap_format(taf
->ofpacts
, s
);
2317 ds_put_char(s
, '\n');
2320 if (!bitmap_is_all_zeros(taf
->set_fields
.bm
, MFF_N_IDS
)) {
2323 ds_put_cstr(s
, " supported on Set-Field:");
2324 BITMAP_FOR_EACH_1 (i
, MFF_N_IDS
, taf
->set_fields
.bm
) {
2325 ds_put_format(s
, " %s", mf_from_id(i
)->name
);
2327 ds_put_char(s
, '\n');
2332 table_action_features_equal(const struct ofputil_table_action_features
*a
,
2333 const struct ofputil_table_action_features
*b
)
2335 return (a
->ofpacts
== b
->ofpacts
2336 && bitmap_equal(a
->set_fields
.bm
, b
->set_fields
.bm
, MFF_N_IDS
));
2340 table_action_features_empty(const struct ofputil_table_action_features
*taf
)
2342 return !taf
->ofpacts
&& bitmap_is_all_zeros(taf
->set_fields
.bm
, MFF_N_IDS
);
2346 print_table_instruction_features(
2347 struct ds
*s
, const struct ofputil_table_instruction_features
*tif
)
2351 if (!bitmap_is_all_zeros(tif
->next
, 255)) {
2352 ds_put_cstr(s
, " next tables: ");
2353 for (start
= bitmap_scan(tif
->next
, 1, 0, 255); start
< 255;
2354 start
= bitmap_scan(tif
->next
, 1, end
, 255)) {
2355 end
= bitmap_scan(tif
->next
, 0, start
+ 1, 255);
2356 if (end
== start
+ 1) {
2357 ds_put_format(s
, "%d,", start
);
2359 ds_put_format(s
, "%d-%d,", start
, end
- 1);
2363 if (ds_last(s
) == ' ') {
2364 ds_put_cstr(s
, "none");
2366 ds_put_char(s
, '\n');
2369 if (tif
->instructions
) {
2370 ds_put_cstr(s
, " instructions: ");
2373 for (i
= 0; i
< 32; i
++) {
2374 if (tif
->instructions
& (1u << i
)) {
2375 ds_put_format(s
, "%s,", ovs_instruction_name_from_type(i
));
2379 ds_put_char(s
, '\n');
2382 if (!table_action_features_equal(&tif
->write
, &tif
->apply
)) {
2383 ds_put_cstr(s
, " Write-Actions features:\n");
2384 print_table_action_features(s
, &tif
->write
);
2385 ds_put_cstr(s
, " Apply-Actions features:\n");
2386 print_table_action_features(s
, &tif
->apply
);
2387 } else if (tif
->write
.ofpacts
2388 || !bitmap_is_all_zeros(tif
->write
.set_fields
.bm
, MFF_N_IDS
)) {
2389 ds_put_cstr(s
, " Write-Actions and Apply-Actions features:\n");
2390 print_table_action_features(s
, &tif
->write
);
2395 table_instruction_features_equal(
2396 const struct ofputil_table_instruction_features
*a
,
2397 const struct ofputil_table_instruction_features
*b
)
2399 return (bitmap_equal(a
->next
, b
->next
, 255)
2400 && a
->instructions
== b
->instructions
2401 && table_action_features_equal(&a
->write
, &b
->write
)
2402 && table_action_features_equal(&a
->apply
, &b
->apply
));
2406 table_instruction_features_empty(
2407 const struct ofputil_table_instruction_features
*tif
)
2409 return (bitmap_is_all_zeros(tif
->next
, 255)
2410 && !tif
->instructions
2411 && table_action_features_empty(&tif
->write
)
2412 && table_action_features_empty(&tif
->apply
));
2416 ofp_print_table_features(struct ds
*s
,
2417 const struct ofputil_table_features
*features
,
2418 const struct ofputil_table_stats
*stats
)
2422 ds_put_format(s
, "\n table %"PRIu8
, features
->table_id
);
2423 if (features
->name
[0]) {
2424 ds_put_format(s
, " (\"%s\")", features
->name
);
2426 ds_put_cstr(s
, ":\n");
2428 ds_put_format(s
, " active=%"PRIu32
", ", stats
->active_count
);
2429 ds_put_format(s
, "lookup=%"PRIu64
", ", stats
->lookup_count
);
2430 ds_put_format(s
, "matched=%"PRIu64
"\n", stats
->matched_count
);
2432 if (features
->metadata_match
|| features
->metadata_match
) {
2433 ds_put_format(s
, " metadata: match=%#"PRIx64
" write=%#"PRIx64
"\n",
2434 ntohll(features
->metadata_match
),
2435 ntohll(features
->metadata_write
));
2438 if (features
->miss_config
!= OFPUTIL_TABLE_MISS_DEFAULT
) {
2439 ds_put_cstr(s
, " config=");
2440 ofp_print_table_miss_config(s
, features
->miss_config
);
2443 if (features
->max_entries
) {
2444 ds_put_format(s
, " max_entries=%"PRIu32
"\n", features
->max_entries
);
2447 if (!table_instruction_features_equal(&features
->nonmiss
,
2449 ds_put_cstr(s
, " instructions (other than table miss):\n");
2450 print_table_instruction_features(s
, &features
->nonmiss
);
2451 ds_put_cstr(s
, " instructions (table miss):\n");
2452 print_table_instruction_features(s
, &features
->miss
);
2453 } else if (!table_instruction_features_empty(&features
->nonmiss
)) {
2454 ds_put_cstr(s
, " instructions (table miss and others):\n");
2455 print_table_instruction_features(s
, &features
->nonmiss
);
2458 if (!bitmap_is_all_zeros(features
->match
.bm
, MFF_N_IDS
)){
2459 ds_put_cstr(s
, " matching:\n");
2460 BITMAP_FOR_EACH_1 (i
, MFF_N_IDS
, features
->match
.bm
) {
2461 const struct mf_field
*f
= mf_from_id(i
);
2462 bool mask
= bitmap_is_set(features
->mask
.bm
, i
);
2463 bool wildcard
= bitmap_is_set(features
->wildcard
.bm
, i
);
2465 ds_put_format(s
, " %s: %s\n",
2467 (mask
? "arbitrary mask"
2468 : wildcard
? "exact match or wildcard"
2469 : "must exact match"));
2475 ofp_print_table_features_reply(struct ds
*s
, const struct ofp_header
*oh
)
2479 ofpbuf_use_const(&b
, oh
, ntohs(oh
->length
));
2482 struct ofputil_table_features tf
;
2485 retval
= ofputil_decode_table_features(&b
, &tf
, true);
2487 if (retval
!= EOF
) {
2488 ofp_print_error(s
, retval
);
2492 ofp_print_table_features(s
, &tf
, NULL
);
2497 bundle_flags_to_name(uint32_t bit
)
2510 ofp_print_bundle_ctrl(struct ds
*s
, const struct ofp_header
*oh
)
2513 struct ofputil_bundle_ctrl_msg bctrl
;
2515 error
= ofputil_decode_bundle_ctrl(oh
, &bctrl
);
2517 ofp_print_error(s
, error
);
2521 ds_put_char(s
, '\n');
2523 ds_put_format(s
, " bundle_id=%#"PRIx32
" type=", bctrl
.bundle_id
);
2524 switch (bctrl
.type
) {
2525 case OFPBCT_OPEN_REQUEST
:
2526 ds_put_cstr(s
, "OPEN_REQUEST");
2528 case OFPBCT_OPEN_REPLY
:
2529 ds_put_cstr(s
, "OPEN_REPLY");
2531 case OFPBCT_CLOSE_REQUEST
:
2532 ds_put_cstr(s
, "CLOSE_REQUEST");
2534 case OFPBCT_CLOSE_REPLY
:
2535 ds_put_cstr(s
, "CLOSE_REPLY");
2537 case OFPBCT_COMMIT_REQUEST
:
2538 ds_put_cstr(s
, "COMMIT_REQUEST");
2540 case OFPBCT_COMMIT_REPLY
:
2541 ds_put_cstr(s
, "COMMIT_REPLY");
2543 case OFPBCT_DISCARD_REQUEST
:
2544 ds_put_cstr(s
, "DISCARD_REQUEST");
2546 case OFPBCT_DISCARD_REPLY
:
2547 ds_put_cstr(s
, "DISCARD_REPLY");
2551 ds_put_cstr(s
, " flags=");
2552 ofp_print_bit_names(s
, bctrl
.flags
, bundle_flags_to_name
, ' ');
2556 ofp_print_bundle_add(struct ds
*s
, const struct ofp_header
*oh
, int verbosity
)
2559 struct ofputil_bundle_add_msg badd
;
2562 error
= ofputil_decode_bundle_add(oh
, &badd
);
2564 ofp_print_error(s
, error
);
2568 ds_put_char(s
, '\n');
2569 ds_put_format(s
, " bundle_id=%#"PRIx32
, badd
.bundle_id
);
2570 ds_put_cstr(s
, " flags=");
2571 ofp_print_bit_names(s
, badd
.flags
, bundle_flags_to_name
, ' ');
2573 ds_put_char(s
, '\n');
2574 msg
= ofp_to_string(badd
.msg
, ntohs(badd
.msg
->length
), verbosity
);
2576 ds_put_cstr(s
, msg
);
2581 ofp_to_string__(const struct ofp_header
*oh
, enum ofpraw raw
,
2582 struct ds
*string
, int verbosity
)
2584 const void *msg
= oh
;
2586 ofp_header_to_string__(oh
, raw
, string
);
2587 switch (ofptype_from_ofpraw(raw
)) {
2589 case OFPTYPE_GROUP_STATS_REQUEST
:
2590 ofp_print_stats(string
, oh
);
2591 ofp_print_ofpst_group_request(string
, oh
);
2594 case OFPTYPE_GROUP_STATS_REPLY
:
2595 ofp_print_group_stats(string
, oh
);
2598 case OFPTYPE_GROUP_DESC_STATS_REQUEST
:
2599 ofp_print_stats(string
, oh
);
2600 ofp_print_ofpst_group_desc_request(string
, oh
);
2603 case OFPTYPE_GROUP_DESC_STATS_REPLY
:
2604 ofp_print_group_desc(string
, oh
);
2607 case OFPTYPE_GROUP_FEATURES_STATS_REQUEST
:
2608 ofp_print_stats(string
, oh
);
2611 case OFPTYPE_GROUP_FEATURES_STATS_REPLY
:
2612 ofp_print_group_features(string
, oh
);
2615 case OFPTYPE_GROUP_MOD
:
2616 ofp_print_group_mod(string
, oh
);
2619 case OFPTYPE_TABLE_FEATURES_STATS_REQUEST
:
2620 case OFPTYPE_TABLE_FEATURES_STATS_REPLY
:
2621 ofp_print_table_features_reply(string
, oh
);
2625 ofp_print_hello(string
, oh
);
2629 ofp_print_error_msg(string
, oh
);
2632 case OFPTYPE_ECHO_REQUEST
:
2633 case OFPTYPE_ECHO_REPLY
:
2634 ofp_print_echo(string
, oh
, verbosity
);
2637 case OFPTYPE_FEATURES_REQUEST
:
2640 case OFPTYPE_FEATURES_REPLY
:
2641 ofp_print_switch_features(string
, oh
);
2644 case OFPTYPE_GET_CONFIG_REQUEST
:
2647 case OFPTYPE_GET_CONFIG_REPLY
:
2648 case OFPTYPE_SET_CONFIG
:
2649 ofp_print_switch_config(string
, ofpmsg_body(oh
));
2652 case OFPTYPE_PACKET_IN
:
2653 ofp_print_packet_in(string
, oh
, verbosity
);
2656 case OFPTYPE_FLOW_REMOVED
:
2657 ofp_print_flow_removed(string
, oh
);
2660 case OFPTYPE_PORT_STATUS
:
2661 ofp_print_port_status(string
, oh
);
2664 case OFPTYPE_PACKET_OUT
:
2665 ofp_print_packet_out(string
, oh
, verbosity
);
2668 case OFPTYPE_FLOW_MOD
:
2669 ofp_print_flow_mod(string
, oh
, verbosity
);
2672 case OFPTYPE_PORT_MOD
:
2673 ofp_print_port_mod(string
, oh
);
2676 case OFPTYPE_TABLE_MOD
:
2677 ofp_print_table_mod(string
, oh
);
2680 case OFPTYPE_METER_MOD
:
2681 ofp_print_meter_mod(string
, oh
);
2684 case OFPTYPE_BARRIER_REQUEST
:
2685 case OFPTYPE_BARRIER_REPLY
:
2688 case OFPTYPE_QUEUE_GET_CONFIG_REQUEST
:
2689 ofp_print_queue_get_config_request(string
, oh
);
2692 case OFPTYPE_QUEUE_GET_CONFIG_REPLY
:
2693 ofp_print_queue_get_config_reply(string
, oh
);
2696 case OFPTYPE_ROLE_REQUEST
:
2697 case OFPTYPE_ROLE_REPLY
:
2698 ofp_print_role_message(string
, oh
);
2700 case OFPTYPE_ROLE_STATUS
:
2701 ofp_print_role_status_message(string
, oh
);
2704 case OFPTYPE_METER_STATS_REQUEST
:
2705 case OFPTYPE_METER_CONFIG_STATS_REQUEST
:
2706 ofp_print_stats(string
, oh
);
2707 ofp_print_meter_stats_request(string
, oh
);
2710 case OFPTYPE_METER_STATS_REPLY
:
2711 ofp_print_stats(string
, oh
);
2712 ofp_print_meter_stats_reply(string
, oh
);
2715 case OFPTYPE_METER_CONFIG_STATS_REPLY
:
2716 ofp_print_stats(string
, oh
);
2717 ofp_print_meter_config_reply(string
, oh
);
2720 case OFPTYPE_METER_FEATURES_STATS_REPLY
:
2721 ofp_print_stats(string
, oh
);
2722 ofp_print_meter_features_reply(string
, oh
);
2725 case OFPTYPE_DESC_STATS_REQUEST
:
2726 case OFPTYPE_METER_FEATURES_STATS_REQUEST
:
2727 ofp_print_stats(string
, oh
);
2730 case OFPTYPE_FLOW_STATS_REQUEST
:
2731 case OFPTYPE_AGGREGATE_STATS_REQUEST
:
2732 ofp_print_stats(string
, oh
);
2733 ofp_print_flow_stats_request(string
, oh
);
2736 case OFPTYPE_TABLE_STATS_REQUEST
:
2737 ofp_print_stats(string
, oh
);
2740 case OFPTYPE_PORT_STATS_REQUEST
:
2741 ofp_print_stats(string
, oh
);
2742 ofp_print_ofpst_port_request(string
, oh
);
2745 case OFPTYPE_QUEUE_STATS_REQUEST
:
2746 ofp_print_stats(string
, oh
);
2747 ofp_print_ofpst_queue_request(string
, oh
);
2750 case OFPTYPE_DESC_STATS_REPLY
:
2751 ofp_print_stats(string
, oh
);
2752 ofp_print_ofpst_desc_reply(string
, oh
);
2755 case OFPTYPE_FLOW_STATS_REPLY
:
2756 ofp_print_stats(string
, oh
);
2757 ofp_print_flow_stats_reply(string
, oh
);
2760 case OFPTYPE_QUEUE_STATS_REPLY
:
2761 ofp_print_stats(string
, oh
);
2762 ofp_print_ofpst_queue_reply(string
, oh
, verbosity
);
2765 case OFPTYPE_PORT_STATS_REPLY
:
2766 ofp_print_stats(string
, oh
);
2767 ofp_print_ofpst_port_reply(string
, oh
, verbosity
);
2770 case OFPTYPE_TABLE_STATS_REPLY
:
2771 ofp_print_stats(string
, oh
);
2772 ofp_print_table_stats_reply(string
, oh
);
2775 case OFPTYPE_AGGREGATE_STATS_REPLY
:
2776 ofp_print_stats(string
, oh
);
2777 ofp_print_aggregate_stats_reply(string
, oh
);
2780 case OFPTYPE_PORT_DESC_STATS_REQUEST
:
2781 ofp_print_stats(string
, oh
);
2782 ofp_print_ofpst_port_desc_request(string
, oh
);
2785 case OFPTYPE_PORT_DESC_STATS_REPLY
:
2786 ofp_print_stats(string
, oh
);
2787 ofp_print_ofpst_port_desc_reply(string
, oh
);
2790 case OFPTYPE_FLOW_MOD_TABLE_ID
:
2791 ofp_print_nxt_flow_mod_table_id(string
, ofpmsg_body(oh
));
2794 case OFPTYPE_SET_FLOW_FORMAT
:
2795 ofp_print_nxt_set_flow_format(string
, ofpmsg_body(oh
));
2798 case OFPTYPE_SET_PACKET_IN_FORMAT
:
2799 ofp_print_nxt_set_packet_in_format(string
, ofpmsg_body(oh
));
2802 case OFPTYPE_FLOW_AGE
:
2805 case OFPTYPE_SET_CONTROLLER_ID
:
2806 ofp_print_nxt_set_controller_id(string
, ofpmsg_body(oh
));
2809 case OFPTYPE_GET_ASYNC_REPLY
:
2810 case OFPTYPE_SET_ASYNC_CONFIG
:
2811 ofp_print_nxt_set_async_config(string
, ofpmsg_body(oh
));
2813 case OFPTYPE_GET_ASYNC_REQUEST
:
2815 case OFPTYPE_FLOW_MONITOR_CANCEL
:
2816 ofp_print_nxt_flow_monitor_cancel(string
, msg
);
2819 case OFPTYPE_FLOW_MONITOR_PAUSED
:
2820 case OFPTYPE_FLOW_MONITOR_RESUMED
:
2823 case OFPTYPE_FLOW_MONITOR_STATS_REQUEST
:
2824 ofp_print_nxst_flow_monitor_request(string
, msg
);
2827 case OFPTYPE_FLOW_MONITOR_STATS_REPLY
:
2828 ofp_print_nxst_flow_monitor_reply(string
, msg
);
2831 case OFPTYPE_BUNDLE_CONTROL
:
2832 ofp_print_bundle_ctrl(string
, msg
);
2835 case OFPTYPE_BUNDLE_ADD_MESSAGE
:
2836 ofp_print_bundle_add(string
, msg
, verbosity
);
2841 /* Composes and returns a string representing the OpenFlow packet of 'len'
2842 * bytes at 'oh' at the given 'verbosity' level. 0 is a minimal amount of
2843 * verbosity and higher numbers increase verbosity. The caller is responsible
2844 * for freeing the string. */
2846 ofp_to_string(const void *oh_
, size_t len
, int verbosity
)
2848 struct ds string
= DS_EMPTY_INITIALIZER
;
2849 const struct ofp_header
*oh
= oh_
;
2852 ds_put_cstr(&string
, "OpenFlow message is empty\n");
2853 } else if (len
< sizeof(struct ofp_header
)) {
2854 ds_put_format(&string
, "OpenFlow packet too short (only %"PRIuSIZE
" bytes):\n",
2856 } else if (ntohs(oh
->length
) > len
) {
2860 error
= ofpraw_decode_partial(&raw
, oh
, len
);
2862 ofp_header_to_string__(oh
, raw
, &string
);
2863 ds_put_char(&string
, '\n');
2866 ds_put_format(&string
,
2867 "(***truncated to %"PRIuSIZE
" bytes from %"PRIu16
"***)\n",
2868 len
, ntohs(oh
->length
));
2869 } else if (ntohs(oh
->length
) < len
) {
2870 ds_put_format(&string
,
2871 "(***only uses %"PRIu16
" bytes out of %"PRIuSIZE
"***)\n",
2872 ntohs(oh
->length
), len
);
2877 error
= ofpraw_decode(&raw
, oh
);
2879 ofp_to_string__(oh
, raw
, &string
, verbosity
);
2880 if (verbosity
>= 5) {
2881 if (ds_last(&string
) != '\n') {
2882 ds_put_char(&string
, '\n');
2884 ds_put_hex_dump(&string
, oh
, len
, 0, true);
2886 if (ds_last(&string
) != '\n') {
2887 ds_put_char(&string
, '\n');
2889 return ds_steal_cstr(&string
);
2892 ofp_print_error(&string
, error
);
2894 ds_put_hex_dump(&string
, oh
, len
, 0, true);
2895 return ds_steal_cstr(&string
);
2899 print_and_free(FILE *stream
, char *string
)
2901 fputs(string
, stream
);
2905 /* Pretty-print the OpenFlow packet of 'len' bytes at 'oh' to 'stream' at the
2906 * given 'verbosity' level. 0 is a minimal amount of verbosity and higher
2907 * numbers increase verbosity. */
2909 ofp_print(FILE *stream
, const void *oh
, size_t len
, int verbosity
)
2911 print_and_free(stream
, ofp_to_string(oh
, len
, verbosity
));
2914 /* Dumps the contents of the Ethernet frame in the 'len' bytes starting at
2915 * 'data' to 'stream'. */
2917 ofp_print_packet(FILE *stream
, const void *data
, size_t len
)
2919 print_and_free(stream
, ofp_packet_to_string(data
, len
));