xref: /onnv-gate/usr/src/cmd/man/src/util/instant.src/info.c (revision 0:68f95e015346)
1 /*
2  *  Copyright 1993 Open Software Foundation, Inc., Cambridge, Massachusetts.
3  *  All rights reserved.
4  */
5 /*
6 #pragma ident	"%Z%%M%	%I%	%E% SMI"
7  * Copyright (c) 1994
8  * Open Software Foundation, Inc.
9  *
10  * Permission is hereby granted to use, copy, modify and freely distribute
11  * the software in this file and its documentation for any purpose without
12  * fee, provided that the above copyright notice appears in all copies and
13  * that both the copyright notice and this permission notice appear in
14  * supporting documentation.  Further, provided that the name of Open
15  * Software Foundation, Inc. ("OSF") not be used in advertising or
16  * publicity pertaining to distribution of the software without prior
17  * written permission from OSF.  OSF makes no representations about the
18  * suitability of this software for any purpose.  It is provided "as is"
19  * without express or implied warranty.
20  */
21 /*
22  * Copyright (c) 1996 X Consortium
23  * Copyright (c) 1995, 1996 Dalrymple Consulting
24  *
25  * Permission is hereby granted, free of charge, to any person obtaining a copy
26  * of this software and associated documentation files (the "Software"), to deal
27  * in the Software without restriction, including without limitation the rights
28  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
29  * copies of the Software, and to permit persons to whom the Software is
30  * furnished to do so, subject to the following conditions:
31  *
32  * The above copyright notice and this permission notice shall be included in
33  * all copies or substantial portions of the Software.
34  *
35  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
36  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
37  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
38  * X CONSORTIUM OR DALRYMPLE CONSULTING BE LIABLE FOR ANY CLAIM, DAMAGES OR
39  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
40  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
41  * OTHER DEALINGS IN THE SOFTWARE.
42  *
43  * Except as contained in this notice, the names of the X Consortium and
44  * Dalrymple Consulting shall not be used in advertising or otherwise to
45  * promote the sale, use or other dealings in this Software without prior
46  * written authorization.
47  */
48 /* ________________________________________________________________________
49  *
50  *  Functions for printing information about an instance in the 'instant'
51  *  program.  Most of these are fairly short and simple.
52  *
53  *  Entry points for this module:
54  *	PrintElemSummary(elem)	print summary info of each element
55  *	PrintContext(elem)	print context of each element
56  *	PrintElemTree(elem)	print tree of document
57  *	PrintStats(elem)	print statistics about doc tree
58  *	PrintIDList(elem)	print list of IDs and element context
59  *  Most Print*() functions start at subtree pointed to by 'elem'.
60  * ________________________________________________________________________
61  */
62 
63 #ifndef lint
64 static char *RCSid =
65   "$Header: /usr/src/docbook-to-man/Instant/RCS/info.c,v 1.2 1996/06/02 21:46:10 fld Exp $";
66 #endif
67 
68 #include <stdio.h>
69 #include <stdlib.h>
70 #include <ctype.h>
71 #include <string.h>
72 
73 #include "general.h"
74 
75 /* ______________________________________________________________________ */
76 /*  Print a summary of each tag use in the instance.  Things like depth in
77  *  the tree, number of children, parent, attributes.
78  */
79 
80 /*  Do the actual printing.  Print the info about the node.  If null,
81  *  print a header for the columns.
82  *  Arguments:
83  *	Pointer to element structure of the node to print.
84  */
85 static void
print_summ(Element_t * e)86 print_summ(
87     Element_t	*e
88 )
89 {
90     int i, n, dsize;
91     char *hfmt="%-18.18s %4s %5s %4s %4s %s\n";
92     char *fmt ="%-18.18s %4d %5d %4d %4d %s\n";
93 
94     if (e == NULL) {
95 	fprintf(outfp, hfmt, "Element", "Att", "Data", "Chd", "Dep", "Parent");
96 	return;
97     }
98     for (i=0,n=0; i<e->ncont; i++) if (IsContElem(e,i)) n++;
99     for (i=0,dsize=0; i<e->ncont; i++)
100 	if (IsContElem(e,i)) dsize += strlen(e->cont[i].ch.data);
101     fprintf(outfp, fmt, e->gi, e->natts, dsize, n, e->depth,
102 	e->parent ? e->parent->gi : "-");
103 
104     for (i=0; i<e->natts; i++) {
105 	fprintf(outfp, "%45d: %s = %s\n", i, e->atts[i].name,
106 	    e->atts[i].sval ? e->atts[i].sval : "empty");
107     }
108 }
109 
110 /*  Descend the tree, calling processing routine.
111  *  Arguments:
112  *	Pointer to element structure at top of tree to traverse.
113  */
114 void
PrintElemSummary(Element_t * e)115 PrintElemSummary(
116     Element_t	*e
117 )
118 {
119     print_summ(0);
120     DescendTree(e, print_summ, 0, 0, 0);
121 }
122 
123 /* ______________________________________________________________________ */
124 /*  Print the context of each tag in the instance (i.e. the tag with its
125  *  ancestors).
126  */
127 
128 /*  Do the actual printing.  Print the context of the node.
129  *  Arguments:
130  *	Pointer to element structure of the node to print.
131  */
132 static void
print_context(Element_t * e)133 print_context(
134     Element_t	*e
135 )
136 {
137     char buf[LINESIZE];
138 
139     fprintf(outfp, "%-22s %s\n", e->gi, FindContext(e, 10, buf));
140 }
141 
142 /*  Descend the tree, calling processing routine.
143  *  Arguments:
144  *	Pointer to element structure at top of tree to traverse.
145  */
146 void
PrintContext(Element_t * e)147 PrintContext(
148     Element_t	*e
149 )
150 {
151     fprintf(outfp, "%-22s %s\n", "Element", "Context");
152     fprintf(outfp, "%-22s %s\n", "---------------", "-----------");
153     DescendTree(e, print_context, 0, 0, 0);
154 
155     putc(NL, outfp);
156 }
157 
158 /* ______________________________________________________________________ */
159 /*  Print tree of the instance.  GI's are printed indented by their depth
160  *  in the tree.
161  */
162 
163 /*  Do the actual printing.  Print the element name, indented the right amount.
164  *  Arguments:
165  *	Pointer to element structure of the node to print.
166  */
167 static void
print_indent(Element_t * e)168 print_indent(
169     Element_t	*e
170 )
171 {
172     int		i, ne, nd;
173     for(i=0; i<e->depth; i++) fputs(".  ", outfp);
174     for(i=0,ne=0; i<e->ncont; i++) if (IsContElem(e,i)) ne++;
175     for(i=0,nd=0; i<e->ncont; i++) if IsContData(e,i) nd++;
176     fprintf(outfp, "%s  (%d,%d)\n", e->gi, ne, nd);
177 }
178 
179 /*  Descend the tree, calling processing routine.
180  *  Arguments:
181  *	Pointer to element structure at top of tree to traverse.
182  */
183 void
PrintElemTree(Element_t * e)184 PrintElemTree(
185     Element_t	*e
186 )
187 {
188     DescendTree(e, print_indent, 0, 0, 0);
189     putc(NL, outfp);
190 }
191 
192 /* ______________________________________________________________________ */
193 /*  Print some statistics about the instance.
194  */
195 
196 /*  Accumulate the totals for the statistics.
197  *  Arguments:
198  *	Pointer to element structure of the node to print.
199  *	Pointer to the total number of elements.
200  *	Pointer to the total amount of content data.
201  *	Pointer to the maximum depth of tree.
202  */
203 static void
acc_tots(Element_t * e,int * tot_el,int * tot_data,int * max_depth)204 acc_tots(
205     Element_t	*e,
206     int		*tot_el,
207     int		*tot_data,
208     int		*max_depth
209 )
210 {
211     int		i;
212     for(i=0; i<e->necont; i++)
213 	acc_tots(e->econt[i], tot_el, tot_data, max_depth);
214     for (i=0; i<e->necont; i++) (*tot_el)++;
215     for (i=0; i<e->ndcont; i++) (*tot_data) += strlen(e->dcont[i]);
216     if (e->depth > (*max_depth)) *max_depth = e->depth;
217 }
218 
219 /*  Descend the tree (recursively), collecting the statistics.
220  *  Arguments:
221  *	Pointer to element structure of the node to print.
222  *	Pointer to the total number of elements.
223  *	Pointer to the total amount of content data.
224  *	Pointer to the maximum depth of tree.
225  */
226 static void
elem_usage(Element_t * e,char * name,int * n_used,int * nchars)227 elem_usage(
228     Element_t	*e,
229     char	*name,
230     int		*n_used,
231     int		*nchars
232 )
233 {
234     int		i;
235     if (!strcmp(name, e->gi)) {
236 	(*n_used)++;
237 	for (i=0; i<e->ncont; i++)
238 	    if (IsContData(e,i)) (*nchars) += strlen(ContData(e,i));
239     }
240     for(i=0; i<e->necont; i++)
241 	elem_usage(e->econt[i], name, n_used, nchars);
242 }
243 
244 /*  Descend the tree, calling processing routine.
245  *  Arguments:
246  *	Pointer to element structure at top of tree to traverse.
247  */
248 void
PrintStats(Element_t * top)249 PrintStats(
250     Element_t	*top
251 )
252 {
253     int		i, n;
254     int		dif_el=0, tot_el=0, tot_data=0, nchars, max_depth=0;
255     float	pct;
256 
257     fprintf(outfp, "%-22s %s   %s\n", "Element name",    "Occurrances", "Character Content");
258     fprintf(outfp, "%-22s %s   %s\n", "---------------", "-----------", "-----------------");
259 
260     acc_tots(top, &tot_el, &tot_data, &max_depth);
261 
262     for (i=0; i<nUsedElem; i++) {
263 	n = 0;
264 	nchars = 0;
265 	elem_usage(top, UsedElem[i], &n, &nchars);
266 	if (n > 0) {
267 	    pct = 100.0 * (float)n / (float)tot_el;
268 	    fprintf(outfp, "%-22s %4d  %4.1f%%   %6d  %4d\n", UsedElem[i],
269 		n, pct, nchars, (nchars/n));
270 	    dif_el++;
271 	}
272     }
273 
274     fprintf(outfp, "\nTotal of %d elements used, %d different ones.\n",
275 	tot_el, dif_el);
276     fprintf(outfp, "Total character data: %d.\n", tot_data);
277     fprintf(outfp, "Maximum element depth: %d.\n", max_depth);
278     putc(NL, outfp);
279 }
280 
281 /* ______________________________________________________________________ */
282 /* Print list of: ID, GI, input file, line number, separated by colons.
283  * This is better for other programs to manipulate (like for keeping a
284  * database of IDs in documents) than humans to read.
285  */
286 
287 void
PrintIDList()288 PrintIDList()
289 {
290     ID_t	*id;
291     Element_t	*ep;
292 
293     for (id=IDList; id; id=id->next) {
294 	ep = id->elem;
295 	fprintf(outfp, "%s:%s:%s:%d\n", id->id, ep->gi,
296 		ep->infile?ep->infile:"-", ep->lineno);
297     }
298 }
299 
300 /* ______________________________________________________________________ */
301 
302