source: trunk/src/kmk/function.c@ 1987

Last change on this file since 1987 was 1986, checked in by bird, 17 years ago

kmk: some make stats cleanup.

  • Property svn:eol-style set to native
File size: 133.3 KB
Line 
1/* Builtin function expansion for GNU Make.
2Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997,
31998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006 Free Software
4Foundation, Inc.
5This file is part of GNU Make.
6
7GNU Make is free software; you can redistribute it and/or modify it under the
8terms of the GNU General Public License as published by the Free Software
9Foundation; either version 2, or (at your option) any later version.
10
11GNU Make is distributed in the hope that it will be useful, but WITHOUT ANY
12WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
13A PARTICULAR PURPOSE. See the GNU General Public License for more details.
14
15You should have received a copy of the GNU General Public License along with
16GNU Make; see the file COPYING. If not, write to the Free Software
17Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. */
18
19#include "make.h"
20#include "filedef.h"
21#include "variable.h"
22#include "dep.h"
23#include "job.h"
24#include "commands.h"
25#include "debug.h"
26
27#ifdef _AMIGA
28#include "amiga.h"
29#endif
30
31#ifdef WINDOWS32 /* bird */
32# include "pathstuff.h"
33#endif
34
35#ifdef KMK_HELPERS
36# include "kbuild.h"
37#endif
38#ifdef CONFIG_WITH_XARGS /* bird */
39# ifdef HAVE_LIMITS_H
40# include <limits.h>
41# endif
42#endif
43#include <assert.h> /* bird */
44
45#if defined (CONFIG_WITH_MATH) || defined (CONFIG_WITH_NANOTS) || defined (CONFIG_WITH_FILE_SIZE) /* bird */
46# include <ctype.h>
47# ifdef _MSC_VER
48typedef __int64 math_int;
49# else
50# include <stdint.h>
51typedef int64_t math_int;
52# endif
53static char *math_int_to_variable_buffer (char *, math_int);
54#endif
55
56#ifdef CONFIG_WITH_NANOTS /* bird */
57# ifdef WINDOWS32
58# include <Windows.h>
59# endif
60#endif
61
62#ifdef __OS2__
63# define CONFIG_WITH_OS2_LIBPATH 1
64#endif
65#ifdef CONFIG_WITH_OS2_LIBPATH
66# define INCL_BASE
67# define INCL_ERRROS
68# include <os2.h>
69
70# define QHINF_EXEINFO 1 /* NE exeinfo. */
71# define QHINF_READRSRCTBL 2 /* Reads from the resource table. */
72# define QHINF_READFILE 3 /* Reads from the executable file. */
73# define QHINF_LIBPATHLENGTH 4 /* Gets the libpath length. */
74# define QHINF_LIBPATH 5 /* Gets the entire libpath. */
75# define QHINF_FIXENTRY 6 /* NE only */
76# define QHINF_STE 7 /* NE only */
77# define QHINF_MAPSEL 8 /* NE only */
78 extern APIRET APIENTRY DosQueryHeaderInfo(HMODULE hmod, ULONG ulIndex, PVOID pvBuffer, ULONG cbBuffer, ULONG ulSubFunction);
79#endif /* CONFIG_WITH_OS2_LIBPATH */
80
81
82struct function_table_entry
83 {
84 const char *name;
85 unsigned char len;
86 unsigned char minimum_args;
87 unsigned char maximum_args;
88 char expand_args;
89 char *(*func_ptr) (char *output, char **argv, const char *fname);
90 };
91
92static unsigned long
93function_table_entry_hash_1 (const void *keyv)
94{
95 const struct function_table_entry *key = keyv;
96 return_STRING_N_HASH_1 (key->name, key->len);
97}
98
99static unsigned long
100function_table_entry_hash_2 (const void *keyv)
101{
102 const struct function_table_entry *key = keyv;
103 return_STRING_N_HASH_2 (key->name, key->len);
104}
105
106static int
107function_table_entry_hash_cmp (const void *xv, const void *yv)
108{
109 const struct function_table_entry *x = xv;
110 const struct function_table_entry *y = yv;
111 int result = x->len - y->len;
112 if (result)
113 return result;
114 return_STRING_N_COMPARE (x->name, y->name, x->len);
115}
116
117static struct hash_table function_table;
118
119#ifdef CONFIG_WITH_MAKE_STATS
120long make_stats_allocations = 0;
121long make_stats_reallocations = 0;
122unsigned long make_stats_allocated = 0;
123unsigned long make_stats_ht_lookups = 0;
124unsigned long make_stats_ht_collisions = 0;
125#endif
126
127
128
129/* Store into VARIABLE_BUFFER at O the result of scanning TEXT and replacing
130 each occurrence of SUBST with REPLACE. TEXT is null-terminated. SLEN is
131 the length of SUBST and RLEN is the length of REPLACE. If BY_WORD is
132 nonzero, substitutions are done only on matches which are complete
133 whitespace-delimited words. */
134
135char *
136subst_expand (char *o, const char *text, const char *subst, const char *replace,
137 unsigned int slen, unsigned int rlen, int by_word)
138{
139 const char *t = text;
140 const char *p;
141
142 if (slen == 0 && !by_word)
143 {
144 /* The first occurrence of "" in any string is its end. */
145 o = variable_buffer_output (o, t, strlen (t));
146 if (rlen > 0)
147 o = variable_buffer_output (o, replace, rlen);
148 return o;
149 }
150
151 do
152 {
153 if (by_word && slen == 0)
154 /* When matching by words, the empty string should match
155 the end of each word, rather than the end of the whole text. */
156 p = end_of_token (next_token (t));
157 else
158 {
159 p = strstr (t, subst);
160 if (p == 0)
161 {
162 /* No more matches. Output everything left on the end. */
163 o = variable_buffer_output (o, t, strlen (t));
164 return o;
165 }
166 }
167
168 /* Output everything before this occurrence of the string to replace. */
169 if (p > t)
170 o = variable_buffer_output (o, t, p - t);
171
172 /* If we're substituting only by fully matched words,
173 or only at the ends of words, check that this case qualifies. */
174 if (by_word
175 && ((p > text && !isblank ((unsigned char)p[-1]))
176 || (p[slen] != '\0' && !isblank ((unsigned char)p[slen]))))
177 /* Struck out. Output the rest of the string that is
178 no longer to be replaced. */
179 o = variable_buffer_output (o, subst, slen);
180 else if (rlen > 0)
181 /* Output the replacement string. */
182 o = variable_buffer_output (o, replace, rlen);
183
184 /* Advance T past the string to be replaced. */
185 t = p + slen;
186 } while (*t != '\0');
187
188 return o;
189}
190
191
192
193/* Store into VARIABLE_BUFFER at O the result of scanning TEXT
194 and replacing strings matching PATTERN with REPLACE.
195 If PATTERN_PERCENT is not nil, PATTERN has already been
196 run through find_percent, and PATTERN_PERCENT is the result.
197 If REPLACE_PERCENT is not nil, REPLACE has already been
198 run through find_percent, and REPLACE_PERCENT is the result.
199 Note that we expect PATTERN_PERCENT and REPLACE_PERCENT to point to the
200 character _AFTER_ the %, not to the % itself.
201*/
202
203char *
204patsubst_expand_pat (char *o, const char *text,
205 const char *pattern, const char *replace,
206 const char *pattern_percent, const char *replace_percent)
207{
208 unsigned int pattern_prepercent_len, pattern_postpercent_len;
209 unsigned int replace_prepercent_len, replace_postpercent_len;
210 const char *t;
211 unsigned int len;
212 int doneany = 0;
213
214 /* Record the length of REPLACE before and after the % so we don't have to
215 compute these lengths more than once. */
216 if (replace_percent)
217 {
218 replace_prepercent_len = replace_percent - replace - 1;
219 replace_postpercent_len = strlen (replace_percent);
220 }
221 else
222 {
223 replace_prepercent_len = strlen (replace);
224 replace_postpercent_len = 0;
225 }
226
227 if (!pattern_percent)
228 /* With no % in the pattern, this is just a simple substitution. */
229 return subst_expand (o, text, pattern, replace,
230 strlen (pattern), strlen (replace), 1);
231
232 /* Record the length of PATTERN before and after the %
233 so we don't have to compute it more than once. */
234 pattern_prepercent_len = pattern_percent - pattern - 1;
235 pattern_postpercent_len = strlen (pattern_percent);
236
237 while ((t = find_next_token (&text, &len)) != 0)
238 {
239 int fail = 0;
240
241 /* Is it big enough to match? */
242 if (len < pattern_prepercent_len + pattern_postpercent_len)
243 fail = 1;
244
245 /* Does the prefix match? */
246 if (!fail && pattern_prepercent_len > 0
247 && (*t != *pattern
248 || t[pattern_prepercent_len - 1] != pattern_percent[-2]
249 || !strneq (t + 1, pattern + 1, pattern_prepercent_len - 1)))
250 fail = 1;
251
252 /* Does the suffix match? */
253 if (!fail && pattern_postpercent_len > 0
254 && (t[len - 1] != pattern_percent[pattern_postpercent_len - 1]
255 || t[len - pattern_postpercent_len] != *pattern_percent
256 || !strneq (&t[len - pattern_postpercent_len],
257 pattern_percent, pattern_postpercent_len - 1)))
258 fail = 1;
259
260 if (fail)
261 /* It didn't match. Output the string. */
262 o = variable_buffer_output (o, t, len);
263 else
264 {
265 /* It matched. Output the replacement. */
266
267 /* Output the part of the replacement before the %. */
268 o = variable_buffer_output (o, replace, replace_prepercent_len);
269
270 if (replace_percent != 0)
271 {
272 /* Output the part of the matched string that
273 matched the % in the pattern. */
274 o = variable_buffer_output (o, t + pattern_prepercent_len,
275 len - (pattern_prepercent_len
276 + pattern_postpercent_len));
277 /* Output the part of the replacement after the %. */
278 o = variable_buffer_output (o, replace_percent,
279 replace_postpercent_len);
280 }
281 }
282
283 /* Output a space, but not if the replacement is "". */
284 if (fail || replace_prepercent_len > 0
285 || (replace_percent != 0 && len + replace_postpercent_len > 0))
286 {
287 o = variable_buffer_output (o, " ", 1);
288 doneany = 1;
289 }
290 }
291#ifndef CONFIG_WITH_VALUE_LENGTH
292 if (doneany)
293 /* Kill the last space. */
294 --o;
295#else
296 /* Kill the last space and make sure there is a terminator there
297 so that strcache_add_len doesn't have to do a lot of exacty work
298 when expand_deps sends the output its way. */
299 if (doneany)
300 *--o = '\0';
301 else
302 o = variable_buffer_output (o, "\0", 1) - 1;
303#endif
304
305 return o;
306}
307
308/* Store into VARIABLE_BUFFER at O the result of scanning TEXT
309 and replacing strings matching PATTERN with REPLACE.
310 If PATTERN_PERCENT is not nil, PATTERN has already been
311 run through find_percent, and PATTERN_PERCENT is the result.
312 If REPLACE_PERCENT is not nil, REPLACE has already been
313 run through find_percent, and REPLACE_PERCENT is the result.
314 Note that we expect PATTERN_PERCENT and REPLACE_PERCENT to point to the
315 character _AFTER_ the %, not to the % itself.
316*/
317
318char *
319patsubst_expand (char *o, const char *text, char *pattern, char *replace)
320{
321 const char *pattern_percent = find_percent (pattern);
322 const char *replace_percent = find_percent (replace);
323
324 /* If there's a percent in the pattern or replacement skip it. */
325 if (replace_percent)
326 ++replace_percent;
327 if (pattern_percent)
328 ++pattern_percent;
329
330 return patsubst_expand_pat (o, text, pattern, replace,
331 pattern_percent, replace_percent);
332}
333
334
335#if defined (CONFIG_WITH_OPTIMIZATION_HACKS) || defined (CONFIG_WITH_VALUE_LENGTH)
336
337/* Char map containing the valid function name characters. */
338char func_char_map[256];
339
340/* Do the hash table lookup. */
341
342MY_INLINE const struct function_table_entry *
343lookup_function_in_hash_tab (const char *s, unsigned char len)
344{
345 struct function_table_entry function_table_entry_key;
346 function_table_entry_key.name = s;
347 function_table_entry_key.len = len;
348
349 return hash_find_item (&function_table, &function_table_entry_key);
350}
351
352/* Look up a function by name. */
353
354MY_INLINE const struct function_table_entry *
355lookup_function (const char *s, unsigned int len)
356{
357 unsigned char ch;
358# if 0 /* insane loop unroll */
359
360 if (len > MAX_FUNCTION_LENGTH)
361 len = MAX_FUNCTION_LENGTH + 1;
362
363# define X(idx) \
364 if (!func_char_map[ch = s[idx]]) \
365 { \
366 if (isblank (ch)) \
367 return lookup_function_in_hash_tab (s, idx); \
368 return 0; \
369 }
370# define Z(idx) \
371 return lookup_function_in_hash_tab (s, idx);
372
373 switch (len)
374 {
375 default:
376 assert (0);
377 case 0: return 0;
378 case 1: return 0;
379 case 2: X(0); X(1); Z(2);
380 case 3: X(0); X(1); X(2); Z(3);
381 case 4: X(0); X(1); X(2); X(3); Z(4);
382 case 5: X(0); X(1); X(2); X(3); X(4); Z(5);
383 case 6: X(0); X(1); X(2); X(3); X(4); X(5); Z(6);
384 case 7: X(0); X(1); X(2); X(3); X(4); X(5); X(6); Z(7);
385 case 8: X(0); X(1); X(2); X(3); X(4); X(5); X(6); X(7); Z(8);
386 case 9: X(0); X(1); X(2); X(3); X(4); X(5); X(6); X(7); X(8); Z(9);
387 case 10: X(0); X(1); X(2); X(3); X(4); X(5); X(6); X(7); X(8); X(9); Z(10);
388 case 11: X(0); X(1); X(2); X(3); X(4); X(5); X(6); X(7); X(8); X(9); X(10); Z(11);
389 case 12: X(0); X(1); X(2); X(3); X(4); X(5); X(6); X(7); X(8); X(9); X(10); X(11); Z(12);
390 case 13: X(0); X(1); X(2); X(3); X(4); X(5); X(6); X(7); X(8); X(9); X(10); X(11); X(12);
391 if ((ch = s[12]) == '\0' || isblank (ch))
392 return lookup_function_in_hash_tab (s, 12);
393 return 0;
394 }
395# undef Z
396# undef X
397
398# else /* normal loop */
399 const char *e = s;
400 if (len > MAX_FUNCTION_LENGTH)
401 len = MAX_FUNCTION_LENGTH;
402 while (func_char_map[ch = *e])
403 {
404 if (!len--)
405 return 0;
406 e++;
407 }
408 if (ch == '\0' || isblank (ch))
409 return lookup_function_in_hash_tab (s, e - s);
410 return 0;
411# endif /* normal loop */
412}
413
414#else /* original code */
415/* Look up a function by name. */
416
417static const struct function_table_entry *
418lookup_function (const char *s)
419{
420 const char *e = s;
421 while (*e && ( (*e >= 'a' && *e <= 'z') || *e == '-'))
422 e++;
423 if (*e == '\0' || isblank ((unsigned char) *e))
424 {
425 struct function_table_entry function_table_entry_key;
426 function_table_entry_key.name = s;
427 function_table_entry_key.len = e - s;
428
429 return hash_find_item (&function_table, &function_table_entry_key);
430 }
431 return 0;
432}
433#endif /* original code */
434
435
436
437/* Return 1 if PATTERN matches STR, 0 if not. */
438
439int
440pattern_matches (const char *pattern, const char *percent, const char *str)
441{
442 unsigned int sfxlen, strlength;
443
444 if (percent == 0)
445 {
446 unsigned int len = strlen (pattern) + 1;
447 char *new_chars = alloca (len);
448 memcpy (new_chars, pattern, len);
449 percent = find_percent (new_chars);
450 if (percent == 0)
451 return streq (new_chars, str);
452 pattern = new_chars;
453 }
454
455 sfxlen = strlen (percent + 1);
456 strlength = strlen (str);
457
458 if (strlength < (percent - pattern) + sfxlen
459 || !strneq (pattern, str, percent - pattern))
460 return 0;
461
462 return !strcmp (percent + 1, str + (strlength - sfxlen));
463}
464
465
466
467/* Find the next comma or ENDPAREN (counting nested STARTPAREN and
468 ENDPARENtheses), starting at PTR before END. Return a pointer to
469 next character.
470
471 If no next argument is found, return NULL.
472*/
473
474static char *
475find_next_argument (char startparen, char endparen,
476 const char *ptr, const char *end)
477{
478 int count = 0;
479
480 for (; ptr < end; ++ptr)
481 if (*ptr == startparen)
482 ++count;
483
484 else if (*ptr == endparen)
485 {
486 --count;
487 if (count < 0)
488 return NULL;
489 }
490
491 else if (*ptr == ',' && !count)
492 return (char *)ptr;
493
494 /* We didn't find anything. */
495 return NULL;
496}
497
498
499
500/* Glob-expand LINE. The returned pointer is
501 only good until the next call to string_glob. */
502
503static char *
504string_glob (char *line)
505{
506 static char *result = 0;
507 static unsigned int length;
508 struct nameseq *chain;
509 unsigned int idx;
510
511#ifndef CONFIG_WITH_ALLOC_CACHES
512 chain = multi_glob (parse_file_seq
513 (&line, '\0', sizeof (struct nameseq),
514 /* We do not want parse_file_seq to strip `./'s.
515 That would break examples like:
516 $(patsubst ./%.c,obj/%.o,$(wildcard ./?*.c)). */
517 0),
518 sizeof (struct nameseq));
519#else /* CONFIG_WITH_ALLOC_CACHES */
520 chain = multi_glob (parse_file_seq
521 (&line, '\0', &nameseq_cache,
522 /* We do not want parse_file_seq to strip `./'s.
523 That would break examples like:
524 $(patsubst ./%.c,obj/%.o,$(wildcard ./?*.c)). */
525 0),
526 &nameseq_cache);
527#endif /* CONFIG_WITH_ALLOC_CACHES */
528
529 if (result == 0)
530 {
531 length = 100;
532 result = xmalloc (100);
533 }
534
535 idx = 0;
536 while (chain != 0)
537 {
538 const char *name = chain->name;
539 unsigned int len = strlen (name);
540
541 struct nameseq *next = chain->next;
542#ifndef CONFIG_WITH_ALLOC_CACHES
543 free (chain);
544#else
545 alloccache_free (&nameseq_cache, chain);
546#endif
547 chain = next;
548
549 /* multi_glob will pass names without globbing metacharacters
550 through as is, but we want only files that actually exist. */
551 if (file_exists_p (name))
552 {
553 if (idx + len + 1 > length)
554 {
555 length += (len + 1) * 2;
556 result = xrealloc (result, length);
557 }
558 memcpy (&result[idx], name, len);
559 idx += len;
560 result[idx++] = ' ';
561 }
562 }
563
564 /* Kill the last space and terminate the string. */
565 if (idx == 0)
566 result[0] = '\0';
567 else
568 result[idx - 1] = '\0';
569
570 return result;
571}
572
573
574/*
575 Builtin functions
576 */
577
578static char *
579func_patsubst (char *o, char **argv, const char *funcname UNUSED)
580{
581 o = patsubst_expand (o, argv[2], argv[0], argv[1]);
582 return o;
583}
584
585
586static char *
587func_join (char *o, char **argv, const char *funcname UNUSED)
588{
589 int doneany = 0;
590
591 /* Write each word of the first argument directly followed
592 by the corresponding word of the second argument.
593 If the two arguments have a different number of words,
594 the excess words are just output separated by blanks. */
595 const char *tp;
596 const char *pp;
597 const char *list1_iterator = argv[0];
598 const char *list2_iterator = argv[1];
599 do
600 {
601 unsigned int len1, len2;
602
603 tp = find_next_token (&list1_iterator, &len1);
604 if (tp != 0)
605 o = variable_buffer_output (o, tp, len1);
606
607 pp = find_next_token (&list2_iterator, &len2);
608 if (pp != 0)
609 o = variable_buffer_output (o, pp, len2);
610
611 if (tp != 0 || pp != 0)
612 {
613 o = variable_buffer_output (o, " ", 1);
614 doneany = 1;
615 }
616 }
617 while (tp != 0 || pp != 0);
618 if (doneany)
619 /* Kill the last blank. */
620 --o;
621
622 return o;
623}
624
625
626static char *
627func_origin (char *o, char **argv, const char *funcname UNUSED)
628{
629 /* Expand the argument. */
630 struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
631 if (v == 0)
632 o = variable_buffer_output (o, "undefined", 9);
633 else
634 switch (v->origin)
635 {
636 default:
637 case o_invalid:
638 abort ();
639 break;
640 case o_default:
641 o = variable_buffer_output (o, "default", 7);
642 break;
643 case o_env:
644 o = variable_buffer_output (o, "environment", 11);
645 break;
646 case o_file:
647 o = variable_buffer_output (o, "file", 4);
648 break;
649 case o_env_override:
650 o = variable_buffer_output (o, "environment override", 20);
651 break;
652 case o_command:
653 o = variable_buffer_output (o, "command line", 12);
654 break;
655 case o_override:
656 o = variable_buffer_output (o, "override", 8);
657 break;
658 case o_automatic:
659 o = variable_buffer_output (o, "automatic", 9);
660 break;
661#ifdef CONFIG_WITH_LOCAL_VARIABLES
662 case o_local:
663 o = variable_buffer_output (o, "local", 5);
664 break;
665#endif
666 }
667
668 return o;
669}
670
671static char *
672func_flavor (char *o, char **argv, const char *funcname UNUSED)
673{
674 struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
675
676 if (v == 0)
677 o = variable_buffer_output (o, "undefined", 9);
678 else
679 if (v->recursive)
680 o = variable_buffer_output (o, "recursive", 9);
681 else
682 o = variable_buffer_output (o, "simple", 6);
683
684 return o;
685}
686
687#ifdef VMS
688# define IS_PATHSEP(c) ((c) == ']')
689#else
690# ifdef HAVE_DOS_PATHS
691# define IS_PATHSEP(c) ((c) == '/' || (c) == '\\')
692# else
693# define IS_PATHSEP(c) ((c) == '/')
694# endif
695#endif
696
697
698static char *
699func_notdir_suffix (char *o, char **argv, const char *funcname)
700{
701 /* Expand the argument. */
702 const char *list_iterator = argv[0];
703 const char *p2;
704 int doneany =0;
705 unsigned int len=0;
706
707 int is_suffix = streq (funcname, "suffix");
708 int is_notdir = !is_suffix;
709 while ((p2 = find_next_token (&list_iterator, &len)) != 0)
710 {
711 const char *p = p2 + len;
712
713
714 while (p >= p2 && (!is_suffix || *p != '.'))
715 {
716 if (IS_PATHSEP (*p))
717 break;
718 --p;
719 }
720
721 if (p >= p2)
722 {
723 if (is_notdir)
724 ++p;
725 else if (*p != '.')
726 continue;
727 o = variable_buffer_output (o, p, len - (p - p2));
728 }
729#ifdef HAVE_DOS_PATHS
730 /* Handle the case of "d:foo/bar". */
731 else if (streq (funcname, "notdir") && p2[0] && p2[1] == ':')
732 {
733 p = p2 + 2;
734 o = variable_buffer_output (o, p, len - (p - p2));
735 }
736#endif
737 else if (is_notdir)
738 o = variable_buffer_output (o, p2, len);
739
740 if (is_notdir || p >= p2)
741 {
742 o = variable_buffer_output (o, " ", 1);
743 doneany = 1;
744 }
745 }
746
747 if (doneany)
748 /* Kill last space. */
749 --o;
750
751 return o;
752}
753
754
755static char *
756func_basename_dir (char *o, char **argv, const char *funcname)
757{
758 /* Expand the argument. */
759 const char *p3 = argv[0];
760 const char *p2;
761 int doneany=0;
762 unsigned int len=0;
763
764 int is_basename= streq (funcname, "basename");
765 int is_dir= !is_basename;
766
767 while ((p2 = find_next_token (&p3, &len)) != 0)
768 {
769 const char *p = p2 + len;
770 while (p >= p2 && (!is_basename || *p != '.'))
771 {
772 if (IS_PATHSEP (*p))
773 break;
774 --p;
775 }
776
777 if (p >= p2 && (is_dir))
778 o = variable_buffer_output (o, p2, ++p - p2);
779 else if (p >= p2 && (*p == '.'))
780 o = variable_buffer_output (o, p2, p - p2);
781#ifdef HAVE_DOS_PATHS
782 /* Handle the "d:foobar" case */
783 else if (p2[0] && p2[1] == ':' && is_dir)
784 o = variable_buffer_output (o, p2, 2);
785#endif
786 else if (is_dir)
787#ifdef VMS
788 o = variable_buffer_output (o, "[]", 2);
789#else
790#ifndef _AMIGA
791 o = variable_buffer_output (o, "./", 2);
792#else
793 ; /* Just a nop... */
794#endif /* AMIGA */
795#endif /* !VMS */
796 else
797 /* The entire name is the basename. */
798 o = variable_buffer_output (o, p2, len);
799
800 o = variable_buffer_output (o, " ", 1);
801 doneany = 1;
802 }
803
804 if (doneany)
805 /* Kill last space. */
806 --o;
807
808 return o;
809}
810
811static char *
812func_addsuffix_addprefix (char *o, char **argv, const char *funcname)
813{
814 int fixlen = strlen (argv[0]);
815 const char *list_iterator = argv[1];
816 int is_addprefix = streq (funcname, "addprefix");
817 int is_addsuffix = !is_addprefix;
818
819 int doneany = 0;
820 const char *p;
821 unsigned int len;
822
823 while ((p = find_next_token (&list_iterator, &len)) != 0)
824 {
825 if (is_addprefix)
826 o = variable_buffer_output (o, argv[0], fixlen);
827 o = variable_buffer_output (o, p, len);
828 if (is_addsuffix)
829 o = variable_buffer_output (o, argv[0], fixlen);
830 o = variable_buffer_output (o, " ", 1);
831 doneany = 1;
832 }
833
834 if (doneany)
835 /* Kill last space. */
836 --o;
837
838 return o;
839}
840
841static char *
842func_subst (char *o, char **argv, const char *funcname UNUSED)
843{
844 o = subst_expand (o, argv[2], argv[0], argv[1], strlen (argv[0]),
845 strlen (argv[1]), 0);
846
847 return o;
848}
849
850
851static char *
852func_firstword (char *o, char **argv, const char *funcname UNUSED)
853{
854 unsigned int i;
855 const char *words = argv[0]; /* Use a temp variable for find_next_token */
856 const char *p = find_next_token (&words, &i);
857
858 if (p != 0)
859 o = variable_buffer_output (o, p, i);
860
861 return o;
862}
863
864static char *
865func_lastword (char *o, char **argv, const char *funcname UNUSED)
866{
867 unsigned int i;
868 const char *words = argv[0]; /* Use a temp variable for find_next_token */
869 const char *p = NULL;
870 const char *t;
871
872 while ((t = find_next_token (&words, &i)))
873 p = t;
874
875 if (p != 0)
876 o = variable_buffer_output (o, p, i);
877
878 return o;
879}
880
881static char *
882func_words (char *o, char **argv, const char *funcname UNUSED)
883{
884 int i = 0;
885 const char *word_iterator = argv[0];
886 char buf[20];
887
888 while (find_next_token (&word_iterator, (unsigned int *) 0) != 0)
889 ++i;
890
891 sprintf (buf, "%d", i);
892 o = variable_buffer_output (o, buf, strlen (buf));
893
894 return o;
895}
896
897/* Set begpp to point to the first non-whitespace character of the string,
898 * and endpp to point to the last non-whitespace character of the string.
899 * If the string is empty or contains nothing but whitespace, endpp will be
900 * begpp-1.
901 */
902char *
903strip_whitespace (const char **begpp, const char **endpp)
904{
905 while (*begpp <= *endpp && isspace ((unsigned char)**begpp))
906 (*begpp) ++;
907 while (*endpp >= *begpp && isspace ((unsigned char)**endpp))
908 (*endpp) --;
909 return (char *)*begpp;
910}
911
912static void
913check_numeric (const char *s, const char *msg)
914{
915 const char *end = s + strlen (s) - 1;
916 const char *beg = s;
917 strip_whitespace (&s, &end);
918
919 for (; s <= end; ++s)
920 if (!ISDIGIT (*s)) /* ISDIGIT only evals its arg once: see make.h. */
921 break;
922
923 if (s <= end || end - beg < 0)
924 fatal (*expanding_var, "%s: '%s'", msg, beg);
925}
926
927
928
929static char *
930func_word (char *o, char **argv, const char *funcname UNUSED)
931{
932 const char *end_p;
933 const char *p;
934 int i;
935
936 /* Check the first argument. */
937 check_numeric (argv[0], _("non-numeric first argument to `word' function"));
938 i = atoi (argv[0]);
939
940 if (i == 0)
941 fatal (*expanding_var,
942 _("first argument to `word' function must be greater than 0"));
943
944 end_p = argv[1];
945 while ((p = find_next_token (&end_p, 0)) != 0)
946 if (--i == 0)
947 break;
948
949 if (i == 0)
950 o = variable_buffer_output (o, p, end_p - p);
951
952 return o;
953}
954
955static char *
956func_wordlist (char *o, char **argv, const char *funcname UNUSED)
957{
958 int start, count;
959
960 /* Check the arguments. */
961 check_numeric (argv[0],
962 _("non-numeric first argument to `wordlist' function"));
963 check_numeric (argv[1],
964 _("non-numeric second argument to `wordlist' function"));
965
966 start = atoi (argv[0]);
967 if (start < 1)
968 fatal (*expanding_var,
969 "invalid first argument to `wordlist' function: `%d'", start);
970
971 count = atoi (argv[1]) - start + 1;
972
973 if (count > 0)
974 {
975 const char *p;
976 const char *end_p = argv[2];
977
978 /* Find the beginning of the "start"th word. */
979 while (((p = find_next_token (&end_p, 0)) != 0) && --start)
980 ;
981
982 if (p)
983 {
984 /* Find the end of the "count"th word from start. */
985 while (--count && (find_next_token (&end_p, 0) != 0))
986 ;
987
988 /* Return the stuff in the middle. */
989 o = variable_buffer_output (o, p, end_p - p);
990 }
991 }
992
993 return o;
994}
995
996static char *
997func_findstring (char *o, char **argv, const char *funcname UNUSED)
998{
999 /* Find the first occurrence of the first string in the second. */
1000 if (strstr (argv[1], argv[0]) != 0)
1001 o = variable_buffer_output (o, argv[0], strlen (argv[0]));
1002
1003 return o;
1004}
1005
1006static char *
1007func_foreach (char *o, char **argv, const char *funcname UNUSED)
1008{
1009 /* expand only the first two. */
1010 char *varname = expand_argument (argv[0], NULL);
1011 char *list = expand_argument (argv[1], NULL);
1012 const char *body = argv[2];
1013#ifdef CONFIG_WITH_VALUE_LENGTH
1014 long body_len = strlen (body);
1015#endif
1016
1017 int doneany = 0;
1018 const char *list_iterator = list;
1019 const char *p;
1020 unsigned int len;
1021 struct variable *var;
1022
1023 push_new_variable_scope ();
1024 var = define_variable (varname, strlen (varname), "", o_automatic, 0);
1025
1026 /* loop through LIST, put the value in VAR and expand BODY */
1027 while ((p = find_next_token (&list_iterator, &len)) != 0)
1028 {
1029#ifndef CONFIG_WITH_VALUE_LENGTH
1030 char *result = 0;
1031
1032 free (var->value);
1033 var->value = savestring (p, len);
1034
1035 result = allocated_variable_expand (body);
1036
1037 o = variable_buffer_output (o, result, strlen (result));
1038 o = variable_buffer_output (o, " ", 1);
1039 doneany = 1;
1040 free (result);
1041#else /* CONFIG_WITH_VALUE_LENGTH */
1042 if (len >= (unsigned int)var->value_alloc_len)
1043 {
1044# ifdef CONFIG_WITH_RDONLY_VARIABLE_VALUE
1045 if (var->rdonly_val)
1046 var->rdonly_val = 0;
1047 else
1048# endif
1049 free (var->value);
1050 var->value_alloc_len = (len + 32) & ~31;
1051 var->value = xmalloc (var->value_alloc_len);
1052 }
1053 memcpy (var->value, p, len);
1054 var->value[len] = '\0';
1055 var->value_length = len;
1056
1057 variable_expand_string_2 (o, body, body_len, &o);
1058 o = variable_buffer_output (o, " ", 1);
1059 doneany = 1;
1060#endif /* CONFIG_WITH_VALUE_LENGTH */
1061 }
1062
1063 if (doneany)
1064 /* Kill the last space. */
1065 --o;
1066
1067 pop_variable_scope ();
1068 free (varname);
1069 free (list);
1070
1071 return o;
1072}
1073
1074struct a_word
1075{
1076 struct a_word *next;
1077 struct a_word *chain;
1078 char *str;
1079 int length;
1080 int matched;
1081};
1082
1083static unsigned long
1084a_word_hash_1 (const void *key)
1085{
1086 return_STRING_HASH_1 (((struct a_word const *) key)->str);
1087}
1088
1089static unsigned long
1090a_word_hash_2 (const void *key)
1091{
1092 return_STRING_HASH_2 (((struct a_word const *) key)->str);
1093}
1094
1095static int
1096a_word_hash_cmp (const void *x, const void *y)
1097{
1098 int result = ((struct a_word const *) x)->length - ((struct a_word const *) y)->length;
1099 if (result)
1100 return result;
1101 return_STRING_COMPARE (((struct a_word const *) x)->str,
1102 ((struct a_word const *) y)->str);
1103}
1104
1105struct a_pattern
1106{
1107 struct a_pattern *next;
1108 char *str;
1109 char *percent;
1110 int length;
1111 int save_c;
1112};
1113
1114static char *
1115func_filter_filterout (char *o, char **argv, const char *funcname)
1116{
1117 struct a_word *wordhead;
1118 struct a_word **wordtail;
1119 struct a_word *wp;
1120 struct a_pattern *pathead;
1121 struct a_pattern **pattail;
1122 struct a_pattern *pp;
1123
1124 struct hash_table a_word_table;
1125 int is_filter = streq (funcname, "filter");
1126 const char *pat_iterator = argv[0];
1127 const char *word_iterator = argv[1];
1128 int literals = 0;
1129 int words = 0;
1130 int hashing = 0;
1131 char *p;
1132 unsigned int len;
1133
1134 /* Chop ARGV[0] up into patterns to match against the words. */
1135
1136 pattail = &pathead;
1137 while ((p = find_next_token (&pat_iterator, &len)) != 0)
1138 {
1139 struct a_pattern *pat = alloca (sizeof (struct a_pattern));
1140
1141 *pattail = pat;
1142 pattail = &pat->next;
1143
1144 if (*pat_iterator != '\0')
1145 ++pat_iterator;
1146
1147 pat->str = p;
1148 pat->length = len;
1149 pat->save_c = p[len];
1150 p[len] = '\0';
1151 pat->percent = find_percent (p);
1152 if (pat->percent == 0)
1153 literals++;
1154 }
1155 *pattail = 0;
1156
1157 /* Chop ARGV[1] up into words to match against the patterns. */
1158
1159 wordtail = &wordhead;
1160 while ((p = find_next_token (&word_iterator, &len)) != 0)
1161 {
1162 struct a_word *word = alloca (sizeof (struct a_word));
1163
1164 *wordtail = word;
1165 wordtail = &word->next;
1166
1167 if (*word_iterator != '\0')
1168 ++word_iterator;
1169
1170 p[len] = '\0';
1171 word->str = p;
1172 word->length = len;
1173 word->matched = 0;
1174 word->chain = 0;
1175 words++;
1176 }
1177 *wordtail = 0;
1178
1179 /* Only use a hash table if arg list lengths justifies the cost. */
1180 hashing = (literals >= 2 && (literals * words) >= 10);
1181 if (hashing)
1182 {
1183 hash_init (&a_word_table, words, a_word_hash_1, a_word_hash_2,
1184 a_word_hash_cmp);
1185 for (wp = wordhead; wp != 0; wp = wp->next)
1186 {
1187 struct a_word *owp = hash_insert (&a_word_table, wp);
1188 if (owp)
1189 wp->chain = owp;
1190 }
1191 }
1192
1193 if (words)
1194 {
1195 int doneany = 0;
1196
1197 /* Run each pattern through the words, killing words. */
1198 for (pp = pathead; pp != 0; pp = pp->next)
1199 {
1200 if (pp->percent)
1201 for (wp = wordhead; wp != 0; wp = wp->next)
1202 wp->matched |= pattern_matches (pp->str, pp->percent, wp->str);
1203 else if (hashing)
1204 {
1205 struct a_word a_word_key;
1206 a_word_key.str = pp->str;
1207 a_word_key.length = pp->length;
1208 wp = hash_find_item (&a_word_table, &a_word_key);
1209 while (wp)
1210 {
1211 wp->matched |= 1;
1212 wp = wp->chain;
1213 }
1214 }
1215 else
1216 for (wp = wordhead; wp != 0; wp = wp->next)
1217 wp->matched |= (wp->length == pp->length
1218 && strneq (pp->str, wp->str, wp->length));
1219 }
1220
1221 /* Output the words that matched (or didn't, for filter-out). */
1222 for (wp = wordhead; wp != 0; wp = wp->next)
1223 if (is_filter ? wp->matched : !wp->matched)
1224 {
1225 o = variable_buffer_output (o, wp->str, strlen (wp->str));
1226 o = variable_buffer_output (o, " ", 1);
1227 doneany = 1;
1228 }
1229
1230 if (doneany)
1231 /* Kill the last space. */
1232 --o;
1233 }
1234
1235 for (pp = pathead; pp != 0; pp = pp->next)
1236 pp->str[pp->length] = pp->save_c;
1237
1238 if (hashing)
1239 hash_free (&a_word_table, 0);
1240
1241 return o;
1242}
1243
1244
1245static char *
1246func_strip (char *o, char **argv, const char *funcname UNUSED)
1247{
1248 const char *p = argv[0];
1249 int doneany = 0;
1250
1251 while (*p != '\0')
1252 {
1253 int i=0;
1254 const char *word_start;
1255
1256 while (isspace ((unsigned char)*p))
1257 ++p;
1258 word_start = p;
1259 for (i=0; *p != '\0' && !isspace ((unsigned char)*p); ++p, ++i)
1260 {}
1261 if (!i)
1262 break;
1263 o = variable_buffer_output (o, word_start, i);
1264 o = variable_buffer_output (o, " ", 1);
1265 doneany = 1;
1266 }
1267
1268 if (doneany)
1269 /* Kill the last space. */
1270 --o;
1271
1272 return o;
1273}
1274
1275/*
1276 Print a warning or fatal message.
1277*/
1278static char *
1279func_error (char *o, char **argv, const char *funcname)
1280{
1281 char **argvp;
1282 char *msg, *p;
1283 int len;
1284
1285 /* The arguments will be broken on commas. Rather than create yet
1286 another special case where function arguments aren't broken up,
1287 just create a format string that puts them back together. */
1288 for (len=0, argvp=argv; *argvp != 0; ++argvp)
1289 len += strlen (*argvp) + 2;
1290
1291 p = msg = alloca (len + 1);
1292
1293 for (argvp=argv; argvp[1] != 0; ++argvp)
1294 {
1295 strcpy (p, *argvp);
1296 p += strlen (*argvp);
1297 *(p++) = ',';
1298 *(p++) = ' ';
1299 }
1300 strcpy (p, *argvp);
1301
1302 switch (*funcname) {
1303 case 'e':
1304 fatal (reading_file, "%s", msg);
1305
1306 case 'w':
1307 error (reading_file, "%s", msg);
1308 break;
1309
1310 case 'i':
1311 printf ("%s\n", msg);
1312 fflush(stdout);
1313 break;
1314
1315 default:
1316 fatal (*expanding_var, "Internal error: func_error: '%s'", funcname);
1317 }
1318
1319 /* The warning function expands to the empty string. */
1320 return o;
1321}
1322
1323
1324/*
1325 chop argv[0] into words, and sort them.
1326 */
1327static char *
1328func_sort (char *o, char **argv, const char *funcname UNUSED)
1329{
1330 const char *t;
1331 char **words;
1332 int wordi;
1333 char *p;
1334 unsigned int len;
1335 int i;
1336
1337 /* Find the maximum number of words we'll have. */
1338 t = argv[0];
1339 wordi = 1;
1340 while (*t != '\0')
1341 {
1342 char c = *(t++);
1343
1344 if (! isspace ((unsigned char)c))
1345 continue;
1346
1347 ++wordi;
1348
1349 while (isspace ((unsigned char)*t))
1350 ++t;
1351 }
1352
1353 words = xmalloc (wordi * sizeof (char *));
1354
1355 /* Now assign pointers to each string in the array. */
1356 t = argv[0];
1357 wordi = 0;
1358 while ((p = find_next_token (&t, &len)) != 0)
1359 {
1360 ++t;
1361 p[len] = '\0';
1362 words[wordi++] = p;
1363 }
1364
1365 if (wordi)
1366 {
1367 /* Now sort the list of words. */
1368 qsort (words, wordi, sizeof (char *), alpha_compare);
1369
1370 /* Now write the sorted list, uniquified. */
1371#ifdef CONFIG_WITH_RSORT
1372 if (strcmp (funcname, "rsort"))
1373 {
1374 /* sort */
1375#endif
1376 for (i = 0; i < wordi; ++i)
1377 {
1378 len = strlen (words[i]);
1379 if (i == wordi - 1 || strlen (words[i + 1]) != len
1380 || strcmp (words[i], words[i + 1]))
1381 {
1382 o = variable_buffer_output (o, words[i], len);
1383 o = variable_buffer_output (o, " ", 1);
1384 }
1385 }
1386#ifdef CONFIG_WITH_RSORT
1387 }
1388 else
1389 {
1390 /* rsort - reverse the result */
1391 i = wordi;
1392 while (i-- > 0)
1393 {
1394 len = strlen (words[i]);
1395 if (i == 0 || strlen (words[i - 1]) != len
1396 || strcmp (words[i], words[i - 1]))
1397 {
1398 o = variable_buffer_output (o, words[i], len);
1399 o = variable_buffer_output (o, " ", 1);
1400 }
1401 }
1402 }
1403#endif
1404
1405 /* Kill the last space. */
1406 --o;
1407 }
1408
1409 free (words);
1410
1411 return o;
1412}
1413
1414/*
1415 $(if condition,true-part[,false-part])
1416
1417 CONDITION is false iff it evaluates to an empty string. White
1418 space before and after condition are stripped before evaluation.
1419
1420 If CONDITION is true, then TRUE-PART is evaluated, otherwise FALSE-PART is
1421 evaluated (if it exists). Because only one of the two PARTs is evaluated,
1422 you can use $(if ...) to create side-effects (with $(shell ...), for
1423 example).
1424*/
1425
1426static char *
1427func_if (char *o, char **argv, const char *funcname UNUSED)
1428{
1429 const char *begp = argv[0];
1430 const char *endp = begp + strlen (argv[0]) - 1;
1431 int result = 0;
1432
1433 /* Find the result of the condition: if we have a value, and it's not
1434 empty, the condition is true. If we don't have a value, or it's the
1435 empty string, then it's false. */
1436
1437 strip_whitespace (&begp, &endp);
1438
1439 if (begp <= endp)
1440 {
1441 char *expansion = expand_argument (begp, endp+1);
1442
1443 result = strlen (expansion);
1444 free (expansion);
1445 }
1446
1447 /* If the result is true (1) we want to eval the first argument, and if
1448 it's false (0) we want to eval the second. If the argument doesn't
1449 exist we do nothing, otherwise expand it and add to the buffer. */
1450
1451 argv += 1 + !result;
1452
1453 if (*argv)
1454 {
1455 char *expansion = expand_argument (*argv, NULL);
1456
1457 o = variable_buffer_output (o, expansion, strlen (expansion));
1458
1459 free (expansion);
1460 }
1461
1462 return o;
1463}
1464
1465/*
1466 $(or condition1[,condition2[,condition3[...]]])
1467
1468 A CONDITION is false iff it evaluates to an empty string. White
1469 space before and after CONDITION are stripped before evaluation.
1470
1471 CONDITION1 is evaluated. If it's true, then this is the result of
1472 expansion. If it's false, CONDITION2 is evaluated, and so on. If none of
1473 the conditions are true, the expansion is the empty string.
1474
1475 Once a CONDITION is true no further conditions are evaluated
1476 (short-circuiting).
1477*/
1478
1479static char *
1480func_or (char *o, char **argv, const char *funcname UNUSED)
1481{
1482 for ( ; *argv ; ++argv)
1483 {
1484 const char *begp = *argv;
1485 const char *endp = begp + strlen (*argv) - 1;
1486 char *expansion;
1487 int result = 0;
1488
1489 /* Find the result of the condition: if it's false keep going. */
1490
1491 strip_whitespace (&begp, &endp);
1492
1493 if (begp > endp)
1494 continue;
1495
1496 expansion = expand_argument (begp, endp+1);
1497 result = strlen (expansion);
1498
1499 /* If the result is false keep going. */
1500 if (!result)
1501 {
1502 free (expansion);
1503 continue;
1504 }
1505
1506 /* It's true! Keep this result and return. */
1507 o = variable_buffer_output (o, expansion, result);
1508 free (expansion);
1509 break;
1510 }
1511
1512 return o;
1513}
1514
1515/*
1516 $(and condition1[,condition2[,condition3[...]]])
1517
1518 A CONDITION is false iff it evaluates to an empty string. White
1519 space before and after CONDITION are stripped before evaluation.
1520
1521 CONDITION1 is evaluated. If it's false, then this is the result of
1522 expansion. If it's true, CONDITION2 is evaluated, and so on. If all of
1523 the conditions are true, the expansion is the result of the last condition.
1524
1525 Once a CONDITION is false no further conditions are evaluated
1526 (short-circuiting).
1527*/
1528
1529static char *
1530func_and (char *o, char **argv, const char *funcname UNUSED)
1531{
1532 char *expansion;
1533 int result;
1534
1535 while (1)
1536 {
1537 const char *begp = *argv;
1538 const char *endp = begp + strlen (*argv) - 1;
1539
1540 /* An empty condition is always false. */
1541 strip_whitespace (&begp, &endp);
1542 if (begp > endp)
1543 return o;
1544
1545 expansion = expand_argument (begp, endp+1);
1546 result = strlen (expansion);
1547
1548 /* If the result is false, stop here: we're done. */
1549 if (!result)
1550 break;
1551
1552 /* Otherwise the result is true. If this is the last one, keep this
1553 result and quit. Otherwise go on to the next one! */
1554
1555 if (*(++argv))
1556 free (expansion);
1557 else
1558 {
1559 o = variable_buffer_output (o, expansion, result);
1560 break;
1561 }
1562 }
1563
1564 free (expansion);
1565
1566 return o;
1567}
1568
1569static char *
1570func_wildcard (char *o, char **argv, const char *funcname UNUSED)
1571{
1572#ifdef _AMIGA
1573 o = wildcard_expansion (argv[0], o);
1574#else
1575 char *p = string_glob (argv[0]);
1576 o = variable_buffer_output (o, p, strlen (p));
1577#endif
1578 return o;
1579}
1580
1581/*
1582 $(eval <makefile string>)
1583
1584 Always resolves to the empty string.
1585
1586 Treat the arguments as a segment of makefile, and parse them.
1587*/
1588
1589static char *
1590func_eval (char *o, char **argv, const char *funcname UNUSED)
1591{
1592 char *buf;
1593 unsigned int len;
1594
1595 /* Eval the buffer. Pop the current variable buffer setting so that the
1596 eval'd code can use its own without conflicting. */
1597
1598 install_variable_buffer (&buf, &len);
1599
1600#ifndef CONFIG_WITH_VALUE_LENGTH
1601 eval_buffer (argv[0]);
1602#else
1603 eval_buffer (argv[0], strchr (argv[0], '\0'));
1604#endif
1605
1606 restore_variable_buffer (buf, len);
1607
1608 return o;
1609}
1610
1611
1612#ifdef CONFIG_WITH_EVALPLUS
1613/* Same as func_eval except that we push and pop the local variable
1614 context before evaluating the buffer. */
1615static char *
1616func_evalctx (char *o, char **argv, const char *funcname UNUSED)
1617{
1618 char *buf;
1619 unsigned int len;
1620
1621 /* Eval the buffer. Pop the current variable buffer setting so that the
1622 eval'd code can use its own without conflicting. */
1623
1624 install_variable_buffer (&buf, &len);
1625
1626 push_new_variable_scope ();
1627
1628 eval_buffer (argv[0], strchr (argv[0], '\0'));
1629
1630 pop_variable_scope ();
1631
1632 restore_variable_buffer (buf, len);
1633
1634 return o;
1635}
1636
1637/* A mix of func_eval and func_value, saves memory for the expansion.
1638 This implements both evalval and evalvalctx, the latter has its own
1639 variable context just like evalctx. */
1640static char *
1641func_evalval (char *o, char **argv, const char *funcname)
1642{
1643 /* Look up the variable. */
1644 struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
1645 if (v)
1646 {
1647 char *buf;
1648 unsigned int len;
1649 int var_ctx;
1650 size_t off;
1651 const struct floc *reading_file_saved = reading_file;
1652
1653 /* Make a copy of the value to the variable buffer since
1654 eval_buffer will make changes to its input. */
1655
1656 off = o - variable_buffer;
1657 variable_buffer_output (o, v->value, v->value_length + 1);
1658 o = variable_buffer + off;
1659
1660 /* Eval the value. Pop the current variable buffer setting so that the
1661 eval'd code can use its own without conflicting. (really necessary?) */
1662
1663 install_variable_buffer (&buf, &len);
1664 var_ctx = !strcmp (funcname, "evalvalctx");
1665 if (var_ctx)
1666 push_new_variable_scope ();
1667 if (v->fileinfo.filenm)
1668 reading_file = &v->fileinfo;
1669
1670 assert (!o[v->value_length]);
1671 eval_buffer (o, o + v->value_length);
1672
1673 reading_file = reading_file_saved;
1674 if (var_ctx)
1675 pop_variable_scope ();
1676 restore_variable_buffer (buf, len);
1677 }
1678
1679 return o;
1680}
1681
1682/* Optimizes the content of one or more variables to save time in
1683 the eval functions. This function will collapse line continuations
1684 and remove comments. */
1685static char *
1686func_eval_optimize_variable (char *o, char **argv, const char *funcname)
1687{
1688 unsigned int i;
1689
1690 for (i = 0; argv[i]; i++)
1691 {
1692 struct variable *v = lookup_variable (argv[i], strlen (argv[i]));
1693# ifdef CONFIG_WITH_RDONLY_VARIABLE_VALUE
1694 if (v && !v->origin != o_automatic && !v->rdonly_val)
1695# else
1696 if (v && !v->origin != o_automatic)
1697# endif
1698 {
1699 char *eos, *src;
1700
1701 eos = collapse_continuations (v->value, v->value_length);
1702 v->value_length = eos - v->value;
1703
1704 /* remove comments */
1705
1706 src = memchr (v->value, '#', v->value_length);
1707 if (src)
1708 {
1709 unsigned char ch = '\0';
1710 char *dst = src;
1711 do
1712 {
1713 /* drop blanks preceeding the comment */
1714 while (dst > v->value)
1715 {
1716 ch = (unsigned char)dst[-1];
1717 if (!isblank (ch))
1718 break;
1719 dst--;
1720 }
1721
1722 /* advance SRC to eol / eos. */
1723 src = memchr (src, '\n', eos - src);
1724 if (!src)
1725 break;
1726
1727 /* drop a preceeding newline if possible (full line comment) */
1728 if (dst > v->value && dst[-1] == '\n')
1729 dst--;
1730
1731 /* copy till next comment or eol. */
1732 while (src < eos)
1733 {
1734 ch = *src++;
1735 if (ch == '#')
1736 break;
1737 *dst++ = ch;
1738 }
1739 }
1740 while (ch == '#' && src < eos);
1741
1742 *dst = '\0';
1743 v->value_length = dst - v->value;
1744 }
1745 }
1746 else if (v)
1747 error (NILF, _("$(%s ): variable `%s' is of the wrong type\n"), funcname, v->name);
1748 }
1749
1750 return o;
1751}
1752
1753#endif /* CONFIG_WITH_EVALPLUS */
1754
1755static char *
1756func_value (char *o, char **argv, const char *funcname UNUSED)
1757{
1758 /* Look up the variable. */
1759 struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
1760
1761 /* Copy its value into the output buffer without expanding it. */
1762 if (v)
1763#ifdef CONFIG_WITH_VALUE_LENGTH
1764 o = variable_buffer_output (o, v->value,
1765 v->value_length >= 0
1766 ? (unsigned int)v->value_length /* FIXME */
1767 : strlen(v->value));
1768#else
1769 o = variable_buffer_output (o, v->value, strlen(v->value));
1770#endif
1771
1772 return o;
1773}
1774
1775/*
1776 \r is replaced on UNIX as well. Is this desirable?
1777 */
1778static void
1779fold_newlines (char *buffer, unsigned int *length)
1780{
1781 char *dst = buffer;
1782 char *src = buffer;
1783 char *last_nonnl = buffer -1;
1784 src[*length] = 0;
1785 for (; *src != '\0'; ++src)
1786 {
1787 if (src[0] == '\r' && src[1] == '\n')
1788 continue;
1789 if (*src == '\n')
1790 {
1791 *dst++ = ' ';
1792 }
1793 else
1794 {
1795 last_nonnl = dst;
1796 *dst++ = *src;
1797 }
1798 }
1799 *(++last_nonnl) = '\0';
1800 *length = last_nonnl - buffer;
1801}
1802
1803
1804
1805int shell_function_pid = 0, shell_function_completed;
1806
1807
1808#ifdef WINDOWS32
1809/*untested*/
1810
1811#include <windows.h>
1812#include <io.h>
1813#include "sub_proc.h"
1814
1815
1816void
1817windows32_openpipe (int *pipedes, int *pid_p, char **command_argv, char **envp)
1818{
1819 SECURITY_ATTRIBUTES saAttr;
1820 HANDLE hIn;
1821 HANDLE hErr;
1822 HANDLE hChildOutRd;
1823 HANDLE hChildOutWr;
1824 HANDLE hProcess;
1825
1826
1827 saAttr.nLength = sizeof (SECURITY_ATTRIBUTES);
1828 saAttr.bInheritHandle = TRUE;
1829 saAttr.lpSecurityDescriptor = NULL;
1830
1831 if (DuplicateHandle (GetCurrentProcess(),
1832 GetStdHandle(STD_INPUT_HANDLE),
1833 GetCurrentProcess(),
1834 &hIn,
1835 0,
1836 TRUE,
1837 DUPLICATE_SAME_ACCESS) == FALSE) {
1838 fatal (NILF, _("create_child_process: DuplicateHandle(In) failed (e=%ld)\n"),
1839 GetLastError());
1840
1841 }
1842 if (DuplicateHandle(GetCurrentProcess(),
1843 GetStdHandle(STD_ERROR_HANDLE),
1844 GetCurrentProcess(),
1845 &hErr,
1846 0,
1847 TRUE,
1848 DUPLICATE_SAME_ACCESS) == FALSE) {
1849 fatal (NILF, _("create_child_process: DuplicateHandle(Err) failed (e=%ld)\n"),
1850 GetLastError());
1851 }
1852
1853 if (!CreatePipe(&hChildOutRd, &hChildOutWr, &saAttr, 0))
1854 fatal (NILF, _("CreatePipe() failed (e=%ld)\n"), GetLastError());
1855
1856 hProcess = process_init_fd(hIn, hChildOutWr, hErr);
1857
1858 if (!hProcess)
1859 fatal (NILF, _("windows32_openpipe (): process_init_fd() failed\n"));
1860
1861 /* make sure that CreateProcess() has Path it needs */
1862 sync_Path_environment();
1863
1864 if (!process_begin(hProcess, command_argv, envp, command_argv[0], NULL)) {
1865 /* register process for wait */
1866 process_register(hProcess);
1867
1868 /* set the pid for returning to caller */
1869 *pid_p = (int) hProcess;
1870
1871 /* set up to read data from child */
1872 pipedes[0] = _open_osfhandle((long) hChildOutRd, O_RDONLY);
1873
1874 /* this will be closed almost right away */
1875 pipedes[1] = _open_osfhandle((long) hChildOutWr, O_APPEND);
1876 } else {
1877 /* reap/cleanup the failed process */
1878 process_cleanup(hProcess);
1879
1880 /* close handles which were duplicated, they weren't used */
1881 CloseHandle(hIn);
1882 CloseHandle(hErr);
1883
1884 /* close pipe handles, they won't be used */
1885 CloseHandle(hChildOutRd);
1886 CloseHandle(hChildOutWr);
1887
1888 /* set status for return */
1889 pipedes[0] = pipedes[1] = -1;
1890 *pid_p = -1;
1891 }
1892}
1893#endif
1894
1895
1896#ifdef __MSDOS__
1897FILE *
1898msdos_openpipe (int* pipedes, int *pidp, char *text)
1899{
1900 FILE *fpipe=0;
1901 /* MSDOS can't fork, but it has `popen'. */
1902 struct variable *sh = lookup_variable ("SHELL", 5);
1903 int e;
1904 extern int dos_command_running, dos_status;
1905
1906 /* Make sure not to bother processing an empty line. */
1907 while (isblank ((unsigned char)*text))
1908 ++text;
1909 if (*text == '\0')
1910 return 0;
1911
1912 if (sh)
1913 {
1914 char buf[PATH_MAX + 7];
1915 /* This makes sure $SHELL value is used by $(shell), even
1916 though the target environment is not passed to it. */
1917 sprintf (buf, "SHELL=%s", sh->value);
1918 putenv (buf);
1919 }
1920
1921 e = errno;
1922 errno = 0;
1923 dos_command_running = 1;
1924 dos_status = 0;
1925 /* If dos_status becomes non-zero, it means the child process
1926 was interrupted by a signal, like SIGINT or SIGQUIT. See
1927 fatal_error_signal in commands.c. */
1928 fpipe = popen (text, "rt");
1929 dos_command_running = 0;
1930 if (!fpipe || dos_status)
1931 {
1932 pipedes[0] = -1;
1933 *pidp = -1;
1934 if (dos_status)
1935 errno = EINTR;
1936 else if (errno == 0)
1937 errno = ENOMEM;
1938 shell_function_completed = -1;
1939 }
1940 else
1941 {
1942 pipedes[0] = fileno (fpipe);
1943 *pidp = 42; /* Yes, the Meaning of Life, the Universe, and Everything! */
1944 errno = e;
1945 shell_function_completed = 1;
1946 }
1947 return fpipe;
1948}
1949#endif
1950
1951/*
1952 Do shell spawning, with the naughty bits for different OSes.
1953 */
1954
1955#ifdef VMS
1956
1957/* VMS can't do $(shell ...) */
1958#define func_shell 0
1959
1960#else
1961#ifndef _AMIGA
1962static char *
1963func_shell (char *o, char **argv, const char *funcname UNUSED)
1964{
1965 char *batch_filename = NULL;
1966
1967#ifdef __MSDOS__
1968 FILE *fpipe;
1969#endif
1970 char **command_argv;
1971 const char *error_prefix;
1972 char **envp;
1973 int pipedes[2];
1974 int pid;
1975
1976#ifndef __MSDOS__
1977 /* Construct the argument list. */
1978 command_argv = construct_command_argv (argv[0], NULL, NULL, &batch_filename);
1979 if (command_argv == 0)
1980 return o;
1981#endif
1982
1983 /* Using a target environment for `shell' loses in cases like:
1984 export var = $(shell echo foobie)
1985 because target_environment hits a loop trying to expand $(var)
1986 to put it in the environment. This is even more confusing when
1987 var was not explicitly exported, but just appeared in the
1988 calling environment.
1989
1990 See Savannah bug #10593.
1991
1992 envp = target_environment (NILF);
1993 */
1994
1995 envp = environ;
1996
1997 /* For error messages. */
1998 if (reading_file && reading_file->filenm)
1999 {
2000 char *p = alloca (strlen (reading_file->filenm)+11+4);
2001 sprintf (p, "%s:%lu: ", reading_file->filenm, reading_file->lineno);
2002 error_prefix = p;
2003 }
2004 else
2005 error_prefix = "";
2006
2007#if defined(__MSDOS__)
2008 fpipe = msdos_openpipe (pipedes, &pid, argv[0]);
2009 if (pipedes[0] < 0)
2010 {
2011 perror_with_name (error_prefix, "pipe");
2012 return o;
2013 }
2014#elif defined(WINDOWS32)
2015 windows32_openpipe (pipedes, &pid, command_argv, envp);
2016 if (pipedes[0] < 0)
2017 {
2018 /* open of the pipe failed, mark as failed execution */
2019 shell_function_completed = -1;
2020
2021 return o;
2022 }
2023 else
2024#else
2025 if (pipe (pipedes) < 0)
2026 {
2027 perror_with_name (error_prefix, "pipe");
2028 return o;
2029 }
2030
2031# ifdef __EMX__
2032 /* close some handles that are unnecessary for the child process */
2033 CLOSE_ON_EXEC(pipedes[1]);
2034 CLOSE_ON_EXEC(pipedes[0]);
2035 /* Never use fork()/exec() here! Use spawn() instead in exec_command() */
2036 pid = child_execute_job (0, pipedes[1], command_argv, envp);
2037 if (pid < 0)
2038 perror_with_name (error_prefix, "spawn");
2039# else /* ! __EMX__ */
2040 pid = vfork ();
2041 if (pid < 0)
2042 perror_with_name (error_prefix, "fork");
2043 else if (pid == 0)
2044 child_execute_job (0, pipedes[1], command_argv, envp);
2045 else
2046# endif
2047#endif
2048 {
2049 /* We are the parent. */
2050 char *buffer;
2051 unsigned int maxlen, i;
2052 int cc;
2053
2054 /* Record the PID for reap_children. */
2055 shell_function_pid = pid;
2056#ifndef __MSDOS__
2057 shell_function_completed = 0;
2058
2059 /* Free the storage only the child needed. */
2060 free (command_argv[0]);
2061 free (command_argv);
2062
2063 /* Close the write side of the pipe. */
2064# ifdef _MSC_VER /* Avoid annoying msvcrt when debugging. (bird) */
2065 if (pipedes[1] != -1)
2066# endif
2067 close (pipedes[1]);
2068#endif
2069
2070 /* Set up and read from the pipe. */
2071
2072 maxlen = 200;
2073 buffer = xmalloc (maxlen + 1);
2074
2075 /* Read from the pipe until it gets EOF. */
2076 for (i = 0; ; i += cc)
2077 {
2078 if (i == maxlen)
2079 {
2080 maxlen += 512;
2081 buffer = xrealloc (buffer, maxlen + 1);
2082 }
2083
2084 EINTRLOOP (cc, read (pipedes[0], &buffer[i], maxlen - i));
2085 if (cc <= 0)
2086 break;
2087 }
2088 buffer[i] = '\0';
2089
2090 /* Close the read side of the pipe. */
2091#ifdef __MSDOS__
2092 if (fpipe)
2093 (void) pclose (fpipe);
2094#else
2095# ifdef _MSC_VER /* Avoid annoying msvcrt when debugging. (bird) */
2096 if (pipedes[0] != -1)
2097# endif
2098 (void) close (pipedes[0]);
2099#endif
2100
2101 /* Loop until child_handler or reap_children() sets
2102 shell_function_completed to the status of our child shell. */
2103 while (shell_function_completed == 0)
2104 reap_children (1, 0);
2105
2106 if (batch_filename) {
2107 DB (DB_VERBOSE, (_("Cleaning up temporary batch file %s\n"),
2108 batch_filename));
2109 remove (batch_filename);
2110 free (batch_filename);
2111 }
2112 shell_function_pid = 0;
2113
2114 /* The child_handler function will set shell_function_completed
2115 to 1 when the child dies normally, or to -1 if it
2116 dies with status 127, which is most likely an exec fail. */
2117
2118 if (shell_function_completed == -1)
2119 {
2120 /* This likely means that the execvp failed, so we should just
2121 write the error message in the pipe from the child. */
2122 fputs (buffer, stderr);
2123 fflush (stderr);
2124 }
2125 else
2126 {
2127 /* The child finished normally. Replace all newlines in its output
2128 with spaces, and put that in the variable output buffer. */
2129 fold_newlines (buffer, &i);
2130 o = variable_buffer_output (o, buffer, i);
2131 }
2132
2133 free (buffer);
2134 }
2135
2136 return o;
2137}
2138
2139#else /* _AMIGA */
2140
2141/* Do the Amiga version of func_shell. */
2142
2143static char *
2144func_shell (char *o, char **argv, const char *funcname)
2145{
2146 /* Amiga can't fork nor spawn, but I can start a program with
2147 redirection of my choice. However, this means that we
2148 don't have an opportunity to reopen stdout to trap it. Thus,
2149 we save our own stdout onto a new descriptor and dup a temp
2150 file's descriptor onto our stdout temporarily. After we
2151 spawn the shell program, we dup our own stdout back to the
2152 stdout descriptor. The buffer reading is the same as above,
2153 except that we're now reading from a file. */
2154
2155#include <dos/dos.h>
2156#include <proto/dos.h>
2157
2158 BPTR child_stdout;
2159 char tmp_output[FILENAME_MAX];
2160 unsigned int maxlen = 200, i;
2161 int cc;
2162 char * buffer, * ptr;
2163 char ** aptr;
2164 int len = 0;
2165 char* batch_filename = NULL;
2166
2167 /* Construct the argument list. */
2168 command_argv = construct_command_argv (argv[0], (char **) NULL,
2169 (struct file *) 0, &batch_filename);
2170 if (command_argv == 0)
2171 return o;
2172
2173 /* Note the mktemp() is a security hole, but this only runs on Amiga.
2174 Ideally we would use main.c:open_tmpfile(), but this uses a special
2175 Open(), not fopen(), and I'm not familiar enough with the code to mess
2176 with it. */
2177 strcpy (tmp_output, "t:MakeshXXXXXXXX");
2178 mktemp (tmp_output);
2179 child_stdout = Open (tmp_output, MODE_NEWFILE);
2180
2181 for (aptr=command_argv; *aptr; aptr++)
2182 len += strlen (*aptr) + 1;
2183
2184 buffer = xmalloc (len + 1);
2185 ptr = buffer;
2186
2187 for (aptr=command_argv; *aptr; aptr++)
2188 {
2189 strcpy (ptr, *aptr);
2190 ptr += strlen (ptr) + 1;
2191 *ptr ++ = ' ';
2192 *ptr = 0;
2193 }
2194
2195 ptr[-1] = '\n';
2196
2197 Execute (buffer, NULL, child_stdout);
2198 free (buffer);
2199
2200 Close (child_stdout);
2201
2202 child_stdout = Open (tmp_output, MODE_OLDFILE);
2203
2204 buffer = xmalloc (maxlen);
2205 i = 0;
2206 do
2207 {
2208 if (i == maxlen)
2209 {
2210 maxlen += 512;
2211 buffer = xrealloc (buffer, maxlen + 1);
2212 }
2213
2214 cc = Read (child_stdout, &buffer[i], maxlen - i);
2215 if (cc > 0)
2216 i += cc;
2217 } while (cc > 0);
2218
2219 Close (child_stdout);
2220
2221 fold_newlines (buffer, &i);
2222 o = variable_buffer_output (o, buffer, i);
2223 free (buffer);
2224 return o;
2225}
2226#endif /* _AMIGA */
2227#endif /* !VMS */
2228
2229#ifdef EXPERIMENTAL
2230
2231/*
2232 equality. Return is string-boolean, ie, the empty string is false.
2233 */
2234static char *
2235func_eq (char *o, char **argv, const char *funcname)
2236{
2237 int result = ! strcmp (argv[0], argv[1]);
2238 o = variable_buffer_output (o, result ? "1" : "", result);
2239 return o;
2240}
2241
2242
2243/*
2244 string-boolean not operator.
2245 */
2246static char *
2247func_not (char *o, char **argv, const char *funcname)
2248{
2249 const char *s = argv[0];
2250 int result = 0;
2251 while (isspace ((unsigned char)*s))
2252 s++;
2253 result = ! (*s);
2254 o = variable_buffer_output (o, result ? "1" : "", result);
2255 return o;
2256}
2257#endif
2258
2259
2260#ifdef CONFIG_WITH_LAZY_DEPS_VARS
2261
2262/* This is also in file.c (bad). */
2263# if VMS
2264# define FILE_LIST_SEPARATOR ','
2265# else
2266# define FILE_LIST_SEPARATOR ' '
2267# endif
2268
2269/* Implements $^ and $+.
2270
2271 The first is somes with with FUNCNAME 'dep', the second as 'dep-all'.
2272
2273 If no second argument is given, or if it's empty, or if it's zero,
2274 all dependencies will be returned. If the second argument is non-zero
2275 the dependency at that position will be returned. If the argument is
2276 negative a fatal error is thrown. */
2277static char *
2278func_deps (char *o, char **argv, const char *funcname)
2279{
2280 unsigned int idx = 0;
2281 struct file *file;
2282
2283 /* Handle the argument if present. */
2284
2285 if (argv[1])
2286 {
2287 char *p = argv[1];
2288 while (isspace ((unsigned int)*p))
2289 p++;
2290 if (*p != '\0')
2291 {
2292 char *n;
2293 long l = strtol (p, &n, 0);
2294 while (isspace ((unsigned int)*n))
2295 n++;
2296 idx = l;
2297 if (*n != '\0' || l < 0 || (long)idx != l)
2298 fatal (NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
2299 }
2300 }
2301
2302 /* Find the file and select the list corresponding to FUNCNAME. */
2303
2304 file = lookup_file (argv[0]);
2305 if (file)
2306 {
2307 struct dep *deps = funcname[4] != '\0' && file->org_deps
2308 ? file->org_deps : file->deps;
2309 struct dep *d;
2310
2311 if ( file->double_colon
2312 && ( file->double_colon != file
2313 || file->last != file))
2314 error (NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
2315 funcname, file->name);
2316
2317 if (idx == 0 /* all */)
2318 {
2319 unsigned int total_len = 0;
2320
2321 /* calc the result length. */
2322
2323 for (d = deps; d; d = d->next)
2324 if (!d->ignore_mtime)
2325 {
2326 const char *c = dep_name (d);
2327
2328#ifndef NO_ARCHIVES
2329 if (ar_name (c))
2330 {
2331 c = strchr (c, '(') + 1;
2332 total_len += strlen (c);
2333 }
2334 else
2335#elif defined (CONFIG_WITH_STRCACHE2)
2336 total_len += strcache2_get_len (&file_strcache, c) + 1;
2337#else
2338 total_len += strlen (c) + 1;
2339#endif
2340 }
2341
2342 if (total_len)
2343 {
2344 /* prepare the variable buffer dude wrt to the output size and
2345 pass along the strings. */
2346
2347 o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
2348
2349 for (d = deps; d; d = d->next)
2350 if (!d->ignore_mtime)
2351 {
2352 unsigned int len;
2353 const char *c = dep_name (d);
2354
2355#ifndef NO_ARCHIVES
2356 if (ar_name (c))
2357 {
2358 c = strchr (c, '(') + 1;
2359 len = strlen (c);
2360 }
2361 else
2362#elif defined (CONFIG_WITH_STRCACHE2)
2363 len = strcache2_get_len (&file_strcache, c) + 1;
2364#else
2365 len = strlen (c) + 1;
2366#endif
2367 o = variable_buffer_output (o, c, len);
2368 o[-1] = FILE_LIST_SEPARATOR;
2369 }
2370
2371 --o; /* nuke the last list separator */
2372 *o = '\0';
2373 }
2374 }
2375 else
2376 {
2377 /* Dependency given by index. */
2378
2379 for (d = deps; d; d = d->next)
2380 if (!d->ignore_mtime)
2381 {
2382 if (--idx == 0) /* 1 based indexing */
2383 {
2384 unsigned int len;
2385 const char *c = dep_name (d);
2386
2387#ifndef NO_ARCHIVES
2388 if (ar_name (c))
2389 {
2390 c = strchr (c, '(') + 1;
2391 len = strlen (c) - 1;
2392 }
2393 else
2394#elif defined (CONFIG_WITH_STRCACHE2)
2395 len = strcache2_get_len (&file_strcache, c);
2396#else
2397 len = strlen (c);
2398#endif
2399 o = variable_buffer_output (o, c, len);
2400 break;
2401 }
2402 }
2403 }
2404 }
2405
2406 return o;
2407}
2408
2409/* Implements $?.
2410
2411 If no second argument is given, or if it's empty, or if it's zero,
2412 all dependencies will be returned. If the second argument is non-zero
2413 the dependency at that position will be returned. If the argument is
2414 negative a fatal error is thrown. */
2415static char *
2416func_deps_newer (char *o, char **argv, const char *funcname)
2417{
2418 unsigned int idx = 0;
2419 struct file *file;
2420
2421 /* Handle the argument if present. */
2422
2423 if (argv[1])
2424 {
2425 char *p = argv[1];
2426 while (isspace ((unsigned int)*p))
2427 p++;
2428 if (*p != '\0')
2429 {
2430 char *n;
2431 long l = strtol (p, &n, 0);
2432 while (isspace ((unsigned int)*n))
2433 n++;
2434 idx = l;
2435 if (*n != '\0' || l < 0 || (long)idx != l)
2436 fatal (NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
2437 }
2438 }
2439
2440 /* Find the file. */
2441
2442 file = lookup_file (argv[0]);
2443 if (file)
2444 {
2445 struct dep *deps = file->deps;
2446 struct dep *d;
2447
2448 if ( file->double_colon
2449 && ( file->double_colon != file
2450 || file->last != file))
2451 error (NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
2452 funcname, file->name);
2453
2454 if (idx == 0 /* all */)
2455 {
2456 unsigned int total_len = 0;
2457
2458 /* calc the result length. */
2459
2460 for (d = deps; d; d = d->next)
2461 if (!d->ignore_mtime && d->changed)
2462 {
2463 const char *c = dep_name (d);
2464
2465#ifndef NO_ARCHIVES
2466 if (ar_name (c))
2467 {
2468 c = strchr (c, '(') + 1;
2469 total_len += strlen (c);
2470 }
2471 else
2472#elif defined (CONFIG_WITH_STRCACHE2)
2473 total_len += strcache2_get_len (&file_strcache, c) + 1;
2474#else
2475 total_len += strlen (c) + 1;
2476#endif
2477 }
2478
2479 if (total_len)
2480 {
2481 /* prepare the variable buffer dude wrt to the output size and
2482 pass along the strings. */
2483
2484 o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
2485
2486 for (d = deps; d; d = d->next)
2487 if (!d->ignore_mtime && d->changed)
2488 {
2489 unsigned int len;
2490 const char *c = dep_name (d);
2491
2492#ifndef NO_ARCHIVES
2493 if (ar_name (c))
2494 {
2495 c = strchr (c, '(') + 1;
2496 len = strlen (c);
2497 }
2498 else
2499#elif defined (CONFIG_WITH_STRCACHE2)
2500 len = strcache2_get_len (&file_strcache, c) + 1;
2501#else
2502 len = strlen (c) + 1;
2503#endif
2504 o = variable_buffer_output (o, c, len);
2505 o[-1] = FILE_LIST_SEPARATOR;
2506 }
2507
2508 --o; /* nuke the last list separator */
2509 *o = '\0';
2510 }
2511 }
2512 else
2513 {
2514 /* Dependency given by index. */
2515
2516 for (d = deps; d; d = d->next)
2517 if (!d->ignore_mtime && d->changed)
2518 {
2519 if (--idx == 0) /* 1 based indexing */
2520 {
2521 unsigned int len;
2522 const char *c = dep_name (d);
2523
2524#ifndef NO_ARCHIVES
2525 if (ar_name (c))
2526 {
2527 c = strchr (c, '(') + 1;
2528 len = strlen (c) - 1;
2529 }
2530 else
2531#elif defined (CONFIG_WITH_STRCACHE2)
2532 len = strcache2_get_len (&file_strcache, c);
2533#else
2534 len = strlen (c);
2535#endif
2536 o = variable_buffer_output (o, c, len);
2537 break;
2538 }
2539 }
2540 }
2541 }
2542
2543 return o;
2544}
2545
2546/* Implements $|, the order only dependency list.
2547
2548 If no second argument is given, or if it's empty, or if it's zero,
2549 all dependencies will be returned. If the second argument is non-zero
2550 the dependency at that position will be returned. If the argument is
2551 negative a fatal error is thrown. */
2552static char *
2553func_deps_order_only (char *o, char **argv, const char *funcname)
2554{
2555 unsigned int idx = 0;
2556 struct file *file;
2557
2558 /* Handle the argument if present. */
2559
2560 if (argv[1])
2561 {
2562 char *p = argv[1];
2563 while (isspace ((unsigned int)*p))
2564 p++;
2565 if (*p != '\0')
2566 {
2567 char *n;
2568 long l = strtol (p, &n, 0);
2569 while (isspace ((unsigned int)*n))
2570 n++;
2571 idx = l;
2572 if (*n != '\0' || l < 0 || (long)idx != l)
2573 fatal (NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
2574 }
2575 }
2576
2577 /* Find the file. */
2578
2579 file = lookup_file (argv[0]);
2580 if (file)
2581 {
2582 struct dep *deps = file->deps;
2583 struct dep *d;
2584
2585 if ( file->double_colon
2586 && ( file->double_colon != file
2587 || file->last != file))
2588 error (NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
2589 funcname, file->name);
2590
2591 if (idx == 0 /* all */)
2592 {
2593 unsigned int total_len = 0;
2594
2595 /* calc the result length. */
2596
2597 for (d = deps; d; d = d->next)
2598 if (d->ignore_mtime)
2599 {
2600 const char *c = dep_name (d);
2601
2602#ifndef NO_ARCHIVES
2603 if (ar_name (c))
2604 {
2605 c = strchr (c, '(') + 1;
2606 total_len += strlen (c);
2607 }
2608 else
2609#elif defined (CONFIG_WITH_STRCACHE2)
2610 total_len += strcache2_get_len (&file_strcache, c) + 1;
2611#else
2612 total_len += strlen (c) + 1;
2613#endif
2614 }
2615
2616 if (total_len)
2617 {
2618 /* prepare the variable buffer dude wrt to the output size and
2619 pass along the strings. */
2620
2621 o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
2622
2623 for (d = deps; d; d = d->next)
2624 if (d->ignore_mtime)
2625 {
2626 unsigned int len;
2627 const char *c = dep_name (d);
2628
2629#ifndef NO_ARCHIVES
2630 if (ar_name (c))
2631 {
2632 c = strchr (c, '(') + 1;
2633 len = strlen (c);
2634 }
2635 else
2636#elif defined (CONFIG_WITH_STRCACHE2)
2637 len = strcache2_get_len (&file_strcache, c) + 1;
2638#else
2639 len = strlen (c) + 1;
2640#endif
2641 o = variable_buffer_output (o, c, len);
2642 o[-1] = FILE_LIST_SEPARATOR;
2643 }
2644
2645 --o; /* nuke the last list separator */
2646 *o = '\0';
2647 }
2648 }
2649 else
2650 {
2651 /* Dependency given by index. */
2652
2653 for (d = deps; d; d = d->next)
2654 if (d->ignore_mtime)
2655 {
2656 if (--idx == 0) /* 1 based indexing */
2657 {
2658 unsigned int len;
2659 const char *c = dep_name (d);
2660
2661#ifndef NO_ARCHIVES
2662 if (ar_name (c))
2663 {
2664 c = strchr (c, '(') + 1;
2665 len = strlen (c) - 1;
2666 }
2667 else
2668#elif defined (CONFIG_WITH_STRCACHE2)
2669 len = strcache2_get_len (&file_strcache, c);
2670#else
2671 len = strlen (c);
2672#endif
2673 o = variable_buffer_output (o, c, len);
2674 break;
2675 }
2676 }
2677 }
2678 }
2679
2680 return o;
2681}
2682#endif /* CONFIG_WITH_LAZY_DEPS_VARS */
2683
2684
2685
2686#ifdef CONFIG_WITH_DEFINED
2687/* Similar to ifdef. */
2688static char *
2689func_defined (char *o, char **argv, const char *funcname)
2690{
2691 struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
2692 int result = v != NULL && *v->value != '\0';
2693 o = variable_buffer_output (o, result ? "1" : "", result);
2694 return o;
2695}
2696#endif /* CONFIG_WITH_DEFINED*/
2697
2698
2699
2700/* Return the absolute name of file NAME which does not contain any `.',
2701 `..' components nor any repeated path separators ('/'). */
2702#ifdef KMK
2703char *
2704#else
2705static char *
2706#endif
2707abspath (const char *name, char *apath)
2708{
2709 char *dest;
2710 const char *start, *end, *apath_limit;
2711
2712 if (name[0] == '\0' || apath == NULL)
2713 return NULL;
2714
2715#ifdef WINDOWS32 /* bird */
2716 dest = w32ify((char *)name, 1);
2717 if (!dest)
2718 return NULL;
2719 {
2720 size_t len = strlen(dest);
2721 memcpy(apath, dest, len);
2722 dest = apath + len;
2723 }
2724
2725 (void)end; (void)start; (void)apath_limit;
2726
2727#elif defined __OS2__ /* bird */
2728 if (_abspath(apath, name, GET_PATH_MAX))
2729 return NULL;
2730 dest = strchr(apath, '\0');
2731
2732 (void)end; (void)start; (void)apath_limit; (void)dest;
2733
2734#else /* !WINDOWS32 && !__OS2__ */
2735 apath_limit = apath + GET_PATH_MAX;
2736
2737#ifdef HAVE_DOS_PATHS /* bird added this */
2738 if (isalpha(name[0]) && name[1] == ':')
2739 {
2740 /* drive spec */
2741 apath[0] = toupper(name[0]);
2742 apath[1] = ':';
2743 apath[2] = '/';
2744 name += 2;
2745 }
2746 else
2747#endif /* HAVE_DOS_PATHS */
2748 if (name[0] != '/')
2749 {
2750 /* It is unlikely we would make it until here but just to make sure. */
2751 if (!starting_directory)
2752 return NULL;
2753
2754 strcpy (apath, starting_directory);
2755
2756 dest = strchr (apath, '\0');
2757 }
2758 else
2759 {
2760 apath[0] = '/';
2761 dest = apath + 1;
2762 }
2763
2764 for (start = end = name; *start != '\0'; start = end)
2765 {
2766 unsigned long len;
2767
2768 /* Skip sequence of multiple path-separators. */
2769 while (*start == '/')
2770 ++start;
2771
2772 /* Find end of path component. */
2773 for (end = start; *end != '\0' && *end != '/'; ++end)
2774 ;
2775
2776 len = end - start;
2777
2778 if (len == 0)
2779 break;
2780 else if (len == 1 && start[0] == '.')
2781 /* nothing */;
2782 else if (len == 2 && start[0] == '.' && start[1] == '.')
2783 {
2784 /* Back up to previous component, ignore if at root already. */
2785 if (dest > apath + 1)
2786 while ((--dest)[-1] != '/');
2787 }
2788 else
2789 {
2790 if (dest[-1] != '/')
2791 *dest++ = '/';
2792
2793 if (dest + len >= apath_limit)
2794 return NULL;
2795
2796 dest = memcpy (dest, start, len);
2797 dest += len;
2798 *dest = '\0';
2799 }
2800 }
2801#endif /* !WINDOWS32 && !__OS2__ */
2802
2803 /* Unless it is root strip trailing separator. */
2804#ifdef HAVE_DOS_PATHS /* bird (is this correct? what about UNC?) */
2805 if (dest > apath + 1 + (apath[0] != '/') && dest[-1] == '/')
2806#else
2807 if (dest > apath + 1 && dest[-1] == '/')
2808#endif
2809 --dest;
2810
2811 *dest = '\0';
2812
2813 return apath;
2814}
2815
2816
2817static char *
2818func_realpath (char *o, char **argv, const char *funcname UNUSED)
2819{
2820 /* Expand the argument. */
2821 const char *p = argv[0];
2822 const char *path = 0;
2823 int doneany = 0;
2824 unsigned int len = 0;
2825 PATH_VAR (in);
2826 PATH_VAR (out);
2827
2828 while ((path = find_next_token (&p, &len)) != 0)
2829 {
2830 if (len < GET_PATH_MAX)
2831 {
2832 strncpy (in, path, len);
2833 in[len] = '\0';
2834
2835 if (
2836#ifdef HAVE_REALPATH
2837 realpath (in, out)
2838#else
2839 abspath (in, out)
2840#endif
2841 )
2842 {
2843 o = variable_buffer_output (o, out, strlen (out));
2844 o = variable_buffer_output (o, " ", 1);
2845 doneany = 1;
2846 }
2847 }
2848 }
2849
2850 /* Kill last space. */
2851 if (doneany)
2852 --o;
2853
2854 return o;
2855}
2856
2857static char *
2858func_abspath (char *o, char **argv, const char *funcname UNUSED)
2859{
2860 /* Expand the argument. */
2861 const char *p = argv[0];
2862 const char *path = 0;
2863 int doneany = 0;
2864 unsigned int len = 0;
2865 PATH_VAR (in);
2866 PATH_VAR (out);
2867
2868 while ((path = find_next_token (&p, &len)) != 0)
2869 {
2870 if (len < GET_PATH_MAX)
2871 {
2872 strncpy (in, path, len);
2873 in[len] = '\0';
2874
2875 if (abspath (in, out))
2876 {
2877 o = variable_buffer_output (o, out, strlen (out));
2878 o = variable_buffer_output (o, " ", 1);
2879 doneany = 1;
2880 }
2881 }
2882 }
2883
2884 /* Kill last space. */
2885 if (doneany)
2886 --o;
2887
2888 return o;
2889}
2890
2891#ifdef CONFIG_WITH_ABSPATHEX
2892/* Same as abspath except that the current path may be given as the
2893 2nd argument. */
2894static char *
2895func_abspathex (char *o, char **argv, const char *funcname UNUSED)
2896{
2897 char *cwd = argv[1];
2898
2899 /* cwd needs leading spaces chopped and may be optional,
2900 in which case we're exactly like $(abspath ). */
2901 while (isblank(*cwd))
2902 cwd++;
2903 if (!*cwd)
2904 o = func_abspath (o, argv, funcname);
2905 else
2906 {
2907 /* Expand the argument. */
2908 const char *p = argv[0];
2909 unsigned int cwd_len = ~0U;
2910 char *path = 0;
2911 int doneany = 0;
2912 unsigned int len = 0;
2913 PATH_VAR (in);
2914 PATH_VAR (out);
2915
2916 while ((path = find_next_token (&p, &len)) != 0)
2917 {
2918 if (len < GET_PATH_MAX)
2919 {
2920#ifdef HAVE_DOS_PATHS
2921 if (path[0] != '/' && path[0] != '\\' && (len < 2 || path[1] != ':') && cwd)
2922#else
2923 if (path[0] != '/' && cwd)
2924#endif
2925 {
2926 /* relative path, prefix with cwd. */
2927 if (cwd_len == ~0U)
2928 cwd_len = strlen (cwd);
2929 if (cwd_len + len + 1 >= GET_PATH_MAX)
2930 continue;
2931 memcpy (in, cwd, cwd_len);
2932 in[cwd_len] = '/';
2933 memcpy (in + cwd_len + 1, path, len);
2934 in[cwd_len + len + 1] = '\0';
2935 }
2936 else
2937 {
2938 /* absolute path pass it as-is. */
2939 memcpy (in, path, len);
2940 in[len] = '\0';
2941 }
2942
2943 if (abspath (in, out))
2944 {
2945 o = variable_buffer_output (o, out, strlen (out));
2946 o = variable_buffer_output (o, " ", 1);
2947 doneany = 1;
2948 }
2949 }
2950 }
2951
2952 /* Kill last space. */
2953 if (doneany)
2954 --o;
2955 }
2956
2957 return o;
2958}
2959#endif
2960
2961#ifdef CONFIG_WITH_XARGS
2962/* Create one or more command lines avoiding the max argument
2963 lenght restriction of the host OS.
2964
2965 The last argument is the list of arguments that the normal
2966 xargs command would be fed from stdin.
2967
2968 The first argument is initial command and it's arguments.
2969
2970 If there are three or more arguments, the 2nd argument is
2971 the command and arguments to be used on subsequent
2972 command lines. Defaults to the initial command.
2973
2974 If there are four or more arguments, the 3rd argument is
2975 the command to be used at the final command line. Defaults
2976 to the sub sequent or initial command .
2977
2978 A future version of this function may define more arguments
2979 and therefor anyone specifying six or more arguments will
2980 cause fatal errors.
2981
2982 Typical usage is:
2983 $(xargs ar cas mylib.a,$(objects))
2984 or
2985 $(xargs ar cas mylib.a,ar as mylib.a,$(objects))
2986
2987 It will then create one or more "ar mylib.a ..." command
2988 lines with proper \n\t separation so it can be used when
2989 writing rules. */
2990static char *
2991func_xargs (char *o, char **argv, const char *funcname UNUSED)
2992{
2993 int argc;
2994 const char *initial_cmd;
2995 size_t initial_cmd_len;
2996 const char *subsequent_cmd;
2997 size_t subsequent_cmd_len;
2998 const char *final_cmd;
2999 size_t final_cmd_len;
3000 const char *args;
3001 size_t max_args;
3002 int i;
3003
3004#ifdef ARG_MAX
3005 /* ARG_MAX is a bit unreliable (environment), so drop 25% of the max. */
3006# define XARGS_MAX (ARG_MAX - (ARG_MAX / 4))
3007#else /* FIXME: update configure with a command line length test. */
3008# define XARGS_MAX 10240
3009#endif
3010
3011 argc = 0;
3012 while (argv[argc])
3013 argc++;
3014 if (argc > 4)
3015 fatal (NILF, _("Too many arguments for $(xargs)!\n"));
3016
3017 /* first: the initial / default command.*/
3018 initial_cmd = argv[0];
3019 while (isspace ((unsigned char)*initial_cmd))
3020 initial_cmd++;
3021 max_args = initial_cmd_len = strlen (initial_cmd);
3022
3023 /* second: the command for the subsequent command lines. defaults to the initial cmd. */
3024 subsequent_cmd = argc > 2 && argv[1][0] != '\0' ? argv[1] : "";
3025 while (isspace ((unsigned char)*subsequent_cmd))
3026 subsequent_cmd++;
3027 if (*subsequent_cmd)
3028 {
3029 subsequent_cmd_len = strlen (subsequent_cmd);
3030 if (subsequent_cmd_len > max_args)
3031 max_args = subsequent_cmd_len;
3032 }
3033 else
3034 {
3035 subsequent_cmd = initial_cmd;
3036 subsequent_cmd_len = initial_cmd_len;
3037 }
3038
3039 /* third: the final command. defaults to the subseq cmd. */
3040 final_cmd = argc > 3 && argv[2][0] != '\0' ? argv[2] : "";
3041 while (isspace ((unsigned char)*final_cmd))
3042 final_cmd++;
3043 if (*final_cmd)
3044 {
3045 final_cmd_len = strlen (final_cmd);
3046 if (final_cmd_len > max_args)
3047 max_args = final_cmd_len;
3048 }
3049 else
3050 {
3051 final_cmd = subsequent_cmd;
3052 final_cmd_len = subsequent_cmd_len;
3053 }
3054
3055 /* last: the arguments to split up into sensible portions. */
3056 args = argv[argc - 1];
3057
3058 /* calc the max argument length. */
3059 if (XARGS_MAX <= max_args + 2)
3060 fatal (NILF, _("$(xargs): the commands are longer than the max exec argument length. (%lu <= %lu)\n"),
3061 (unsigned long)XARGS_MAX, (unsigned long)max_args + 2);
3062 max_args = XARGS_MAX - max_args - 1;
3063
3064 /* generate the commands. */
3065 i = 0;
3066 for (i = 0; ; i++)
3067 {
3068 unsigned int len;
3069 const char *iterator = args;
3070 const char *end = args;
3071 const char *cur;
3072 const char *tmp;
3073
3074 /* scan the arguments till we reach the end or the max length. */
3075 while ((cur = find_next_token(&iterator, &len))
3076 && (size_t)((cur + len) - args) < max_args)
3077 end = cur + len;
3078 if (cur && end == args)
3079 fatal (NILF, _("$(xargs): command + one single arg is too much. giving up.\n"));
3080
3081 /* emit the command. */
3082 if (i == 0)
3083 {
3084 o = variable_buffer_output (o, (char *)initial_cmd, initial_cmd_len);
3085 o = variable_buffer_output (o, " ", 1);
3086 }
3087 else if (cur)
3088 {
3089 o = variable_buffer_output (o, "\n\t", 2);
3090 o = variable_buffer_output (o, (char *)subsequent_cmd, subsequent_cmd_len);
3091 o = variable_buffer_output (o, " ", 1);
3092 }
3093 else
3094 {
3095 o = variable_buffer_output (o, "\n\t", 2);
3096 o = variable_buffer_output (o, (char *)final_cmd, final_cmd_len);
3097 o = variable_buffer_output (o, " ", 1);
3098 }
3099
3100 tmp = end;
3101 while (tmp > args && isspace ((unsigned char)tmp[-1])) /* drop trailing spaces. */
3102 tmp--;
3103 o = variable_buffer_output (o, (char *)args, tmp - args);
3104
3105
3106 /* next */
3107 if (!cur)
3108 break;
3109 args = end;
3110 while (isspace ((unsigned char)*args))
3111 args++;
3112 }
3113
3114 return o;
3115}
3116#endif
3117
3118#ifdef CONFIG_WITH_TOUPPER_TOLOWER
3119static char *
3120func_toupper_tolower (char *o, char **argv, const char *funcname)
3121{
3122 /* Expand the argument. */
3123 const char *p = argv[0];
3124 while (*p)
3125 {
3126 /* convert to temporary buffer */
3127 char tmp[256];
3128 unsigned int i;
3129 if (!strcmp(funcname, "toupper"))
3130 for (i = 0; i < sizeof(tmp) && *p; i++, p++)
3131 tmp[i] = toupper(*p);
3132 else
3133 for (i = 0; i < sizeof(tmp) && *p; i++, p++)
3134 tmp[i] = tolower(*p);
3135 o = variable_buffer_output (o, tmp, i);
3136 }
3137
3138 return o;
3139}
3140#endif /* CONFIG_WITH_TOUPPER_TOLOWER */
3141
3142#if defined(CONFIG_WITH_VALUE_LENGTH) && defined(CONFIG_WITH_COMPARE)
3143
3144/* Strip leading spaces and other things off a command. */
3145static const char *
3146comp_cmds_strip_leading (const char *s, const char *e)
3147{
3148 while (s < e)
3149 {
3150 const char ch = *s;
3151 if (!isblank (ch)
3152 && ch != '@'
3153#ifdef CONFIG_WITH_COMMANDS_FUNC
3154 && ch != '%'
3155#endif
3156 && ch != '+'
3157 && ch != '-')
3158 break;
3159 s++;
3160 }
3161 return s;
3162}
3163
3164/* Worker for func_comp_vars() which is called if the comparision failed.
3165 It will do the slow command by command comparision of the commands
3166 when there invoked as comp-cmds. */
3167static char *
3168comp_vars_ne (char *o, const char *s1, const char *e1, const char *s2, const char *e2,
3169 char *ne_retval, const char *funcname)
3170{
3171 /* give up at once if not comp-cmds or comp-cmds-ex. */
3172 if (strcmp (funcname, "comp-cmds") != 0
3173 && strcmp (funcname, "comp-cmds-ex") != 0)
3174 o = variable_buffer_output (o, ne_retval, strlen (ne_retval));
3175 else
3176 {
3177 const char * const s1_start = s1;
3178 int new_cmd = 1;
3179 int diff;
3180 for (;;)
3181 {
3182 /* if it's a new command, strip leading stuff. */
3183 if (new_cmd)
3184 {
3185 s1 = comp_cmds_strip_leading (s1, e1);
3186 s2 = comp_cmds_strip_leading (s2, e2);
3187 new_cmd = 0;
3188 }
3189 if (s1 >= e1 || s2 >= e2)
3190 break;
3191
3192 /*
3193 * Inner compare loop which compares one line.
3194 * FIXME: parse quoting!
3195 */
3196 for (;;)
3197 {
3198 const char ch1 = *s1;
3199 const char ch2 = *s2;
3200 diff = ch1 - ch2;
3201 if (diff)
3202 break;
3203 if (ch1 == '\n')
3204 break;
3205 assert (ch1 != '\r');
3206
3207 /* next */
3208 s1++;
3209 s2++;
3210 if (s1 >= e1 || s2 >= e2)
3211 break;
3212 }
3213
3214 /*
3215 * If we exited because of a difference try to end-of-command
3216 * comparision, e.g. ignore trailing spaces.
3217 */
3218 if (diff)
3219 {
3220 /* strip */
3221 while (s1 < e1 && isblank (*s1))
3222 s1++;
3223 while (s2 < e2 && isblank (*s2))
3224 s2++;
3225 if (s1 >= e1 || s2 >= e2)
3226 break;
3227
3228 /* compare again and check that it's a newline. */
3229 if (*s2 != '\n' || *s1 != '\n')
3230 break;
3231 }
3232 /* Break out if we exited because of EOS. */
3233 else if (s1 >= e1 || s2 >= e2)
3234 break;
3235
3236 /*
3237 * Detect the end of command lines.
3238 */
3239 if (*s1 == '\n')
3240 new_cmd = s1 == s1_start || s1[-1] != '\\';
3241 s1++;
3242 s2++;
3243 }
3244
3245 /*
3246 * Ignore trailing empty lines.
3247 */
3248 if (s1 < e1 || s2 < e2)
3249 {
3250 while (s1 < e1 && (isblank (*s1) || *s1 == '\n'))
3251 if (*s1++ == '\n')
3252 s1 = comp_cmds_strip_leading (s1, e1);
3253 while (s2 < e2 && (isblank (*s2) || *s2 == '\n'))
3254 if (*s2++ == '\n')
3255 s2 = comp_cmds_strip_leading (s2, e2);
3256 }
3257
3258 /* emit the result. */
3259 if (s1 == e1 && s2 == e2)
3260 o = variable_buffer_output (o, "", 1) - 1; /** @todo check why this was necessary back the... */
3261 else
3262 o = variable_buffer_output (o, ne_retval, strlen (ne_retval));
3263 }
3264 return o;
3265}
3266
3267/*
3268 $(comp-vars var1,var2,not-equal-return)
3269 or
3270 $(comp-cmds cmd-var1,cmd-var2,not-equal-return)
3271
3272 Compares the two variables (that's given by name to avoid unnecessary
3273 expanding) and return the string in the third argument if not equal.
3274 If equal, nothing is returned.
3275
3276 comp-vars will to an exact comparision only stripping leading and
3277 trailing spaces.
3278
3279 comp-cmds will compare command by command, ignoring not only leading
3280 and trailing spaces on each line but also leading one leading '@',
3281 '-', '+' and '%'
3282*/
3283static char *
3284func_comp_vars (char *o, char **argv, const char *funcname)
3285{
3286 const char *s1, *e1, *x1, *s2, *e2, *x2;
3287 char *a1 = NULL, *a2 = NULL;
3288 size_t l, l1, l2;
3289 struct variable *var1 = lookup_variable (argv[0], strlen (argv[0]));
3290 struct variable *var2 = lookup_variable (argv[1], strlen (argv[1]));
3291
3292 /* the simple cases */
3293 if (var1 == var2)
3294 return variable_buffer_output (o, "", 0); /* eq */
3295 if (!var1 || !var2)
3296 return variable_buffer_output (o, argv[2], strlen(argv[2]));
3297 if (var1->value == var2->value)
3298 return variable_buffer_output (o, "", 0); /* eq */
3299 if (!var1->recursive && !var2->recursive)
3300 {
3301 if ( var1->value_length == var2->value_length
3302 && !memcmp (var1->value, var2->value, var1->value_length))
3303 return variable_buffer_output (o, "", 0); /* eq */
3304
3305 /* ignore trailing and leading blanks */
3306 s1 = var1->value;
3307 e1 = s1 + var1->value_length;
3308 while (isblank ((unsigned char) *s1))
3309 s1++;
3310 while (e1 > s1 && isblank ((unsigned char) e1[-1]))
3311 e1--;
3312
3313 s2 = var2->value;
3314 e2 = s2 + var2->value_length;
3315 while (isblank ((unsigned char) *s2))
3316 s2++;
3317 while (e2 > s2 && isblank ((unsigned char) e2[-1]))
3318 e2--;
3319
3320 if (e1 - s1 != e2 - s2)
3321 return comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3322 if (!memcmp (s1, s2, e1 - s1))
3323 return variable_buffer_output (o, "", 0); /* eq */
3324 return comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3325 }
3326
3327 /* ignore trailing and leading blanks */
3328 s1 = var1->value;
3329 e1 = s1 + var1->value_length;
3330 while (isblank ((unsigned char) *s1))
3331 s1++;
3332 while (e1 > s1 && isblank ((unsigned char) e1[-1]))
3333 e1--;
3334
3335 s2 = var2->value;
3336 e2 = s2 + var2->value_length;
3337 while (isblank((unsigned char)*s2))
3338 s2++;
3339 while (e2 > s2 && isblank ((unsigned char) e2[-1]))
3340 e2--;
3341
3342 /* both empty after stripping? */
3343 if (s1 == e1 && s2 == e2)
3344 return variable_buffer_output (o, "", 0); /* eq */
3345
3346 /* optimist. */
3347 if ( e1 - s1 == e2 - s2
3348 && !memcmp(s1, s2, e1 - s1))
3349 return variable_buffer_output (o, "", 0); /* eq */
3350
3351 /* compare up to the first '$' or the end. */
3352 x1 = var1->recursive ? memchr (s1, '$', e1 - s1) : NULL;
3353 x2 = var2->recursive ? memchr (s2, '$', e2 - s2) : NULL;
3354 if (!x1 && !x2)
3355 return comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3356
3357 l1 = x1 ? x1 - s1 : e1 - s1;
3358 l2 = x2 ? x2 - s2 : e2 - s2;
3359 l = l1 <= l2 ? l1 : l2;
3360 if (l && memcmp (s1, s2, l))
3361 return comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3362
3363 /* one or both buffers now require expanding. */
3364 if (!x1)
3365 s1 += l;
3366 else
3367 {
3368 s1 = a1 = allocated_variable_expand ((char *)s1 + l);
3369 if (!l)
3370 while (isblank ((unsigned char) *s1))
3371 s1++;
3372 e1 = strchr (s1, '\0');
3373 while (e1 > s1 && isblank ((unsigned char) e1[-1]))
3374 e1--;
3375 }
3376
3377 if (!x2)
3378 s2 += l;
3379 else
3380 {
3381 s2 = a2 = allocated_variable_expand ((char *)s2 + l);
3382 if (!l)
3383 while (isblank ((unsigned char) *s2))
3384 s2++;
3385 e2 = strchr (s2, '\0');
3386 while (e2 > s2 && isblank ((unsigned char) e2[-1]))
3387 e2--;
3388 }
3389
3390 /* the final compare */
3391 if ( e1 - s1 != e2 - s2
3392 || memcmp (s1, s2, e1 - s1))
3393 o = comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3394 else
3395 o = variable_buffer_output (o, "", 1) - 1; /* eq */ /** @todo check why this was necessary back the... */
3396 if (a1)
3397 free (a1);
3398 if (a2)
3399 free (a2);
3400 return o;
3401}
3402
3403/*
3404 $(comp-cmds-ex cmds1,cmds2,not-equal-return)
3405
3406 Compares the two strings and return the string in the third argument
3407 if not equal. If equal, nothing is returned.
3408
3409 The comparision will be performed command by command, ignoring not
3410 only leading and trailing spaces on each line but also leading one
3411 leading '@', '-', '+' and '%'.
3412*/
3413static char *
3414func_comp_cmds_ex (char *o, char **argv, const char *funcname)
3415{
3416 const char *s1, *e1, *s2, *e2;
3417 size_t l1, l2;
3418
3419 /* the simple cases */
3420 s1 = argv[0];
3421 s2 = argv[1];
3422 if (s1 == s2)
3423 return variable_buffer_output (o, "", 0); /* eq */
3424 l1 = strlen (argv[0]);
3425 l2 = strlen (argv[1]);
3426
3427 if ( l1 == l2
3428 && !memcmp (s1, s2, l1))
3429 return variable_buffer_output (o, "", 0); /* eq */
3430
3431 /* ignore trailing and leading blanks */
3432 e1 = s1 + l1;
3433 s1 = comp_cmds_strip_leading (s1, e1);
3434
3435 e2 = s2 + l2;
3436 s2 = comp_cmds_strip_leading (s2, e2);
3437
3438 if (e1 - s1 != e2 - s2)
3439 return comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3440 if (!memcmp (s1, s2, e1 - s1))
3441 return variable_buffer_output (o, "", 0); /* eq */
3442 return comp_vars_ne (o, s1, e1, s2, e2, argv[2], funcname);
3443}
3444#endif
3445
3446#ifdef CONFIG_WITH_DATE
3447# if defined (_MSC_VER) /* FIXME: !defined (HAVE_STRPTIME) */
3448char *strptime(const char *s, const char *format, struct tm *tm)
3449{
3450 return (char *)"strptime is not implemented";
3451}
3452# endif
3453/* Check if the string is all blanks or not. */
3454static int
3455all_blanks (const char *s)
3456{
3457 if (!s)
3458 return 1;
3459 while (isspace ((unsigned char)*s))
3460 s++;
3461 return *s == '\0';
3462}
3463
3464/* The first argument is the strftime format string, a iso
3465 timestamp is the default if nothing is given.
3466
3467 The second argument is a time value if given. The format
3468 is either the format from the first argument or given as
3469 an additional third argument. */
3470static char *
3471func_date (char *o, char **argv, const char *funcname)
3472{
3473 char *p;
3474 char *buf;
3475 size_t buf_size;
3476 struct tm t;
3477 const char *format;
3478
3479 /* determin the format - use a single word as the default. */
3480 format = !strcmp (funcname, "date-utc")
3481 ? "%Y-%m-%dT%H:%M:%SZ"
3482 : "%Y-%m-%dT%H:%M:%S";
3483 if (!all_blanks (argv[0]))
3484 format = argv[0];
3485
3486 /* get the time. */
3487 memset (&t, 0, sizeof(t));
3488 if (argv[0] && !all_blanks (argv[1]))
3489 {
3490 const char *input_format = !all_blanks (argv[2]) ? argv[2] : format;
3491 p = strptime (argv[1], input_format, &t);
3492 if (!p || *p != '\0')
3493 {
3494 error (NILF, _("$(%s): strptime(%s,%s,) -> %s\n"), funcname,
3495 argv[1], input_format, p ? p : "<null>");
3496 return variable_buffer_output (o, "", 0);
3497 }
3498 }
3499 else
3500 {
3501 time_t tval;
3502 time (&tval);
3503 if (!strcmp (funcname, "date-utc"))
3504 t = *gmtime (&tval);
3505 else
3506 t = *localtime (&tval);
3507 }
3508
3509 /* format it. note that zero isn't necessarily an error, so we'll
3510 have to keep shut about failures. */
3511 buf_size = 64;
3512 buf = xmalloc (buf_size);
3513 while (strftime (buf, buf_size, format, &t) == 0)
3514 {
3515 if (buf_size >= 4096)
3516 {
3517 *buf = '\0';
3518 break;
3519 }
3520 buf = xrealloc (buf, buf_size <<= 1);
3521 }
3522 o = variable_buffer_output (o, buf, strlen (buf));
3523 free (buf);
3524 return o;
3525}
3526#endif
3527
3528#ifdef CONFIG_WITH_FILE_SIZE
3529/* Prints the size of the specified file. Only one file is
3530 permitted, notthing is stripped. -1 is returned if stat
3531 fails. */
3532static char *
3533func_file_size (char *o, char **argv, const char *funcname UNUSED)
3534{
3535 struct stat st;
3536 if (stat (argv[0], &st))
3537 return variable_buffer_output (o, "-1", 2);
3538 return math_int_to_variable_buffer (o, st.st_size);
3539}
3540#endif
3541
3542#ifdef CONFIG_WITH_WHICH
3543/* Checks if the specified file exists an is executable.
3544 On systems employing executable extensions, the name may
3545 be modified to include the extension. */
3546static int func_which_test_x (char *file)
3547{
3548 struct stat st;
3549# if defined(WINDOWS32) || defined(__OS2__)
3550 char *ext;
3551 char *slash;
3552
3553 /* fix slashes first. */
3554 slash = file;
3555 while ((slash = strchr (slash, '\\')) != NULL)
3556 *slash++ = '/';
3557
3558 /* straight */
3559 if (stat (file, &st) == 0
3560 && S_ISREG (st.st_mode))
3561 return 1;
3562
3563 /* don't try add an extension if there already is one */
3564 ext = strchr (file, '\0');
3565 if (ext - file >= 4
3566 && ( !stricmp (ext - 4, ".exe")
3567 || !stricmp (ext - 4, ".cmd")
3568 || !stricmp (ext - 4, ".bat")
3569 || !stricmp (ext - 4, ".com")))
3570 return 0;
3571
3572 /* try the extensions. */
3573 strcpy (ext, ".exe");
3574 if (stat (file, &st) == 0
3575 && S_ISREG (st.st_mode))
3576 return 1;
3577
3578 strcpy (ext, ".cmd");
3579 if (stat (file, &st) == 0
3580 && S_ISREG (st.st_mode))
3581 return 1;
3582
3583 strcpy (ext, ".bat");
3584 if (stat (file, &st) == 0
3585 && S_ISREG (st.st_mode))
3586 return 1;
3587
3588 strcpy (ext, ".com");
3589 if (stat (file, &st) == 0
3590 && S_ISREG (st.st_mode))
3591 return 1;
3592
3593 return 0;
3594
3595# else
3596
3597 return access (file, X_OK) == 0
3598 && stat (file, &st) == 0
3599 && S_ISREG (st.st_mode);
3600# endif
3601}
3602
3603/* Searches for the specified programs in the PATH and print
3604 their full location if found. Prints nothing if not found. */
3605static char *
3606func_which (char *o, char **argv, const char *funcname UNUSED)
3607{
3608 const char *path;
3609 struct variable *path_var;
3610 unsigned i;
3611 int first = 1;
3612 PATH_VAR (buf);
3613
3614 path_var = lookup_variable ("PATH", 4);
3615 if (path_var)
3616 path = path_var->value;
3617 else
3618 path = ".";
3619
3620 /* iterate input */
3621 for (i = 0; argv[i]; i++)
3622 {
3623 unsigned int len;
3624 const char *iterator = argv[i];
3625 char *cur;
3626
3627 while ((cur = find_next_token (&iterator, &len)))
3628 {
3629 /* if there is a separator, don't walk the path. */
3630 if (memchr (cur, '/', len)
3631#ifdef HAVE_DOS_PATHS
3632 || memchr (cur, '\\', len)
3633 || memchr (cur, ':', len)
3634#endif
3635 )
3636 {
3637 if (len + 1 + 4 < GET_PATH_MAX) /* +4 for .exe */
3638 {
3639 memcpy (buf, cur, len);
3640 buf[len] = '\0';
3641 if (func_which_test_x (buf))
3642 o = variable_buffer_output (o, buf, strlen (buf));
3643 }
3644 }
3645 else
3646 {
3647 const char *comp = path;
3648 for (;;)
3649 {
3650 const char *src = comp;
3651 const char *end = strchr (comp, PATH_SEPARATOR_CHAR);
3652 size_t comp_len = end ? (size_t)(end - comp) : strlen (comp);
3653 if (!comp_len)
3654 {
3655 comp_len = 1;
3656 src = ".";
3657 }
3658 if (len + comp_len + 2 + 4 < GET_PATH_MAX) /* +4 for .exe */
3659 {
3660 memcpy (buf, comp, comp_len);
3661 buf [comp_len] = '/';
3662 memcpy (&buf[comp_len + 1], cur, len);
3663 buf[comp_len + 1 + len] = '\0';
3664
3665 if (func_which_test_x (buf))
3666 {
3667 if (!first)
3668 o = variable_buffer_output (o, " ", 1);
3669 o = variable_buffer_output (o, buf, strlen (buf));
3670 first = 0;
3671 break;
3672 }
3673 }
3674
3675 /* next */
3676 if (!end)
3677 break;
3678 comp = end + 1;
3679 }
3680 }
3681 }
3682 }
3683
3684 return variable_buffer_output (o, "", 0);
3685}
3686#endif /* CONFIG_WITH_WHICH */
3687
3688#ifdef CONFIG_WITH_IF_CONDITIONALS
3689
3690/* Evaluates the expression given in the argument using the
3691 same evaluator as for the new 'if' statements, except now
3692 we don't force the result into a boolean like for 'if' and
3693 '$(if-expr ,,)'. */
3694static char *
3695func_expr (char *o, char **argv, const char *funcname UNUSED)
3696{
3697 o = expr_eval_to_string (o, argv[0]);
3698 return o;
3699}
3700
3701/* Same as '$(if ,,)' except the first argument is evaluated
3702 using the same evaluator as for the new 'if' statements. */
3703static char *
3704func_if_expr (char *o, char **argv, const char *funcname UNUSED)
3705{
3706 int rc;
3707 char *to_expand;
3708
3709 /* Evaluate the condition in argv[0] and expand the 2nd or
3710 3rd argument according to the result. */
3711 rc = expr_eval_if_conditionals (argv[0], NULL);
3712 to_expand = rc == 0 ? argv[1] : argv[2];
3713 if (*to_expand)
3714 {
3715 char *expansion = expand_argument (to_expand, NULL);
3716
3717 o = variable_buffer_output (o, expansion, strlen (expansion));
3718
3719 free (expansion);
3720 }
3721
3722 return o;
3723}
3724
3725#endif /* CONFIG_WITH_IF_CONDITIONALS */
3726
3727#ifdef CONFIG_WITH_STACK
3728
3729/* Push an item (string without spaces). */
3730static char *
3731func_stack_push (char *o, char **argv, const char *funcname UNUSED)
3732{
3733 do_variable_definition(NILF, argv[0], argv[1], o_file, f_append, 0 /* !target_var */);
3734 return o;
3735}
3736
3737/* Pops an item off the stack / get the top stack element.
3738 (This is what's tricky to do in pure GNU make syntax.) */
3739static char *
3740func_stack_pop_top (char *o, char **argv, const char *funcname)
3741{
3742 struct variable *stack_var;
3743 const char *stack = argv[0];
3744
3745 stack_var = lookup_variable (stack, strlen (stack) );
3746 if (stack_var)
3747 {
3748 unsigned int len;
3749 const char *iterator = stack_var->value;
3750 char *lastitem = NULL;
3751 char *cur;
3752
3753 while ((cur = find_next_token (&iterator, &len)))
3754 lastitem = cur;
3755
3756 if (lastitem != NULL)
3757 {
3758 if (strcmp (funcname, "stack-popv") != 0)
3759 o = variable_buffer_output (o, lastitem, len);
3760 if (strcmp (funcname, "stack-top") != 0)
3761 {
3762 *lastitem = '\0';
3763 while (lastitem > stack_var->value && isspace (lastitem[-1]))
3764 *--lastitem = '\0';
3765#ifdef CONFIG_WITH_VALUE_LENGTH
3766 stack_var->value_length = lastitem - stack_var->value;
3767#endif
3768 }
3769 }
3770 }
3771 return o;
3772}
3773#endif /* CONFIG_WITH_STACK */
3774
3775#if defined (CONFIG_WITH_MATH) || defined (CONFIG_WITH_NANOTS) || defined (CONFIG_WITH_FILE_SIZE)
3776/* outputs the number (as a string) into the variable buffer. */
3777static char *
3778math_int_to_variable_buffer (char *o, math_int num)
3779{
3780 static const char xdigits[17] = "0123456789abcdef";
3781 int negative;
3782 char strbuf[24]; /* 16 hex + 2 prefix + sign + term => 20
3783 or 20 dec + sign + term => 22 */
3784 char *str = &strbuf[sizeof (strbuf) - 1];
3785
3786 negative = num < 0;
3787 if (negative)
3788 num = -num;
3789
3790 *str = '\0';
3791
3792 do
3793 {
3794#ifdef HEX_MATH_NUMBERS
3795 *--str = xdigits[num & 0xf];
3796 num >>= 4;
3797#else
3798 *--str = xdigits[num % 10];
3799 num /= 10;
3800#endif
3801 }
3802 while (num);
3803
3804#ifdef HEX_MATH_NUMBERS
3805 *--str = 'x';
3806 *--str = '0';
3807#endif
3808
3809 if (negative)
3810 *--str = '-';
3811
3812 return variable_buffer_output (o, str, &strbuf[sizeof (strbuf) - 1] - str);
3813}
3814#endif /* CONFIG_WITH_MATH || CONFIG_WITH_NANOTS */
3815
3816#ifdef CONFIG_WITH_MATH
3817
3818/* Converts a string to an integer, causes an error if the format is invalid. */
3819static math_int
3820math_int_from_string (const char *str)
3821{
3822 const char *start;
3823 unsigned base = 0;
3824 int negative = 0;
3825 math_int num = 0;
3826
3827 /* strip spaces */
3828 while (isspace (*str))
3829 str++;
3830 if (!*str)
3831 {
3832 error (NILF, _("bad number: empty\n"));
3833 return 0;
3834 }
3835 start = str;
3836
3837 /* check for +/- */
3838 while (*str == '+' || *str == '-' || isspace (*str))
3839 if (*str++ == '-')
3840 negative = !negative;
3841
3842 /* check for prefix - we do not accept octal numbers, sorry. */
3843 if (*str == '0' && (str[1] == 'x' || str[1] == 'X'))
3844 {
3845 base = 16;
3846 str += 2;
3847 }
3848 else
3849 {
3850 /* look for a hex digit, if not found treat it as decimal */
3851 const char *p2 = str;
3852 for ( ; *p2; p2++)
3853 if (isxdigit (*p2) && !isdigit (*p2) && isascii (*p2) )
3854 {
3855 base = 16;
3856 break;
3857 }
3858 if (base == 0)
3859 base = 10;
3860 }
3861
3862 /* must have at least one digit! */
3863 if ( !isascii (*str)
3864 || !(base == 16 ? isxdigit (*str) : isdigit (*str)) )
3865 {
3866 error (NILF, _("bad number: '%s'\n"), start);
3867 return 0;
3868 }
3869
3870 /* convert it! */
3871 while (*str && !isspace (*str))
3872 {
3873 int ch = *str++;
3874 if (ch >= '0' && ch <= '9')
3875 ch -= '0';
3876 else if (base == 16 && ch >= 'a' && ch <= 'f')
3877 ch -= 'a' - 10;
3878 else if (base == 16 && ch >= 'A' && ch <= 'F')
3879 ch -= 'A' - 10;
3880 else
3881 {
3882 error (NILF, _("bad number: '%s' (base=%d, pos=%d)\n"), start, base, str - start);
3883 return 0;
3884 }
3885 num *= base;
3886 num += ch;
3887 }
3888
3889 /* check trailing spaces. */
3890 while (isspace (*str))
3891 str++;
3892 if (*str)
3893 {
3894 error (NILF, _("bad number: '%s'\n"), start);
3895 return 0;
3896 }
3897
3898 return negative ? -num : num;
3899}
3900
3901/* Add two or more integer numbers. */
3902static char *
3903func_int_add (char *o, char **argv, const char *funcname UNUSED)
3904{
3905 math_int num;
3906 int i;
3907
3908 num = math_int_from_string (argv[0]);
3909 for (i = 1; argv[i]; i++)
3910 num += math_int_from_string (argv[i]);
3911
3912 return math_int_to_variable_buffer (o, num);
3913}
3914
3915/* Subtract two or more integer numbers. */
3916static char *
3917func_int_sub (char *o, char **argv, const char *funcname UNUSED)
3918{
3919 math_int num;
3920 int i;
3921
3922 num = math_int_from_string (argv[0]);
3923 for (i = 1; argv[i]; i++)
3924 num -= math_int_from_string (argv[i]);
3925
3926 return math_int_to_variable_buffer (o, num);
3927}
3928
3929/* Multiply two or more integer numbers. */
3930static char *
3931func_int_mul (char *o, char **argv, const char *funcname UNUSED)
3932{
3933 math_int num;
3934 int i;
3935
3936 num = math_int_from_string (argv[0]);
3937 for (i = 1; argv[i]; i++)
3938 num *= math_int_from_string (argv[i]);
3939
3940 return math_int_to_variable_buffer (o, num);
3941}
3942
3943/* Divide an integer number by one or more divisors. */
3944static char *
3945func_int_div (char *o, char **argv, const char *funcname UNUSED)
3946{
3947 math_int num;
3948 math_int divisor;
3949 int i;
3950
3951 num = math_int_from_string (argv[0]);
3952 for (i = 1; argv[i]; i++)
3953 {
3954 divisor = math_int_from_string (argv[i]);
3955 if (!divisor)
3956 {
3957 error (NILF, _("divide by zero ('%s')\n"), argv[i]);
3958 return math_int_to_variable_buffer (o, 0);
3959 }
3960 num /= divisor;
3961 }
3962
3963 return math_int_to_variable_buffer (o, num);
3964}
3965
3966
3967/* Divide and return the remainder. */
3968static char *
3969func_int_mod (char *o, char **argv, const char *funcname UNUSED)
3970{
3971 math_int num;
3972 math_int divisor;
3973
3974 num = math_int_from_string (argv[0]);
3975 divisor = math_int_from_string (argv[1]);
3976 if (!divisor)
3977 {
3978 error (NILF, _("divide by zero ('%s')\n"), argv[1]);
3979 return math_int_to_variable_buffer (o, 0);
3980 }
3981 num %= divisor;
3982
3983 return math_int_to_variable_buffer (o, num);
3984}
3985
3986/* 2-complement. */
3987static char *
3988func_int_not (char *o, char **argv, const char *funcname UNUSED)
3989{
3990 math_int num;
3991
3992 num = math_int_from_string (argv[0]);
3993 num = ~num;
3994
3995 return math_int_to_variable_buffer (o, num);
3996}
3997
3998/* Bitwise AND (two or more numbers). */
3999static char *
4000func_int_and (char *o, char **argv, const char *funcname UNUSED)
4001{
4002 math_int num;
4003 int i;
4004
4005 num = math_int_from_string (argv[0]);
4006 for (i = 1; argv[i]; i++)
4007 num &= math_int_from_string (argv[i]);
4008
4009 return math_int_to_variable_buffer (o, num);
4010}
4011
4012/* Bitwise OR (two or more numbers). */
4013static char *
4014func_int_or (char *o, char **argv, const char *funcname UNUSED)
4015{
4016 math_int num;
4017 int i;
4018
4019 num = math_int_from_string (argv[0]);
4020 for (i = 1; argv[i]; i++)
4021 num |= math_int_from_string (argv[i]);
4022
4023 return math_int_to_variable_buffer (o, num);
4024}
4025
4026/* Bitwise XOR (two or more numbers). */
4027static char *
4028func_int_xor (char *o, char **argv, const char *funcname UNUSED)
4029{
4030 math_int num;
4031 int i;
4032
4033 num = math_int_from_string (argv[0]);
4034 for (i = 1; argv[i]; i++)
4035 num ^= math_int_from_string (argv[i]);
4036
4037 return math_int_to_variable_buffer (o, num);
4038}
4039
4040/* Compare two integer numbers. Returns make boolean (true="1"; false=""). */
4041static char *
4042func_int_cmp (char *o, char **argv, const char *funcname)
4043{
4044 math_int num1;
4045 math_int num2;
4046 int rc;
4047
4048 num1 = math_int_from_string (argv[0]);
4049 num2 = math_int_from_string (argv[1]);
4050
4051 funcname += sizeof ("int-") - 1;
4052 if (!strcmp (funcname, "eq"))
4053 rc = num1 == num2;
4054 else if (!strcmp (funcname, "ne"))
4055 rc = num1 != num2;
4056 else if (!strcmp (funcname, "gt"))
4057 rc = num1 > num2;
4058 else if (!strcmp (funcname, "ge"))
4059 rc = num1 >= num2;
4060 else if (!strcmp (funcname, "lt"))
4061 rc = num1 < num2;
4062 else /*if (!strcmp (funcname, "le"))*/
4063 rc = num1 <= num2;
4064
4065 return variable_buffer_output (o, rc ? "1" : "", rc);
4066}
4067
4068#endif /* CONFIG_WITH_MATH */
4069
4070#ifdef CONFIG_WITH_NANOTS
4071/* Returns the current timestamp as nano seconds. The time
4072 source is a high res monotone one if the platform provides
4073 this (and we know about it).
4074
4075 Tip. Use this with int-sub to profile makefile reading
4076 and similar. */
4077static char *
4078func_nanots (char *o, char **argv, const char *funcname)
4079{
4080 math_int ts;
4081
4082#if defined (WINDOWS32)
4083 static int s_state = -1;
4084 static LARGE_INTEGER s_freq;
4085
4086 if (s_state == -1)
4087 s_state = QueryPerformanceFrequency (&s_freq);
4088 if (s_state)
4089 {
4090 LARGE_INTEGER pc;
4091 if (!QueryPerformanceCounter (&pc))
4092 {
4093 s_state = 0;
4094 return func_nanots (o, argv, funcname);
4095 }
4096 ts = (math_int)((long double)pc.QuadPart / (long double)s_freq.QuadPart * 1000000000);
4097 }
4098 else
4099 {
4100 /* fall back to low resolution system time. */
4101 LARGE_INTEGER bigint;
4102 FILETIME ft = {0,0};
4103 GetSystemTimeAsFileTime (&ft);
4104 bigint.u.LowPart = ft.dwLowDateTime;
4105 bigint.u.HighPart = ft.dwLowDateTime;
4106 ts = bigint.QuadPart * 100;
4107 }
4108
4109/* FIXME: Linux and others have the realtime clock_* api, detect and use it. */
4110
4111#elif HAVE_GETTIMEOFDAY
4112 struct timeval tv;
4113 if (!gettimeofday (&tv, NULL))
4114 ts = (math_int)tv.tv_sec * 1000000000
4115 + tv.tv_usec * 1000;
4116 else
4117 {
4118 error (NILF, _("$(nanots): gettimeofday failed"));
4119 ts = 0;
4120 }
4121
4122#else
4123# error "PORTME"
4124#endif
4125
4126 return math_int_to_variable_buffer (o, ts);
4127}
4128#endif
4129
4130#ifdef CONFIG_WITH_OS2_LIBPATH
4131/* Sets or gets the OS/2 libpath variables.
4132
4133 The first argument indicates which variable - BEGINLIBPATH,
4134 ENDLIBPATH, LIBPATHSTRICT or LIBPATH.
4135
4136 The second indicates whether this is a get (not present) or
4137 set (present) operation. When present it is the new value for
4138 the variable. */
4139static char *
4140func_os2_libpath (char *o, char **argv, const char *funcname UNUSED)
4141{
4142 char buf[4096];
4143 ULONG fVar;
4144 APIRET rc;
4145
4146 /* translate variable name (first arg) */
4147 if (!strcmp (argv[0], "BEGINLIBPATH"))
4148 fVar = BEGIN_LIBPATH;
4149 else if (!strcmp (argv[0], "ENDLIBPATH"))
4150 fVar = END_LIBPATH;
4151 else if (!strcmp (argv[0], "LIBPATHSTRICT"))
4152 fVar = LIBPATHSTRICT;
4153 else if (!strcmp (argv[0], "LIBPATH"))
4154 fVar = 0;
4155 else
4156 {
4157 error (NILF, _("$(libpath): unknown variable `%s'"), argv[0]);
4158 return variable_buffer_output (o, "", 0);
4159 }
4160
4161 if (!argv[1])
4162 {
4163 /* get the variable value. */
4164 if (fVar != 0)
4165 {
4166 buf[0] = buf[1] = buf[2] = buf[3] = '\0';
4167 rc = DosQueryExtLIBPATH (buf, fVar);
4168 }
4169 else
4170 rc = DosQueryHeaderInfo (NULLHANDLE, 0, buf, sizeof(buf), QHINF_LIBPATH);
4171 if (rc != NO_ERROR)
4172 {
4173 error (NILF, _("$(libpath): failed to query `%s', rc=%d"), argv[0], rc);
4174 return variable_buffer_output (o, "", 0);
4175 }
4176 o = variable_buffer_output (o, buf, strlen (buf));
4177 }
4178 else
4179 {
4180 /* set the variable value. */
4181 size_t len;
4182 size_t len_max = sizeof (buf) < 2048 ? sizeof (buf) : 2048;
4183 const char *val;
4184 const char *end;
4185
4186 if (fVar == 0)
4187 {
4188 error (NILF, _("$(libpath): LIBPATH is read-only"));
4189 return variable_buffer_output (o, "", 0);
4190 }
4191
4192 /* strip leading and trailing spaces and check for max length. */
4193 val = argv[1];
4194 while (isspace (*val))
4195 val++;
4196 end = strchr (val, '\0');
4197 while (end > val && isspace (end[-1]))
4198 end--;
4199
4200 len = end - val;
4201 if (len >= len_max)
4202 {
4203 error (NILF, _("$(libpath): The new `%s' value is too long (%d bytes, max %d)"),
4204 argv[0], len, len_max);
4205 return variable_buffer_output (o, "", 0);
4206 }
4207
4208 /* make a stripped copy in low memory and try set it. */
4209 memcpy (buf, val, len);
4210 buf[len] = '\0';
4211 rc = DosSetExtLIBPATH (buf, fVar);
4212 if (rc != NO_ERROR)
4213 {
4214 error (NILF, _("$(libpath): failed to set `%s' to `%s', rc=%d"), argv[0], buf, rc);
4215 return variable_buffer_output (o, "", 0);
4216 }
4217
4218 o = variable_buffer_output (o, "", 0);
4219 }
4220 return o;
4221}
4222#endif /* CONFIG_WITH_OS2_LIBPATH */
4223
4224#if defined (CONFIG_WITH_MAKE_STATS) || defined (CONFIG_WITH_MINIMAL_STATS)
4225/* Retrieve make statistics. */
4226static char *
4227func_make_stats (char *o, char **argv, const char *funcname UNUSED)
4228{
4229 char buf[512];
4230 int len;
4231
4232 if (!argv[0] || (!argv[0][0] && !argv[1]))
4233 {
4234# ifdef CONFIG_WITH_MAKE_STATS
4235 len = sprintf (buf, "alloc-cur: %5ld/%3ld %3luMB hash: %5lu %2lu%%",
4236 make_stats_allocations,
4237 make_stats_reallocations,
4238 make_stats_allocated / (1024*1024),
4239 make_stats_ht_lookups,
4240 (make_stats_ht_collisions * 100) / make_stats_ht_lookups);
4241 o = variable_buffer_output (o, buf, len);
4242#endif
4243 }
4244 else
4245 {
4246 /* selective */
4247 int i;
4248 for (i = 0; argv[i]; i++)
4249 {
4250 unsigned long val;
4251 if (i != 0)
4252 o = variable_buffer_output (o, " ", 1);
4253 if (0)
4254 continue;
4255# ifdef CONFIG_WITH_MAKE_STATS
4256 else if (!strcmp(argv[i], "allocations"))
4257 val = make_stats_allocations;
4258 else if (!strcmp(argv[i], "reallocations"))
4259 val = make_stats_reallocations;
4260 else if (!strcmp(argv[i], "allocated"))
4261 val = make_stats_allocated;
4262 else if (!strcmp(argv[i], "ht_lookups"))
4263 val = make_stats_ht_lookups;
4264 else if (!strcmp(argv[i], "ht_collisions"))
4265 val = make_stats_ht_collisions;
4266 else if (!strcmp(argv[i], "ht_collisions_pct"))
4267 val = (make_stats_ht_collisions * 100) / make_stats_ht_lookups;
4268#endif
4269 else
4270 {
4271 o = variable_buffer_output (o, argv[i], strlen (argv[i]));
4272 continue;
4273 }
4274
4275 len = sprintf (buf, "%ld", val);
4276 o = variable_buffer_output (o, buf, len);
4277 }
4278 }
4279
4280 return o;
4281}
4282#endif /* CONFIG_WITH_MAKE_STATS */
4283
4284#ifdef CONFIG_WITH_COMMANDS_FUNC
4285/* Gets all the commands for a target, separated by newlines.
4286
4287 This is useful when creating and checking target dependencies since
4288 it reduces the amount of work and the memory consuption. A new prefix
4289 character '%' has been introduced for skipping certain lines, like
4290 for instance the one calling this function and pushing to a dep file.
4291 Blank lines are also skipped.
4292
4293 The commands function takes exactly one argument, which is the name of
4294 the target which commands should be returned.
4295
4296 The commands-sc is identical to commands except that it uses a ';' to
4297 separate the commands.
4298
4299 The commands-usr is similar to commands except that it takes a 2nd
4300 argument that is used to separate the commands. */
4301char *
4302func_commands (char *o, char **argv, const char *funcname)
4303{
4304 struct file *file;
4305 static int recursive = 0;
4306
4307 if (recursive)
4308 {
4309 error (reading_file, _("$(%s ) was invoked recursivly"), funcname);
4310 return variable_buffer_output (o, "recursive", sizeof ("recursive") - 1);
4311 }
4312 if (*argv[0] == '\0')
4313 {
4314 error (reading_file, _("$(%s ) was invoked with an empty target name"), funcname);
4315 return o;
4316 }
4317 recursive = 1;
4318
4319 file = lookup_file (argv[0]);
4320 if (file && file->cmds)
4321 {
4322 unsigned int i;
4323 int cmd_sep_len;
4324 struct commands *cmds = file->cmds;
4325 const char *cmd_sep;
4326
4327 if (!strcmp (funcname, "commands"))
4328 {
4329 cmd_sep = "\n";
4330 cmd_sep_len = 1;
4331 }
4332 else if (!strcmp (funcname, "commands-sc"))
4333 {
4334 cmd_sep = ";";
4335 cmd_sep_len = 1;
4336 }
4337 else /*if (!strcmp (funcname, "commands-usr"))*/
4338 {
4339 cmd_sep = argv[1];
4340 cmd_sep_len = strlen (cmd_sep);
4341 }
4342
4343 initialize_file_variables (file, 1 /* reading - FIXME: we don't know? */);
4344 set_file_variables (file); /* FIXME: this must *NOT* be done twice! */
4345 chop_commands (cmds);
4346
4347 for (i = 0; i < cmds->ncommand_lines; i++)
4348 {
4349 char *p;
4350 char *in, *out, *ref;
4351
4352 /* Skip it if it has a '%' prefix or is blank. */
4353 if (cmds->lines_flags[i] & COMMAND_GETTER_SKIP_IT)
4354 continue;
4355 p = cmds->command_lines[i];
4356 while (isblank ((unsigned char)*p))
4357 p++;
4358 if (*p == '\0')
4359 continue;
4360
4361 /* --- copied from new_job() in job.c --- */
4362
4363 /* Collapse backslash-newline combinations that are inside variable
4364 or function references. These are left alone by the parser so
4365 that they will appear in the echoing of commands (where they look
4366 nice); and collapsed by construct_command_argv when it tokenizes.
4367 But letting them survive inside function invocations loses because
4368 we don't want the functions to see them as part of the text. */
4369
4370 /* IN points to where in the line we are scanning.
4371 OUT points to where in the line we are writing.
4372 When we collapse a backslash-newline combination,
4373 IN gets ahead of OUT. */
4374
4375 in = out = p;
4376 while ((ref = strchr (in, '$')) != 0)
4377 {
4378 ++ref; /* Move past the $. */
4379
4380 if (out != in)
4381 /* Copy the text between the end of the last chunk
4382 we processed (where IN points) and the new chunk
4383 we are about to process (where REF points). */
4384 memmove (out, in, ref - in);
4385
4386 /* Move both pointers past the boring stuff. */
4387 out += ref - in;
4388 in = ref;
4389
4390 if (*ref == '(' || *ref == '{')
4391 {
4392 char openparen = *ref;
4393 char closeparen = openparen == '(' ? ')' : '}';
4394 int count;
4395 char *p;
4396
4397 *out++ = *in++; /* Copy OPENPAREN. */
4398 /* IN now points past the opening paren or brace.
4399 Count parens or braces until it is matched. */
4400 count = 0;
4401 while (*in != '\0')
4402 {
4403 if (*in == closeparen && --count < 0)
4404 break;
4405 else if (*in == '\\' && in[1] == '\n')
4406 {
4407 /* We have found a backslash-newline inside a
4408 variable or function reference. Eat it and
4409 any following whitespace. */
4410
4411 int quoted = 0;
4412 for (p = in - 1; p > ref && *p == '\\'; --p)
4413 quoted = !quoted;
4414
4415 if (quoted)
4416 /* There were two or more backslashes, so this is
4417 not really a continuation line. We don't collapse
4418 the quoting backslashes here as is done in
4419 collapse_continuations, because the line will
4420 be collapsed again after expansion. */
4421 *out++ = *in++;
4422 else
4423 {
4424 /* Skip the backslash, newline and
4425 any following whitespace. */
4426 in = next_token (in + 2);
4427
4428 /* Discard any preceding whitespace that has
4429 already been written to the output. */
4430 while (out > ref
4431 && isblank ((unsigned char)out[-1]))
4432 --out;
4433
4434 /* Replace it all with a single space. */
4435 *out++ = ' ';
4436 }
4437 }
4438 else
4439 {
4440 if (*in == openparen)
4441 ++count;
4442
4443 *out++ = *in++;
4444 }
4445 }
4446 }
4447 /* Some of these can be amended ($< perhaps), but we're likely to be called while the
4448 dep expansion happens, so it would have to be on a hackish basis. sad... */
4449 else if (*ref == '<' || *ref == '*' || *ref == '%' || *ref == '^' || *ref == '+')
4450 error (reading_file, _("$(%s ) does not work reliably with $%c in all cases"), funcname, *ref);
4451 }
4452
4453 /* There are no more references in this line to worry about.
4454 Copy the remaining uninteresting text to the output. */
4455 if (out != in)
4456 strcpy (out, in);
4457
4458 /* --- copied from new_job() in job.c --- */
4459
4460 /* Finally, expand the line. */
4461 if (i)
4462 o = variable_buffer_output (o, cmd_sep, cmd_sep_len);
4463 o = variable_expand_for_file_2 (o, cmds->command_lines[i], ~0U, file, NULL);
4464
4465 /* Skip it if it has a '%' prefix or is blank. */
4466 p = o;
4467 while (isblank ((unsigned char)*o)
4468 || *o == '@'
4469 || *o == '-'
4470 || *o == '+')
4471 o++;
4472 if (*o != '\0' && *o != '%')
4473 o = strchr (o, '\0');
4474 else if (i)
4475 o = p - cmd_sep_len;
4476 else
4477 o = p;
4478 } /* for each command line */
4479 }
4480 /* else FIXME: bitch about it? */
4481
4482 recursive = 0;
4483 return o;
4484}
4485#endif /* CONFIG_WITH_COMMANDS_FUNC */
4486
4487#ifdef KMK
4488/* Useful when debugging kmk and/or makefiles. */
4489char *
4490func_breakpoint (char *o, char **argv, const char *funcname)
4491{
4492#ifdef _MSC_VER
4493 __debugbreak();
4494#elif defined(__i386__) || defined(__x86__) || defined(__X86__) || defined(_M_IX86) || defined(__i386) \
4495 || defined(__amd64__) || defined(__x86_64__) || defined(__AMD64__) || defined(_M_X64) || defined(__amd64)
4496 __asm__ __volatile__ ("int3\n\t");
4497#else
4498 char *p = (char *)0;
4499 *p = '\0';
4500#endif
4501 return o;
4502}
4503#endif /* KMK */
4504
4505
4506/* Lookup table for builtin functions.
4507
4508 This doesn't have to be sorted; we use a straight lookup. We might gain
4509 some efficiency by moving most often used functions to the start of the
4510 table.
4511
4512 If MAXIMUM_ARGS is 0, that means there is no maximum and all
4513 comma-separated values are treated as arguments.
4514
4515 EXPAND_ARGS means that all arguments should be expanded before invocation.
4516 Functions that do namespace tricks (foreach) don't automatically expand. */
4517
4518static char *func_call (char *o, char **argv, const char *funcname);
4519
4520
4521static struct function_table_entry function_table_init[] =
4522{
4523 /* Name/size */ /* MIN MAX EXP? Function */
4524 { STRING_SIZE_TUPLE("abspath"), 0, 1, 1, func_abspath},
4525 { STRING_SIZE_TUPLE("addprefix"), 2, 2, 1, func_addsuffix_addprefix},
4526 { STRING_SIZE_TUPLE("addsuffix"), 2, 2, 1, func_addsuffix_addprefix},
4527 { STRING_SIZE_TUPLE("basename"), 0, 1, 1, func_basename_dir},
4528 { STRING_SIZE_TUPLE("dir"), 0, 1, 1, func_basename_dir},
4529 { STRING_SIZE_TUPLE("notdir"), 0, 1, 1, func_notdir_suffix},
4530 { STRING_SIZE_TUPLE("subst"), 3, 3, 1, func_subst},
4531 { STRING_SIZE_TUPLE("suffix"), 0, 1, 1, func_notdir_suffix},
4532 { STRING_SIZE_TUPLE("filter"), 2, 2, 1, func_filter_filterout},
4533 { STRING_SIZE_TUPLE("filter-out"), 2, 2, 1, func_filter_filterout},
4534 { STRING_SIZE_TUPLE("findstring"), 2, 2, 1, func_findstring},
4535 { STRING_SIZE_TUPLE("firstword"), 0, 1, 1, func_firstword},
4536 { STRING_SIZE_TUPLE("flavor"), 0, 1, 1, func_flavor},
4537 { STRING_SIZE_TUPLE("join"), 2, 2, 1, func_join},
4538 { STRING_SIZE_TUPLE("lastword"), 0, 1, 1, func_lastword},
4539 { STRING_SIZE_TUPLE("patsubst"), 3, 3, 1, func_patsubst},
4540 { STRING_SIZE_TUPLE("realpath"), 0, 1, 1, func_realpath},
4541#ifdef CONFIG_WITH_RSORT
4542 { STRING_SIZE_TUPLE("rsort"), 0, 1, 1, func_sort},
4543#endif
4544 { STRING_SIZE_TUPLE("shell"), 0, 1, 1, func_shell},
4545 { STRING_SIZE_TUPLE("sort"), 0, 1, 1, func_sort},
4546 { STRING_SIZE_TUPLE("strip"), 0, 1, 1, func_strip},
4547 { STRING_SIZE_TUPLE("wildcard"), 0, 1, 1, func_wildcard},
4548 { STRING_SIZE_TUPLE("word"), 2, 2, 1, func_word},
4549 { STRING_SIZE_TUPLE("wordlist"), 3, 3, 1, func_wordlist},
4550 { STRING_SIZE_TUPLE("words"), 0, 1, 1, func_words},
4551 { STRING_SIZE_TUPLE("origin"), 0, 1, 1, func_origin},
4552 { STRING_SIZE_TUPLE("foreach"), 3, 3, 0, func_foreach},
4553 { STRING_SIZE_TUPLE("call"), 1, 0, 1, func_call},
4554 { STRING_SIZE_TUPLE("info"), 0, 1, 1, func_error},
4555 { STRING_SIZE_TUPLE("error"), 0, 1, 1, func_error},
4556 { STRING_SIZE_TUPLE("warning"), 0, 1, 1, func_error},
4557 { STRING_SIZE_TUPLE("if"), 2, 3, 0, func_if},
4558 { STRING_SIZE_TUPLE("or"), 1, 0, 0, func_or},
4559 { STRING_SIZE_TUPLE("and"), 1, 0, 0, func_and},
4560 { STRING_SIZE_TUPLE("value"), 0, 1, 1, func_value},
4561 { STRING_SIZE_TUPLE("eval"), 0, 1, 1, func_eval},
4562#ifdef CONFIG_WITH_EVALPLUS
4563 { STRING_SIZE_TUPLE("evalctx"), 0, 1, 1, func_evalctx},
4564 { STRING_SIZE_TUPLE("evalval"), 1, 1, 1, func_evalval},
4565 { STRING_SIZE_TUPLE("evalvalctx"), 1, 1, 1, func_evalval},
4566 { STRING_SIZE_TUPLE("evalcall"), 1, 0, 1, func_call},
4567 { STRING_SIZE_TUPLE("evalcall2"), 1, 0, 1, func_call},
4568 { STRING_SIZE_TUPLE("eval-opt-var"), 1, 0, 1, func_eval_optimize_variable},
4569#endif
4570#ifdef EXPERIMENTAL
4571 { STRING_SIZE_TUPLE("eq"), 2, 2, 1, func_eq},
4572 { STRING_SIZE_TUPLE("not"), 0, 1, 1, func_not},
4573#endif
4574#ifdef CONFIG_WITH_LAZY_DEPS_VARS
4575 { STRING_SIZE_TUPLE("deps"), 1, 2, 1, func_deps},
4576 { STRING_SIZE_TUPLE("deps-all"), 1, 2, 1, func_deps},
4577 { STRING_SIZE_TUPLE("deps-newer"), 1, 2, 1, func_deps_newer},
4578 { STRING_SIZE_TUPLE("deps-oo"), 1, 2, 1, func_deps_order_only},
4579#endif
4580#ifdef CONFIG_WITH_DEFINED
4581 { STRING_SIZE_TUPLE("defined"), 1, 1, 1, func_defined},
4582#endif
4583#ifdef CONFIG_WITH_TOUPPER_TOLOWER
4584 { STRING_SIZE_TUPLE("toupper"), 0, 1, 1, func_toupper_tolower},
4585 { STRING_SIZE_TUPLE("tolower"), 0, 1, 1, func_toupper_tolower},
4586#endif
4587#ifdef CONFIG_WITH_ABSPATHEX
4588 { STRING_SIZE_TUPLE("abspathex"), 0, 2, 1, func_abspathex},
4589#endif
4590#ifdef CONFIG_WITH_XARGS
4591 { STRING_SIZE_TUPLE("xargs"), 2, 0, 1, func_xargs},
4592#endif
4593#if defined(CONFIG_WITH_VALUE_LENGTH) && defined(CONFIG_WITH_COMPARE)
4594 { STRING_SIZE_TUPLE("comp-vars"), 3, 3, 1, func_comp_vars},
4595 { STRING_SIZE_TUPLE("comp-cmds"), 3, 3, 1, func_comp_vars},
4596 { STRING_SIZE_TUPLE("comp-cmds-ex"), 3, 3, 1, func_comp_cmds_ex},
4597#endif
4598#ifdef CONFIG_WITH_DATE
4599 { STRING_SIZE_TUPLE("date"), 0, 1, 1, func_date},
4600 { STRING_SIZE_TUPLE("date-utc"), 0, 3, 1, func_date},
4601#endif
4602#ifdef CONFIG_WITH_FILE_SIZE
4603 { STRING_SIZE_TUPLE("file-size"), 1, 1, 1, func_file_size},
4604#endif
4605#ifdef CONFIG_WITH_WHICH
4606 { STRING_SIZE_TUPLE("which"), 0, 0, 1, func_which},
4607#endif
4608#ifdef CONFIG_WITH_IF_CONDITIONALS
4609 { STRING_SIZE_TUPLE("expr"), 1, 1, 0, func_expr},
4610 { STRING_SIZE_TUPLE("if-expr"), 2, 3, 0, func_if_expr},
4611#endif
4612#ifdef CONFIG_WITH_STACK
4613 { STRING_SIZE_TUPLE("stack-push"), 2, 2, 1, func_stack_push},
4614 { STRING_SIZE_TUPLE("stack-pop"), 1, 1, 1, func_stack_pop_top},
4615 { STRING_SIZE_TUPLE("stack-popv"), 1, 1, 1, func_stack_pop_top},
4616 { STRING_SIZE_TUPLE("stack-top"), 1, 1, 1, func_stack_pop_top},
4617#endif
4618#ifdef CONFIG_WITH_MATH
4619 { STRING_SIZE_TUPLE("int-add"), 2, 0, 1, func_int_add},
4620 { STRING_SIZE_TUPLE("int-sub"), 2, 0, 1, func_int_sub},
4621 { STRING_SIZE_TUPLE("int-mul"), 2, 0, 1, func_int_mul},
4622 { STRING_SIZE_TUPLE("int-div"), 2, 0, 1, func_int_div},
4623 { STRING_SIZE_TUPLE("int-mod"), 2, 2, 1, func_int_mod},
4624 { STRING_SIZE_TUPLE("int-not"), 1, 1, 1, func_int_not},
4625 { STRING_SIZE_TUPLE("int-and"), 2, 0, 1, func_int_and},
4626 { STRING_SIZE_TUPLE("int-or"), 2, 0, 1, func_int_or},
4627 { STRING_SIZE_TUPLE("int-xor"), 2, 0, 1, func_int_xor},
4628 { STRING_SIZE_TUPLE("int-eq"), 2, 2, 1, func_int_cmp},
4629 { STRING_SIZE_TUPLE("int-ne"), 2, 2, 1, func_int_cmp},
4630 { STRING_SIZE_TUPLE("int-gt"), 2, 2, 1, func_int_cmp},
4631 { STRING_SIZE_TUPLE("int-ge"), 2, 2, 1, func_int_cmp},
4632 { STRING_SIZE_TUPLE("int-lt"), 2, 2, 1, func_int_cmp},
4633 { STRING_SIZE_TUPLE("int-le"), 2, 2, 1, func_int_cmp},
4634#endif
4635#ifdef CONFIG_WITH_NANOTS
4636 { STRING_SIZE_TUPLE("nanots"), 0, 0, 0, func_nanots},
4637#endif
4638#ifdef CONFIG_WITH_OS2_LIBPATH
4639 { STRING_SIZE_TUPLE("libpath"), 1, 2, 1, func_os2_libpath},
4640#endif
4641#if defined (CONFIG_WITH_MAKE_STATS) || defined (CONFIG_WITH_MINIMAL_STATS)
4642 { STRING_SIZE_TUPLE("make-stats"), 0, 0, 0, func_make_stats},
4643#endif
4644#ifdef CONFIG_WITH_COMMANDS_FUNC
4645 { STRING_SIZE_TUPLE("commands"), 1, 1, 1, func_commands},
4646 { STRING_SIZE_TUPLE("commands-sc"), 1, 1, 1, func_commands},
4647 { STRING_SIZE_TUPLE("commands-usr"), 2, 2, 1, func_commands},
4648#endif
4649#ifdef KMK_HELPERS
4650 { STRING_SIZE_TUPLE("kb-src-tool"), 1, 1, 0, func_kbuild_source_tool},
4651 { STRING_SIZE_TUPLE("kb-obj-base"), 1, 1, 0, func_kbuild_object_base},
4652 { STRING_SIZE_TUPLE("kb-obj-suff"), 1, 1, 0, func_kbuild_object_suffix},
4653 { STRING_SIZE_TUPLE("kb-src-prop"), 3, 4, 0, func_kbuild_source_prop},
4654 { STRING_SIZE_TUPLE("kb-src-one"), 0, 1, 0, func_kbuild_source_one},
4655#endif
4656#ifdef KMK
4657 { STRING_SIZE_TUPLE("breakpoint"), 0, 0, 0, func_breakpoint},
4658#endif
4659};
4660
4661#define FUNCTION_TABLE_ENTRIES (sizeof (function_table_init) / sizeof (struct function_table_entry))
4662
4663
4664
4665/* These must come after the definition of function_table. */
4666
4667static char *
4668expand_builtin_function (char *o, int argc, char **argv,
4669 const struct function_table_entry *entry_p)
4670{
4671 if (argc < (int)entry_p->minimum_args)
4672 fatal (*expanding_var,
4673 _("insufficient number of arguments (%d) to function `%s'"),
4674 argc, entry_p->name);
4675
4676 /* I suppose technically some function could do something with no
4677 arguments, but so far none do, so just test it for all functions here
4678 rather than in each one. We can change it later if necessary. */
4679
4680 if (!argc)
4681 return o;
4682
4683 if (!entry_p->func_ptr)
4684 fatal (*expanding_var,
4685 _("unimplemented on this platform: function `%s'"), entry_p->name);
4686
4687 return entry_p->func_ptr (o, argv, entry_p->name);
4688}
4689
4690/* Check for a function invocation in *STRINGP. *STRINGP points at the
4691 opening ( or { and is not null-terminated. If a function invocation
4692 is found, expand it into the buffer at *OP, updating *OP, incrementing
4693 *STRINGP past the reference and returning nonzero. If not, return zero. */
4694
4695static int
4696handle_function2 (const struct function_table_entry *entry_p, char **op, const char **stringp) /* bird split it up. */
4697{
4698 char openparen = (*stringp)[0];
4699 char closeparen = openparen == '(' ? ')' : '}';
4700 const char *beg;
4701 const char *end;
4702 int count = 0;
4703 char *abeg = NULL;
4704 char **argv, **argvp;
4705 int nargs;
4706
4707 beg = *stringp + 1;
4708
4709 /* We found a builtin function. Find the beginning of its arguments (skip
4710 whitespace after the name). */
4711
4712 beg = next_token (beg + entry_p->len);
4713
4714 /* Find the end of the function invocation, counting nested use of
4715 whichever kind of parens we use. Since we're looking, count commas
4716 to get a rough estimate of how many arguments we might have. The
4717 count might be high, but it'll never be low. */
4718
4719 for (nargs=1, end=beg; *end != '\0'; ++end)
4720 if (*end == ',')
4721 ++nargs;
4722 else if (*end == openparen)
4723 ++count;
4724 else if (*end == closeparen && --count < 0)
4725 break;
4726
4727 if (count >= 0)
4728 fatal (*expanding_var,
4729 _("unterminated call to function `%s': missing `%c'"),
4730 entry_p->name, closeparen);
4731
4732 *stringp = end;
4733
4734 /* Get some memory to store the arg pointers. */
4735 argvp = argv = alloca (sizeof (char *) * (nargs + 2));
4736
4737 /* Chop the string into arguments, then a nul. As soon as we hit
4738 MAXIMUM_ARGS (if it's >0) assume the rest of the string is part of the
4739 last argument.
4740
4741 If we're expanding, store pointers to the expansion of each one. If
4742 not, make a duplicate of the string and point into that, nul-terminating
4743 each argument. */
4744
4745 if (entry_p->expand_args)
4746 {
4747 const char *p;
4748 for (p=beg, nargs=0; p <= end; ++argvp)
4749 {
4750 const char *next;
4751
4752 ++nargs;
4753
4754 if (nargs == entry_p->maximum_args
4755 || (! (next = find_next_argument (openparen, closeparen, p, end))))
4756 next = end;
4757
4758 *argvp = expand_argument (p, next);
4759 p = next + 1;
4760 }
4761 }
4762 else
4763 {
4764 int len = end - beg;
4765 char *p, *aend;
4766
4767 abeg = xmalloc (len+1);
4768 memcpy (abeg, beg, len);
4769 abeg[len] = '\0';
4770 aend = abeg + len;
4771
4772 for (p=abeg, nargs=0; p <= aend; ++argvp)
4773 {
4774 char *next;
4775
4776 ++nargs;
4777
4778 if (nargs == entry_p->maximum_args
4779 || (! (next = find_next_argument (openparen, closeparen, p, aend))))
4780 next = aend;
4781
4782 *argvp = p;
4783 *next = '\0';
4784 p = next + 1;
4785 }
4786 }
4787 *argvp = NULL;
4788
4789 /* Finally! Run the function... */
4790 *op = expand_builtin_function (*op, nargs, argv, entry_p);
4791
4792 /* Free memory. */
4793 if (entry_p->expand_args)
4794 for (argvp=argv; *argvp != 0; ++argvp)
4795 free (*argvp);
4796 if (abeg)
4797 free (abeg);
4798
4799 return 1;
4800}
4801
4802
4803int /* bird split it up and hacked it. */
4804#ifndef CONFIG_WITH_VALUE_LENGTH
4805handle_function (char **op, const char **stringp)
4806{
4807 const struct function_table_entry *entry_p = lookup_function (*stringp + 1);
4808 if (!entry_p)
4809 return 0;
4810 return handle_function2 (entry_p, op, stringp);
4811}
4812#else /* CONFIG_WITH_VALUE_LENGTH */
4813handle_function (char **op, const char **stringp, const char *nameend, const char *eol)
4814{
4815 const char *fname = *stringp + 1;
4816 const struct function_table_entry *entry_p =
4817 lookup_function_in_hash_tab (fname, nameend - fname);
4818 if (!entry_p)
4819 return 0;
4820 return handle_function2 (entry_p, op, stringp);
4821}
4822#endif /* CONFIG_WITH_VALUE_LENGTH */
4823
4824
4825
4826/* User-defined functions. Expand the first argument as either a builtin
4827 function or a make variable, in the context of the rest of the arguments
4828 assigned to $1, $2, ... $N. $0 is the name of the function. */
4829
4830static char *
4831func_call (char *o, char **argv, const char *funcname UNUSED)
4832{
4833 static int max_args = 0;
4834 char *fname;
4835 char *cp;
4836 char *body;
4837 int flen;
4838 int i;
4839 int saved_args;
4840 const struct function_table_entry *entry_p;
4841 struct variable *v;
4842#ifdef CONFIG_WITH_EVALPLUS
4843 char *buf;
4844 unsigned int len;
4845#endif
4846
4847 /* There is no way to define a variable with a space in the name, so strip
4848 leading and trailing whitespace as a favor to the user. */
4849 fname = argv[0];
4850 while (*fname != '\0' && isspace ((unsigned char)*fname))
4851 ++fname;
4852
4853 cp = fname + strlen (fname) - 1;
4854 while (cp > fname && isspace ((unsigned char)*cp))
4855 --cp;
4856 cp[1] = '\0';
4857
4858 /* Calling nothing is a no-op */
4859 if (*fname == '\0')
4860 return o;
4861
4862 /* Are we invoking a builtin function? */
4863
4864#ifndef CONFIG_WITH_VALUE_LENGTH
4865 entry_p = lookup_function (fname);
4866#else
4867 entry_p = lookup_function (fname, cp - fname + 1);
4868#endif
4869 if (entry_p)
4870 {
4871 /* How many arguments do we have? */
4872 for (i=0; argv[i+1]; ++i)
4873 ;
4874 return expand_builtin_function (o, i, argv+1, entry_p);
4875 }
4876
4877 /* Not a builtin, so the first argument is the name of a variable to be
4878 expanded and interpreted as a function. Find it. */
4879 flen = strlen (fname);
4880
4881 v = lookup_variable (fname, flen);
4882
4883 if (v == 0)
4884 warn_undefined (fname, flen);
4885
4886 if (v == 0 || *v->value == '\0')
4887 return o;
4888
4889 body = alloca (flen + 4);
4890 body[0] = '$';
4891 body[1] = '(';
4892 memcpy (body + 2, fname, flen);
4893 body[flen+2] = ')';
4894 body[flen+3] = '\0';
4895
4896 /* Set up arguments $(1) .. $(N). $(0) is the function name. */
4897
4898 push_new_variable_scope ();
4899
4900 for (i=0; *argv; ++i, ++argv)
4901 {
4902 char num[11];
4903
4904 sprintf (num, "%d", i);
4905 define_variable (num, strlen (num), *argv, o_automatic, 0);
4906 }
4907
4908 /* If the number of arguments we have is < max_args, it means we're inside
4909 a recursive invocation of $(call ...). Fill in the remaining arguments
4910 in the new scope with the empty value, to hide them from this
4911 invocation. */
4912
4913 for (; i < max_args; ++i)
4914 {
4915 char num[11];
4916
4917#ifndef CONFIG_WITH_VALUE_LENGTH
4918 sprintf (num, "%d", i);
4919 define_variable (num, strlen (num), "", o_automatic, 0);
4920#else
4921 define_variable (num, sprintf (num, "%d", i), "", o_automatic, 0);
4922#endif
4923 }
4924
4925 saved_args = max_args;
4926 max_args = i;
4927
4928#ifdef CONFIG_WITH_EVALPLUS
4929 if (!strcmp (funcname, "call"))
4930 {
4931#endif
4932 /* Expand the body in the context of the arguments, adding the result to
4933 the variable buffer. */
4934
4935 v->exp_count = EXP_COUNT_MAX;
4936#ifndef CONFIG_WITH_VALUE_LENGTH
4937 o = variable_expand_string (o, body, flen+3);
4938 v->exp_count = 0;
4939
4940 o += strlen (o);
4941#else /* CONFIG_WITH_VALUE_LENGTH */
4942 variable_expand_string_2 (o, body, flen+3, &o);
4943 v->exp_count = 0;
4944#endif /* CONFIG_WITH_VALUE_LENGTH */
4945#ifdef CONFIG_WITH_EVALPLUS
4946 }
4947 else
4948 {
4949 const struct floc *reading_file_saved = reading_file;
4950 char *eos;
4951
4952 if (!strcmp (funcname, "evalcall"))
4953 {
4954 /* Evaluate the variable value without expanding it. We
4955 need a copy since eval_buffer is destructive. */
4956
4957 size_t off = o - variable_buffer;
4958 eos = variable_buffer_output (o, v->value, v->value_length + 1) - 1;
4959 o = variable_buffer + off;
4960 if (v->fileinfo.filenm)
4961 reading_file = &v->fileinfo;
4962 }
4963 else
4964 {
4965 /* Expand the body first and then evaluate the output. */
4966
4967 v->exp_count = EXP_COUNT_MAX;
4968 o = variable_expand_string_2 (o, body, flen+3, &eos);
4969 v->exp_count = 0;
4970 }
4971
4972 install_variable_buffer (&buf, &len);
4973 eval_buffer (o, eos);
4974 restore_variable_buffer (buf, len);
4975 reading_file = reading_file_saved;
4976 }
4977#endif /* CONFIG_WITH_EVALPLUS */
4978
4979 max_args = saved_args;
4980
4981 pop_variable_scope ();
4982
4983 return o;
4984}
4985
4986void
4987hash_init_function_table (void)
4988{
4989 hash_init (&function_table, FUNCTION_TABLE_ENTRIES * 2,
4990 function_table_entry_hash_1, function_table_entry_hash_2,
4991 function_table_entry_hash_cmp);
4992 hash_load (&function_table, function_table_init,
4993 FUNCTION_TABLE_ENTRIES, sizeof (struct function_table_entry));
4994#if defined (CONFIG_WITH_OPTIMIZATION_HACKS) || defined (CONFIG_WITH_VALUE_LENGTH)
4995 {
4996 unsigned int i;
4997 for (i = 0; i < FUNCTION_TABLE_ENTRIES; i++)
4998 {
4999 const char *fn = function_table_init[i].name;
5000 while (*fn)
5001 {
5002 func_char_map[(int)*fn] = 1;
5003 fn++;
5004 }
5005 assert (function_table_init[i].len <= MAX_FUNCTION_LENGTH);
5006 assert (function_table_init[i].len >= MIN_FUNCTION_LENGTH);
5007 }
5008 }
5009#endif
5010}
Note: See TracBrowser for help on using the repository browser.