Add the DragonFly cvs id and perform general cleanups on cvs/rcs/sccs ids. Most
[dragonfly.git] / usr.sbin / atm / scspd / scsp_print.c
1 /*
2  *
3  * ===================================
4  * HARP  |  Host ATM Research Platform
5  * ===================================
6  *
7  *
8  * This Host ATM Research Platform ("HARP") file (the "Software") is
9  * made available by Network Computing Services, Inc. ("NetworkCS")
10  * "AS IS".  NetworkCS does not provide maintenance, improvements or
11  * support of any kind.
12  *
13  * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
14  * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
15  * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
16  * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
17  * In no event shall NetworkCS be responsible for any damages, including
18  * but not limited to consequential damages, arising from or relating to
19  * any use of the Software or related support.
20  *
21  * Copyright 1994-1998 Network Computing Services, Inc.
22  *
23  * Copies of this Software may be made, however, the above copyright
24  * notice must be reproduced on all copies.
25  *
26  *      @(#) $FreeBSD: src/usr.sbin/atm/scspd/scsp_print.c,v 1.3 1999/08/28 01:15:34 peter Exp $
27  *      @(#) $DragonFly: src/usr.sbin/atm/scspd/scsp_print.c,v 1.2 2003/06/17 04:29:52 dillon Exp $
28  */
29
30
31 /*
32  * Server Cache Synchronization Protocol (SCSP) Support
33  * ----------------------------------------------------
34  *
35  * Print routines
36  *
37  */
38
39 #include <sys/types.h>
40 #include <sys/param.h>
41 #include <sys/socket.h>
42 #include <net/if.h>
43 #include <netinet/in.h>
44 #include <netatm/port.h> 
45 #include <netatm/queue.h> 
46 #include <netatm/atm.h>
47 #include <netatm/atm_if.h>
48 #include <netatm/atm_sap.h>
49 #include <netatm/atm_sys.h>
50 #include <netatm/atm_ioctl.h>
51   
52 #include <errno.h>
53 #include <libatm.h>
54 #include <stdio.h>
55 #include <stdlib.h>
56 #include <string.h>
57 #include <syslog.h>
58 #include <unistd.h>
59
60 #include "scsp_msg.h"
61 #include "scsp_if.h"
62 #include "scsp_var.h"
63
64 /*
65  * Indent string
66  */
67 #define MIN_INDENT      2
68 #define MAX_INDENT      64
69 static char     indent[MAX_INDENT + 1];
70
71
72 /*
73  * Value-name translation table entry
74  */
75 struct type_name {
76         char    *name;
77         u_char  type;
78 };
79 typedef struct type_name        Type_name;
80
81
82 /*
83  * SCSP name-type tables
84  */
85 static Type_name if_msg_types[] = {
86         { "Config Request",             SCSP_CFG_REQ },
87         { "Config Response",            SCSP_CFG_RSP },
88         { "Cache Indication",           SCSP_CACHE_IND },
89         { "Cache Response",             SCSP_CACHE_RSP },
90         { "Solicit Indication",         SCSP_SOLICIT_IND },
91         { "Solicit Response",           SCSP_SOLICIT_RSP },
92         { "Cache Update Indication",    SCSP_UPDATE_IND },
93         { "Cache Update Request",       SCSP_UPDATE_REQ },
94         { "Cache Update Response",      SCSP_UPDATE_RSP },
95         { (char *)0,    0 }
96 };
97
98 static Type_name msg_types[] = {
99         { "Cache Alignment",    SCSP_CA_MSG },
100         { "CSU Request",        SCSP_CSU_REQ_MSG },
101         { "CSU Reply",          SCSP_CSU_REPLY_MSG },
102         { "CSU Solicit",        SCSP_CSUS_MSG },
103         { "Hello",              SCSP_HELLO_MSG },
104         { (char *)0,            0 }
105 };
106
107 static Type_name proto_types[] = {
108         { "ATMARP",     SCSP_PROTO_ATMARP },
109         { "NHRP",       SCSP_PROTO_NHRP },
110         { "MARS",       SCSP_PROTO_MARS },
111         { "DHCP",       SCSP_PROTO_DHCP },
112         { "LNNI",       SCSP_PROTO_LNNI },
113         { (char *)0,    0 }
114 };
115
116 static Type_name ext_types[] = {
117         { "End of Extensions",  SCSP_EXT_END },
118         { "Authentication",     SCSP_EXT_AUTH },
119         { "Vendor Private",     SCSP_EXT_VENDOR },
120         { (char *)0,            0 }
121 };
122
123 static Type_name hfsm_state_names[] = {
124         { "Down",               SCSP_HFSM_DOWN },
125         { "Waiting",            SCSP_HFSM_WAITING },
126         { "Unidirectional",     SCSP_HFSM_UNI_DIR },
127         { "Bidirectional",      SCSP_HFSM_BI_DIR },
128         { (char *)0,            0 }
129 };
130
131 static Type_name hfsm_event_names[] = {
132         { "VC open",            SCSP_HFSM_VC_ESTAB },
133         { "VC closed",          SCSP_HFSM_VC_CLOSED },
134         { "Hello timer",        SCSP_HFSM_HELLO_T },
135         { "Receive timer",      SCSP_HFSM_RCV_T },
136         { "Msg received",       SCSP_HFSM_RCVD },
137         { (char *)0,            0 }
138 };
139
140 static Type_name cafsm_state_names[] = {
141         { "Down",                       SCSP_CAFSM_DOWN },
142         { "Master/Slave negotiation",   SCSP_CAFSM_NEG },
143         { "Master",                     SCSP_CAFSM_MASTER },
144         { "Slave",                      SCSP_CAFSM_SLAVE },
145         { "Update cache",               SCSP_CAFSM_UPDATE },
146         { "Aligned",                    SCSP_CAFSM_ALIGNED },
147         { (char *)0,                    0 }
148 };
149
150 static Type_name cafsm_event_names[] = {
151         { "Hello FSM up",               SCSP_CAFSM_HELLO_UP },
152         { "Hello FSM down",             SCSP_CAFSM_HELLO_DOWN },
153         { "CA received",                SCSP_CAFSM_CA_MSG },
154         { "CSU Solicit received",       SCSP_CAFSM_CSUS_MSG },
155         { "CSU Request received",       SCSP_CAFSM_CSU_REQ },
156         { "CSU Reply received",         SCSP_CAFSM_CSU_REPLY },
157         { "CA timer",                   SCSP_CAFSM_CA_T },
158         { "CSUS timer",                 SCSP_CAFSM_CSUS_T },
159         { "CSU timer",                  SCSP_CAFSM_CSU_T },
160         { "Cache Update",               SCSP_CAFSM_CACHE_UPD },
161         { "Cache Response",             SCSP_CAFSM_CACHE_RSP },
162         { (char *)0,                    0 }
163 };
164
165 static Type_name cifsm_state_names[] = {
166         { "Null",       SCSP_CIFSM_NULL },
167         { "Summarize",  SCSP_CIFSM_SUM },
168         { "Update",     SCSP_CIFSM_UPD },
169         { "Aligned",    SCSP_CIFSM_ALIGN },
170         { (char *)0,                    0 }
171 };
172
173 static Type_name cifsm_event_names[] = {
174         { "CA FSM down",        SCSP_CIFSM_CA_DOWN },
175         { "CA FSM to Summarize",SCSP_CIFSM_CA_SUMM },
176         { "CA FSM to Update",   SCSP_CIFSM_CA_UPD },
177         { "CA FSM to Aligned",  SCSP_CIFSM_CA_ALIGN },
178         { "Solicit Rsp",        SCSP_CIFSM_SOL_RSP },
179         { "Update Req",         SCSP_CIFSM_UPD_REQ },
180         { "Update Rsp",         SCSP_CIFSM_UPD_RSP },
181         { "CSU Request",        SCSP_CIFSM_CSU_REQ },
182         { "CSU Reply",          SCSP_CIFSM_CSU_REPLY },
183         { "CSU Solicit",        SCSP_CIFSM_CSU_SOL },
184         { (char *)0,                    0 }
185 };
186
187 static Type_name atmarp_state_names[] = {
188         { "New",        SCSP_ASTATE_NEW },
189         { "Updated",    SCSP_ASTATE_UPD },
190         { "Deleted",    SCSP_ASTATE_DEL },
191         { (char *)0,    0 }
192 };
193
194
195 /*
196  * Initialize the indent string
197  *
198  * Arguments:
199  *      none
200  *
201  * Returns:
202  *      none
203  *
204  */
205 static void
206 init_indent()
207 {
208         indent[0] = '\0';
209 }
210
211
212 /*
213  * Increment the indent string
214  *
215  * Arguments:
216  *      none
217  *
218  * Returns:
219  *      none
220  *
221  */
222 static void
223 inc_indent()
224 {
225         if (strlen(indent) >= MAX_INDENT)
226                 return;
227         strcat(indent, "  ");
228 }
229
230
231 /*
232  * Decrement the indent string
233  *
234  * Arguments:
235  *      none
236  *
237  * Returns:
238  *      none
239  *
240  */
241 static void
242 dec_indent()
243 {
244         if (strlen(indent) < MIN_INDENT)
245                 return;
246         indent[strlen(indent) - 2] = '\0';
247 }
248
249
250
251 /*
252  * Search for a type in a name-type table
253  *
254  * Arguments:
255  *      type    the value being searched for
256  *      tbl     pointer to the table to search
257  *
258  * Returns:
259  *      pointer to a string identifying the type
260  *
261  */
262 static char *
263 scsp_type_name(type, tbl)
264         u_char  type;
265         Type_name       *tbl;
266 {
267         int     i;
268
269         /*
270          * Search the table
271          */
272         for (i = 0; tbl[i].name != (char *)0 && tbl[i].type != type;
273                         i++)
274                 ;
275
276         /*
277          * Check the result and return the appropriate value
278          */
279         if (tbl[i].name)
280                 return(tbl[i].name);
281         else
282                 return("-");
283 }
284
285
286 /*
287  * Format a Hello FSM state name
288  *
289  * Arguments:
290  *      state   the state
291  *
292  * Returns:
293  *      pointer to a string identifying the state
294  *
295  */
296 char *
297 format_hfsm_state(state)
298         int     state;
299 {
300         return(scsp_type_name((u_char)state, hfsm_state_names));
301 }
302
303
304 /*
305  * Format a Hello FSM event name
306  *
307  * Arguments:
308  *      event   the event
309  *
310  * Returns:
311  *      pointer to a string identifying the event
312  *
313  */
314 char *
315 format_hfsm_event(event)
316         int     event;
317 {
318         char    *cp;
319
320         cp = scsp_type_name((u_char)event, hfsm_event_names);
321         return(cp);
322 }
323
324
325 /*
326  * Format a CA FSM state name
327  *
328  * Arguments:
329  *      state   the state
330  *
331  * Returns:
332  *      pointer to a string identifying the state
333  *
334  */
335 char *
336 format_cafsm_state(state)
337         int     state;
338 {
339         return(scsp_type_name((u_char)state, cafsm_state_names));
340 }
341
342
343 /*
344  * Format a CA FSM event name
345  *
346  * Arguments:
347  *      event   the event
348  *
349  * Returns:
350  *      pointer to a string identifying the event
351  *
352  */
353 char *
354 format_cafsm_event(event)
355         int     event;
356 {
357         return(scsp_type_name((u_char)event, cafsm_event_names));
358 }
359
360
361 /*
362  * Format a client interface FSM state name
363  *
364  * Arguments:
365  *      state   the state
366  *
367  * Returns:
368  *      pointer to a string identifying the state
369  *
370  */
371 char *
372 format_cifsm_state(state)
373         int     state;
374 {
375         return(scsp_type_name((u_char)state, cifsm_state_names));
376 }
377
378
379 /*
380  * Format a client interface FSM event name
381  *
382  * Arguments:
383  *      event   the event
384  *
385  * Returns:
386  *      pointer to a string identifying the event
387  *
388  */
389 char *
390 format_cifsm_event(event)
391         int     event;
392 {
393         return(scsp_type_name((u_char)event, cifsm_event_names));
394 }
395
396
397 /*
398  * Print a Sender or Receiver ID structure
399  *
400  * Arguments:
401  *      fp      file to print message to
402  *      idp     pointer to ID to be printed
403  *
404  * Returns:
405  *      none
406  *
407  */
408 void
409 print_scsp_id(fp, idp)
410         FILE    *fp;
411         Scsp_id *idp;
412 {
413         int     i;
414
415         inc_indent();
416         fprintf(fp, "%sNext:                 %p\n", indent, idp->next);
417         fprintf(fp, "%sLength:               %d\n", indent,
418                         idp->id_len);
419         fprintf(fp, "%sID:                   0x", indent);
420         for (i = 0; i < idp->id_len; i++)
421                 fprintf(fp, "%02x ", idp->id[i]);
422         fprintf(fp, "\n");
423         dec_indent();
424 }
425
426
427 /*
428  * Print a Cache Key structure
429  *
430  * Arguments:
431  *      fp      file to print message to
432  *      ckp     pointer to cache key structure
433  *
434  * Returns:
435  *      none
436  *
437  */
438 void
439 print_scsp_cache_key(fp, ckp)
440         FILE            *fp;
441         Scsp_ckey       *ckp;
442 {
443         int     i;
444
445         inc_indent();
446         fprintf(fp, "%sLength:               %d\n", indent,
447                         ckp->key_len);
448         fprintf(fp, "%sKey:                  0x", indent);
449         for (i = 0; i < ckp->key_len; i++)
450                 fprintf(fp, "%02x ", ckp->key[i]);
451         fprintf(fp, "\n");
452         dec_indent();
453 }
454
455
456 /*
457  * Print the mandatory common part of a message
458  *
459  * Arguments:
460  *      fp      file to print message to
461  *      mcp     pointer to mandatory common part structure
462  *
463  * Returns:
464  *      none
465  *
466  */
467 static void
468 print_scsp_mcp(fp, mcp)
469         FILE            *fp;
470         Scsp_mcp        *mcp;
471 {
472         inc_indent();
473         fprintf(fp, "%sProtocol ID:          %s (0x%02x)\n", indent,
474                         scsp_type_name(mcp->pid, proto_types),
475                         mcp->pid);
476         fprintf(fp, "%sServer Group ID:      %d\n", indent, mcp->sgid);
477         fprintf(fp, "%sFlags:                0x%04x\n", indent,
478                         mcp->flags);
479         fprintf(fp, "%sRecord Count:         %d\n", indent,
480                         mcp->rec_cnt);
481         fprintf(fp, "%sSender ID:\n", indent);
482         print_scsp_id(fp, &mcp->sid);
483         fprintf(fp, "%sReceiver ID:\n", indent);
484         print_scsp_id(fp, &mcp->rid);
485         dec_indent();
486 }
487
488
489 /*
490  * Print an extension
491  *
492  * Arguments:
493  *      fp      file to print message to
494  *      exp     pointer to extension
495  *
496  * Returns:
497  *      none
498  *
499  */
500 static void
501 print_scsp_ext(fp, exp)
502         FILE            *fp;
503         Scsp_ext        *exp;
504 {
505         int     i;
506         u_char  *cp;
507
508         inc_indent();
509         fprintf(fp, "%sNext:                 %p\n", indent, exp->next);
510         fprintf(fp, "%sType:                 %s (0x%02x)\n", indent,
511                         scsp_type_name(exp->type, ext_types),
512                         exp->type);
513         fprintf(fp, "%sLength:               %d\n", indent, exp->len);
514         if (exp->len) {
515                 fprintf(fp, "%sValue:                0x", indent);
516                 cp = (u_char *)((caddr_t)exp + sizeof(Scsp_ext));
517                 for (i = 0; i < exp->len; i++)
518                         fprintf(fp, "%02x ", *cp++);
519                 fprintf(fp, "\n");
520         }
521         dec_indent();
522 }
523
524
525 /*
526  * Print an ATMARP Cache State Advertisement record
527  *
528  * Arguments:
529  *      fp      file to print message to
530  *      acsp    pointer to extension
531  *
532  * Returns:
533  *      none
534  *
535  */
536 static void
537 print_scsp_atmarp_csa(fp, acsp)
538         FILE            *fp;
539         Scsp_atmarp_csa *acsp;
540 {
541         inc_indent();
542         fprintf(fp, "%sState:                 %s (%d)\n", indent,
543                         scsp_type_name(acsp->sa_state,
544                                 atmarp_state_names),
545                         acsp->sa_state);
546         fprintf(fp, "%sSource ATM addr:       %s\n", indent,
547                         format_atm_addr(&acsp->sa_sha));
548         fprintf(fp, "%sSource ATM subaddr:    %s\n", indent,
549                         format_atm_addr(&acsp->sa_ssa));
550         fprintf(fp, "%sSource IP addr:        %s\n", indent,
551                         format_ip_addr(&acsp->sa_spa));
552         fprintf(fp, "%sTarget ATM addr:       %s\n", indent,
553                         format_atm_addr(&acsp->sa_tha));
554         fprintf(fp, "%sTarget ATM subaddr:    %s\n", indent,
555                         format_atm_addr(&acsp->sa_tsa));
556         fprintf(fp, "%sTarget IP addr:        %s\n", indent,
557                         format_ip_addr(&acsp->sa_tpa));
558         dec_indent();
559 }
560
561
562 /*
563  * Print a Cache State Advertisement record or
564  * Cache State Advertisement Summary record
565  *
566  * Arguments:
567  *      fp      file to print message to
568  *      csap    pointer to CSA or CSAS
569  *
570  * Returns:
571  *      none
572  *
573  */
574 static void
575 print_scsp_csa(fp, csap)
576         FILE            *fp;
577         Scsp_csa        *csap;
578 {
579         inc_indent();
580         fprintf(fp, "%sNext:                 %p\n", indent, csap->next);
581         fprintf(fp, "%sHops:                 %d\n", indent, csap->hops);
582         fprintf(fp, "%sNull Flag:            %s\n", indent,
583                         csap->null ? "True" : "False");
584         fprintf(fp, "%sSequence no.:         %ld (0x%lx)\n",
585                         indent, csap->seq, csap->seq);
586         fprintf(fp, "%sCache Key:\n", indent);
587         print_scsp_cache_key(fp, &csap->key);
588         fprintf(fp, "%sOriginator ID:\n", indent);
589         print_scsp_id(fp, &csap->oid);
590         if (csap->atmarp_data) {
591                 fprintf(fp, "%sATMARP data:\n", indent);
592                 print_scsp_atmarp_csa(fp, csap->atmarp_data);
593         }
594         dec_indent();
595 }
596
597
598 /*
599  * Print a Cache Alignment message
600  *
601  * Arguments:
602  *      fp      file to print message to
603  *      cap     pointer to extension
604  *
605  * Returns:
606  *      none
607  *
608  */
609 static void
610 print_scsp_ca(fp, cap)
611         FILE    *fp;
612         Scsp_ca *cap;
613 {
614         int             n;
615         Scsp_csa        *csap;
616
617         inc_indent();
618         fprintf(fp, "%sCA Seq. No.:          %ld\n", indent,
619                         cap->ca_seq);
620         fprintf(fp, "%sM bit:                %s\n", indent,
621                         cap->ca_m ? "True" : "False");
622         fprintf(fp, "%sI bit:                %s\n", indent,
623                         cap->ca_i ? "True" : "False");
624         fprintf(fp, "%sO bit:                %s\n", indent,
625                         cap->ca_o ? "True" : "False");
626         fprintf(fp, "%sMandatory Common Part:\n", indent);
627         print_scsp_mcp(fp, &cap->ca_mcp);
628         for (csap = cap->ca_csa_rec, n = 1; csap;
629                         csap = csap->next, n++) {
630                 fprintf(fp, "%sCSA Record %d (%p):\n", indent, n, csap);
631                 print_scsp_csa(fp, csap);
632         }
633         dec_indent();
634 }
635
636
637 /*
638  * Print a Cache State Update Request, Cache State Update Reply, or
639  * Cache State Update Solicit message
640  *
641  * Arguments:
642  *      fp      file to print message to
643  *      csup    pointer to CSU message
644  *
645  * Returns:
646  *      none
647  *
648  */
649 static void
650 print_scsp_csu(fp, csup)
651         FILE            *fp;
652         Scsp_csu_msg    *csup;
653 {
654         int             i;
655         Scsp_csa        *csap;
656
657         inc_indent();
658         fprintf(fp, "%sMandatory Common Part:\n", indent);
659         print_scsp_mcp(fp, &csup->csu_mcp);
660         for (csap = csup->csu_csa_rec, i = 1; csap;
661                         csap = csap->next, i++) {
662                 fprintf(fp, "%sCSA Record %d:\n", indent, i);
663                 print_scsp_csa(fp, csap);
664         }
665         dec_indent();
666 }
667
668
669 /*
670  * Print a Hello message
671  *
672  * Arguments:
673  *      fp      file to print message to
674  *      hp      pointer to hello message
675  *
676  * Returns:
677  *      none
678  *
679  */
680 static void
681 print_scsp_hello(fp, hp)
682         FILE            *fp;
683         Scsp_hello      *hp;
684 {
685         Scsp_id *ridp;
686
687         inc_indent();
688         fprintf(fp, "%sHello Interval:       %d\n", indent,
689                         hp->hello_int);
690         fprintf(fp, "%sDead Factor:          %d\n", indent,
691                         hp->dead_factor);
692         fprintf(fp, "%sFamily ID:            %d\n", indent,
693                         hp->family_id);
694         fprintf(fp, "%sMandatory Common Part:\n", indent);
695         print_scsp_mcp(fp, &hp->hello_mcp);
696         ridp = hp->hello_mcp.rid.next;
697         if (ridp) {
698                 fprintf(fp, "%sAdditional Receiver IDs:\n", indent);
699                 for (; ridp; ridp = ridp->next)
700                         print_scsp_id(fp, ridp);
701         }
702         dec_indent();
703 }
704
705
706 #ifdef NOTDEF
707 /*
708  * NHRP-specific Cache State Advertisement record
709  */
710 struct scsp_nhrp_csa {
711         u_char  req_id;                 /* Request ID */
712         u_char  state;                  /* State */
713         u_char  pref_len;               /* Prefix length */
714         u_short flags;                  /* See below */
715         u_short mtu;                    /* Maximim transmission unit */
716         u_short hold_time;              /* Entry holding time */
717         u_char  caddr_tlen;             /* Client addr type/length */
718         u_char  csaddr_tlen;            /* Client subaddr type/length */
719         u_char  cproto_len;             /* Client proto addr length */
720         u_char  pref;                   /* Preference */
721         Atm_addr        caddr;          /* Client address */
722         Atm_addr        csaddr;         /* Client subaddress */
723         struct in_addr  cproto_addr;    /* Client protocol address */
724 };
725 typedef struct scsp_nhrp        Scsp_nhrp;
726
727 #define SCSP_NHRP_UNIQ  0x8000
728 #define SCSP_NHRP_ARP   0x4000
729
730 #endif
731
732
733 /*
734  * Print an SCSP message
735  *
736  * Arguments:
737  *      fp      file to print message to
738  *      msg     pointer to message to be printed
739  *
740  * Returns:
741  *      none
742  *
743  */
744 void
745 print_scsp_msg(fp, msg)
746         FILE            *fp;
747         Scsp_msg        *msg;
748 {
749         int             n;
750         Scsp_ext        *exp;
751
752         /*
753          * Initialize
754          */
755         init_indent();
756
757         /*
758          * Print the message type
759          */
760         inc_indent();
761         fprintf(fp, "%sMessage type:         %s (0x%02x)\n", indent,
762                         scsp_type_name(msg->sc_msg_type, msg_types),
763                         msg->sc_msg_type);
764
765         /*
766          * Print the body of the message
767          */
768         switch(msg->sc_msg_type) {
769         case SCSP_CA_MSG:
770                 print_scsp_ca(fp, msg->sc_ca);
771                 break;
772         case SCSP_CSU_REQ_MSG:
773         case SCSP_CSU_REPLY_MSG:
774         case SCSP_CSUS_MSG:
775                 print_scsp_csu(fp, msg->sc_csu_msg);
776                 break;
777         case SCSP_HELLO_MSG:
778                 print_scsp_hello(fp, msg->sc_hello);
779                 break;
780         }
781
782         /*
783          * Print any extensions
784          */
785         for (exp = msg->sc_ext, n = 1; exp; exp = exp->next, n++) {
786                 fprintf(fp, "%sExtension %d:\n", indent, n);
787                 print_scsp_ext(fp, exp);
788         }
789         dec_indent();
790
791         (void)fflush(fp);
792 }
793
794
795 /*
796  * Print an SCSP ATMARP message
797  *
798  * Arguments:
799  *      fp      file to print message to
800  *      acp     pointer to ATMARP message
801  *
802  * Returns:
803  *      none
804  *
805  */
806 static void
807 print_scsp_if_atmarp(fp, amp)
808         FILE            *fp;
809         Scsp_atmarp_msg *amp;
810 {
811         inc_indent();
812         fprintf(fp, "%sState:                %s (%d)\n", indent,
813                         scsp_type_name(amp->sa_state,
814                                 atmarp_state_names),
815                         amp->sa_state);
816         fprintf(fp, "%sCached protocol addr: %s\n", indent,
817                         format_ip_addr(&amp->sa_cpa));
818         fprintf(fp, "%sCached ATM addr:      %s\n", indent,
819                         format_atm_addr(&amp->sa_cha));
820         fprintf(fp, "%sCached ATM subaddr:      %s\n", indent,
821                         format_atm_addr(&amp->sa_csa));
822         fprintf(fp, "%sCache key:\n", indent);
823         print_scsp_cache_key(fp, &amp->sa_key);
824         fprintf(fp, "%sOriginator ID:\n", indent);
825         print_scsp_id(fp, &amp->sa_oid);
826         fprintf(fp, "%sSequence number:         %ld (0x%08lx)\n", indent,
827                         amp->sa_seq, (u_long)amp->sa_seq);
828         dec_indent();
829 }
830
831
832 /*
833  * Print an SCSP client interface message
834  *
835  * Arguments:
836  *      fp      file to print message to
837  *      imsg    pointer to message to be printed
838  *
839  * Returns:
840  *      none
841  *
842  */
843 void
844 print_scsp_if_msg(fp, imsg)
845         FILE            *fp;
846         Scsp_if_msg     *imsg;
847 {
848         int             len;
849         Scsp_atmarp_msg *ap;
850
851         /*
852          * Initialize
853          */
854         init_indent();
855         fprintf(fp, "SCSP Client Interface Message at %p\n", imsg);
856
857         /*
858          * Print the message header
859          */
860         inc_indent();
861         fprintf(fp, "%sMessage type:         %s (0x%02x)\n", indent,
862                         scsp_type_name(imsg->si_type, if_msg_types),
863                         imsg->si_type);
864         fprintf(fp, "%sResponse code:        %d\n", indent,
865                         imsg->si_rc);
866         fprintf(fp, "%sProtocol type:        %s (%d)\n", indent,
867                         scsp_type_name(imsg->si_proto, proto_types),
868                         imsg->si_proto);
869         fprintf(fp, "%sLength:               %d\n", indent,
870                         imsg->si_len);
871         fprintf(fp, "%sToken:                0x%lx\n", indent,
872                         imsg->si_tok);
873
874         /*
875          * Print the body of the message
876          */
877         switch(imsg->si_type) {
878         case SCSP_CFG_REQ:
879                 fprintf(fp, "%sInterface:            %s\n", indent,
880                                 imsg->si_cfg.atmarp_netif);
881                 break;
882         case SCSP_CACHE_RSP:
883         case SCSP_UPDATE_IND:
884         case SCSP_UPDATE_REQ:
885                 len = imsg->si_len - sizeof(Scsp_if_msg_hdr);
886                 ap = &imsg->si_atmarp;
887                 while (len) {
888                         switch(imsg->si_proto) {
889                         case SCSP_PROTO_ATMARP:
890                                 fprintf(fp, "%sATMARP CSA:\n", indent);
891                                 print_scsp_if_atmarp(fp, ap);
892                                 len -= sizeof(Scsp_atmarp_msg);
893                                 ap++;
894                                 break;
895                         case SCSP_PROTO_NHRP:
896                         case SCSP_PROTO_MARS:
897                         case SCSP_PROTO_DHCP:
898                         case SCSP_PROTO_LNNI:
899                         default:
900                                 fprintf(fp, "Protocol type not implemented\n");
901                                 break;
902                         }
903                 }
904                 break;
905         }
906         dec_indent();
907
908         (void)fflush(fp);
909 }
910
911
912 /*
913  * Print an SCSP pending connection block
914  *
915  * Arguments:
916  *      fp      file to print message to
917  *      pp      pointer to pending control block
918  *
919  * Returns:
920  *      none
921  *
922  */
923 void
924 print_scsp_pending(fp, pp)
925         FILE            *fp;
926         Scsp_pending    *pp;
927 {
928         /*
929          * Initialize
930          */
931         init_indent();
932
933         /*
934          * Print a header
935          */
936         fprintf(fp, "Pending control block at %p\n", pp);
937
938         /*
939          * Print the fields of the control block
940          */
941         inc_indent();
942         fprintf(fp, "%sNext:                 %p\n", indent, pp->sp_next);
943         fprintf(fp, "%sSocket:               %d\n", indent,
944                         pp->sp_sock);
945
946         dec_indent();
947 }
948
949
950 /*
951  * Print an SCSP server control block
952  *
953  * Arguments:
954  *      fp      file to print message to
955  *      ssp     pointer to server control block
956  *
957  * Returns:
958  *      none
959  *
960  */
961 void
962 print_scsp_server(fp, ssp)
963         FILE            *fp;
964         Scsp_server     *ssp;
965 {
966         /*
967          * Initialize
968          */
969         init_indent();
970
971         /*
972          * Print a header
973          */
974         fprintf(fp, "Server control block at %p\n", ssp);
975
976         /*
977          * Print the fields of the client control block
978          */
979         inc_indent();
980         fprintf(fp, "%sNext:                 %p\n", indent,
981                         ssp->ss_next);
982         fprintf(fp, "%sName:                 %s\n", indent,
983                         ssp->ss_name);
984         fprintf(fp, "%sNetwork Interface:    %s\n", indent,
985                         ssp->ss_intf);
986         fprintf(fp, "%sState:                %d\n", indent,
987                         ssp->ss_state);
988         fprintf(fp, "%sProtocol ID:          0x%lx\n", indent,
989                         ssp->ss_pid);
990         fprintf(fp, "%sID length:            %d\n", indent,
991                         ssp->ss_id_len);
992         fprintf(fp, "%sCache key length:     %d\n", indent,
993                         ssp->ss_ckey_len);
994         fprintf(fp, "%sServer Group ID:      0x%lx\n", indent,
995                         ssp->ss_sgid);
996         fprintf(fp, "%sFamily ID:            0x%lx\n", indent,
997                         ssp->ss_fid);
998         fprintf(fp, "%sSocket:               %d\n", indent,
999                         ssp->ss_sock);
1000         fprintf(fp, "%sDCS Listen Socket:    %d\n", indent,
1001                         ssp->ss_dcs_lsock);
1002         fprintf(fp, "%sLocal Server ID:\n", indent);
1003         print_scsp_id(fp, &ssp->ss_lsid);
1004         fprintf(fp, "%sATM address:          %s\n", indent,
1005                         format_atm_addr(&ssp->ss_addr));
1006         fprintf(fp, "%sATM subaddress:       %s\n", indent,
1007                         format_atm_addr(&ssp->ss_subaddr));
1008         fprintf(fp, "%sInterface MTU:        %d\n", indent,
1009                         ssp->ss_mtu);
1010         fprintf(fp, "%sMark:                 %d\n", indent,
1011                         ssp->ss_mark);
1012         dec_indent();
1013 }
1014
1015
1016 /*
1017  * Print an SCSP client cache summary entry control block
1018  *
1019  * Arguments:
1020  *      fp      file to print message to
1021  *      csep    pointer to summary entry
1022  *
1023  * Returns:
1024  *      none
1025  *
1026  */
1027 void
1028 print_scsp_cse(fp, csep)
1029         FILE            *fp;
1030         Scsp_cse        *csep;
1031 {
1032         /*
1033          * Print the fields of the cache summary entry
1034          */
1035         inc_indent();
1036         fprintf(fp, "%sNext CSE:             %p\n", indent, csep->sc_next);
1037         fprintf(fp, "%sCSA sequence no.:     %ld (0x%lx)\n", indent,
1038                         csep->sc_seq, csep->sc_seq);
1039         fprintf(fp, "%sCache key:\n", indent);
1040         print_scsp_cache_key(fp, &csep->sc_key);
1041         fprintf(fp, "%sOrigin ID:\n", indent);
1042         print_scsp_id(fp, &csep->sc_oid);
1043         dec_indent();
1044 }
1045
1046
1047 /*
1048  * Print an SCSP CSU Request retransmission control block
1049  *
1050  * Arguments:
1051  *      fp      file to print message to
1052  *      csurp   pointer to retransmission entry
1053  *
1054  * Returns:
1055  *      none
1056  *
1057  */
1058 void
1059 print_scsp_csu_rexmt(fp, rxp)
1060         FILE            *fp;
1061         Scsp_csu_rexmt  *rxp;
1062 {
1063         int             i;
1064         Scsp_csa        *csap;
1065
1066         inc_indent();
1067         fprintf(fp, "%sNext CSU Req rexmt:   %p\n", indent, rxp->sr_next);
1068         fprintf(fp, "%sDCS address:          %p\n", indent, rxp->sr_dcs);
1069         for (csap = rxp->sr_csa, i = 1; csap;
1070                         csap = csap->next, i++) {
1071                 fprintf(fp, "%sCSA %d:\n", indent, i);
1072                 print_scsp_csa(fp, csap);
1073         }
1074         dec_indent();
1075 }
1076
1077
1078 /*
1079  * Print an SCSP DCS control block
1080  *
1081  * Arguments:
1082  *      fp      file to print message to
1083  *      dcsp    pointer to DCS control block
1084  *
1085  * Returns:
1086  *      none
1087  *
1088  */
1089 void
1090 print_scsp_dcs(fp, dcsp)
1091         FILE            *fp;
1092         Scsp_dcs        *dcsp;
1093 {
1094         Scsp_csa        *csap;
1095         Scsp_cse        *csep;
1096         Scsp_csu_rexmt  *rxp;
1097
1098         /*
1099          * Initialize
1100          */
1101         init_indent();
1102
1103         /*
1104          * Print a header
1105          */
1106         fprintf(fp, "DCS control block at %p\n", dcsp);
1107
1108         /*
1109          * Print the fields of the DCS control block
1110          */
1111         inc_indent();
1112         fprintf(fp, "%sNext DCS block:       %p\n", indent, dcsp->sd_next);
1113         fprintf(fp, "%sServer control block: %p\n", indent, dcsp->sd_server);
1114         fprintf(fp, "%sDCS ID:\n", indent);
1115         print_scsp_id(fp, &dcsp->sd_dcsid);
1116         fprintf(fp, "%sDCS address:          %s\n", indent,
1117                         format_atm_addr(&dcsp->sd_addr));
1118         fprintf(fp, "%sDCS subaddress        %s\n", indent,
1119                         format_atm_addr(&dcsp->sd_subaddr));
1120         fprintf(fp, "%sSocket:               %d\n", indent,
1121                         dcsp->sd_sock);
1122         fprintf(fp, "%sOpen VCC Retry Timer:\n", indent);
1123         fprintf(fp, "%sHello FSM State:      %s\n", indent,
1124                         format_hfsm_state(dcsp->sd_hello_state));
1125         fprintf(fp, "%sHello Interval:       %d\n", indent,
1126                         dcsp->sd_hello_int);
1127         fprintf(fp, "%sHello Dead Factor:    %d\n", indent,
1128                         dcsp->sd_hello_df);
1129         fprintf(fp, "%sHello Rcvd:           %d\n", indent,
1130                         dcsp->sd_hello_rcvd);
1131         fprintf(fp, "%sCA FSM State:         %s\n", indent,
1132                         format_cafsm_state(dcsp->sd_ca_state));
1133         fprintf(fp, "%sCA Seq. No.:          0x%lx\n", indent,
1134                         dcsp->sd_ca_seq);
1135         fprintf(fp, "%sCA Rexmit Int:        %d\n", indent,
1136                         dcsp->sd_ca_rexmt_int);
1137         fprintf(fp, "%sCA Retransmit Msg:    %p\n", indent,
1138                         dcsp->sd_ca_rexmt_msg);
1139         fprintf(fp, "%sCSASs to send:        ", indent);
1140         if (dcsp->sd_ca_csas == (Scsp_cse *)0) {
1141                 fprintf(fp, "Empty\n");
1142         } else {
1143                 fprintf(fp, "%p\n", dcsp->sd_ca_csas);
1144         }
1145         fprintf(fp, "%sCSUS Rexmit Int:      %d\n", indent,
1146                         dcsp->sd_csus_rexmt_int);
1147         fprintf(fp, "%sCache Request List:   ", indent);
1148         if (dcsp->sd_crl == (Scsp_csa *)0) {
1149                 fprintf(fp, "Empty\n");
1150         } else {
1151                 fprintf(fp, "%p\n", dcsp->sd_crl);
1152         }
1153         fprintf(fp, "%sCSUS Rexmit Msg:      %p\n", indent,
1154                         dcsp->sd_csus_rexmt_msg);
1155         fprintf(fp, "%sCSA Hop count:        %d\n", indent,
1156                         dcsp->sd_hops);
1157         fprintf(fp, "%sCSAs Pending ACK:     %p\n", indent,
1158                         dcsp->sd_csu_ack_pend);
1159         fprintf(fp, "%sCSAs ACKed:           %p\n", indent,
1160                         dcsp->sd_csu_ack);
1161         fprintf(fp, "%sCSU Req Rexmit Int:   %d\n", indent,
1162                         dcsp->sd_csu_rexmt_int);
1163         fprintf(fp, "%sCSU Req Rexmit Max:   %d\n", indent,
1164                         dcsp->sd_csu_rexmt_max);
1165         fprintf(fp, "%sCSU Req Rexmit Queue  ", indent);
1166         if (!dcsp->sd_csu_rexmt) {
1167                 fprintf(fp, "Empty\n");
1168         } else {
1169                 fprintf(fp, "%p\n", dcsp->sd_csu_rexmt);
1170         }
1171         fprintf(fp, "%sClient I/F state:     %d\n", indent,
1172                         dcsp->sd_client_state);
1173
1174         /*
1175          * Print the list of CSASs waiting to be sent
1176          */
1177         if (dcsp->sd_ca_csas) {
1178                 fprintf(fp, "\n%sCSASs to send:", indent);
1179                 inc_indent();
1180                 for (csep = dcsp->sd_ca_csas; csep;
1181                                 csep = csep->sc_next) {
1182                         fprintf(fp, "%sCache summary entry at %p\n",
1183                                         indent, csep);
1184                         print_scsp_cse(fp, csep);
1185                 }
1186                 dec_indent();
1187         }
1188
1189         /*
1190          * Print the Cache Request List
1191          */
1192         if (dcsp->sd_crl) {
1193                 fprintf(fp, "\n%sCache Request List:\n", indent);
1194                 inc_indent();
1195                 for (csap = dcsp->sd_crl; csap; csap = csap->next) {
1196                         fprintf(fp, "%sCSA at %p\n", indent, csap);
1197                         print_scsp_csa(fp, csap);
1198                 }
1199                 dec_indent();
1200         }
1201
1202         /*
1203          * Print the CSU retransmit queue
1204          */
1205         if (dcsp->sd_csu_rexmt) {
1206                 fprintf(fp, "\n%sCSU Req Rexmit Queue:\n", indent);
1207                 inc_indent();
1208                 for (rxp = dcsp->sd_csu_rexmt; rxp;
1209                                 rxp = rxp->sr_next) {
1210                         fprintf(fp, "%sCSU Rexmit Block at %p\n",
1211                                         indent, rxp);
1212                         print_scsp_csu_rexmt(fp, rxp);
1213                 }
1214                 dec_indent();
1215         }
1216
1217         dec_indent();
1218 }
1219
1220
1221 /*
1222  * Print SCSP's control blocks
1223  *
1224  * Arguments:
1225  *      none
1226  *
1227  * Returns:
1228  *      None
1229  *
1230  */
1231 void
1232 print_scsp_dump()
1233 {
1234         int             i;
1235         Scsp_server     *ssp;
1236         Scsp_dcs        *dcsp;
1237         Scsp_cse        *scp;
1238         Scsp_pending    *pp;
1239         FILE            *df;
1240         char            fname[64];
1241         static int      dump_no = 0;
1242
1243         /*
1244          * Build a file name
1245          */
1246         UM_ZERO(fname, sizeof(fname));
1247         sprintf(fname, "/tmp/scspd.%d.%03d.out", getpid(), dump_no++);
1248
1249         /*
1250          * Open the output file
1251          */
1252         df = fopen(fname, "w");
1253         if (df == (FILE *)0)
1254                 return;
1255
1256         /*
1257          * Dump the server control blocks
1258          */
1259         for (ssp = scsp_server_head; ssp; ssp = ssp->ss_next) {
1260                 print_scsp_server(df, ssp);
1261                 fprintf(df, "\n");
1262
1263                 /*
1264                  * Print the client's cache summary
1265                  */
1266                 for (i = 0; i < SCSP_HASHSZ; i++) {
1267                         for (scp = ssp->ss_cache[i]; scp;
1268                                         scp = scp->sc_next) {
1269                                 print_scsp_cse(df, scp);
1270                                 fprintf(df, "\n");
1271                         }
1272                 }
1273
1274                 /*
1275                  * Print the client's DCS control blocks
1276                  */
1277                 for (dcsp = ssp->ss_dcs; dcsp; dcsp = dcsp->sd_next) {
1278                         print_scsp_dcs(df, dcsp);
1279                         fprintf(df, "\n\n");
1280                 }
1281                 fprintf(df, "\n\n");
1282         }
1283
1284         /*
1285          * Print the pending connection blocks
1286          */
1287         for (pp = scsp_pending_head; pp; pp = pp->sp_next) {
1288                 print_scsp_pending(df, pp);
1289                 fprintf(df, "\n");
1290         }
1291
1292         /*
1293          * Close the output file
1294          */
1295         (void)fclose(df);
1296 }