]>
Commit | Line | Data |
---|---|---|
718e3744 | 1 | /* BGP dump to ascii converter |
896014f4 DL |
2 | * Copyright (C) 1999 Kunihiro Ishiguro |
3 | * | |
4 | * This file is part of GNU Zebra. | |
5 | * | |
6 | * GNU Zebra is free software; you can redistribute it and/or modify it | |
7 | * under the terms of the GNU General Public License as published by the | |
8 | * Free Software Foundation; either version 2, or (at your option) any | |
9 | * later version. | |
10 | * | |
11 | * GNU Zebra is distributed in the hope that it will be useful, but | |
12 | * WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
14 | * General Public License for more details. | |
15 | * | |
16 | * You should have received a copy of the GNU General Public License along | |
17 | * with this program; see the file COPYING; if not, write to the Free Software | |
18 | * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | |
19 | */ | |
718e3744 | 20 | |
21 | #include <zebra.h> | |
22 | ||
23 | #include "zebra.h" | |
24 | #include "stream.h" | |
25 | #include "log.h" | |
26 | #include "prefix.h" | |
27 | #include "command.h" | |
7625a0de DS |
28 | #include "memory.h" |
29 | #include "privs.h" | |
039f3a34 | 30 | #include "filter.h" |
718e3744 | 31 | |
32 | #include "bgpd/bgpd.h" | |
33 | #include "bgpd/bgp_dump.h" | |
34 | #include "bgpd/bgp_attr.h" | |
35 | #include "bgpd/bgp_aspath.h" | |
36 | ||
7625a0de DS |
37 | /* privileges */ |
38 | static zebra_capabilities_t _caps_p [] = | |
39 | { | |
40 | ZCAP_BIND, | |
41 | ZCAP_NET_RAW, | |
42 | ZCAP_NET_ADMIN, | |
43 | }; | |
44 | ||
45 | struct zebra_privs_t bgpd_privs = | |
46 | { | |
b2f36157 DL |
47 | #if defined(FRR_USER) && defined(FRR_GROUP) |
48 | .user = FRR_USER, | |
49 | .group = FRR_GROUP, | |
7625a0de DS |
50 | #endif |
51 | #ifdef VTY_GROUP | |
52 | .vty_group = VTY_GROUP, | |
53 | #endif | |
54 | .caps_p = _caps_p, | |
55 | .cap_num_p = array_size(_caps_p), | |
56 | .cap_num_i = 0, | |
57 | }; | |
58 | ||
718e3744 | 59 | enum MRT_MSG_TYPES { |
60 | MSG_NULL, | |
61 | MSG_START, /* sender is starting up */ | |
62 | MSG_DIE, /* receiver should shut down */ | |
63 | MSG_I_AM_DEAD, /* sender is shutting down */ | |
64 | MSG_PEER_DOWN, /* sender's peer is down */ | |
65 | MSG_PROTOCOL_BGP, /* msg is a BGP packet */ | |
66 | MSG_PROTOCOL_RIP, /* msg is a RIP packet */ | |
67 | MSG_PROTOCOL_IDRP, /* msg is an IDRP packet */ | |
68 | MSG_PROTOCOL_RIPNG, /* msg is a RIPNG packet */ | |
69 | MSG_PROTOCOL_BGP4PLUS, /* msg is a BGP4+ packet */ | |
70 | MSG_PROTOCOL_BGP4PLUS_01, /* msg is a BGP4+ (draft 01) packet */ | |
71 | MSG_PROTOCOL_OSPF, /* msg is an OSPF packet */ | |
72 | MSG_TABLE_DUMP /* routing table dump */ | |
73 | }; | |
74 | ||
7625a0de | 75 | static int |
718e3744 | 76 | attr_parse (struct stream *s, u_int16_t len) |
77 | { | |
78 | u_int flag; | |
79 | u_int type; | |
80 | u_int16_t length; | |
81 | u_int16_t lim; | |
82 | ||
83 | lim = s->getp + len; | |
84 | ||
7625a0de | 85 | printf ("attr_parse s->getp %zd, len %d, lim %d\n", s->getp, len, lim); |
718e3744 | 86 | |
87 | while (s->getp < lim) | |
88 | { | |
89 | flag = stream_getc (s); | |
90 | type = stream_getc (s); | |
91 | ||
7625a0de | 92 | if (flag & BGP_ATTR_FLAG_EXTLEN) |
718e3744 | 93 | length = stream_getw (s); |
94 | else | |
95 | length = stream_getc (s); | |
96 | ||
97 | printf ("FLAG: %d\n", flag); | |
98 | printf ("TYPE: %d\n", type); | |
99 | printf ("Len: %d\n", length); | |
100 | ||
101 | switch (type) | |
102 | { | |
103 | case BGP_ATTR_ORIGIN: | |
104 | { | |
105 | u_char origin; | |
106 | origin = stream_getc (s); | |
107 | printf ("ORIGIN: %d\n", origin); | |
108 | } | |
109 | break; | |
110 | case BGP_ATTR_AS_PATH: | |
111 | { | |
7625a0de DS |
112 | struct aspath *aspath; |
113 | ||
114 | aspath = aspath_parse (s, length, 1); | |
115 | printf ("ASPATH: %s\n", aspath->str); | |
116 | aspath_free(aspath); | |
718e3744 | 117 | } |
118 | break; | |
7625a0de | 119 | case BGP_ATTR_NEXT_HOP: |
718e3744 | 120 | { |
121 | struct in_addr nexthop; | |
122 | nexthop.s_addr = stream_get_ipv4 (s); | |
123 | printf ("NEXTHOP: %s\n", inet_ntoa (nexthop)); | |
718e3744 | 124 | } |
125 | break; | |
126 | default: | |
7625a0de | 127 | stream_getw_from (s, length); |
718e3744 | 128 | break; |
129 | } | |
130 | } | |
131 | ||
132 | return 0; | |
133 | } | |
134 | ||
135 | int | |
136 | main (int argc, char **argv) | |
137 | { | |
138 | int ret; | |
139 | FILE *fp; | |
140 | struct stream *s; | |
141 | time_t now; | |
142 | int type; | |
143 | int subtype; | |
7625a0de | 144 | size_t len; |
718e3744 | 145 | int source_as; |
146 | int dest_as; | |
b892f1dd | 147 | ifindex_t ifindex; |
718e3744 | 148 | int family; |
149 | struct in_addr sip; | |
150 | struct in_addr dip; | |
151 | u_int16_t viewno, seq_num; | |
152 | struct prefix_ipv4 p; | |
153 | ||
154 | s = stream_new (10000); | |
155 | ||
156 | if (argc != 2) | |
157 | { | |
158 | fprintf (stderr, "Usage: %s FILENAME\n", argv[0]); | |
159 | exit (1); | |
160 | } | |
161 | fp = fopen (argv[1], "r"); | |
162 | if (!fp) | |
163 | { | |
1db63918 DS |
164 | fprintf (stdout,"%% Can't open configuration file %s due to '%s'.\n", |
165 | argv[1], safe_strerror(errno)); | |
718e3744 | 166 | exit (1); |
167 | } | |
168 | ||
169 | while (1) | |
170 | { | |
171 | stream_reset (s); | |
172 | ||
173 | ret = fread (s->data, 12, 1, fp); | |
7625a0de | 174 | if (!ret || feof (fp)) |
718e3744 | 175 | { |
176 | printf ("END OF FILE\n"); | |
177 | break; | |
178 | } | |
179 | if (ferror (fp)) | |
180 | { | |
181 | printf ("ERROR OF FREAD\n"); | |
182 | break; | |
183 | } | |
184 | ||
185 | /* Extract header. */ | |
186 | now = stream_getl (s); | |
187 | type = stream_getw (s); | |
188 | subtype = stream_getw (s); | |
189 | len = stream_getl (s); | |
190 | ||
191 | printf ("TIME: %s", ctime (&now)); | |
192 | ||
193 | /* printf ("TYPE: %d/%d\n", type, subtype); */ | |
194 | ||
195 | if (type == MSG_PROTOCOL_BGP4MP) | |
196 | printf ("TYPE: BGP4MP"); | |
4db5d90a AF |
197 | else if (type == MSG_PROTOCOL_BGP4MP_ET) |
198 | printf ("TYPE: BGP4MP_ET"); | |
718e3744 | 199 | else if (type == MSG_TABLE_DUMP) |
200 | printf ("TYPE: MSG_TABLE_DUMP"); | |
201 | else | |
202 | printf ("TYPE: Unknown %d", type); | |
203 | ||
204 | if (type == MSG_TABLE_DUMP) | |
205 | switch (subtype) | |
206 | { | |
207 | case AFI_IP: | |
208 | printf ("/AFI_IP\n"); | |
209 | break; | |
210 | case AFI_IP6: | |
211 | printf ("/AFI_IP6\n"); | |
212 | break; | |
213 | default: | |
214 | printf ("/UNKNOWN %d", subtype); | |
215 | break; | |
216 | } | |
217 | else | |
218 | { | |
219 | switch (subtype) | |
220 | { | |
221 | case BGP4MP_STATE_CHANGE: | |
222 | printf ("/CHANGE\n"); | |
223 | break; | |
224 | case BGP4MP_MESSAGE: | |
225 | printf ("/MESSAGE\n"); | |
226 | break; | |
227 | case BGP4MP_ENTRY: | |
228 | printf ("/ENTRY\n"); | |
229 | break; | |
230 | case BGP4MP_SNAPSHOT: | |
231 | printf ("/SNAPSHOT\n"); | |
232 | break; | |
233 | default: | |
234 | printf ("/UNKNOWN %d", subtype); | |
235 | break; | |
236 | } | |
237 | } | |
238 | ||
7625a0de | 239 | printf ("len: %zd\n", len); |
718e3744 | 240 | |
c16b6d31 | 241 | fread (s->data + 12, len, 1, fp); |
718e3744 | 242 | if (feof (fp)) |
243 | { | |
244 | printf ("ENDOF FILE 2\n"); | |
245 | break; | |
246 | } | |
247 | if (ferror (fp)) | |
248 | { | |
249 | printf ("ERROR OF FREAD 2\n"); | |
250 | break; | |
251 | } | |
252 | ||
253 | /* printf ("now read %d\n", len); */ | |
254 | ||
255 | if (type == MSG_TABLE_DUMP) | |
256 | { | |
257 | u_char status; | |
258 | time_t originated; | |
259 | struct in_addr peer; | |
260 | u_int16_t attrlen; | |
261 | ||
262 | viewno = stream_getw (s); | |
263 | seq_num = stream_getw (s); | |
264 | printf ("VIEW: %d\n", viewno); | |
265 | printf ("SEQUENCE: %d\n", seq_num); | |
266 | ||
267 | /* start */ | |
268 | while (s->getp < len - 16) | |
269 | { | |
270 | p.prefix.s_addr = stream_get_ipv4 (s); | |
271 | p.prefixlen = stream_getc (s); | |
272 | printf ("PREFIX: %s/%d\n", inet_ntoa (p.prefix), p.prefixlen); | |
273 | ||
274 | status = stream_getc (s); | |
275 | originated = stream_getl (s); | |
276 | peer.s_addr = stream_get_ipv4 (s); | |
277 | source_as = stream_getw(s); | |
278 | ||
279 | printf ("FROM: %s AS%d\n", inet_ntoa (peer), source_as); | |
280 | printf ("ORIGINATED: %s", ctime (&originated)); | |
281 | ||
282 | attrlen = stream_getw (s); | |
283 | printf ("ATTRLEN: %d\n", attrlen); | |
284 | ||
285 | attr_parse (s, attrlen); | |
286 | ||
287 | printf ("STATUS: 0x%x\n", status); | |
288 | } | |
289 | } | |
290 | else | |
291 | { | |
292 | source_as = stream_getw (s); | |
293 | dest_as = stream_getw (s); | |
294 | printf ("source_as: %d\n", source_as); | |
295 | printf ("dest_as: %d\n", dest_as); | |
296 | ||
297 | ifindex = stream_getw (s); | |
298 | family = stream_getw (s); | |
299 | ||
300 | printf ("ifindex: %d\n", ifindex); | |
301 | printf ("family: %d\n", family); | |
302 | ||
303 | sip.s_addr = stream_get_ipv4 (s); | |
304 | dip.s_addr = stream_get_ipv4 (s); | |
305 | ||
306 | printf ("saddr: %s\n", inet_ntoa (sip)); | |
307 | printf ("daddr: %s\n", inet_ntoa (dip)); | |
308 | ||
309 | printf ("\n"); | |
310 | } | |
311 | } | |
312 | fclose (fp); | |
313 | return 0; | |
314 | } |