diff mbox series

[iproute2] ip-route: fix json formatting for multipath routing

Message ID 99a4a6ffec5d9e7b508863873bf2097bfbb79ec6.1572534380.git.aclaudi@redhat.com
State Superseded
Delegated to: stephen hemminger
Headers show
Series [iproute2] ip-route: fix json formatting for multipath routing | expand

Commit Message

Andrea Claudi Oct. 31, 2019, 3:09 p.m. UTC
json output for multipath routing is broken due to some non-jsonified
print in print_rta_multipath(). To reproduce the issue:

$ ip route add default \
  nexthop via 192.168.1.1 weight 1 \
  nexthop via 192.168.2.1 weight 1
$ ip -j route | jq
parse error: Invalid numeric literal at line 1, column 58

Fix this opening a "multipath" json array that can contain multiple
route objects, and using print_*() instead of fprintf().

This is the output for the above commands applying this patch:

[
  {
    "dst": "default",
    "flags": [],
    "multipath": [
      {
        "gateway": "192.168.1.1",
        "dev": "wlp61s0",
        "weight": 1,
        "flags": [
          "linkdown"
        ]
      },
      {
        "gateway": "192.168.2.1",
        "dev": "ens1u1",
        "weight": 1,
        "flags": []
      }
    ]
  }
]

Fixes: f48e14880a0e5 ("iproute: refactor multipath print")
Signed-off-by: Andrea Claudi <aclaudi@redhat.com>
Reported-by: Patrick Hagara <phagara@redhat.com>
---
 ip/iproute.c | 23 +++++++++++++++++------
 1 file changed, 17 insertions(+), 6 deletions(-)

Comments

David Ahern Oct. 31, 2019, 4:11 p.m. UTC | #1
On 10/31/19 9:09 AM, Andrea Claudi wrote:
> json output for multipath routing is broken due to some non-jsonified
> print in print_rta_multipath(). To reproduce the issue:
> 
> $ ip route add default \
>   nexthop via 192.168.1.1 weight 1 \
>   nexthop via 192.168.2.1 weight 1
> $ ip -j route | jq
> parse error: Invalid numeric literal at line 1, column 58
> 
> Fix this opening a "multipath" json array that can contain multiple
> route objects, and using print_*() instead of fprintf().
> 
> This is the output for the above commands applying this patch:
> 
> [
>   {
>     "dst": "default",
>     "flags": [],
>     "multipath": [
>       {
>         "gateway": "192.168.1.1",
>         "dev": "wlp61s0",
>         "weight": 1,
>         "flags": [
>           "linkdown"
>         ]
>       },
>       {
>         "gateway": "192.168.2.1",
>         "dev": "ens1u1",
>         "weight": 1,
>         "flags": []
>       }
>     ]
>   }
> ]
> 
> Fixes: f48e14880a0e5 ("iproute: refactor multipath print")
> Signed-off-by: Andrea Claudi <aclaudi@redhat.com>
> Reported-by: Patrick Hagara <phagara@redhat.com>
> ---
>  ip/iproute.c | 23 +++++++++++++++++------
>  1 file changed, 17 insertions(+), 6 deletions(-)
> 

This is fixed -next by 4ecefff3cf25 ("ip: fix ip route show json output
for multipath nexthops"). Stephen can cherry pick it for master
Andrea Claudi Oct. 31, 2019, 4:28 p.m. UTC | #2
On Thu, Oct 31, 2019 at 5:11 PM David Ahern <dsahern@gmail.com> wrote:
>
> On 10/31/19 9:09 AM, Andrea Claudi wrote:
> > json output for multipath routing is broken due to some non-jsonified
> > print in print_rta_multipath(). To reproduce the issue:
> >
> > $ ip route add default \
> >   nexthop via 192.168.1.1 weight 1 \
> >   nexthop via 192.168.2.1 weight 1
> > $ ip -j route | jq
> > parse error: Invalid numeric literal at line 1, column 58
> >
> > Fix this opening a "multipath" json array that can contain multiple
> > route objects, and using print_*() instead of fprintf().
> >
> > This is the output for the above commands applying this patch:
> >
> > [
> >   {
> >     "dst": "default",
> >     "flags": [],
> >     "multipath": [
> >       {
> >         "gateway": "192.168.1.1",
> >         "dev": "wlp61s0",
> >         "weight": 1,
> >         "flags": [
> >           "linkdown"
> >         ]
> >       },
> >       {
> >         "gateway": "192.168.2.1",
> >         "dev": "ens1u1",
> >         "weight": 1,
> >         "flags": []
> >       }
> >     ]
> >   }
> > ]
> >
> > Fixes: f48e14880a0e5 ("iproute: refactor multipath print")
> > Signed-off-by: Andrea Claudi <aclaudi@redhat.com>
> > Reported-by: Patrick Hagara <phagara@redhat.com>
> > ---
> >  ip/iproute.c | 23 +++++++++++++++++------
> >  1 file changed, 17 insertions(+), 6 deletions(-)
> >
>
> This is fixed -next by 4ecefff3cf25 ("ip: fix ip route show json output
> for multipath nexthops"). Stephen can cherry pick it for master

Oops, I overlooked that. Thanks David for pointing this out, please
ignore this and sorry for the noise.
Stephen Hemminger Nov. 1, 2019, 4:37 p.m. UTC | #3
On Thu, 31 Oct 2019 10:11:23 -0600
David Ahern <dsahern@gmail.com> wrote:

> On 10/31/19 9:09 AM, Andrea Claudi wrote:
> > json output for multipath routing is broken due to some non-jsonified
> > print in print_rta_multipath(). To reproduce the issue:
> > 
> > $ ip route add default \
> >   nexthop via 192.168.1.1 weight 1 \
> >   nexthop via 192.168.2.1 weight 1
> > $ ip -j route | jq
> > parse error: Invalid numeric literal at line 1, column 58
> > 
> > Fix this opening a "multipath" json array that can contain multiple
> > route objects, and using print_*() instead of fprintf().
> > 
> > This is the output for the above commands applying this patch:
> > 
> > [
> >   {
> >     "dst": "default",
> >     "flags": [],
> >     "multipath": [
> >       {
> >         "gateway": "192.168.1.1",
> >         "dev": "wlp61s0",
> >         "weight": 1,
> >         "flags": [
> >           "linkdown"
> >         ]
> >       },
> >       {
> >         "gateway": "192.168.2.1",
> >         "dev": "ens1u1",
> >         "weight": 1,
> >         "flags": []
> >       }
> >     ]
> >   }
> > ]
> > 
> > Fixes: f48e14880a0e5 ("iproute: refactor multipath print")
> > Signed-off-by: Andrea Claudi <aclaudi@redhat.com>
> > Reported-by: Patrick Hagara <phagara@redhat.com>
> > ---
> >  ip/iproute.c | 23 +++++++++++++++++------
> >  1 file changed, 17 insertions(+), 6 deletions(-)
> >   
> 
> This is fixed -next by 4ecefff3cf25 ("ip: fix ip route show json output
> for multipath nexthops"). Stephen can cherry pick it for master

Sure, cherry-picked the other commit (it was clean)
diff mbox series

Patch

diff --git a/ip/iproute.c b/ip/iproute.c
index a453385113cb9..4c268c72c5bd6 100644
--- a/ip/iproute.c
+++ b/ip/iproute.c
@@ -649,12 +649,16 @@  static void print_rta_multipath(FILE *fp, const struct rtmsg *r,
 	int len = RTA_PAYLOAD(rta);
 	int first = 1;
 
+	open_json_array(PRINT_JSON, "multipath");
+
 	while (len >= sizeof(*nh)) {
 		struct rtattr *tb[RTA_MAX + 1];
 
 		if (nh->rtnh_len > len)
 			break;
 
+		open_json_object(NULL);
+
 		if (!is_json_context()) {
 			if ((r->rtm_flags & RTM_F_CLONED) &&
 			    r->rtm_type == RTN_MULTICAST) {
@@ -689,22 +693,29 @@  static void print_rta_multipath(FILE *fp, const struct rtmsg *r,
 
 		if ((r->rtm_flags & RTM_F_CLONED) &&
 		    r->rtm_type == RTN_MULTICAST) {
-			fprintf(fp, "%s", ll_index_to_name(nh->rtnh_ifindex));
+			print_string(PRINT_ANY, "dev", "%s",
+				     ll_index_to_name(nh->rtnh_ifindex));
 			if (nh->rtnh_hops != 1)
-				fprintf(fp, "(ttl>%d)", nh->rtnh_hops);
-			fprintf(fp, " ");
+				print_uint(PRINT_ANY, "ttl", "(ttl>%d)",
+					   nh->rtnh_hops);
+			print_string(PRINT_FP, NULL, " ", NULL);
 		} else {
-			fprintf(fp, "dev %s ", ll_index_to_name(nh->rtnh_ifindex));
+			print_string(PRINT_ANY, "dev", "dev %s ",
+				     ll_index_to_name(nh->rtnh_ifindex));
 			if (r->rtm_family != AF_MPLS)
-				fprintf(fp, "weight %d ",
-					nh->rtnh_hops+1);
+				print_uint(PRINT_ANY, "weight", "weight %d ",
+					   nh->rtnh_hops + 1);
 		}
 
 		print_rt_flags(fp, nh->rtnh_flags);
 
 		len -= NLMSG_ALIGN(nh->rtnh_len);
 		nh = RTNH_NEXT(nh);
+
+		close_json_object();
 	}
+
+	close_json_array(PRINT_JSON, "multipath");
 }
 
 int print_route(struct nlmsghdr *n, void *arg)