1*3625efb1SRichard Lowe /*
2*3625efb1SRichard Lowe * CDDL HEADER START
3*3625efb1SRichard Lowe *
4*3625efb1SRichard Lowe * The contents of this file are subject to the terms of the
5*3625efb1SRichard Lowe * Common Development and Distribution License (the "License").
6*3625efb1SRichard Lowe * You may not use this file except in compliance with the License.
7*3625efb1SRichard Lowe *
8*3625efb1SRichard Lowe * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9*3625efb1SRichard Lowe * or http://www.opensolaris.org/os/licensing.
10*3625efb1SRichard Lowe * See the License for the specific language governing permissions
11*3625efb1SRichard Lowe * and limitations under the License.
12*3625efb1SRichard Lowe *
13*3625efb1SRichard Lowe * When distributing Covered Code, include this CDDL HEADER in each
14*3625efb1SRichard Lowe * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15*3625efb1SRichard Lowe * If applicable, add the following below this CDDL HEADER, with the
16*3625efb1SRichard Lowe * fields enclosed by brackets "[]" replaced with your own identifying
17*3625efb1SRichard Lowe * information: Portions Copyright [yyyy] [name of copyright owner]
18*3625efb1SRichard Lowe *
19*3625efb1SRichard Lowe * CDDL HEADER END
20*3625efb1SRichard Lowe */
21*3625efb1SRichard Lowe /*
22*3625efb1SRichard Lowe * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
23*3625efb1SRichard Lowe * Use is subject to license terms.
24*3625efb1SRichard Lowe */
25*3625efb1SRichard Lowe
26*3625efb1SRichard Lowe /*
27*3625efb1SRichard Lowe * state.c
28*3625efb1SRichard Lowe *
29*3625efb1SRichard Lowe * This file contains the routines that write the .make.state file
30*3625efb1SRichard Lowe */
31*3625efb1SRichard Lowe
32*3625efb1SRichard Lowe /*
33*3625efb1SRichard Lowe * Included files
34*3625efb1SRichard Lowe */
35*3625efb1SRichard Lowe #include <mk/defs.h>
36*3625efb1SRichard Lowe #include <mksh/misc.h> /* errmsg() */
37*3625efb1SRichard Lowe #include <setjmp.h> /* setjmp() */
38*3625efb1SRichard Lowe #include <unistd.h> /* getpid() */
39*3625efb1SRichard Lowe #include <errno.h> /* errno */
40*3625efb1SRichard Lowe #include <locale.h> /* MB_CUR_MAX */
41*3625efb1SRichard Lowe
42*3625efb1SRichard Lowe /*
43*3625efb1SRichard Lowe * Defined macros
44*3625efb1SRichard Lowe */
45*3625efb1SRichard Lowe #define LONGJUMP_VALUE 17
46*3625efb1SRichard Lowe #define XFWRITE(string, length, fd) {if (fwrite(string, 1, length, fd) == 0) \
47*3625efb1SRichard Lowe longjmp(long_jump, LONGJUMP_VALUE);}
48*3625efb1SRichard Lowe #define XPUTC(ch, fd) { \
49*3625efb1SRichard Lowe if (putc((int) ch, fd) == EOF) \
50*3625efb1SRichard Lowe longjmp(long_jump, LONGJUMP_VALUE); \
51*3625efb1SRichard Lowe }
52*3625efb1SRichard Lowe #define XFPUTS(string, fd) fputs(string, fd)
53*3625efb1SRichard Lowe
54*3625efb1SRichard Lowe /*
55*3625efb1SRichard Lowe * typedefs & structs
56*3625efb1SRichard Lowe */
57*3625efb1SRichard Lowe
58*3625efb1SRichard Lowe /*
59*3625efb1SRichard Lowe * Static variables
60*3625efb1SRichard Lowe */
61*3625efb1SRichard Lowe
62*3625efb1SRichard Lowe /*
63*3625efb1SRichard Lowe * File table of contents
64*3625efb1SRichard Lowe */
escape_target_name(Name np)65*3625efb1SRichard Lowe static char * escape_target_name(Name np)
66*3625efb1SRichard Lowe {
67*3625efb1SRichard Lowe if(np->dollar) {
68*3625efb1SRichard Lowe int len = strlen(np->string_mb);
69*3625efb1SRichard Lowe char * buff = (char*)malloc(2 * len);
70*3625efb1SRichard Lowe int pos = 0;
71*3625efb1SRichard Lowe wchar_t wc;
72*3625efb1SRichard Lowe int pp = 0;
73*3625efb1SRichard Lowe while(pos < len) {
74*3625efb1SRichard Lowe int n = mbtowc(&wc, np->string_mb + pos, MB_CUR_MAX);
75*3625efb1SRichard Lowe if(n < 0) { // error - this shouldn't happen
76*3625efb1SRichard Lowe (void)free(buff);
77*3625efb1SRichard Lowe return strdup(np->string_mb);
78*3625efb1SRichard Lowe }
79*3625efb1SRichard Lowe if(wc == dollar_char) {
80*3625efb1SRichard Lowe buff[pp] = '\\'; pp++;
81*3625efb1SRichard Lowe buff[pp] = '$'; pp++;
82*3625efb1SRichard Lowe } else {
83*3625efb1SRichard Lowe for(int j=0;j<n;j++) {
84*3625efb1SRichard Lowe buff[pp] = np->string_mb[pos+j]; pp++;
85*3625efb1SRichard Lowe }
86*3625efb1SRichard Lowe }
87*3625efb1SRichard Lowe pos += n;
88*3625efb1SRichard Lowe }
89*3625efb1SRichard Lowe buff[pp] = '\0';
90*3625efb1SRichard Lowe return buff;
91*3625efb1SRichard Lowe } else {
92*3625efb1SRichard Lowe return strdup(np->string_mb);
93*3625efb1SRichard Lowe }
94*3625efb1SRichard Lowe }
95*3625efb1SRichard Lowe
96*3625efb1SRichard Lowe static void print_auto_depes(register Dependency dependency, register FILE *fd, register Boolean built_this_run, register int *line_length, register char *target_name, jmp_buf long_jump);
97*3625efb1SRichard Lowe
98*3625efb1SRichard Lowe /*
99*3625efb1SRichard Lowe * write_state_file(report_recursive, exiting)
100*3625efb1SRichard Lowe *
101*3625efb1SRichard Lowe * Write a new version of .make.state
102*3625efb1SRichard Lowe *
103*3625efb1SRichard Lowe * Parameters:
104*3625efb1SRichard Lowe * report_recursive Should only be done at end of run
105*3625efb1SRichard Lowe * exiting true if called from the exit handler
106*3625efb1SRichard Lowe *
107*3625efb1SRichard Lowe * Global variables used:
108*3625efb1SRichard Lowe * built_last_make_run The Name ".BUILT_LAST_MAKE_RUN", written
109*3625efb1SRichard Lowe * command_changed If no command changed we do not need to write
110*3625efb1SRichard Lowe * current_make_version The Name "<current version>", written
111*3625efb1SRichard Lowe * do_not_exec_rule If -n is on we do not write statefile
112*3625efb1SRichard Lowe * hashtab The hashtable that contains all names
113*3625efb1SRichard Lowe * keep_state If .KEEP_STATE is no on we do not write file
114*3625efb1SRichard Lowe * make_state The Name ".make.state", used for opening file
115*3625efb1SRichard Lowe * make_version The Name ".MAKE_VERSION", written
116*3625efb1SRichard Lowe * recursive_name The Name ".RECURSIVE", written
117*3625efb1SRichard Lowe * rewrite_statefile Indicates that something changed
118*3625efb1SRichard Lowe */
119*3625efb1SRichard Lowe
120*3625efb1SRichard Lowe void
write_state_file(int,Boolean exiting)121*3625efb1SRichard Lowe write_state_file(int, Boolean exiting)
122*3625efb1SRichard Lowe {
123*3625efb1SRichard Lowe register FILE *fd;
124*3625efb1SRichard Lowe int lock_err;
125*3625efb1SRichard Lowe char buffer[MAXPATHLEN];
126*3625efb1SRichard Lowe char make_state_tempfile[MAXPATHLEN];
127*3625efb1SRichard Lowe jmp_buf long_jump;
128*3625efb1SRichard Lowe register int attempts = 0;
129*3625efb1SRichard Lowe Name_set::iterator np, e;
130*3625efb1SRichard Lowe register Property lines;
131*3625efb1SRichard Lowe register int m;
132*3625efb1SRichard Lowe Dependency dependency;
133*3625efb1SRichard Lowe register Boolean name_printed;
134*3625efb1SRichard Lowe Boolean built_this_run = false;
135*3625efb1SRichard Lowe char *target_name;
136*3625efb1SRichard Lowe int line_length;
137*3625efb1SRichard Lowe register Cmd_line cp;
138*3625efb1SRichard Lowe
139*3625efb1SRichard Lowe
140*3625efb1SRichard Lowe if (!rewrite_statefile ||
141*3625efb1SRichard Lowe !command_changed ||
142*3625efb1SRichard Lowe !keep_state ||
143*3625efb1SRichard Lowe do_not_exec_rule ||
144*3625efb1SRichard Lowe (report_dependencies_level > 0)) {
145*3625efb1SRichard Lowe return;
146*3625efb1SRichard Lowe }
147*3625efb1SRichard Lowe /* Lock the file for writing. */
148*3625efb1SRichard Lowe make_state_lockfile = getmem(strlen(make_state->string_mb) + strlen(".lock") + 1);
149*3625efb1SRichard Lowe (void) sprintf(make_state_lockfile,
150*3625efb1SRichard Lowe "%s.lock",
151*3625efb1SRichard Lowe make_state->string_mb);
152*3625efb1SRichard Lowe if (lock_err = file_lock(make_state->string_mb,
153*3625efb1SRichard Lowe make_state_lockfile,
154*3625efb1SRichard Lowe (int *) &make_state_locked, 0)) {
155*3625efb1SRichard Lowe retmem_mb(make_state_lockfile);
156*3625efb1SRichard Lowe make_state_lockfile = NULL;
157*3625efb1SRichard Lowe
158*3625efb1SRichard Lowe /*
159*3625efb1SRichard Lowe * We need to make sure that we are not being
160*3625efb1SRichard Lowe * called by the exit handler so we don't call
161*3625efb1SRichard Lowe * it again.
162*3625efb1SRichard Lowe */
163*3625efb1SRichard Lowe
164*3625efb1SRichard Lowe if (exiting) {
165*3625efb1SRichard Lowe (void) sprintf(buffer, "%s/.make.state.%d.XXXXXX", tmpdir, getpid());
166*3625efb1SRichard Lowe report_pwd = true;
167*3625efb1SRichard Lowe warning(gettext("Writing to %s"), buffer);
168*3625efb1SRichard Lowe int fdes = mkstemp(buffer);
169*3625efb1SRichard Lowe if ((fdes < 0) || (fd = fdopen(fdes, "w")) == NULL) {
170*3625efb1SRichard Lowe fprintf(stderr,
171*3625efb1SRichard Lowe gettext("Could not open statefile `%s': %s"),
172*3625efb1SRichard Lowe buffer,
173*3625efb1SRichard Lowe errmsg(errno));
174*3625efb1SRichard Lowe return;
175*3625efb1SRichard Lowe }
176*3625efb1SRichard Lowe } else {
177*3625efb1SRichard Lowe report_pwd = true;
178*3625efb1SRichard Lowe fatal(gettext("Can't lock .make.state"));
179*3625efb1SRichard Lowe }
180*3625efb1SRichard Lowe }
181*3625efb1SRichard Lowe
182*3625efb1SRichard Lowe (void) sprintf(make_state_tempfile,
183*3625efb1SRichard Lowe "%s.tmp",
184*3625efb1SRichard Lowe make_state->string_mb);
185*3625efb1SRichard Lowe /* Delete old temporary statefile (in case it exists) */
186*3625efb1SRichard Lowe (void) unlink(make_state_tempfile);
187*3625efb1SRichard Lowe if ((fd = fopen(make_state_tempfile, "w")) == NULL) {
188*3625efb1SRichard Lowe lock_err = errno; /* Save it! unlink() can change errno */
189*3625efb1SRichard Lowe (void) unlink(make_state_lockfile);
190*3625efb1SRichard Lowe retmem_mb(make_state_lockfile);
191*3625efb1SRichard Lowe make_state_lockfile = NULL;
192*3625efb1SRichard Lowe make_state_locked = false;
193*3625efb1SRichard Lowe fatal(gettext("Could not open temporary statefile `%s': %s"),
194*3625efb1SRichard Lowe make_state_tempfile,
195*3625efb1SRichard Lowe errmsg(lock_err));
196*3625efb1SRichard Lowe }
197*3625efb1SRichard Lowe /*
198*3625efb1SRichard Lowe * Set a trap for failed writes. If a write fails, the routine
199*3625efb1SRichard Lowe * will try saving the .make.state file under another name in /tmp.
200*3625efb1SRichard Lowe */
201*3625efb1SRichard Lowe if (setjmp(long_jump)) {
202*3625efb1SRichard Lowe (void) fclose(fd);
203*3625efb1SRichard Lowe if (attempts++ > 5) {
204*3625efb1SRichard Lowe if ((make_state_lockfile != NULL) &&
205*3625efb1SRichard Lowe make_state_locked) {
206*3625efb1SRichard Lowe (void) unlink(make_state_lockfile);
207*3625efb1SRichard Lowe retmem_mb(make_state_lockfile);
208*3625efb1SRichard Lowe make_state_lockfile = NULL;
209*3625efb1SRichard Lowe make_state_locked = false;
210*3625efb1SRichard Lowe }
211*3625efb1SRichard Lowe fatal(gettext("Giving up on writing statefile"));
212*3625efb1SRichard Lowe }
213*3625efb1SRichard Lowe sleep(10);
214*3625efb1SRichard Lowe (void) sprintf(buffer, "%s/.make.state.%d.XXXXXX", tmpdir, getpid());
215*3625efb1SRichard Lowe int fdes = mkstemp(buffer);
216*3625efb1SRichard Lowe if ((fdes < 0) || (fd = fdopen(fdes, "w")) == NULL) {
217*3625efb1SRichard Lowe fatal(gettext("Could not open statefile `%s': %s"),
218*3625efb1SRichard Lowe buffer,
219*3625efb1SRichard Lowe errmsg(errno));
220*3625efb1SRichard Lowe }
221*3625efb1SRichard Lowe warning(gettext("Initial write of statefile failed. Trying again on %s"),
222*3625efb1SRichard Lowe buffer);
223*3625efb1SRichard Lowe }
224*3625efb1SRichard Lowe
225*3625efb1SRichard Lowe /* Write the version stamp. */
226*3625efb1SRichard Lowe XFWRITE(make_version->string_mb,
227*3625efb1SRichard Lowe strlen(make_version->string_mb),
228*3625efb1SRichard Lowe fd);
229*3625efb1SRichard Lowe XPUTC(colon_char, fd);
230*3625efb1SRichard Lowe XPUTC(tab_char, fd);
231*3625efb1SRichard Lowe XFWRITE(current_make_version->string_mb,
232*3625efb1SRichard Lowe strlen(current_make_version->string_mb),
233*3625efb1SRichard Lowe fd);
234*3625efb1SRichard Lowe XPUTC(newline_char, fd);
235*3625efb1SRichard Lowe
236*3625efb1SRichard Lowe /*
237*3625efb1SRichard Lowe * Go through all the targets, dump their dependencies and
238*3625efb1SRichard Lowe * command used.
239*3625efb1SRichard Lowe */
240*3625efb1SRichard Lowe for (np = hashtab.begin(), e = hashtab.end(); np != e; np++) {
241*3625efb1SRichard Lowe /*
242*3625efb1SRichard Lowe * If the target has no command used nor dependencies,
243*3625efb1SRichard Lowe * we can go to the next one.
244*3625efb1SRichard Lowe */
245*3625efb1SRichard Lowe if ((lines = get_prop(np->prop, line_prop)) == NULL) {
246*3625efb1SRichard Lowe continue;
247*3625efb1SRichard Lowe }
248*3625efb1SRichard Lowe /* If this target is a special target, don't print. */
249*3625efb1SRichard Lowe if (np->special_reader != no_special) {
250*3625efb1SRichard Lowe continue;
251*3625efb1SRichard Lowe }
252*3625efb1SRichard Lowe /*
253*3625efb1SRichard Lowe * Find out if any of the targets dependencies should
254*3625efb1SRichard Lowe * be written to .make.state.
255*3625efb1SRichard Lowe */
256*3625efb1SRichard Lowe for (m = 0, dependency = lines->body.line.dependencies;
257*3625efb1SRichard Lowe dependency != NULL;
258*3625efb1SRichard Lowe dependency = dependency->next) {
259*3625efb1SRichard Lowe if (m = !dependency->stale
260*3625efb1SRichard Lowe && (dependency->name != force)
261*3625efb1SRichard Lowe #ifndef PRINT_EXPLICIT_DEPEN
262*3625efb1SRichard Lowe && dependency->automatic
263*3625efb1SRichard Lowe #endif
264*3625efb1SRichard Lowe ) {
265*3625efb1SRichard Lowe break;
266*3625efb1SRichard Lowe }
267*3625efb1SRichard Lowe }
268*3625efb1SRichard Lowe /* Only print if dependencies listed. */
269*3625efb1SRichard Lowe if (m || (lines->body.line.command_used != NULL)) {
270*3625efb1SRichard Lowe name_printed = false;
271*3625efb1SRichard Lowe /*
272*3625efb1SRichard Lowe * If this target was built during this make run,
273*3625efb1SRichard Lowe * we mark it.
274*3625efb1SRichard Lowe */
275*3625efb1SRichard Lowe built_this_run = false;
276*3625efb1SRichard Lowe if (np->has_built) {
277*3625efb1SRichard Lowe built_this_run = true;
278*3625efb1SRichard Lowe XFWRITE(built_last_make_run->string_mb,
279*3625efb1SRichard Lowe strlen(built_last_make_run->string_mb),
280*3625efb1SRichard Lowe fd);
281*3625efb1SRichard Lowe XPUTC(colon_char, fd);
282*3625efb1SRichard Lowe XPUTC(newline_char, fd);
283*3625efb1SRichard Lowe }
284*3625efb1SRichard Lowe /* If the target has dependencies, we dump them. */
285*3625efb1SRichard Lowe target_name = escape_target_name(np);
286*3625efb1SRichard Lowe if (np->has_long_member_name) {
287*3625efb1SRichard Lowe target_name =
288*3625efb1SRichard Lowe get_prop(np->prop, long_member_name_prop)
289*3625efb1SRichard Lowe ->body.long_member_name.member_name->
290*3625efb1SRichard Lowe string_mb;
291*3625efb1SRichard Lowe }
292*3625efb1SRichard Lowe if (m) {
293*3625efb1SRichard Lowe XFPUTS(target_name, fd);
294*3625efb1SRichard Lowe XPUTC(colon_char, fd);
295*3625efb1SRichard Lowe XFPUTS("\t", fd);
296*3625efb1SRichard Lowe name_printed = true;
297*3625efb1SRichard Lowe line_length = 0;
298*3625efb1SRichard Lowe for (dependency =
299*3625efb1SRichard Lowe lines->body.line.dependencies;
300*3625efb1SRichard Lowe dependency != NULL;
301*3625efb1SRichard Lowe dependency = dependency->next) {
302*3625efb1SRichard Lowe print_auto_depes(dependency,
303*3625efb1SRichard Lowe fd,
304*3625efb1SRichard Lowe built_this_run,
305*3625efb1SRichard Lowe &line_length,
306*3625efb1SRichard Lowe target_name,
307*3625efb1SRichard Lowe long_jump);
308*3625efb1SRichard Lowe }
309*3625efb1SRichard Lowe XFPUTS("\n", fd);
310*3625efb1SRichard Lowe }
311*3625efb1SRichard Lowe /* If there is a command used, we dump it. */
312*3625efb1SRichard Lowe if (lines->body.line.command_used != NULL) {
313*3625efb1SRichard Lowe /*
314*3625efb1SRichard Lowe * Only write the target name if it
315*3625efb1SRichard Lowe * wasn't done for the dependencies.
316*3625efb1SRichard Lowe */
317*3625efb1SRichard Lowe if (!name_printed) {
318*3625efb1SRichard Lowe XFPUTS(target_name, fd);
319*3625efb1SRichard Lowe XPUTC(colon_char, fd);
320*3625efb1SRichard Lowe XPUTC(newline_char, fd);
321*3625efb1SRichard Lowe }
322*3625efb1SRichard Lowe /*
323*3625efb1SRichard Lowe * Write the command lines.
324*3625efb1SRichard Lowe * Prefix each textual line with a tab.
325*3625efb1SRichard Lowe */
326*3625efb1SRichard Lowe for (cp = lines->body.line.command_used;
327*3625efb1SRichard Lowe cp != NULL;
328*3625efb1SRichard Lowe cp = cp->next) {
329*3625efb1SRichard Lowe char *csp;
330*3625efb1SRichard Lowe int n;
331*3625efb1SRichard Lowe
332*3625efb1SRichard Lowe XPUTC(tab_char, fd);
333*3625efb1SRichard Lowe if (cp->command_line != NULL) {
334*3625efb1SRichard Lowe for (csp = cp->
335*3625efb1SRichard Lowe command_line->
336*3625efb1SRichard Lowe string_mb,
337*3625efb1SRichard Lowe n = strlen(cp->
338*3625efb1SRichard Lowe command_line->
339*3625efb1SRichard Lowe string_mb);
340*3625efb1SRichard Lowe n > 0;
341*3625efb1SRichard Lowe n--, csp++) {
342*3625efb1SRichard Lowe XPUTC(*csp, fd);
343*3625efb1SRichard Lowe if (*csp ==
344*3625efb1SRichard Lowe (int) newline_char) {
345*3625efb1SRichard Lowe XPUTC(tab_char,
346*3625efb1SRichard Lowe fd);
347*3625efb1SRichard Lowe }
348*3625efb1SRichard Lowe }
349*3625efb1SRichard Lowe }
350*3625efb1SRichard Lowe XPUTC(newline_char, fd);
351*3625efb1SRichard Lowe }
352*3625efb1SRichard Lowe }
353*3625efb1SRichard Lowe (void)free(target_name);
354*3625efb1SRichard Lowe }
355*3625efb1SRichard Lowe }
356*3625efb1SRichard Lowe if (fclose(fd) == EOF) {
357*3625efb1SRichard Lowe longjmp(long_jump, LONGJUMP_VALUE);
358*3625efb1SRichard Lowe }
359*3625efb1SRichard Lowe if (attempts == 0) {
360*3625efb1SRichard Lowe if (unlink(make_state->string_mb) != 0 && errno != ENOENT) {
361*3625efb1SRichard Lowe lock_err = errno; /* Save it! unlink() can change errno */
362*3625efb1SRichard Lowe /* Delete temporary statefile */
363*3625efb1SRichard Lowe (void) unlink(make_state_tempfile);
364*3625efb1SRichard Lowe (void) unlink(make_state_lockfile);
365*3625efb1SRichard Lowe retmem_mb(make_state_lockfile);
366*3625efb1SRichard Lowe make_state_lockfile = NULL;
367*3625efb1SRichard Lowe make_state_locked = false;
368*3625efb1SRichard Lowe fatal(gettext("Could not delete old statefile `%s': %s"),
369*3625efb1SRichard Lowe make_state->string_mb,
370*3625efb1SRichard Lowe errmsg(lock_err));
371*3625efb1SRichard Lowe }
372*3625efb1SRichard Lowe if (rename(make_state_tempfile, make_state->string_mb) != 0) {
373*3625efb1SRichard Lowe lock_err = errno; /* Save it! unlink() can change errno */
374*3625efb1SRichard Lowe /* Delete temporary statefile */
375*3625efb1SRichard Lowe (void) unlink(make_state_tempfile);
376*3625efb1SRichard Lowe (void) unlink(make_state_lockfile);
377*3625efb1SRichard Lowe retmem_mb(make_state_lockfile);
378*3625efb1SRichard Lowe make_state_lockfile = NULL;
379*3625efb1SRichard Lowe make_state_locked = false;
380*3625efb1SRichard Lowe fatal(gettext("Could not rename `%s' to `%s': %s"),
381*3625efb1SRichard Lowe make_state_tempfile,
382*3625efb1SRichard Lowe make_state->string_mb,
383*3625efb1SRichard Lowe errmsg(lock_err));
384*3625efb1SRichard Lowe }
385*3625efb1SRichard Lowe }
386*3625efb1SRichard Lowe if ((make_state_lockfile != NULL) && make_state_locked) {
387*3625efb1SRichard Lowe (void) unlink(make_state_lockfile);
388*3625efb1SRichard Lowe retmem_mb(make_state_lockfile);
389*3625efb1SRichard Lowe make_state_lockfile = NULL;
390*3625efb1SRichard Lowe make_state_locked = false;
391*3625efb1SRichard Lowe }
392*3625efb1SRichard Lowe }
393*3625efb1SRichard Lowe
394*3625efb1SRichard Lowe /*
395*3625efb1SRichard Lowe * print_auto_depes(dependency, fd, built_this_run,
396*3625efb1SRichard Lowe * line_length, target_name, long_jump)
397*3625efb1SRichard Lowe *
398*3625efb1SRichard Lowe * Will print a dependency list for automatic entries.
399*3625efb1SRichard Lowe *
400*3625efb1SRichard Lowe * Parameters:
401*3625efb1SRichard Lowe * dependency The dependency to print
402*3625efb1SRichard Lowe * fd The file to print it to
403*3625efb1SRichard Lowe * built_this_run If on we prefix each line with .BUILT_THIS...
404*3625efb1SRichard Lowe * line_length Pointer to line length var that we update
405*3625efb1SRichard Lowe * target_name We need this when we restart line
406*3625efb1SRichard Lowe * long_jump setjmp/longjmp buffer used for IO error action
407*3625efb1SRichard Lowe *
408*3625efb1SRichard Lowe * Global variables used:
409*3625efb1SRichard Lowe * built_last_make_run The Name ".BUILT_LAST_MAKE_RUN", written
410*3625efb1SRichard Lowe * force The Name " FORCE", compared against
411*3625efb1SRichard Lowe */
412*3625efb1SRichard Lowe static void
print_auto_depes(register Dependency dependency,register FILE * fd,register Boolean built_this_run,register int * line_length,register char * target_name,jmp_buf long_jump)413*3625efb1SRichard Lowe print_auto_depes(register Dependency dependency, register FILE *fd, register Boolean built_this_run, register int *line_length, register char *target_name, jmp_buf long_jump)
414*3625efb1SRichard Lowe {
415*3625efb1SRichard Lowe if (!dependency->automatic ||
416*3625efb1SRichard Lowe dependency->stale ||
417*3625efb1SRichard Lowe (dependency->name == force)) {
418*3625efb1SRichard Lowe return;
419*3625efb1SRichard Lowe }
420*3625efb1SRichard Lowe XFWRITE(dependency->name->string_mb,
421*3625efb1SRichard Lowe strlen(dependency->name->string_mb),
422*3625efb1SRichard Lowe fd);
423*3625efb1SRichard Lowe /*
424*3625efb1SRichard Lowe * Check if the dependency line is too long.
425*3625efb1SRichard Lowe * If so, break it and start a new one.
426*3625efb1SRichard Lowe */
427*3625efb1SRichard Lowe if ((*line_length += (int) strlen(dependency->name->string_mb) + 1) > 450) {
428*3625efb1SRichard Lowe *line_length = 0;
429*3625efb1SRichard Lowe XPUTC(newline_char, fd);
430*3625efb1SRichard Lowe if (built_this_run) {
431*3625efb1SRichard Lowe XFPUTS(built_last_make_run->string_mb, fd);
432*3625efb1SRichard Lowe XPUTC(colon_char, fd);
433*3625efb1SRichard Lowe XPUTC(newline_char, fd);
434*3625efb1SRichard Lowe }
435*3625efb1SRichard Lowe XFPUTS(target_name, fd);
436*3625efb1SRichard Lowe XPUTC(colon_char, fd);
437*3625efb1SRichard Lowe XPUTC(tab_char, fd);
438*3625efb1SRichard Lowe } else {
439*3625efb1SRichard Lowe XFPUTS(" ", fd);
440*3625efb1SRichard Lowe }
441*3625efb1SRichard Lowe return;
442*3625efb1SRichard Lowe }
443*3625efb1SRichard Lowe
444*3625efb1SRichard Lowe
445