From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mga11.intel.com (mga11.intel.com [192.55.52.93]) by dpdk.org (Postfix) with ESMTP id 8F7108E5D for ; Tue, 13 Oct 2015 09:54:22 +0200 (CEST) Received: from orsmga002.jf.intel.com ([10.7.209.21]) by fmsmga102.fm.intel.com with ESMTP; 13 Oct 2015 00:54:20 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.17,677,1437462000"; d="scan'208";a="825407620" Received: from unknown (HELO stargo) ([10.217.248.233]) by orsmga002.jf.intel.com with SMTP; 13 Oct 2015 00:54:19 -0700 Received: by stargo (sSMTP sendmail emulation); Tue, 13 Oct 2015 09:55:06 +0200 From: Marcin Kerlin To: dev@dpdk.org Date: Tue, 13 Oct 2015 09:34:28 +0200 Message-Id: <1444721669-32581-5-git-send-email-marcinx.kerlin@intel.com> X-Mailer: git-send-email 1.9.1 In-Reply-To: <1444721669-32581-1-git-send-email-marcinx.kerlin@intel.com> References: <1441967499-21255-1-git-send-email-maciejx.t.gajdzica@intel.com> <1444721669-32581-1-git-send-email-marcinx.kerlin@intel.com> Subject: [dpdk-dev] [PATCH v3 4/5] ip_pipline: added cli commands for bulk add/delete to firewall pipeline X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: patches and discussions about DPDK List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 13 Oct 2015 07:54:23 -0000 Added two new cli commands to firewall pipeline. Commands bulk add and bulk delete takes as argument a file with rules to add/delete. The file is parsed, and then rules are passed to backend functions which add/delete records from pipeline tables. Signed-off-by: Maciej Gajdzica Acked-by: Cristian Dumitrescu --- examples/ip_pipeline/pipeline/pipeline_firewall.c | 858 +++++++++++++++++++++ examples/ip_pipeline/pipeline/pipeline_firewall.h | 14 + .../ip_pipeline/pipeline/pipeline_firewall_be.c | 157 ++++ .../ip_pipeline/pipeline/pipeline_firewall_be.h | 38 + 4 files changed, 1067 insertions(+) diff --git a/examples/ip_pipeline/pipeline/pipeline_firewall.c b/examples/ip_pipeline/pipeline/pipeline_firewall.c index f6924ab..4137923 100644 --- a/examples/ip_pipeline/pipeline/pipeline_firewall.c +++ b/examples/ip_pipeline/pipeline/pipeline_firewall.c @@ -51,6 +51,8 @@ #include "pipeline_common_fe.h" #include "pipeline_firewall.h" +#define BUF_SIZE 1024 + struct app_pipeline_firewall_rule { struct pipeline_firewall_key key; int32_t priority; @@ -73,6 +75,18 @@ struct app_pipeline_firewall { void *default_rule_entry_ptr; }; +struct app_pipeline_add_bulk_params { + struct pipeline_firewall_key *keys; + uint32_t n_keys; + uint32_t *priorities; + uint32_t *port_ids; +}; + +struct app_pipeline_del_bulk_params { + struct pipeline_firewall_key *keys; + uint32_t n_keys; +}; + static void print_firewall_ipv4_rule(struct app_pipeline_firewall_rule *rule) { @@ -256,6 +270,358 @@ app_pipeline_firewall_key_check_and_normalize(struct pipeline_firewall_key *key) } } +static int +app_pipeline_add_bulk_parse_file(char *filename, + struct app_pipeline_add_bulk_params *params) +{ + FILE *f; + char file_buf[BUF_SIZE]; + uint32_t i; + int status = 0; + + f = fopen(filename, "r"); + if (f == NULL) + return -1; + + params->n_keys = 0; + while (fgets(file_buf, BUF_SIZE, f) != NULL) + params->n_keys++; + rewind(f); + + if (params->n_keys == 0) { + status = -1; + goto end; + } + + params->keys = rte_malloc(NULL, + params->n_keys * sizeof(struct pipeline_firewall_key), + RTE_CACHE_LINE_SIZE); + if (params->keys == NULL) { + status = -1; + goto end; + } + + params->priorities = rte_malloc(NULL, + params->n_keys * sizeof(uint32_t), + RTE_CACHE_LINE_SIZE); + if (params->priorities == NULL) { + status = -1; + goto end; + } + + params->port_ids = rte_malloc(NULL, + params->n_keys * sizeof(uint32_t), + RTE_CACHE_LINE_SIZE); + if (params->port_ids == NULL) { + status = -1; + goto end; + } + + i = 0; + while (fgets(file_buf, BUF_SIZE, f) != NULL) { + char *str; + + str = strtok(file_buf, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->priorities[i] = atoi(str); + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip = atoi(str)<<24; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip |= atoi(str)<<16; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip |= atoi(str)<<8; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip |= atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip_mask = atoi(str); + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip = atoi(str)<<24; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip |= atoi(str)<<16; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip |= atoi(str)<<8; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip |= atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip_mask = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_port_from = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_port_to = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_port_from = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_port_to = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.proto = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + /* Need to add 2 to str to skip leading 0x */ + params->keys[i].key.ipv4_5tuple.proto_mask = strtol(str+2, NULL, 16); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->port_ids[i] = atoi(str); + params->keys[i].type = PIPELINE_FIREWALL_IPV4_5TUPLE; + + i++; + } + +end: + fclose(f); + return status; +} + +static int +app_pipeline_del_bulk_parse_file(char *filename, + struct app_pipeline_del_bulk_params *params) +{ + FILE *f; + char file_buf[BUF_SIZE]; + uint32_t i; + int status = 0; + + f = fopen(filename, "r"); + if (f == NULL) + return -1; + + params->n_keys = 0; + while (fgets(file_buf, BUF_SIZE, f) != NULL) + params->n_keys++; + rewind(f); + + if (params->n_keys == 0) { + status = -1; + goto end; + } + + params->keys = rte_malloc(NULL, + params->n_keys * sizeof(struct pipeline_firewall_key), + RTE_CACHE_LINE_SIZE); + if (params->keys == NULL) { + status = -1; + goto end; + } + + i = 0; + while (fgets(file_buf, BUF_SIZE, f) != NULL) { + char *str; + + str = strtok(file_buf, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip = atoi(str)<<24; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip |= atoi(str)<<16; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip |= atoi(str)<<8; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip |= atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_ip_mask = atoi(str); + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip = atoi(str)<<24; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip |= atoi(str)<<16; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip |= atoi(str)<<8; + + str = strtok(NULL, " ."); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip |= atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_ip_mask = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_port_from = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.src_port_to = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_port_from = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.dst_port_to = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + params->keys[i].key.ipv4_5tuple.proto = atoi(str); + + str = strtok(NULL, " "); + if (str == NULL) { + status = -1; + goto end; + } + /* Need to add 2 to str to skip leading 0x */ + params->keys[i].key.ipv4_5tuple.proto_mask = strtol(str+2, NULL, 16); + + params->keys[i].type = PIPELINE_FIREWALL_IPV4_5TUPLE; + + i++; + } + + for (i = 0; i < params->n_keys; i++) { + if (app_pipeline_firewall_key_check_and_normalize(¶ms->keys[i]) != 0) { + status = -1; + goto end; + } + } + +end: + fclose(f); + return status; +} + int app_pipeline_firewall_add_rule(struct app_params *app, uint32_t pipeline_id, @@ -407,6 +773,332 @@ app_pipeline_firewall_delete_rule(struct app_params *app, } int +app_pipeline_firewall_add_bulk(struct app_params *app, + uint32_t pipeline_id, + struct pipeline_firewall_key *keys, + uint32_t n_keys, + uint32_t *priorities, + uint32_t *port_ids) +{ + struct app_pipeline_firewall *p; + struct pipeline_firewall_add_bulk_msg_req *req; + struct pipeline_firewall_add_bulk_msg_rsp *rsp; + + struct app_pipeline_firewall_rule **rules; + int *new_rules; + + int *keys_found; + void **entries_ptr; + + uint32_t i; + int status = 0; + + /* Check input arguments */ + if (app == NULL) + return -1; + + p = app_pipeline_data_fe(app, pipeline_id); + if (p == NULL) + return -1; + + rules = rte_malloc(NULL, + n_keys * sizeof(struct app_pipeline_firewall_rule *), + RTE_CACHE_LINE_SIZE); + if (rules == NULL) + return -1; + + new_rules = rte_malloc(NULL, + n_keys * sizeof(int), + RTE_CACHE_LINE_SIZE); + if (new_rules == NULL) { + rte_free(rules); + return -1; + } + + /* check data integrity and add to rule list */ + for (i = 0; i < n_keys; i++) { + if (port_ids[i] >= p->n_ports_out) { + rte_free(rules); + rte_free(new_rules); + return -1; + } + + if (app_pipeline_firewall_key_check_and_normalize(&keys[i]) != 0) { + rte_free(rules); + rte_free(new_rules); + return -1; + } + + rules[i] = app_pipeline_firewall_rule_find(p, &keys[i]); + new_rules[i] = (rules[i] == NULL); + if (rules[i] == NULL) { + rules[i] = rte_malloc(NULL, sizeof(rules[i]), + RTE_CACHE_LINE_SIZE); + + if (rules[i] == NULL) { + uint32_t j; + + for (j = 0; j <= i; j++) + if (new_rules[j]) + rte_free(rules[j]); + + rte_free(rules); + rte_free(new_rules); + return -1; + } + } + } + + keys_found = rte_malloc(NULL, + n_keys * sizeof(int), + RTE_CACHE_LINE_SIZE); + if (keys_found == NULL) { + uint32_t j; + + for (j = 0; j < n_keys; j++) + if (new_rules[j]) + rte_free(rules[j]); + + rte_free(rules); + rte_free(new_rules); + return -1; + } + + entries_ptr = rte_malloc(NULL, + n_keys * sizeof(struct rte_pipeline_table_entry *), + RTE_CACHE_LINE_SIZE); + if (entries_ptr == NULL) { + uint32_t j; + + for (j = 0; j < n_keys; j++) + if (new_rules[j]) + rte_free(rules[j]); + + rte_free(rules); + rte_free(new_rules); + rte_free(keys_found); + return -1; + } + for (i = 0; i < n_keys; i++) { + entries_ptr[i] = rte_malloc(NULL, + sizeof(struct rte_pipeline_table_entry), + RTE_CACHE_LINE_SIZE); + + if (entries_ptr[i] == NULL) { + uint32_t j; + + for (j = 0; j < n_keys; j++) + if (new_rules[j]) + rte_free(rules[j]); + + for (j = 0; j <= i; j++) + rte_free(entries_ptr[j]); + + rte_free(rules); + rte_free(new_rules); + rte_free(keys_found); + rte_free(entries_ptr); + return -1; + } + } + + /* Allocate and write request */ + req = app_msg_alloc(app); + if (req == NULL) { + uint32_t j; + + for (j = 0; j < n_keys; j++) + if (new_rules[j]) + rte_free(rules[j]); + + for (j = 0; j < n_keys; j++) + rte_free(entries_ptr[j]); + + rte_free(rules); + rte_free(new_rules); + rte_free(keys_found); + rte_free(entries_ptr); + return -1; + } + + req->type = PIPELINE_MSG_REQ_CUSTOM; + req->subtype = PIPELINE_FIREWALL_MSG_REQ_ADD_BULK; + + req->keys = keys; + req->n_keys = n_keys; + req->port_ids = port_ids; + req->priorities = priorities; + req->keys_found = keys_found; + req->entries_ptr = entries_ptr; + + /* Send request and wait for response */ + rsp = app_msg_send_recv(app, pipeline_id, req, MSG_TIMEOUT_DEFAULT); + if (rsp == NULL) { + uint32_t j; + + for (j = 0; j < n_keys; j++) + if (new_rules[j]) + rte_free(rules[j]); + + for (j = 0; j < n_keys; j++) + rte_free(entries_ptr[j]); + + rte_free(rules); + rte_free(new_rules); + rte_free(keys_found); + rte_free(entries_ptr); + return -1; + } + + if (rsp->status) { + for (i = 0; i < n_keys; i++) + if (new_rules[i]) + rte_free(rules[i]); + + for (i = 0; i < n_keys; i++) + rte_free(entries_ptr[i]); + + status = -1; + goto cleanup; + } + + for (i = 0; i < n_keys; i++) { + if (entries_ptr[i] == NULL || + ((new_rules[i] == 0) && (keys_found[i] == 0)) || + ((new_rules[i] == 1) && (keys_found[i] == 1))) { + for (i = 0; i < n_keys; i++) + if (new_rules[i]) + rte_free(rules[i]); + + for (i = 0; i < n_keys; i++) + rte_free(entries_ptr[i]); + + status = -1; + goto cleanup; + } + } + + for (i = 0; i < n_keys; i++) { + memcpy(&rules[i]->key, &keys[i], sizeof(keys[i])); + rules[i]->priority = priorities[i]; + rules[i]->port_id = port_ids[i]; + rules[i]->entry_ptr = entries_ptr[i]; + + /* Commit rule */ + if (new_rules[i]) { + TAILQ_INSERT_TAIL(&p->rules, rules[i], node); + p->n_rules++; + } + + print_firewall_ipv4_rule(rules[i]); + } + +cleanup: + app_msg_free(app, rsp); + rte_free(rules); + rte_free(new_rules); + rte_free(keys_found); + rte_free(entries_ptr); + + return status; +} + +int +app_pipeline_firewall_delete_bulk(struct app_params *app, + uint32_t pipeline_id, + struct pipeline_firewall_key *keys, + uint32_t n_keys) +{ + struct app_pipeline_firewall *p; + struct pipeline_firewall_del_bulk_msg_req *req; + struct pipeline_firewall_del_bulk_msg_rsp *rsp; + + struct app_pipeline_firewall_rule **rules; + int *keys_found; + + uint32_t i; + int status = 0; + + /* Check input arguments */ + if (app == NULL) + return -1; + + p = app_pipeline_data_fe(app, pipeline_id); + if (p == NULL) + return -1; + + rules = rte_malloc(NULL, + n_keys * sizeof(struct app_pipeline_firewall_rule *), + RTE_CACHE_LINE_SIZE); + if (rules == NULL) + return -1; + + for (i = 0; i < n_keys; i++) { + if (app_pipeline_firewall_key_check_and_normalize(&keys[i]) != 0) { + return -1; + } + + rules[i] = app_pipeline_firewall_rule_find(p, &keys[i]); + } + + keys_found = rte_malloc(NULL, + n_keys * sizeof(int), + RTE_CACHE_LINE_SIZE); + if (keys_found == NULL) { + rte_free(rules); + return -1; + } + + /* Allocate and write request */ + req = app_msg_alloc(app); + if (req == NULL) { + rte_free(rules); + rte_free(keys_found); + return -1; + } + + req->type = PIPELINE_MSG_REQ_CUSTOM; + req->subtype = PIPELINE_FIREWALL_MSG_REQ_DEL_BULK; + + req->keys = keys; + req->n_keys = n_keys; + req->keys_found = keys_found; + + /* Send request and wait for response */ + rsp = app_msg_send_recv(app, pipeline_id, req, MSG_TIMEOUT_DEFAULT); + if (rsp == NULL) { + rte_free(rules); + rte_free(keys_found); + return -1; + } + + if (rsp->status) { + status = -1; + goto cleanup; + } + + for (i = 0; i < n_keys; i++) { + if (keys_found[i] == 0) { + status = -1; + goto cleanup; + } + } + + for (i = 0; i < n_keys; i++) { + TAILQ_REMOVE(&p->rules, rules[i], node); + p->n_rules--; + rte_free(rules[i]); + } + +cleanup: + app_msg_free(app, rsp); + rte_free(rules); + rte_free(keys_found); + + return status; +} + +int app_pipeline_firewall_add_default_rule(struct app_params *app, uint32_t pipeline_id, uint32_t port_id) @@ -795,6 +1487,170 @@ cmdline_parse_inst_t cmd_firewall_del_ipv4 = { }; /* + * p firewall add bulk + */ + +struct cmd_firewall_add_bulk_result { + cmdline_fixed_string_t p_string; + uint32_t pipeline_id; + cmdline_fixed_string_t firewall_string; + cmdline_fixed_string_t add_string; + cmdline_fixed_string_t bulk_string; + cmdline_fixed_string_t file_path; +}; + +static void +cmd_firewall_add_bulk_parsed( + void *parsed_result, + __attribute__((unused)) struct cmdline *cl, + void *data) +{ + struct cmd_firewall_add_bulk_result *params = parsed_result; + struct app_params *app = data; + int status; + + struct app_pipeline_add_bulk_params add_bulk_params; + + status = app_pipeline_add_bulk_parse_file(params->file_path, &add_bulk_params); + if (status != 0) { + printf("Command failed\n"); + goto end; + } + + status = app_pipeline_firewall_add_bulk(app, params->pipeline_id, add_bulk_params.keys, + add_bulk_params.n_keys, add_bulk_params.priorities, add_bulk_params.port_ids); + if (status != 0) { + printf("Command failed\n"); + goto end; + } + +end: + rte_free(add_bulk_params.keys); + rte_free(add_bulk_params.priorities); + rte_free(add_bulk_params.port_ids); +} + +cmdline_parse_token_string_t cmd_firewall_add_bulk_p_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_add_bulk_result, p_string, + "p"); + +cmdline_parse_token_num_t cmd_firewall_add_bulk_pipeline_id = + TOKEN_NUM_INITIALIZER(struct cmd_firewall_add_bulk_result, pipeline_id, + UINT32); + +cmdline_parse_token_string_t cmd_firewall_add_bulk_firewall_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_add_bulk_result, + firewall_string, "firewall"); + +cmdline_parse_token_string_t cmd_firewall_add_bulk_add_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_add_bulk_result, + add_string, "add"); + +cmdline_parse_token_string_t cmd_firewall_add_bulk_bulk_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_add_bulk_result, + bulk_string, "bulk"); + +cmdline_parse_token_string_t cmd_firewall_add_bulk_file_path_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_add_bulk_result, + file_path, NULL); + +cmdline_parse_inst_t cmd_firewall_add_bulk = { + .f = cmd_firewall_add_bulk_parsed, + .data = NULL, + .help_str = "Firewall rule add bulk", + .tokens = { + (void *) &cmd_firewall_add_bulk_p_string, + (void *) &cmd_firewall_add_bulk_pipeline_id, + (void *) &cmd_firewall_add_bulk_firewall_string, + (void *) &cmd_firewall_add_bulk_add_string, + (void *) &cmd_firewall_add_bulk_bulk_string, + (void *) &cmd_firewall_add_bulk_file_path_string, + NULL, + }, +}; + +/* + * p firewall del bulk + */ + +struct cmd_firewall_del_bulk_result { + cmdline_fixed_string_t p_string; + uint32_t pipeline_id; + cmdline_fixed_string_t firewall_string; + cmdline_fixed_string_t del_string; + cmdline_fixed_string_t bulk_string; + cmdline_fixed_string_t file_path; +}; + +static void +cmd_firewall_del_bulk_parsed( + void *parsed_result, + __attribute__((unused)) struct cmdline *cl, + void *data) +{ + struct cmd_firewall_del_bulk_result *params = parsed_result; + struct app_params *app = data; + int status; + + struct app_pipeline_del_bulk_params del_bulk_params; + + status = app_pipeline_del_bulk_parse_file(params->file_path, &del_bulk_params); + if (status != 0) { + printf("Command failed\n"); + goto end; + } + + status = app_pipeline_firewall_delete_bulk(app, params->pipeline_id, + del_bulk_params.keys, del_bulk_params.n_keys); + if (status != 0) { + printf("Command failed\n"); + goto end; + } + +end: + rte_free(del_bulk_params.keys); +} + +cmdline_parse_token_string_t cmd_firewall_del_bulk_p_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_del_bulk_result, p_string, + "p"); + +cmdline_parse_token_num_t cmd_firewall_del_bulk_pipeline_id = + TOKEN_NUM_INITIALIZER(struct cmd_firewall_del_bulk_result, pipeline_id, + UINT32); + +cmdline_parse_token_string_t cmd_firewall_del_bulk_firewall_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_del_bulk_result, + firewall_string, "firewall"); + +cmdline_parse_token_string_t cmd_firewall_del_bulk_add_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_del_bulk_result, + del_string, "del"); + +cmdline_parse_token_string_t cmd_firewall_del_bulk_bulk_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_del_bulk_result, + bulk_string, "bulk"); + +cmdline_parse_token_string_t cmd_firewall_del_bulk_file_path_string = + TOKEN_STRING_INITIALIZER(struct cmd_firewall_del_bulk_result, + file_path, NULL); + +cmdline_parse_inst_t cmd_firewall_del_bulk = { + .f = cmd_firewall_del_bulk_parsed, + .data = NULL, + .help_str = "Firewall rule del bulk", + .tokens = { + (void *) &cmd_firewall_del_bulk_p_string, + (void *) &cmd_firewall_del_bulk_pipeline_id, + (void *) &cmd_firewall_del_bulk_firewall_string, + (void *) &cmd_firewall_del_bulk_add_string, + (void *) &cmd_firewall_del_bulk_bulk_string, + (void *) &cmd_firewall_del_bulk_file_path_string, + NULL, + }, +}; + +/* * p firewall add default */ struct cmd_firewall_add_default_result { @@ -984,6 +1840,8 @@ cmdline_parse_inst_t cmd_firewall_ls = { static cmdline_parse_ctx_t pipeline_cmds[] = { (cmdline_parse_inst_t *) &cmd_firewall_add_ipv4, (cmdline_parse_inst_t *) &cmd_firewall_del_ipv4, + (cmdline_parse_inst_t *) &cmd_firewall_add_bulk, + (cmdline_parse_inst_t *) &cmd_firewall_del_bulk, (cmdline_parse_inst_t *) &cmd_firewall_add_default, (cmdline_parse_inst_t *) &cmd_firewall_del_default, (cmdline_parse_inst_t *) &cmd_firewall_ls, diff --git a/examples/ip_pipeline/pipeline/pipeline_firewall.h b/examples/ip_pipeline/pipeline/pipeline_firewall.h index 82e905d..ccc4e64 100644 --- a/examples/ip_pipeline/pipeline/pipeline_firewall.h +++ b/examples/ip_pipeline/pipeline/pipeline_firewall.h @@ -50,6 +50,20 @@ app_pipeline_firewall_delete_rule(struct app_params *app, struct pipeline_firewall_key *key); int +app_pipeline_firewall_add_bulk(struct app_params *app, + uint32_t pipeline_id, + struct pipeline_firewall_key *keys, + uint32_t n_keys, + uint32_t *priorities, + uint32_t *port_ids); + +int +app_pipeline_firewall_delete_bulk(struct app_params *app, + uint32_t pipeline_id, + struct pipeline_firewall_key *keys, + uint32_t n_keys); + +int app_pipeline_firewall_add_default_rule(struct app_params *app, uint32_t pipeline_id, uint32_t port_id); diff --git a/examples/ip_pipeline/pipeline/pipeline_firewall_be.c b/examples/ip_pipeline/pipeline/pipeline_firewall_be.c index b6f305f..1c376f7 100644 --- a/examples/ip_pipeline/pipeline/pipeline_firewall_be.c +++ b/examples/ip_pipeline/pipeline/pipeline_firewall_be.c @@ -80,6 +80,12 @@ static void * pipeline_firewall_msg_req_del_handler(struct pipeline *p, void *msg); static void * +pipeline_firewall_msg_req_add_bulk_handler(struct pipeline *p, void *msg); + +static void * +pipeline_firewall_msg_req_del_bulk_handler(struct pipeline *p, void *msg); + +static void * pipeline_firewall_msg_req_add_default_handler(struct pipeline *p, void *msg); static void * @@ -90,6 +96,10 @@ static pipeline_msg_req_handler custom_handlers[] = { pipeline_firewall_msg_req_add_handler, [PIPELINE_FIREWALL_MSG_REQ_DEL] = pipeline_firewall_msg_req_del_handler, + [PIPELINE_FIREWALL_MSG_REQ_ADD_BULK] = + pipeline_firewall_msg_req_add_bulk_handler, + [PIPELINE_FIREWALL_MSG_REQ_DEL_BULK] = + pipeline_firewall_msg_req_del_bulk_handler, [PIPELINE_FIREWALL_MSG_REQ_ADD_DEFAULT] = pipeline_firewall_msg_req_add_default_handler, [PIPELINE_FIREWALL_MSG_REQ_DEL_DEFAULT] = @@ -698,6 +708,153 @@ pipeline_firewall_msg_req_del_handler(struct pipeline *p, void *msg) return rsp; } +static void * +pipeline_firewall_msg_req_add_bulk_handler(struct pipeline *p, void *msg) +{ + struct pipeline_firewall_add_bulk_msg_req *req = msg; + struct pipeline_firewall_add_bulk_msg_rsp *rsp = msg; + + struct rte_table_acl_rule_add_params *params[req->n_keys]; + struct firewall_table_entry *entries[req->n_keys]; + + uint32_t i, n_keys; + + n_keys = req->n_keys; + + for (i = 0; i < n_keys; i++) { + entries[i] = rte_malloc(NULL, + sizeof(struct firewall_table_entry), + RTE_CACHE_LINE_SIZE); + if (entries[i] == NULL) { + rsp->status = -1; + return rsp; + } + + params[i] = rte_malloc(NULL, + sizeof(struct rte_table_acl_rule_add_params), + RTE_CACHE_LINE_SIZE); + if (params[i] == NULL) { + rsp->status = -1; + return rsp; + } + + entries[i]->head.action = RTE_PIPELINE_ACTION_PORT; + entries[i]->head.port_id = p->port_out_id[req->port_ids[i]]; + + switch (req->keys[i].type) { + case PIPELINE_FIREWALL_IPV4_5TUPLE: + params[i]->priority = req->priorities[i]; + params[i]->field_value[0].value.u8 = + req->keys[i].key.ipv4_5tuple.proto; + params[i]->field_value[0].mask_range.u8 = + req->keys[i].key.ipv4_5tuple.proto_mask; + params[i]->field_value[1].value.u32 = + req->keys[i].key.ipv4_5tuple.src_ip; + params[i]->field_value[1].mask_range.u32 = + req->keys[i].key.ipv4_5tuple.src_ip_mask; + params[i]->field_value[2].value.u32 = + req->keys[i].key.ipv4_5tuple.dst_ip; + params[i]->field_value[2].mask_range.u32 = + req->keys[i].key.ipv4_5tuple.dst_ip_mask; + params[i]->field_value[3].value.u16 = + req->keys[i].key.ipv4_5tuple.src_port_from; + params[i]->field_value[3].mask_range.u16 = + req->keys[i].key.ipv4_5tuple.src_port_to; + params[i]->field_value[4].value.u16 = + req->keys[i].key.ipv4_5tuple.dst_port_from; + params[i]->field_value[4].mask_range.u16 = + req->keys[i].key.ipv4_5tuple.dst_port_to; + break; + + default: + rsp->status = -1; /* Error */ + + for (i = 0; i < n_keys; i++) { + rte_free(entries[i]); + rte_free(params[i]); + } + + return rsp; + } + } + + rsp->status = rte_pipeline_table_entry_add_bulk(p->p, p->table_id[0], + (void *)params, (struct rte_pipeline_table_entry **)entries, + n_keys, req->keys_found, + (struct rte_pipeline_table_entry **)req->entries_ptr); + + for (i = 0; i < n_keys; i++) { + rte_free(entries[i]); + rte_free(params[i]); + } + + return rsp; +} + +static void * +pipeline_firewall_msg_req_del_bulk_handler(struct pipeline *p, void *msg) +{ + struct pipeline_firewall_del_bulk_msg_req *req = msg; + struct pipeline_firewall_del_bulk_msg_rsp *rsp = msg; + + struct rte_table_acl_rule_delete_params *params[req->n_keys]; + + uint32_t i, n_keys; + + n_keys = req->n_keys; + + for (i = 0; i < n_keys; i++) { + params[i] = rte_malloc(NULL, + sizeof(struct rte_table_acl_rule_delete_params), + RTE_CACHE_LINE_SIZE); + if (params[i] == NULL) { + rsp->status = -1; + return rsp; + } + + switch (req->keys[i].type) { + case PIPELINE_FIREWALL_IPV4_5TUPLE: + params[i]->field_value[0].value.u8 = + req->keys[i].key.ipv4_5tuple.proto; + params[i]->field_value[0].mask_range.u8 = + req->keys[i].key.ipv4_5tuple.proto_mask; + params[i]->field_value[1].value.u32 = + req->keys[i].key.ipv4_5tuple.src_ip; + params[i]->field_value[1].mask_range.u32 = + req->keys[i].key.ipv4_5tuple.src_ip_mask; + params[i]->field_value[2].value.u32 = + req->keys[i].key.ipv4_5tuple.dst_ip; + params[i]->field_value[2].mask_range.u32 = + req->keys[i].key.ipv4_5tuple.dst_ip_mask; + params[i]->field_value[3].value.u16 = + req->keys[i].key.ipv4_5tuple.src_port_from; + params[i]->field_value[3].mask_range.u16 = + req->keys[i].key.ipv4_5tuple.src_port_to; + params[i]->field_value[4].value.u16 = + req->keys[i].key.ipv4_5tuple.dst_port_from; + params[i]->field_value[4].mask_range.u16 = + req->keys[i].key.ipv4_5tuple.dst_port_to; + break; + + default: + rsp->status = -1; /* Error */ + + for (i = 0; i < n_keys; i++) + rte_free(params[i]); + + return rsp; + } + } + + rsp->status = rte_pipeline_table_entry_delete_bulk(p->p, p->table_id[0], + (void **)¶ms, n_keys, req->keys_found, NULL); + + for (i = 0; i < n_keys; i++) + rte_free(params[i]); + + return rsp; +} + void * pipeline_firewall_msg_req_add_default_handler(struct pipeline *p, void *msg) { diff --git a/examples/ip_pipeline/pipeline/pipeline_firewall_be.h b/examples/ip_pipeline/pipeline/pipeline_firewall_be.h index 8e1fd69..f5b0522 100644 --- a/examples/ip_pipeline/pipeline/pipeline_firewall_be.h +++ b/examples/ip_pipeline/pipeline/pipeline_firewall_be.h @@ -63,6 +63,8 @@ struct pipeline_firewall_key { enum pipeline_firewall_msg_req_type { PIPELINE_FIREWALL_MSG_REQ_ADD = 0, PIPELINE_FIREWALL_MSG_REQ_DEL, + PIPELINE_FIREWALL_MSG_REQ_ADD_BULK, + PIPELINE_FIREWALL_MSG_REQ_DEL_BULK, PIPELINE_FIREWALL_MSG_REQ_ADD_DEFAULT, PIPELINE_FIREWALL_MSG_REQ_DEL_DEFAULT, PIPELINE_FIREWALL_MSG_REQS @@ -106,6 +108,42 @@ struct pipeline_firewall_del_msg_rsp { }; /* + * MSG ADD BULK + */ +struct pipeline_firewall_add_bulk_msg_req { + enum pipeline_msg_req_type type; + enum pipeline_firewall_msg_req_type subtype; + + struct pipeline_firewall_key *keys; + uint32_t n_keys; + + uint32_t *priorities; + uint32_t *port_ids; + int *keys_found; + void **entries_ptr; +}; +struct pipeline_firewall_add_bulk_msg_rsp { + int status; +}; + +/* + * MSG DEL BULK + */ +struct pipeline_firewall_del_bulk_msg_req { + enum pipeline_msg_req_type type; + enum pipeline_firewall_msg_req_type subtype; + + /* key */ + struct pipeline_firewall_key *keys; + uint32_t n_keys; + int *keys_found; +}; + +struct pipeline_firewall_del_bulk_msg_rsp { + int status; +}; + +/* * MSG ADD DEFAULT */ struct pipeline_firewall_add_default_msg_req { -- 1.9.1 -------------------------------------------------------------- Intel Shannon Limited Registered in Ireland Registered Office: Collinstown Industrial Park, Leixlip, County Kildare Registered Number: 308263 Business address: Dromore House, East Park, Shannon, Co. Clare This e-mail and any attachments may contain confidential material for the sole use of the intended recipient(s). Any review or distribution by others is strictly prohibited. If you are not the intended recipient, please contact the sender and delete all copies.