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 46static const char rcsid[] _U_ = 47 "$Id: print-radius.c,v 1.27.2.1 2005/09/26 01:02:40 guy Exp $"; 48#endif 49 50#ifdef HAVE_CONFIG_H 51#include "config.h" 52#endif 53 54#include <tcpdump-stdinc.h> 55 56#include <string.h> 57 58#include <stdio.h> 59 60#include "interface.h" 61#include "addrtoname.h" 62#include "extract.h" 63#include "oui.h" 64 65#define TAM_SIZE(x) (sizeof(x)/sizeof(x[0]) ) 66 67#define PRINT_HEX(bytes_len, ptr_data) \ 68 while(bytes_len) \ 69 { \ 70 printf("%02X", *ptr_data ); \ 71 ptr_data++; \ 72 bytes_len--; \ 73 } 74 75 76/* Radius packet codes */ 77#define RADCMD_ACCESS_REQ 1 /* Access-Request */ 78#define RADCMD_ACCESS_ACC 2 /* Access-Accept */ 79#define RADCMD_ACCESS_REJ 3 /* Access-Reject */ 80#define RADCMD_ACCOUN_REQ 4 /* Accounting-Request */ 81#define RADCMD_ACCOUN_RES 5 /* Accounting-Response */ 82#define RADCMD_ACCESS_CHA 11 /* Access-Challenge */ 83#define RADCMD_STATUS_SER 12 /* Status-Server */ 84#define RADCMD_STATUS_CLI 13 /* Status-Client */ 85#define RADCMD_RESERVED 255 /* Reserved */ 86 87static struct tok radius_command_values[] = { 88 { RADCMD_ACCESS_REQ, "Access Request" }, 89 { RADCMD_ACCESS_ACC, "Access Accept" }, 90 { RADCMD_ACCESS_REJ, "Access Reject" }, 91 { RADCMD_ACCOUN_REQ, "Accounting Request" }, 92 { RADCMD_ACCOUN_RES, "Accounting Response" }, 93 { RADCMD_ACCESS_CHA, "Access Challenge" }, 94 { RADCMD_STATUS_SER, "Status Server" }, 95 { RADCMD_STATUS_CLI, "Status Client" }, 96 { RADCMD_RESERVED, "Reserved" }, 97 { 0, NULL} 98}; 99 100/********************************/ 101/* Begin Radius Attribute types */ 102/********************************/ 103#define SERV_TYPE 6 104#define FRM_IPADDR 8 105#define LOG_IPHOST 14 106#define LOG_SERVICE 15 107#define FRM_IPX 23 108#define SESSION_TIMEOUT 27 109#define IDLE_TIMEOUT 28 110#define FRM_ATALK_LINK 37 111#define FRM_ATALK_NETWORK 38 112 113#define ACCT_DELAY 41 114#define ACCT_SESSION_TIME 46 115 116#define TUNNEL_TYPE 64 117#define TUNNEL_MEDIUM 65 118#define TUNNEL_CLIENT_END 66 119#define TUNNEL_SERVER_END 67 120#define TUNNEL_PASS 69 121 122#define ARAP_PASS 70 123#define ARAP_FEATURES 71 124 125#define TUNNEL_PRIV_GROUP 81 126#define TUNNEL_ASSIGN_ID 82 127#define TUNNEL_PREFERENCE 83 128 129#define ARAP_CHALLENGE_RESP 84 130#define ACCT_INT_INTERVAL 85 131 132#define TUNNEL_CLIENT_AUTH 90 133#define TUNNEL_SERVER_AUTH 91 134/********************************/ 135/* End Radius Attribute types */ 136/********************************/ 137 138 139static void print_attr_string(register u_char *, u_int, u_short ); 140static void print_attr_num(register u_char *, u_int, u_short ); 141static void print_vendor_attr(register u_char *, u_int, u_short ); 142static void print_attr_address(register u_char *, u_int, u_short); 143static void print_attr_time(register u_char *, u_int, u_short); 144static void print_attr_strange(register u_char *, u_int, u_short); 145 146 147struct radius_hdr { u_int8_t code; /* Radius packet code */ 148 u_int8_t id; /* Radius packet id */ 149 u_int16_t len; /* Radius total length */ 150 u_int8_t auth[16]; /* Authenticator */ 151 }; 152 153#define MIN_RADIUS_LEN 20 154 155struct radius_attr { u_int8_t type; /* Attribute type */ 156 u_int8_t len; /* Attribute length */ 157 }; 158 159 160/* Service-Type Attribute standard values */ 161static const char *serv_type[]={ NULL, 162 "Login", 163 "Framed", 164 "Callback Login", 165 "Callback Framed", 166 "Outbound", 167 "Administrative", 168 "NAS Prompt", 169 "Authenticate Only", 170 "Callback NAS Prompt", 171 "Call Check", 172 "Callback Administrative", 173 }; 174 175/* Framed-Protocol Attribute standard values */ 176static const char *frm_proto[]={ NULL, 177 "PPP", 178 "SLIP", 179 "ARAP", 180 "Gandalf proprietary", 181 "Xylogics IPX/SLIP", 182 "X.75 Synchronous", 183 }; 184 185/* Framed-Routing Attribute standard values */ 186static const char *frm_routing[]={ "None", 187 "Send", 188 "Listen", 189 "Send&Listen", 190 }; 191 192/* Framed-Compression Attribute standard values */ 193static const char *frm_comp[]={ "None", 194 "VJ TCP/IP", 195 "IPX", 196 "Stac-LZS", 197 }; 198 199/* Login-Service Attribute standard values */ 200static const char *login_serv[]={ "Telnet", 201 "Rlogin", 202 "TCP Clear", 203 "PortMaster(proprietary)", 204 "LAT", 205 "X.25-PAD", 206 "X.25-T3POS", 207 "Unassigned", 208 "TCP Clear Quiet", 209 }; 210 211 212/* Termination-Action Attribute standard values */ 213static const char *term_action[]={ "Default", 214 "RADIUS-Request", 215 }; 216 217/* NAS-Port-Type Attribute standard values */ 218static const char *nas_port_type[]={ "Async", 219 "Sync", 220 "ISDN Sync", 221 "ISDN Async V.120", 222 "ISDN Async V.110", 223 "Virtual", 224 "PIAFS", 225 "HDLC Clear Channel", 226 "X.25", 227 "X.75", 228 "G.3 Fax", 229 "SDSL", 230 "ADSL-CAP", 231 "ADSL-DMT", 232 "ISDN-DSL", 233 "Ethernet", 234 "xDSL", 235 "Cable", 236 "Wireless - Other", 237 "Wireless - IEEE 802.11", 238 }; 239 240/* Acct-Status-Type Accounting Attribute standard values */ 241static const char *acct_status[]={ NULL, 242 "Start", 243 "Stop", 244 "Interim-Update", 245 "Unassigned", 246 "Unassigned", 247 "Unassigned", 248 "Accounting-On", 249 "Accounting-Off", 250 "Tunnel-Start", 251 "Tunnel-Stop", 252 "Tunnel-Reject", 253 "Tunnel-Link-Start", 254 "Tunnel-Link-Stop", 255 "Tunnel-Link-Reject", 256 "Failed", 257 }; 258 259/* Acct-Authentic Accounting Attribute standard values */ 260static const char *acct_auth[]={ NULL, 261 "RADIUS", 262 "Local", 263 "Remote", 264 }; 265 266/* Acct-Terminate-Cause Accounting Attribute standard values */ 267static const char *acct_term[]={ NULL, 268 "User Request", 269 "Lost Carrier", 270 "Lost Service", 271 "Idle Timeout", 272 "Session Timeout", 273 "Admin Reset", 274 "Admin Reboot", 275 "Port Error", 276 "NAS Error", 277 "NAS Request", 278 "NAS Reboot", 279 "Port Unneeded", 280 "Port Preempted", 281 "Port Suspended", 282 "Service Unavailable", 283 "Callback", 284 "User Error", 285 "Host Request", 286 }; 287 288/* Tunnel-Type Attribute standard values */ 289static const char *tunnel_type[]={ NULL, 290 "PPTP", 291 "L2F", 292 "L2TP", 293 "ATMP", 294 "VTP", 295 "AH", 296 "IP-IP", 297 "MIN-IP-IP", 298 "ESP", 299 "GRE", 300 "DVS", 301 "IP-in-IP Tunneling", 302 }; 303 304/* Tunnel-Medium-Type Attribute standard values */ 305static const char *tunnel_medium[]={ NULL, 306 "IPv4", 307 "IPv6", 308 "NSAP", 309 "HDLC", 310 "BBN 1822", 311 "802", 312 "E.163", 313 "E.164", 314 "F.69", 315 "X.121", 316 "IPX", 317 "Appletalk", 318 "Decnet IV", 319 "Banyan Vines", 320 "E.164 with NSAP subaddress", 321 }; 322 323/* ARAP-Zone-Access Attribute standard values */ 324static const char *arap_zone[]={ NULL, 325 "Only access to dfl zone", 326 "Use zone filter inc.", 327 "Not used", 328 "Use zone filter exc.", 329 }; 330 331static const char *prompt[]={ "No Echo", 332 "Echo", 333 }; 334 335 336struct attrtype { const char *name; /* Attribute name */ 337 const char **subtypes; /* Standard Values (if any) */ 338 u_char siz_subtypes; /* Size of total standard values */ 339 u_char first_subtype; /* First standard value is 0 or 1 */ 340 void (*print_func)(register u_char *, u_int, u_short ); 341 } attr_type[]= 342 { 343 { NULL, NULL, 0, 0, NULL }, 344 { "Username", NULL, 0, 0, print_attr_string }, 345 { "Password", NULL, 0, 0, NULL }, 346 { "CHAP Password", NULL, 0, 0, NULL }, 347 { "NAS IP Address", NULL, 0, 0, print_attr_address }, 348 { "NAS Port", NULL, 0, 0, print_attr_num }, 349 { "Service Type", serv_type, TAM_SIZE(serv_type)-1, 1, print_attr_num }, 350 { "Framed Protocol", frm_proto, TAM_SIZE(frm_proto)-1, 1, print_attr_num }, 351 { "Framed IP Address", NULL, 0, 0, print_attr_address }, 352 { "Framed IP Network", NULL, 0, 0, print_attr_address }, 353 { "Framed Routing", frm_routing, TAM_SIZE(frm_routing), 0, print_attr_num }, 354 { "Filter ID", NULL, 0, 0, print_attr_string }, 355 { "Framed MTU", NULL, 0, 0, print_attr_num }, 356 { "Framed Compression", frm_comp, TAM_SIZE(frm_comp), 0, print_attr_num }, 357 { "Login IP Host", NULL, 0, 0, print_attr_address }, 358 { "Login Service", login_serv, TAM_SIZE(login_serv), 0, print_attr_num }, 359 { "Login TCP Port", NULL, 0, 0, print_attr_num }, 360 { "Unassigned", NULL, 0, 0, NULL }, /*17*/ 361 { "Reply", NULL, 0, 0, print_attr_string }, 362 { "Callback-number", NULL, 0, 0, print_attr_string }, 363 { "Callback-ID", NULL, 0, 0, print_attr_string }, 364 { "Unassigned", NULL, 0, 0, NULL }, /*21*/ 365 { "Framed Route", NULL, 0, 0, print_attr_string }, 366 { "Framed IPX Network", NULL, 0, 0, print_attr_num }, 367 { "State", NULL, 0, 0, print_attr_string }, 368 { "Class", NULL, 0, 0, print_attr_string }, 369 { "Vendor Specific", NULL, 0, 0, print_vendor_attr }, 370 { "Session Timeout", NULL, 0, 0, print_attr_num }, 371 { "Idle Timeout", NULL, 0, 0, print_attr_num }, 372 { "Termination Action", term_action, TAM_SIZE(term_action), 0, print_attr_num }, 373 { "Called Station", NULL, 0, 0, print_attr_string }, 374 { "Calling Station", NULL, 0, 0, print_attr_string }, 375 { "NAS ID", NULL, 0, 0, print_attr_string }, 376 { "Proxy State", NULL, 0, 0, print_attr_string }, 377 { "Login LAT Service", NULL, 0, 0, print_attr_string }, 378 { "Login LAT Node", NULL, 0, 0, print_attr_string }, 379 { "Login LAT Group", NULL, 0, 0, print_attr_string }, 380 { "Framed Appletalk Link", NULL, 0, 0, print_attr_num }, 381 { "Framed Appltalk Net", NULL, 0, 0, print_attr_num }, 382 { "Framed Appletalk Zone", NULL, 0, 0, print_attr_string }, 383 { "Accounting Status", acct_status, TAM_SIZE(acct_status)-1, 1, print_attr_num }, 384 { "Accounting Delay", NULL, 0, 0, print_attr_num }, 385 { "Accounting Input Octets", NULL, 0, 0, print_attr_num }, 386 { "Accounting Output Octets", NULL, 0, 0, print_attr_num }, 387 { "Accounting Session ID", NULL, 0, 0, print_attr_string }, 388 { "Accounting Authentication", acct_auth, TAM_SIZE(acct_auth)-1, 1, print_attr_num }, 389 { "Accounting Session Time", NULL, 0, 0, print_attr_num }, 390 { "Accounting Input Packets", NULL, 0, 0, print_attr_num }, 391 { "Accounting Output Packets", NULL, 0, 0, print_attr_num }, 392 { "Accounting Termination Cause", acct_term, TAM_SIZE(acct_term)-1, 1, print_attr_num }, 393 { "Accounting Multilink Session ID", NULL, 0, 0, print_attr_string }, 394 { "Accounting Link Count", NULL, 0, 0, print_attr_num }, 395 { "Accounting Input Giga", NULL, 0, 0, print_attr_num }, 396 { "Accounting Output Giga", NULL, 0, 0, print_attr_num }, 397 { "Unassigned", NULL, 0, 0, NULL }, /*54*/ 398 { "Event Timestamp", NULL, 0, 0, print_attr_time }, 399 { "Unassigned", NULL, 0, 0, NULL }, /*56*/ 400 { "Unassigned", NULL, 0, 0, NULL }, /*57*/ 401 { "Unassigned", NULL, 0, 0, NULL }, /*58*/ 402 { "Unassigned", NULL, 0, 0, NULL }, /*59*/ 403 { "CHAP challenge", NULL, 0, 0, print_attr_string }, 404 { "NAS Port Type", nas_port_type, TAM_SIZE(nas_port_type), 0, print_attr_num }, 405 { "Port Limit", NULL, 0, 0, print_attr_num }, 406 { "Login LAT Port", NULL, 0, 0, print_attr_string }, /*63*/ 407 { "Tunnel Type", tunnel_type, TAM_SIZE(tunnel_type)-1, 1, print_attr_num }, 408 { "Tunnel Medium", tunnel_medium, TAM_SIZE(tunnel_medium)-1, 1, print_attr_num }, 409 { "Tunnel Client End", NULL, 0, 0, print_attr_string }, 410 { "Tunnel Server End", NULL, 0, 0, print_attr_string }, 411 { "Accounting Tunnel connect", NULL, 0, 0, print_attr_string }, 412 { "Tunnel Password", NULL, 0, 0, print_attr_string }, 413 { "ARAP Password", NULL, 0, 0, print_attr_strange }, 414 { "ARAP Feature", NULL, 0, 0, print_attr_strange }, 415 { "ARAP Zone Acces", arap_zone, TAM_SIZE(arap_zone)-1, 1, print_attr_num }, /*72*/ 416 { "ARAP Security", NULL, 0, 0, print_attr_string }, 417 { "ARAP Security Data", NULL, 0, 0, print_attr_string }, 418 { "Password Retry", NULL, 0, 0, print_attr_num }, 419 { "Prompt", prompt, TAM_SIZE(prompt), 0, print_attr_num }, 420 { "Connect Info", NULL, 0, 0, print_attr_string }, 421 { "Config Token", NULL, 0, 0, print_attr_string }, 422 { "EAP Message", NULL, 0, 0, print_attr_string }, 423 { "Message Authentication", NULL, 0, 0, print_attr_string }, /*80*/ 424 { "Tunnel Private Group", NULL, 0, 0, print_attr_string }, 425 { "Tunnel Assigned ID", NULL, 0, 0, print_attr_string }, 426 { "Tunnel Preference", NULL, 0, 0, print_attr_num }, 427 { "ARAP Challenge Response", NULL, 0, 0, print_attr_strange }, 428 { "Accounting Interim Interval", NULL, 0, 0, print_attr_num }, 429 { "Accounting Tunnel packets lost", NULL, 0, 0, print_attr_num }, /*86*/ 430 { "NAS Port ID", NULL, 0, 0, print_attr_string }, 431 { "Framed Pool", NULL, 0, 0, print_attr_string }, 432 { "Unassigned", NULL, 0, 0, NULL }, 433 { "Tunnel Client Authentication ID", NULL, 0, 0, print_attr_string }, 434 { "Tunnel Server Authentication ID", NULL, 0, 0, print_attr_string }, 435 { "Unassigned", NULL, 0, 0, NULL }, /*92*/ 436 { "Unassigned", NULL, 0, 0, NULL } /*93*/ 437 }; 438 439 440/*****************************/ 441/* Print an attribute string */ 442/* value pointed by 'data' */ 443/* and 'length' size. */ 444/*****************************/ 445/* Returns nothing. */ 446/*****************************/ 447static void 448print_attr_string(register u_char *data, u_int length, u_short attr_code ) 449{ 450 register u_int i; 451 452 TCHECK2(data[0],length); 453 454 switch(attr_code) 455 { 456 case TUNNEL_PASS: 457 if (length < 3) 458 { 459 printf(" [|radius]"); 460 return; 461 } 462 if (*data && (*data <=0x1F) ) 463 printf("Tag %u, ",*data); 464 data++; 465 length--; 466 printf("Salt %u ",EXTRACT_16BITS(data) ); 467 data+=2; 468 length-=2; 469 break; 470 case TUNNEL_CLIENT_END: 471 case TUNNEL_SERVER_END: 472 case TUNNEL_PRIV_GROUP: 473 case TUNNEL_ASSIGN_ID: 474 case TUNNEL_CLIENT_AUTH: 475 case TUNNEL_SERVER_AUTH: 476 if (*data <= 0x1F) 477 { 478 if (length < 1) 479 { 480 printf(" [|radius]"); 481 return; 482 } 483 printf("Tag %u",*data); 484 data++; 485 length--; 486 } 487 break; 488 } 489 490 for (i=0; *data && i < length ; i++, data++) 491 printf("%c",(*data < 32 || *data > 128) ? '.' : *data ); 492 493 return; 494 495 trunc: 496 printf(" [|radius]"); 497} 498 499/* 500 * print vendor specific attributes 501 */ 502 503static void 504print_vendor_attr(register u_char *data, u_int length, u_short attr_code _U_) 505{ 506 u_int idx; 507 u_int vendor_id; 508 u_int vendor_type; 509 u_int vendor_length; 510 511 if (length < 4) 512 goto trunc; 513 TCHECK2(*data, 4); 514 vendor_id = EXTRACT_32BITS(data); 515 data+=4; 516 length-=4; 517 518 printf("Vendor: %s (%u)", 519 tok2str(smi_values,"Unknown",vendor_id), 520 vendor_id); 521 522 while (length >= 2) { 523 TCHECK2(*data, 2); 524 525 vendor_type = *(data); 526 vendor_length = *(data+1); 527 528 if (vendor_length < 2) 529 { 530 printf("\n\t Vendor Attribute: %u, Length: %u (bogus, must be >= 2)", 531 vendor_type, 532 vendor_length); 533 return; 534 } 535 if (vendor_length > length) 536 { 537 printf("\n\t Vendor Attribute: %u, Length: %u (bogus, goes past end of vendor-specific attribute)", 538 vendor_type, 539 vendor_length); 540 return; 541 } 542 data+=2; 543 vendor_length-=2; 544 length-=2; 545 TCHECK2(*data, vendor_length); 546 547 printf("\n\t Vendor Attribute: %u, Length: %u, Value: ", 548 vendor_type, 549 vendor_length); 550 for (idx = 0; idx < vendor_length ; idx++, data++) 551 printf("%c",(*data < 32 || *data > 128) ? '.' : *data ); 552 length-=vendor_length; 553 } 554 return; 555 556 trunc: 557 printf(" [|radius]"); 558} 559 560 561 562/******************************/ 563/* Print an attribute numeric */ 564/* value pointed by 'data' */ 565/* and 'length' size. */ 566/******************************/ 567/* Returns nothing. */ 568/******************************/ 569static void 570print_attr_num(register u_char *data, u_int length, u_short attr_code ) 571{ 572 u_int8_t tag; 573 u_int32_t timeout; 574 575 if (length != 4) 576 { 577 printf("ERROR: length %u != 4", length); 578 return; 579 } 580 581 TCHECK2(data[0],4); 582 /* This attribute has standard values */ 583 if (attr_type[attr_code].siz_subtypes) 584 { 585 static const char **table; 586 u_int32_t data_value; 587 table = attr_type[attr_code].subtypes; 588 589 if ( (attr_code == TUNNEL_TYPE) || (attr_code == TUNNEL_MEDIUM) ) 590 { 591 if (!*data) 592 printf("Tag[Unused]"); 593 else 594 printf("Tag[%d]", *data); 595 data++; 596 data_value = EXTRACT_24BITS(data); 597 } 598 else 599 { 600 data_value = EXTRACT_32BITS(data); 601 } 602 if ( data_value <= (u_int32_t)(attr_type[attr_code].siz_subtypes - 1 + 603 attr_type[attr_code].first_subtype) && 604 data_value >= attr_type[attr_code].first_subtype ) 605 printf("%s",table[data_value]); 606 else 607 printf("#%u",data_value); 608 } 609 else 610 { 611 switch(attr_code) /* Be aware of special cases... */ 612 { 613 case FRM_IPX: 614 if (EXTRACT_32BITS( data) == 0xFFFFFFFE ) 615 printf("NAS Select"); 616 else 617 printf("%d",EXTRACT_32BITS( data) ); 618 break; 619 620 case SESSION_TIMEOUT: 621 case IDLE_TIMEOUT: 622 case ACCT_DELAY: 623 case ACCT_SESSION_TIME: 624 case ACCT_INT_INTERVAL: 625 timeout = EXTRACT_32BITS( data); 626 if ( timeout < 60 ) 627 printf( "%02d secs", timeout); 628 else 629 { 630 if ( timeout < 3600 ) 631 printf( "%02d:%02d min", 632 timeout / 60, timeout % 60); 633 else 634 printf( "%02d:%02d:%02d hours", 635 timeout / 3600, (timeout % 3600) / 60, 636 timeout % 60); 637 } 638 break; 639 640 case FRM_ATALK_LINK: 641 if (EXTRACT_32BITS(data) ) 642 printf("%d",EXTRACT_32BITS(data) ); 643 else 644 printf("Unnumbered" ); 645 break; 646 647 case FRM_ATALK_NETWORK: 648 if (EXTRACT_32BITS(data) ) 649 printf("%d",EXTRACT_32BITS(data) ); 650 else 651 printf("NAS assigned" ); 652 break; 653 654 case TUNNEL_PREFERENCE: 655 tag = *data; 656 data++; 657 if (tag == 0) 658 printf("Tag (Unused) %d",EXTRACT_24BITS(data) ); 659 else 660 printf("Tag (%d) %d", tag, EXTRACT_24BITS(data) ); 661 break; 662 663 default: 664 printf("%d",EXTRACT_32BITS( data) ); 665 break; 666 667 } /* switch */ 668 669 } /* if-else */ 670 671 return; 672 673 trunc: 674 printf(" [|radius]"); 675} 676 677 678/*****************************/ 679/* Print an attribute IPv4 */ 680/* address value pointed by */ 681/* 'data' and 'length' size. */ 682/*****************************/ 683/* Returns nothing. */ 684/*****************************/ 685static void 686print_attr_address(register u_char *data, u_int length, u_short attr_code ) 687{ 688 if (length != 4) 689 { 690 printf("ERROR: length %u != 4", length); 691 return; 692 } 693 694 TCHECK2(data[0],4); 695 696 switch(attr_code) 697 { 698 case FRM_IPADDR: 699 case LOG_IPHOST: 700 if (EXTRACT_32BITS(data) == 0xFFFFFFFF ) 701 printf("User Selected"); 702 else 703 if (EXTRACT_32BITS(data) == 0xFFFFFFFE ) 704 printf("NAS Select"); 705 else 706 printf("%s",ipaddr_string(data)); 707 break; 708 709 default: 710 printf("%s",ipaddr_string(data) ); 711 break; 712 } 713 714 return; 715 716 trunc: 717 printf(" [|radius]"); 718} 719 720 721/*************************************/ 722/* Print an attribute of 'secs since */ 723/* January 1, 1970 00:00 UTC' value */ 724/* pointed by 'data' and 'length' */ 725/* size. */ 726/*************************************/ 727/* Returns nothing. */ 728/*************************************/ 729static void print_attr_time(register u_char *data, u_int length, u_short attr_code _U_) 730{ 731 time_t attr_time; 732 char string[26]; 733 734 if (length != 4) 735 { 736 printf("ERROR: length %u != 4", length); 737 return; 738 } 739 740 TCHECK2(data[0],4); 741 742 attr_time = EXTRACT_32BITS(data); 743 strlcpy(string, ctime(&attr_time), sizeof(string)); 744 /* Get rid of the newline */ 745 string[24] = '\0'; 746 printf("%.24s", string); 747 return; 748 749 trunc: 750 printf(" [|radius]"); 751} 752 753 754/***********************************/ 755/* Print an attribute of 'strange' */ 756/* data format pointed by 'data' */ 757/* and 'length' size. */ 758/***********************************/ 759/* Returns nothing. */ 760/***********************************/ 761static void print_attr_strange(register u_char *data, u_int length, u_short attr_code) 762{ 763 u_short len_data; 764 765 switch(attr_code) 766 { 767 case ARAP_PASS: 768 if (length != 16) 769 { 770 printf("ERROR: length %u != 16", length); 771 return; 772 } 773 printf("User_challenge ("); 774 TCHECK2(data[0],8); 775 len_data = 8; 776 PRINT_HEX(len_data, data); 777 printf(") User_resp("); 778 TCHECK2(data[0],8); 779 len_data = 8; 780 PRINT_HEX(len_data, data); 781 printf(")"); 782 break; 783 784 case ARAP_FEATURES: 785 if (length != 14) 786 { 787 printf("ERROR: length %u != 14", length); 788 return; 789 } 790 TCHECK2(data[0],1); 791 if (*data) 792 printf("User can change password"); 793 else 794 printf("User cannot change password"); 795 data++; 796 TCHECK2(data[0],1); 797 printf(", Min password length: %d",*data); 798 data++; 799 printf(", created at: "); 800 TCHECK2(data[0],4); 801 len_data = 4; 802 PRINT_HEX(len_data, data); 803 printf(", expires in: "); 804 TCHECK2(data[0],4); 805 len_data = 4; 806 PRINT_HEX(len_data, data); 807 printf(", Current Time: "); 808 TCHECK2(data[0],4); 809 len_data = 4; 810 PRINT_HEX(len_data, data); 811 break; 812 813 case ARAP_CHALLENGE_RESP: 814 if (length < 8) 815 { 816 printf("ERROR: length %u != 8", length); 817 return; 818 } 819 TCHECK2(data[0],8); 820 len_data = 8; 821 PRINT_HEX(len_data, data); 822 break; 823 } 824 return; 825 826 trunc: 827 printf(" [|radius]"); 828} 829 830 831 832static void 833radius_attrs_print(register const u_char *attr, u_int length) 834{ 835 register const struct radius_attr *rad_attr = (struct radius_attr *)attr; 836 const char *attr_string; 837 838 while (length > 0) 839 { 840 if (length < 2) 841 goto trunc; 842 TCHECK(*rad_attr); 843 844 if (rad_attr->type > 0 && rad_attr->type < TAM_SIZE(attr_type)) 845 attr_string = attr_type[rad_attr->type].name; 846 else 847 attr_string = "Unknown"; 848 if (rad_attr->len < 2) 849 { 850 printf("\n\t %s Attribute (%u), length: %u (bogus, must be >= 2)", 851 attr_string, 852 rad_attr->type, 853 rad_attr->len); 854 return; 855 } 856 if (rad_attr->len > length) 857 { 858 printf("\n\t %s Attribute (%u), length: %u (bogus, goes past end of packet)", 859 attr_string, 860 rad_attr->type, 861 rad_attr->len); 862 return; 863 } 864 printf("\n\t %s Attribute (%u), length: %u, Value: ", 865 attr_string, 866 rad_attr->type, 867 rad_attr->len); 868 869 if (rad_attr->type < TAM_SIZE(attr_type)) 870 { 871 if (rad_attr->len > 2) 872 { 873 if ( attr_type[rad_attr->type].print_func ) 874 (*attr_type[rad_attr->type].print_func)( 875 ((u_char *)(rad_attr+1)), 876 rad_attr->len - 2, rad_attr->type); 877 } 878 } 879 /* do we also want to see a hex dump ? */ 880 if (vflag> 1) 881 print_unknown_data((u_char *)rad_attr+2,"\n\t ",(rad_attr->len)-2); 882 883 length-=(rad_attr->len); 884 rad_attr = (struct radius_attr *)( ((char *)(rad_attr))+rad_attr->len); 885 } 886 return; 887 888trunc: 889 printf(" [|radius]"); 890} 891 892 893void 894radius_print(const u_char *dat, u_int length) 895{ 896 register const struct radius_hdr *rad; 897 u_int len, auth_idx; 898 899 TCHECK2(*dat, MIN_RADIUS_LEN); 900 rad = (struct radius_hdr *)dat; 901 len = EXTRACT_16BITS(&rad->len); 902 903 if (len < MIN_RADIUS_LEN) 904 { 905 printf(" [|radius]"); 906 return; 907 } 908 909 if (len > length) 910 len = length; 911 912 if (vflag < 1) { 913 printf("RADIUS, %s (%u), id: 0x%02x length: %u", 914 tok2str(radius_command_values,"Unknown Command",rad->code), 915 rad->code, 916 rad->id, 917 len); 918 return; 919 } 920 else { 921 printf("RADIUS, length: %u\n\t%s (%u), id: 0x%02x, Authenticator: ", 922 len, 923 tok2str(radius_command_values,"Unknown Command",rad->code), 924 rad->code, 925 rad->id); 926 927 for(auth_idx=0; auth_idx < 16; auth_idx++) 928 printf("%02x", rad->auth[auth_idx] ); 929 } 930 931 if (len > MIN_RADIUS_LEN) 932 radius_attrs_print( dat + MIN_RADIUS_LEN, len - MIN_RADIUS_LEN); 933 return; 934 935trunc: 936 printf(" [|radius]"); 937} 938