X-Git-Url: http://v3vee.org/palacios/gitweb/gitweb.cgi?a=blobdiff_plain;f=linux_module%2Fpalacios-vnet-ctrl.c;h=6dae6bbf7730736448ba7a0162dbbe840ff9aa7a;hb=c8b23e99efde3aa5a2c26d1b8e9bc7dc914e6113;hp=12dec1f253705b7a7c58bc75ffb52cbfa0a98c8b;hpb=0975ec64a5a81c1c51bc49791b40e785d1679d28;p=palacios.git diff --git a/linux_module/palacios-vnet-ctrl.c b/linux_module/palacios-vnet-ctrl.c index 12dec1f..6dae6bb 100644 --- a/linux_module/palacios-vnet-ctrl.c +++ b/linux_module/palacios-vnet-ctrl.c @@ -22,6 +22,7 @@ #include #include #include "palacios-vnet.h" +#include "palacios.h" #define VNET_SERVER_PORT 9000 @@ -61,10 +62,33 @@ struct vnet_ctrl_state { static struct vnet_ctrl_state vnet_ctrl_s; +char *skip_blank(char **start) +{ + char *cur; + + do { + cur = strsep(start, " \t"); + } while (cur != NULL && *cur=='\0'); + + return cur; +} + +char *skip_lines(char **start) +{ + char *cur; + + do { + cur = strsep(start, "\r\n"); + } while (cur != NULL && *cur=='\0'); + + return cur; +} + + static int parse_mac_str(char * str, uint8_t * qual, uint8_t * mac) { char * token; - printk("Parsing MAC (%s)\n", str); + INFO("Parsing MAC (%s)\n", str); *qual = MAC_NOSET; if(strnicmp("any", str, strlen(str)) == 0){ @@ -80,7 +104,7 @@ static int parse_mac_str(char * str, uint8_t * qual, uint8_t * mac) { if (strnicmp("not", token, strlen("not")) == 0) { *qual = MAC_NOT; } else { - printk("Invalid MAC String token (%s)\n", token); + WARNING("Invalid MAC String token (%s)\n", token); return -1; } } @@ -95,15 +119,15 @@ static int parse_mac_str(char * str, uint8_t * qual, uint8_t * mac) { for (i = 0; i < 6; i++) { token = strsep(&str, ":"); if (!token) { - printk("Invalid MAC String token (%s)\n", token); + WARNING("Invalid MAC String token (%s)\n", token); return -1; } mac[i] = simple_strtol(token, &token, 16); } - printk("MAC: %2x:%2x:%2x:%2x:%2x:%2x\n", mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]); + DEBUG("MAC: %2x:%2x:%2x:%2x:%2x:%2x\n", mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]); }else { - printk("Invalid MAC String token (%s)\n", token); + WARNING("Invalid MAC String token (%s)\n", token); return -1; } @@ -120,7 +144,7 @@ static int str2mac(char * str, uint8_t * mac){ for (i = 0; i < ETH_ALEN; i++) { hex = strsep(&str, ":"); if (!hex) { - printk("Invalid MAC String token (%s)\n", str); + WARNING("Invalid MAC String token (%s)\n", str); return -1; } mac[i] = simple_strtol(hex, &hex, 16); @@ -161,41 +185,41 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { struct vnet_link_iter * link = NULL; // src MAC - token = strsep(&str, " "); + token = skip_blank(&str); if (!token) { return -1; } parse_mac_str(token, &(route->src_mac_qual), route->src_mac); - // dst MAC - token = strsep(&str, " "); + // Dst MAC + token = skip_blank(&str); if (!token) { return -1; } parse_mac_str(token, &(route->dst_mac_qual), route->dst_mac); // dst LINK type - token = strsep(&str, " "); + token = skip_blank(&str); if (!token) { return -1; } - printk("dst type =(%s)\n", token); + INFO("dst type =(%s)\n", token); if (strnicmp("interface", token, strlen("interface")) == 0) { route->dst_type = LINK_INTERFACE; } else if (strnicmp("edge", token, strlen("edge")) == 0) { route->dst_type = LINK_EDGE; } else { - printk("Invalid Destination Link Type (%s)\n", token); + WARNING("Invalid Destination Link Type (%s)\n", token); return -1; } // dst link - token = strsep(&str, " "); + token = skip_blank(&str); if (!token) { return -1; } - printk("dst ID=(%s)\n", token); + DEBUG("dst ID=(%s)\n", token); // Figure out link here if (route->dst_type == LINK_EDGE) { @@ -203,7 +227,7 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { // Figure out Link Here if (in4_pton(token, strlen(token), (uint8_t *)&(link_ip), '\0', NULL) != 1) { - printk("Invalid Dst IP address (%s)\n", token); + WARNING("Invalid Dst IP address (%s)\n", token); return -EFAULT; } @@ -211,26 +235,26 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { if (link != NULL){ route->dst_id = link->idx; }else{ - printk("can not find dst link %s\n", token); + WARNING("can not find dst link %s\n", token); return -1; } - printk("link_ip = %d, link_id = %d\n", link_ip, link->idx); + INFO("link_ip = %d, link_id = %d\n", link_ip, link->idx); } else if (route->dst_type == LINK_INTERFACE) { uint8_t mac[ETH_ALEN]; if(str2mac(token, mac) == -1){ - printk("wrong MAC format (%s)\n", token); + WARNING("wrong MAC format (%s)\n", token); return -1; } route->dst_id = v3_vnet_find_dev(mac); if (route->dst_id == -1){ - printk("can not find dst device %s\n", token); + WARNING("can not find dst device %s\n", token); return -1; } } else { - printk("Unsupported dst link type\n"); + WARNING("Unsupported dst link type\n"); return -1; } @@ -238,9 +262,9 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { route->src_type = -1; // src LINK - token = strsep(&str, " "); + token = skip_blank(&str); - printk("SRC type = %s\n", token); + INFO("SRC type = %s\n", token); if (!token) { return -1; @@ -253,7 +277,7 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { } else if (strnicmp("any", token, strlen("any")) == 0) { route->src_type = LINK_ANY; } else { - printk("Invalid Src link type (%s)\n", token); + WARNING("Invalid Src link type (%s)\n", token); return -1; } @@ -262,7 +286,7 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { route->src_id = -1; } else if (route->src_type == LINK_EDGE) { uint32_t src_ip; - token = strsep(&str, " "); + token = skip_blank(&str); if (!token) { return -1; @@ -270,7 +294,7 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { // Figure out Link Here if (in4_pton(token, strlen(token), (uint8_t *)&(src_ip), '\0', NULL) != 1) { - printk("Invalid SRC IP address (%s)\n", token); + WARNING("Invalid SRC IP address (%s)\n", token); return -EFAULT; } @@ -278,24 +302,24 @@ static int parse_route_str(char * str, struct v3_vnet_route * route) { if (link != NULL){ route->src_id = link->idx; }else{ - printk("can not find src link %s\n", token); + WARNING("can not find src link %s\n", token); return -1; } } else if(route->src_type == LINK_INTERFACE){ uint8_t mac[ETH_ALEN]; if(str2mac(token, mac) == -1){ - printk("wrong MAC format (%s)\n", token); + WARNING("wrong MAC format (%s)\n", token); return -1; } route->src_id = v3_vnet_find_dev(mac); if (route->src_id == -1){ - printk("can not find dst device %s\n", token); + WARNING("can not find dst device %s\n", token); return -1; } } else { - printk("Invalid link type\n"); + WARNING("Invalid link type\n"); return -1; } @@ -398,13 +422,13 @@ static int route_seq_show(struct seq_file * s, void * v) { break; case MAC_NOT: seq_printf(s, "not-%x:%x:%x:%x:%x:%x ", - route->src_mac[0], route->src_mac[1], route->src_mac[2], - route->src_mac[3], route->src_mac[4], route->src_mac[5]); + route->dst_mac[0], route->dst_mac[1], route->dst_mac[2], + route->dst_mac[3], route->dst_mac[4], route->dst_mac[5]); break; default: seq_printf(s, "%x:%x:%x:%x:%x:%x ", - route->src_mac[0], route->src_mac[1], route->src_mac[2], - route->src_mac[3], route->src_mac[4], route->src_mac[5]); + route->dst_mac[0], route->dst_mac[1], route->dst_mac[2], + route->dst_mac[3], route->dst_mac[4], route->dst_mac[5]); break; } @@ -520,12 +544,12 @@ static int inject_route(struct vnet_route_iter * route) { route->idx = v3_vnet_add_route(route->route); - spin_lock_irqsave(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_lock_irqsave(&(vnet_ctrl_s.lock), flags); list_add(&(route->node), &(vnet_ctrl_s.route_list)); vnet_ctrl_s.num_routes ++; - spin_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); - printk("VNET Control: One route added to VNET core\n"); + INFO("VNET Control: One route added to VNET core\n"); return 0; } @@ -536,14 +560,14 @@ static void delete_route(struct vnet_route_iter * route) { v3_vnet_del_route(route->idx); - spin_lock_irqsave(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_lock_irqsave(&(vnet_ctrl_s.lock), flags); list_del(&(route->node)); vnet_ctrl_s.num_routes --; - spin_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); - printk("VNET Control: Route %d deleted from VNET\n", route->idx); + INFO("VNET Control: Route %d deleted from VNET\n", route->idx); - kfree(route); + palacios_free(route); route = NULL; } @@ -581,32 +605,35 @@ route_write(struct file * file, } route_buf[size] = '\0'; - printk("Route written: %s\n", route_buf); + INFO("Route written: %s\n", route_buf); - while ((buf_iter = strsep(&line_str, "\r\n"))) { + while ((buf_iter = skip_lines(&line_str))) { - token = strsep(&buf_iter, " "); + token = skip_blank(&buf_iter); if (!token) { return -EFAULT; } if (strnicmp("ADD", token, strlen("ADD")) == 0) { struct vnet_route_iter * new_route = NULL; - new_route = kmalloc(sizeof(struct vnet_route_iter), GFP_KERNEL); + new_route = palacios_alloc(sizeof(struct vnet_route_iter)); if (!new_route) { + ERROR("Cannot allocate new route\n"); return -ENOMEM; } memset(new_route, 0, sizeof(struct vnet_route_iter)); if (parse_route_str(buf_iter, &(new_route->route)) == -1) { - kfree(new_route); + ERROR("Cannot parse new route\n"); + palacios_free(new_route); return -EFAULT; } if (inject_route(new_route) != 0) { - kfree(new_route); + ERROR("Cannot inject new route\n"); + palacios_free(new_route); return -EFAULT; } } else if (strnicmp("DEL", token, strlen("DEL")) == 0) { @@ -614,16 +641,16 @@ route_write(struct file * file, uint32_t d_idx; struct vnet_route_iter * route = NULL; - idx_str = strsep(&buf_iter, " "); + idx_str = skip_blank(&buf_iter); if (!idx_str) { - printk("Missing route idx in DEL Route command\n"); + WARNING("Missing route idx in DEL Route command\n"); return -EFAULT; } d_idx = simple_strtoul(idx_str, &idx_str, 10); - printk("VNET: deleting route %d\n", d_idx); + INFO("VNET: deleting route %d\n", d_idx); list_for_each_entry(route, &(vnet_ctrl_s.route_list), node) { if (route->idx == d_idx) { @@ -632,7 +659,7 @@ route_write(struct file * file, } } } else { - printk("Invalid Route command string\n"); + WARNING("Invalid Route command string\n"); } } @@ -645,12 +672,12 @@ static void delete_link(struct vnet_link_iter * link){ vnet_brg_delete_link(link->idx); - spin_lock_irqsave(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_lock_irqsave(&(vnet_ctrl_s.lock), flags); list_del(&(link->node)); vnet_ctrl_s.num_links --; - spin_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); - kfree(link); + palacios_free(link); link = NULL; } @@ -688,11 +715,12 @@ link_write(struct file * file, const char * buf, size_t size, loff_t * ppos) { return -EFAULT; } - while ((link_iter = strsep(&line_str, "\r\n"))) { - printk("Link written: %s\n", link_buf); - - token = strsep(&link_iter, " "); + link_buf[size] = '\0'; + INFO("Link written: %s\n", link_buf); + + while ((link_iter = skip_lines(&line_str))) { + token = skip_blank(&link_iter); if (!token) { return -EFAULT; } @@ -706,15 +734,15 @@ link_write(struct file * file, const char * buf, size_t size, loff_t * ppos) { int link_idx; unsigned long flags; - ip_str = strsep(&link_iter, " "); + ip_str = skip_blank(&link_iter); if ((!ip_str) || (!link_iter)) { - printk("Missing fields in ADD Link command\n"); + WARNING("Missing fields in ADD Link command\n"); return -EFAULT; } if (in4_pton(ip_str, strlen(ip_str), (uint8_t *)&(d_ip), '\0', NULL) != 1) { - printk("Invalid Dst IP address (%s)\n", ip_str); + WARNING("Invalid Dst IP address (%s)\n", ip_str); return -EFAULT; } @@ -723,11 +751,16 @@ link_write(struct file * file, const char * buf, size_t size, loff_t * ppos) { link_idx = vnet_brg_add_link(d_ip, d_port, d_proto); if(link_idx < 0){ - printk("VNET Control: Failed to create link\n"); + WARNING("VNET Control: Failed to create link\n"); + return -EFAULT; + } + + link = palacios_alloc(sizeof(struct vnet_link_iter)); + if (!link) { + WARNING("VNET Control: Cannot allocate link\n"); return -EFAULT; } - link = kmalloc(sizeof(struct vnet_link_iter), GFP_KERNEL); memset(link, 0, sizeof(struct vnet_link_iter)); link->dst_ip = d_ip; @@ -735,28 +768,37 @@ link_write(struct file * file, const char * buf, size_t size, loff_t * ppos) { link->proto = d_proto; link->idx = link_idx; - spin_lock_irqsave(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_lock_irqsave(&(vnet_ctrl_s.lock), flags); list_add(&(link->node), &(vnet_ctrl_s.link_iter_list)); vnet_ctrl_s.num_links ++; - spin_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); + palacios_spinlock_unlock_irqrestore(&(vnet_ctrl_s.lock), flags); } else if (strnicmp("DEL", token, strlen("DEL")) == 0) { char * idx_str = NULL; uint32_t d_idx; + struct vnet_link_iter * link = NULL; - idx_str = strsep(&link_iter, " "); + idx_str = skip_blank(&link_iter); if (!idx_str) { - printk("Missing link idx in DEL Link command\n"); + WARNING("Missing link idx in DEL Link command\n"); return -EFAULT; } d_idx = simple_strtoul(idx_str, &idx_str, 10); - vnet_brg_delete_link(d_idx); - - printk("VNET Control: One link deleted\n"); + INFO("VNET: deleting link %d\n", d_idx); + + list_for_each_entry(link, &(vnet_ctrl_s.link_iter_list), node) { + if (link->idx == d_idx) { + delete_link(link); + break; + } + } + + DEBUG("VNET Control: One link deleted\n"); + } else { - printk("Invalid Link command string\n"); + WARNING("Invalid Link command string\n"); } } @@ -799,10 +841,10 @@ debug_write(struct file * file, const char * buf, size_t size, loff_t * ppos) { return -EFAULT; } - in_iter = strsep(&line_str, "\r\n"); + in_iter = skip_lines(&line_str); level = simple_strtol(in_iter, &in_iter, 10); - printk("VNET Control: Set VNET Debug level to %d\n", level); + DEBUG("VNET Control: Set VNET Debug level to %d\n", level); if(level >= 0){ net_debug = level; @@ -876,39 +918,40 @@ static int init_proc_files(void) { struct proc_dir_entry * debug_entry = NULL; struct proc_dir_entry * vnet_root = NULL; - vnet_root = proc_mkdir("vnet", NULL); + + vnet_root = proc_mkdir("vnet", palacios_get_procdir()); + if (vnet_root == NULL) { return -1; } - route_entry = create_proc_entry("routes", 0, vnet_root); + + PAL_PROC_CREATE(route_entry,"routes",0644, vnet_root,&route_fops); + if (route_entry == NULL) { remove_proc_entry("vnet", NULL); return -1; } - route_entry->proc_fops = &route_fops; + PAL_PROC_CREATE(link_entry,"links", 0644, vnet_root,&link_fops); - link_entry = create_proc_entry("links", 0, vnet_root); if (link_entry == NULL) { remove_proc_entry("routes", vnet_root); remove_proc_entry("vnet", NULL); return -1; } - link_entry->proc_fops = &link_fops; - - stat_entry = create_proc_entry("stats", 0, vnet_root); + PAL_PROC_CREATE(stat_entry,"stats", 0644, vnet_root, &stat_fops); + if(stat_entry == NULL) { remove_proc_entry("links", vnet_root); remove_proc_entry("routes", vnet_root); remove_proc_entry("vnet", NULL); return -1; } - stat_entry->proc_fops = &stat_fops; + PAL_PROC_CREATE(debug_entry,"debug", 0644, vnet_root,&debug_fops); - debug_entry = create_proc_entry("debug", 0, vnet_root); if(debug_entry == NULL) { remove_proc_entry("links", vnet_root); remove_proc_entry("routes", vnet_root); @@ -916,7 +959,6 @@ static int init_proc_files(void) { remove_proc_entry("vnet", NULL); return -1; } - debug_entry->proc_fops = &debug_fops; vnet_ctrl_s.vnet_proc_root = vnet_root; @@ -931,7 +973,7 @@ static void destroy_proc_files(void) { remove_proc_entry("links", vnet_root); remove_proc_entry("routes", vnet_root); remove_proc_entry("stats", vnet_root); - remove_proc_entry("vnet", NULL); + remove_proc_entry("vnet", palacios_get_procdir()); } @@ -945,23 +987,30 @@ int vnet_ctrl_init(void) { INIT_LIST_HEAD(&(vnet_ctrl_s.link_iter_list)); INIT_LIST_HEAD(&(vnet_ctrl_s.route_list)); - spin_lock_init(&(vnet_ctrl_s.lock)); + palacios_spinlock_init(&(vnet_ctrl_s.lock)); init_proc_files(); - printk("VNET Linux control module initiated\n"); + NOTICE("VNET Linux control module initiated\n"); return 0; } void vnet_ctrl_deinit(void){ + + INFO("VNET Control Deinit Started\n"); + destroy_proc_files(); deinit_links_list(); deinit_routes_list(); vnet_ctrl_s.status = 0; + + palacios_spinlock_deinit(&(vnet_ctrl_s.lock)); + + INFO("VNET Control Deinit Finished\n"); }