3 * Copyright (C) James R. Leu 2000
6 * This software is covered under the LGPL, for more
7 * info check out http://www.gnu.org/copyleft/lgpl.html
11 #include <netinet/in.h>
12 #include "ldp_struct.h"
13 #include "ldp_nortel.h"
16 #include "mpls_mm_impl.h"
17 #include "mpls_trace_impl.h"
22 ldp_buf
*ldp_buf_create(int size
)
24 ldp_buf
*b
= (ldp_buf
*) mpls_malloc(sizeof(ldp_buf
));
30 memset(b
, 0 , sizeof(ldp_buf
));
31 c
= (char*) mpls_malloc(size
);
44 b
->current
= b
->buffer
;
49 void ldp_buf_delete(ldp_buf
* b
)
55 void ldp_buf_dump(mpls_instance_handle handle
, ldp_buf
* b
, int size
)
57 unsigned char *buf
= b
->current
;
61 for (i
= 0; i
< size
; i
++) {
62 LDP_TRACE_OUT(handle
, "%02x ", buf
[i
]);
65 LDP_TRACE_OUT(handle
, "\n");
69 LDP_TRACE_OUT(handle
, "\n");
72 int ldp_encode_one_mesg(ldp_global
* g
, uint32_t lsraddr
, int label_space
,
73 ldp_buf
* b
, ldp_mesg
* msg
)
75 ldp_trace_flags type
= LDP_TRACE_FLAG_INIT
;
77 unsigned char *hdrBuf
= b
->buffer
;
78 unsigned char *bodyBuf
= hdrBuf
+ MPLS_LDP_HDRSIZE
;
80 int bodyBuf_size
= b
->total
- MPLS_LDP_HDRSIZE
;
81 int hdrBuf_size
= MPLS_LDP_HDRSIZE
;
86 switch (msg
->u
.generic
.flags
.flags
.msgType
) {
87 case MPLS_INIT_MSGTYPE
:
88 body_size
= Mpls_encodeLdpInitMsg(&msg
->u
.init
, bodyBuf
, bodyBuf_size
);
90 case MPLS_NOT_MSGTYPE
:
91 body_size
= Mpls_encodeLdpNotMsg(&msg
->u
.notif
, bodyBuf
, bodyBuf_size
);
93 case MPLS_KEEPAL_MSGTYPE
:
95 Mpls_encodeLdpKeepAliveMsg(&msg
->u
.keep
, bodyBuf
, bodyBuf_size
);
97 case MPLS_HELLO_MSGTYPE
:
98 body_size
= Mpls_encodeLdpHelloMsg(&msg
->u
.hello
, bodyBuf
, bodyBuf_size
);
100 case MPLS_LBLREQ_MSGTYPE
:
102 Mpls_encodeLdpLblReqMsg(&msg
->u
.request
, bodyBuf
, bodyBuf_size
);
104 case MPLS_LBLMAP_MSGTYPE
:
105 body_size
= Mpls_encodeLdpLblMapMsg(&msg
->u
.map
, bodyBuf
, bodyBuf_size
);
107 case MPLS_ADDR_MSGTYPE
:
108 case MPLS_ADDRWITH_MSGTYPE
:
109 body_size
= Mpls_encodeLdpAdrMsg(&msg
->u
.addr
, bodyBuf
, bodyBuf_size
);
111 case MPLS_LBLWITH_MSGTYPE
:
112 case MPLS_LBLREL_MSGTYPE
:
114 Mpls_encodeLdpLbl_W_R_Msg(&msg
->u
.release
, bodyBuf
, bodyBuf_size
);
116 case MPLS_LBLABORT_MSGTYPE
:
118 Mpls_encodeLdpLblAbortMsg(&msg
->u
.abort
, bodyBuf
, bodyBuf_size
);
128 msg
->header
.protocolVersion
= 1;
129 msg
->header
.pduLength
= body_size
;
130 msg
->header
.pduLength
= body_size
+ MPLS_LDPIDLEN
;
131 msg
->header
.lsrAddress
= lsraddr
;
132 msg
->header
.labelSpace
= label_space
;
134 switch (msg
->u
.generic
.flags
.flags
.msgType
) {
135 case MPLS_INIT_MSGTYPE
:
136 type
= LDP_TRACE_FLAG_INIT
;
137 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_INIT
,
138 printHeader(g
->user_data
, &msg
->header
),
139 printInitMsg(g
->user_data
, &msg
->u
.init
));
141 case MPLS_NOT_MSGTYPE
:
142 type
= LDP_TRACE_FLAG_NOTIF
;
143 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_NOTIF
,
144 printHeader(g
->user_data
, &msg
->header
),
145 printNotMsg(g
->user_data
, &msg
->u
.notif
));
147 case MPLS_KEEPAL_MSGTYPE
:
148 type
= LDP_TRACE_FLAG_PERIODIC
;
149 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_PERIODIC
,
150 printHeader(g
->user_data
, &msg
->header
),
151 printKeepAliveMsg(g
->user_data
, &msg
->u
.keep
));
153 case MPLS_HELLO_MSGTYPE
:
154 type
= LDP_TRACE_FLAG_PERIODIC
;
155 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_PERIODIC
,
156 printHeader(g
->user_data
, &msg
->header
),
157 printHelloMsg(g
->user_data
, &msg
->u
.hello
));
159 case MPLS_LBLREQ_MSGTYPE
:
160 type
= LDP_TRACE_FLAG_LABEL
;
161 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_LABEL
,
162 printHeader(g
->user_data
, &msg
->header
),
163 printLlbReqMsg(g
->user_data
, &msg
->u
.request
));
165 case MPLS_LBLMAP_MSGTYPE
:
166 type
= LDP_TRACE_FLAG_LABEL
;
167 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_LABEL
,
168 printHeader(g
->user_data
, &msg
->header
),
169 printLlbMapMsg(g
->user_data
, &msg
->u
.map
));
171 case MPLS_ADDR_MSGTYPE
:
172 case MPLS_ADDRWITH_MSGTYPE
:
173 type
= LDP_TRACE_FLAG_ADDRESS
;
174 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_ADDRESS
,
175 printHeader(g
->user_data
, &msg
->header
),
176 printAddressMsg(g
->user_data
, &msg
->u
.addr
));
178 case MPLS_LBLWITH_MSGTYPE
:
179 case MPLS_LBLREL_MSGTYPE
:
180 type
= LDP_TRACE_FLAG_LABEL
;
181 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_LABEL
,
182 printHeader(g
->user_data
, &msg
->header
),
183 printLbl_W_R_Msg(g
->user_data
, &msg
->u
.release
));
185 case MPLS_LBLABORT_MSGTYPE
:
186 type
= LDP_TRACE_FLAG_LABEL
;
187 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_LABEL
,
188 printHeader(g
->user_data
, &msg
->header
),
189 printLlbAbortMsg(g
->user_data
, &msg
->u
.abort
));
194 Mpls_encodeLdpMsgHeader(&msg
->header
, hdrBuf
, hdrBuf_size
)) < 0) {
198 b
->current_size
= hdr_size
+ body_size
;
199 b
->current
= b
->buffer
;
200 b
->size
= b
->current_size
;
202 LDP_DUMP_PKT(g
->user_data
, type
, MPLS_TRACE_STATE_SEND
,
203 ldp_buf_dump(g
->user_data
, b
, b
->size
));
208 mpls_return_enum
ldp_decode_header(ldp_global
* g
, ldp_buf
* b
, ldp_mesg
* msg
)
212 LDP_ENTER(g
->user_data
, "ldp_decode_header");
215 Mpls_decodeLdpMsgHeader(&msg
->header
, b
->current
, b
->current_size
);
217 if (encodedSize
< 0) {
218 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_PACKET
,
219 "Failed while decoding HEADER:%d\n", encodedSize
);
220 LDP_EXIT(g
->user_data
, "ldp_decode_header - failure");
224 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_PACKET
, MPLS_TRACE_STATE_RECV
,
225 ldp_buf_dump(g
->user_data
, b
, encodedSize
));
227 b
->current_size
-= encodedSize
;
228 b
->current
+= encodedSize
;
230 LDP_EXIT(g
->user_data
, "ldp_decode_header");
234 int ldp_decode_one_mesg(ldp_global
* g
, ldp_buf
* b
, ldp_mesg
* msg
)
243 LDP_ENTER(g
->user_data
, "ldp_decode_one_mesg");
245 if (msg
->header
.pduLength
> (b
->size
- 4)) {
246 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
247 LDP_TRACE_FLAG_PACKET
, "Buffer too small. Decoding failed\n");
248 LDP_EXIT(g
->user_data
, "ldp_decode_one_mesg - failure");
252 max_mesg_size
= b
->current_size
;
254 /* found the message type */
255 memcpy((u_char
*) & type
, b
->current
, 2);
256 type
= ntohs(type
) & 0x7fff; /* ignore the U bit for now */
258 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_PACKET
,
259 "Found type %x\n", type
);
262 case MPLS_INIT_MSGTYPE
:
264 MPLS_MSGPTR(Init
) = &msg
->u
.init
;
265 encodedSize
= Mpls_decodeLdpInitMsg(MPLS_MSGPARAM(Init
),
266 b
->current
, max_mesg_size
);
267 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_INIT
, MPLS_TRACE_STATE_RECV
,
268 ldp_buf_dump(g
->user_data
, b
, encodedSize
));
269 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
270 LDP_TRACE_FLAG_INIT
, "decodedSize for Init msg = %d\n", encodedSize
);
271 if (encodedSize
< 0) {
272 goto ldp_decode_one_mesg
;
274 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_INIT
,
275 printHeader(g
->user_data
, &msg
->header
),
276 printInitMsg(g
->user_data
, MPLS_MSGPARAM(Init
)));
277 b
->current
+= encodedSize
;
278 mesgSize
+= encodedSize
;
281 case MPLS_NOT_MSGTYPE
:
283 MPLS_MSGPTR(Notif
) = &msg
->u
.notif
;
284 encodedSize
= Mpls_decodeLdpNotMsg(MPLS_MSGPARAM(Notif
),
285 b
->current
, max_mesg_size
);
286 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_NOTIF
, MPLS_TRACE_STATE_RECV
,
287 ldp_buf_dump(g
->user_data
, b
,
288 (encodedSize
< 0) ? max_mesg_size
: encodedSize
));
289 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
, LDP_TRACE_FLAG_NOTIF
,
290 "decodedSize for Notif msg = %d\n", encodedSize
);
291 if (encodedSize
< 0) {
292 goto ldp_decode_one_mesg
;
294 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
295 LDP_TRACE_FLAG_NOTIF
,
296 printHeader(g
->user_data
, &msg
->header
),
297 printNotMsg(g
->user_data
, MPLS_MSGPARAM(Notif
)));
298 b
->current
+= encodedSize
;
299 mesgSize
+= encodedSize
;
302 case MPLS_KEEPAL_MSGTYPE
:
304 MPLS_MSGPTR(KeepAl
) = &msg
->u
.keep
;
305 encodedSize
= Mpls_decodeLdpKeepAliveMsg(MPLS_MSGPARAM(KeepAl
),
306 b
->current
, max_mesg_size
);
307 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_PERIODIC
,
308 MPLS_TRACE_STATE_RECV
, ldp_buf_dump(g
->user_data
, b
, encodedSize
));
309 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
310 LDP_TRACE_FLAG_PERIODIC
,
311 "decodedSize for KeepAlive msg = %d\n", encodedSize
);
312 if (encodedSize
< 0) {
313 goto ldp_decode_one_mesg
;
315 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
316 LDP_TRACE_FLAG_PERIODIC
,
317 printHeader(g
->user_data
, &msg
->header
),
318 printKeepAliveMsg(g
->user_data
, MPLS_MSGPARAM(KeepAl
)));
319 b
->current
+= encodedSize
;
320 mesgSize
+= encodedSize
;
323 case MPLS_HELLO_MSGTYPE
:
325 MPLS_MSGPTR(Hello
) = &msg
->u
.hello
;
326 encodedSize
= Mpls_decodeLdpHelloMsg(MPLS_MSGPARAM(Hello
),
327 b
->current
, max_mesg_size
);
328 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_PERIODIC
,
329 MPLS_TRACE_STATE_RECV
, ldp_buf_dump(g
->user_data
, b
, encodedSize
));
330 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
331 LDP_TRACE_FLAG_PERIODIC
, "decodedSize for Hello msg = %d\n",
333 if (encodedSize
< 0) {
334 goto ldp_decode_one_mesg
;
336 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
337 LDP_TRACE_FLAG_PERIODIC
,
338 printHeader(g
->user_data
, &msg
->header
),
339 printHelloMsg(g
->user_data
, MPLS_MSGPARAM(Hello
)));
340 b
->current
+= encodedSize
;
341 mesgSize
+= encodedSize
;
344 case MPLS_LBLREQ_MSGTYPE
:
346 MPLS_MSGPTR(LblReq
) = &msg
->u
.request
;
347 encodedSize
= Mpls_decodeLdpLblReqMsg(MPLS_MSGPARAM(LblReq
),
348 b
->current
, max_mesg_size
);
349 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_LABEL
, MPLS_TRACE_STATE_RECV
,
350 ldp_buf_dump(g
->user_data
, b
, encodedSize
));
351 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
352 LDP_TRACE_FLAG_LABEL
, "decodedSize for Req msg = %d\n", encodedSize
);
353 if (encodedSize
< 0) {
354 goto ldp_decode_one_mesg
;
356 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
357 LDP_TRACE_FLAG_LABEL
,
358 printHeader(g
->user_data
, &msg
->header
),
359 printLlbReqMsg(g
->user_data
, MPLS_MSGPARAM(LblReq
)));
360 b
->current
+= encodedSize
;
361 mesgSize
+= encodedSize
;
364 case MPLS_LBLMAP_MSGTYPE
:
366 MPLS_MSGPTR(LblMap
) = &msg
->u
.map
;
367 encodedSize
= Mpls_decodeLdpLblMapMsg(MPLS_MSGPARAM(LblMap
),
368 b
->current
, max_mesg_size
);
369 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_LABEL
, MPLS_TRACE_STATE_RECV
,
370 ldp_buf_dump(g
->user_data
, b
, encodedSize
));
371 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
372 LDP_TRACE_FLAG_LABEL
, "decodedSize for Map msg = %d\n", encodedSize
);
373 if (encodedSize
< 0) {
374 goto ldp_decode_one_mesg
;
376 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
377 LDP_TRACE_FLAG_LABEL
,
378 printHeader(g
->user_data
, &msg
->header
),
379 printLlbMapMsg(g
->user_data
, MPLS_MSGPARAM(LblMap
)));
380 b
->current
+= encodedSize
;
381 mesgSize
+= encodedSize
;
384 case MPLS_ADDR_MSGTYPE
:
385 case MPLS_ADDRWITH_MSGTYPE
:
387 MPLS_MSGPTR(Adr
) = &msg
->u
.addr
;
388 encodedSize
= Mpls_decodeLdpAdrMsg(MPLS_MSGPARAM(Adr
),
389 b
->current
, max_mesg_size
);
390 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_ADDRESS
,
391 MPLS_TRACE_STATE_RECV
, ldp_buf_dump(g
->user_data
, b
, encodedSize
));
392 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
393 LDP_TRACE_FLAG_ADDRESS
, "decodedSize for Adr msg = %d\n",
395 if (encodedSize
< 0) {
396 goto ldp_decode_one_mesg
;
398 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
399 LDP_TRACE_FLAG_ADDRESS
,
400 printHeader(g
->user_data
, &msg
->header
),
401 printAddressMsg(g
->user_data
, MPLS_MSGPARAM(Adr
)));
402 b
->current
+= encodedSize
;
403 mesgSize
+= encodedSize
;
406 case MPLS_LBLWITH_MSGTYPE
:
407 case MPLS_LBLREL_MSGTYPE
:
409 MPLS_MSGPTR(Lbl_W_R_
) = &msg
->u
.release
;
410 encodedSize
= Mpls_decodeLdpLbl_W_R_Msg(MPLS_MSGPARAM(Lbl_W_R_
),
411 b
->current
, max_mesg_size
);
412 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_LABEL
, MPLS_TRACE_STATE_RECV
,
413 ldp_buf_dump(g
->user_data
, b
, encodedSize
));
414 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
415 LDP_TRACE_FLAG_LABEL
,
416 "decodedSize for Lbl Release/Mapping msg = %d\n", encodedSize
);
417 if (encodedSize
< 0) {
418 goto ldp_decode_one_mesg
;
420 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
421 LDP_TRACE_FLAG_LABEL
,
422 printHeader(g
->user_data
, &msg
->header
),
423 printLbl_W_R_Msg(g
->user_data
, MPLS_MSGPARAM(Lbl_W_R_
)));
424 b
->current
+= encodedSize
;
425 mesgSize
+= encodedSize
;
428 case MPLS_LBLABORT_MSGTYPE
:
430 MPLS_MSGPTR(LblAbort
) = &msg
->u
.abort
;
431 encodedSize
= Mpls_decodeLdpLblAbortMsg(MPLS_MSGPARAM(LblAbort
),
432 b
->current
, max_mesg_size
);
433 LDP_DUMP_PKT(g
->user_data
, LDP_TRACE_FLAG_LABEL
, MPLS_TRACE_STATE_RECV
,
434 ldp_buf_dump(g
->user_data
, b
, encodedSize
));
435 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
436 LDP_TRACE_FLAG_LABEL
, "decodedSize for Abort msg = %d\n",
438 if (encodedSize
< 0) {
439 goto ldp_decode_one_mesg
;
441 LDP_TRACE_PKT(g
->user_data
, MPLS_TRACE_STATE_RECV
,
442 LDP_TRACE_FLAG_LABEL
,
443 printHeader(g
->user_data
, &msg
->header
),
444 printLlbAbortMsg(g
->user_data
, MPLS_MSGPARAM(LblAbort
)));
445 b
->current
+= encodedSize
;
446 mesgSize
+= encodedSize
;
451 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
452 LDP_TRACE_FLAG_PACKET
, "Unknown message type = %x\n", type
);
453 goto ldp_decode_one_mesg
;
457 LDP_TRACE_LOG(g
->user_data
, MPLS_TRACE_STATE_RECV
,
458 LDP_TRACE_FLAG_PACKET
, "Mesg size: %d (%d)\n", mesgSize
, b
->size
);
460 b
->current_size
-= mesgSize
;
462 LDP_EXIT(g
->user_data
, "ldp_decode_one_mesg");
467 LDP_EXIT(g
->user_data
, "ldp_decode_one_mesg - failure");