]>
git.proxmox.com Git - mirror_frr.git/blob - isisd/isis_misc.c
2 * IS-IS Rout(e)ing protocol - isis_misc.h
3 * Miscellanous routines
5 * Copyright (C) 2001,2002 Sampo Saaristo
6 * Tampere University of Technology
7 * Institute of Communications Engineering
9 * This program is free software; you can redistribute it and/or modify it
10 * under the terms of the GNU General Public Licenseas published by the Free
11 * Software Foundation; either version 2 of the License, or (at your option)
14 * This program is distributed in the hope that it will be useful,but WITHOUT
15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
19 * You should have received a copy of the GNU General Public License along
20 * with this program; if not, write to the Free Software Foundation, Inc.,
21 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
29 #include <sys/utsname.h>
37 #include "isisd/dict.h"
38 #include "isisd/isis_constants.h"
39 #include "isisd/isis_common.h"
40 #include "isisd/isis_circuit.h"
41 #include "isisd/isisd.h"
42 #include "isisd/isis_misc.h"
44 #include "isisd/isis_tlv.h"
45 #include "isisd/isis_lsp.h"
46 #include "isisd/isis_constants.h"
47 #include "isisd/isis_adjacency.h"
49 /* staticly assigned vars for printing purposes */
50 struct in_addr new_prefix
;
51 /* len of xxxx.xxxx.xxxx + place for #0 termination */
53 /* len of xxxx.xxxx.xxxx + place for #0 termination */
55 /* len of xx.xxxx.xxxx.xxxx.xxxx.xxxx.xxxx.xxxx.xxxx.xxxx.xx */
57 /* + place for #0 termination */
58 /* len of xxxx.xxxx.xxxx.xx.xx + place for #0 termination */
60 /* len of xxYxxMxWxdxxhxxmxxs + place for #0 termination */
65 * This converts the isonet to its printable format
68 isonet_print (u_char
* from
, int len
)
80 sprintf (pos
, "%02x", *(from
+ i
));
86 { /* No dot at the end of address */
87 sprintf (pos
, "%02x", *(from
+ i
));
92 sprintf (pos
, "%02x.", *(from
+ i
));
103 * Returns 0 on error, length of buff on ok
104 * extract dot from the dotted str, and insert all the number in a buff
107 dotformat2buff (u_char
* buff
, u_char
* dotted
)
110 u_char
*pos
= dotted
;
115 dotlen
= strlen (dotted
);
118 /* this can't be an iso net, its too long */
122 while ((pos
- dotted
) < dotlen
&& len
< 20)
126 /* we expect the . at 2, and than every 5 */
127 if ((pos
- dotted
) != nextdotpos
)
136 /* we must have at least two chars left here */
137 if (dotlen
- (pos
- dotted
) < 2)
143 if ((isxdigit ((int) *pos
)) && (isxdigit ((int) *(pos
+ 1))))
145 memcpy (number
, pos
, 2);
154 *(buff
+ len
) = (char) strtol (number
, NULL
, 16);
162 * conversion of XXXX.XXXX.XXXX to memory
165 sysid2buff (u_char
* buff
, u_char
* dotted
)
168 u_char
*pos
= dotted
;
172 // surely not a sysid_string if not 14 length
173 if (strlen (dotted
) != 14)
178 while (len
< ISIS_SYS_ID_LEN
)
182 /* the . is not positioned correctly */
183 if (((pos
- dotted
) != 4) && ((pos
- dotted
) != 9))
191 if ((isxdigit ((int) *pos
)) && (isxdigit ((int) *(pos
+ 1))))
193 memcpy (number
, pos
, 2);
202 *(buff
+ len
) = (char) strtol (number
, NULL
, 16);
211 * converts the nlpids struct (filled by TLV #129)
216 nlpid2string (struct nlpids
*nlpids
)
218 char *pos
= nlpidstring
;
221 for (i
= 0; i
< nlpids
->count
; i
++)
223 switch (nlpids
->nlpids
[i
])
226 pos
+= sprintf (pos
, "IPv4");
229 pos
+= sprintf (pos
, "IPv6");
232 pos
+= sprintf (pos
, "SNAP");
235 pos
+= sprintf (pos
, "CLNP");
238 pos
+= sprintf (pos
, "ES-IS");
241 pos
+= sprintf (pos
, "unknown");
244 if (nlpids
->count
- i
> 1)
245 pos
+= sprintf (pos
, ", ");
255 * supports the given af ?
258 speaks (struct nlpids
*nlpids
, int family
)
262 if (nlpids
== (struct nlpids
*) NULL
)
264 for (i
= 0; i
< nlpids
->count
; i
++)
266 if (family
== AF_INET
&& nlpids
->nlpids
[i
] == NLPID_IP
)
268 if (family
== AF_INET6
&& nlpids
->nlpids
[i
] == NLPID_IPV6
)
276 * Returns 0 on error, IS-IS Circuit Type on ok
279 string2circuit_t (u_char
* str
)
285 if (!strcmp (str
, "level-1"))
288 if (!strcmp (str
, "level-2-only") || !strcmp (str
, "level-2"))
291 if (!strcmp (str
, "level-1-2"))
292 return IS_LEVEL_1_AND_2
;
298 circuit_t2string (int circuit_t
)
306 case IS_LEVEL_1_AND_2
:
312 return NULL
; /* not reached */
316 syst2string (int type
)
320 case ISIS_SYSTYPE_ES
:
322 case ISIS_SYSTYPE_IS
:
324 case ISIS_SYSTYPE_L1_IS
:
326 case ISIS_SYSTYPE_L2_IS
:
332 return NULL
; /* not reached */
336 * Print functions - we print to static vars
339 snpa_print (u_char
* from
)
347 while (i
< ETH_ALEN
- 1)
351 sprintf (pos
, "%02x.", *(from
+ i
));
356 sprintf (pos
, "%02x", *(from
+ i
));
363 sprintf (pos
, "%02x", *(from
+ (ISIS_SYS_ID_LEN
- 1)));
371 sysid_print (u_char
* from
)
379 while (i
< ISIS_SYS_ID_LEN
- 1)
383 sprintf (pos
, "%02x.", *(from
+ i
));
388 sprintf (pos
, "%02x", *(from
+ i
));
395 sprintf (pos
, "%02x", *(from
+ (ISIS_SYS_ID_LEN
- 1)));
403 rawlspid_print (u_char
* from
)
408 memcpy (pos
, sysid_print (from
), 15);
410 sprintf (pos
, ".%02x", LSP_PSEUDO_ID (from
));
412 sprintf (pos
, "-%02x", LSP_FRAGMENT (from
));
421 time2string (u_int32_t time
)
423 char *pos
= datestring
;
429 if (time
/ SECS_PER_YEAR
)
430 pos
+= sprintf (pos
, "%uY", time
/ SECS_PER_YEAR
);
431 rest
= time
% SECS_PER_YEAR
;
432 if (rest
/ SECS_PER_MONTH
)
433 pos
+= sprintf (pos
, "%uM", rest
/ SECS_PER_MONTH
);
434 rest
= rest
% SECS_PER_MONTH
;
435 if (rest
/ SECS_PER_WEEK
)
436 pos
+= sprintf (pos
, "%uw", rest
/ SECS_PER_WEEK
);
437 rest
= rest
% SECS_PER_WEEK
;
438 if (rest
/ SECS_PER_DAY
)
439 pos
+= sprintf (pos
, "%ud", rest
/ SECS_PER_DAY
);
440 rest
= rest
% SECS_PER_DAY
;
441 if (rest
/ SECS_PER_HOUR
)
442 pos
+= sprintf (pos
, "%uh", rest
/ SECS_PER_HOUR
);
443 rest
= rest
% SECS_PER_HOUR
;
444 if (rest
/ SECS_PER_MINUTE
)
445 pos
+= sprintf (pos
, "%um", rest
/ SECS_PER_MINUTE
);
446 rest
= rest
% SECS_PER_MINUTE
;
448 pos
+= sprintf (pos
, "%us", rest
);
456 * routine to decrement a timer by a random
459 * first argument is the timer and the second is
463 isis_jitter (unsigned long timer
, unsigned long jitter
)
473 * randomizing just the percent value provides
474 * no good random numbers - hence the spread
475 * to RANDOM_SPREAD (100000), which is ok as
476 * most IS-IS timers are no longer than 16 bit
479 j
= 1 + (int) ((RANDOM_SPREAD
* rand ()) / (RAND_MAX
+ 1.0));
481 k
= timer
- (timer
* (100 - jitter
)) / 100;
483 timer
= timer
- (k
* j
/ RANDOM_SPREAD
);
489 newprefix2inaddr (u_char
* prefix_start
, u_char prefix_masklen
)
491 memset (&new_prefix
, 0, sizeof (new_prefix
));
492 memcpy (&new_prefix
, prefix_start
, (prefix_masklen
& 0x3F) ?
493 ((((prefix_masklen
& 0x3F) - 1) >> 3) + 1) : 0);
498 * Returns host.name if any, otherwise
499 * it returns the system hostname.
504 static struct utsname names
;
505 const char *hostname
;
506 extern struct host host
;
508 hostname
= host
.name
;
512 hostname
= names
.nodename
;