Re-implement zebra socket reconnecting
[olsrd.git] / src / print_packet.c
1
2 /*
3  * The olsr.org Optimized Link-State Routing daemon(olsrd)
4  * Copyright (c) 2004, Andreas Tonnesen(andreto@olsr.org)
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  * * Redistributions of source code must retain the above copyright
12  *   notice, this list of conditions and the following disclaimer.
13  * * Redistributions in binary form must reproduce the above copyright
14  *   notice, this list of conditions and the following disclaimer in
15  *   the documentation and/or other materials provided with the
16  *   distribution.
17  * * Neither the name of olsr.org, olsrd nor the names of its
18  *   contributors may be used to endorse or promote products derived
19  *   from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
25  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
27  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
29  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
31  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32  * POSSIBILITY OF SUCH DAMAGE.
33  *
34  * Visit http://www.olsr.org for more information.
35  *
36  * If you find this software useful feel free to make a donation
37  * to the project. For more information see the website or contact
38  * the copyright holders.
39  *
40  */
41
42 #include "print_packet.h"
43 #include "ipcalc.h"
44 #include "mantissa.h"
45 #include "defs.h"
46 #include "olsr.h"
47 #include "lq_packet.h"
48 #include "net_olsr.h"
49
50 static void print_messagedump(FILE *, uint8_t *, int16_t);
51
52 static void print_midmsg(FILE *, uint8_t *, int16_t);
53
54 static void print_hnamsg(FILE *, uint8_t *, int16_t);
55
56 static void print_olsr_tcmsg(FILE *, uint8_t *, int16_t);
57
58 static void print_olsr_tcmsg_lq(FILE *, uint8_t *, int16_t);
59
60 static void print_hellomsg(FILE *, uint8_t *, int16_t);
61
62 static void print_hellomsg_lq(FILE *, uint8_t *, int16_t);
63
64 /* Entire packet */
65 int8_t
66 print_olsr_serialized_packet(FILE * handle, union olsr_packet *pkt, uint16_t size, union olsr_ip_addr *from_addr)
67 {
68   int16_t remainsize = size - OLSR_HEADERSIZE;
69   union olsr_message *msg;
70   struct ipaddr_str buf;
71
72   /* Print packet header (no IP4/6 difference) */
73   fprintf(handle, "  ============== OLSR PACKET ==============\n   source: %s\n   length: %d bytes\n   seqno: %d\n\n",
74           from_addr ? olsr_ip_to_string(&buf, from_addr) : "UNKNOWN", ntohs(pkt->v4.olsr_packlen), ntohs(pkt->v4.olsr_seqno));
75
76   /* Check size */
77   if (size != ntohs(pkt->v4.olsr_packlen))
78     fprintf(handle, "   SIZE MISSMATCH(%d != %d)!\n", size, ntohs(pkt->v4.olsr_packlen));
79
80   msg = (union olsr_message *)pkt->v4.olsr_msg;
81
82   /* Print all messages */
83   while ((remainsize > 0) && ntohs(msg->v4.olsr_msgsize)) {
84     print_olsr_serialized_message(handle, msg);
85     remainsize -= ntohs(msg->v4.olsr_msgsize);
86     msg = (union olsr_message *)((char *)msg + ntohs(msg->v4.olsr_msgsize));
87   }
88
89   /* Done */
90   fprintf(handle, "  =========================================\n\n");
91   return 1;
92 }
93
94 /* Single message */
95 int8_t
96 print_olsr_serialized_message(FILE * handle, union olsr_message * msg)
97 {
98   struct ipaddr_str buf;
99
100   fprintf(handle, "   ------------ OLSR MESSAGE ------------\n");
101   fprintf(handle, "    Sender main addr: %s\n", olsr_ip_to_string(&buf, (union olsr_ip_addr *)&msg->v4.originator));
102   fprintf(handle, "    Type: %s, size: %d, vtime: %u ms\n", olsr_msgtype_to_string(msg->v4.olsr_msgtype),
103           ntohs(msg->v4.olsr_msgsize), me_to_reltime(msg->v4.olsr_vtime));
104   fprintf(handle, "    TTL: %d, Hopcnt: %d, seqno: %d\n", (olsr_cnf->ip_version == AF_INET) ? msg->v4.ttl : msg->v6.ttl,
105           (olsr_cnf->ip_version == AF_INET) ? msg->v4.hopcnt : msg->v6.hopcnt,
106           ntohs((olsr_cnf->ip_version == AF_INET) ? msg->v4.seqno : msg->v6.seqno));
107
108   switch (msg->v4.olsr_msgtype) {
109     /* Print functions for individual messagetypes */
110   case (MID_MESSAGE):
111     print_midmsg(handle, (olsr_cnf->ip_version == AF_INET) ? (uint8_t *) & msg->v4.message : (uint8_t *) & msg->v6.message,
112                  ntohs(msg->v4.olsr_msgsize));
113     break;
114   case (HNA_MESSAGE):
115     print_hnamsg(handle, (olsr_cnf->ip_version == AF_INET) ? (uint8_t *) & msg->v4.message : (uint8_t *) & msg->v6.message,
116                  ntohs(msg->v4.olsr_msgsize));
117     break;
118   case (TC_MESSAGE):
119     print_olsr_tcmsg(handle, (olsr_cnf->ip_version == AF_INET) ? (uint8_t *) & msg->v4.message : (uint8_t *) & msg->v6.message,
120                      ntohs(msg->v4.olsr_msgsize));
121     break;
122   case (LQ_TC_MESSAGE):
123     print_olsr_tcmsg_lq(handle,
124                         (olsr_cnf->ip_version == AF_INET) ? (uint8_t *) & msg->v4.message : (uint8_t *) & msg->v6.message,
125                         ntohs(msg->v4.olsr_msgsize));
126     break;
127   case (HELLO_MESSAGE):
128     print_hellomsg(handle, (olsr_cnf->ip_version == AF_INET) ? (uint8_t *) & msg->v4.message : (uint8_t *) & msg->v6.message,
129                    ntohs(msg->v4.olsr_msgsize));
130     break;
131   case (LQ_HELLO_MESSAGE):
132     print_hellomsg_lq(handle, (olsr_cnf->ip_version == AF_INET) ? (uint8_t *) & msg->v4.message : (uint8_t *) & msg->v6.message,
133                       ntohs(msg->v4.olsr_msgsize));
134     break;
135   default:
136     print_messagedump(handle, (uint8_t *) msg, ntohs(msg->v4.olsr_msgsize));
137   }
138
139   fprintf(handle, "   --------------------------------------\n\n");
140   return 1;
141 }
142
143 static void
144 print_messagedump(FILE * handle, uint8_t * msg, int16_t size)
145 {
146   int i, x = 0;
147
148   fprintf(handle, "     Data dump:\n     ");
149   for (i = 0; i < size; i++) {
150     if (x == 4) {
151       x = 0;
152       fprintf(handle, "\n     ");
153     }
154     x++;
155     if (olsr_cnf->ip_version == AF_INET)
156       fprintf(handle, " %-3i ", (u_char) msg[i]);
157     else
158       fprintf(handle, " %-2x ", (u_char) msg[i]);
159   }
160   fprintf(handle, "\n");
161 }
162
163 static void
164 print_hellomsg(FILE * handle, uint8_t * data, int16_t totsize)
165 {
166   union olsr_ip_addr *haddr;
167   int hellosize = totsize - ((olsr_cnf->ip_version == AF_INET) ? OLSR_MSGHDRSZ_IPV4 : OLSR_MSGHDRSZ_IPV6);
168
169   fprintf(handle, "    +Htime: %u ms\n", me_to_reltime(data[2]));
170
171   fprintf(handle, "    +Willingness: %d\n", data[3]);
172
173   if (olsr_cnf->ip_version == AF_INET) {
174     /* IPv4 */
175     struct hellomsg *h;
176     struct hellinfo *hinf;
177
178     h = (struct hellomsg *)data;
179
180     for (hinf = h->hell_info; (char *)hinf < ((char *)data + hellosize);
181          hinf = (struct hellinfo *)((char *)hinf + ntohs(hinf->size))) {
182
183       fprintf(handle, "    ++ Link: %s, Status: %s, Size: %d\n", olsr_link_to_string(EXTRACT_LINK(hinf->link_code)),
184               olsr_status_to_string(EXTRACT_STATUS(hinf->link_code)), ntohs(hinf->size));
185
186       for (haddr = (union olsr_ip_addr *)&hinf->neigh_addr; (char *)haddr < (char *)hinf + ntohs(hinf->size);
187            haddr += sizeof(haddr->v4)) {
188         struct ipaddr_str buf;
189         fprintf(handle, "    ++ %s\n", olsr_ip_to_string(&buf, haddr));
190       }
191     }
192
193   } else {
194     /* IPv6 */
195     struct hellomsg6 *h6;
196     struct hellinfo6 *hinf6;
197
198     h6 = (struct hellomsg6 *)data;
199
200     for (hinf6 = h6->hell_info; (char *)hinf6 < ((char *)data + (hellosize));
201          hinf6 = (struct hellinfo6 *)((char *)hinf6 + ntohs(hinf6->size))) {
202       fprintf(handle, "    ++ Link: %s, Status: %s, Size: %d\n", olsr_link_to_string(EXTRACT_LINK(hinf6->link_code)),
203               olsr_status_to_string(EXTRACT_STATUS(hinf6->link_code)), ntohs(hinf6->size));
204
205       for (haddr = (union olsr_ip_addr *)hinf6->neigh_addr; (char *)haddr < (char *)hinf6 + ntohs(hinf6->size); haddr++) {
206         struct ipaddr_str buf;
207         fprintf(handle, "    ++ %s\n", olsr_ip_to_string(&buf, haddr));
208       }
209     }
210
211   }
212
213 }
214
215 static void
216 print_hellomsg_lq(FILE * handle, uint8_t * data, int16_t totsize)
217 {
218   union olsr_ip_addr *haddr;
219   int hellosize = totsize - ((olsr_cnf->ip_version == AF_INET) ? OLSR_MSGHDRSZ_IPV4 : OLSR_MSGHDRSZ_IPV6);
220
221   fprintf(handle, "    +Htime: %u ms\n", me_to_reltime(data[2]));
222
223   fprintf(handle, "    +Willingness: %d\n", data[3]);
224
225   if (olsr_cnf->ip_version == AF_INET) {
226     /* IPv4 */
227     struct hellomsg *h;
228     struct hellinfo *hinf;
229
230     h = (struct hellomsg *)data;
231
232     for (hinf = h->hell_info; (char *)hinf < ((char *)data + hellosize);
233          hinf = (struct hellinfo *)((char *)hinf + ntohs(hinf->size))) {
234
235       fprintf(handle, "    ++ Link: %s, Status: %s, Size: %d\n", olsr_link_to_string(EXTRACT_LINK(hinf->link_code)),
236               olsr_status_to_string(EXTRACT_STATUS(hinf->link_code)), ntohs(hinf->size));
237
238       for (haddr = (union olsr_ip_addr *)&hinf->neigh_addr; (char *)haddr < (char *)hinf + ntohs(hinf->size);
239            haddr += sizeof(haddr->v4)) {
240         struct ipaddr_str buf;
241         uint8_t *quality = (uint8_t *) haddr + olsr_cnf->ipsize;
242         fprintf(handle, "    ++ %s\n", olsr_ip_to_string(&buf, haddr));
243         fprintf(handle, "    ++ LQ = %d, RLQ = %d\n", quality[0], quality[1]);
244       }
245     }
246
247   } else {
248     /* IPv6 */
249     struct hellomsg6 *h6;
250     struct hellinfo6 *hinf6;
251
252     h6 = (struct hellomsg6 *)data;
253
254     for (hinf6 = h6->hell_info; (char *)hinf6 < ((char *)data + (hellosize));
255          hinf6 = (struct hellinfo6 *)((char *)hinf6 + ntohs(hinf6->size))) {
256       fprintf(handle, "    ++ Link: %s, Status: %s, Size: %d\n", olsr_link_to_string(EXTRACT_LINK(hinf6->link_code)),
257               olsr_status_to_string(EXTRACT_STATUS(hinf6->link_code)), ntohs(hinf6->size));
258
259       for (haddr = (union olsr_ip_addr *)hinf6->neigh_addr; (char *)haddr < (char *)hinf6 + ntohs(hinf6->size) + 4; haddr++) {
260         struct ipaddr_str buf;
261         uint8_t *quality = (uint8_t *) haddr + olsr_cnf->ipsize;
262         fprintf(handle, "    ++ %s\n", olsr_ip_to_string(&buf, haddr));
263         fprintf(handle, "    ++ LQ = %d, RLQ = %d\n", quality[0], quality[1]);
264       }
265     }
266
267   }
268 }
269
270 static void
271 print_olsr_tcmsg_lq(FILE * handle, uint8_t * data, int16_t totsize)
272 {
273   int remsize = totsize - ((olsr_cnf->ip_version == AF_INET) ? OLSR_MSGHDRSZ_IPV4 : OLSR_MSGHDRSZ_IPV6);
274
275   fprintf(handle, "    +ANSN: %d\n", htons(((struct olsr_tcmsg *)data)->ansn));
276
277   data += 4;
278   remsize -= 4;
279
280   while (remsize) {
281     struct ipaddr_str buf;
282     fprintf(handle, "    +Neighbor: %s\n", olsr_ip_to_string(&buf, (union olsr_ip_addr *)(ARM_NOWARN_ALIGN)data));
283     data += olsr_cnf->ipsize;
284     fprintf(handle, "    +LQ: %d, ", *data);
285     data += 1;
286     fprintf(handle, "RLQ: %d\n", *data);
287     data += 3;
288     remsize -= (olsr_cnf->ipsize + 4);
289   }
290
291 }
292
293 static void
294 print_olsr_tcmsg(FILE * handle, uint8_t * data, int16_t totsize)
295 {
296   int remsize = totsize - ((olsr_cnf->ip_version == AF_INET) ? OLSR_MSGHDRSZ_IPV4 : OLSR_MSGHDRSZ_IPV6);
297
298   fprintf(handle, "    +ANSN: %d\n", htons(((struct olsr_tcmsg *)data)->ansn));
299
300   data += 4;
301   remsize -= 4;
302
303   while (remsize) {
304     struct ipaddr_str buf;
305     fprintf(handle, "    +Neighbor: %s\n", olsr_ip_to_string(&buf, (union olsr_ip_addr *)(ARM_NOWARN_ALIGN)data));
306     data += olsr_cnf->ipsize;
307
308     remsize -= olsr_cnf->ipsize;
309   }
310
311 }
312
313 static void
314 print_hnamsg(FILE * handle, uint8_t * data, int16_t totsize)
315 {
316   int remsize = totsize - ((olsr_cnf->ip_version == AF_INET) ? OLSR_MSGHDRSZ_IPV4 : OLSR_MSGHDRSZ_IPV6);
317
318   while (remsize) {
319     struct ipaddr_str buf;
320     fprintf(handle, "    +Network: %s\n", olsr_ip_to_string(&buf, (union olsr_ip_addr *)(ARM_NOWARN_ALIGN)data));
321     data += olsr_cnf->ipsize;
322     fprintf(handle, "    +Netmask: %s\n", olsr_ip_to_string(&buf, (union olsr_ip_addr *)(ARM_NOWARN_ALIGN)data));
323     data += olsr_cnf->ipsize;
324
325     remsize -= (olsr_cnf->ipsize * 2);
326   }
327
328 }
329
330 static void
331 print_midmsg(FILE * handle, uint8_t * data, int16_t totsize)
332 {
333   int remsize = totsize - ((olsr_cnf->ip_version == AF_INET) ? OLSR_MSGHDRSZ_IPV4 : OLSR_MSGHDRSZ_IPV6);
334
335   while (remsize) {
336     struct ipaddr_str buf;
337     fprintf(handle, "    +Alias: %s\n", olsr_ip_to_string(&buf, (union olsr_ip_addr *)(ARM_NOWARN_ALIGN)data));
338     data += olsr_cnf->ipsize;
339     remsize -= olsr_cnf->ipsize;
340   }
341 }
342
343 /*
344  * Local Variables:
345  * c-basic-offset: 2
346  * indent-tabs-mode: nil
347  * End:
348  */