1 /* 2 * Copyright (C) 2000 Alfredo Andres Omella. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in 12 * the documentation and/or other materials provided with the 13 * distribution. 14 * 3. The names of the authors may not be used to endorse or promote 15 * products derived from this software without specific prior 16 * written permission. 17 * 18 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 19 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 20 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 21 */ 22 /* 23 * Radius printer routines as specified on: 24 * 25 * RFC 2865: 26 * "Remote Authentication Dial In User Service (RADIUS)" 27 * 28 * RFC 2866: 29 * "RADIUS Accounting" 30 * 31 * RFC 2867: 32 * "RADIUS Accounting Modifications for Tunnel Protocol Support" 33 * 34 * RFC 2868: 35 * "RADIUS Attributes for Tunnel Protocol Support" 36 * 37 * RFC 2869: 38 * "RADIUS Extensions" 39 * 40 * Alfredo Andres Omella (aandres@s21sec.com) v0.1 2000/09/15 41 * 42 * TODO: Among other things to print ok MacIntosh and Vendor values 43 */ 44 45 #ifndef lint 46 static const char rcsid[] = 47 "$Id: print-radius.c,v 1.10.2.2 2002/07/03 16:35:04 fenner Exp $"; 48 #endif 49 50 #ifdef HAVE_CONFIG_H 51 #include "config.h" 52 #endif 53 54 #include <string.h> 55 56 #include <sys/param.h> 57 58 #include <netinet/in.h> 59 60 #include <stdio.h> 61 62 #ifdef TIME_WITH_SYS_TIME 63 #include <time.h> 64 #endif 65 66 #include "interface.h" 67 #include "addrtoname.h" 68 #include "extract.h" 69 70 #define TAM_SIZE(x) (sizeof(x)/sizeof(x[0]) ) 71 72 #define PRINT_HEX(bytes_len, ptr_data) \ 73 while(bytes_len) \ 74 { \ 75 printf("%02X", *ptr_data ); \ 76 ptr_data++; \ 77 bytes_len--; \ 78 } 79 80 81 /* Radius packet codes */ 82 #define RADCMD_ACCESS_REQ 1 /* Access-Request */ 83 #define RADCMD_ACCESS_ACC 2 /* Access-Accept */ 84 #define RADCMD_ACCESS_REJ 3 /* Access-Reject */ 85 #define RADCMD_ACCOUN_REQ 4 /* Accounting-Request */ 86 #define RADCMD_ACCOUN_RES 5 /* Accounting-Response */ 87 #define RADCMD_ACCESS_CHA 11 /* Access-Challenge */ 88 #define RADCMD_STATUS_SER 12 /* Status-Server */ 89 #define RADCMD_STATUS_CLI 13 /* Status-Client */ 90 #define RADCMD_RESERVED 255 /* Reserved */ 91 92 93 /********************************/ 94 /* Begin Radius Attribute types */ 95 /********************************/ 96 #define SERV_TYPE 6 97 #define FRM_IPADDR 8 98 #define LOG_IPHOST 14 99 #define LOG_SERVICE 15 100 #define FRM_IPX 23 101 #define SESSION_TIMEOUT 27 102 #define IDLE_TIMEOUT 28 103 #define FRM_ATALK_LINK 37 104 #define FRM_ATALK_NETWORK 38 105 106 #define ACCT_DELAY 41 107 #define ACCT_SESSION_TIME 46 108 109 #define TUNNEL_TYPE 64 110 #define TUNNEL_MEDIUM 65 111 #define TUNNEL_CLIENT_END 66 112 #define TUNNEL_SERVER_END 67 113 #define TUNNEL_PASS 69 114 115 #define ARAP_PASS 70 116 #define ARAP_FEATURES 71 117 118 #define TUNNEL_PRIV_GROUP 81 119 #define TUNNEL_ASSIGN_ID 82 120 #define TUNNEL_PREFERENCE 83 121 122 #define ARAP_CHALLENGE_RESP 84 123 #define ACCT_INT_INTERVAL 85 124 125 #define TUNNEL_CLIENT_AUTH 90 126 #define TUNNEL_SERVER_AUTH 91 127 /********************************/ 128 /* End Radius Attribute types */ 129 /********************************/ 130 131 132 static void print_attr_string(register u_char *, u_int, u_short ); 133 static void print_attr_num(register u_char *, u_int, u_short ); 134 static void print_attr_address(register u_char *, u_int, u_short); 135 static void print_attr_time(register u_char *, u_int, u_short); 136 static void print_attr_strange(register u_char *, u_int, u_short); 137 138 139 struct radius_hdr { u_int8_t code; /* Radius packet code */ 140 u_int8_t id; /* Radius packet id */ 141 u_int16_t len; /* Radius total length */ 142 u_int8_t auth[16]; /* Authenticator */ 143 }; 144 145 #define MIN_RADIUS_LEN 20 146 147 struct radius_attr { u_int8_t type; /* Attribute type */ 148 u_int8_t len; /* Attribute length */ 149 }; 150 151 152 /* Service-Type Attribute standard values */ 153 static const char *serv_type[]={ NULL, 154 "Login", 155 "Framed", 156 "Callback Login", 157 "Callback Framed", 158 "Outbound", 159 "Administrative", 160 "NAS Prompt", 161 "Authenticate Only", 162 "Callback NAS Prompt", 163 "Call Check", 164 "Callback Administrative", 165 }; 166 167 /* Framed-Protocol Attribute standard values */ 168 static const char *frm_proto[]={ NULL, 169 "PPP", 170 "SLIP", 171 "ARAP", 172 "Gandalf proprietary", 173 "Xylogics IPX/SLIP", 174 "X.75 Synchronous", 175 }; 176 177 /* Framed-Routing Attribute standard values */ 178 static const char *frm_routing[]={ "None", 179 "Send", 180 "Listen", 181 "Send&Listen", 182 }; 183 184 /* Framed-Compression Attribute standard values */ 185 static const char *frm_comp[]={ "None", 186 "VJ TCP/IP", 187 "IPX", 188 "Stac-LZS", 189 }; 190 191 /* Login-Service Attribute standard values */ 192 static const char *login_serv[]={ "Telnet", 193 "Rlogin", 194 "TCP Clear", 195 "PortMaster(proprietary)", 196 "LAT", 197 "X.25-PAD", 198 "X.25-T3POS", 199 "Unassigned", 200 "TCP Clear Quiet", 201 }; 202 203 204 /* Termination-Action Attribute standard values */ 205 static const char *term_action[]={ "Default", 206 "RADIUS-Request", 207 }; 208 209 /* NAS-Port-Type Attribute standard values */ 210 static const char *nas_port_type[]={ "Async", 211 "Sync", 212 "ISDN Sync", 213 "ISDN Async V.120", 214 "ISDN Async V.110", 215 "Virtual", 216 "PIAFS", 217 "HDLC Clear Channel", 218 "X.25", 219 "X.75", 220 "G.3 Fax", 221 "SDSL", 222 "ADSL-CAP", 223 "ADSL-DMT", 224 "ISDN-DSL", 225 "Ethernet", 226 "xDSL", 227 "Cable", 228 "Wireless - Other", 229 "Wireless - IEEE 802.11", 230 }; 231 232 /* Acct-Status-Type Accounting Attribute standard values */ 233 static const char *acct_status[]={ NULL, 234 "Start", 235 "Stop", 236 "Interim-Update", 237 "Unassigned", 238 "Unassigned", 239 "Unassigned", 240 "Accounting-On", 241 "Accounting-Off", 242 "Tunnel-Start", 243 "Tunnel-Stop", 244 "Tunnel-Reject", 245 "Tunnel-Link-Start", 246 "Tunnel-Link-Stop", 247 "Tunnel-Link-Reject", 248 "Failed", 249 }; 250 251 /* Acct-Authentic Accounting Attribute standard values */ 252 static const char *acct_auth[]={ NULL, 253 "RADIUS", 254 "Local", 255 "Remote", 256 }; 257 258 /* Acct-Terminate-Cause Accounting Attribute standard values */ 259 static const char *acct_term[]={ NULL, 260 "User Request", 261 "Lost Carrier", 262 "Lost Service", 263 "Idle Timeout", 264 "Session Timeout", 265 "Admin Reset", 266 "Admin Reboot", 267 "Port Error", 268 "NAS Error", 269 "NAS Request", 270 "NAS Reboot", 271 "Port Unneeded", 272 "Port Preempted", 273 "Port Suspended", 274 "Service Unavailable", 275 "Callback", 276 "User Error", 277 "Host Request", 278 }; 279 280 /* Tunnel-Type Attribute standard values */ 281 static const char *tunnel_type[]={ NULL, 282 "PPTP", 283 "L2F", 284 "L2TP", 285 "ATMP", 286 "VTP", 287 "AH", 288 "IP-IP", 289 "MIN-IP-IP", 290 "ESP", 291 "GRE", 292 "DVS", 293 "IP-in-IP Tunneling", 294 }; 295 296 /* Tunnel-Medium-Type Attribute standard values */ 297 static const char *tunnel_medium[]={ NULL, 298 "IPv4", 299 "IPv6", 300 "NSAP", 301 "HDLC", 302 "BBN 1822", 303 "802", 304 "E.163", 305 "E.164", 306 "F.69", 307 "X.121", 308 "IPX", 309 "Appletalk", 310 "Decnet IV", 311 "Banyan Vines", 312 "E.164 with NSAP subaddress", 313 }; 314 315 /* ARAP-Zone-Access Attribute standard values */ 316 static const char *arap_zone[]={ NULL, 317 "Only access to dfl zone", 318 "Use zone filter inc.", 319 "Not used", 320 "Use zone filter exc.", 321 }; 322 323 static const char *prompt[]={ "No Echo", 324 "Echo", 325 }; 326 327 328 struct attrtype { char *name; /* Attribute name */ 329 const char **subtypes; /* Standard Values (if any) */ 330 u_char siz_subtypes; /* Size of total standard values */ 331 u_char first_subtype; /* First standard value is 0 or 1 */ 332 void (*print_func)(register u_char *, u_int, u_short ); 333 } attr_type[]= 334 { 335 { NULL, NULL, 0, 0, NULL }, 336 { "User", NULL, 0, 0, print_attr_string }, 337 { "Pass", NULL, 0, 0, NULL }, 338 { "CHAP-Pass", NULL, 0, 0, NULL }, 339 { "NAS_ipaddr", NULL, 0, 0, print_attr_address }, 340 { "NAS_port", NULL, 0, 0, print_attr_num }, 341 { "Service_type", serv_type, TAM_SIZE(serv_type)-1, 1, print_attr_num }, 342 { "Framed_proto", frm_proto, TAM_SIZE(frm_proto)-1, 1, print_attr_num }, 343 { "Framed_ipaddr", NULL, 0, 0, print_attr_address }, 344 { "Framed_ipnet", NULL, 0, 0, print_attr_address }, 345 { "Framed_routing", frm_routing, TAM_SIZE(frm_routing), 0, 346 print_attr_num }, 347 { "Filter_id", NULL, 0, 0, print_attr_string }, 348 { "Framed_mtu", NULL, 0, 0, print_attr_num }, 349 { "Framed_compress", frm_comp, TAM_SIZE(frm_comp), 0, print_attr_num }, 350 { "Login_iphost", NULL, 0, 0, print_attr_address }, 351 { "Login_service", login_serv, TAM_SIZE(login_serv), 0, print_attr_num }, 352 { "Login_TCP_port", NULL, 0, 0, print_attr_num }, 353 /*17*/ { "Unassigned", NULL, 0, 0, NULL }, 354 { "Reply", NULL, 0, 0, print_attr_string }, 355 { "Callback-number", NULL, 0, 0, print_attr_string }, 356 { "Callback-id", NULL, 0, 0, print_attr_string }, 357 /*21*/ { "Unassigned", NULL, 0, 0, NULL }, 358 { "Framed_route", NULL, 0, 0, print_attr_string }, 359 { "Framed_ipx_net", NULL, 0, 0, print_attr_num }, 360 { "State", NULL, 0, 0, print_attr_string }, 361 { "Class", NULL, 0, 0, print_attr_string }, 362 { "Vendor_specific", NULL, 0, 0, print_attr_string }, 363 { "Session_timeout", NULL, 0, 0, print_attr_num }, 364 { "Idle_timeout", NULL, 0, 0, print_attr_num }, 365 { "Term_action", term_action, TAM_SIZE(term_action), 0, print_attr_num }, 366 { "Called_station", NULL, 0, 0, print_attr_string }, 367 { "Calling_station", NULL, 0, 0, print_attr_string }, 368 { "NAS_id", NULL, 0, 0, print_attr_string }, 369 { "Proxy_state", NULL, 0, 0, print_attr_string }, 370 { "Login_LAT_service", NULL, 0, 0, print_attr_string }, 371 { "Login_LAT_node", NULL, 0, 0, print_attr_string }, 372 { "Login_LAT_group", NULL, 0, 0, print_attr_string }, 373 { "Framed_atalk_link", NULL, 0, 0, print_attr_num }, 374 { "Framed_atalk_net", NULL, 0, 0, print_attr_num }, 375 { "Framed_atalk_zone", NULL, 0, 0, print_attr_string }, 376 { "Acct_status", acct_status, TAM_SIZE(acct_status)-1, 1, print_attr_num }, 377 { "Acct_delay", NULL, 0, 0, print_attr_num }, 378 { "Acct_in_octets", NULL, 0, 0, print_attr_num }, 379 { "Acct_out_octets", NULL, 0, 0, print_attr_num }, 380 { "Acct_session_id", NULL, 0, 0, print_attr_string }, 381 { "Acct_authentic", acct_auth, TAM_SIZE(acct_auth)-1, 1, print_attr_num }, 382 { "Acct_session_time", NULL, 0, 0, print_attr_num }, 383 { "Acct_in_packets", NULL, 0, 0, print_attr_num }, 384 { "Acct_out_packets", NULL, 0, 0, print_attr_num }, 385 { "Acct_term_cause", acct_term, TAM_SIZE(acct_term)-1, 1, print_attr_num }, 386 { "Acct_multi_session_id", NULL, 0, 0, print_attr_string }, 387 { "Acct_link_count", NULL, 0, 0, print_attr_num }, 388 { "Acct_in_giga", NULL, 0, 0, print_attr_num }, 389 { "Acct_out_giga", NULL, 0, 0, print_attr_num }, 390 /*54*/ { "Unassigned", NULL, 0, 0, NULL }, 391 { "Event_timestamp", NULL, 0, 0, print_attr_time }, 392 /*56*/ { "Unassigned", NULL, 0, 0, NULL }, 393 /*57*/ { "Unassigned", NULL, 0, 0, NULL }, 394 /*58*/ { "Unassigned", NULL, 0, 0, NULL }, 395 /*59*/ { "Unassigned", NULL, 0, 0, NULL }, 396 { "CHAP_challenge", NULL, 0, 0, print_attr_string }, 397 { "NAS_port_type", nas_port_type, TAM_SIZE(nas_port_type), 0, 398 print_attr_num }, 399 { "Port_limit", NULL, 0, 0, print_attr_num }, 400 /*63*/ { "Login_LAT_port", NULL, 0, 0, print_attr_string }, 401 { "Tunnel_type", tunnel_type, TAM_SIZE(tunnel_type)-1, 1, print_attr_num }, 402 { "Tunnel_medium", tunnel_medium, TAM_SIZE(tunnel_medium)-1, 1, 403 print_attr_num }, 404 { "Tunnel_client_end", NULL, 0, 0, print_attr_string }, 405 { "Tunnel_server_end", NULL, 0, 0, print_attr_string }, 406 { "Acct_tunnel_connect", NULL, 0, 0, print_attr_string }, 407 { "Tunnel_pass", NULL, 0, 0, print_attr_string }, 408 { "ARAP_pass", NULL, 0, 0, print_attr_strange }, 409 { "ARAP_feature", NULL, 0, 0, print_attr_strange }, 410 /*72*/ { "ARAP_zone_acces", arap_zone, TAM_SIZE(arap_zone)-1, 1, 411 print_attr_num }, 412 { "ARAP_security", NULL, 0, 0, print_attr_string }, 413 { "ARAP_security_data", NULL, 0, 0, print_attr_string }, 414 { "Password_retry", NULL, 0, 0, print_attr_num }, 415 { "Prompt", prompt, TAM_SIZE(prompt), 0, print_attr_num }, 416 { "Connect_info", NULL, 0, 0, print_attr_string }, 417 { "Config_token", NULL, 0, 0, print_attr_string }, 418 { "EAP_msg", NULL, 0, 0, print_attr_string }, 419 /*80*/ { "Message_auth", NULL, 0, 0, print_attr_string }, 420 { "Tunnel_priv_group", NULL, 0, 0, print_attr_string }, 421 { "Tunnel_assign_id", NULL, 0, 0, print_attr_string }, 422 { "Tunnel_pref", NULL, 0, 0, print_attr_num }, 423 { "ARAP_challenge_resp", NULL, 0, 0, print_attr_strange }, 424 { "Acct_interim_interval", NULL, 0, 0, print_attr_num }, 425 /*86*/ { "Acct_tunnel_pack_lost", NULL, 0, 0, print_attr_num }, 426 { "NAS_port_id", NULL, 0, 0, print_attr_string }, 427 { "Framed_pool", NULL, 0, 0, print_attr_string }, 428 { "Unassigned", NULL, 0, 0, NULL }, 429 { "Tunnel_client_auth_id", NULL, 0, 0, print_attr_string }, 430 { "Tunnel_server_auth_id", NULL, 0, 0, print_attr_string }, 431 /*92*/ { "Unassigned", NULL, 0, 0, NULL }, 432 /*93*/ { "Unassigned", NULL, 0, 0, NULL } 433 }; 434 435 436 /*****************************/ 437 /* Print an attribute string */ 438 /* value pointed by 'data' */ 439 /* and 'length' size. */ 440 /*****************************/ 441 /* Returns nothing. */ 442 /*****************************/ 443 static void 444 print_attr_string(register u_char *data, u_int length, u_short attr_code ) 445 { 446 register u_int i; 447 448 TCHECK2(data[0],length); 449 450 printf("{"); 451 switch(attr_code) 452 { 453 case TUNNEL_PASS: 454 if (*data && (*data <=0x1F) ) 455 printf("Tag[%d] ",*data); 456 data++; 457 printf("Salt[%d] ",EXTRACT_16BITS(data) ); 458 data+=2; 459 length-=2; 460 break; 461 case TUNNEL_CLIENT_END: 462 case TUNNEL_SERVER_END: 463 case TUNNEL_PRIV_GROUP: 464 case TUNNEL_ASSIGN_ID: 465 case TUNNEL_CLIENT_AUTH: 466 case TUNNEL_SERVER_AUTH: 467 if (*data <= 0x1F) 468 { 469 printf("Tag[%d] ",*data); 470 data++; 471 length--; 472 } 473 break; 474 } 475 476 for (i=0; i < length ; i++, data++) 477 printf("%c",(*data < 32 || *data > 128) ? '.' : *data ); 478 479 printf("}"); 480 481 return; 482 483 trunc: 484 printf("|radius"); 485 } 486 487 488 /******************************/ 489 /* Print an attribute numeric */ 490 /* value pointed by 'data' */ 491 /* and 'length' size. */ 492 /******************************/ 493 /* Returns nothing. */ 494 /******************************/ 495 static void 496 print_attr_num(register u_char *data, u_int length, u_short attr_code ) 497 { 498 u_int8_t tag; 499 u_int32_t timeout; 500 501 if (length != 4) 502 { 503 printf("{length %u != 4}", length); 504 return; 505 } 506 507 TCHECK2(data[0],4); 508 /* This attribute has standard values */ 509 if (attr_type[attr_code].siz_subtypes) 510 { 511 static const char **table; 512 u_int32_t data_value; 513 table = attr_type[attr_code].subtypes; 514 515 if ( (attr_code == TUNNEL_TYPE) || (attr_code == TUNNEL_MEDIUM) ) 516 { 517 if (!*data) 518 printf("{Tag[Unused]"); 519 else 520 printf("{Tag[%d]", *data); 521 data++; 522 data_value = EXTRACT_24BITS(data); 523 } 524 else 525 { 526 data_value = EXTRACT_32BITS(data); 527 } 528 if ( data_value <= (attr_type[attr_code].siz_subtypes - 1 + 529 attr_type[attr_code].first_subtype) && 530 data_value >= attr_type[attr_code].first_subtype ) 531 printf("{%s}",table[data_value]); 532 else 533 printf("{#%d}",data_value); 534 } 535 else 536 { 537 switch(attr_code) /* Be aware of special cases... */ 538 { 539 case FRM_IPX: 540 if (EXTRACT_32BITS( data) == 0xFFFFFFFE ) 541 printf("{NAS_select}"); 542 else 543 printf("{%d}",EXTRACT_32BITS( data) ); 544 break; 545 546 case SESSION_TIMEOUT: 547 case IDLE_TIMEOUT: 548 case ACCT_DELAY: 549 case ACCT_SESSION_TIME: 550 case ACCT_INT_INTERVAL: 551 timeout = EXTRACT_32BITS( data); 552 if ( timeout < 60 ) 553 printf( "{%02d secs}", timeout); 554 else 555 { 556 if ( timeout < 3600 ) 557 printf( "{%02d:%02d min}", 558 timeout / 60, timeout % 60); 559 else 560 printf( "{%02d:%02d:%02d hours}", 561 timeout / 3600, (timeout % 3600) / 60, 562 timeout % 60); 563 } 564 break; 565 566 case FRM_ATALK_LINK: 567 if (EXTRACT_32BITS(data) ) 568 printf("{%d}",EXTRACT_32BITS(data) ); 569 else 570 printf("{Unnumbered}" ); 571 break; 572 573 case FRM_ATALK_NETWORK: 574 if (EXTRACT_32BITS(data) ) 575 printf("{%d}",EXTRACT_32BITS(data) ); 576 else 577 printf("{NAS_assign}" ); 578 break; 579 580 case TUNNEL_PREFERENCE: 581 tag = *data; 582 data++; 583 if (tag == 0) 584 printf("{Tag[Unused] %d}",EXTRACT_24BITS(data) ); 585 else 586 printf("{Tag[%d] %d}", tag, EXTRACT_24BITS(data) ); 587 break; 588 589 default: 590 printf("{%d}",EXTRACT_32BITS( data) ); 591 break; 592 593 } /* switch */ 594 595 } /* if-else */ 596 597 return; 598 599 trunc: 600 printf("|radius}"); 601 } 602 603 604 /*****************************/ 605 /* Print an attribute IPv4 */ 606 /* address value pointed by */ 607 /* 'data' and 'length' size. */ 608 /*****************************/ 609 /* Returns nothing. */ 610 /*****************************/ 611 static void 612 print_attr_address(register u_char *data, u_int length, u_short attr_code ) 613 { 614 if (length != 4) 615 { 616 printf("{length %u != 4}", length); 617 return; 618 } 619 620 TCHECK2(data[0],4); 621 622 switch(attr_code) 623 { 624 case FRM_IPADDR: 625 case LOG_IPHOST: 626 if (EXTRACT_32BITS(data) == 0xFFFFFFFF ) 627 printf("{User_select}"); 628 else 629 if (EXTRACT_32BITS(data) == 0xFFFFFFFE ) 630 printf("{NAS_select}"); 631 else 632 printf("{%s}",ipaddr_string(data)); 633 break; 634 635 default: 636 printf("{%s}",ipaddr_string(data) ); 637 break; 638 } 639 640 return; 641 642 trunc: 643 printf("{|radius}"); 644 } 645 646 647 /*************************************/ 648 /* Print an attribute of 'secs since */ 649 /* January 1, 1970 00:00 UTC' value */ 650 /* pointed by 'data' and 'length' */ 651 /* size. */ 652 /*************************************/ 653 /* Returns nothing. */ 654 /*************************************/ 655 static void print_attr_time(register u_char *data, u_int length, u_short attr_code) 656 { 657 time_t attr_time; 658 char string[26]; 659 660 if (length != 4) 661 { 662 printf("{length %u != 4}", length); 663 return; 664 } 665 666 TCHECK2(data[0],4); 667 668 attr_time = EXTRACT_32BITS(data); 669 strlcpy(string, ctime(&attr_time), sizeof(string)); 670 /* Get rid of the newline */ 671 string[24] = '\0'; 672 printf("{%.24s}", string); 673 return; 674 675 trunc: 676 printf("{|radius}"); 677 } 678 679 680 /***********************************/ 681 /* Print an attribute of 'strange' */ 682 /* data format pointed by 'data' */ 683 /* and 'length' size. */ 684 /***********************************/ 685 /* Returns nothing. */ 686 /***********************************/ 687 static void print_attr_strange(register u_char *data, u_int length, u_short attr_code) 688 { 689 u_short len_data; 690 691 switch(attr_code) 692 { 693 case ARAP_PASS: 694 if (length != 16) 695 { 696 printf("{length %u != 16}", length); 697 return; 698 } 699 printf("{User_challenge["); 700 TCHECK2(data[0],8); 701 len_data = 8; 702 PRINT_HEX(len_data, data); 703 printf("] User_resp["); 704 TCHECK2(data[0],8); 705 len_data = 8; 706 PRINT_HEX(len_data, data); 707 printf("]}"); 708 break; 709 710 case ARAP_FEATURES: 711 if (length != 14) 712 { 713 printf("{length %u != 14}", length); 714 return; 715 } 716 TCHECK2(data[0],1); 717 if (*data) 718 printf("{User_can_change_pass"); 719 else 720 printf("{User_cant_change_pass"); 721 data++; 722 TCHECK2(data[0],1); 723 printf(" Min_pass_len[%d]",*data); 724 data++; 725 printf(" Pass_created_at["); 726 TCHECK2(data[0],4); 727 len_data = 4; 728 PRINT_HEX(len_data, data); 729 printf("] Pass_expired_in["); 730 TCHECK2(data[0],4); 731 len_data = 4; 732 PRINT_HEX(len_data, data); 733 printf("] Current_time["); 734 len_data = 4; 735 TCHECK2(data[0],4); 736 PRINT_HEX(len_data, data); 737 printf("]}"); 738 break; 739 740 case ARAP_CHALLENGE_RESP: 741 if (length < 8) 742 { 743 printf("{length %u != 8}", length); 744 return; 745 } 746 printf("{"); 747 TCHECK2(data[0],8); 748 len_data = 8; 749 PRINT_HEX(len_data, data); 750 printf("}"); 751 break; 752 } 753 754 trunc: 755 printf("|radius}"); 756 } 757 758 759 760 static void 761 radius_attr_print(register const u_char *attr, u_int length) 762 { 763 register const struct radius_attr *rad_attr = (struct radius_attr *)attr; 764 765 if (length < 3) 766 { 767 printf(" [|radius]"); 768 return; 769 } 770 771 printf(" Attr[ "); 772 while (length > 0) 773 { 774 if (rad_attr->len == 0) 775 { 776 printf("(zero-length attribute)"); 777 return; 778 } 779 if ( rad_attr->len <= length ) 780 { 781 if ( !rad_attr->type || (rad_attr->type > (TAM_SIZE(attr_type)-1)) ) 782 printf("#%d",rad_attr->type); 783 else 784 { 785 printf(" %s",attr_type[rad_attr->type].name); 786 787 if (rad_attr->len > 2) 788 { 789 if ( attr_type[rad_attr->type].print_func ) 790 (*attr_type[rad_attr->type].print_func)( 791 ((u_char *)(rad_attr+1)), 792 rad_attr->len - 2, rad_attr->type); 793 } 794 } 795 } 796 else 797 { 798 printf(" [|radius]"); 799 return; 800 } 801 length-=(rad_attr->len); 802 rad_attr = (struct radius_attr *)( ((char *)(rad_attr))+rad_attr->len); 803 } 804 805 printf(" ]"); 806 } 807 808 809 void 810 radius_print(const u_char *dat, u_int length) 811 { 812 register const struct radius_hdr *rad; 813 register int i; 814 int len; 815 816 i = min(length, snapend - dat); 817 818 if (i < MIN_RADIUS_LEN) 819 { 820 printf(" [|radius]"); 821 return; 822 } 823 824 rad = (struct radius_hdr *)dat; 825 len = ntohs(rad->len); 826 827 if (len < MIN_RADIUS_LEN) 828 { 829 printf(" [|radius]"); 830 return; 831 } 832 833 if (len < i) 834 i = len; 835 836 i -= MIN_RADIUS_LEN; 837 838 switch (rad->code) 839 { 840 case RADCMD_ACCESS_REQ: 841 printf(" rad-access-req %d", length); 842 break; 843 844 case RADCMD_ACCESS_ACC: 845 printf(" rad-access-accept %d", length); 846 break; 847 848 case RADCMD_ACCESS_REJ: 849 printf(" rad-access-reject %d", length); 850 break; 851 852 case RADCMD_ACCOUN_REQ: 853 printf(" rad-account-req %d", length); 854 break; 855 856 case RADCMD_ACCOUN_RES: 857 printf(" rad-account-resp %d", length); 858 break; 859 860 case RADCMD_ACCESS_CHA: 861 printf(" rad-access-cha %d", length); 862 break; 863 864 case RADCMD_STATUS_SER: 865 printf(" rad-status-serv %d", length); 866 break; 867 868 case RADCMD_STATUS_CLI: 869 printf(" rad-status-cli %d", length); 870 break; 871 872 case RADCMD_RESERVED: 873 printf(" rad-reserved %d", length); 874 break; 875 876 default: 877 printf(" rad-#%d %d", rad->code, length); 878 break; 879 } 880 printf(" [id %d]", rad->id); 881 882 if (i) 883 radius_attr_print( dat + MIN_RADIUS_LEN, i); 884 } 885