Ignore:
Timestamp:
Mar 14, 2018, 10:28:10 PM (7 years ago)
Author:
bird
Message:

kmk: Merged in changes from GNU make 4.2.1 (2e55f5e4abdc0e38c1d64be703b446695e70b3b6 / https://git.savannah.gnu.org/git/make.git).

Location:
trunk/src/kmk
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/kmk

  • trunk/src/kmk/function.c

    r2912 r3140  
    11/* Builtin function expansion for GNU Make.
    2 Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997,
    3 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009,
    4 2010 Free Software Foundation, Inc.
     2Copyright (C) 1988-2016 Free Software Foundation, Inc.
    53This file is part of GNU Make.
    64
     
    1715this program.  If not, see <http://www.gnu.org/licenses/>.  */
    1816
    19 #include "make.h"
     17#include "makeint.h"
    2018#include "filedef.h"
    2119#include "variable.h"
     
    9492struct function_table_entry
    9593  {
     94    union {
     95      char *(*func_ptr) (char *output, char **argv, const char *fname);
     96      gmk_func_ptr alloc_func_ptr;
     97    } fptr;
    9698    const char *name;
    9799    unsigned char len;
    98100    unsigned char minimum_args;
    99101    unsigned char maximum_args;
    100     char expand_args;
    101     char *(*func_ptr) (char *output, char **argv, const char *fname);
     102    unsigned char expand_args:1;
     103    unsigned char alloc_fn:1;
    102104  };
    103105
     
    157159      o = variable_buffer_output (o, t, strlen (t));
    158160      if (rlen > 0)
    159         o = variable_buffer_output (o, replace, rlen);
     161        o = variable_buffer_output (o, replace, rlen);
    160162      return o;
    161163    }
     
    164166    {
    165167      if (by_word && slen == 0)
    166         /* When matching by words, the empty string should match
    167            the end of each word, rather than the end of the whole text.  */
    168         p = end_of_token (next_token (t));
     168        /* When matching by words, the empty string should match
     169           the end of each word, rather than the end of the whole text.  */
     170        p = end_of_token (next_token (t));
    169171      else
    170         {
    171           p = strstr (t, subst);
    172           if (p == 0)
    173             {
    174               /* No more matches.  Output everything left on the end.  */
    175               o = variable_buffer_output (o, t, strlen (t));
    176               return o;
    177             }
    178         }
     172        {
     173          p = strstr (t, subst);
     174          if (p == 0)
     175            {
     176              /* No more matches.  Output everything left on the end.  */
     177              o = variable_buffer_output (o, t, strlen (t));
     178              return o;
     179            }
     180        }
    179181
    180182      /* Output everything before this occurrence of the string to replace.  */
    181183      if (p > t)
    182         o = variable_buffer_output (o, t, p - t);
     184        o = variable_buffer_output (o, t, p - t);
    183185
    184186      /* If we're substituting only by fully matched words,
    185         or only at the ends of words, check that this case qualifies.  */
     187        or only at the ends of words, check that this case qualifies.  */
    186188      if (by_word
    187           && ((p > text && !isblank ((unsigned char)p[-1]))
    188               || (p[slen] != '\0' && !isblank ((unsigned char)p[slen]))))
    189         /* Struck out.  Output the rest of the string that is
    190            no longer to be replaced.  */
    191         o = variable_buffer_output (o, subst, slen);
     189          && ((p > text && !ISSPACE (p[-1]))
     190              || ! STOP_SET (p[slen], MAP_SPACE|MAP_NUL)))
     191        /* Struck out.  Output the rest of the string that is
     192           no longer to be replaced.  */
     193        o = variable_buffer_output (o, subst, slen);
    192194      else if (rlen > 0)
    193         /* Output the replacement string.  */
    194         o = variable_buffer_output (o, replace, rlen);
     195        /* Output the replacement string.  */
     196        o = variable_buffer_output (o, replace, rlen);
    195197
    196198      /* Advance T past the string to be replaced.  */
     
    240242    /* With no % in the pattern, this is just a simple substitution.  */
    241243    return subst_expand (o, text, pattern, replace,
    242                         strlen (pattern), strlen (replace), 1);
     244                        strlen (pattern), strlen (replace), 1);
    243245
    244246  /* Record the length of PATTERN before and after the %
     
    253255      /* Is it big enough to match?  */
    254256      if (len < pattern_prepercent_len + pattern_postpercent_len)
    255         fail = 1;
     257        fail = 1;
    256258
    257259      /* Does the prefix match? */
    258260      if (!fail && pattern_prepercent_len > 0
    259           && (*t != *pattern
    260               || t[pattern_prepercent_len - 1] != pattern_percent[-2]
    261               || !strneq (t + 1, pattern + 1, pattern_prepercent_len - 1)))
    262         fail = 1;
     261          && (*t != *pattern
     262              || t[pattern_prepercent_len - 1] != pattern_percent[-2]
     263              || !strneq (t + 1, pattern + 1, pattern_prepercent_len - 1)))
     264        fail = 1;
    263265
    264266      /* Does the suffix match? */
    265267      if (!fail && pattern_postpercent_len > 0
    266           && (t[len - 1] != pattern_percent[pattern_postpercent_len - 1]
    267               || t[len - pattern_postpercent_len] != *pattern_percent
    268               || !strneq (&t[len - pattern_postpercent_len],
    269                           pattern_percent, pattern_postpercent_len - 1)))
    270         fail = 1;
     268          && (t[len - 1] != pattern_percent[pattern_postpercent_len - 1]
     269              || t[len - pattern_postpercent_len] != *pattern_percent
     270              || !strneq (&t[len - pattern_postpercent_len],
     271                          pattern_percent, pattern_postpercent_len - 1)))
     272        fail = 1;
    271273
    272274      if (fail)
    273         /* It didn't match.  Output the string.  */
    274         o = variable_buffer_output (o, t, len);
     275        /* It didn't match.  Output the string.  */
     276        o = variable_buffer_output (o, t, len);
    275277      else
    276         {
    277           /* It matched.  Output the replacement.  */
    278 
    279           /* Output the part of the replacement before the %.  */
    280           o = variable_buffer_output (o, replace, replace_prepercent_len);
    281 
    282           if (replace_percent != 0)
    283             {
    284               /* Output the part of the matched string that
    285                 matched the % in the pattern.  */
    286               o = variable_buffer_output (o, t + pattern_prepercent_len,
    287                                           len - (pattern_prepercent_len
    288                                                 + pattern_postpercent_len));
    289               /* Output the part of the replacement after the %.  */
    290               o = variable_buffer_output (o, replace_percent,
    291                                           replace_postpercent_len);
    292             }
    293         }
     278        {
     279          /* It matched.  Output the replacement.  */
     280
     281          /* Output the part of the replacement before the %.  */
     282          o = variable_buffer_output (o, replace, replace_prepercent_len);
     283
     284          if (replace_percent != 0)
     285            {
     286              /* Output the part of the matched string that
     287                matched the % in the pattern.  */
     288              o = variable_buffer_output (o, t + pattern_prepercent_len,
     289                                          len - (pattern_prepercent_len
     290                                                + pattern_postpercent_len));
     291              /* Output the part of the replacement after the %.  */
     292              o = variable_buffer_output (o, replace_percent,
     293                                          replace_postpercent_len);
     294            }
     295        }
    294296
    295297      /* Output a space, but not if the replacement is "".  */
    296298      if (fail || replace_prepercent_len > 0
    297           || (replace_percent != 0 && len + replace_postpercent_len > 0))
    298         {
    299           o = variable_buffer_output (o, " ", 1);
    300           doneany = 1;
    301         }
     299          || (replace_percent != 0 && len + replace_postpercent_len > 0))
     300        {
     301          o = variable_buffer_output (o, " ", 1);
     302          doneany = 1;
     303        }
    302304    }
    303305#ifndef CONFIG_WITH_VALUE_LENGTH
     
    376378        if (!func_char_map[ch = s[idx]]) \
    377379          { \
    378             if (isblank (ch)) \
     380            if (ISBLANK (ch)) \
    379381              return lookup_function_in_hash_tab (s, idx); \
    380382            return 0; \
     
    401403      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);
    402404      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);
    403         if ((ch = s[12]) == '\0' || isblank (ch))
     405        if ((ch = s[12]) == '\0' || ISBLANK (ch))
    404406          return lookup_function_in_hash_tab (s, 12);
    405407        return 0;
     
    418420      e++;
    419421    }
    420   if (ch == '\0' || isblank (ch))
     422  if (ch == '\0' || ISBLANK (ch))
    421423    return lookup_function_in_hash_tab (s, e - s);
    422424  return 0;
     
    430432lookup_function (const char *s)
    431433{
     434  struct function_table_entry function_table_entry_key;
    432435  const char *e = s;
    433   while (*e && ( (*e >= 'a' && *e <= 'z') || *e == '-'))
     436  while (STOP_SET (*e, MAP_USERFUNC))
    434437    e++;
    435   if (*e == '\0' || isblank ((unsigned char) *e))
    436     {
    437       struct function_table_entry function_table_entry_key;
    438       function_table_entry_key.name = s;
    439       function_table_entry_key.len = e - s;
    440 
    441       return hash_find_item (&function_table, &function_table_entry_key);
    442     }
    443   return 0;
     438
     439  if (e == s || !STOP_SET(*e, MAP_NUL|MAP_SPACE))
     440    return NULL;
     441
     442  function_table_entry_key.name = s;
     443  function_table_entry_key.len = e - s;
     444
     445  return hash_find_item (&function_table, &function_table_entry_key);
    444446}
    445447#endif /* original code */
     
    461463      percent = find_percent (new_chars);
    462464      if (percent == 0)
    463         return streq (new_chars, str);
     465        return streq (new_chars, str);
    464466      pattern = new_chars;
    465467    }
     
    496498    else if (*ptr == endparen)
    497499      {
    498         --count;
    499         if (count < 0)
    500           return NULL;
     500        --count;
     501        if (count < 0)
     502          return NULL;
    501503      }
    502504
     
    521523  unsigned int idx;
    522524
    523   chain = PARSE_FILE_SEQ (&line, struct nameseq, '\0', NULL,
    524                           /* We do not want parse_file_seq to strip `./'s.
     525  chain = PARSE_FILE_SEQ (&line, struct nameseq, MAP_NUL, NULL,
     526                          /* We do not want parse_file_seq to strip './'s.
    525527                             That would break examples like:
    526528                             $(patsubst ./%.c,obj/%.o,$(wildcard ./?*.c)).  */
     
    599601      tp = find_next_token (&list1_iterator, &len1);
    600602      if (tp != 0)
    601         o = variable_buffer_output (o, tp, len1);
     603        o = variable_buffer_output (o, tp, len1);
    602604
    603605      pp = find_next_token (&list2_iterator, &len2);
    604606      if (pp != 0)
    605         o = variable_buffer_output (o, pp, len2);
     607        o = variable_buffer_output (o, pp, len2);
    606608
    607609      if (tp != 0 || pp != 0)
    608         {
    609           o = variable_buffer_output (o, " ", 1);
    610           doneany = 1;
    611         }
     610        {
     611          o = variable_buffer_output (o, " ", 1);
     612          doneany = 1;
     613        }
    612614    }
    613615  while (tp != 0 || pp != 0);
     
    632634      default:
    633635      case o_invalid:
    634         abort ();
    635         break;
     636        abort ();
     637        break;
    636638      case o_default:
    637         o = variable_buffer_output (o, "default", 7);
    638         break;
     639        o = variable_buffer_output (o, "default", 7);
     640        break;
    639641      case o_env:
    640         o = variable_buffer_output (o, "environment", 11);
    641         break;
     642        o = variable_buffer_output (o, "environment", 11);
     643        break;
    642644      case o_file:
    643         o = variable_buffer_output (o, "file", 4);
    644         break;
     645        o = variable_buffer_output (o, "file", 4);
     646        break;
    645647      case o_env_override:
    646         o = variable_buffer_output (o, "environment override", 20);
    647         break;
     648        o = variable_buffer_output (o, "environment override", 20);
     649        break;
    648650      case o_command:
    649         o = variable_buffer_output (o, "command line", 12);
    650         break;
     651        o = variable_buffer_output (o, "command line", 12);
     652        break;
    651653      case o_override:
    652         o = variable_buffer_output (o, "override", 8);
    653         break;
     654        o = variable_buffer_output (o, "override", 8);
     655        break;
    654656      case o_automatic:
    655         o = variable_buffer_output (o, "automatic", 9);
    656         break;
     657        o = variable_buffer_output (o, "automatic", 9);
     658        break;
    657659#ifdef CONFIG_WITH_LOCAL_VARIABLES
    658660      case o_local:
     
    704706#endif /* CONFIG_WITH_WHERE_FUNCTION */
    705707
    706 #ifdef VMS
    707 # define IS_PATHSEP(c) ((c) == ']')
    708 #else
    709 # ifdef HAVE_DOS_PATHS
    710 #  define IS_PATHSEP(c) ((c) == '/' || (c) == '\\')
    711 # else
    712 #  define IS_PATHSEP(c) ((c) == '/')
    713 # endif
    714 #endif
    715 
    716 
    717708static char *
    718709func_notdir_suffix (char *o, char **argv, const char *funcname)
     
    724715  unsigned int len=0;
    725716
    726   int is_suffix = streq (funcname, "suffix");
     717  int is_suffix = funcname[0] == 's';
    727718  int is_notdir = !is_suffix;
     719  int stop = MAP_DIRSEP | (is_suffix ? MAP_DOT : 0);
     720#ifdef VMS
     721  /* For VMS list_iterator points to a comma separated list. To use the common
     722     [find_]next_token, create a local copy and replace the commas with
     723     spaces. Obviously, there is a problem if there is a ',' in the VMS filename
     724     (can only happen on ODS5), the same problem as with spaces in filenames,
     725     which seems to be present in make on all platforms. */
     726  char *vms_list_iterator = alloca(strlen(list_iterator) + 1);
     727  int i;
     728  for (i = 0; list_iterator[i]; i++)
     729    if (list_iterator[i] == ',')
     730      vms_list_iterator[i] = ' ';
     731    else
     732      vms_list_iterator[i] = list_iterator[i];
     733  vms_list_iterator[i] = list_iterator[i];
     734  while ((p2 = find_next_token((const char**) &vms_list_iterator, &len)) != 0)
     735#else
    728736  while ((p2 = find_next_token (&list_iterator, &len)) != 0)
    729     {
    730       const char *p = p2 + len;
    731 
    732 
    733       while (p >= p2 && (!is_suffix || *p != '.'))
    734         {
    735           if (IS_PATHSEP (*p))
    736             break;
    737           --p;
    738         }
     737#endif
     738    {
     739      const char *p = p2 + len - 1;
     740
     741      while (p >= p2 && ! STOP_SET (*p, stop))
     742        --p;
    739743
    740744      if (p >= p2)
    741         {
    742           if (is_notdir)
    743             ++p;
    744           else if (*p != '.')
    745             continue;
    746           o = variable_buffer_output (o, p, len - (p - p2));
    747         }
     745        {
     746          if (is_notdir)
     747            ++p;
     748          else if (*p != '.')
     749            continue;
     750          o = variable_buffer_output (o, p, len - (p - p2));
     751        }
    748752#ifdef HAVE_DOS_PATHS
    749753      /* Handle the case of "d:foo/bar".  */
    750       else if (streq (funcname, "notdir") && p2[0] && p2[1] == ':')
    751         {
    752           p = p2 + 2;
    753           o = variable_buffer_output (o, p, len - (p - p2));
    754         }
     754      else if (is_notdir && p2[0] && p2[1] == ':')
     755        {
     756          p = p2 + 2;
     757          o = variable_buffer_output (o, p, len - (p - p2));
     758        }
    755759#endif
    756760      else if (is_notdir)
    757         o = variable_buffer_output (o, p2, len);
     761        o = variable_buffer_output (o, p2, len);
    758762
    759763      if (is_notdir || p >= p2)
    760         {
    761           o = variable_buffer_output (o, " ", 1);
    762           doneany = 1;
    763         }
     764        {
     765#ifdef VMS
     766          if (vms_comma_separator)
     767            o = variable_buffer_output (o, ",", 1);
     768          else
     769#endif
     770          o = variable_buffer_output (o, " ", 1);
     771
     772          doneany = 1;
     773        }
    764774    }
    765775
     
    778788  const char *p3 = argv[0];
    779789  const char *p2;
    780   int doneany=0;
    781   unsigned int len=0;
    782 
    783   int is_basename= streq (funcname, "basename");
    784   int is_dir= !is_basename;
    785 
     790  int doneany = 0;
     791  unsigned int len = 0;
     792
     793  int is_basename = funcname[0] == 'b';
     794  int is_dir = !is_basename;
     795  int stop = MAP_DIRSEP | (is_basename ? MAP_DOT : 0) | MAP_NUL;
     796#ifdef VMS
     797  /* As in func_notdir_suffix ... */
     798  char *vms_p3 = alloca (strlen(p3) + 1);
     799  int i;
     800  for (i = 0; p3[i]; i++)
     801    if (p3[i] == ',')
     802      vms_p3[i] = ' ';
     803    else
     804      vms_p3[i] = p3[i];
     805  vms_p3[i] = p3[i];
     806  while ((p2 = find_next_token((const char**) &vms_p3, &len)) != 0)
     807#else
    786808  while ((p2 = find_next_token (&p3, &len)) != 0)
    787     {
    788       const char *p = p2 + len;
    789       while (p >= p2 && (!is_basename  || *p != '.'))
    790         {
    791           if (IS_PATHSEP (*p))
    792             break;
    793           --p;
    794         }
     809#endif
     810    {
     811      const char *p = p2 + len - 1;
     812      while (p >= p2 && ! STOP_SET (*p, stop))
     813        --p;
    795814
    796815      if (p >= p2 && (is_dir))
     
    805824      else if (is_dir)
    806825#ifdef VMS
    807         o = variable_buffer_output (o, "[]", 2);
     826        {
     827          extern int vms_report_unix_paths;
     828          if (vms_report_unix_paths)
     829            o = variable_buffer_output (o, "./", 2);
     830          else
     831            o = variable_buffer_output (o, "[]", 2);
     832        }
    808833#else
    809834#ifndef _AMIGA
     
    817842        o = variable_buffer_output (o, p2, len);
    818843
    819       o = variable_buffer_output (o, " ", 1);
     844#ifdef VMS
     845      if (vms_comma_separator)
     846        o = variable_buffer_output (o, ",", 1);
     847      else
     848#endif
     849        o = variable_buffer_output (o, " ", 1);
    820850      doneany = 1;
    821851    }
     
    827857  return o;
    828858}
     859
     860#if 1 /* rewrite to new MAP stuff? */
     861# ifdef VMS
     862#  define IS_PATHSEP(c) ((c) == ']')
     863# else
     864#  ifdef HAVE_DOS_PATHS
     865#   define IS_PATHSEP(c) ((c) == '/' || (c) == '\\')
     866#  else
     867#   define IS_PATHSEP(c) ((c) == '/')
     868#  endif
     869# endif
     870#endif
    829871
    830872#ifdef CONFIG_WITH_ROOT_FUNC
     
    848890      const char *p2 = p;
    849891
    850 #ifdef HAVE_DOS_PATHS
     892# ifdef HAVE_DOS_PATHS
    851893      if (   len >= 2
    852894          && p2[1] == ':'
     
    889931        p2 = NULL;
    890932
    891 #elif defined (VMS) || defined (AMGIA)
     933# elif defined (VMS) || defined (AMGIA)
    892934      /* XXX: VMS and AMGIA */
    893       fatal (NILF, _("$(root ) is not implemented on this platform"));
    894 #else
     935      O (fatal, NILF, _("$(root ) is not implemented on this platform"));
     936# else
    895937      if (IS_PATHSEP(*p2))
    896938        {
     
    900942      else
    901943        p2 = NULL;
    902 #endif
     944# endif
    903945      if (p2 != NULL)
    904946        {
     
    938980      const char *p2 = p;
    939981
    940 #ifdef HAVE_DOS_PATHS
     982# ifdef HAVE_DOS_PATHS
    941983      if (   len >= 2
    942984          && p2[1] == ':'
     
    9761018        }
    9771019
    978 #elif defined (VMS) || defined (AMGIA)
     1020# elif defined (VMS) || defined (AMGIA)
    9791021      /* XXX: VMS and AMGIA */
    980       fatal (NILF, _("$(root ) is not implemented on this platform"));
    981 #endif
     1022      O (fatal, NILF, _("$(root ) is not implemented on this platform"));
     1023# endif
    9821024
    9831025      /* Exclude all subsequent / leading path separators. */
     
    10071049  int fixlen = strlen (argv[0]);
    10081050  const char *list_iterator = argv[1];
    1009   int is_addprefix = streq (funcname, "addprefix");
     1051  int is_addprefix = funcname[3] == 'p';
    10101052  int is_addsuffix = !is_addprefix;
    10111053
     
    10171059    {
    10181060      if (is_addprefix)
    1019         o = variable_buffer_output (o, argv[0], fixlen);
     1061        o = variable_buffer_output (o, argv[0], fixlen);
    10201062      o = variable_buffer_output (o, p, len);
    10211063      if (is_addsuffix)
    1022         o = variable_buffer_output (o, argv[0], fixlen);
     1064        o = variable_buffer_output (o, argv[0], fixlen);
    10231065      o = variable_buffer_output (o, " ", 1);
    10241066      doneany = 1;
     
    10361078{
    10371079  o = subst_expand (o, argv[2], argv[0], argv[1], strlen (argv[0]),
    1038                     strlen (argv[1]), 0);
     1080                    strlen (argv[1]), 0);
    10391081
    10401082  return o;
     
    10631105    rc = 1;
    10641106  else
    1065 #if 1 /* FIXME: later */
    1066     fatal (*expanding_var,
    1067            _("second argument to `%s' function must be `name' or `value', not `%s'"),
    1068            funcname, arg1);
    1069 #else
     1107# if 1 /* FIXME: later */
     1108    OSS (fatal, *expanding_var,
     1109         _("second argument to `%s' function must be `name' or `value', not `%s'"),
     1110         funcname, arg1);
     1111# else
    10701112    {
    10711113      /* check the expanded form */
     
    10801122        rc = 1;
    10811123      else
    1082         fatal (*expanding_var,
    1083                _("second argument to `%s' function must be `name' or `value', not `%s'"),
    1084                funcname, exp);
     1124        OSS (fatal, *expanding_var,
     1125             _("second argument to `%s' function must be `name' or `value', not `%s'"),
     1126             funcname, exp);
    10851127      free (exp);
    10861128    }
    1087 #endif
     1129# endif
    10881130
    10891131  return rc;
     
    11921234  char buf[20];
    11931235
    1194   while (find_next_token (&word_iterator, (unsigned int *) 0) != 0)
     1236  while (find_next_token (&word_iterator, NULL) != 0)
    11951237    ++i;
    11961238
     
    12091251strip_whitespace (const char **begpp, const char **endpp)
    12101252{
    1211   while (*begpp <= *endpp && isspace ((unsigned char)**begpp))
     1253  while (*begpp <= *endpp && ISSPACE (**begpp))
    12121254    (*begpp) ++;
    1213   while (*endpp >= *begpp && isspace ((unsigned char)**endpp))
     1255  while (*endpp >= *begpp && ISSPACE (**endpp))
    12141256    (*endpp) --;
    12151257  return (char *)*begpp;
     
    12241266
    12251267  for (; s <= end; ++s)
    1226     if (!ISDIGIT (*s))  /* ISDIGIT only evals its arg once: see make.h.  */
     1268    if (!ISDIGIT (*s))  /* ISDIGIT only evals its arg once: see makeint.h.  */
    12271269      break;
    12281270
    12291271  if (s <= end || end - beg < 0)
    1230     fatal (*expanding_var, "%s: '%s'", msg, beg);
     1272    OSS (fatal, *expanding_var, "%s: '%s'", msg, beg);
    12311273}
    12321274
     
    12411283
    12421284  /* Check the first argument.  */
    1243   check_numeric (argv[0], _("non-numeric first argument to `word' function"));
     1285  check_numeric (argv[0], _("non-numeric first argument to 'word' function"));
    12441286  i = atoi (argv[0]);
    12451287
    12461288  if (i == 0)
    1247     fatal (*expanding_var,
    1248            _("first argument to `word' function must be greater than 0"));
     1289    O (fatal, *expanding_var,
     1290       _("first argument to 'word' function must be greater than 0"));
    12491291
    12501292  end_p = argv[1];
     
    12661308  /* Check the arguments.  */
    12671309  check_numeric (argv[0],
    1268                  _("non-numeric first argument to `wordlist' function"));
     1310                 _("non-numeric first argument to 'wordlist' function"));
    12691311  check_numeric (argv[1],
    1270                  _("non-numeric second argument to `wordlist' function"));
     1312                 _("non-numeric second argument to 'wordlist' function"));
    12711313
    12721314  start = atoi (argv[0]);
    12731315  if (start < 1)
    1274     fatal (*expanding_var,
    1275            "invalid first argument to `wordlist' function: `%d'", start);
     1316    ON (fatal, *expanding_var,
     1317        "invalid first argument to 'wordlist' function: '%d'", start);
    12761318
    12771319  count = atoi (argv[1]) - start + 1;
     
    13271369  struct variable *var;
    13281370
     1371  /* Clean up the variable name by removing whitespace.  */
     1372  char *vp = next_token (varname);
     1373  end_of_token (vp)[0] = '\0';
     1374
    13291375  push_new_variable_scope ();
    1330   var = define_variable (varname, strlen (varname), "", o_automatic, 0);
     1376  var = define_variable (vp, strlen (vp), "", o_automatic, 0);
    13311377
    13321378  /* loop through LIST,  put the value in VAR and expand BODY */
     
    13901436
    13911437    install_variable_buffer (&buf, &buf_len);
    1392     eval_buffer (text, text + text_len);
     1438    eval_buffer (text, NULL, text + text_len);
    13931439    restore_variable_buffer (buf, buf_len);
    13941440}
     
    14971543    return result;
    14981544  return_STRING_COMPARE (((struct a_word const *) x)->str,
    1499                         ((struct a_word const *) y)->str);
     1545                        ((struct a_word const *) y)->str);
    15001546}
    15011547
     
    15061552  char *percent;
    15071553  int length;
    1508   int save_c;
    15091554};
    15101555
     
    15201565
    15211566  struct hash_table a_word_table;
    1522   int is_filter = streq (funcname, "filter");
     1567  int is_filter = funcname[CSTRLEN ("filter")] == '\0';
    15231568  const char *pat_iterator = argv[0];
    15241569  const char *word_iterator = argv[1];
     
    15291574  unsigned int len;
    15301575
    1531   /* Chop ARGV[0] up into patterns to match against the words.  */
     1576  /* Chop ARGV[0] up into patterns to match against the words.
     1577     We don't need to preserve it because our caller frees all the
     1578     argument memory anyway.  */
    15321579
    15331580  pattail = &pathead;
     
    15401587
    15411588      if (*pat_iterator != '\0')
    1542         ++pat_iterator;
     1589        ++pat_iterator;
    15431590
    15441591      pat->str = p;
    1545       pat->length = len;
    1546       pat->save_c = p[len];
    15471592      p[len] = '\0';
    15481593      pat->percent = find_percent (p);
    15491594      if (pat->percent == 0)
    1550         literals++;
     1595        literals++;
     1596
     1597      /* find_percent() might shorten the string so LEN is wrong.  */
     1598      pat->length = strlen (pat->str);
    15511599    }
    15521600  *pattail = 0;
     
    15631611
    15641612      if (*word_iterator != '\0')
    1565         ++word_iterator;
     1613        ++word_iterator;
    15661614
    15671615      p[len] = '\0';
     
    15811629                 a_word_hash_cmp);
    15821630      for (wp = wordhead; wp != 0; wp = wp->next)
    1583         {
    1584           struct a_word *owp = hash_insert (&a_word_table, wp);
    1585           if (owp)
    1586             wp->chain = owp;
    1587         }
     1631        {
     1632          struct a_word *owp = hash_insert (&a_word_table, wp);
     1633          if (owp)
     1634            wp->chain = owp;
     1635        }
    15881636    }
    15891637
     
    15941642      /* Run each pattern through the words, killing words.  */
    15951643      for (pp = pathead; pp != 0; pp = pp->next)
    1596         {
    1597           if (pp->percent)
    1598             for (wp = wordhead; wp != 0; wp = wp->next)
    1599               wp->matched |= pattern_matches (pp->str, pp->percent, wp->str);
    1600           else if (hashing)
    1601             {
    1602               struct a_word a_word_key;
    1603               a_word_key.str = pp->str;
    1604               a_word_key.length = pp->length;
    1605               wp = hash_find_item (&a_word_table, &a_word_key);
    1606               while (wp)
    1607                 {
    1608                   wp->matched |= 1;
    1609                   wp = wp->chain;
    1610                 }
    1611             }
    1612           else
    1613             for (wp = wordhead; wp != 0; wp = wp->next)
    1614               wp->matched |= (wp->length == pp->length
    1615                               && strneq (pp->str, wp->str, wp->length));
    1616         }
     1644        {
     1645          if (pp->percent)
     1646            for (wp = wordhead; wp != 0; wp = wp->next)
     1647              wp->matched |= pattern_matches (pp->str, pp->percent, wp->str);
     1648          else if (hashing)
     1649            {
     1650              struct a_word a_word_key;
     1651              a_word_key.str = pp->str;
     1652              a_word_key.length = pp->length;
     1653              wp = hash_find_item (&a_word_table, &a_word_key);
     1654              while (wp)
     1655                {
     1656                  wp->matched |= 1;
     1657                  wp = wp->chain;
     1658                }
     1659            }
     1660          else
     1661            for (wp = wordhead; wp != 0; wp = wp->next)
     1662              wp->matched |= (wp->length == pp->length
     1663                              && strneq (pp->str, wp->str, wp->length));
     1664        }
    16171665
    16181666      /* Output the words that matched (or didn't, for filter-out).  */
    16191667      for (wp = wordhead; wp != 0; wp = wp->next)
    1620         if (is_filter ? wp->matched : !wp->matched)
    1621           {
    1622             o = variable_buffer_output (o, wp->str, strlen (wp->str));
    1623             o = variable_buffer_output (o, " ", 1);
    1624             doneany = 1;
    1625           }
     1668        if (is_filter ? wp->matched : !wp->matched)
     1669          {
     1670            o = variable_buffer_output (o, wp->str, strlen (wp->str));
     1671            o = variable_buffer_output (o, " ", 1);
     1672            doneany = 1;
     1673          }
    16261674
    16271675      if (doneany)
    1628         /* Kill the last space.  */
    1629         --o;
    1630     }
    1631 
    1632   for (pp = pathead; pp != 0; pp = pp->next)
    1633     pp->str[pp->length] = pp->save_c;
     1676        /* Kill the last space.  */
     1677        --o;
     1678    }
    16341679
    16351680  if (hashing)
     
    16511696      const char *word_start;
    16521697
    1653       while (isspace ((unsigned char)*p))
    1654         ++p;
     1698      NEXT_TOKEN (p);
    16551699      word_start = p;
    1656       for (i=0; *p != '\0' && !isspace ((unsigned char)*p); ++p, ++i)
    1657         {}
     1700      for (i=0; *p != '\0' && !ISSPACE (*p); ++p, ++i)
     1701        {}
    16581702      if (!i)
    1659         break;
     1703        break;
    16601704      o = variable_buffer_output (o, word_start, i);
    16611705      o = variable_buffer_output (o, " ", 1);
     
    16971741  strcpy (p, *argvp);
    16981742
    1699   switch (*funcname) {
     1743  switch (*funcname)
     1744    {
    17001745    case 'e':
    1701       fatal (reading_file, "%s", msg);
     1746      OS (fatal, reading_file, "%s", msg);
    17021747
    17031748    case 'w':
    1704       error (reading_file, "%s", msg);
     1749      OS (error, reading_file, "%s", msg);
    17051750      break;
    17061751
    17071752    case 'i':
    1708       printf ("%s\n", msg);
    1709       fflush(stdout);
     1753      outputs (0, msg);
     1754      outputs (0, "\n");
    17101755      break;
    17111756
    17121757    default:
    1713       fatal (*expanding_var, "Internal error: func_error: '%s'", funcname);
    1714   }
     1758      OS (fatal, *expanding_var, "Internal error: func_error: '%s'", funcname);
     1759    }
    17151760
    17161761  /* The warning function expands to the empty string.  */
     
    17301775  char *p;
    17311776  unsigned int len;
    1732   int i;
    17331777
    17341778  /* Find the maximum number of words we'll have.  */
    17351779  t = argv[0];
    1736   wordi = 1;
    1737   while (*t != '\0')
    1738     {
    1739       char c = *(t++);
    1740 
    1741       if (! isspace ((unsigned char)c))
    1742         continue;
    1743 
     1780  wordi = 0;
     1781  while ((p = find_next_token (&t, NULL)) != 0)
     1782    {
     1783      ++t;
    17441784      ++wordi;
    1745 
    1746       while (isspace ((unsigned char)*t))
    1747         ++t;
    1748     }
    1749 
    1750   words = xmalloc (wordi * sizeof (char *));
     1785    }
     1786
     1787  words = xmalloc ((wordi == 0 ? 1 : wordi) * sizeof (char *));
    17511788
    17521789  /* Now assign pointers to each string in the array.  */
     
    17631800  if (wordi)
    17641801    {
     1802      int i;
     1803
    17651804      /* Now sort the list of words.  */
    17661805      qsort (words, wordi, sizeof (char *), alpha_compare);
     
    19291968{
    19301969  char *expansion;
    1931   int result;
    19321970
    19331971  while (1)
     
    19351973      const char *begp = *argv;
    19361974      const char *endp = begp + strlen (*argv) - 1;
     1975      int result;
    19371976
    19381977      /* An empty condition is always false.  */
     
    19972036
    19982037#ifndef CONFIG_WITH_VALUE_LENGTH
    1999   eval_buffer (argv[0]);
     2038  eval_buffer (argv[0], NULL);
    20002039#else
    2001   eval_buffer (argv[0], strchr (argv[0], '\0'));
     2040  eval_buffer (argv[0], NULL, strchr (argv[0], '\0'));
    20022041#endif
    20032042
     
    20242063  push_new_variable_scope ();
    20252064
    2026   eval_buffer (argv[0], strchr (argv[0], '\0'));
     2065  eval_buffer (argv[0], NULL, strchr (argv[0], '\0'));
    20272066
    20282067  pop_variable_scope ();
     
    20472086      int var_ctx;
    20482087      size_t off;
    2049       const struct floc *reading_file_saved = reading_file;
     2088      const floc *reading_file_saved = reading_file;
    20502089# ifdef CONFIG_WITH_MAKE_STATS
    20512090      unsigned long long uStartTick = CURRENT_CLOCK_TICK();
     
    20852124
    20862125        install_variable_buffer (&buf, &len); /* Really necessary? */
    2087         eval_buffer (o, o + v->value_length);
     2126        eval_buffer (o, NULL, o + v->value_length);
    20882127        restore_variable_buffer (buf, len);
    20892128      }
     
    21342173                    {
    21352174                      ch = (unsigned char)dst[-1];
    2136                       if (!isblank (ch))
     2175                      if (!ISBLANK (ch))
    21372176                        break;
    21382177                      dst--;
     
    21752214        }
    21762215      else if (v)
    2177         error (NILF, _("$(%s ): variable `%s' is of the wrong type\n"), funcname, v->name);
     2216        OSS (error, NILF, _("$(%s ): variable `%s' is of the wrong type\n"), funcname, v->name);
    21782217    }
    21792218
     
    21972236    }
    21982237#else
    2199     o = variable_buffer_output (o, v->value, strlen(v->value));
     2238    o = variable_buffer_output (o, v->value, strlen (v->value));
    22002239#endif
    22012240
     
    22042243
    22052244/*
    2206   \r  is replaced on UNIX as well. Is this desirable?
     2245  \r is replaced on UNIX as well. Is this desirable?
    22072246 */
    22082247static void
    2209 fold_newlines (char *buffer, unsigned int *length)
     2248fold_newlines (char *buffer, unsigned int *length, int trim_newlines)
    22102249{
    22112250  char *dst = buffer;
    22122251  char *src = buffer;
    2213   char *last_nonnl = buffer -1;
     2252  char *last_nonnl = buffer - 1;
    22142253  src[*length] = 0;
    22152254  for (; *src != '\0'; ++src)
    22162255    {
    22172256      if (src[0] == '\r' && src[1] == '\n')
    2218         continue;
     2257        continue;
    22192258      if (*src == '\n')
    2220         {
    2221           *dst++ = ' ';
    2222         }
     2259        {
     2260          *dst++ = ' ';
     2261        }
    22232262      else
    2224         {
    2225           last_nonnl = dst;
    2226           *dst++ = *src;
    2227         }
    2228     }
     2263        {
     2264          last_nonnl = dst;
     2265          *dst++ = *src;
     2266        }
     2267    }
     2268
     2269  if (!trim_newlines && (last_nonnl < (dst - 2)))
     2270    last_nonnl = dst - 2;
     2271
    22292272  *(++last_nonnl) = '\0';
    22302273  *length = last_nonnl - buffer;
    22312274}
    22322275
    2233 
    2234 
    2235 int shell_function_pid = 0, shell_function_completed;
    2236 
     2276pid_t shell_function_pid = 0;
     2277static int shell_function_completed;
     2278
     2279void
     2280shell_completed (int exit_code, int exit_sig)
     2281{
     2282  char buf[256];
     2283
     2284  shell_function_pid = 0;
     2285  if (exit_sig == 0 && exit_code == 127)
     2286    shell_function_completed = -1;
     2287  else
     2288    shell_function_completed = 1;
     2289
     2290  sprintf (buf, "%d", exit_code);
     2291  define_variable_cname (".SHELLSTATUS", buf, o_override, 0);
     2292}
    22372293
    22382294#ifdef WINDOWS32
     
    22442300
    22452301
    2246 void
    2247 windows32_openpipe (int *pipedes, pid_t *pid_p, char **command_argv, char **envp)
     2302int
     2303windows32_openpipe (int *pipedes, int errfd, pid_t *pid_p, char **command_argv, char **envp)
    22482304{
    22492305  SECURITY_ATTRIBUTES saAttr;
    2250   HANDLE hIn;
    2251   HANDLE hErr;
     2306  HANDLE hIn = INVALID_HANDLE_VALUE;
     2307  HANDLE hErr = INVALID_HANDLE_VALUE;
    22522308  HANDLE hChildOutRd;
    22532309  HANDLE hChildOutWr;
    2254   HANDLE hProcess;
    2255 
     2310  HANDLE hProcess, tmpIn, tmpErr;
     2311  DWORD e;
     2312
     2313  /* Set status for return.  */
     2314  pipedes[0] = pipedes[1] = -1;
     2315  *pid_p = (pid_t)-1;
    22562316
    22572317  saAttr.nLength = sizeof (SECURITY_ATTRIBUTES);
     
    22592319  saAttr.lpSecurityDescriptor = NULL;
    22602320
    2261   if (DuplicateHandle (GetCurrentProcess(),
    2262                       GetStdHandle(STD_INPUT_HANDLE),
    2263                       GetCurrentProcess(),
    2264                       &hIn,
    2265                       0,
    2266                       TRUE,
    2267                       DUPLICATE_SAME_ACCESS) == FALSE) {
    2268     fatal (NILF, _("windows32_openpipe(): DuplicateHandle(In) failed (e=%ld)\n"),
    2269            GetLastError());
    2270 
    2271   }
    2272   if (DuplicateHandle(GetCurrentProcess(),
    2273                       GetStdHandle(STD_ERROR_HANDLE),
    2274                       GetCurrentProcess(),
    2275                       &hErr,
    2276                       0,
    2277                       TRUE,
    2278                       DUPLICATE_SAME_ACCESS) == FALSE) {
    2279     fatal (NILF, _("windows32_open_pipe(): DuplicateHandle(Err) failed (e=%ld)\n"),
    2280            GetLastError());
    2281   }
    2282 
    2283   if (!CreatePipe(&hChildOutRd, &hChildOutWr, &saAttr, 0))
    2284     fatal (NILF, _("CreatePipe() failed (e=%ld)\n"), GetLastError());
    2285 
    2286   hProcess = process_init_fd(hIn, hChildOutWr, hErr);
     2321  /* Standard handles returned by GetStdHandle can be NULL or
     2322     INVALID_HANDLE_VALUE if the parent process closed them.  If that
     2323     happens, we open the null device and pass its handle to
     2324     process_begin below as the corresponding handle to inherit.  */
     2325  tmpIn = GetStdHandle (STD_INPUT_HANDLE);
     2326  if (DuplicateHandle (GetCurrentProcess (), tmpIn,
     2327                       GetCurrentProcess (), &hIn,
     2328                       0, TRUE, DUPLICATE_SAME_ACCESS) == FALSE)
     2329    {
     2330      e = GetLastError ();
     2331      if (e == ERROR_INVALID_HANDLE)
     2332        {
     2333          tmpIn = CreateFile ("NUL", GENERIC_READ,
     2334                              FILE_SHARE_READ | FILE_SHARE_WRITE, NULL,
     2335                              OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
     2336          if (tmpIn != INVALID_HANDLE_VALUE
     2337              && DuplicateHandle (GetCurrentProcess (), tmpIn,
     2338                                  GetCurrentProcess (), &hIn,
     2339                                  0, TRUE, DUPLICATE_SAME_ACCESS) == FALSE)
     2340            CloseHandle (tmpIn);
     2341        }
     2342      if (hIn == INVALID_HANDLE_VALUE)
     2343        {
     2344          ON (error, NILF,
     2345              _("windows32_openpipe: DuplicateHandle(In) failed (e=%ld)\n"), e);
     2346          return -1;
     2347        }
     2348    }
     2349  tmpErr = (HANDLE)_get_osfhandle (errfd);
     2350  if (DuplicateHandle (GetCurrentProcess (), tmpErr,
     2351                       GetCurrentProcess (), &hErr,
     2352                       0, TRUE, DUPLICATE_SAME_ACCESS) == FALSE)
     2353    {
     2354      e = GetLastError ();
     2355      if (e == ERROR_INVALID_HANDLE)
     2356        {
     2357          tmpErr = CreateFile ("NUL", GENERIC_WRITE,
     2358                               FILE_SHARE_READ | FILE_SHARE_WRITE, NULL,
     2359                               OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
     2360          if (tmpErr != INVALID_HANDLE_VALUE
     2361              && DuplicateHandle (GetCurrentProcess (), tmpErr,
     2362                                  GetCurrentProcess (), &hErr,
     2363                                  0, TRUE, DUPLICATE_SAME_ACCESS) == FALSE)
     2364            CloseHandle (tmpErr);
     2365        }
     2366      if (hErr == INVALID_HANDLE_VALUE)
     2367        {
     2368          ON (error, NILF,
     2369              _("windows32_openpipe: DuplicateHandle(Err) failed (e=%ld)\n"), e);
     2370          return -1;
     2371        }
     2372    }
     2373
     2374  if (! CreatePipe (&hChildOutRd, &hChildOutWr, &saAttr, 0))
     2375    {
     2376      ON (error, NILF, _("CreatePipe() failed (e=%ld)\n"), GetLastError());
     2377      return -1;
     2378    }
     2379
     2380  hProcess = process_init_fd (hIn, hChildOutWr, hErr);
    22872381
    22882382  if (!hProcess)
    2289     fatal (NILF, _("windows32_openpipe(): process_init_fd() failed\n"));
     2383    {
     2384      O (error, NILF, _("windows32_openpipe(): process_init_fd() failed\n"));
     2385      return -1;
     2386    }
    22902387
    22912388  /* make sure that CreateProcess() has Path it needs */
    2292   sync_Path_environment();
    2293   /* `sync_Path_environment' may realloc `environ', so take note of
     2389  sync_Path_environment ();
     2390  /* 'sync_Path_environment' may realloc 'environ', so take note of
    22942391     the new value.  */
    22952392  envp = environ;
    22962393
    2297   if (!process_begin(hProcess, command_argv, envp, command_argv[0], NULL)) {
    2298     /* register process for wait */
    2299     process_register(hProcess);
    2300 
    2301     /* set the pid for returning to caller */
    2302     *pid_p = (pid_t) hProcess;
    2303 
    2304   /* set up to read data from child */
    2305   pipedes[0] = _open_osfhandle((intptr_t) hChildOutRd, O_RDONLY);
    2306 
    2307   /* this will be closed almost right away */
    2308   pipedes[1] = _open_osfhandle((intptr_t) hChildOutWr, O_APPEND);
    2309   } else {
    2310     /* reap/cleanup the failed process */
    2311         process_cleanup(hProcess);
    2312 
    2313     /* close handles which were duplicated, they weren't used */
    2314         CloseHandle(hIn);
    2315         CloseHandle(hErr);
    2316 
    2317         /* close pipe handles, they won't be used */
    2318         CloseHandle(hChildOutRd);
    2319         CloseHandle(hChildOutWr);
    2320 
    2321     /* set status for return */
    2322     pipedes[0] = pipedes[1] = -1;
    2323     *pid_p = (pid_t)-1;
    2324   }
     2394  if (! process_begin (hProcess, command_argv, envp, command_argv[0], NULL))
     2395    {
     2396      /* register process for wait */
     2397      process_register (hProcess);
     2398
     2399      /* set the pid for returning to caller */
     2400      *pid_p = (pid_t) hProcess;
     2401
     2402      /* set up to read data from child */
     2403      pipedes[0] = _open_osfhandle ((intptr_t) hChildOutRd, O_RDONLY);
     2404
     2405      /* this will be closed almost right away */
     2406      pipedes[1] = _open_osfhandle ((intptr_t) hChildOutWr, O_APPEND);
     2407      return 0;
     2408    }
     2409  else
     2410    {
     2411      /* reap/cleanup the failed process */
     2412      process_cleanup (hProcess);
     2413
     2414      /* close handles which were duplicated, they weren't used */
     2415      if (hIn != INVALID_HANDLE_VALUE)
     2416        CloseHandle (hIn);
     2417      if (hErr != INVALID_HANDLE_VALUE)
     2418        CloseHandle (hErr);
     2419
     2420      /* close pipe handles, they won't be used */
     2421      CloseHandle (hChildOutRd);
     2422      CloseHandle (hChildOutWr);
     2423
     2424      return -1;
     2425    }
    23252426}
    23262427#endif
     
    23322433{
    23332434  FILE *fpipe=0;
    2334   /* MSDOS can't fork, but it has `popen'.  */
     2435  /* MSDOS can't fork, but it has 'popen'.  */
    23352436  struct variable *sh = lookup_variable ("SHELL", 5);
    23362437  int e;
     
    23382439
    23392440  /* Make sure not to bother processing an empty line.  */
    2340   while (isblank ((unsigned char)*text))
    2341     ++text;
     2441  NEXT_TOKEN (text);
    23422442  if (*text == '\0')
    23432443    return 0;
     
    23472447      char buf[PATH_MAX + 7];
    23482448      /* This makes sure $SHELL value is used by $(shell), even
    2349         though the target environment is not passed to it.  */
     2449        though the target environment is not passed to it.  */
    23502450      sprintf (buf, "SHELL=%s", sh->value);
    23512451      putenv (buf);
     
    23662466      *pidp = -1;
    23672467      if (dos_status)
    2368         errno = EINTR;
     2468        errno = EINTR;
    23692469      else if (errno == 0)
    2370         errno = ENOMEM;
    2371       shell_function_completed = -1;
     2470        errno = ENOMEM;
     2471      if (fpipe)
     2472        pclose (fpipe);
     2473      shell_completed (127, 0);
    23722474    }
    23732475  else
     
    23762478      *pidp = 42; /* Yes, the Meaning of Life, the Universe, and Everything! */
    23772479      errno = e;
    2378       shell_function_completed = 1;
    23792480    }
    23802481  return fpipe;
     
    23892490
    23902491/* VMS can't do $(shell ...)  */
     2492
     2493char *
     2494func_shell_base (char *o, char **argv, int trim_newlines)
     2495{
     2496  fprintf (stderr, "This platform does not support shell\n");
     2497  die (MAKE_TROUBLE);
     2498  return NULL;
     2499}
     2500
    23912501#define func_shell 0
    23922502
    23932503#else
    23942504#ifndef _AMIGA
    2395 static char *
    2396 func_shell (char * volatile o, char **argv, const char *funcname UNUSED)
     2505char *
     2506func_shell_base (char *o, char **argv, int trim_newlines)
    23972507{
    23982508  char *batch_filename = NULL;
    2399 
     2509  int errfd;
    24002510#ifdef __MSDOS__
    24012511  FILE *fpipe;
    24022512#endif
    24032513  char **command_argv;
    2404   const char * volatile error_prefix; /* bird: this volatile and the 'o' one, is for shutting up gcc warnings */
     2514  const char * volatile error_prefix; /* bird: this volatile ~~and the 'o' one~~, is for shutting up gcc warnings */
    24052515  char **envp;
    24062516  int pipedes[2];
     
    24082518
    24092519#ifndef __MSDOS__
     2520#ifdef WINDOWS32
     2521  /* Reset just_print_flag.  This is needed on Windows when batch files
     2522     are used to run the commands, because we normally refrain from
     2523     creating batch files under -n.  */
     2524  int j_p_f = just_print_flag;
     2525  just_print_flag = 0;
     2526#endif
     2527
    24102528  /* Construct the argument list.  */
    24112529  command_argv = construct_command_argv (argv[0], NULL, NULL, 0,
    24122530                                         &batch_filename);
    24132531  if (command_argv == 0)
    2414     return o;
    2415 #endif
    2416 
    2417   /* Using a target environment for `shell' loses in cases like:
    2418      export var = $(shell echo foobie)
    2419      because target_environment hits a loop trying to expand $(var)
    2420      to put it in the environment.  This is even more confusing when
    2421      var was not explicitly exported, but just appeared in the
    2422      calling environment.
     2532    {
     2533#ifdef WINDOWS32
     2534      just_print_flag = j_p_f;
     2535#endif
     2536      return o;
     2537    }
     2538#endif /* !__MSDOS__ */
     2539
     2540  /* Using a target environment for 'shell' loses in cases like:
     2541       export var = $(shell echo foobie)
     2542       bad := $(var)
     2543     because target_environment hits a loop trying to expand $(var) to put it
     2544     in the environment.  This is even more confusing when 'var' was not
     2545     explicitly exported, but just appeared in the calling environment.
    24232546
    24242547     See Savannah bug #10593.
    24252548
    2426   envp = target_environment (NILF);
     2549  envp = target_environment (NULL);
    24272550  */
    24282551
     
    24332556    {
    24342557      char *p = alloca (strlen (reading_file->filenm)+11+4);
    2435       sprintf (p, "%s:%lu: ", reading_file->filenm, reading_file->lineno);
     2558      sprintf (p, "%s:%lu: ", reading_file->filenm,
     2559               reading_file->lineno + reading_file->offset);
    24362560      error_prefix = p;
    24372561    }
    24382562  else
    24392563    error_prefix = "";
     2564
     2565  /* Set up the output in case the shell writes something.  */
     2566  output_start ();
     2567
     2568  errfd = (output_context && output_context->err >= 0
     2569           ? output_context->err : FD_STDERR);
    24402570
    24412571#if defined(__MSDOS__)
     
    24462576      return o;
    24472577    }
     2578
    24482579#elif defined(WINDOWS32)
    2449   windows32_openpipe (pipedes, &pid, command_argv, envp);
     2580  windows32_openpipe (pipedes, errfd, &pid, command_argv, envp);
     2581  /* Restore the value of just_print_flag.  */
     2582  just_print_flag = j_p_f;
     2583
    24502584  if (pipedes[0] < 0)
    24512585    {
    2452       /* open of the pipe failed, mark as failed execution */
    2453       shell_function_completed = -1;
    2454 
     2586      /* Open of the pipe failed, mark as failed execution. */
     2587      shell_completed (127, 0);
     2588      perror_with_name (error_prefix, "pipe");
    24552589      return o;
    24562590    }
    2457   else
     2591
    24582592#else
    24592593  if (pipe (pipedes) < 0)
     
    24632597    }
    24642598
    2465 # ifdef __EMX__
    2466   /* close some handles that are unnecessary for the child process */
     2599  /* Close handles that are unnecessary for the child process.  */
    24672600  CLOSE_ON_EXEC(pipedes[1]);
    24682601  CLOSE_ON_EXEC(pipedes[0]);
    2469   /* Never use fork()/exec() here! Use spawn() instead in exec_command() */
    2470   pid = child_execute_job (0, pipedes[1], command_argv, envp);
     2602
     2603  {
     2604    struct output out;
     2605    out.syncout = 1;
     2606    out.out = pipedes[1];
     2607    out.err = errfd;
     2608
     2609    pid = child_execute_job (&out, 1, command_argv, envp);
     2610  }
     2611
    24712612  if (pid < 0)
    2472     perror_with_name (error_prefix, "spawn");
    2473 # else /* ! __EMX__ */
    2474   pid = vfork ();
    2475   if (pid < 0)
    2476     perror_with_name (error_prefix, "fork");
    2477   else if (pid == 0)
    2478     child_execute_job (0, pipedes[1], command_argv, envp);
    2479   else
    2480 # endif
    2481 #endif
    2482     {
    2483       /* We are the parent.  */
    2484       char *buffer;
    2485       unsigned int maxlen, i;
    2486       int cc;
    2487 
    2488       /* Record the PID for reap_children.  */
    2489       shell_function_pid = pid;
     2613    {
     2614      perror_with_name (error_prefix, "fork");
     2615      return o;
     2616    }
     2617#endif
     2618
     2619  {
     2620    char *buffer;
     2621    unsigned int maxlen, i;
     2622    int cc;
     2623
     2624    /* Record the PID for reap_children.  */
     2625    shell_function_pid = pid;
    24902626#ifndef  __MSDOS__
    2491       shell_function_completed = 0;
    2492 
    2493       /* Free the storage only the child needed.  */
    2494       free (command_argv[0]);
    2495       free (command_argv);
    2496 
    2497       /* Close the write side of the pipe.  We test for -1, since
    2498         pipedes[1] is -1 on MS-Windows, and some versions of MS
    2499          libraries barf when `close' is called with -1.  */
    2500       if (pipedes[1] >= 0)
    2501         close (pipedes[1]);
    2502 #endif
    2503 
    2504       /* Set up and read from the pipe.  */
    2505 
    2506       maxlen = 200;
    2507       buffer = xmalloc (maxlen + 1);
    2508 
    2509       /* Read from the pipe until it gets EOF.  */
    2510       for (i = 0; ; i += cc)
    2511         {
    2512           if (i == maxlen)
    2513             {
    2514               maxlen += 512;
    2515               buffer = xrealloc (buffer, maxlen + 1);
    2516             }
    2517 
    2518           EINTRLOOP (cc, read (pipedes[0], &buffer[i], maxlen - i));
    2519           if (cc <= 0)
    2520             break;
    2521         }
    2522       buffer[i] = '\0';
    2523 
    2524       /* Close the read side of the pipe.  */
     2627    shell_function_completed = 0;
     2628
     2629    /* Free the storage only the child needed.  */
     2630    free (command_argv[0]);
     2631    free (command_argv);
     2632
     2633    /* Close the write side of the pipe.  We test for -1, since
     2634      pipedes[1] is -1 on MS-Windows, and some versions of MS
     2635       libraries barf when 'close' is called with -1.  */
     2636    if (pipedes[1] >= 0)
     2637      close (pipedes[1]);
     2638#endif
     2639
     2640    /* Set up and read from the pipe.  */
     2641
     2642    maxlen = 200;
     2643    buffer = xmalloc (maxlen + 1);
     2644
     2645    /* Read from the pipe until it gets EOF.  */
     2646    for (i = 0; ; i += cc)
     2647      {
     2648        if (i == maxlen)
     2649          {
     2650            maxlen += 512;
     2651            buffer = xrealloc (buffer, maxlen + 1);
     2652          }
     2653
     2654        EINTRLOOP (cc, read (pipedes[0], &buffer[i], maxlen - i));
     2655        if (cc <= 0)
     2656          break;
     2657      }
     2658    buffer[i] = '\0';
     2659
     2660    /* Close the read side of the pipe.  */
    25252661#ifdef  __MSDOS__
    2526       if (fpipe)
    2527         (void) pclose (fpipe);
     2662    if (fpipe)
     2663      {
     2664        int st = pclose (fpipe);
     2665        shell_completed (st, 0);
     2666      }
    25282667#else
    25292668# ifdef _MSC_VER /* Avoid annoying msvcrt when debugging. (bird) */
    25302669      if (pipedes[0] != -1)
    25312670# endif
    2532       (void) close (pipedes[0]);
    2533 #endif
    2534 
    2535       /* Loop until child_handler or reap_children()  sets
    2536          shell_function_completed to the status of our child shell.  */
    2537       while (shell_function_completed == 0)
    2538         reap_children (1, 0);
    2539 
    2540       if (batch_filename) {
    2541         DB (DB_VERBOSE, (_("Cleaning up temporary batch file %s\n"),
    2542                        batch_filename));
    2543         remove (batch_filename);
    2544         free (batch_filename);
     2671        (void) close (pipedes[0]);
     2672#endif
     2673
     2674    /* Loop until child_handler or reap_children()  sets
     2675       shell_function_completed to the status of our child shell.  */
     2676    while (shell_function_completed == 0)
     2677      reap_children (1, 0);
     2678
     2679    if (batch_filename)
     2680      {
     2681        DB (DB_VERBOSE, (_("Cleaning up temporary batch file %s\n"),
     2682                         batch_filename));
     2683        remove (batch_filename);
     2684        free (batch_filename);
    25452685      }
    2546       shell_function_pid = 0;
    2547 
    2548       /* The child_handler function will set shell_function_completed
    2549          to 1 when the child dies normally, or to -1 if it
    2550          dies with status 127, which is most likely an exec fail.  */
    2551 
    2552       if (shell_function_completed == -1)
    2553         {
    2554           /* This likely means that the execvp failed, so we should just
    2555              write the error message in the pipe from the child.  */
    2556           fputs (buffer, stderr);
    2557           fflush (stderr);
    2558         }
    2559       else
    2560         {
    2561           /* The child finished normally.  Replace all newlines in its output
    2562              with spaces, and put that in the variable output buffer.  */
    2563           fold_newlines (buffer, &i);
    2564           o = variable_buffer_output (o, buffer, i);
    2565         }
    2566 
    2567       free (buffer);
    2568     }
    2569 
    2570   return o;
    2571 }
    2572 
    2573 #else   /* _AMIGA */
     2686    shell_function_pid = 0;
     2687
     2688    /* shell_completed() will set shell_function_completed to 1 when the
     2689       child dies normally, or to -1 if it dies with status 127, which is
     2690      most likely an exec fail.  */
     2691
     2692    if (shell_function_completed == -1)
     2693      {
     2694        /* This likely means that the execvp failed, so we should just
     2695           write the error message in the pipe from the child.  */
     2696        fputs (buffer, stderr);
     2697        fflush (stderr);
     2698      }
     2699    else
     2700      {
     2701        /* The child finished normally.  Replace all newlines in its output
     2702           with spaces, and put that in the variable output buffer.  */
     2703        fold_newlines (buffer, &i, trim_newlines);
     2704        o = variable_buffer_output (o, buffer, i);
     2705      }
     2706
     2707    free (buffer);
     2708  }
     2709
     2710  return o;
     2711}
     2712
     2713#else   /* _AMIGA */
    25742714
    25752715/* Do the Amiga version of func_shell.  */
    25762716
    2577 static char *
    2578 func_shell (char *o, char **argv, const char *funcname)
     2717char *
     2718func_shell_base (char *o, char **argv, int trim_newlines)
    25792719{
    25802720  /* Amiga can't fork nor spawn, but I can start a program with
     
    26062746
    26072747  /* Note the mktemp() is a security hole, but this only runs on Amiga.
    2608      Ideally we would use main.c:open_tmpfile(), but this uses a special
     2748     Ideally we would use output_tmpfile(), but this uses a special
    26092749     Open(), not fopen(), and I'm not familiar enough with the code to mess
    26102750     with it.  */
     
    26412781    {
    26422782      if (i == maxlen)
    2643         {
    2644           maxlen += 512;
    2645           buffer = xrealloc (buffer, maxlen + 1);
    2646         }
     2783        {
     2784          maxlen += 512;
     2785          buffer = xrealloc (buffer, maxlen + 1);
     2786        }
    26472787
    26482788      cc = Read (child_stdout, &buffer[i], maxlen - i);
    26492789      if (cc > 0)
    2650         i += cc;
     2790        i += cc;
    26512791    } while (cc > 0);
    26522792
    26532793  Close (child_stdout);
    26542794
    2655   fold_newlines (buffer, &i);
     2795  fold_newlines (buffer, &i, trim_newlines);
    26562796  o = variable_buffer_output (o, buffer, i);
    26572797  free (buffer);
     
    26592799}
    26602800#endif  /* _AMIGA */
     2801
     2802static char *
     2803func_shell (char *o, char **argv, const char *funcname UNUSED)
     2804{
     2805  return func_shell_base (o, argv, 1);
     2806}
    26612807#endif  /* !VMS */
    26622808
     
    26642810
    26652811/*
    2666   equality. Return is string-boolean, ie, the empty string is false.
     2812  equality. Return is string-boolean, i.e., the empty string is false.
    26672813 */
    26682814static char *
     
    26832829  const char *s = argv[0];
    26842830  int result = 0;
    2685   while (isspace ((unsigned char)*s))
    2686     s++;
     2831  NEXT_TOKEN (s);
    26872832  result = ! (*s);
    26882833  o = variable_buffer_output (o,  result ? "1" : "", result);
     
    26922837
    26932838
    2694 #ifdef CONFIG_WITH_STRING_FUNCTIONS
    2695 /*
    2696   $(length string)
    2697 
    2698   XXX: This doesn't take multibyte locales into account.
    2699  */
    2700 static char *
    2701 func_length (char *o, char **argv, const char *funcname UNUSED)
    2702 {
    2703   size_t len = strlen (argv[0]);
    2704   return math_int_to_variable_buffer (o, len);
    2705 }
    2706 
    2707 /*
    2708   $(length-var var)
    2709 
    2710   XXX: This doesn't take multibyte locales into account.
    2711  */
    2712 static char *
    2713 func_length_var (char *o, char **argv, const char *funcname UNUSED)
    2714 {
    2715   struct variable *var = lookup_variable (argv[0], strlen (argv[0]));
    2716   return math_int_to_variable_buffer (o, var ? var->value_length : 0);
    2717 }
    2718 
    2719 
    2720 /* func_insert and func_substr helper. */
    2721 static char *
    2722 helper_pad (char *o, size_t to_add, const char *pad, size_t pad_len)
    2723 {
    2724   while (to_add > 0)
    2725     {
    2726       size_t size = to_add > pad_len ? pad_len : to_add;
    2727       o = variable_buffer_output (o, pad, size);
    2728       to_add -= size;
    2729     }
    2730   return o;
    2731 }
    2732 
    2733 /*
    2734   $(insert in, str[, n[, length[, pad]]])
    2735 
    2736   XXX: This doesn't take multibyte locales into account.
    2737  */
    2738 static char *
    2739 func_insert (char *o, char **argv, const char *funcname UNUSED)
    2740 {
    2741   const char *in      = argv[0];
    2742   math_int    in_len  = (math_int)strlen (in);
    2743   const char *str     = argv[1];
    2744   math_int    str_len = (math_int)strlen (str);
    2745   math_int    n       = 0;
    2746   math_int    length  = str_len;
    2747   const char *pad     = "                ";
    2748   size_t      pad_len = 16;
    2749   size_t      i;
    2750 
    2751   if (argv[2] != NULL)
    2752     {
    2753       n = math_int_from_string (argv[2]);
    2754       if (n > 0)
    2755         n--;            /* one-origin */
    2756       else if (n == 0)
    2757         n = str_len;    /* append */
    2758       else
    2759         { /* n < 0: from the end */
    2760           n = str_len + n;
    2761           if (n < 0)
    2762             n = 0;
    2763         }
    2764       if (n > 16*1024*1024) /* 16MB */
    2765         fatal (NILF, _("$(insert ): n=%s is out of bounds\n"), argv[2]);
    2766 
    2767       if (argv[3] != NULL)
    2768         {
    2769           length = math_int_from_string (argv[3]);
    2770           if (length < 0 || length > 16*1024*1024 /* 16MB */)
    2771               fatal (NILF, _("$(insert ): length=%s is out of bounds\n"), argv[3]);
    2772 
    2773           if (argv[4] != NULL)
    2774             {
    2775               const char *tmp = argv[4];
    2776               for (i = 0; tmp[i] == ' '; i++)
    2777                 /* nothing */;
    2778               if (tmp[i] != '\0')
    2779                 {
    2780                   pad = argv[4];
    2781                   pad_len = strlen (pad);
    2782                 }
    2783               /* else: it was all default spaces. */
    2784             }
    2785         }
    2786     }
    2787 
    2788   /* the head of the original string */
    2789   if (n > 0)
    2790     {
    2791       if (n <= str_len)
    2792         o = variable_buffer_output (o, str, n);
    2793       else
    2794         {
    2795           o = variable_buffer_output (o, str, str_len);
    2796           o = helper_pad (o, n - str_len, pad, pad_len);
    2797         }
    2798     }
    2799 
    2800   /* insert the string */
    2801   if (length <= in_len)
    2802     o = variable_buffer_output (o, in, length);
    2803   else
    2804     {
    2805       o = variable_buffer_output (o, in, in_len);
    2806       o = helper_pad (o, length - in_len, pad, pad_len);
    2807     }
    2808 
    2809   /* the tail of the original string */
    2810   if (n < str_len)
    2811     o = variable_buffer_output (o, str + n, str_len - n);
    2812 
    2813   return o;
    2814 }
    2815 
    2816 
    2817 /*
    2818   $(pos needle, haystack[, start])
    2819   $(lastpos needle, haystack[, start])
    2820 
    2821   XXX: This doesn't take multibyte locales into account.
    2822  */
    2823 static char *
    2824 func_pos (char *o, char **argv, const char *funcname UNUSED)
    2825 {
    2826   const char *needle       = *argv[0] ? argv[0] : " ";
    2827   size_t      needle_len   = strlen (needle);
    2828   const char *haystack     = argv[1];
    2829   size_t      haystack_len = strlen (haystack);
    2830   math_int    start        = 0;
    2831   const char *hit;
    2832 
    2833   if (argv[2] != NULL)
    2834     {
    2835       start = math_int_from_string (argv[2]);
    2836       if (start > 0)
    2837         start--;            /* one-origin */
    2838       else if (start < 0)
    2839         start = haystack_len + start; /* from the end */
    2840       if (start < 0 || start + needle_len > haystack_len)
    2841         return math_int_to_variable_buffer (o, 0);
    2842     }
    2843   else if (funcname[0] == 'l')
    2844     start = haystack_len - 1;
    2845 
    2846   /* do the searching */
    2847   if (funcname[0] != 'l')
    2848     { /* pos */
    2849       if (needle_len == 1)
    2850         hit = strchr (haystack + start, *needle);
    2851       else
    2852         hit = strstr (haystack + start, needle);
    2853     }
    2854   else
    2855     { /* last pos */
    2856       int    ch  = *needle;
    2857       size_t off = start + 1;
    2858 
    2859       hit = NULL;
    2860       while (off-- > 0)
    2861         {
    2862           if (   haystack[off] == ch
    2863               && (   needle_len == 1
    2864                   || strncmp (&haystack[off], needle, needle_len) == 0))
    2865             {
    2866               hit = haystack + off;
    2867               break;
    2868             }
    2869         }
    2870     }
    2871 
    2872   return math_int_to_variable_buffer (o, hit ? hit - haystack + 1 : 0);
    2873 }
    2874 
    2875 
    2876 /*
    2877   $(substr str, start[, length[, pad]])
    2878 
    2879   XXX: This doesn't take multibyte locales into account.
    2880  */
    2881 static char *
    2882 func_substr (char *o, char **argv, const char *funcname UNUSED)
    2883 {
    2884   const char *str     = argv[0];
    2885   math_int    str_len = (math_int)strlen (str);
    2886   math_int    start   = math_int_from_string (argv[1]);
    2887   math_int    length  = 0;
    2888   const char *pad     = NULL;
    2889   size_t      pad_len = 0;
    2890 
    2891   if (argv[2] != NULL)
    2892     {
    2893       if (argv[3] != NULL)
    2894         {
    2895           pad = argv[3];
    2896           for (pad_len = 0; pad[pad_len] == ' '; pad_len++)
    2897             /* nothing */;
    2898           if (pad[pad_len] != '\0')
    2899               pad_len = strlen (pad);
    2900           else
    2901             {
    2902               pad = "                ";
    2903               pad_len = 16;
    2904             }
    2905         }
    2906       length = math_int_from_string (argv[2]);
    2907       if (pad != NULL && length > 16*1024*1024 /* 16MB */)
    2908         fatal (NILF, _("$(substr ): length=%s is out of bounds\n"), argv[2]);
    2909       if (pad != NULL && length < 0)
    2910         fatal (NILF, _("$(substr ): negative length (%s) and padding doesn't mix.\n"), argv[2]);
    2911       if (length == 0)
    2912         return o;
    2913     }
    2914 
    2915   /* Note that negative start is and length are used for referencing from the
    2916      end of the string. */
    2917   if (pad == NULL)
    2918     {
    2919       if (start > 0)
    2920         start--;      /* one-origin */
    2921       else
    2922         {
    2923           start = str_len + start;
    2924           if (start <= 0)
    2925             {
    2926               if (length < 0)
    2927                 return o;
    2928               start += length;
    2929               if (start <= 0)
    2930                 return o;
    2931               length = start;
    2932               start = 0;
    2933             }
    2934         }
    2935 
    2936       if (start >= str_len)
    2937         return o;
    2938       if (length == 0)
    2939         length = str_len - start;
    2940       else if (length < 0)
    2941         {
    2942           if (str_len <= -length)
    2943             return o;
    2944           length += str_len;
    2945           if (length <= start)
    2946             return o;
    2947           length -= start;
    2948         }
    2949       else if (start + length > str_len)
    2950         length = str_len - start;
    2951 
    2952       o = variable_buffer_output (o, str + start, length);
    2953     }
    2954   else
    2955     {
    2956       if (start > 0)
    2957         {
    2958           start--;      /* one-origin */
    2959           if (start >= str_len)
    2960             return length ? helper_pad (o, length, pad, pad_len) : o;
    2961           if (length == 0)
    2962             length = str_len - start;
    2963         }
    2964       else
    2965         {
    2966           start = str_len + start;
    2967           if (start <= 0)
    2968             {
    2969               if (start + length <= 0)
    2970                 return length ? helper_pad (o, length, pad, pad_len) : o;
    2971               o = helper_pad (o, -start, pad, pad_len);
    2972               return variable_buffer_output (o, str, length + start);
    2973             }
    2974           if (length == 0)
    2975             length = str_len - start;
    2976         }
    2977       if (start + length <= str_len)
    2978         o = variable_buffer_output (o, str + start, length);
    2979       else
    2980         {
    2981           o = variable_buffer_output (o, str + start, str_len - start);
    2982           o = helper_pad (o, start + length - str_len, pad, pad_len);
    2983         }
    2984     }
    2985 
    2986   return o;
    2987 }
    2988 
    2989 
    2990 /*
    2991   $(translate string, from-set[, to-set[, pad-char]])
    2992 
    2993   XXX: This doesn't take multibyte locales into account.
    2994  */
    2995 static char *
    2996 func_translate (char *o, char **argv, const char *funcname UNUSED)
    2997 {
    2998   const unsigned char *str      = (const unsigned char *)argv[0];
    2999   const unsigned char *from_set = (const unsigned char *)argv[1];
    3000   const char          *to_set   = argv[2] != NULL ? argv[2] : "";
    3001   char                 trans_tab[1 << CHAR_BIT];
    3002   int                  i;
    3003   char                 ch;
    3004 
    3005   /* init the array. */
    3006   for (i = 0; i < (1 << CHAR_BIT); i++)
    3007     trans_tab[i] = i;
    3008 
    3009   while (   (i = *from_set) != '\0'
    3010          && (ch = *to_set) != '\0')
    3011     {
    3012       trans_tab[i] = ch;
    3013       from_set++;
    3014       to_set++;
    3015     }
    3016 
    3017   if (i != '\0')
    3018     {
    3019       ch = '\0';                        /* no padding == remove char */
    3020       if (argv[2] != NULL && argv[3] != NULL)
    3021         {
    3022           ch = argv[3][0];
    3023           if (ch && argv[3][1])
    3024             fatal (NILF, _("$(translate ): pad=`%s' expected a single char\n"), argv[3]);
    3025           if (ch == '\0')               /* no char == space */
    3026             ch = ' ';
    3027         }
    3028       while ((i = *from_set++) != '\0')
    3029         trans_tab[i] = ch;
    3030     }
    3031 
    3032   /* do the translation */
    3033   while ((i = *str++) != '\0')
    3034     {
    3035       ch = trans_tab[i];
    3036       if (ch)
    3037         o = variable_buffer_output (o, &ch, 1);
    3038     }
    3039 
    3040   return o;
    3041 }
    3042 #endif /* CONFIG_WITH_STRING_FUNCTIONS */
    3043 
    3044 
    3045 #ifdef CONFIG_WITH_LAZY_DEPS_VARS
    3046 
    3047 /* This is also in file.c (bad).  */
    3048 # if VMS
    3049 #  define FILE_LIST_SEPARATOR ','
     2839
     2840#ifdef HAVE_DOS_PATHS
     2841# ifdef __CYGWIN__
     2842#  define IS_ABSOLUTE(n) ((n[0] && n[1] == ':') || STOP_SET (n[0], MAP_DIRSEP))
    30502843# else
    3051 #  define FILE_LIST_SEPARATOR ' '
     2844#  define IS_ABSOLUTE(n) (n[0] && n[1] == ':')
    30522845# endif
    3053 
    3054 /* Implements $^ and $+.
    3055 
    3056    The first comes with FUNCNAME 'deps', the second as 'deps-all'.
    3057 
    3058    If no second argument is given, or if it's empty, or if it's zero,
    3059    all dependencies will be returned.  If the second argument is non-zero
    3060    the dependency at that position will be returned.  If the argument is
    3061    negative a fatal error is thrown.  */
    3062 static char *
    3063 func_deps (char *o, char **argv, const char *funcname)
    3064 {
    3065   unsigned int idx = 0;
    3066   struct file *file;
    3067 
    3068   /* Handle the argument if present. */
    3069 
    3070   if (argv[1])
    3071     {
    3072       char *p = argv[1];
    3073       while (isspace ((unsigned int)*p))
    3074         p++;
    3075       if (*p != '\0')
    3076         {
    3077           char *n;
    3078           long l = strtol (p, &n, 0);
    3079           while (isspace ((unsigned int)*n))
    3080             n++;
    3081           idx = l;
    3082           if (*n != '\0' || l < 0 || (long)idx != l)
    3083             fatal (NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
    3084         }
    3085     }
    3086 
    3087   /* Find the file and select the list corresponding to FUNCNAME. */
    3088 
    3089   file = lookup_file (argv[0]);
    3090   if (file)
    3091     {
    3092       struct dep *deps;
    3093       struct dep *d;
    3094       if (funcname[4] == '\0')
    3095         {
    3096           deps = file->deps_no_dupes;
    3097           if (!deps && file->deps)
    3098             deps = file->deps = create_uniqute_deps_chain (file->deps);
    3099         }
    3100       else
    3101         deps = file->deps;
    3102 
    3103       if (   file->double_colon
    3104           && (   file->double_colon != file
    3105               || file->last != file))
    3106           error (NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
    3107                  funcname, file->name);
    3108 
    3109       if (idx == 0 /* all */)
    3110         {
    3111           unsigned int total_len = 0;
    3112 
    3113           /* calc the result length. */
    3114 
    3115           for (d = deps; d; d = d->next)
    3116             if (!d->ignore_mtime)
    3117               {
    3118                 const char *c = dep_name (d);
    3119 
    3120 #ifndef NO_ARCHIVES
    3121                 if (ar_name (c))
    3122                   {
    3123                     c = strchr (c, '(') + 1;
    3124                     total_len += strlen (c);
    3125                   }
    3126                 else
    3127 #elif defined (CONFIG_WITH_STRCACHE2)
    3128                   total_len += strcache2_get_len (&file_strcache, c) + 1;
    3129 #else
    3130                   total_len += strlen (c) + 1;
    3131 #endif
    3132               }
    3133 
    3134           if (total_len)
    3135             {
    3136               /* prepare the variable buffer dude wrt to the output size and
    3137                  pass along the strings.  */
    3138 
    3139               o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
    3140 
    3141               for (d = deps; d; d = d->next)
    3142                 if (!d->ignore_mtime)
    3143                   {
    3144                     unsigned int len;
    3145                     const char *c = dep_name (d);
    3146 
    3147 #ifndef NO_ARCHIVES
    3148                     if (ar_name (c))
    3149                       {
    3150                         c = strchr (c, '(') + 1;
    3151                         len = strlen (c);
    3152                       }
    3153                     else
    3154 #elif defined (CONFIG_WITH_STRCACHE2)
    3155                       len = strcache2_get_len (&file_strcache, c) + 1;
    3156 #else
    3157                       len = strlen (c) + 1;
    3158 #endif
    3159                     o = variable_buffer_output (o, c, len);
    3160                     o[-1] = FILE_LIST_SEPARATOR;
    3161                   }
    3162 
    3163                 --o;        /* nuke the last list separator */
    3164                 *o = '\0';
    3165             }
    3166         }
    3167       else
    3168         {
    3169           /* Dependency given by index.  */
    3170 
    3171           for (d = deps; d; d = d->next)
    3172             if (!d->ignore_mtime)
    3173               {
    3174                 if (--idx == 0) /* 1 based indexing */
    3175                   {
    3176                     unsigned int len;
    3177                     const char *c = dep_name (d);
    3178 
    3179 #ifndef NO_ARCHIVES
    3180                     if (ar_name (c))
    3181                       {
    3182                         c = strchr (c, '(') + 1;
    3183                         len = strlen (c) - 1;
    3184                       }
    3185                     else
    3186 #elif defined (CONFIG_WITH_STRCACHE2)
    3187                       len = strcache2_get_len (&file_strcache, c);
    3188 #else
    3189                       len = strlen (c);
    3190 #endif
    3191                     o = variable_buffer_output (o, c, len);
    3192                     break;
    3193                   }
    3194               }
    3195         }
    3196     }
    3197 
    3198   return o;
    3199 }
    3200 
    3201 /* Implements $?.
    3202 
    3203    If no second argument is given, or if it's empty, or if it's zero,
    3204    all dependencies will be returned.  If the second argument is non-zero
    3205    the dependency at that position will be returned.  If the argument is
    3206    negative a fatal error is thrown.  */
    3207 static char *
    3208 func_deps_newer (char *o, char **argv, const char *funcname)
    3209 {
    3210   unsigned int idx = 0;
    3211   struct file *file;
    3212 
    3213   /* Handle the argument if present. */
    3214 
    3215   if (argv[1])
    3216     {
    3217       char *p = argv[1];
    3218       while (isspace ((unsigned int)*p))
    3219         p++;
    3220       if (*p != '\0')
    3221         {
    3222           char *n;
    3223           long l = strtol (p, &n, 0);
    3224           while (isspace ((unsigned int)*n))
    3225             n++;
    3226           idx = l;
    3227           if (*n != '\0' || l < 0 || (long)idx != l)
    3228             fatal (NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
    3229         }
    3230     }
    3231 
    3232   /* Find the file. */
    3233 
    3234   file = lookup_file (argv[0]);
    3235   if (file)
    3236     {
    3237       struct dep *deps = file->deps;
    3238       struct dep *d;
    3239 
    3240       if (   file->double_colon
    3241           && (   file->double_colon != file
    3242               || file->last != file))
    3243           error (NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
    3244                  funcname, file->name);
    3245 
    3246       if (idx == 0 /* all */)
    3247         {
    3248           unsigned int total_len = 0;
    3249 
    3250           /* calc the result length. */
    3251 
    3252           for (d = deps; d; d = d->next)
    3253             if (!d->ignore_mtime && d->changed)
    3254               {
    3255                 const char *c = dep_name (d);
    3256 
    3257 #ifndef NO_ARCHIVES
    3258                 if (ar_name (c))
    3259                   {
    3260                     c = strchr (c, '(') + 1;
    3261                     total_len += strlen (c);
    3262                   }
    3263                 else
    3264 #elif defined (CONFIG_WITH_STRCACHE2)
    3265                   total_len += strcache2_get_len (&file_strcache, c) + 1;
    3266 #else
    3267                   total_len += strlen (c) + 1;
    3268 #endif
    3269               }
    3270 
    3271           if (total_len)
    3272             {
    3273               /* prepare the variable buffer dude wrt to the output size and
    3274                  pass along the strings.  */
    3275 
    3276               o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
    3277 
    3278               for (d = deps; d; d = d->next)
    3279                 if (!d->ignore_mtime && d->changed)
    3280                   {
    3281                     unsigned int len;
    3282                     const char *c = dep_name (d);
    3283 
    3284 #ifndef NO_ARCHIVES
    3285                     if (ar_name (c))
    3286                       {
    3287                         c = strchr (c, '(') + 1;
    3288                         len = strlen (c);
    3289                       }
    3290                     else
    3291 #elif defined (CONFIG_WITH_STRCACHE2)
    3292                       len = strcache2_get_len (&file_strcache, c) + 1;
    3293 #else
    3294                       len = strlen (c) + 1;
    3295 #endif
    3296                     o = variable_buffer_output (o, c, len);
    3297                     o[-1] = FILE_LIST_SEPARATOR;
    3298                   }
    3299 
    3300                 --o;        /* nuke the last list separator */
    3301                 *o = '\0';
    3302             }
    3303         }
    3304       else
    3305         {
    3306           /* Dependency given by index.  */
    3307 
    3308           for (d = deps; d; d = d->next)
    3309             if (!d->ignore_mtime && d->changed)
    3310               {
    3311                 if (--idx == 0) /* 1 based indexing */
    3312                   {
    3313                     unsigned int len;
    3314                     const char *c = dep_name (d);
    3315 
    3316 #ifndef NO_ARCHIVES
    3317                     if (ar_name (c))
    3318                       {
    3319                         c = strchr (c, '(') + 1;
    3320                         len = strlen (c) - 1;
    3321                       }
    3322                     else
    3323 #elif defined (CONFIG_WITH_STRCACHE2)
    3324                       len = strcache2_get_len (&file_strcache, c);
    3325 #else
    3326                       len = strlen (c);
    3327 #endif
    3328                     o = variable_buffer_output (o, c, len);
    3329                     break;
    3330                   }
    3331               }
    3332         }
    3333     }
    3334 
    3335   return o;
    3336 }
    3337 
    3338 /* Implements $|, the order only dependency list.
    3339 
    3340    If no second argument is given, or if it's empty, or if it's zero,
    3341    all dependencies will be returned.  If the second argument is non-zero
    3342    the dependency at that position will be returned.  If the argument is
    3343    negative a fatal error is thrown.  */
    3344 static char *
    3345 func_deps_order_only (char *o, char **argv, const char *funcname)
    3346 {
    3347   unsigned int idx = 0;
    3348   struct file *file;
    3349 
    3350   /* Handle the argument if present. */
    3351 
    3352   if (argv[1])
    3353     {
    3354       char *p = argv[1];
    3355       while (isspace ((unsigned int)*p))
    3356         p++;
    3357       if (*p != '\0')
    3358         {
    3359           char *n;
    3360           long l = strtol (p, &n, 0);
    3361           while (isspace ((unsigned int)*n))
    3362             n++;
    3363           idx = l;
    3364           if (*n != '\0' || l < 0 || (long)idx != l)
    3365             fatal (NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
    3366         }
    3367     }
    3368 
    3369   /* Find the file. */
    3370 
    3371   file = lookup_file (argv[0]);
    3372   if (file)
    3373     {
    3374       struct dep *deps = file->deps;
    3375       struct dep *d;
    3376 
    3377       if (   file->double_colon
    3378           && (   file->double_colon != file
    3379               || file->last != file))
    3380           error (NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
    3381                  funcname, file->name);
    3382 
    3383       if (idx == 0 /* all */)
    3384         {
    3385           unsigned int total_len = 0;
    3386 
    3387           /* calc the result length. */
    3388 
    3389           for (d = deps; d; d = d->next)
    3390             if (d->ignore_mtime)
    3391               {
    3392                 const char *c = dep_name (d);
    3393 
    3394 #ifndef NO_ARCHIVES
    3395                 if (ar_name (c))
    3396                   {
    3397                     c = strchr (c, '(') + 1;
    3398                     total_len += strlen (c);
    3399                   }
    3400                 else
    3401 #elif defined (CONFIG_WITH_STRCACHE2)
    3402                   total_len += strcache2_get_len (&file_strcache, c) + 1;
    3403 #else
    3404                   total_len += strlen (c) + 1;
    3405 #endif
    3406               }
    3407 
    3408           if (total_len)
    3409             {
    3410               /* prepare the variable buffer dude wrt to the output size and
    3411                  pass along the strings.  */
    3412 
    3413               o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
    3414 
    3415               for (d = deps; d; d = d->next)
    3416                 if (d->ignore_mtime)
    3417                   {
    3418                     unsigned int len;
    3419                     const char *c = dep_name (d);
    3420 
    3421 #ifndef NO_ARCHIVES
    3422                     if (ar_name (c))
    3423                       {
    3424                         c = strchr (c, '(') + 1;
    3425                         len = strlen (c);
    3426                       }
    3427                     else
    3428 #elif defined (CONFIG_WITH_STRCACHE2)
    3429                       len = strcache2_get_len (&file_strcache, c) + 1;
    3430 #else
    3431                       len = strlen (c) + 1;
    3432 #endif
    3433                     o = variable_buffer_output (o, c, len);
    3434                     o[-1] = FILE_LIST_SEPARATOR;
    3435                   }
    3436 
    3437                 --o;        /* nuke the last list separator */
    3438                 *o = '\0';
    3439             }
    3440         }
    3441       else
    3442         {
    3443           /* Dependency given by index.  */
    3444 
    3445           for (d = deps; d; d = d->next)
    3446             if (d->ignore_mtime)
    3447               {
    3448                 if (--idx == 0) /* 1 based indexing */
    3449                   {
    3450                     unsigned int len;
    3451                     const char *c = dep_name (d);
    3452 
    3453 #ifndef NO_ARCHIVES
    3454                     if (ar_name (c))
    3455                       {
    3456                         c = strchr (c, '(') + 1;
    3457                         len = strlen (c) - 1;
    3458                       }
    3459                     else
    3460 #elif defined (CONFIG_WITH_STRCACHE2)
    3461                       len = strcache2_get_len (&file_strcache, c);
    3462 #else
    3463                       len = strlen (c);
    3464 #endif
    3465                     o = variable_buffer_output (o, c, len);
    3466                     break;
    3467                   }
    3468               }
    3469         }
    3470     }
    3471 
    3472   return o;
    3473 }
    3474 #endif /* CONFIG_WITH_LAZY_DEPS_VARS */
    3475 
    3476 
    3477 
    3478 #ifdef CONFIG_WITH_DEFINED
    3479 /* Similar to ifdef. */
    3480 static char *
    3481 func_defined (char *o, char **argv, const char *funcname UNUSED)
    3482 {
    3483   struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
    3484   int result = v != NULL && *v->value != '\0';
    3485   o = variable_buffer_output (o,  result ? "1" : "", result);
    3486   return o;
    3487 }
    3488 #endif /* CONFIG_WITH_DEFINED*/
    3489 
    3490 
    3491 
    3492 #ifdef HAVE_DOS_PATHS
    3493 #define IS_ABSOLUTE(n) (n[0] && n[1] == ':')
    3494 #define ROOT_LEN 3
     2846# define ROOT_LEN 3
    34952847#else
    34962848#define IS_ABSOLUTE(n) (n[0] == '/')
     
    34982850#endif
    34992851
    3500 /* Return the absolute name of file NAME which does not contain any `.',
    3501    `..' components nor any repeated path separators ('/').   */
     2852/* Return the absolute name of file NAME which does not contain any '.',
     2853   '..' components nor any repeated path separators ('/').   */
    35022854#ifdef KMK
    35032855char *
     
    35402892      /* It is unlikely we would make it until here but just to make sure. */
    35412893      if (!starting_directory)
    3542         return NULL;
     2894        return NULL;
    35432895
    35442896      strcpy (apath, starting_directory);
    35452897
    35462898#ifdef HAVE_DOS_PATHS
    3547       if (IS_PATHSEP(name[0]))
    3548         {
    3549           if (IS_PATHSEP(name[1]))
    3550             {
    3551               /* A UNC.  Don't prepend a drive letter.  */
    3552               apath[0] = name[0];
    3553               apath[1] = name[1];
    3554               root_len = 2;
    3555             }
    3556           /* We have /foo, an absolute file name except for the drive
    3557              letter.  Assume the missing drive letter is the current
    3558              drive, which we can get if we remove from starting_directory
    3559              everything past the root directory.  */
    3560           apath[root_len] = '\0';
    3561         }
     2899      if (STOP_SET (name[0], MAP_DIRSEP))
     2900        {
     2901          if (STOP_SET (name[1], MAP_DIRSEP))
     2902            {
     2903              /* A UNC.  Don't prepend a drive letter.  */
     2904              apath[0] = name[0];
     2905              apath[1] = name[1];
     2906              root_len = 2;
     2907            }
     2908          /* We have /foo, an absolute file name except for the drive
     2909             letter.  Assume the missing drive letter is the current
     2910             drive, which we can get if we remove from starting_directory
     2911             everything past the root directory.  */
     2912          apath[root_len] = '\0';
     2913        }
    35622914#endif
    35632915
     
    35662918  else
    35672919    {
     2920#if defined(__CYGWIN__) && defined(HAVE_DOS_PATHS)
     2921      if (STOP_SET (name[0], MAP_DIRSEP))
     2922        root_len = 1;
     2923#endif
    35682924      strncpy (apath, name, root_len);
    35692925      apath[root_len] = '\0';
     
    35722928      name += root_len;
    35732929#ifdef HAVE_DOS_PATHS
    3574       if (!IS_PATHSEP(apath[2]))
    3575         {
    3576           /* Convert d:foo into d:./foo and increase root_len.  */
    3577           apath[2] = '.';
    3578           apath[3] = '/';
    3579           dest++;
    3580           root_len++;
    3581           /* strncpy above copied one character too many.  */
    3582           name--;
    3583         }
     2930      if (! STOP_SET (apath[root_len - 1], MAP_DIRSEP))
     2931        {
     2932          /* Convert d:foo into d:./foo and increase root_len.  */
     2933          apath[2] = '.';
     2934          apath[3] = '/';
     2935          dest++;
     2936          root_len++;
     2937          /* strncpy above copied one character too many.  */
     2938          name--;
     2939        }
    35842940      else
    3585         apath[2] = '/'; /* make sure it's a forward slash */
     2941        apath[root_len - 1] = '/'; /* make sure it's a forward slash */
    35862942#endif
    35872943    }
     
    35922948
    35932949      /* Skip sequence of multiple path-separators.  */
    3594       while (IS_PATHSEP(*start))
    3595         ++start;
     2950      while (STOP_SET (*start, MAP_DIRSEP))
     2951        ++start;
    35962952
    35972953      /* Find end of path component.  */
    3598       for (end = start; *end != '\0' && !IS_PATHSEP(*end); ++end)
     2954      for (end = start; ! STOP_SET (*end, MAP_DIRSEP|MAP_NUL); ++end)
    35992955        ;
    36002956
     
    36022958
    36032959      if (len == 0)
    3604         break;
     2960        break;
    36052961      else if (len == 1 && start[0] == '.')
    3606         /* nothing */;
     2962        /* nothing */;
    36072963      else if (len == 2 && start[0] == '.' && start[1] == '.')
    3608         {
    3609           /* Back up to previous component, ignore if at root already.  */
    3610           if (dest > apath + root_len)
    3611             for (--dest; !IS_PATHSEP(dest[-1]); --dest);
    3612         }
     2964        {
     2965          /* Back up to previous component, ignore if at root already.  */
     2966          if (dest > apath + root_len)
     2967            for (--dest; ! STOP_SET (dest[-1], MAP_DIRSEP); --dest)
     2968              ;
     2969        }
    36132970      else
    3614         {
    3615           if (!IS_PATHSEP(dest[-1]))
     2971        {
     2972          if (! STOP_SET (dest[-1], MAP_DIRSEP))
    36162973            *dest++ = '/';
    36172974
    3618           if (dest + len >= apath_limit)
     2975          if (dest + len >= apath_limit)
    36192976            return NULL;
    36202977
    3621           dest = memcpy (dest, start, len);
     2978          dest = memcpy (dest, start, len);
    36222979          dest += len;
    3623           *dest = '\0';
    3624         }
     2980          *dest = '\0';
     2981        }
    36252982    }
    36262983#endif /* !WINDOWS32 && !__OS2__ */
    36272984
    36282985  /* Unless it is root strip trailing separator.  */
    3629   if (dest > apath + root_len && IS_PATHSEP(dest[-1]))
     2986  if (dest > apath + root_len && STOP_SET (dest[-1], MAP_DIRSEP))
    36302987    --dest;
    36312988
     
    36443001  int doneany = 0;
    36453002  unsigned int len = 0;
    3646 #ifndef HAVE_REALPATH
    3647   struct stat st;
    3648 #endif
    3649   PATH_VAR (in);
    3650   PATH_VAR (out);
    36513003
    36523004  while ((path = find_next_token (&p, &len)) != 0)
     
    36543006      if (len < GET_PATH_MAX)
    36553007        {
     3008          char *rp;
     3009          struct stat st;
     3010          PATH_VAR (in);
     3011          PATH_VAR (out);
     3012
    36563013          strncpy (in, path, len);
    36573014          in[len] = '\0';
    36583015
    3659           if (
    36603016#ifdef HAVE_REALPATH
    3661               realpath (in, out)
     3017          ENULLLOOP (rp, realpath (in, out));
    36623018#else
    3663               abspath (in, out) && stat (out, &st) == 0
    3664 #endif
    3665              )
     3019          rp = abspath (in, out);
     3020#endif
     3021
     3022          if (rp)
    36663023            {
    3667               o = variable_buffer_output (o, out, strlen (out));
    3668               o = variable_buffer_output (o, " ", 1);
    3669               doneany = 1;
     3024              int r;
     3025              EINTRLOOP (r, stat (out, &st));
     3026              if (r == 0)
     3027                {
     3028                  o = variable_buffer_output (o, out, strlen (out));
     3029                  o = variable_buffer_output (o, " ", 1);
     3030                  doneany = 1;
     3031                }
    36703032            }
    36713033        }
     
    36753037  if (doneany)
    36763038    --o;
     3039
     3040  return o;
     3041}
     3042
     3043static char *
     3044func_file (char *o, char **argv, const char *funcname UNUSED)
     3045{
     3046  char *fn = argv[0];
     3047
     3048  if (fn[0] == '>')
     3049    {
     3050      FILE *fp;
     3051      const char *mode = "w";
     3052
     3053      /* We are writing a file.  */
     3054      ++fn;
     3055      if (fn[0] == '>')
     3056        {
     3057          mode = "a";
     3058          ++fn;
     3059        }
     3060      NEXT_TOKEN (fn);
     3061
     3062      if (fn[0] == '\0')
     3063        O (fatal, *expanding_var, _("file: missing filename"));
     3064
     3065      ENULLLOOP (fp, fopen (fn, mode));
     3066      if (fp == NULL)
     3067        OSS (fatal, reading_file, _("open: %s: %s"), fn, strerror (errno));
     3068
     3069      if (argv[1])
     3070        {
     3071          int l = strlen (argv[1]);
     3072          int nl = l == 0 || argv[1][l-1] != '\n';
     3073
     3074          if (fputs (argv[1], fp) == EOF || (nl && fputc ('\n', fp) == EOF))
     3075            OSS (fatal, reading_file, _("write: %s: %s"), fn, strerror (errno));
     3076        }
     3077      if (fclose (fp))
     3078        OSS (fatal, reading_file, _("close: %s: %s"), fn, strerror (errno));
     3079    }
     3080  else if (fn[0] == '<')
     3081    {
     3082      char *preo = o;
     3083      FILE *fp;
     3084
     3085      ++fn;
     3086      NEXT_TOKEN (fn);
     3087      if (fn[0] == '\0')
     3088        O (fatal, *expanding_var, _("file: missing filename"));
     3089
     3090      if (argv[1])
     3091        O (fatal, *expanding_var, _("file: too many arguments"));
     3092
     3093      ENULLLOOP (fp, fopen (fn, "r"));
     3094      if (fp == NULL)
     3095        {
     3096          if (errno == ENOENT)
     3097            return o;
     3098          OSS (fatal, reading_file, _("open: %s: %s"), fn, strerror (errno));
     3099        }
     3100
     3101      while (1)
     3102        {
     3103          char buf[1024];
     3104          size_t l = fread (buf, 1, sizeof (buf), fp);
     3105          if (l > 0)
     3106            o = variable_buffer_output (o, buf, l);
     3107
     3108          if (ferror (fp))
     3109            if (errno != EINTR)
     3110              OSS (fatal, reading_file, _("read: %s: %s"), fn, strerror (errno));
     3111          if (feof (fp))
     3112            break;
     3113        }
     3114      if (fclose (fp))
     3115        OSS (fatal, reading_file, _("close: %s: %s"), fn, strerror (errno));
     3116
     3117      /* Remove trailing newline.  */
     3118      if (o > preo && o[-1] == '\n')
     3119        if (--o > preo && o[-1] == '\r')
     3120          --o;
     3121    }
     3122  else
     3123    OS (fatal, *expanding_var, _("file: invalid file operation: %s"), fn);
    36773124
    36783125  return o;
     
    36873134  int doneany = 0;
    36883135  unsigned int len = 0;
    3689   PATH_VAR (in);
    3690   PATH_VAR (out);
    36913136
    36923137  while ((path = find_next_token (&p, &len)) != 0)
     
    36943139      if (len < GET_PATH_MAX)
    36953140        {
     3141          PATH_VAR (in);
     3142          PATH_VAR (out);
     3143
    36963144          strncpy (in, path, len);
    36973145          in[len] = '\0';
     
    37243172     in which case we're exactly like $(abspath ). */
    37253173  if (cwd)
    3726     while (isblank (*cwd))
     3174    while (ISBLANK (*cwd))
    37273175      cwd++;
    37283176  if (!cwd || !*cwd)
     
    38383286    argc++;
    38393287  if (argc > 4)
    3840     fatal (NILF, _("Too many arguments for $(xargs)!\n"));
     3288    O (fatal, NILF, _("Too many arguments for $(xargs)!\n"));
    38413289
    38423290  /* first: the initial / default command.*/
    38433291  initial_cmd = argv[0];
    3844   while (isspace ((unsigned char)*initial_cmd))
     3292  while (ISSPACE (*initial_cmd))
    38453293    initial_cmd++;
    38463294  max_args = initial_cmd_len = strlen (initial_cmd);
     
    38483296  /* second: the command for the subsequent command lines. defaults to the initial cmd. */
    38493297  subsequent_cmd = argc > 2 && argv[1][0] != '\0' ? argv[1] : "";
    3850   while (isspace ((unsigned char)*subsequent_cmd))
     3298  while (ISSPACE (*subsequent_cmd))
    38513299    subsequent_cmd++;
    38523300  if (*subsequent_cmd)
     
    38643312  /* third: the final command. defaults to the subseq cmd. */
    38653313  final_cmd = argc > 3 && argv[2][0] != '\0' ? argv[2] : "";
    3866   while (isspace ((unsigned char)*final_cmd))
     3314  while (ISSPACE (*final_cmd))
    38673315    final_cmd++;
    38683316  if (*final_cmd)
     
    38833331  /* calc the max argument length. */
    38843332  if (XARGS_MAX <= max_args + 2)
    3885     fatal (NILF, _("$(xargs): the commands are longer than the max exec argument length. (%lu <= %lu)\n"),
    3886            (unsigned long)XARGS_MAX, (unsigned long)max_args + 2);
     3333    ONN (fatal, NILF, _("$(xargs): the commands are longer than the max exec argument length. (%lu <= %lu)\n"),
     3334         (unsigned long)XARGS_MAX, (unsigned long)max_args + 2);
    38873335  max_args = XARGS_MAX - max_args - 1;
    38883336
     
    39023350        end = cur + len;
    39033351      if (cur && end == args)
    3904         fatal (NILF, _("$(xargs): command + one single arg is too much. giving up.\n"));
     3352        O (fatal, NILF, _("$(xargs): command + one single arg is too much. giving up.\n"));
    39053353
    39063354      /* emit the command. */
     
    39243372
    39253373      tmp = end;
    3926       while (tmp > args && isspace ((unsigned char)tmp[-1])) /* drop trailing spaces. */
     3374      while (tmp > args && ISSPACE (tmp[-1])) /* drop trailing spaces. */
    39273375        tmp--;
    39283376      o = variable_buffer_output (o, (char *)args, tmp - args);
     
    39333381        break;
    39343382      args = end;
    3935       while (isspace ((unsigned char)*args))
     3383      while (ISSPACE (*args))
    39363384        args++;
    39373385    }
     
    39403388}
    39413389#endif
     3390
     3391
     3392#ifdef CONFIG_WITH_STRING_FUNCTIONS
     3393/*
     3394  $(length string)
     3395
     3396  XXX: This doesn't take multibyte locales into account.
     3397 */
     3398static char *
     3399func_length (char *o, char **argv, const char *funcname UNUSED)
     3400{
     3401  size_t len = strlen (argv[0]);
     3402  return math_int_to_variable_buffer (o, len);
     3403}
     3404
     3405/*
     3406  $(length-var var)
     3407
     3408  XXX: This doesn't take multibyte locales into account.
     3409 */
     3410static char *
     3411func_length_var (char *o, char **argv, const char *funcname UNUSED)
     3412{
     3413  struct variable *var = lookup_variable (argv[0], strlen (argv[0]));
     3414  return math_int_to_variable_buffer (o, var ? var->value_length : 0);
     3415}
     3416
     3417
     3418/* func_insert and func_substr helper. */
     3419static char *
     3420helper_pad (char *o, size_t to_add, const char *pad, size_t pad_len)
     3421{
     3422  while (to_add > 0)
     3423    {
     3424      size_t size = to_add > pad_len ? pad_len : to_add;
     3425      o = variable_buffer_output (o, pad, size);
     3426      to_add -= size;
     3427    }
     3428  return o;
     3429}
     3430
     3431/*
     3432  $(insert in, str[, n[, length[, pad]]])
     3433
     3434  XXX: This doesn't take multibyte locales into account.
     3435 */
     3436static char *
     3437func_insert (char *o, char **argv, const char *funcname UNUSED)
     3438{
     3439  const char *in      = argv[0];
     3440  math_int    in_len  = (math_int)strlen (in);
     3441  const char *str     = argv[1];
     3442  math_int    str_len = (math_int)strlen (str);
     3443  math_int    n       = 0;
     3444  math_int    length  = str_len;
     3445  const char *pad     = "                ";
     3446  size_t      pad_len = 16;
     3447  size_t      i;
     3448
     3449  if (argv[2] != NULL)
     3450    {
     3451      n = math_int_from_string (argv[2]);
     3452      if (n > 0)
     3453        n--;            /* one-origin */
     3454      else if (n == 0)
     3455        n = str_len;    /* append */
     3456      else
     3457        { /* n < 0: from the end */
     3458          n = str_len + n;
     3459          if (n < 0)
     3460            n = 0;
     3461        }
     3462      if (n > 16*1024*1024) /* 16MB */
     3463        OS (fatal, NILF, _("$(insert ): n=%s is out of bounds\n"), argv[2]);
     3464
     3465      if (argv[3] != NULL)
     3466        {
     3467          length = math_int_from_string (argv[3]);
     3468          if (length < 0 || length > 16*1024*1024 /* 16MB */)
     3469              OS (fatal, NILF, _("$(insert ): length=%s is out of bounds\n"), argv[3]);
     3470
     3471          if (argv[4] != NULL)
     3472            {
     3473              const char *tmp = argv[4];
     3474              for (i = 0; tmp[i] == ' '; i++)
     3475                /* nothing */;
     3476              if (tmp[i] != '\0')
     3477                {
     3478                  pad = argv[4];
     3479                  pad_len = strlen (pad);
     3480                }
     3481              /* else: it was all default spaces. */
     3482            }
     3483        }
     3484    }
     3485
     3486  /* the head of the original string */
     3487  if (n > 0)
     3488    {
     3489      if (n <= str_len)
     3490        o = variable_buffer_output (o, str, n);
     3491      else
     3492        {
     3493          o = variable_buffer_output (o, str, str_len);
     3494          o = helper_pad (o, n - str_len, pad, pad_len);
     3495        }
     3496    }
     3497
     3498  /* insert the string */
     3499  if (length <= in_len)
     3500    o = variable_buffer_output (o, in, length);
     3501  else
     3502    {
     3503      o = variable_buffer_output (o, in, in_len);
     3504      o = helper_pad (o, length - in_len, pad, pad_len);
     3505    }
     3506
     3507  /* the tail of the original string */
     3508  if (n < str_len)
     3509    o = variable_buffer_output (o, str + n, str_len - n);
     3510
     3511  return o;
     3512}
     3513
     3514
     3515/*
     3516  $(pos needle, haystack[, start])
     3517  $(lastpos needle, haystack[, start])
     3518
     3519  XXX: This doesn't take multibyte locales into account.
     3520 */
     3521static char *
     3522func_pos (char *o, char **argv, const char *funcname UNUSED)
     3523{
     3524  const char *needle       = *argv[0] ? argv[0] : " ";
     3525  size_t      needle_len   = strlen (needle);
     3526  const char *haystack     = argv[1];
     3527  size_t      haystack_len = strlen (haystack);
     3528  math_int    start        = 0;
     3529  const char *hit;
     3530
     3531  if (argv[2] != NULL)
     3532    {
     3533      start = math_int_from_string (argv[2]);
     3534      if (start > 0)
     3535        start--;            /* one-origin */
     3536      else if (start < 0)
     3537        start = haystack_len + start; /* from the end */
     3538      if (start < 0 || start + needle_len > haystack_len)
     3539        return math_int_to_variable_buffer (o, 0);
     3540    }
     3541  else if (funcname[0] == 'l')
     3542    start = haystack_len - 1;
     3543
     3544  /* do the searching */
     3545  if (funcname[0] != 'l')
     3546    { /* pos */
     3547      if (needle_len == 1)
     3548        hit = strchr (haystack + start, *needle);
     3549      else
     3550        hit = strstr (haystack + start, needle);
     3551    }
     3552  else
     3553    { /* last pos */
     3554      int    ch  = *needle;
     3555      size_t off = start + 1;
     3556
     3557      hit = NULL;
     3558      while (off-- > 0)
     3559        {
     3560          if (   haystack[off] == ch
     3561              && (   needle_len == 1
     3562                  || strncmp (&haystack[off], needle, needle_len) == 0))
     3563            {
     3564              hit = haystack + off;
     3565              break;
     3566            }
     3567        }
     3568    }
     3569
     3570  return math_int_to_variable_buffer (o, hit ? hit - haystack + 1 : 0);
     3571}
     3572
     3573
     3574/*
     3575  $(substr str, start[, length[, pad]])
     3576
     3577  XXX: This doesn't take multibyte locales into account.
     3578 */
     3579static char *
     3580func_substr (char *o, char **argv, const char *funcname UNUSED)
     3581{
     3582  const char *str     = argv[0];
     3583  math_int    str_len = (math_int)strlen (str);
     3584  math_int    start   = math_int_from_string (argv[1]);
     3585  math_int    length  = 0;
     3586  const char *pad     = NULL;
     3587  size_t      pad_len = 0;
     3588
     3589  if (argv[2] != NULL)
     3590    {
     3591      if (argv[3] != NULL)
     3592        {
     3593          pad = argv[3];
     3594          for (pad_len = 0; pad[pad_len] == ' '; pad_len++)
     3595            /* nothing */;
     3596          if (pad[pad_len] != '\0')
     3597              pad_len = strlen (pad);
     3598          else
     3599            {
     3600              pad = "                ";
     3601              pad_len = 16;
     3602            }
     3603        }
     3604      length = math_int_from_string (argv[2]);
     3605      if (pad != NULL && length > 16*1024*1024 /* 16MB */)
     3606        OS (fatal, NILF, _("$(substr ): length=%s is out of bounds\n"), argv[2]);
     3607      if (pad != NULL && length < 0)
     3608        OS (fatal, NILF, _("$(substr ): negative length (%s) and padding doesn't mix.\n"), argv[2]);
     3609      if (length == 0)
     3610        return o;
     3611    }
     3612
     3613  /* Note that negative start is and length are used for referencing from the
     3614     end of the string. */
     3615  if (pad == NULL)
     3616    {
     3617      if (start > 0)
     3618        start--;      /* one-origin */
     3619      else
     3620        {
     3621          start = str_len + start;
     3622          if (start <= 0)
     3623            {
     3624              if (length < 0)
     3625                return o;
     3626              start += length;
     3627              if (start <= 0)
     3628                return o;
     3629              length = start;
     3630              start = 0;
     3631            }
     3632        }
     3633
     3634      if (start >= str_len)
     3635        return o;
     3636      if (length == 0)
     3637        length = str_len - start;
     3638      else if (length < 0)
     3639        {
     3640          if (str_len <= -length)
     3641            return o;
     3642          length += str_len;
     3643          if (length <= start)
     3644            return o;
     3645          length -= start;
     3646        }
     3647      else if (start + length > str_len)
     3648        length = str_len - start;
     3649
     3650      o = variable_buffer_output (o, str + start, length);
     3651    }
     3652  else
     3653    {
     3654      if (start > 0)
     3655        {
     3656          start--;      /* one-origin */
     3657          if (start >= str_len)
     3658            return length ? helper_pad (o, length, pad, pad_len) : o;
     3659          if (length == 0)
     3660            length = str_len - start;
     3661        }
     3662      else
     3663        {
     3664          start = str_len + start;
     3665          if (start <= 0)
     3666            {
     3667              if (start + length <= 0)
     3668                return length ? helper_pad (o, length, pad, pad_len) : o;
     3669              o = helper_pad (o, -start, pad, pad_len);
     3670              return variable_buffer_output (o, str, length + start);
     3671            }
     3672          if (length == 0)
     3673            length = str_len - start;
     3674        }
     3675      if (start + length <= str_len)
     3676        o = variable_buffer_output (o, str + start, length);
     3677      else
     3678        {
     3679          o = variable_buffer_output (o, str + start, str_len - start);
     3680          o = helper_pad (o, start + length - str_len, pad, pad_len);
     3681        }
     3682    }
     3683
     3684  return o;
     3685}
     3686
     3687
     3688/*
     3689  $(translate string, from-set[, to-set[, pad-char]])
     3690
     3691  XXX: This doesn't take multibyte locales into account.
     3692 */
     3693static char *
     3694func_translate (char *o, char **argv, const char *funcname UNUSED)
     3695{
     3696  const unsigned char *str      = (const unsigned char *)argv[0];
     3697  const unsigned char *from_set = (const unsigned char *)argv[1];
     3698  const char          *to_set   = argv[2] != NULL ? argv[2] : "";
     3699  char                 trans_tab[1 << CHAR_BIT];
     3700  int                  i;
     3701  char                 ch;
     3702
     3703  /* init the array. */
     3704  for (i = 0; i < (1 << CHAR_BIT); i++)
     3705    trans_tab[i] = i;
     3706
     3707  while (   (i = *from_set) != '\0'
     3708         && (ch = *to_set) != '\0')
     3709    {
     3710      trans_tab[i] = ch;
     3711      from_set++;
     3712      to_set++;
     3713    }
     3714
     3715  if (i != '\0')
     3716    {
     3717      ch = '\0';                        /* no padding == remove char */
     3718      if (argv[2] != NULL && argv[3] != NULL)
     3719        {
     3720          ch = argv[3][0];
     3721          if (ch && argv[3][1])
     3722            OS (fatal, NILF, _("$(translate ): pad=`%s' expected a single char\n"), argv[3]);
     3723          if (ch == '\0')               /* no char == space */
     3724            ch = ' ';
     3725        }
     3726      while ((i = *from_set++) != '\0')
     3727        trans_tab[i] = ch;
     3728    }
     3729
     3730  /* do the translation */
     3731  while ((i = *str++) != '\0')
     3732    {
     3733      ch = trans_tab[i];
     3734      if (ch)
     3735        o = variable_buffer_output (o, &ch, 1);
     3736    }
     3737
     3738  return o;
     3739}
     3740#endif /* CONFIG_WITH_STRING_FUNCTIONS */
     3741
     3742
     3743#ifdef CONFIG_WITH_LAZY_DEPS_VARS
     3744
     3745/* This is also in file.c (bad).  */
     3746# if VMS
     3747#  define FILE_LIST_SEPARATOR ','
     3748# else
     3749#  define FILE_LIST_SEPARATOR ' '
     3750# endif
     3751
     3752/* Implements $^ and $+.
     3753
     3754   The first comes with FUNCNAME 'deps', the second as 'deps-all'.
     3755
     3756   If no second argument is given, or if it's empty, or if it's zero,
     3757   all dependencies will be returned.  If the second argument is non-zero
     3758   the dependency at that position will be returned.  If the argument is
     3759   negative a fatal error is thrown.  */
     3760static char *
     3761func_deps (char *o, char **argv, const char *funcname)
     3762{
     3763  unsigned int idx = 0;
     3764  struct file *file;
     3765
     3766  /* Handle the argument if present. */
     3767
     3768  if (argv[1])
     3769    {
     3770      char *p = argv[1];
     3771      while (ISSPACE (*p))
     3772        p++;
     3773      if (*p != '\0')
     3774        {
     3775          char *n;
     3776          long l = strtol (p, &n, 0);
     3777          while (ISSPACE (*n))
     3778            n++;
     3779          idx = l;
     3780          if (*n != '\0' || l < 0 || (long)idx != l)
     3781            OSS (fatal, NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
     3782        }
     3783    }
     3784
     3785  /* Find the file and select the list corresponding to FUNCNAME. */
     3786
     3787  file = lookup_file (argv[0]);
     3788  if (file)
     3789    {
     3790      struct dep *deps;
     3791      struct dep *d;
     3792      if (funcname[4] == '\0')
     3793        {
     3794          deps = file->deps_no_dupes;
     3795          if (!deps && file->deps)
     3796            deps = file->deps = create_uniqute_deps_chain (file->deps);
     3797        }
     3798      else
     3799        deps = file->deps;
     3800
     3801      if (   file->double_colon
     3802          && (   file->double_colon != file
     3803              || file->last != file))
     3804          OSS (error, NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
     3805               funcname, file->name);
     3806
     3807      if (idx == 0 /* all */)
     3808        {
     3809          unsigned int total_len = 0;
     3810
     3811          /* calc the result length. */
     3812
     3813          for (d = deps; d; d = d->next)
     3814            if (!d->ignore_mtime)
     3815              {
     3816                const char *c = dep_name (d);
     3817
     3818#ifndef NO_ARCHIVES
     3819                if (ar_name (c))
     3820                  {
     3821                    c = strchr (c, '(') + 1;
     3822                    total_len += strlen (c);
     3823                  }
     3824                else
     3825#elif defined (CONFIG_WITH_STRCACHE2)
     3826                  total_len += strcache2_get_len (&file_strcache, c) + 1;
     3827#else
     3828                  total_len += strlen (c) + 1;
     3829#endif
     3830              }
     3831
     3832          if (total_len)
     3833            {
     3834              /* prepare the variable buffer dude wrt to the output size and
     3835                 pass along the strings.  */
     3836
     3837              o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
     3838
     3839              for (d = deps; d; d = d->next)
     3840                if (!d->ignore_mtime)
     3841                  {
     3842                    unsigned int len;
     3843                    const char *c = dep_name (d);
     3844
     3845#ifndef NO_ARCHIVES
     3846                    if (ar_name (c))
     3847                      {
     3848                        c = strchr (c, '(') + 1;
     3849                        len = strlen (c);
     3850                      }
     3851                    else
     3852#elif defined (CONFIG_WITH_STRCACHE2)
     3853                      len = strcache2_get_len (&file_strcache, c) + 1;
     3854#else
     3855                      len = strlen (c) + 1;
     3856#endif
     3857                    o = variable_buffer_output (o, c, len);
     3858                    o[-1] = FILE_LIST_SEPARATOR;
     3859                  }
     3860
     3861                --o;        /* nuke the last list separator */
     3862                *o = '\0';
     3863            }
     3864        }
     3865      else
     3866        {
     3867          /* Dependency given by index.  */
     3868
     3869          for (d = deps; d; d = d->next)
     3870            if (!d->ignore_mtime)
     3871              {
     3872                if (--idx == 0) /* 1 based indexing */
     3873                  {
     3874                    unsigned int len;
     3875                    const char *c = dep_name (d);
     3876
     3877#ifndef NO_ARCHIVES
     3878                    if (ar_name (c))
     3879                      {
     3880                        c = strchr (c, '(') + 1;
     3881                        len = strlen (c) - 1;
     3882                      }
     3883                    else
     3884#elif defined (CONFIG_WITH_STRCACHE2)
     3885                      len = strcache2_get_len (&file_strcache, c);
     3886#else
     3887                      len = strlen (c);
     3888#endif
     3889                    o = variable_buffer_output (o, c, len);
     3890                    break;
     3891                  }
     3892              }
     3893        }
     3894    }
     3895
     3896  return o;
     3897}
     3898
     3899/* Implements $?.
     3900
     3901   If no second argument is given, or if it's empty, or if it's zero,
     3902   all dependencies will be returned.  If the second argument is non-zero
     3903   the dependency at that position will be returned.  If the argument is
     3904   negative a fatal error is thrown.  */
     3905static char *
     3906func_deps_newer (char *o, char **argv, const char *funcname)
     3907{
     3908  unsigned int idx = 0;
     3909  struct file *file;
     3910
     3911  /* Handle the argument if present. */
     3912
     3913  if (argv[1])
     3914    {
     3915      char *p = argv[1];
     3916      while (ISSPACE (*p))
     3917        p++;
     3918      if (*p != '\0')
     3919        {
     3920          char *n;
     3921          long l = strtol (p, &n, 0);
     3922          while (ISSPACE (*n))
     3923            n++;
     3924          idx = l;
     3925          if (*n != '\0' || l < 0 || (long)idx != l)
     3926            OSS (fatal, NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
     3927        }
     3928    }
     3929
     3930  /* Find the file. */
     3931
     3932  file = lookup_file (argv[0]);
     3933  if (file)
     3934    {
     3935      struct dep *deps = file->deps;
     3936      struct dep *d;
     3937
     3938      if (   file->double_colon
     3939          && (   file->double_colon != file
     3940              || file->last != file))
     3941          OSS (error, NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
     3942               funcname, file->name);
     3943
     3944      if (idx == 0 /* all */)
     3945        {
     3946          unsigned int total_len = 0;
     3947
     3948          /* calc the result length. */
     3949
     3950          for (d = deps; d; d = d->next)
     3951            if (!d->ignore_mtime && d->changed)
     3952              {
     3953                const char *c = dep_name (d);
     3954
     3955#ifndef NO_ARCHIVES
     3956                if (ar_name (c))
     3957                  {
     3958                    c = strchr (c, '(') + 1;
     3959                    total_len += strlen (c);
     3960                  }
     3961                else
     3962#elif defined (CONFIG_WITH_STRCACHE2)
     3963                  total_len += strcache2_get_len (&file_strcache, c) + 1;
     3964#else
     3965                  total_len += strlen (c) + 1;
     3966#endif
     3967              }
     3968
     3969          if (total_len)
     3970            {
     3971              /* prepare the variable buffer dude wrt to the output size and
     3972                 pass along the strings.  */
     3973
     3974              o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
     3975
     3976              for (d = deps; d; d = d->next)
     3977                if (!d->ignore_mtime && d->changed)
     3978                  {
     3979                    unsigned int len;
     3980                    const char *c = dep_name (d);
     3981
     3982#ifndef NO_ARCHIVES
     3983                    if (ar_name (c))
     3984                      {
     3985                        c = strchr (c, '(') + 1;
     3986                        len = strlen (c);
     3987                      }
     3988                    else
     3989#elif defined (CONFIG_WITH_STRCACHE2)
     3990                      len = strcache2_get_len (&file_strcache, c) + 1;
     3991#else
     3992                      len = strlen (c) + 1;
     3993#endif
     3994                    o = variable_buffer_output (o, c, len);
     3995                    o[-1] = FILE_LIST_SEPARATOR;
     3996                  }
     3997
     3998                --o;        /* nuke the last list separator */
     3999                *o = '\0';
     4000            }
     4001        }
     4002      else
     4003        {
     4004          /* Dependency given by index.  */
     4005
     4006          for (d = deps; d; d = d->next)
     4007            if (!d->ignore_mtime && d->changed)
     4008              {
     4009                if (--idx == 0) /* 1 based indexing */
     4010                  {
     4011                    unsigned int len;
     4012                    const char *c = dep_name (d);
     4013
     4014#ifndef NO_ARCHIVES
     4015                    if (ar_name (c))
     4016                      {
     4017                        c = strchr (c, '(') + 1;
     4018                        len = strlen (c) - 1;
     4019                      }
     4020                    else
     4021#elif defined (CONFIG_WITH_STRCACHE2)
     4022                      len = strcache2_get_len (&file_strcache, c);
     4023#else
     4024                      len = strlen (c);
     4025#endif
     4026                    o = variable_buffer_output (o, c, len);
     4027                    break;
     4028                  }
     4029              }
     4030        }
     4031    }
     4032
     4033  return o;
     4034}
     4035
     4036/* Implements $|, the order only dependency list.
     4037
     4038   If no second argument is given, or if it's empty, or if it's zero,
     4039   all dependencies will be returned.  If the second argument is non-zero
     4040   the dependency at that position will be returned.  If the argument is
     4041   negative a fatal error is thrown.  */
     4042static char *
     4043func_deps_order_only (char *o, char **argv, const char *funcname)
     4044{
     4045  unsigned int idx = 0;
     4046  struct file *file;
     4047
     4048  /* Handle the argument if present. */
     4049
     4050  if (argv[1])
     4051    {
     4052      char *p = argv[1];
     4053      while (ISSPACE (*p))
     4054        p++;
     4055      if (*p != '\0')
     4056        {
     4057          char *n;
     4058          long l = strtol (p, &n, 0);
     4059          while (ISSPACE (*n))
     4060            n++;
     4061          idx = l;
     4062          if (*n != '\0' || l < 0 || (long)idx != l)
     4063            OSS (fatal, NILF, _("%s: invalid index value: `%s'\n"), funcname, p);
     4064        }
     4065    }
     4066
     4067  /* Find the file. */
     4068
     4069  file = lookup_file (argv[0]);
     4070  if (file)
     4071    {
     4072      struct dep *deps = file->deps;
     4073      struct dep *d;
     4074
     4075      if (   file->double_colon
     4076          && (   file->double_colon != file
     4077              || file->last != file))
     4078          OSS (error, NILF, _("$(%s ) cannot be used on files with multiple double colon rules like `%s'\n"),
     4079               funcname, file->name);
     4080
     4081      if (idx == 0 /* all */)
     4082        {
     4083          unsigned int total_len = 0;
     4084
     4085          /* calc the result length. */
     4086
     4087          for (d = deps; d; d = d->next)
     4088            if (d->ignore_mtime)
     4089              {
     4090                const char *c = dep_name (d);
     4091
     4092#ifndef NO_ARCHIVES
     4093                if (ar_name (c))
     4094                  {
     4095                    c = strchr (c, '(') + 1;
     4096                    total_len += strlen (c);
     4097                  }
     4098                else
     4099#elif defined (CONFIG_WITH_STRCACHE2)
     4100                  total_len += strcache2_get_len (&file_strcache, c) + 1;
     4101#else
     4102                  total_len += strlen (c) + 1;
     4103#endif
     4104              }
     4105
     4106          if (total_len)
     4107            {
     4108              /* prepare the variable buffer dude wrt to the output size and
     4109                 pass along the strings.  */
     4110
     4111              o = variable_buffer_output (o + total_len, "", 0) - total_len; /* a hack */
     4112
     4113              for (d = deps; d; d = d->next)
     4114                if (d->ignore_mtime)
     4115                  {
     4116                    unsigned int len;
     4117                    const char *c = dep_name (d);
     4118
     4119#ifndef NO_ARCHIVES
     4120                    if (ar_name (c))
     4121                      {
     4122                        c = strchr (c, '(') + 1;
     4123                        len = strlen (c);
     4124                      }
     4125                    else
     4126#elif defined (CONFIG_WITH_STRCACHE2)
     4127                      len = strcache2_get_len (&file_strcache, c) + 1;
     4128#else
     4129                      len = strlen (c) + 1;
     4130#endif
     4131                    o = variable_buffer_output (o, c, len);
     4132                    o[-1] = FILE_LIST_SEPARATOR;
     4133                  }
     4134
     4135                --o;        /* nuke the last list separator */
     4136                *o = '\0';
     4137            }
     4138        }
     4139      else
     4140        {
     4141          /* Dependency given by index.  */
     4142
     4143          for (d = deps; d; d = d->next)
     4144            if (d->ignore_mtime)
     4145              {
     4146                if (--idx == 0) /* 1 based indexing */
     4147                  {
     4148                    unsigned int len;
     4149                    const char *c = dep_name (d);
     4150
     4151#ifndef NO_ARCHIVES
     4152                    if (ar_name (c))
     4153                      {
     4154                        c = strchr (c, '(') + 1;
     4155                        len = strlen (c) - 1;
     4156                      }
     4157                    else
     4158#elif defined (CONFIG_WITH_STRCACHE2)
     4159                      len = strcache2_get_len (&file_strcache, c);
     4160#else
     4161                      len = strlen (c);
     4162#endif
     4163                    o = variable_buffer_output (o, c, len);
     4164                    break;
     4165                  }
     4166              }
     4167        }
     4168    }
     4169
     4170  return o;
     4171}
     4172#endif /* CONFIG_WITH_LAZY_DEPS_VARS */
     4173
     4174
     4175
     4176#ifdef CONFIG_WITH_DEFINED
     4177/* Similar to ifdef. */
     4178static char *
     4179func_defined (char *o, char **argv, const char *funcname UNUSED)
     4180{
     4181  struct variable *v = lookup_variable (argv[0], strlen (argv[0]));
     4182  int result = v != NULL && *v->value != '\0';
     4183  o = variable_buffer_output (o,  result ? "1" : "", result);
     4184  return o;
     4185}
     4186#endif /* CONFIG_WITH_DEFINED*/
    39424187
    39434188#ifdef CONFIG_WITH_TOUPPER_TOLOWER
     
    39744219      {
    39754220        const char ch = *s;
    3976         if (!isblank (ch)
     4221        if (!ISBLANK (ch)
    39774222         && ch != '@'
    39784223#ifdef CONFIG_WITH_COMMANDS_FUNC
     
    40444289              {
    40454290                /* strip */
    4046                 while (s1 < e1 && isblank (*s1))
     4291                while (s1 < e1 && ISBLANK (*s1))
    40474292                  s1++;
    4048                 while (s2 < e2 && isblank (*s2))
     4293                while (s2 < e2 && ISBLANK (*s2))
    40494294                  s2++;
    40504295                if (s1 >= e1 || s2 >= e2)
     
    40734318        if (s1 < e1 || s2 < e2)
    40744319          {
    4075             while (s1 < e1 && (isblank (*s1) || *s1 == '\n'))
     4320            while (s1 < e1 && (ISBLANK (*s1) || *s1 == '\n'))
    40764321              if (*s1++ == '\n')
    40774322                s1 = comp_cmds_strip_leading (s1, e1);
    4078             while (s2 < e2 && (isblank (*s2) || *s2 == '\n'))
     4323            while (s2 < e2 && (ISBLANK (*s2) || *s2 == '\n'))
    40794324              if (*s2++ == '\n')
    40804325                s2 = comp_cmds_strip_leading (s2, e2);
     
    41324377    s1 = var1->value;
    41334378    e1 = s1 + var1->value_length;
    4134     while (isblank ((unsigned char) *s1))
     4379    while (ISBLANK (*s1))
    41354380      s1++;
    4136     while (e1 > s1 && isblank ((unsigned char) e1[-1]))
     4381    while (e1 > s1 && ISBLANK (e1[-1]))
    41374382      e1--;
    41384383
    41394384    s2 = var2->value;
    41404385    e2 = s2 + var2->value_length;
    4141     while (isblank ((unsigned char) *s2))
     4386    while (ISBLANK (*s2))
    41424387      s2++;
    4143     while (e2 > s2 && isblank ((unsigned char) e2[-1]))
     4388    while (e2 > s2 && ISBLANK (e2[-1]))
    41444389      e2--;
    41454390
     
    41544399  s1 = var1->value;
    41554400  e1 = s1 + var1->value_length;
    4156   while (isblank ((unsigned char) *s1))
     4401  while (ISBLANK (*s1))
    41574402    s1++;
    4158   while (e1 > s1 && isblank ((unsigned char) e1[-1]))
     4403  while (e1 > s1 && ISBLANK (e1[-1]))
    41594404    e1--;
    41604405
    41614406  s2 = var2->value;
    41624407  e2 = s2 + var2->value_length;
    4163   while (isblank((unsigned char)*s2))
     4408  while (ISBLANK (*s2))
    41644409    s2++;
    4165   while (e2 > s2 && isblank ((unsigned char) e2[-1]))
     4410  while (e2 > s2 && ISBLANK (e2[-1]))
    41664411    e2--;
    41674412
     
    41944439      s1 = a1 = allocated_variable_expand ((char *)s1 + l);
    41954440      if (!l)
    4196         while (isblank ((unsigned char) *s1))
     4441        while (ISBLANK (*s1))
    41974442          s1++;
    41984443      e1 = strchr (s1, '\0');
    4199       while (e1 > s1 && isblank ((unsigned char) e1[-1]))
     4444      while (e1 > s1 && ISBLANK (e1[-1]))
    42004445        e1--;
    42014446    }
     
    42074452      s2 = a2 = allocated_variable_expand ((char *)s2 + l);
    42084453      if (!l)
    4209         while (isblank ((unsigned char) *s2))
     4454        while (ISBLANK (*s2))
    42104455          s2++;
    42114456      e2 = strchr (s2, '\0');
    4212       while (e2 > s2 && isblank ((unsigned char) e2[-1]))
     4457      while (e2 > s2 && ISBLANK (e2[-1]))
    42134458        e2--;
    42144459    }
     
    42834528  if (!s)
    42844529    return 1;
    4285   while (isspace ((unsigned char)*s))
     4530  while (ISSPACE (*s))
    42864531    s++;
    42874532  return *s == '\0';
     
    43184563      if (!p || *p != '\0')
    43194564        {
    4320           error (NILF, _("$(%s): strptime(%s,%s,) -> %s\n"), funcname,
     4565          OSSSS (error, NILF, _("$(%s): strptime(%s,%s,) -> %s\n"), funcname,
    43214566                 argv[1], input_format, p ? p : "<null>");
    43224567          return variable_buffer_output (o, "", 0);
     
    45604805
    45614806      if (argv[i + 1] == NULL)
    4562         fatal (NILF, _("$(select ): not an even argument count\n"));
    4563 
    4564       while (isspace ((unsigned char)*cond))
     4807        O (fatal, NILF, _("$(select ): not an even argument count\n"));
     4808
     4809      while (ISSPACE (*cond))
    45654810        cond++;
    45664811      if (   (*cond == 'o' && strncmp (cond, "otherwise", 9) == 0)
     
    45684813        {
    45694814          const char *end = cond + (*cond == 'o' ? 9 : 7);
    4570           while (isspace ((unsigned char)*end))
     4815          while (ISSPACE (*end))
    45714816            end++;
    45724817          if (*end == ':')
    45734818            do end++;
    4574             while (isspace ((unsigned char)*end));
     4819            while (ISSPACE (*end));
    45754820          is_otherwise = *end == '\0';
    45764821        }
     
    46484893            {
    46494894              *lastitem = '\0';
    4650               while (lastitem > stack_var->value && isspace (lastitem[-1]))
     4895              while (lastitem > stack_var->value && ISSPACE (lastitem[-1]))
    46514896                *--lastitem = '\0';
    46524897#ifdef CONFIG_WITH_VALUE_LENGTH
     
    47144959
    47154960  /* strip spaces */
    4716   while (isspace (*str))
     4961  while (ISSPACE (*str))
    47174962    str++;
    47184963  if (!*str)
    47194964    {
    4720       error (NILF, _("bad number: empty\n"));
     4965      O (error, NILF, _("bad number: empty\n"));
    47214966      return 0;
    47224967    }
     
    47244969
    47254970  /* check for +/- */
    4726   while (*str == '+' || *str == '-' || isspace (*str))
     4971  while (*str == '+' || *str == '-' || ISSPACE (*str))
    47274972      if (*str++ == '-')
    47284973        negative = !negative;
     
    47524997      ||  !(base == 16 ? isxdigit (*str) : isdigit (*str)) )
    47534998    {
    4754       error (NILF, _("bad number: '%s'\n"), start);
     4999      OS (error, NILF, _("bad number: '%s'\n"), start);
    47555000      return 0;
    47565001    }
    47575002
    47585003  /* convert it! */
    4759   while (*str && !isspace (*str))
     5004  while (*str && !ISSPACE (*str))
    47605005    {
    47615006      int ch = *str++;
     
    47685013      else
    47695014        {
    4770           error (NILF, _("bad number: '%s' (base=%u, pos=%lu)\n"), start, base, (unsigned long)(str - start));
     5015          OSNN (error, NILF, _("bad number: '%s' (base=%u, pos=%lu)\n"), start, base, (unsigned long)(str - start));
    47715016          return 0;
    47725017        }
     
    47765021
    47775022  /* check trailing spaces. */
    4778   while (isspace (*str))
     5023  while (ISSPACE (*str))
    47795024    str++;
    47805025  if (*str)
    47815026    {
    4782       error (NILF, _("bad number: '%s'\n"), start);
     5027      OS (error, NILF, _("bad number: '%s'\n"), start);
    47835028      return 0;
    47845029    }
     
    48435088      if (!divisor)
    48445089        {
    4845           error (NILF, _("divide by zero ('%s')\n"), argv[i]);
     5090          OS (error, NILF, _("divide by zero ('%s')\n"), argv[i]);
    48465091          return math_int_to_variable_buffer (o, 0);
    48475092        }
     
    48645109  if (!divisor)
    48655110    {
    4866       error (NILF, _("divide by zero ('%s')\n"), argv[1]);
     5111      OS (error, NILF, _("divide by zero ('%s')\n"), argv[1]);
    48675112      return math_int_to_variable_buffer (o, 0);
    48685113    }
     
    49975242  else
    49985243    {
    4999       error (NILF, _("$(libpath): unknown variable `%s'"), argv[0]);
     5244      OS (error, NILF, _("$(libpath): unknown variable `%s'"), argv[0]);
    50005245      return variable_buffer_output (o, "", 0);
    50015246    }
     
    50135258      if (rc != NO_ERROR)
    50145259        {
    5015           error (NILF, _("$(libpath): failed to query `%s', rc=%d"), argv[0], rc);
     5260          OSN (error, NILF, _("$(libpath): failed to query `%s', rc=%d"), argv[0], rc);
    50165261          return variable_buffer_output (o, "", 0);
    50175262        }
     
    50285273      if (fVar == 0)
    50295274        {
    5030           error (NILF, _("$(libpath): LIBPATH is read-only"));
     5275          O (error, NILF, _("$(libpath): LIBPATH is read-only"));
    50315276          return variable_buffer_output (o, "", 0);
    50325277        }
     
    50345279      /* strip leading and trailing spaces and check for max length. */
    50355280      val = argv[1];
    5036       while (isspace (*val))
     5281      while (ISSPACE (*val))
    50375282        val++;
    50385283      end = strchr (val, '\0');
    5039       while (end > val && isspace (end[-1]))
     5284      while (end > val && ISSPACE (end[-1]))
    50405285        end--;
    50415286
     
    50435288      if (len >= len_max)
    50445289        {
    5045           error (NILF, _("$(libpath): The new `%s' value is too long (%d bytes, max %d)"),
    5046                  argv[0], len, len_max);
     5290          OSNN (error,  NILF, _("$(libpath): The new `%s' value is too long (%d bytes, max %d)"),
     5291                argv[0], len, len_max);
    50475292          return variable_buffer_output (o, "", 0);
    50485293        }
     
    50545299      if (rc != NO_ERROR)
    50555300        {
    5056           error (NILF, _("$(libpath): failed to set `%s' to `%s', rc=%d"), argv[0], buf, rc);
     5301          OSSN (error, (NILF, _("$(libpath): failed to set `%s' to `%s', rc=%d"), argv[0], buf, rc);
    50575302          return variable_buffer_output (o, "", 0);
    50585303        }
     
    51495394  if (recursive)
    51505395    {
    5151       error (reading_file, _("$(%s ) was invoked recursivly"), funcname);
     5396      OS (error, reading_file, _("$(%s ) was invoked recursivly"), funcname);
    51525397      return variable_buffer_output (o, "recursive", sizeof ("recursive") - 1);
    51535398    }
    51545399  if (*argv[0] == '\0')
    51555400    {
    5156       error (reading_file, _("$(%s ) was invoked with an empty target name"), funcname);
     5401      OS (error, reading_file, _("$(%s ) was invoked with an empty target name"), funcname);
    51575402      return o;
    51585403    }
     
    51965441            continue;
    51975442          p = cmds->command_lines[i];
    5198           while (isblank ((unsigned char)*p))
     5443          while (ISBLANK (*p))
    51995444            p++;
    52005445          if (*p == '\0')
     
    52715516                                 already been written to the output.  */
    52725517                              while (out > ref
    5273                                      && isblank ((unsigned char)out[-1]))
     5518                                     && ISBLANK (out[-1]))
    52745519                                --out;
    52755520
     
    52905535                 dep expansion happens, so it would have to be on a hackish basis. sad... */
    52915536              else if (*ref == '<' || *ref == '*' || *ref == '%' || *ref == '^' || *ref == '+')
    5292                 error (reading_file, _("$(%s ) does not work reliably with $%c in all cases"), funcname, *ref);
     5537                OSN (error, reading_file, _("$(%s ) does not work reliably with $%c in all cases"), funcname, *ref);
    52935538            }
    52945539
     
    53075552          /* Skip it if it has a '%' prefix or is blank. */
    53085553          p = o;
    5309           while (isblank ((unsigned char)*o)
     5554          while (ISBLANK (*o)
    53105555              || *o == '@'
    53115556              || *o == '-'
     
    53705615            symbolic = 1;
    53715616          else
    5372             error (reading_file, _("$(%s ) invalid argument `%s'"),
    5373                    funcname, argv[0]);
     5617            OSS (error, reading_file, _("$(%s ) invalid argument `%s'"),
     5618                 funcname, argv[0]);
    53745619        }
    53755620    }
     
    54245669  /* Figure what kind of input this is. */
    54255670  psz = argv[0];
    5426   while (isblank ((unsigned char)*psz))
     5671  while (ISBLANK (*psz))
    54275672    psz++;
    54285673
     
    54355680          if (*psz < '0' || *psz >= '8')
    54365681            {
    5437               error (reading_file, _("$(%s ) illegal number `%s'"), funcname, argv[0]);
     5682              OSS (error, reading_file, _("$(%s ) illegal number `%s'"), funcname, argv[0]);
    54385683              break;
    54395684            }
     
    54435688
    54445689      if (argv[1] != NULL)
    5445           error (reading_file, _("$(%s ) too many arguments for octal mode"), funcname);
     5690          OS (error, reading_file, _("$(%s ) too many arguments for octal mode"), funcname);
    54465691  }
    54475692  else
     
    54495694      u = umask(0);
    54505695      umask(u);
    5451       error (reading_file, _("$(%s ) symbol mode is not implemented"), funcname);
     5696      OS (error, reading_file, _("$(%s ) symbol mode is not implemented"), funcname);
    54525697  }
    54535698
     
    54655710# ifdef KBUILD_OS_WINDOWS
    54665711  const char *cmd = argv[0];
    5467   while (isblank ((unsigned char)*cmd))
     5712  while (ISBLANK (*cmd))
    54685713    cmd++;
    54695714  if (strcmp (cmd, "invalidate") == 0)
    54705715    {
    54715716      if (argv[1] != NULL)
    5472         error (reading_file, "$(dircache-ctl invalidate) takes no parameters");
     5717        O (error, reading_file, "$(dircache-ctl invalidate) takes no parameters");
    54735718      dir_cache_invalid_all ();
    54745719    }
     
    54765721    {
    54775722      if (argv[1] != NULL)
    5478         error (reading_file, "$(dircache-ctl invalidate-missing) takes no parameters");
     5723        O (error, reading_file, "$(dircache-ctl invalidate-missing) takes no parameters");
    54795724      dir_cache_invalid_missing ();
    54805725    }
     
    54855730        {
    54865731          const char *dir = argv[i];
    5487           while (isblank ((unsigned char)*dir))
     5732          while (ISBLANK (*dir))
    54885733            dir++;
    54895734          if (*dir)
     
    54975742        {
    54985743          const char *dir = argv[i];
    5499           while (isblank ((unsigned char)*dir))
     5744          while (ISBLANK (*dir))
    55005745            dir++;
    55015746          if (*dir)
     
    55045749    }
    55055750  else
    5506     error (reading_file, "Unknown $(dircache-ctl ) command: '%s'", cmd);
     5751    OS (error, reading_file, "Unknown $(dircache-ctl ) command: '%s'", cmd);
    55075752# endif
    55085753  return o;
     
    55265771static char *func_call (char *o, char **argv, const char *funcname);
    55275772
     5773#define FT_ENTRY(_name, _min, _max, _exp, _func) \
     5774  { { (_func) }, STRING_SIZE_TUPLE(_name), (_min), (_max), (_exp), 0 }
    55285775
    55295776static struct function_table_entry function_table_init[] =
    55305777{
    5531  /* Name/size */                    /* MIN MAX EXP? Function */
    5532   { STRING_SIZE_TUPLE("abspath"),       0,  1,  1,  func_abspath},
    5533   { STRING_SIZE_TUPLE("addprefix"),     2,  2,  1,  func_addsuffix_addprefix},
    5534   { STRING_SIZE_TUPLE("addsuffix"),     2,  2,  1,  func_addsuffix_addprefix},
    5535   { STRING_SIZE_TUPLE("basename"),      0,  1,  1,  func_basename_dir},
    5536   { STRING_SIZE_TUPLE("dir"),           0,  1,  1,  func_basename_dir},
    5537   { STRING_SIZE_TUPLE("notdir"),        0,  1,  1,  func_notdir_suffix},
     5778 /*         Name            MIN MAX EXP? Function */
     5779  FT_ENTRY ("abspath",       0,  1,  1,  func_abspath),
     5780  FT_ENTRY ("addprefix",     2,  2,  1,  func_addsuffix_addprefix),
     5781  FT_ENTRY ("addsuffix",     2,  2,  1,  func_addsuffix_addprefix),
     5782  FT_ENTRY ("basename",      0,  1,  1,  func_basename_dir),
     5783  FT_ENTRY ("dir",           0,  1,  1,  func_basename_dir),
     5784  FT_ENTRY ("notdir",        0,  1,  1,  func_notdir_suffix),
    55385785#ifdef CONFIG_WITH_ROOT_FUNC
    5539   { STRING_SIZE_TUPLE("root"),          0,  1,  1,  func_root},
    5540   { STRING_SIZE_TUPLE("notroot"),       0,  1,  1,  func_notroot},
    5541 #endif
    5542   { STRING_SIZE_TUPLE("subst"),         3,  3,  1,  func_subst},
    5543   { STRING_SIZE_TUPLE("suffix"),        0,  1,  1,  func_notdir_suffix},
    5544   { STRING_SIZE_TUPLE("filter"),        2,  2,  1,  func_filter_filterout},
    5545   { STRING_SIZE_TUPLE("filter-out"),    2,  2,  1,  func_filter_filterout},
    5546   { STRING_SIZE_TUPLE("findstring"),    2,  2,  1,  func_findstring},
     5786  FT_ENTRY ("root",          0,  1,  1,  func_root),
     5787  FT_ENTRY ("notroot",       0,  1,  1,  func_notroot),
     5788#endif
     5789  FT_ENTRY ("subst",         3,  3,  1,  func_subst),
     5790  FT_ENTRY ("suffix",        0,  1,  1,  func_notdir_suffix),
     5791  FT_ENTRY ("filter",        2,  2,  1,  func_filter_filterout),
     5792  FT_ENTRY ("filter-out",    2,  2,  1,  func_filter_filterout),
     5793  FT_ENTRY ("findstring",    2,  2,  1,  func_findstring),
    55475794#ifdef CONFIG_WITH_DEFINED_FUNCTIONS
    5548   { STRING_SIZE_TUPLE("firstdefined"),  0,  2,  1,  func_firstdefined},
    5549 #endif
    5550   { STRING_SIZE_TUPLE("firstword"),     0,  1,  1,  func_firstword},
    5551   { STRING_SIZE_TUPLE("flavor"),        0,  1,  1,  func_flavor},
    5552   { STRING_SIZE_TUPLE("join"),          2,  2,  1,  func_join},
     5795  FT_ENTRY ("firstdefined",  0,  2,  1,  func_firstdefined),
     5796#endif
     5797  FT_ENTRY ("firstword",     0,  1,  1,  func_firstword),
     5798  FT_ENTRY ("flavor",        0,  1,  1,  func_flavor),
     5799  FT_ENTRY ("join",          2,  2,  1,  func_join),
    55535800#ifdef CONFIG_WITH_DEFINED_FUNCTIONS
    5554   { STRING_SIZE_TUPLE("lastdefined"),   0,  2,  1,  func_lastdefined},
    5555 #endif
    5556   { STRING_SIZE_TUPLE("lastword"),      0,  1,  1,  func_lastword},
    5557   { STRING_SIZE_TUPLE("patsubst"),      3,  3,  1,  func_patsubst},
    5558   { STRING_SIZE_TUPLE("realpath"),      0,  1,  1,  func_realpath},
     5801  FT_ENTRY ("lastdefined",   0,  2,  1,  func_lastdefined),
     5802#endif
     5803  FT_ENTRY ("lastword",      0,  1,  1,  func_lastword),
     5804  FT_ENTRY ("patsubst",      3,  3,  1,  func_patsubst),
     5805  FT_ENTRY ("realpath",      0,  1,  1,  func_realpath),
    55595806#ifdef CONFIG_WITH_RSORT
    5560   { STRING_SIZE_TUPLE("rsort"),         0,  1,  1,  func_sort},
    5561 #endif
    5562   { STRING_SIZE_TUPLE("shell"),         0,  1,  1,  func_shell},
    5563   { STRING_SIZE_TUPLE("sort"),          0,  1,  1,  func_sort},
    5564   { STRING_SIZE_TUPLE("strip"),         0,  1,  1,  func_strip},
     5807  FT_ENTRY ("rsort",         0,  1,  1,  func_sort),
     5808#endif
     5809  FT_ENTRY ("shell",         0,  1,  1,  func_shell),
     5810  FT_ENTRY ("sort",          0,  1,  1,  func_sort),
     5811  FT_ENTRY ("strip",         0,  1,  1,  func_strip),
    55655812#ifdef CONFIG_WITH_WHERE_FUNCTION
    5566   { STRING_SIZE_TUPLE("where"),         0,  1,  1,  func_where},
    5567 #endif
    5568   { STRING_SIZE_TUPLE("wildcard"),      0,  1,  1,  func_wildcard},
    5569   { STRING_SIZE_TUPLE("word"),          2,  2,  1,  func_word},
    5570   { STRING_SIZE_TUPLE("wordlist"),      3,  3,  1,  func_wordlist},
    5571   { STRING_SIZE_TUPLE("words"),         0,  1,  1,  func_words},
    5572   { STRING_SIZE_TUPLE("origin"),        0,  1,  1,  func_origin},
    5573   { STRING_SIZE_TUPLE("foreach"),       3,  3,  0,  func_foreach},
     5813  FT_ENTRY ("where",         0,  1,  1,  func_where),
     5814#endif
     5815  FT_ENTRY ("wildcard",      0,  1,  1,  func_wildcard),
     5816  FT_ENTRY ("word",          2,  2,  1,  func_word),
     5817  FT_ENTRY ("wordlist",      3,  3,  1,  func_wordlist),
     5818  FT_ENTRY ("words",         0,  1,  1,  func_words),
     5819  FT_ENTRY ("origin",        0,  1,  1,  func_origin),
     5820  FT_ENTRY ("foreach",       3,  3,  0,  func_foreach),
    55745821#ifdef CONFIG_WITH_LOOP_FUNCTIONS
    5575   { STRING_SIZE_TUPLE("for"),           4,  4,  0,  func_for},
    5576   { STRING_SIZE_TUPLE("while"),         2,  2,  0,  func_while},
    5577 #endif
    5578   { STRING_SIZE_TUPLE("call"),          1,  0,  1,  func_call},
    5579   { STRING_SIZE_TUPLE("info"),          0,  1,  1,  func_error},
    5580   { STRING_SIZE_TUPLE("error"),         0,  1,  1,  func_error},
    5581   { STRING_SIZE_TUPLE("warning"),       0,  1,  1,  func_error},
    5582   { STRING_SIZE_TUPLE("if"),            2,  3,  0,  func_if},
    5583   { STRING_SIZE_TUPLE("or"),            1,  0,  0,  func_or},
    5584   { STRING_SIZE_TUPLE("and"),           1,  0,  0,  func_and},
    5585   { STRING_SIZE_TUPLE("value"),         0,  1,  1,  func_value},
    5586   { STRING_SIZE_TUPLE("eval"),          0,  1,  1,  func_eval},
     5822  FT_ENTRY ("for",           4,  4,  0,  func_for),
     5823  FT_ENTRY ("while",         2,  2,  0,  func_while),
     5824#endif
     5825  FT_ENTRY ("call",          1,  0,  1,  func_call),
     5826  FT_ENTRY ("info",          0,  1,  1,  func_error),
     5827  FT_ENTRY ("error",         0,  1,  1,  func_error),
     5828  FT_ENTRY ("warning",       0,  1,  1,  func_error),
     5829  FT_ENTRY ("if",            2,  3,  0,  func_if),
     5830  FT_ENTRY ("or",            1,  0,  0,  func_or),
     5831  FT_ENTRY ("and",           1,  0,  0,  func_and),
     5832  FT_ENTRY ("value",         0,  1,  1,  func_value),
     5833#ifdef EXPERIMENTAL
     5834  FT_ENTRY ("eq",            2,  2,  1,  func_eq),
     5835  FT_ENTRY ("not",           0,  1,  1,  func_not),
     5836#endif
     5837  FT_ENTRY ("eval",          0,  1,  1,  func_eval),
    55875838#ifdef CONFIG_WITH_EVALPLUS
    5588   { STRING_SIZE_TUPLE("evalctx"),       0,  1,  1,  func_evalctx},
    5589   { STRING_SIZE_TUPLE("evalval"),       1,  1,  1,  func_evalval},
    5590   { STRING_SIZE_TUPLE("evalvalctx"),    1,  1,  1,  func_evalval},
    5591   { STRING_SIZE_TUPLE("evalcall"),      1,  0,  1,  func_call},
    5592   { STRING_SIZE_TUPLE("evalcall2"),     1,  0,  1,  func_call},
    5593   { STRING_SIZE_TUPLE("eval-opt-var"),  1,  0,  1,  func_eval_optimize_variable},
    5594 #endif
    5595 #ifdef EXPERIMENTAL
    5596   { STRING_SIZE_TUPLE("eq"),            2,  2,  1,  func_eq},
    5597   { STRING_SIZE_TUPLE("not"),           0,  1,  1,  func_not},
    5598 #endif
     5839  FT_ENTRY ("evalctx",       0,  1,  1,  func_evalctx),
     5840  FT_ENTRY ("evalval",       1,  1,  1,  func_evalval),
     5841  FT_ENTRY ("evalvalctx",    1,  1,  1,  func_evalval),
     5842  FT_ENTRY ("evalcall",      1,  0,  1,  func_call),
     5843  FT_ENTRY ("evalcall2",     1,  0,  1,  func_call),
     5844  FT_ENTRY ("eval-opt-var",  1,  0,  1,  func_eval_optimize_variable),
     5845#endif
     5846  FT_ENTRY ("file",          1,  2,  1,  func_file),
    55995847#ifdef CONFIG_WITH_STRING_FUNCTIONS
    5600   { STRING_SIZE_TUPLE("length"),        1,  1,  1,  func_length},
    5601   { STRING_SIZE_TUPLE("length-var"),    1,  1,  1,  func_length_var},
    5602   { STRING_SIZE_TUPLE("insert"),        2,  5,  1,  func_insert},
    5603   { STRING_SIZE_TUPLE("pos"),           2,  3,  1,  func_pos},
    5604   { STRING_SIZE_TUPLE("lastpos"),       2,  3,  1,  func_pos},
    5605   { STRING_SIZE_TUPLE("substr"),        2,  4,  1,  func_substr},
    5606   { STRING_SIZE_TUPLE("translate"),     2,  4,  1,  func_translate},
     5848  FT_ENTRY ("length",        1,  1,  1,  func_length),
     5849  FT_ENTRY ("length-var",    1,  1,  1,  func_length_var),
     5850  FT_ENTRY ("insert",        2,  5,  1,  func_insert),
     5851  FT_ENTRY ("pos",           2,  3,  1,  func_pos),
     5852  FT_ENTRY ("lastpos",       2,  3,  1,  func_pos),
     5853  FT_ENTRY ("substr",        2,  4,  1,  func_substr),
     5854  FT_ENTRY ("translate",     2,  4,  1,  func_translate),
    56075855#endif
    56085856#ifdef CONFIG_WITH_PRINTF
    5609   { STRING_SIZE_TUPLE("printf"),        1,  0,  1,  kmk_builtin_func_printf},
     5857  FT_ENTRY ("printf",        1,  0,  1,  kmk_builtin_func_printf),
    56105858#endif
    56115859#ifdef CONFIG_WITH_LAZY_DEPS_VARS
    5612   { STRING_SIZE_TUPLE("deps"),          1,  2,  1,  func_deps},
    5613   { STRING_SIZE_TUPLE("deps-all"),      1,  2,  1,  func_deps},
    5614   { STRING_SIZE_TUPLE("deps-newer"),    1,  2,  1,  func_deps_newer},
    5615   { STRING_SIZE_TUPLE("deps-oo"),       1,  2,  1,  func_deps_order_only},
     5860  FT_ENTRY ("deps",          1,  2,  1,  func_deps),
     5861  FT_ENTRY ("deps-all",      1,  2,  1,  func_deps),
     5862  FT_ENTRY ("deps-newer",    1,  2,  1,  func_deps_newer),
     5863  FT_ENTRY ("deps-oo",       1,  2,  1,  func_deps_order_only),
    56165864#endif
    56175865#ifdef CONFIG_WITH_DEFINED
    5618   { STRING_SIZE_TUPLE("defined"),       1,  1,  1,  func_defined},
     5866  FT_ENTRY ("defined",       1,  1,  1,  func_defined),
    56195867#endif
    56205868#ifdef CONFIG_WITH_TOUPPER_TOLOWER
    5621   { STRING_SIZE_TUPLE("toupper"),       0,  1,  1,  func_toupper_tolower},
    5622   { STRING_SIZE_TUPLE("tolower"),       0,  1,  1,  func_toupper_tolower},
     5869  FT_ENTRY ("toupper",       0,  1,  1,  func_toupper_tolower),
     5870  FT_ENTRY ("tolower",       0,  1,  1,  func_toupper_tolower),
    56235871#endif
    56245872#ifdef CONFIG_WITH_ABSPATHEX
    5625   { STRING_SIZE_TUPLE("abspathex"),     0,  2,  1,  func_abspathex},
     5873  FT_ENTRY ("abspathex",     0,  2,  1,  func_abspathex),
    56265874#endif
    56275875#ifdef CONFIG_WITH_XARGS
    5628   { STRING_SIZE_TUPLE("xargs"),         2,  0,  1,  func_xargs},
     5876  FT_ENTRY ("xargs",         2,  0,  1,  func_xargs),
    56295877#endif
    56305878#if defined(CONFIG_WITH_VALUE_LENGTH) && defined(CONFIG_WITH_COMPARE)
    5631   { STRING_SIZE_TUPLE("comp-vars"),     3,  3,  1,  func_comp_vars},
    5632   { STRING_SIZE_TUPLE("comp-cmds"),     3,  3,  1,  func_comp_vars},
    5633   { STRING_SIZE_TUPLE("comp-cmds-ex"),  3,  3,  1,  func_comp_cmds_ex},
     5879  FT_ENTRY ("comp-vars",     3,  3,  1,  func_comp_vars),
     5880  FT_ENTRY ("comp-cmds",     3,  3,  1,  func_comp_vars),
     5881  FT_ENTRY ("comp-cmds-ex",  3,  3,  1,  func_comp_cmds_ex),
    56345882#endif
    56355883#ifdef CONFIG_WITH_DATE
    5636   { STRING_SIZE_TUPLE("date"),          0,  1,  1,  func_date},
    5637   { STRING_SIZE_TUPLE("date-utc"),      0,  3,  1,  func_date},
     5884  FT_ENTRY ("date",          0,  1,  1,  func_date),
     5885  FT_ENTRY ("date-utc",      0,  3,  1,  func_date),
    56385886#endif
    56395887#ifdef CONFIG_WITH_FILE_SIZE
    5640   { STRING_SIZE_TUPLE("file-size"),     1,  1,  1,  func_file_size},
     5888  FT_ENTRY ("file-size",     1,  1,  1,  func_file_size),
    56415889#endif
    56425890#ifdef CONFIG_WITH_WHICH
    5643   { STRING_SIZE_TUPLE("which"),         0,  0,  1,  func_which},
     5891  FT_ENTRY ("which",         0,  0,  1,  func_which),
    56445892#endif
    56455893#ifdef CONFIG_WITH_IF_CONDITIONALS
    5646   { STRING_SIZE_TUPLE("expr"),          1,  1,  0,  func_expr},
    5647   { STRING_SIZE_TUPLE("if-expr"),       2,  3,  0,  func_if_expr},
    5648   { STRING_SIZE_TUPLE("select"),        2,  0,  0,  func_select},
     5894  FT_ENTRY ("expr",          1,  1,  0,  func_expr),
     5895  FT_ENTRY ("if-expr",       2,  3,  0,  func_if_expr),
     5896  FT_ENTRY ("select",        2,  0,  0,  func_select),
    56495897#endif
    56505898#ifdef CONFIG_WITH_SET_CONDITIONALS
    5651   { STRING_SIZE_TUPLE("intersects"),    2,  2,  1,  func_set_intersects},
     5899  FT_ENTRY ("intersects",    2,  2,  1,  func_set_intersects),
    56525900#endif
    56535901#ifdef CONFIG_WITH_STACK
    5654   { STRING_SIZE_TUPLE("stack-push"),    2,  2,  1,  func_stack_push},
    5655   { STRING_SIZE_TUPLE("stack-pop"),     1,  1,  1,  func_stack_pop_top},
    5656   { STRING_SIZE_TUPLE("stack-popv"),    1,  1,  1,  func_stack_pop_top},
    5657   { STRING_SIZE_TUPLE("stack-top"),     1,  1,  1,  func_stack_pop_top},
     5902  FT_ENTRY ("stack-push",    2,  2,  1,  func_stack_push),
     5903  FT_ENTRY ("stack-pop",     1,  1,  1,  func_stack_pop_top),
     5904  FT_ENTRY ("stack-popv",    1,  1,  1,  func_stack_pop_top),
     5905  FT_ENTRY ("stack-top",     1,  1,  1,  func_stack_pop_top),
    56585906#endif
    56595907#ifdef CONFIG_WITH_MATH
    5660   { STRING_SIZE_TUPLE("int-add"),       2,  0,  1,  func_int_add},
    5661   { STRING_SIZE_TUPLE("int-sub"),       2,  0,  1,  func_int_sub},
    5662   { STRING_SIZE_TUPLE("int-mul"),       2,  0,  1,  func_int_mul},
    5663   { STRING_SIZE_TUPLE("int-div"),       2,  0,  1,  func_int_div},
    5664   { STRING_SIZE_TUPLE("int-mod"),       2,  2,  1,  func_int_mod},
    5665   { STRING_SIZE_TUPLE("int-not"),       1,  1,  1,  func_int_not},
    5666   { STRING_SIZE_TUPLE("int-and"),       2,  0,  1,  func_int_and},
    5667   { STRING_SIZE_TUPLE("int-or"),        2,  0,  1,  func_int_or},
    5668   { STRING_SIZE_TUPLE("int-xor"),       2,  0,  1,  func_int_xor},
    5669   { STRING_SIZE_TUPLE("int-eq"),        2,  2,  1,  func_int_cmp},
    5670   { STRING_SIZE_TUPLE("int-ne"),        2,  2,  1,  func_int_cmp},
    5671   { STRING_SIZE_TUPLE("int-gt"),        2,  2,  1,  func_int_cmp},
    5672   { STRING_SIZE_TUPLE("int-ge"),        2,  2,  1,  func_int_cmp},
    5673   { STRING_SIZE_TUPLE("int-lt"),        2,  2,  1,  func_int_cmp},
    5674   { STRING_SIZE_TUPLE("int-le"),        2,  2,  1,  func_int_cmp},
     5908  FT_ENTRY ("int-add",       2,  0,  1,  func_int_add),
     5909  FT_ENTRY ("int-sub",       2,  0,  1,  func_int_sub),
     5910  FT_ENTRY ("int-mul",       2,  0,  1,  func_int_mul),
     5911  FT_ENTRY ("int-div",       2,  0,  1,  func_int_div),
     5912  FT_ENTRY ("int-mod",       2,  2,  1,  func_int_mod),
     5913  FT_ENTRY ("int-not",       1,  1,  1,  func_int_not),
     5914  FT_ENTRY ("int-and",       2,  0,  1,  func_int_and),
     5915  FT_ENTRY ("int-or",        2,  0,  1,  func_int_or),
     5916  FT_ENTRY ("int-xor",       2,  0,  1,  func_int_xor),
     5917  FT_ENTRY ("int-eq",        2,  2,  1,  func_int_cmp),
     5918  FT_ENTRY ("int-ne",        2,  2,  1,  func_int_cmp),
     5919  FT_ENTRY ("int-gt",        2,  2,  1,  func_int_cmp),
     5920  FT_ENTRY ("int-ge",        2,  2,  1,  func_int_cmp),
     5921  FT_ENTRY ("int-lt",        2,  2,  1,  func_int_cmp),
     5922  FT_ENTRY ("int-le",        2,  2,  1,  func_int_cmp),
    56755923#endif
    56765924#ifdef CONFIG_WITH_NANOTS
    5677   { STRING_SIZE_TUPLE("nanots"),        0,  0,  0,  func_nanots},
     5925  FT_ENTRY ("nanots",        0,  0,  0,  func_nanots),
    56785926#endif
    56795927#ifdef CONFIG_WITH_OS2_LIBPATH
    5680   { STRING_SIZE_TUPLE("libpath"),       1,  2,  1,  func_os2_libpath},
     5928  FT_ENTRY ("libpath",       1,  2,  1,  func_os2_libpath),
    56815929#endif
    56825930#if defined (CONFIG_WITH_MAKE_STATS) || defined (CONFIG_WITH_MINIMAL_STATS)
    5683   { STRING_SIZE_TUPLE("make-stats"),    0,  0,  0,  func_make_stats},
     5931  FT_ENTRY ("make-stats",    0,  0,  0,  func_make_stats),
    56845932#endif
    56855933#ifdef CONFIG_WITH_COMMANDS_FUNC
    5686   { STRING_SIZE_TUPLE("commands"),      1,  1,  1,  func_commands},
    5687   { STRING_SIZE_TUPLE("commands-sc"),   1,  1,  1,  func_commands},
    5688   { STRING_SIZE_TUPLE("commands-usr"),  2,  2,  1,  func_commands},
     5934  FT_ENTRY ("commands",      1,  1,  1,  func_commands),
     5935  FT_ENTRY ("commands-sc",   1,  1,  1,  func_commands),
     5936  FT_ENTRY ("commands-usr",  2,  2,  1,  func_commands),
    56895937#endif
    56905938#ifdef KMK_HELPERS
    5691   { STRING_SIZE_TUPLE("kb-src-tool"),   1,  1,  0,  func_kbuild_source_tool},
    5692   { STRING_SIZE_TUPLE("kb-obj-base"),   1,  1,  0,  func_kbuild_object_base},
    5693   { STRING_SIZE_TUPLE("kb-obj-suff"),   1,  1,  0,  func_kbuild_object_suffix},
    5694   { STRING_SIZE_TUPLE("kb-src-prop"),   3,  4,  0,  func_kbuild_source_prop},
    5695   { STRING_SIZE_TUPLE("kb-src-one"),    0,  1,  0,  func_kbuild_source_one},
    5696   { STRING_SIZE_TUPLE("kb-exp-tmpl"),   6,  6,  1,  func_kbuild_expand_template},
     5939  FT_ENTRY ("kb-src-tool",   1,  1,  0,  func_kbuild_source_tool),
     5940  FT_ENTRY ("kb-obj-base",   1,  1,  0,  func_kbuild_object_base),
     5941  FT_ENTRY ("kb-obj-suff",   1,  1,  0,  func_kbuild_object_suffix),
     5942  FT_ENTRY ("kb-src-prop",   3,  4,  0,  func_kbuild_source_prop),
     5943  FT_ENTRY ("kb-src-one",    0,  1,  0,  func_kbuild_source_one),
     5944  FT_ENTRY ("kb-exp-tmpl",   6,  6,  1,  func_kbuild_expand_template),
    56975945#endif
    56985946#ifdef KMK
    5699   { STRING_SIZE_TUPLE("dircache-ctl"),  1,  0,  1,  func_dircache_ctl},
    5700   { STRING_SIZE_TUPLE("breakpoint"),    0,  0,  0,  func_breakpoint},
    5701   { STRING_SIZE_TUPLE("set-umask"),     1,  3,  1,  func_set_umask},
    5702   { STRING_SIZE_TUPLE("get-umask"),     0,  0,  0,  func_get_umask},
     5947  FT_ENTRY ("dircache-ctl",  1,  0,  1,  func_dircache_ctl),
     5948  FT_ENTRY ("breakpoint",    0,  0,  0,  func_breakpoint),
     5949  FT_ENTRY ("set-umask",     1,  3,  1,  func_set_umask),
     5950  FT_ENTRY ("get-umask",     0,  0,  0,  func_get_umask),
    57035951#endif
    57045952};
     
    57145962                         const struct function_table_entry *entry_p)
    57155963{
     5964  char *p;
     5965
    57165966  if (argc < (int)entry_p->minimum_args)
    5717     fatal (*expanding_var,
    5718            _("insufficient number of arguments (%d) to function `%s'"),
     5967    fatal (*expanding_var, strlen (entry_p->name),
     5968           _("insufficient number of arguments (%d) to function '%s'"),
    57195969           argc, entry_p->name);
    57205970
    5721   /* I suppose technically some function could do something with no
    5722      arguments, but so far none do, so just test it for all functions here
     5971  /* I suppose technically some function could do something with no arguments,
     5972     but so far no internal ones do, so just test it for all functions here
    57235973     rather than in each one.  We can change it later if necessary.  */
    57245974
    5725   if (!argc)
     5975  if (!argc && !entry_p->alloc_fn)
    57265976    return o;
    57275977
    5728   if (!entry_p->func_ptr)
    5729     fatal (*expanding_var,
    5730            _("unimplemented on this platform: function `%s'"), entry_p->name);
    5731 
    5732   return entry_p->func_ptr (o, argv, entry_p->name);
     5978  if (!entry_p->fptr.func_ptr)
     5979    OS (fatal, *expanding_var,
     5980        _("unimplemented on this platform: function '%s'"), entry_p->name);
     5981
     5982  if (!entry_p->alloc_fn)
     5983    return entry_p->fptr.func_ptr (o, argv, entry_p->name);
     5984
     5985  /* This function allocates memory and returns it to us.
     5986     Write it to the variable buffer, then free it.  */
     5987
     5988  p = entry_p->fptr.alloc_func_ptr (entry_p->name, argc, argv);
     5989  if (p)
     5990    {
     5991      o = variable_buffer_output (o, p, strlen (p));
     5992      free (p);
     5993    }
     5994
     5995  return o;
    57335996}
    57345997
     
    57556018     whitespace after the name).  */
    57566019
    5757   beg = next_token (beg + entry_p->len);
     6020  beg += entry_p->len;
     6021  NEXT_TOKEN (beg);
    57586022
    57596023  /* Find the end of the function invocation, counting nested use of
     
    57716035
    57726036  if (count >= 0)
    5773     fatal (*expanding_var,
    5774            _("unterminated call to function `%s': missing `%c'"),
    5775            entry_p->name, closeparen);
     6037    fatal (*expanding_var, strlen (entry_p->name),
     6038           _("unterminated call to function '%s': missing '%c'"),
     6039           entry_p->name, closeparen);
    57766040
    57776041  *stringp = end;
     
    58396103    for (argvp=argv; *argvp != 0; ++argvp)
    58406104      free (*argvp);
    5841   if (abeg)
     6105  else
    58426106    free (abeg);
    58436107
     
    58966160  static int max_args = 0;
    58976161  char *fname;
    5898   char *cp;
    58996162  char *body;
    59006163  int flen;
     
    59076170  unsigned int len;
    59086171#endif
     6172#ifdef CONFIG_WITH_VALUE_LENGTH
     6173  char *fname_end;
     6174#endif
    59096175#if defined (CONFIG_WITH_EVALPLUS) || defined (CONFIG_WITH_VALUE_LENGTH)
    59106176  char num[11];
    59116177#endif
    59126178
    5913   /* There is no way to define a variable with a space in the name, so strip
    5914      leading and trailing whitespace as a favor to the user.  */
    5915   fname = argv[0];
    5916   while (*fname != '\0' && isspace ((unsigned char)*fname))
    5917     ++fname;
    5918 
    5919   cp = fname + strlen (fname) - 1;
    5920   while (cp > fname && isspace ((unsigned char)*cp))
    5921     --cp;
    5922   cp[1] = '\0';
     6179  /* Clean up the name of the variable to be invoked.  */
     6180  fname = next_token (argv[0]);
     6181#ifndef CONFIG_WITH_VALUE_LENGTH
     6182  end_of_token (fname)[0] = '\0';
     6183#else
     6184  fname_end = end_of_token (fname);
     6185  *fname_end = '\0';
     6186#endif
    59236187
    59246188  /* Calling nothing is a no-op */
     6189#ifndef CONFIG_WITH_VALUE_LENGTH
    59256190  if (*fname == '\0')
     6191#else
     6192  if (fname == fname_end)
     6193#endif
    59266194    return o;
    59276195
     
    59316199  entry_p = lookup_function (fname);
    59326200#else
    5933   entry_p = lookup_function (fname, cp - fname + 1);
     6201  entry_p = lookup_function (fname, fname_end - fname);
    59346202#endif
    59356203  if (entry_p)
     
    60256293  else
    60266294    {
    6027       const struct floc *reading_file_saved = reading_file;
     6295      const floc *reading_file_saved = reading_file;
    60286296      char *eos;
    60296297
     
    60496317
    60506318      install_variable_buffer (&buf, &len);
    6051       eval_buffer (o, eos);
     6319      eval_buffer (o, NULL, eos);
    60526320      restore_variable_buffer (buf, len);
    60536321      reading_file = reading_file_saved;
     
    60796347
    60806348void
     6349define_new_function (const floc *flocp, const char *name,
     6350                     unsigned int min, unsigned int max, unsigned int flags,
     6351                     gmk_func_ptr func)
     6352{
     6353  const char *e = name;
     6354  struct function_table_entry *ent;
     6355  size_t len;
     6356
     6357  while (STOP_SET (*e, MAP_USERFUNC))
     6358    e++;
     6359  len = e - name;
     6360
     6361  if (len == 0)
     6362    O (fatal, flocp, _("Empty function name"));
     6363  if (*name == '.' || *e != '\0')
     6364    OS (fatal, flocp, _("Invalid function name: %s"), name);
     6365  if (len > 255)
     6366    OS (fatal, flocp, _("Function name too long: %s"), name);
     6367  if (min > 255)
     6368    ONS (fatal, flocp,
     6369         _("Invalid minimum argument count (%u) for function %s"), min, name);
     6370  if (max > 255 || (max && max < min))
     6371    ONS (fatal, flocp,
     6372         _("Invalid maximum argument count (%u) for function %s"), max, name);
     6373
     6374  ent = xmalloc (sizeof (struct function_table_entry));
     6375  ent->name = name;
     6376  ent->len = len;
     6377  ent->minimum_args = min;
     6378  ent->maximum_args = max;
     6379  ent->expand_args = ANY_SET(flags, GMK_FUNC_NOEXPAND) ? 0 : 1;
     6380  ent->alloc_fn = 1;
     6381  ent->fptr.alloc_func_ptr = func;
     6382
     6383  hash_insert (&function_table, ent);
     6384}
     6385
     6386void
    60816387hash_init_function_table (void)
    60826388{
    60836389  hash_init (&function_table, FUNCTION_TABLE_ENTRIES * 2,
    6084              function_table_entry_hash_1, function_table_entry_hash_2,
    6085              function_table_entry_hash_cmp);
     6390             function_table_entry_hash_1, function_table_entry_hash_2,
     6391             function_table_entry_hash_cmp);
    60866392  hash_load (&function_table, function_table_init,
    6087              FUNCTION_TABLE_ENTRIES, sizeof (struct function_table_entry));
     6393             FUNCTION_TABLE_ENTRIES, sizeof (struct function_table_entry));
    60886394#if defined (CONFIG_WITH_OPTIMIZATION_HACKS) || defined (CONFIG_WITH_VALUE_LENGTH)
    60896395  {
Note: See TracChangeset for help on using the changeset viewer.