125117Ssklower /* 225117Ssklower * Copyright (c) 1985 Regents of the University of California. 334940Sbostic * All rights reserved. 434940Sbostic * 542829Sbostic * %sccs.include.redist.c% 625117Ssklower */ 725117Ssklower 825117Ssklower #ifndef lint 925117Ssklower char copyright[] = 1034940Sbostic "@(#) Copyright (c) 1985 Regents of the University of California.\n\ 1125117Ssklower All rights reserved.\n"; 1234940Sbostic #endif /* not lint */ 1325117Ssklower 1425117Ssklower #ifndef lint 15*46933Sbostic static char sccsid[] = "@(#)trsp.c 6.8 (Berkeley) 03/02/91"; 1634940Sbostic #endif /* not lint */ 1725117Ssklower 18*46933Sbostic #include <sys/cdefs.h> 1925117Ssklower #include <sys/param.h> 2025117Ssklower #include <sys/socket.h> 2125117Ssklower #include <sys/socketvar.h> 2225117Ssklower #define PRUREQUESTS 2325117Ssklower #include <sys/protosw.h> 2425117Ssklower 2525117Ssklower #include <net/route.h> 2625117Ssklower #include <net/if.h> 2725117Ssklower 2825117Ssklower #define TCPSTATES 2925117Ssklower #include <netinet/tcp_fsm.h> 3025117Ssklower #define TCPTIMERS 3125117Ssklower #include <netinet/tcp_timer.h> 3225117Ssklower 3325117Ssklower #include <netns/ns.h> 34*46933Sbostic #include <netns/sp.h> 3525117Ssklower #include <netns/idp.h> 3625117Ssklower #include <netns/spidp.h> 3735616Sbostic #include <netns/spp_timer.h> 3825117Ssklower #include <netns/spp_var.h> 39*46933Sbostic #include <netns/ns_pcb.h> 40*46933Sbostic #include <netns/idp_var.h> 4125117Ssklower #define SANAMES 4225117Ssklower #include <netns/spp_debug.h> 4325117Ssklower 4425117Ssklower #include <stdio.h> 4525117Ssklower #include <errno.h> 4625117Ssklower #include <nlist.h> 4737985Sbostic #include <paths.h> 4825117Ssklower 4925117Ssklower unsigned long ntime; 5025117Ssklower int sflag; 5125117Ssklower int tflag; 5225117Ssklower int jflag; 5325117Ssklower int aflag; 5425117Ssklower int zflag; 5525117Ssklower int numeric(); 5625117Ssklower struct nlist nl[] = { 5725117Ssklower { "_spp_debug" }, 5825117Ssklower { "_spp_debx" }, 5925117Ssklower 0 6025117Ssklower }; 6125117Ssklower struct spp_debug spp_debug[SPP_NDEBUG]; 6225117Ssklower caddr_t spp_pcbs[SPP_NDEBUG]; 6325117Ssklower int spp_debx; 6425117Ssklower 6525117Ssklower main(argc, argv) 6625117Ssklower int argc; 6725117Ssklower char **argv; 6825117Ssklower { 6925117Ssklower int i, mask = 0, npcbs = 0; 7037309Sbostic char *system, *core; 7125117Ssklower 7237309Sbostic system = _PATH_UNIX; 7337309Sbostic core = _PATH_KMEM; 7437309Sbostic 7525117Ssklower argc--, argv++; 7625117Ssklower again: 7725117Ssklower if (argc > 0 && !strcmp(*argv, "-a")) { 7825117Ssklower aflag++, argc--, argv++; 7925117Ssklower goto again; 8025117Ssklower } 8125117Ssklower if (argc > 0 && !strcmp(*argv, "-z")) { 8225117Ssklower zflag++, argc--, argv++; 8325117Ssklower goto again; 8425117Ssklower } 8525117Ssklower if (argc > 0 && !strcmp(*argv, "-s")) { 8625117Ssklower sflag++, argc--, argv++; 8725117Ssklower goto again; 8825117Ssklower } 8925117Ssklower if (argc > 0 && !strcmp(*argv, "-t")) { 9025117Ssklower tflag++, argc--, argv++; 9125117Ssklower goto again; 9225117Ssklower } 9325117Ssklower if (argc > 0 && !strcmp(*argv, "-j")) { 9425117Ssklower jflag++, argc--, argv++; 9525117Ssklower goto again; 9625117Ssklower } 9725117Ssklower if (argc > 0 && !strcmp(*argv, "-p")) { 9825117Ssklower argc--, argv++; 9925117Ssklower if (argc < 1) { 10025117Ssklower fprintf(stderr, "-p: missing sppcb address\n"); 10125117Ssklower exit(1); 10225117Ssklower } 10325117Ssklower if (npcbs >= SPP_NDEBUG) { 10425117Ssklower fprintf(stderr, "-p: too many pcb's specified\n"); 10525117Ssklower exit(1); 10625117Ssklower } 10725117Ssklower sscanf(*argv, "%x", &spp_pcbs[npcbs++]); 10825117Ssklower argc--, argv++; 10925117Ssklower goto again; 11025117Ssklower } 11125117Ssklower if (argc > 0) { 11225117Ssklower system = *argv; 11325117Ssklower argc--, argv++; 11425117Ssklower mask++; 11525117Ssklower } 11625117Ssklower if (argc > 0) { 11725117Ssklower core = *argv; 11825117Ssklower argc--, argv++; 11925117Ssklower mask++; 12025117Ssklower } 12125117Ssklower (void) nlist(system, nl); 12225117Ssklower if (nl[0].n_value == 0) { 12325117Ssklower fprintf(stderr, "trsp: %s: no namelist\n", system); 12425117Ssklower exit(1); 12525117Ssklower } 12625117Ssklower (void) close(0); 12725117Ssklower if (open(core, 0) < 0) { 12825117Ssklower fprintf(stderr, "trsp: "); perror(core); 12925117Ssklower exit(2); 13025117Ssklower } 13125117Ssklower if (mask) { 13225117Ssklower nl[0].n_value &= 0x7fffffff; 13325117Ssklower nl[1].n_value &= 0x7fffffff; 13425117Ssklower } 13525117Ssklower (void) lseek(0, nl[1].n_value, 0); 13625117Ssklower if (read(0, &spp_debx, sizeof (spp_debx)) != sizeof (spp_debx)) { 13725117Ssklower fprintf(stderr, "trsp: "); perror("spp_debx"); 13825117Ssklower exit(3); 13925117Ssklower } 14025117Ssklower printf("spp_debx=%d\n", spp_debx); 14125117Ssklower (void) lseek(0, nl[0].n_value, 0); 14225117Ssklower if (read(0, spp_debug, sizeof (spp_debug)) != sizeof (spp_debug)) { 14325117Ssklower fprintf(stderr, "trsp: "); perror("spp_debug"); 14425117Ssklower exit(3); 14525117Ssklower } 14625117Ssklower /* 14725117Ssklower * Here, we just want to clear out the old trace data and start over. 14825117Ssklower */ 14925117Ssklower if (zflag) { 15025117Ssklower char *cp = (char *) spp_debug, 15125117Ssklower *cplim = cp + sizeof(spp_debug); 15225117Ssklower (void) close(0); 15325117Ssklower if (open(core, 2) < 0) { 15425117Ssklower fprintf(stderr, "trsp: "); perror(core); 15525117Ssklower exit(2); 15625117Ssklower } 15725117Ssklower while(cp < cplim) *cp++ = 0; 15825117Ssklower (void) lseek(0, nl[0].n_value, 0); 15925117Ssklower if (write(0, spp_debug, sizeof (spp_debug)) != sizeof (spp_debug)) { 16025117Ssklower fprintf(stderr, "trsp: "); perror("spp_debug"); 16125117Ssklower exit(3); 16225117Ssklower } 16325117Ssklower (void) lseek(0, nl[1].n_value, 0); 16425117Ssklower spp_debx = 0; 16525117Ssklower if (write(0, &spp_debx, sizeof (spp_debx)) != sizeof (spp_debx)) { 16625117Ssklower fprintf(stderr, "trsp: "); perror("spp_debx"); 16725117Ssklower exit(3); 16825117Ssklower } 16925117Ssklower exit(0); 17025117Ssklower } 17125117Ssklower /* 17225117Ssklower * If no control blocks have been specified, figure 17325117Ssklower * out how many distinct one we have and summarize 17425117Ssklower * them in spp_pcbs for sorting the trace records 17525117Ssklower * below. 17625117Ssklower */ 17725117Ssklower if (npcbs == 0) { 17825117Ssklower for (i = 0; i < SPP_NDEBUG; i++) { 17925117Ssklower register int j; 18025117Ssklower register struct spp_debug *sd = &spp_debug[i]; 18125117Ssklower 18225117Ssklower if (sd->sd_cb == 0) 18325117Ssklower continue; 18425117Ssklower for (j = 0; j < npcbs; j++) 18525117Ssklower if (spp_pcbs[j] == sd->sd_cb) 18625117Ssklower break; 18725117Ssklower if (j >= npcbs) 18825117Ssklower spp_pcbs[npcbs++] = sd->sd_cb; 18925117Ssklower } 19025117Ssklower } 19125117Ssklower qsort(spp_pcbs, npcbs, sizeof (caddr_t), numeric); 19225117Ssklower if (jflag) { 19325117Ssklower char *cp = ""; 19425117Ssklower 19525117Ssklower for (i = 0; i < npcbs; i++) { 19625117Ssklower printf("%s%x", cp, spp_pcbs[i]); 19725117Ssklower cp = ", "; 19825117Ssklower } 19925117Ssklower if (*cp) 20025117Ssklower putchar('\n'); 20125117Ssklower exit(0); 20225117Ssklower } 20325117Ssklower for (i = 0; i < npcbs; i++) { 20425117Ssklower printf("\n%x:\n", spp_pcbs[i]); 20525117Ssklower dotrace(spp_pcbs[i]); 20625117Ssklower } 20725117Ssklower exit(0); 20825117Ssklower } 20925117Ssklower 21025117Ssklower dotrace(sppcb) 21125117Ssklower register caddr_t sppcb; 21225117Ssklower { 21325117Ssklower register int i; 21425117Ssklower register struct spp_debug *sd; 21525117Ssklower 21625117Ssklower for (i = spp_debx % SPP_NDEBUG; i < SPP_NDEBUG; i++) { 21725117Ssklower sd = &spp_debug[i]; 21825117Ssklower if (sppcb && sd->sd_cb != sppcb) 21925117Ssklower continue; 22025117Ssklower ntime = ntohl(sd->sd_time); 22125117Ssklower spp_trace(sd->sd_act, sd->sd_ostate, sd->sd_cb, &sd->sd_sp, 22225117Ssklower &sd->sd_si, sd->sd_req); 22325117Ssklower } 22425117Ssklower for (i = 0; i < spp_debx % SPP_NDEBUG; i++) { 22525117Ssklower sd = &spp_debug[i]; 22625117Ssklower if (sppcb && sd->sd_cb != sppcb) 22725117Ssklower continue; 22825117Ssklower ntime = ntohl(sd->sd_time); 22925117Ssklower spp_trace(sd->sd_act, sd->sd_ostate, sd->sd_cb, &sd->sd_sp, 23025117Ssklower &sd->sd_si, sd->sd_req); 23125117Ssklower } 23225117Ssklower } 23325117Ssklower 23425117Ssklower ptime(ms) 23525117Ssklower int ms; 23625117Ssklower { 23725117Ssklower 23825117Ssklower printf("%03d ", (ms/10) % 1000); 23925117Ssklower } 24025117Ssklower 24125117Ssklower numeric(c1, c2) 24225117Ssklower caddr_t *c1, *c2; 24325117Ssklower { 24425117Ssklower 24525117Ssklower return (*c1 - *c2); 24625117Ssklower } 24725117Ssklower 24825117Ssklower spp_trace(act, ostate, asp, sp, si, req) 24925117Ssklower short act, ostate; 25025117Ssklower struct sppcb *asp, *sp; 25125117Ssklower struct spidp *si; 25225117Ssklower int req; 25325117Ssklower { 25425117Ssklower u_short seq, ack, len, alo; 25525117Ssklower int flags, timer; 25625117Ssklower char *cp; 25725117Ssklower 25825117Ssklower if(ostate >= TCP_NSTATES) ostate = 0; 25925117Ssklower if(act > SA_DROP) act = SA_DROP; 26025117Ssklower printf("\n"); 26125117Ssklower ptime(ntime); 26225117Ssklower printf("%s:%s", tcpstates[ostate], sanames[act]); 26325117Ssklower 26425117Ssklower if (si != 0) { 26525117Ssklower seq = si->si_seq; 26625117Ssklower ack = si->si_ack; 26725117Ssklower alo = si->si_alo; 26825117Ssklower len = si->si_len; 26925117Ssklower switch (act) { 27025117Ssklower case SA_RESPOND: 27125117Ssklower case SA_OUTPUT: 27225117Ssklower seq = ntohs(seq); 27325117Ssklower ack = ntohs(ack); 27425117Ssklower alo = ntohs(alo); 27525117Ssklower len = ntohs(len); 27625117Ssklower case SA_INPUT: 27725117Ssklower case SA_DROP: 27825117Ssklower if (aflag) { 27925117Ssklower printf("\n\tsna="); 28025117Ssklower ns_printhost(&si->si_sna); 28125117Ssklower printf("\tdna="); 28225117Ssklower ns_printhost(&si->si_dna); 28325117Ssklower } 28425117Ssklower printf("\n\t"); 285*46933Sbostic #define p1(name, f) { \ 286*46933Sbostic printf("%s = %x, ", name, f); \ 287*46933Sbostic } 288*46933Sbostic p1("seq", seq); 289*46933Sbostic p1("ack", ack); 290*46933Sbostic p1("alo", alo); 291*46933Sbostic p1("len", len); 29225117Ssklower flags = si->si_cc; 29325117Ssklower printf("flags=%x", flags); 294*46933Sbostic #define pf(name, f) { \ 295*46933Sbostic if (flags & f) { \ 296*46933Sbostic printf("%s%s", cp, name); \ 297*46933Sbostic cp = ","; \ 298*46933Sbostic } \ 299*46933Sbostic } 30025117Ssklower if (flags) { 30125117Ssklower char *cp = "<"; 302*46933Sbostic pf("SP_SP", SP_SP); 303*46933Sbostic pf("SP_SA", SP_SA); 304*46933Sbostic pf("SP_OB", SP_OB); 305*46933Sbostic pf("SP_EM", SP_EM); 30625117Ssklower printf(">"); 30725117Ssklower } 30825117Ssklower printf(", "); 309*46933Sbostic #define p2(name, f) { \ 310*46933Sbostic printf("%s = %x, ", name, f); \ 311*46933Sbostic } 312*46933Sbostic p2("sid", si->si_sid); 313*46933Sbostic p2("did", si->si_did); 314*46933Sbostic p2("dt", si->si_dt); 31525117Ssklower printf("\n\tsna="); 31625117Ssklower ns_printhost(&si->si_sna); 31725117Ssklower printf("\tdna="); 31825117Ssklower ns_printhost(&si->si_dna); 31925117Ssklower } 32025117Ssklower } 32125117Ssklower if(act == SA_USER) { 32225117Ssklower printf("\treq=%s", prurequests[req&0xff]); 32325117Ssklower if ((req & 0xff) == PRU_SLOWTIMO) 32425117Ssklower printf("<%s>", tcptimers[req>>8]); 32525117Ssklower } 32625117Ssklower printf(" -> %s", tcpstates[sp->s_state]); 32725117Ssklower 32825117Ssklower /* print out internal state of sp !?! */ 32925117Ssklower printf("\n"); 33025117Ssklower if (sp == 0) 33125117Ssklower return; 332*46933Sbostic #define p3(name, f) { \ 333*46933Sbostic printf("%s = %x, ", name, f); \ 334*46933Sbostic } 335*46933Sbostic if (sflag) { 336*46933Sbostic printf("\t"); 337*46933Sbostic p3("rack", sp->s_rack); 338*46933Sbostic p3("ralo", sp->s_ralo); 339*46933Sbostic p3("smax", sp->s_smax); 340*46933Sbostic p3("snxt", sp->s_snxt); 341*46933Sbostic p3("flags", sp->s_flags); 34225117Ssklower #undef pf 343*46933Sbostic #define pf(name, f) { \ 344*46933Sbostic if (flags & f) { \ 345*46933Sbostic printf("%s%s", cp, name); \ 346*46933Sbostic cp = ","; \ 347*46933Sbostic } \ 348*46933Sbostic } 34925117Ssklower flags = sp->s_flags; 35025117Ssklower if (flags || sp->s_oobflags) { 35125117Ssklower char *cp = "<"; 352*46933Sbostic pf("ACKNOW", SF_ACKNOW); 353*46933Sbostic pf("DELACK", SF_DELACK); 354*46933Sbostic pf("HI", SF_HI); 355*46933Sbostic pf("HO", SF_HO); 356*46933Sbostic pf("PI", SF_PI); 357*46933Sbostic pf("WIN", SF_WIN); 358*46933Sbostic pf("RXT", SF_RXT); 359*46933Sbostic pf("RVD", SF_RVD); 36025117Ssklower flags = sp->s_oobflags; 361*46933Sbostic pf("SOOB", SF_SOOB); 362*46933Sbostic pf("IOOB", SF_IOOB); 36325117Ssklower printf(">"); 36425117Ssklower } 36525117Ssklower } 36625117Ssklower /* print out timers? */ 36725117Ssklower if (tflag) { 36825117Ssklower char *cp = "\t"; 36925117Ssklower register int i; 37025117Ssklower 37125117Ssklower printf("\n\tTIMERS: "); 372*46933Sbostic p3("idle", sp->s_idle); 373*46933Sbostic p3("force", sp->s_force); 374*46933Sbostic p3("rtseq", sp->s_rtseq); 37525117Ssklower for (i = 0; i < TCPT_NTIMERS; i++) { 37625117Ssklower if (sp->s_timer[i] == 0) 37725117Ssklower continue; 37825117Ssklower printf("%s%s=%d", cp, tcptimers[i], sp->s_timer[i]); 37925117Ssklower if (i == TCPT_REXMT) 38025117Ssklower printf(" (s_rxtshft=%d)", sp->s_rxtshift); 38125117Ssklower cp = ", "; 38225117Ssklower } 38325117Ssklower if (*cp != '\t') 38425117Ssklower putchar('\n'); 38525117Ssklower } 38625117Ssklower } 38725117Ssklower 38825117Ssklower ns_printhost(p) 38925117Ssklower register struct ns_addr *p; 39025117Ssklower { 39125117Ssklower 39225117Ssklower printf("<net:%x%x,host:%4.4x%4.4x%4.4x,port:%x>", 39325117Ssklower p->x_net.s_net[0], 39425117Ssklower p->x_net.s_net[1], 39525117Ssklower p->x_host.s_host[0], 39625117Ssklower p->x_host.s_host[1], 39725117Ssklower p->x_host.s_host[2], 39825117Ssklower p->x_port); 39925117Ssklower 40025117Ssklower } 40125117Ssklower 402