Re: [PATCH iproute2 1/6] ip vrf: Add name_is_vrf

2016-06-29 Thread David Ahern

On 6/29/16 9:06 AM, Stephen Hemminger wrote:

On Mon, 27 Jun 2016 11:50:56 -0700
David Ahern  wrote:


diff --git a/ip/ip_common.h b/ip/ip_common.h
index e8da9e034b15..410eb135774a 100644
--- a/ip/ip_common.h
+++ b/ip/ip_common.h
@@ -90,6 +90,8 @@ struct link_util *get_link_slave_kind(const char *slave_kind);

 void br_dump_bridge_id(const struct ifla_bridge_id *id, char *buf, size_t len);

+bool name_is_vrf(char *name);
+
 #ifndefINFINITY_LIFE_TIME
 #define INFINITY_LIFE_TIME  0xU
 #endif
diff --git a/ip/iplink_vrf.c b/ip/iplink_vrf.c
index e3c7b4652da5..abd43c08423e 100644
--- a/ip/iplink_vrf.c
+++ b/ip/iplink_vrf.c
@@ -96,3 +96,56 @@ struct link_util vrf_slave_link_util = {
.print_opt  = vrf_slave_print_opt,
.slave  = true,
 };
+
+bool name_is_vrf(char *name)


Why not?
bool name_is_vrf(const char *name)


sure.




+{
+   struct {
+   struct nlmsghdr n;
+   struct ifinfomsgi;
+   charbuf[1024];
+   } req = {
+   .n = {
+   .nlmsg_len   = NLMSG_LENGTH(sizeof(struct ifinfomsg)),
+   .nlmsg_flags = NLM_F_REQUEST,
+   .nlmsg_type  = RTM_GETLINK,
+   },
+   .i = {
+   .ifi_family  = preferred_family,
+   },
+   };
+   struct {
+   struct nlmsghdr n;
+   char buf[8192];
+   } answer;
+   struct rtattr *tb[IFLA_MAX+1];
+   struct rtattr *li[IFLA_INFO_MAX+1];
+   struct ifinfomsg *ifi;
+   int len;
+
+   addattr_l(, sizeof(req), IFLA_IFNAME, name, strlen(name) + 1);
+
+   if (rtnl_talk(, , , sizeof(answer)) < 0)
+   goto err;

Just return false instead of all these goto's?
Also you might want to give some indication of error.


Any failure and the user gets the message "not a VRF". The reason can be 
the device is not a VRF or the device does not exist but that's the same 
thing in this case:


$ ./ip link show vrf foo
Error: argument "foo" is wrong: Not a valid VRF name

$ ./ip link show vrf eth1
Error: argument "eth1" is wrong: Not a valid VRF name




Re: [PATCH iproute2 1/6] ip vrf: Add name_is_vrf

2016-06-29 Thread Stephen Hemminger
On Mon, 27 Jun 2016 11:50:56 -0700
David Ahern  wrote:

> diff --git a/ip/ip_common.h b/ip/ip_common.h
> index e8da9e034b15..410eb135774a 100644
> --- a/ip/ip_common.h
> +++ b/ip/ip_common.h
> @@ -90,6 +90,8 @@ struct link_util *get_link_slave_kind(const char 
> *slave_kind);
>  
>  void br_dump_bridge_id(const struct ifla_bridge_id *id, char *buf, size_t 
> len);
>  
> +bool name_is_vrf(char *name);
> +
>  #ifndef  INFINITY_LIFE_TIME
>  #define INFINITY_LIFE_TIME  0xU
>  #endif
> diff --git a/ip/iplink_vrf.c b/ip/iplink_vrf.c
> index e3c7b4652da5..abd43c08423e 100644
> --- a/ip/iplink_vrf.c
> +++ b/ip/iplink_vrf.c
> @@ -96,3 +96,56 @@ struct link_util vrf_slave_link_util = {
>   .print_opt  = vrf_slave_print_opt,
>   .slave  = true,
>  };
> +
> +bool name_is_vrf(char *name)

Why not?
bool name_is_vrf(const char *name)

> +{
> + struct {
> + struct nlmsghdr n;
> + struct ifinfomsgi;
> + charbuf[1024];
> + } req = {
> + .n = {
> + .nlmsg_len   = NLMSG_LENGTH(sizeof(struct ifinfomsg)),
> + .nlmsg_flags = NLM_F_REQUEST,
> + .nlmsg_type  = RTM_GETLINK,
> + },
> + .i = {
> + .ifi_family  = preferred_family,
> + },
> + };
> + struct {
> + struct nlmsghdr n;
> + char buf[8192];
> + } answer;
> + struct rtattr *tb[IFLA_MAX+1];
> + struct rtattr *li[IFLA_INFO_MAX+1];
> + struct ifinfomsg *ifi;
> + int len;
> +
> + addattr_l(, sizeof(req), IFLA_IFNAME, name, strlen(name) + 1);
> +
> + if (rtnl_talk(, , , sizeof(answer)) < 0)
> + goto err;
Just return false instead of all these goto's?
Also you might want to give some indication of error.

> +
> + ifi = NLMSG_DATA();
> + len = answer.n.nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));
> + if (len < 0) {
> + fprintf(stderr, "BUG: Invalid response to link query.\n");
> + goto err;
> + }
> +
> + parse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);
> +
> + if (!tb[IFLA_LINKINFO])
> + goto err;
> +
> + parse_rtattr_nested(li, IFLA_INFO_MAX, tb[IFLA_LINKINFO]);
> +
> + if (!li[IFLA_INFO_KIND])
> + goto err;
> +
> + return strcmp(RTA_DATA(li[IFLA_INFO_KIND]), "vrf") == 0;
> +
> +err:
> + return false;
> +}


[PATCH iproute2 1/6] ip vrf: Add name_is_vrf

2016-06-27 Thread David Ahern
Add name_is_vrf function to determine if given name corresponds to a
VRF device.

Signed-off-by: David Ahern 
---
 ip/ip_common.h  |  2 ++
 ip/iplink_vrf.c | 53 +
 2 files changed, 55 insertions(+)

diff --git a/ip/ip_common.h b/ip/ip_common.h
index e8da9e034b15..410eb135774a 100644
--- a/ip/ip_common.h
+++ b/ip/ip_common.h
@@ -90,6 +90,8 @@ struct link_util *get_link_slave_kind(const char *slave_kind);
 
 void br_dump_bridge_id(const struct ifla_bridge_id *id, char *buf, size_t len);
 
+bool name_is_vrf(char *name);
+
 #ifndefINFINITY_LIFE_TIME
 #define INFINITY_LIFE_TIME  0xU
 #endif
diff --git a/ip/iplink_vrf.c b/ip/iplink_vrf.c
index e3c7b4652da5..abd43c08423e 100644
--- a/ip/iplink_vrf.c
+++ b/ip/iplink_vrf.c
@@ -96,3 +96,56 @@ struct link_util vrf_slave_link_util = {
.print_opt  = vrf_slave_print_opt,
.slave  = true,
 };
+
+bool name_is_vrf(char *name)
+{
+   struct {
+   struct nlmsghdr n;
+   struct ifinfomsgi;
+   charbuf[1024];
+   } req = {
+   .n = {
+   .nlmsg_len   = NLMSG_LENGTH(sizeof(struct ifinfomsg)),
+   .nlmsg_flags = NLM_F_REQUEST,
+   .nlmsg_type  = RTM_GETLINK,
+   },
+   .i = {
+   .ifi_family  = preferred_family,
+   },
+   };
+   struct {
+   struct nlmsghdr n;
+   char buf[8192];
+   } answer;
+   struct rtattr *tb[IFLA_MAX+1];
+   struct rtattr *li[IFLA_INFO_MAX+1];
+   struct ifinfomsg *ifi;
+   int len;
+
+   addattr_l(, sizeof(req), IFLA_IFNAME, name, strlen(name) + 1);
+
+   if (rtnl_talk(, , , sizeof(answer)) < 0)
+   goto err;
+
+   ifi = NLMSG_DATA();
+   len = answer.n.nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));
+   if (len < 0) {
+   fprintf(stderr, "BUG: Invalid response to link query.\n");
+   goto err;
+   }
+
+   parse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);
+
+   if (!tb[IFLA_LINKINFO])
+   goto err;
+
+   parse_rtattr_nested(li, IFLA_INFO_MAX, tb[IFLA_LINKINFO]);
+
+   if (!li[IFLA_INFO_KIND])
+   goto err;
+
+   return strcmp(RTA_DATA(li[IFLA_INFO_KIND]), "vrf") == 0;
+
+err:
+   return false;
+}
-- 
2.1.4



[PATCH iproute2 1/6] ip vrf: Add name_is_vrf

2016-06-14 Thread David Ahern
Add name_is_vrf function to determine if given name corresponds to a
VRF device.

Signed-off-by: David Ahern 
---
 ip/ip_common.h  |  2 ++
 ip/iplink_vrf.c | 53 +
 2 files changed, 55 insertions(+)

diff --git a/ip/ip_common.h b/ip/ip_common.h
index e8da9e034b15..410eb135774a 100644
--- a/ip/ip_common.h
+++ b/ip/ip_common.h
@@ -90,6 +90,8 @@ struct link_util *get_link_slave_kind(const char *slave_kind);
 
 void br_dump_bridge_id(const struct ifla_bridge_id *id, char *buf, size_t len);
 
+bool name_is_vrf(char *name);
+
 #ifndefINFINITY_LIFE_TIME
 #define INFINITY_LIFE_TIME  0xU
 #endif
diff --git a/ip/iplink_vrf.c b/ip/iplink_vrf.c
index e3c7b4652da5..abd43c08423e 100644
--- a/ip/iplink_vrf.c
+++ b/ip/iplink_vrf.c
@@ -96,3 +96,56 @@ struct link_util vrf_slave_link_util = {
.print_opt  = vrf_slave_print_opt,
.slave  = true,
 };
+
+bool name_is_vrf(char *name)
+{
+   struct {
+   struct nlmsghdr n;
+   struct ifinfomsgi;
+   charbuf[1024];
+   } req = {
+   .n = {
+   .nlmsg_len   = NLMSG_LENGTH(sizeof(struct ifinfomsg)),
+   .nlmsg_flags = NLM_F_REQUEST,
+   .nlmsg_type  = RTM_GETLINK,
+   },
+   .i = {
+   .ifi_family  = preferred_family,
+   },
+   };
+   struct {
+   struct nlmsghdr n;
+   char buf[8192];
+   } answer;
+   struct rtattr *tb[IFLA_MAX+1];
+   struct rtattr *li[IFLA_INFO_MAX+1];
+   struct ifinfomsg *ifi;
+   int len;
+
+   addattr_l(, sizeof(req), IFLA_IFNAME, name, strlen(name) + 1);
+
+   if (rtnl_talk(, , , sizeof(answer)) < 0)
+   goto err;
+
+   ifi = NLMSG_DATA();
+   len = answer.n.nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));
+   if (len < 0) {
+   fprintf(stderr, "BUG: Invalid response to link query.\n");
+   goto err;
+   }
+
+   parse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);
+
+   if (!tb[IFLA_LINKINFO])
+   goto err;
+
+   parse_rtattr_nested(li, IFLA_INFO_MAX, tb[IFLA_LINKINFO]);
+
+   if (!li[IFLA_INFO_KIND])
+   goto err;
+
+   return strcmp(RTA_DATA(li[IFLA_INFO_KIND]), "vrf") == 0;
+
+err:
+   return false;
+}
-- 
2.1.4