Mercurial > octave
comparison kpathsea/variable.c @ 1268:76a0c05089d4
[project @ 1995-04-20 19:15:51 by jwe]
Initial revision
author | jwe |
---|---|
date | Thu, 20 Apr 1995 19:15:51 +0000 |
parents | |
children | 611d403c7f3d |
comparison
equal
deleted
inserted
replaced
1267:69501f98669d | 1268:76a0c05089d4 |
---|---|
1 /* variable.c: variable expansion. | |
2 | |
3 Copyright (C) 1993, 94 Karl Berry. | |
4 | |
5 This program is free software; you can redistribute it and/or modify | |
6 it under the terms of the GNU General Public License as published by | |
7 the Free Software Foundation; either version 2, or (at your option) | |
8 any later version. | |
9 | |
10 This program is distributed in the hope that it will be useful, | |
11 but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
13 GNU General Public License for more details. | |
14 | |
15 You should have received a copy of the GNU General Public License | |
16 along with this program; if not, write to the Free Software | |
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ | |
18 | |
19 #include <kpathsea/config.h> | |
20 | |
21 #include <kpathsea/c-ctype.h> | |
22 #include <kpathsea/cnf.h> | |
23 #include <kpathsea/fn.h> | |
24 #include <kpathsea/variable.h> | |
25 | |
26 | |
27 /* Append the result of value of `var' to EXPANSION, where `var' begins | |
28 at START and ends at END. If `var' is not set, do not complain. */ | |
29 | |
30 static void | |
31 expand P3C(fn_type *, expansion, const_string, start, const_string, end) | |
32 { | |
33 string value; | |
34 unsigned len = end - start + 1; | |
35 string var = xmalloc (len + 1); | |
36 strncpy (var, start, len); | |
37 var[len] = 0; | |
38 | |
39 /* First check the environment variable. */ | |
40 value = getenv (var); | |
41 | |
42 /* If no envvar, check the config files. */ | |
43 if (!value) | |
44 value = kpse_cnf_get (var); | |
45 | |
46 if (value) | |
47 { | |
48 value = kpse_var_expand (value); | |
49 fn_grow (expansion, value, strlen (value)); | |
50 free (value); | |
51 } | |
52 | |
53 free (var); | |
54 } | |
55 | |
56 /* Can't think of when it would be useful to change these (and the | |
57 diagnostic messages assume them), but ... */ | |
58 #ifndef IS_VAR_START /* starts all variable references */ | |
59 #define IS_VAR_START(c) ((c) == '$') | |
60 #endif | |
61 #ifndef IS_VAR_CHAR /* variable name constituent */ | |
62 #define IS_VAR_CHAR(c) (ISALNUM (c) || (c) == '_') | |
63 #endif | |
64 #ifndef IS_VAR_BEGIN_DELIMITER /* start delimited variable name (after $) */ | |
65 #define IS_VAR_BEGIN_DELIMITER(c) ((c) == '{') | |
66 #endif | |
67 #ifndef IS_VAR_END_DELIMITER | |
68 #define IS_VAR_END_DELIMITER(c) ((c) == '}') | |
69 #endif | |
70 | |
71 | |
72 /* Maybe we should generalize to allow some or all of the various shell | |
73 ${...} constructs, especially ${var-value}. */ | |
74 | |
75 string | |
76 kpse_var_expand P1C(const_string, src) | |
77 { | |
78 const_string s; | |
79 string ret; | |
80 fn_type expansion; | |
81 expansion = fn_init (); | |
82 | |
83 /* Copy everything but variable constructs. */ | |
84 for (s = src; *s; s++) | |
85 { | |
86 if (IS_VAR_START (*s)) | |
87 { | |
88 s++; | |
89 | |
90 /* Three cases: `$VAR', `${VAR}', `$<anything-else>'. */ | |
91 | |
92 if (IS_VAR_CHAR (*s)) | |
93 { /* $V: collect name constituents, then expand. */ | |
94 const_string var_end = s; | |
95 | |
96 do | |
97 var_end++; | |
98 while (IS_VAR_CHAR (*var_end)); | |
99 | |
100 var_end--; /* had to go one past */ | |
101 expand (&expansion, s, var_end); | |
102 s = var_end; | |
103 } | |
104 | |
105 else if (IS_VAR_BEGIN_DELIMITER (*s)) | |
106 { /* ${: scan ahead for matching delimiter, then expand. */ | |
107 const_string var_end = ++s; | |
108 | |
109 while (*var_end && !IS_VAR_END_DELIMITER (*var_end)) | |
110 var_end++; | |
111 | |
112 if (! *var_end) | |
113 { | |
114 WARNING1 ("%s: No matching right brace for ${", src); | |
115 s = var_end - 1; /* will incr to null at top of loop */ | |
116 } | |
117 else | |
118 { | |
119 expand (&expansion, s, var_end - 1); | |
120 s = var_end; /* will incr past } at top of loop*/ | |
121 } | |
122 } | |
123 | |
124 | |
125 else | |
126 { /* $<something-else>: error. */ | |
127 WARNING2 ("%s: Unrecognized variable construct `$%c'", src, *s); | |
128 /* Just ignore those chars and keep going. */ | |
129 } | |
130 } | |
131 else | |
132 fn_1grow (&expansion, *s); | |
133 } | |
134 fn_1grow (&expansion, 0); | |
135 | |
136 ret = FN_STRING (expansion); | |
137 return ret; | |
138 } | |
139 | |
140 #ifdef TEST | |
141 | |
142 static void | |
143 test_var (string test, string right_answer) | |
144 { | |
145 string result = kpse_var_expand (test); | |
146 | |
147 printf ("expansion of `%s'\t=> %s", test, result); | |
148 if (!STREQ (result, right_answer)) | |
149 printf (" [should be `%s']", right_answer); | |
150 putchar ('\n'); | |
151 } | |
152 | |
153 | |
154 int | |
155 main () | |
156 { | |
157 test_var ("a", "a"); | |
158 test_var ("$foo", ""); | |
159 test_var ("a$foo", "a"); | |
160 test_var ("$foo a", " a"); | |
161 test_var ("a$foo b", "a b"); | |
162 | |
163 xputenv ("FOO", "foo value"); | |
164 test_var ("a$FOO", "afoo value"); | |
165 | |
166 xputenv ("Dollar", "$"); | |
167 test_var ("$Dollar a", "$ a"); | |
168 | |
169 test_var ("a${FOO}b", "afoo valueb"); | |
170 test_var ("a${}b", "ab"); | |
171 | |
172 test_var ("$$", ""); /* and error */ | |
173 test_var ("a${oops", "a"); /* and error */ | |
174 | |
175 return 0; | |
176 } | |
177 | |
178 #endif /* TEST */ | |
179 | |
180 | |
181 /* | |
182 Local variables: | |
183 standalone-compile-command: "gcc -g -I. -I.. -DTEST variable.c kpathsea.a" | |
184 End: | |
185 */ |