From 15f1f1b63ab5514f8dfafa8f4c90ecee44693e1d Mon Sep 17 00:00:00 2001 From: Ben Pfaff Date: Thu, 23 Sep 2010 13:19:49 -0700 Subject: [PATCH] ofp-parse: Factor out duplicated code into new functions. --- lib/learning-switch.c | 40 ++------------------------ lib/ofp-parse.c | 65 ++++++++++++++++++++++++++++++++++++++++++- lib/ofp-parse.h | 3 ++ utilities/ovs-ofctl.c | 41 ++------------------------- 4 files changed, 72 insertions(+), 77 deletions(-) diff --git a/lib/learning-switch.c b/lib/learning-switch.c index 4e7645d7c..b20506b16 100644 --- a/lib/learning-switch.c +++ b/lib/learning-switch.c @@ -252,45 +252,9 @@ static void send_default_flows(struct lswitch *sw, struct rconn *rconn, FILE *default_flows) { - char line[1024]; + struct ofpbuf *b; - while (fgets(line, sizeof line, default_flows)) { - struct ofpbuf *b; - struct ofp_flow_mod *ofm; - uint16_t priority, idle_timeout, hard_timeout; - uint64_t cookie; - struct ofp_match match; - - char *comment; - - /* Delete comments. */ - comment = strchr(line, '#'); - if (comment) { - *comment = '\0'; - } - - /* Drop empty lines. */ - if (line[strspn(line, " \t\n")] == '\0') { - continue; - } - - /* Parse and send. str_to_flow() will expand and reallocate the data - * in 'buffer', so we can't keep pointers to across the str_to_flow() - * call. */ - make_openflow(sizeof *ofm, OFPT_FLOW_MOD, &b); - parse_ofp_str(line, &match, b, - NULL, NULL, &priority, &idle_timeout, &hard_timeout, - &cookie); - ofm = b->data; - ofm->match = match; - ofm->command = htons(OFPFC_ADD); - ofm->cookie = htonll(cookie); - ofm->idle_timeout = htons(idle_timeout); - ofm->hard_timeout = htons(hard_timeout); - ofm->buffer_id = htonl(UINT32_MAX); - ofm->priority = htons(priority); - - update_openflow_length(b); + while ((b = parse_ofp_add_flow_file(default_flows)) != NULL) { queue_tx(sw, rconn, b); } } diff --git a/lib/ofp-parse.c b/lib/ofp-parse.c index 32e790a86..069687b15 100644 --- a/lib/ofp-parse.c +++ b/lib/ofp-parse.c @@ -21,6 +21,7 @@ #include #include +#include "dynamic-string.h" #include "netdev.h" #include "ofp-util.h" #include "ofpbuf.h" @@ -29,7 +30,7 @@ #include "socket-util.h" #include "vconn.h" #include "vlog.h" - +#include "xtoxll.h" VLOG_DEFINE_THIS_MODULE(ofp_parse) @@ -502,3 +503,65 @@ parse_ofp_str(char *string, struct ofp_match *match, struct ofpbuf *actions, free(new); } } + +/* Parses 'string' as a OFPT_FLOW_MOD with subtype OFPFC_ADD and returns an + * ofpbuf that contains it. */ +struct ofpbuf * +parse_ofp_add_flow_str(char *string) +{ + struct ofpbuf *buffer; + struct ofp_flow_mod *ofm; + uint16_t priority, idle_timeout, hard_timeout; + uint64_t cookie; + struct ofp_match match; + + /* parse_ofp_str() will expand and reallocate the data in 'buffer', so we + * can't keep pointers to across the parse_ofp_str() call. */ + make_openflow(sizeof *ofm, OFPT_FLOW_MOD, &buffer); + parse_ofp_str(string, &match, buffer, + NULL, NULL, &priority, &idle_timeout, &hard_timeout, + &cookie); + ofm = buffer->data; + ofm->match = match; + ofm->command = htons(OFPFC_ADD); + ofm->cookie = htonll(cookie); + ofm->idle_timeout = htons(idle_timeout); + ofm->hard_timeout = htons(hard_timeout); + ofm->buffer_id = htonl(UINT32_MAX); + ofm->priority = htons(priority); + update_openflow_length(buffer); + + return buffer; +} + +/* Parses an OFPT_FLOW_MOD with subtype OFPFC_ADD from 'stream' and returns an + * ofpbuf that contains it. Returns a null pointer if end-of-file is reached + * before reading a flow. */ +struct ofpbuf * +parse_ofp_add_flow_file(FILE *stream) +{ + struct ofpbuf *b = NULL; + struct ds s = DS_EMPTY_INITIALIZER; + + while (!ds_get_line(&s, stream)) { + char *line = ds_cstr(&s); + char *comment; + + /* Delete comments. */ + comment = strchr(line, '#'); + if (comment) { + *comment = '\0'; + } + + /* Drop empty lines. */ + if (line[strspn(line, " \t\n")] == '\0') { + continue; + } + + b = parse_ofp_add_flow_str(line); + break; + } + ds_destroy(&s); + + return b; +} diff --git a/lib/ofp-parse.h b/lib/ofp-parse.h index aa0489c0c..ac8e6d2f1 100644 --- a/lib/ofp-parse.h +++ b/lib/ofp-parse.h @@ -20,6 +20,7 @@ #define OFP_PARSE_H 1 #include +#include struct ofp_match; struct ofpbuf; @@ -29,5 +30,7 @@ void parse_ofp_str(char *string, struct ofp_match *match, uint16_t *out_port, uint16_t *priority, uint16_t *idle_timeout, uint16_t *hard_timeout, uint64_t *cookie); +struct ofpbuf *parse_ofp_add_flow_str(char *string); +struct ofpbuf *parse_ofp_add_flow_file(FILE *); #endif /* ofp-parse.h */ diff --git a/utilities/ovs-ofctl.c b/utilities/ovs-ofctl.c index 55278fb67..c21c4f982 100644 --- a/utilities/ovs-ofctl.c +++ b/utilities/ovs-ofctl.c @@ -524,8 +524,8 @@ static void do_add_flows(int argc OVS_UNUSED, char *argv[]) { struct vconn *vconn; + struct ofpbuf *b; FILE *file; - char line[1024]; file = fopen(argv[2], "r"); if (file == NULL) { @@ -533,43 +533,8 @@ do_add_flows(int argc OVS_UNUSED, char *argv[]) } open_vconn(argv[1], &vconn); - while (fgets(line, sizeof line, file)) { - struct ofpbuf *buffer; - struct ofp_flow_mod *ofm; - uint16_t priority, idle_timeout, hard_timeout; - uint64_t cookie; - struct ofp_match match; - - char *comment; - - /* Delete comments. */ - comment = strchr(line, '#'); - if (comment) { - *comment = '\0'; - } - - /* Drop empty lines. */ - if (line[strspn(line, " \t\n")] == '\0') { - continue; - } - - /* Parse and send. parse_ofp_str() will expand and reallocate - * the data in 'buffer', so we can't keep pointers to across the - * parse_ofp_str() call. */ - make_openflow(sizeof *ofm, OFPT_FLOW_MOD, &buffer); - parse_ofp_str(line, &match, buffer, - NULL, NULL, &priority, &idle_timeout, &hard_timeout, - &cookie); - ofm = buffer->data; - ofm->match = match; - ofm->command = htons(OFPFC_ADD); - ofm->cookie = htonll(cookie); - ofm->idle_timeout = htons(idle_timeout); - ofm->hard_timeout = htons(hard_timeout); - ofm->buffer_id = htonl(UINT32_MAX); - ofm->priority = htons(priority); - - send_openflow_buffer(vconn, buffer); + while ((b = parse_ofp_add_flow_file(file)) != NULL) { + send_openflow_buffer(vconn, b); } vconn_close(vconn); fclose(file); -- 2.43.0