1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License, Version 1.0 only 6 * (the "License"). You may not use this file except in compliance 7 * with the License. 8 * 9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10 * or http://www.opensolaris.org/os/licensing. 11 * See the License for the specific language governing permissions 12 * and limitations under the License. 13 * 14 * When distributing Covered Code, include this CDDL HEADER in each 15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16 * If applicable, add the following below this CDDL HEADER, with the 17 * fields enclosed by brackets "[]" replaced with your own identifying 18 * information: Portions Copyright [yyyy] [name of copyright owner] 19 * 20 * CDDL HEADER END 21 */ 22 /* 23 * Copyright 1991-1998,2003 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 #pragma ident "%Z%%M% %I% %E% SMI" 28 29 #include <sys/types.h> 30 #include <sys/errno.h> 31 #include <setjmp.h> 32 33 #include <netinet/in.h> 34 #include <netdb.h> 35 36 #include <sys/tiuser.h> 37 #include <rpc/types.h> 38 #include <rpc/xdr.h> 39 #include <rpc/auth.h> 40 #include <rpc/auth_unix.h> 41 #include <rpc/auth_des.h> 42 #include <rpc/clnt.h> 43 #include <rpc/rpc_msg.h> 44 #include <rpc/pmap_clnt.h> 45 #include <rpc/svc.h> 46 #include <rpcsvc/yp_prot.h> 47 #include <rpc/pmap_prot.h> 48 #include "snoop.h" 49 50 #ifndef MIN 51 #define MIN(a, b) ((a) < (b) ? (a) : (b)) 52 #endif 53 54 int pos; 55 struct cache_struct *find_xid(); 56 extern jmp_buf xdr_err; 57 void protoprint(); 58 void print_rpcsec_gss_cred(int xid, int authlen); 59 char *nameof_prog(); 60 char *nameof_astat(); 61 char *nameof_why(); 62 63 #define LAST_FRAG ((ulong_t)1 << 31) 64 65 interpret_rpc(flags, rpc, fraglen, type) 66 int flags; 67 char *rpc; 68 int fraglen, type; 69 { 70 ulong_t xid; 71 int direction; 72 struct cache_struct *x; 73 int rpcvers, prog, vers, proc; 74 int status, astat, rstat, why; 75 char *lp; 76 unsigned recmark; 77 int markpos; 78 extern int pi_frame; 79 int lo, hi; 80 81 xdr_init(rpc, fraglen); 82 83 if (setjmp(xdr_err)) { 84 if (flags & F_DTAIL) 85 (void) sprintf(get_line(0, 0), 86 "---- short frame ---"); 87 return (fraglen); 88 } 89 90 if (type == IPPROTO_TCP) { /* record mark */ 91 markpos = getxdr_pos(); 92 recmark = getxdr_long(); 93 } 94 95 xid = getxdr_u_long(); 96 direction = getxdr_long(); 97 98 if (direction == CALL) { 99 rpcvers = getxdr_long(); 100 pos = getxdr_pos(); 101 prog = getxdr_long(); 102 vers = getxdr_long(); 103 proc = getxdr_long(); 104 stash_xid(xid, pi_frame, prog, vers, proc); 105 if (!(flags & (F_SUM | F_DTAIL))) 106 protoprint(flags, CALL, xid, prog, vers, proc, 107 rpc, fraglen); 108 } else { 109 x = find_xid(xid); 110 } 111 112 if (flags & F_SUM) { 113 switch (direction) { 114 case CALL: 115 (void) sprintf(get_sum_line(), 116 "RPC C XID=%lu PROG=%d (%s) VERS=%d PROC=%d", 117 xid, 118 prog, nameof_prog(prog), 119 vers, proc); 120 if (getxdr_long() == RPCSEC_GSS) { /* Cred auth type */ 121 extract_rpcsec_gss_cred_info(xid); 122 /* RPCSEC_GSS cred auth data */ 123 } else { 124 xdr_skip(getxdr_long()); 125 /* non RPCSEC_GSS cred auth data */ 126 } 127 xdr_skip(4); /* Verf auth type */ 128 xdr_skip(RNDUP(getxdr_long())); /* Verf auth data */ 129 130 protoprint(flags, CALL, xid, prog, vers, proc, 131 rpc, fraglen); 132 break; 133 134 case REPLY: 135 lp = get_sum_line(); 136 if (x == NULL) 137 (void) sprintf(lp, "RPC R XID=%lu", xid); 138 else 139 (void) sprintf(lp, "RPC R (#%d) XID=%lu", 140 x->xid_frame, xid); 141 142 lp += strlen(lp); 143 status = getxdr_long(); 144 switch (status) { 145 case MSG_ACCEPTED: 146 /* eat flavor and verifier */ 147 (void) getxdr_long(); 148 xdr_skip(RNDUP(getxdr_long())); 149 astat = getxdr_long(); 150 (void) sprintf(lp, " %s", 151 nameof_astat(astat)); 152 lp += strlen(lp); 153 154 switch (astat) { 155 case SUCCESS: 156 if (x) { 157 protoprint(flags, REPLY, 158 xid, 159 x->xid_prog, 160 x->xid_vers, 161 x->xid_proc, 162 rpc, fraglen); 163 } 164 break; 165 166 case PROG_UNAVAIL : 167 case PROG_MISMATCH: 168 case PROC_UNAVAIL : 169 lo = getxdr_long(); 170 hi = getxdr_long(); 171 (void) sprintf(lp, 172 " (low=%d, high=%d)", 173 lo, hi); 174 break; 175 176 case GARBAGE_ARGS: 177 case SYSTEM_ERR: 178 default: 179 ; 180 } 181 break; 182 183 case MSG_DENIED: 184 rstat = getxdr_long(); 185 186 switch (rstat) { 187 case RPC_MISMATCH: 188 lo = getxdr_long(); 189 hi = getxdr_long(); 190 (void) sprintf(lp, 191 " Vers mismatch (low=%d, high=%d)", 192 lo, hi); 193 break; 194 195 case AUTH_ERROR: 196 why = getxdr_u_long(); 197 (void) sprintf(lp, 198 " Can't authenticate (%s)", 199 nameof_why(why)); 200 break; 201 } 202 } 203 break; 204 } 205 } 206 207 if (flags & F_DTAIL) { 208 show_header("RPC: ", "SUN RPC Header", fraglen); 209 show_space(); 210 if (type == IPPROTO_TCP) { /* record mark */ 211 (void) sprintf(get_line(markpos, markpos+4), 212 "Record Mark: %s fragment, length = %d", 213 recmark & LAST_FRAG ? "last" : "", 214 recmark & ~LAST_FRAG); 215 } 216 217 (void) sprintf(get_line(0, 0), 218 "Transaction id = %lu", 219 xid); 220 (void) sprintf(get_line(0, 0), 221 "Type = %d (%s)", 222 direction, 223 direction == CALL ? "Call":"Reply"); 224 225 switch (direction) { 226 case CALL: 227 rpc_detail_call(flags, xid, rpcvers, 228 prog, vers, proc, rpc, fraglen); 229 break; 230 case REPLY: 231 rpc_detail_reply(flags, xid, x, rpc, fraglen); 232 break; 233 } 234 } 235 236 return (fraglen); 237 } 238 239 rpc_detail_call(flags, xid, rpcvers, prog, vers, proc, data, len) 240 int flags, xid, rpcvers, prog, vers, proc; 241 char *data; 242 int len; 243 { 244 char *nameof_flavor(); 245 char *nameof_prog(); 246 247 (void) sprintf(get_line(pos, getxdr_pos()), 248 "RPC version = %d", 249 rpcvers); 250 (void) sprintf(get_line(pos, getxdr_pos()), 251 "Program = %d (%s), version = %d, procedure = %d", 252 prog, nameof_prog(prog), vers, proc); 253 print_creds(xid); 254 print_verif(CALL); 255 show_trailer(); 256 protoprint(flags, CALL, xid, prog, vers, proc, data, len); 257 } 258 259 char * 260 nameof_flavor(flavor) 261 int flavor; 262 { 263 switch (flavor) { 264 case AUTH_NONE : return ("None"); 265 case AUTH_UNIX : return ("Unix"); 266 case AUTH_SHORT: return ("Unix short"); 267 case AUTH_DES : return ("DES"); 268 case RPCSEC_GSS: return ("RPCSEC_GSS"); 269 default: return ("unknown"); 270 } 271 } 272 273 char * 274 tohex(char *p, int len) 275 { 276 int i, j; 277 static char hbuff[1024]; 278 static char *hexstr = "0123456789ABCDEF"; 279 char toobig = 0; 280 281 if (len * 2 > sizeof (hbuff)) { 282 toobig++; 283 len = sizeof (hbuff) / 2; 284 } 285 286 j = 0; 287 for (i = 0; i < len; i++) { 288 hbuff[j++] = hexstr[p[i] >> 4 & 0x0f]; 289 hbuff[j++] = hexstr[p[i] & 0x0f]; 290 } 291 292 if (toobig) { 293 hbuff[len * 2 - strlen("<Too Long>")] = '\0'; 294 strcat(hbuff, "<Too Long>"); 295 } else 296 hbuff[j] = '\0'; 297 298 return (hbuff); 299 } 300 301 print_creds(int xid) 302 { 303 int pos, flavor, authlen; 304 int uid, gid, len; 305 int tlen, idlen; 306 int i, namekind; 307 char *p, *line; 308 309 pos = getxdr_pos(); 310 flavor = getxdr_long(); 311 authlen = getxdr_long(); 312 (void) sprintf(get_line(pos, getxdr_pos()), 313 "Credentials: Flavor = %d (%s), len = %d bytes", 314 flavor, nameof_flavor(flavor), authlen); 315 if (authlen <= 0) 316 return; 317 318 switch (flavor) { 319 case AUTH_UNIX: 320 (void) showxdr_time(" Time = %s"); 321 (void) showxdr_string(MAX_MACHINE_NAME, " Hostname = %s"); 322 pos = getxdr_pos(); 323 uid = getxdr_u_long(); 324 gid = getxdr_u_long(); 325 (void) sprintf(get_line(pos, getxdr_pos()), 326 " Uid = %d, Gid = %d", 327 uid, gid); 328 len = getxdr_u_long(); 329 line = get_line(pos, len * 4); 330 if (len == 0) 331 (void) sprintf(line, " Groups = (none)"); 332 else { 333 (void) sprintf(line, " Groups = "); 334 line += strlen(line); 335 while (len--) { 336 gid = getxdr_u_long(); 337 (void) sprintf(line, "%d ", gid); 338 line += strlen(line); 339 } 340 } 341 break; 342 343 case AUTH_DES: 344 namekind = getxdr_u_long(); 345 (void) sprintf(get_line(pos, getxdr_pos()), 346 " Name kind = %d (%s)", 347 namekind, 348 namekind == ADN_FULLNAME ? 349 "fullname" : "nickname"); 350 switch (namekind) { 351 case ADN_FULLNAME: 352 (void) showxdr_string(64, 353 " Network name = %s"); 354 (void) showxdr_hex(8, 355 " Conversation key = 0x%s (DES encrypted)"); 356 (void) showxdr_hex(4, 357 " Window = 0x%s (DES encrypted)"); 358 break; 359 360 case ADN_NICKNAME: 361 (void) showxdr_hex(4, " Nickname = 0x%s"); 362 break; 363 }; 364 break; 365 366 case RPCSEC_GSS: 367 print_rpcsec_gss_cred(xid, authlen); 368 break; 369 370 default: 371 (void) showxdr_hex(authlen, "[%s]"); 372 break; 373 } 374 } 375 376 print_verif(direction) 377 int direction; 378 { 379 int pos, flavor, verlen; 380 381 pos = getxdr_pos(); 382 flavor = getxdr_long(); 383 verlen = getxdr_long(); 384 (void) sprintf(get_line(pos, getxdr_pos()), 385 "Verifier : Flavor = %d (%s), len = %d bytes", 386 flavor, nameof_flavor(flavor), verlen); 387 if (verlen == 0) 388 return; 389 390 switch (flavor) { 391 case AUTH_DES: 392 (void) showxdr_hex(8, " Timestamp = 0x%s (DES encrypted)"); 393 if (direction == CALL) 394 (void) showxdr_hex(4, 395 " Window = 0x%s (DES encrypted)"); 396 else 397 (void) showxdr_hex(4, " Nickname = 0x%s"); 398 break; 399 400 /* For other flavors like AUTH_NONE, AUTH_UNIX, RPCSEC_GSS etc. */ 401 default: 402 (void) showxdr_hex(verlen, "[%s]"); 403 break; 404 } 405 } 406 407 struct rpcnames { 408 int rp_prog; 409 char *rp_name; 410 } rpcnames[] = { 411 100000, "PMAP", /* Portmapper */ 412 100001, "RSTAT", /* Remote stats */ 413 100002, "RUSERS", /* Remote users */ 414 100003, "NFS", /* Nfs */ 415 100004, "NIS", /* Network Information Service */ 416 100005, "MOUNT", /* Mount demon */ 417 100006, "DBX", /* Remote dbx */ 418 100007, "NISBIND", /* NIS binder */ 419 100008, "WALL", /* Shutdown msg */ 420 100009, "NISPASSWD", /* Yppasswd server */ 421 100010, "ETHERSTAT", /* Ether stats */ 422 100011, "RQUOTA", /* Disk quotas */ 423 100012, "SPRAY", /* Spray packets */ 424 100013, "IBM3270", /* 3270 mapper */ 425 100014, "IBMRJE", /* RJE mapper */ 426 100015, "SELNSVC", /* Selection service */ 427 100016, "RDATABASE", /* Remote database access */ 428 100017, "REX", /* Remote execution */ 429 100018, "ALICE", /* Alice Office Automation */ 430 100019, "SCHED", /* Scheduling service */ 431 100020, "LLM", /* Local lock manager */ 432 100021, "NLM", /* Network lock manager */ 433 100022, "X25INR", /* X.25 inr protocol */ 434 100023, "STATMON1", /* Status monitor 1 */ 435 100024, "STATMON2", /* Status monitor 2 */ 436 100025, "SELNLIB", /* Selection library */ 437 100026, "BOOTPARAM", /* Boot parameters service */ 438 100027, "MAZEPROG", /* Mazewars game */ 439 100028, "NISUPDATE", /* NIS update */ 440 100029, "KEYSERVE", /* Key server */ 441 100030, "SECURECMD", /* Secure login */ 442 100031, "NETFWDI", /* NFS net forwarder init */ 443 100032, "NETFWDT", /* NFS net forwarder trans */ 444 100033, "SUNLINKMAP", /* Sunlink MAP */ 445 100034, "NETMON", /* Network monitor */ 446 100035, "DBASE", /* Lightweight database */ 447 100036, "PWDAUTH", /* Password authorization */ 448 100037, "TFS", /* Translucent file svc */ 449 100038, "NSE", /* NSE server */ 450 100039, "NSE_ACTIVATE", /* NSE activate daemon */ 451 100040, "SUNVIEW_HELP", /* Sunview help */ 452 100041, "PNP", /* PNP install */ 453 100042, "IPADDR_ALLOC", /* IP addr allocator */ 454 100043, "FILEHANDLE", /* Show filehandle */ 455 100044, "MVSNFS", /* MVS NFS mount */ 456 100045, "REM_FILEOP_USER", /* Remote user file operations */ 457 100046, "BATCH_NISUPDATE", /* Batched ypupdate */ 458 100047, "NEM", /* Network execution mgr */ 459 100048, "RAYTRACE_RD", /* Raytrace/mandelbrot remote daemon */ 460 100049, "RAYTRACE_LD", /* Raytrace/mandelbrot local daemon */ 461 100050, "REM_FILEOP_GROUP", /* Remote group file operations */ 462 100051, "REM_FILEOP_SYSTEM", /* Remote system file operations */ 463 100052, "REM_SYSTEM_ROLE", /* Remote system role operations */ 464 100055, "IOADMD", /* Ioadmd */ 465 100056, "FILEMERGE", /* Filemerge */ 466 100057, "NAMEBIND", /* Name Binding Program */ 467 100058, "NJE", /* Sunlink NJE */ 468 100059, "MVSATTR", /* MVSNFS get attribute service */ 469 100060, "RMGR", /* SunAccess/SunLink resource manager */ 470 100061, "UIDALLOC", /* UID allocation service */ 471 100062, "LBSERVER", /* License broker */ 472 100063, "LBBINDER", /* NETlicense client binder */ 473 100064, "GIDALLOC", /* GID allocation service */ 474 100065, "SUNISAM", /* SunIsam */ 475 100066, "RDBSRV", /* Remote Debug Server */ 476 100067, "NETDIR", /* Network directory daemon */ 477 100068, "CMSD", /* Network calendar program */ 478 100069, "NISXFR", /* NIS transfer */ 479 100070, "TIMED", /* RPC.timed */ 480 100071, "BUGTRAQ", /* Bugtraqd */ 481 100072, "NeFS", /* Internal use only */ 482 100073, "BILLBOARD", /* Connectathon Billboard - NFS */ 483 100074, "BILLBOARD", /* Connectathon Billboard - X */ 484 100075, "SCHEDROOM", /* Sun meeting room scheduler */ 485 100076, "AUTHNEGOTIATE", /* Authentication negotiation */ 486 100077, "ATTRPROG", /* Database manipulation */ 487 100080, "AUTODUMP", /* Sun consulting special */ 488 100081, "EVENT_SVC", /* Event protocol */ 489 100085, "ARM_PSD", /* ARM policy */ 490 100086, "ARMTOD", /* ARM TOD */ 491 100087, "NA.ADMIN", /* Sun (SNAG) administration agent */ 492 100099, "PLD", /* Genesil 8.1 hot plot */ 493 100101, "NA.EVENT", /* SNM (SunNet Manager) event dispatcher */ 494 100102, "NA.LOGGER", /* SNM report logger */ 495 100103, "NA.DISCOVER", /* SNM network discovery agent */ 496 100104, "NA.SYNC", /* SNM sync interface agent */ 497 100105, "NA.DISKINFO", /* SNM disk info agent */ 498 100106, "NA.IOSTAT", /* SNM iostat agent */ 499 100107, "NA.HOSTPERF", /* SNM rstat proxy agent */ 500 100108, "NA.CONFIG", /* SNM host configuration agent */ 501 100109, "NA.ACTIVITY", /* SNM activity daemon */ 502 100111, "NA.LPSTAT", /* SNM printer agent */ 503 100112, "NA.HOSTMEM", /* SNM host network memory agent */ 504 100113, "NA.SAMPLE", /* SNM sample agent */ 505 100114, "NA.X25", /* SNM X.25 agent */ 506 100115, "NA.PING", /* SNM ping proxy agent */ 507 100116, "NA.RPCNFS", /* SNM rpc and nfs agent */ 508 100117, "NA.HOSTIF", /* SNM host interface agent */ 509 100118, "NA.ETHERIF", /* SNM ethernet interface agent */ 510 100119, "NA.IPPATH", /* SNM traceroute proxy agent */ 511 100120, "NA.IPROUTES", /* SNM routing table agent */ 512 100121, "NA.LAYERS", /* SNM protocol layers gent */ 513 100122, "NA.SNMP", /* SNM SNMP proxy agent */ 514 100123, "NA.TRAFFIC", /* SNM network traffic agent */ 515 100124, "NA.DNI", /* DNI (DECnet) proxy agent */ 516 100125, "NA.CHAT", /* IBM Channel attach proxy agent */ 517 100126, "NA.FDDI", /* FDDI agent */ 518 100127, "NA.FDDISMT", /* FDDI SMT proxy agent */ 519 100128, "NA.MHS", /* MHS agent */ 520 100130, "SNM_GRAPHER", /* SNM 3D grapher */ 521 100132, "NA.TR", /* Token Ring agent */ 522 100134, "NA.TOKENRING", /* Token Ring agent */ 523 100136, "NA.FRAMERELAY", /* Frame Relay agent */ 524 100175, "NA.SNMPTRAP", /* SNM SNMP trap daemon */ 525 100180, "NA.MIPROUTES", /* SNM multicast routing table agent */ 526 100201, "MVSNFSSTAT", /* MVS/NFS Memory usage statistic server */ 527 100227, "NFS_ACL", /* NFS ACL support */ 528 100300, "NIS+", /* NIS+ name service */ 529 100302, "NIS+ CB", /* NIS+ callbacks */ 530 101002, "NSELINKTOOL", /* NSE link daemon */ 531 101003, "NSELINKAPP", /* NSE link application */ 532 110001, "GOLABEL", /* SunOS MLS */ 533 110002, "PUC", /* SunOS MLS */ 534 150001, "PCNFSD", /* PC passwd authorization */ 535 150002, "TOPS", /* TOPS name mapping */ 536 150003, "TOPS", /* TOPS external attribute storage */ 537 150004, "TOPS", /* TOPS hierarchical file system */ 538 150005, "TOPS", /* TOPS NFS transparency extensions */ 539 150006, "SOLARNET_FW", /* SolarNet Framework protocol */ 540 160001, "CM", /* Nihon Sun - Japanese Input system */ 541 300004, "FRAME 1", /* Frame program 1 */ 542 300009, "FRAME 2", /* Frame program 2 */ 543 390101, "RAP", /* Legato RAP protocol */ 544 390102, "RAPRD", /* Legato RAP resource dir protocol */ 545 500021, "ZNS", /* Zeus Network Service */ 546 }; 547 548 compare(a, b) 549 register struct rpcnames *a, *b; 550 { 551 return (a->rp_prog - b->rp_prog); 552 } 553 554 char * 555 nameof_prog(prog) 556 int prog; 557 { 558 struct rpcnames *r; 559 struct rpcnames *bsearch(); 560 int elems = sizeof (rpcnames) / sizeof (*r); 561 562 r = bsearch(&prog, rpcnames, elems, sizeof (*r), compare); 563 if (r) 564 return (r->rp_name); 565 566 if (prog >= 0x40000000 && prog <= 0x5fffffff) 567 return ("transient"); 568 569 return ("?"); 570 } 571 572 char * 573 nameof_astat(status) 574 int status; 575 { 576 switch (status) { 577 case SUCCESS : return ("Success"); 578 case PROG_UNAVAIL : return ("Program unavailable"); 579 case PROG_MISMATCH: return ("Program number mismatch"); 580 case PROC_UNAVAIL : return ("Procedure unavailable"); 581 case GARBAGE_ARGS : return ("Garbage arguments"); 582 case SYSTEM_ERR : return ("System error"); 583 default: return ("unknown"); 584 } 585 } 586 587 char * 588 nameof_why(why) 589 int why; 590 { 591 switch (why) { 592 case AUTH_BADCRED: return ("bogus credentials (seal broken)"); 593 case AUTH_REJECTEDCRED: return ("client should begin new session"); 594 case AUTH_BADVERF: return ("bogus verifier (seal broken)"); 595 case AUTH_REJECTEDVERF: return ("verifier expired or was replayed"); 596 case AUTH_TOOWEAK: return ("too weak"); 597 case AUTH_INVALIDRESP: return ("bogus response verifier"); 598 case AUTH_TIMEEXPIRE: return ("time of credential expired"); 599 case AUTH_TKT_FILE: return ("something wrong with ticket file"); 600 case AUTH_DECODE: return ("can't decode authenticator"); 601 case AUTH_NET_ADDR: return ("net address in ticket wrong"); 602 case RPCSEC_GSS_NOCRED: return ("no credentials for user"); 603 case RPCSEC_GSS_FAILED: return ("GSS failure, credentials deleted"); 604 case AUTH_FAILED: 605 default: 606 return ("unknown reason"); 607 } 608 } 609 610 rpc_detail_reply(flags, xid, x, data, len) 611 int flags, xid; 612 struct cache_struct *x; 613 char *data; 614 int len; 615 { 616 int status; 617 int astat, rstat, why; 618 int pos; 619 620 if (x) { 621 (void) sprintf(get_line(0, 0), 622 "This is a reply to frame %d", 623 x->xid_frame); 624 } 625 pos = getxdr_pos(); 626 status = getxdr_long(); 627 (void) sprintf(get_line(pos, getxdr_pos()), 628 "Status = %d (%s)", 629 status, status ? "Denied" : "Accepted"); 630 631 switch (status) { 632 case MSG_ACCEPTED: 633 print_verif(REPLY); 634 pos = getxdr_pos(); 635 astat = getxdr_long(); 636 (void) sprintf(get_line(pos, getxdr_pos()), 637 "Accept status = %d (%s)", 638 astat, nameof_astat(astat)); 639 640 switch (astat) { 641 case SUCCESS: 642 if (x) { 643 show_trailer(); 644 protoprint(flags, REPLY, xid, 645 x->xid_prog, x->xid_vers, x->xid_proc, 646 data, len); 647 } 648 break; 649 case PROG_UNAVAIL : 650 break; 651 case PROG_MISMATCH: 652 case PROC_UNAVAIL : 653 showxdr_long(" Low = %d"); 654 showxdr_long(" High = %d"); 655 break; 656 case GARBAGE_ARGS: 657 case SYSTEM_ERR: 658 default: 659 ; 660 } 661 662 break; 663 664 case MSG_DENIED: 665 pos = getxdr_pos(); 666 rstat = getxdr_long(); 667 (void) sprintf(get_line(pos, getxdr_pos()), 668 "Reject status = %d (%s)", 669 rstat, 670 rstat ? "can't authenticate" 671 : "version mismatch"); 672 673 switch (rstat) { 674 case RPC_MISMATCH: 675 showxdr_long(" Low = %d"); 676 showxdr_long(" High = %d"); 677 break; 678 case AUTH_ERROR: 679 why = getxdr_u_long(); 680 (void) sprintf(get_line(pos, getxdr_pos()), 681 " Why = %d (%s)", 682 why, nameof_why(why)); 683 break; 684 } 685 break; 686 } 687 } 688 689 /* 690 * Return true if this is a valid RPC packet 691 */ 692 valid_rpc(rpc, rpclen) 693 char *rpc; 694 int rpclen; 695 { 696 XDR xdrm; 697 struct rpc_msg msg; 698 699 if (rpclen < 12) 700 return (0); 701 702 xdrmem_create(&xdrm, rpc, rpclen, XDR_DECODE); 703 if (xdr_u_int(&xdrm, &msg.rm_xid) && 704 xdr_u_int(&xdrm, (uint_t *)&msg.rm_direction)) { 705 switch (msg.rm_direction) { 706 case CALL: 707 if (xdr_rpcvers(&xdrm, &msg.rm_call.cb_rpcvers) && 708 msg.rm_call.cb_rpcvers == 2) 709 return (1); 710 break; 711 case REPLY: 712 if (xdr_u_int(&xdrm, 713 (uint_t *)&msg.rm_reply.rp_stat) && 714 (msg.rm_reply.rp_stat == MSG_ACCEPTED || 715 msg.rm_reply.rp_stat == MSG_DENIED)) 716 return (1); 717 break; 718 } 719 } 720 721 return (0); 722 } 723 724 struct cache_struct *xcpfirst = &xid_cache[0]; 725 struct cache_struct *xcp = &xid_cache[0]; 726 struct cache_struct *xcplast = &xid_cache[XID_CACHE_SIZE - 1]; 727 728 struct cache_struct * 729 find_xid(xid) 730 ulong_t xid; 731 { 732 struct cache_struct *x; 733 734 for (x = xcp; x >= xcpfirst; x--) 735 if (x->xid_num == xid) 736 return (x); 737 for (x = xcplast; x > xcp; x--) 738 if (x->xid_num == xid) 739 return (x); 740 return (NULL); 741 } 742 743 stash_xid(xid, frame, prog, vers, proc) 744 ulong_t xid; 745 int frame, prog, vers, proc; 746 { 747 struct cache_struct *x; 748 749 x = find_xid(xid); 750 if (x == NULL) { 751 x = xcp++; 752 if (xcp > xcplast) 753 xcp = xcpfirst; 754 x->xid_num = xid; 755 x->xid_frame = frame; 756 } 757 x->xid_prog = prog; 758 x->xid_vers = vers; 759 x->xid_proc = proc; 760 x->xid_gss_proc = RPCSEC_GSS_DATA; 761 x->xid_gss_service = rpc_gss_svc_default; 762 } 763 764 void 765 check_retransmit(line, xid) 766 char *line; 767 ulong_t xid; 768 { 769 struct cache_struct *x; 770 extern int pi_frame; 771 772 x = find_xid(xid); 773 if (x && x->xid_frame != pi_frame) 774 (void) strcat(line, " (retransmit)"); 775 } 776