Line data Source code
1 : /* RCS $Id: dmdump.c,v 1.4 2007-06-12 06:05:11 obo Exp $
2 : --
3 : -- SYNOPSIS
4 : -- Dump the internal dag to stdout.
5 : --
6 : -- DESCRIPTION
7 : -- This file contains the routine that is called to dump a version of
8 : -- the digested makefile to the standard output. May be useful perhaps
9 : -- to the ordinary user, and invaluable for debugging make.
10 : --
11 : -- AUTHOR
12 : -- Dennis Vadura, dvadura@dmake.wticorp.com
13 : --
14 : -- WWW
15 : -- http://dmake.wticorp.com/
16 : --
17 : -- COPYRIGHT
18 : -- Copyright (c) 1996,1997 by WTI Corp. All rights reserved.
19 : --
20 : -- This program is NOT free software; you can redistribute it and/or
21 : -- modify it under the terms of the Software License Agreement Provided
22 : -- in the file <distribution-root>/readme/license.txt.
23 : --
24 : -- LOG
25 : -- Use cvs log to obtain detailed change logs.
26 : */
27 :
28 : #include "extern.h"
29 :
30 : #define M_TEST (M_PRECIOUS | M_VAR_MASK)
31 :
32 : static void dump_name ANSI((CELLPTR, int, int));
33 : static void dump_normal_target ANSI((CELLPTR, CELLPTR, int));
34 : static void dump_prerequisites ANSI((LINKPTR, CELLPTR, int, int, int));
35 : static void dump_conditionals ANSI((CELLPTR,STRINGPTR,int,int));
36 : static void dump_macro ANSI((HASHPTR, int));
37 :
38 :
39 : PUBLIC void
40 0 : Dump()/*
41 : ======== Dump onto standard output the digested makefile. Note that
42 : the form of the dump is not representative of the contents
43 : of the original makefile contents at all */
44 : {
45 : HASHPTR hp;
46 : int i;
47 :
48 : DB_ENTER( "Dump" );
49 :
50 0 : puts( "# Dump of dmake macro variables:" );
51 0 : for( i=0; i<HASH_TABLE_SIZE; i++)
52 0 : for( hp=Macs[i]; hp != NIL(HASH); hp = hp->ht_next ) {
53 0 : int flag = hp->ht_flag;
54 0 : dump_macro(hp, flag);
55 : }
56 :
57 0 : puts( "\n#====================================" );
58 0 : puts( "# Dump of targets:\n" );
59 :
60 0 : for( i=0; i<HASH_TABLE_SIZE; i++ )
61 0 : for( hp = Defs[i]; hp != NIL(HASH); hp = hp->ht_next )
62 0 : if( !(hp->CP_OWNR->ce_flag & F_PERCENT) ) {
63 0 : if( hp->CP_OWNR == Root )
64 0 : puts( "# ******* ROOT TARGET ********" );
65 0 : if (Targets->ce_prq && hp->CP_OWNR == Targets->ce_prq->cl_prq)
66 0 : puts( "# ******* FIRST USER DEFINED TARGET ******" );
67 0 : dump_normal_target( hp->CP_OWNR,NIL(CELL),hp->CP_OWNR->ce_flag);
68 : }
69 :
70 0 : puts( "\n#====================================" );
71 0 : puts( "# Dump of inference graph\n" );
72 :
73 0 : for( i=0; i<HASH_TABLE_SIZE; i++ )
74 0 : for( hp = Defs[i]; hp != NIL(HASH); hp = hp->ht_next )
75 0 : if( (hp->CP_OWNR->ce_flag & F_PERCENT) &&
76 0 : !(hp->CP_OWNR->ce_flag & F_MAGIC) )
77 0 : dump_normal_target(hp->CP_OWNR,NIL(CELL),hp->CP_OWNR->ce_flag);
78 :
79 0 : DB_VOID_RETURN;
80 : }
81 :
82 :
83 :
84 : PUBLIC void
85 0 : Dump_recipe( sp )/*
86 : ===================
87 : Given a string pointer print the recipe line out */
88 : STRINGPTR sp;
89 : {
90 : char *st;
91 : char *nl;
92 :
93 0 : if( sp == NIL(STRING) ) return;
94 :
95 0 : putchar( '\t' );
96 0 : if( sp->st_attr & A_SILENT ) putchar( '@' );
97 0 : if( sp->st_attr & A_IGNORE ) putchar( '-' );
98 0 : if( sp->st_attr & A_SHELL ) putchar( '+' );
99 0 : if( sp->st_attr & A_SWAP ) putchar( '%' );
100 :
101 0 : st = sp->st_string;
102 0 : for( nl=strchr(st,'\n'); nl != NIL( char); nl=strchr(st,'\n') ) {
103 0 : *nl = '\0';
104 0 : printf( "%s\\\n", st );
105 0 : *nl = '\n';
106 0 : st = nl+1;
107 : }
108 0 : printf( "%s\n", st );
109 : }
110 :
111 :
112 : static char *_attrs[] = { ".PRECIOUS", ".SILENT", ".LIBRARY",
113 : ".EPILOG", ".PROLOG", ".IGNORE", ".SYMBOL", ".NOINFER",
114 : ".UPDATEALL", ".SEQUENTIAL", ".SETDIR=", ".USESHELL",
115 : #if defined(MSDOS)
116 : ".SWAP",
117 : #else
118 : # if defined(__CYGWIN__)
119 : ".WINPATH",
120 : # else
121 : "- unused -",
122 : # endif
123 : #endif
124 : ".MKSARGS",
125 : ".PHONY", ".NOSTATE", ".IGNOREGROUP", ".EXECUTE", ".ERRREMOVE" };
126 :
127 : static void
128 0 : dump_normal_target( cp, namecp, flag )/*
129 : ========================================
130 : Dump in makefile like format the dag information */
131 : CELLPTR cp;
132 : CELLPTR namecp;
133 : int flag;
134 : {
135 : register STRINGPTR sp;
136 : t_attr attr;
137 : unsigned int k;
138 :
139 : DB_ENTER( "dump_normal_target" );
140 :
141 0 : if(!(cp->ce_flag & F_TARGET) && !cp->ce_attr && !cp->ce_prq) {
142 0 : DB_VOID_RETURN;
143 : }
144 :
145 0 : if(cp->ce_set && cp->ce_set != cp) {
146 0 : DB_VOID_RETURN;
147 : }
148 :
149 0 : if( cp->ce_flag & F_MULTI ) {
150 : /* recursively print multi or %-targets. */
151 0 : int tflag = cp->ce_prq->cl_prq->ce_flag;
152 0 : if( !(cp->ce_flag & F_PERCENT) ) tflag |= F_MULTI;
153 0 : dump_conditionals(cp, cp->ce_cond, TRUE, TRUE);
154 0 : putchar('\n');
155 :
156 : #ifdef DBUG
157 : /* Output also master targtet. (Only in debug builds) */
158 : printf("Master name(s) (DBUG build): ");
159 : dump_name(cp, FALSE, TRUE );
160 : putchar('\n');
161 : #endif
162 :
163 : /* %-targets set namecp (3rd parameter) to NULL so that the next
164 : * recursive dump_normal_target() prints the name of cp->ce_prq->cl_prq
165 : * instead of cp. This should be the same unless CeMeToo(cp) points
166 : * to a cell that is the head of an .UPDATEALL list. */
167 0 : dump_prerequisites(cp->ce_prq,(cp->ce_flag&F_PERCENT)?NIL(CELL):cp,
168 : FALSE, TRUE, tflag);
169 : }
170 : else {
171 0 : dump_name(namecp?namecp:cp, FALSE, TRUE );
172 :
173 0 : for( k=0, attr=1; attr <= MAX_ATTR; attr <<= 1, k++ )
174 0 : if( cp->ce_attr & attr ) {
175 0 : printf( "%s%s ", _attrs[k],
176 0 : (attr != A_SETDIR) ? "" : (cp->ce_dir?cp->ce_dir:"") );
177 : }
178 :
179 0 : putchar( ':' );
180 :
181 0 : if( flag & F_MULTI ) putchar( ':' );
182 0 : if( flag & F_SINGLE ) putchar( '!' );
183 0 : putchar( ' ' );
184 :
185 0 : dump_prerequisites( cp->ce_prq, NIL(CELL), FALSE, FALSE, F_DEFAULT);
186 0 : dump_prerequisites( cp->ce_indprq, NIL(CELL),TRUE, FALSE, F_DEFAULT);
187 :
188 0 : putchar( '\n' );
189 0 : if( cp->ce_flag & F_GROUP ) puts( "[" );
190 0 : for( sp = cp->ce_recipe; sp != NIL(STRING); sp = sp->st_next )
191 0 : Dump_recipe( sp );
192 0 : if( cp->ce_flag & F_GROUP ) {
193 0 : puts( "]" );
194 0 : putchar( '\n' );
195 : }
196 0 : dump_conditionals(cp, cp->ce_cond, flag&F_MULTI, FALSE);
197 0 : putchar('\n');
198 : }
199 :
200 0 : DB_VOID_RETURN;
201 : }
202 :
203 :
204 : static void
205 0 : dump_conditionals( cp, sp, multi, global )
206 : CELLPTR cp;
207 : STRINGPTR sp;
208 : int multi;
209 : int global;
210 : {
211 0 : if (sp) {
212 0 : dump_name(cp, FALSE, TRUE);
213 0 : printf(".%sCONDITIONALS %s\n", global?"GLOBAL":"",multi?"::":":");
214 :
215 0 : while(sp) {
216 0 : printf("\t%s\n",sp->st_string);
217 0 : sp=sp->st_next;
218 : }
219 : }
220 0 : }
221 :
222 :
223 : static void
224 0 : dump_macro(hp, flag)
225 : HASHPTR hp;
226 : int flag;
227 : {
228 0 : printf( "%s ", hp->ht_name );
229 0 : if(flag & M_EXPANDED)
230 0 : putchar( ':' );
231 :
232 0 : printf( "= " );
233 0 : if(hp->ht_value != NIL(char))
234 0 : printf( "%s",hp->ht_value );
235 :
236 0 : if(flag & M_PRECIOUS)
237 0 : printf( "\t # PRECIOUS " );
238 :
239 0 : putchar( '\n' );
240 0 : }
241 :
242 :
243 : static void
244 0 : dump_prerequisites( lp, namecp, quote, recurse, flag )/*
245 : ========================================================
246 : Dump as prerequisites if recurse is FALSE or as targets
247 : if recurse is TRUE. (For F_MULTI/F_PERCENT targets.) */
248 : LINKPTR lp;
249 : CELLPTR namecp;
250 : int quote;
251 : int recurse;
252 : int flag;
253 : {
254 0 : for( ; lp; lp=lp->cl_next )
255 0 : if( recurse )
256 0 : dump_normal_target(lp->cl_prq, namecp, flag);
257 0 : else if( lp->cl_prq )
258 0 : dump_name(lp->cl_prq, quote, FALSE);
259 0 : }
260 :
261 :
262 : static void
263 0 : dump_name( cp, quote, all )/*
264 : =============================
265 : Prints out the first or all (if all is TRUE) names of an lcell list.
266 : If quote is true enclose in ' quotes, if quote
267 : is FALSE and the name includes a space enclose in " quotes. */
268 : CELLPTR cp;
269 : int quote;
270 : int all;
271 : {
272 : LINKPTR lp;
273 0 : char qc = '\'';
274 :
275 0 : for(lp=CeMeToo(cp);lp;lp=lp->cl_next) {
276 0 : if( !quote && strchr(lp->cl_prq->CE_NAME,' ') != NIL(char)) {
277 0 : quote = TRUE;
278 0 : qc = '"';
279 : }
280 :
281 0 : if (quote) putchar(qc);
282 0 : printf( "%s", lp->cl_prq->CE_NAME );
283 0 : if (quote) putchar(qc);
284 0 : putchar(' ');
285 0 : if (!all) break;
286 : }
287 0 : }
|