1
by James Troup
Import upstream version 1.3.3 |
1 |
/********************************************
|
2 |
init.c
|
|
3 |
copyright 1991, Michael D. Brennan
|
|
4 |
||
5 |
This is a source file for mawk, an implementation of
|
|
6 |
the AWK programming language.
|
|
7 |
||
8 |
Mawk is distributed without warranty under the terms of
|
|
9 |
the GNU General Public License, version 2, 1991.
|
|
10 |
********************************************/
|
|
11 |
||
12 |
||
13 |
/* $Log: init.c,v $
|
|
14 |
* Revision 1.11 1995/08/20 17:35:21 mike
|
|
15 |
* include <stdlib.h> for MSC, needed for environ decl
|
|
16 |
*
|
|
17 |
* Revision 1.10 1995/06/09 22:51:50 mike
|
|
18 |
* silently exit(0) if no program
|
|
19 |
*
|
|
20 |
* Revision 1.9 1995/06/06 00:18:30 mike
|
|
21 |
* change mawk_exit(1) to mawk_exit(2)
|
|
22 |
*
|
|
23 |
* Revision 1.8 1994/12/14 14:40:34 mike
|
|
24 |
* -Wi option
|
|
25 |
*
|
|
26 |
* Revision 1.7 1994/12/11 22:43:20 mike
|
|
27 |
* don't assume **environ is writable
|
|
28 |
*
|
|
29 |
* Revision 1.6 1994/12/11 22:14:16 mike
|
|
30 |
* remove THINK_C #defines. Not a political statement, just no indication
|
|
31 |
* that anyone ever used it.
|
|
32 |
*
|
|
33 |
* Revision 1.5 1994/10/08 19:15:45 mike
|
|
34 |
* remove SM_DOS
|
|
35 |
*
|
|
36 |
* Revision 1.4 1994/03/11 02:23:49 mike
|
|
37 |
* -We option
|
|
38 |
*
|
|
39 |
* Revision 1.3 1993/07/17 00:45:14 mike
|
|
40 |
* indent
|
|
41 |
*
|
|
42 |
* Revision 1.2 1993/07/04 12:52:00 mike
|
|
43 |
* start on autoconfig changes
|
|
44 |
*
|
|
45 |
* Revision 5.5 1993/01/07 02:50:33 mike
|
|
46 |
* relative vs absolute code
|
|
47 |
*
|
|
48 |
* Revision 5.4 1992/12/24 01:58:19 mike
|
|
49 |
* 1.1.2d changes for MsDOS
|
|
50 |
*
|
|
51 |
* Revision 5.3 1992/07/10 16:17:10 brennan
|
|
52 |
* MsDOS: remove NO_BINMODE macro
|
|
53 |
*
|
|
54 |
* Revision 5.2 1992/01/09 08:46:14 brennan
|
|
55 |
* small change for MSC
|
|
56 |
*
|
|
57 |
* Revision 5.1 91/12/05 07:56:07 brennan
|
|
58 |
* 1.1 pre-release
|
|
59 |
*
|
|
60 |
*/
|
|
61 |
||
62 |
||
63 |
/* init.c */
|
|
64 |
#include "mawk.h" |
|
65 |
#include "code.h" |
|
66 |
#include "memory.h" |
|
67 |
#include "symtype.h" |
|
68 |
#include "init.h" |
|
69 |
#include "bi_vars.h" |
|
70 |
#include "field.h" |
|
71 |
||
72 |
#ifdef MSDOS
|
|
73 |
#include <fcntl.h> |
|
74 |
#ifdef MSDOS_MSC
|
|
75 |
#include <stdlib.h> |
|
76 |
#endif
|
|
77 |
#endif
|
|
78 |
||
79 |
static void PROTO(process_cmdline, (int, char **)) ; |
|
80 |
static void PROTO(set_ARGV, (int, char **, int)) ; |
|
81 |
static void PROTO(bad_option, (char *)) ; |
|
82 |
static void PROTO(no_program, (void)) ; |
|
83 |
||
84 |
extern void PROTO(print_version, (void)) ; |
|
85 |
extern int PROTO(is_cmdline_assign, (char *)) ; |
|
86 |
||
87 |
#if MSDOS
|
|
88 |
void PROTO(stdout_init, (void)) ; |
|
89 |
#if HAVE_REARGV
|
|
90 |
void PROTO(reargv, (int *, char ***)) ; |
|
91 |
#endif
|
|
92 |
#endif
|
|
93 |
||
94 |
char *progname ; |
|
95 |
short interactive_flag = 0 ; |
|
96 |
||
97 |
#ifndef SET_PROGNAME
|
|
98 |
#define SET_PROGNAME() \
|
|
99 |
{char *p = strrchr(argv[0],'/') ;\
|
|
100 |
progname = p ? p+1 : argv[0] ; }
|
|
101 |
#endif
|
|
102 |
||
103 |
void
|
|
104 |
initialize(argc, argv) |
|
105 |
int argc ; char **argv ; |
|
106 |
{
|
|
107 |
||
108 |
SET_PROGNAME() ; |
|
109 |
||
110 |
bi_vars_init() ; /* load the builtin variables */ |
|
111 |
bi_funct_init() ; /* load the builtin functions */ |
|
112 |
kw_init() ; /* load the keywords */ |
|
113 |
field_init() ; |
|
114 |
||
115 |
#if MSDOS
|
|
116 |
{
|
|
117 |
char *p = getenv("MAWKBINMODE") ; |
|
118 |
||
119 |
if (p) set_binmode(atoi(p)) ; |
|
120 |
}
|
|
121 |
#endif
|
|
122 |
||
123 |
||
124 |
process_cmdline(argc, argv) ; |
|
125 |
||
126 |
code_init() ; |
|
127 |
fpe_init() ; |
|
128 |
set_stderr() ; |
|
129 |
||
130 |
#if MSDOS
|
|
131 |
stdout_init() ; |
|
132 |
#endif
|
|
133 |
}
|
|
134 |
||
135 |
int dump_code_flag ; /* if on dump internal code */ |
|
136 |
short posix_space_flag ; |
|
137 |
||
138 |
#ifdef DEBUG
|
|
139 |
int dump_RE ; /* if on dump compiled REs */ |
|
140 |
#endif
|
|
141 |
||
142 |
||
143 |
static void |
|
144 |
bad_option(s) |
|
145 |
char *s ; |
|
146 |
{
|
|
147 |
errmsg(0, "not an option: %s", s) ; mawk_exit(2) ; |
|
148 |
}
|
|
149 |
||
150 |
static void |
|
151 |
no_program() |
|
152 |
{
|
|
153 |
mawk_exit(0) ; |
|
154 |
}
|
|
155 |
||
156 |
static void |
|
157 |
process_cmdline(argc, argv) |
|
158 |
int argc ; |
|
159 |
char **argv ; |
|
160 |
{
|
|
161 |
int i, nextarg ; |
|
162 |
char *optarg ; |
|
163 |
PFILE dummy ; /* starts linked list of filenames */ |
|
164 |
PFILE *tail = &dummy ; |
|
165 |
||
166 |
for (i = 1; i < argc && argv[i][0] == '-'; i = nextarg) |
|
167 |
{
|
|
168 |
if (argv[i][1] == 0) /* - alone */ |
|
169 |
{
|
|
170 |
if (!pfile_name) no_program() ; |
|
171 |
break ; /* the for loop */ |
|
172 |
}
|
|
173 |
/* safe to look at argv[i][2] */
|
|
174 |
||
175 |
if (argv[i][2] == 0) |
|
176 |
{
|
|
177 |
if (i == argc - 1 && argv[i][1] != '-') |
|
178 |
{
|
|
179 |
if (strchr("WFvf", argv[i][1])) |
|
180 |
{
|
|
181 |
errmsg(0, "option %s lacks argument", argv[i]) ; |
|
182 |
mawk_exit(2) ; |
|
183 |
}
|
|
184 |
bad_option(argv[i]) ; |
|
185 |
}
|
|
186 |
||
187 |
optarg = argv[i + 1] ; |
|
188 |
nextarg = i + 2 ; |
|
189 |
}
|
|
190 |
else /* argument glued to option */ |
|
191 |
{
|
|
192 |
optarg = &argv[i][2] ; |
|
193 |
nextarg = i + 1 ; |
|
194 |
}
|
|
195 |
||
196 |
switch (argv[i][1]) |
|
197 |
{
|
|
198 |
case 'W': |
|
199 |
||
200 |
if (optarg[0] >= 'a' && optarg[0] <= 'z') |
|
201 |
optarg[0] += 'A' - 'a' ; |
|
202 |
if (optarg[0] == 'V') print_version() ; |
|
203 |
else if (optarg[0] == 'D') |
|
204 |
{
|
|
205 |
dump_code_flag = 1 ; |
|
206 |
}
|
|
207 |
else if (optarg[0] == 'S') |
|
208 |
{
|
|
209 |
char *p = strchr(optarg, '=') ; |
|
210 |
int x = p ? atoi(p + 1) : 0 ; |
|
211 |
||
212 |
if (x > SPRINTF_SZ) |
|
213 |
{
|
|
214 |
sprintf_buff = (char *) zmalloc(x) ; |
|
215 |
sprintf_limit = sprintf_buff + x ; |
|
216 |
}
|
|
217 |
}
|
|
218 |
#if MSDOS
|
|
219 |
else if (optarg[0] == 'B') |
|
220 |
{
|
|
221 |
char *p = strchr(optarg, '=') ; |
|
222 |
int x = p ? atoi(p + 1) : 0 ; |
|
223 |
||
224 |
set_binmode(x) ; |
|
225 |
}
|
|
226 |
#endif
|
|
227 |
else if (optarg[0] == 'P') |
|
228 |
{
|
|
229 |
posix_space_flag = 1 ; |
|
230 |
}
|
|
231 |
else if (optarg[0] == 'E') |
|
232 |
{
|
|
233 |
if ( pfile_name ) |
|
234 |
{
|
|
235 |
errmsg(0, "-W exec is incompatible with -f") ; |
|
236 |
mawk_exit(2) ; |
|
237 |
}
|
|
238 |
else if ( nextarg == argc ) no_program() ; |
|
239 |
||
240 |
pfile_name = argv[nextarg] ; |
|
241 |
i = nextarg + 1 ; |
|
242 |
goto no_more_opts ; |
|
243 |
}
|
|
244 |
else if (optarg[0] == 'I') |
|
245 |
{
|
|
246 |
interactive_flag = 1 ; |
|
247 |
setbuf(stdout,(char*)0) ; |
|
248 |
}
|
|
249 |
else errmsg(0, "vacuous option: -W %s", optarg) ; |
|
250 |
||
251 |
||
252 |
break ; |
|
253 |
||
254 |
case 'v': |
|
255 |
if (!is_cmdline_assign(optarg)) |
|
256 |
{
|
|
257 |
errmsg(0, "improper assignment: -v %s", optarg) ; |
|
258 |
mawk_exit(2) ; |
|
259 |
}
|
|
260 |
break ; |
|
261 |
||
262 |
case 'F': |
|
263 |
||
264 |
rm_escape(optarg) ; /* recognize escape sequences */ |
|
265 |
cell_destroy(FS) ; |
|
266 |
FS->type = C_STRING ; |
|
267 |
FS->ptr = (PTR) new_STRING(optarg) ; |
|
268 |
cast_for_split(cellcpy(&fs_shadow, FS)) ; |
|
269 |
break ; |
|
270 |
||
271 |
case '-': |
|
272 |
if (argv[i][2] != 0) bad_option(argv[i]) ; |
|
273 |
i++ ; |
|
274 |
goto no_more_opts ; |
|
275 |
||
276 |
case 'f': |
|
277 |
/* first file goes in pfile_name ; any more go
|
|
278 |
on a list */
|
|
279 |
if (!pfile_name) pfile_name = optarg ; |
|
280 |
else
|
|
281 |
{
|
|
282 |
tail = tail->link = ZMALLOC(PFILE) ; |
|
283 |
tail->fname = optarg ; |
|
284 |
}
|
|
285 |
break ; |
|
286 |
||
287 |
default: |
|
288 |
bad_option(argv[i]) ; |
|
289 |
}
|
|
290 |
}
|
|
291 |
||
292 |
no_more_opts: |
|
293 |
||
294 |
tail->link = (PFILE *) 0 ; |
|
295 |
pfile_list = dummy.link ; |
|
296 |
||
297 |
if (pfile_name) |
|
298 |
{
|
|
299 |
set_ARGV(argc, argv, i) ; |
|
300 |
scan_init((char *) 0) ; |
|
301 |
}
|
|
302 |
else /* program on command line */ |
|
303 |
{
|
|
304 |
if (i == argc) no_program() ; |
|
305 |
set_ARGV(argc, argv, i + 1) ; |
|
306 |
||
307 |
#if MSDOS && ! HAVE_REARGV /* reversed quotes */ |
|
308 |
{
|
|
309 |
char *p ; |
|
310 |
||
311 |
for (p = argv[i]; *p; p++) |
|
312 |
if (*p == '\'') *p = '\"' ; |
|
313 |
}
|
|
314 |
#endif
|
|
315 |
scan_init(argv[i]) ; |
|
316 |
/* #endif */
|
|
317 |
}
|
|
318 |
}
|
|
319 |
||
320 |
||
321 |
static void |
|
322 |
set_ARGV(argc, argv, i) |
|
323 |
int argc ; char **argv ; |
|
324 |
int i ; /* argv[i] = ARGV[i] */ |
|
325 |
{
|
|
326 |
SYMTAB *st_p ; |
|
327 |
CELL argi ; |
|
328 |
register CELL *cp ; |
|
329 |
||
330 |
st_p = insert("ARGV") ; |
|
331 |
st_p->type = ST_ARRAY ; |
|
332 |
Argv = st_p->stval.array = new_ARRAY() ; |
|
333 |
argi.type = C_DOUBLE ; |
|
334 |
argi.dval = 0.0 ; |
|
335 |
cp = array_find(st_p->stval.array, &argi, CREATE) ; |
|
336 |
cp->type = C_STRING ; |
|
337 |
cp->ptr = (PTR) new_STRING(progname) ; |
|
338 |
||
339 |
/* ARGV[0] is set, do the rest
|
|
340 |
The type of ARGV[1] ... should be C_MBSTRN
|
|
341 |
because the user might enter numbers from the command line */
|
|
342 |
||
343 |
for (argi.dval = 1.0; i < argc; i++, argi.dval += 1.0) |
|
344 |
{
|
|
345 |
cp = array_find(st_p->stval.array, &argi, CREATE) ; |
|
346 |
cp->type = C_MBSTRN ; |
|
347 |
cp->ptr = (PTR) new_STRING(argv[i]) ; |
|
348 |
}
|
|
349 |
ARGC->type = C_DOUBLE ; |
|
350 |
ARGC->dval = argi.dval ; |
|
351 |
}
|
|
352 |
||
353 |
||
354 |
/*----- ENVIRON ----------*/
|
|
355 |
||
356 |
void
|
|
357 |
load_environ(ENV) |
|
358 |
ARRAY ENV ; |
|
359 |
{
|
|
360 |
CELL c ; |
|
361 |
#ifndef MSDOS_MSC /* MSC declares it near */ |
|
362 |
extern char **environ ; |
|
363 |
#endif
|
|
364 |
register char **p = environ ; /* walks environ */ |
|
365 |
char *s ; /* looks for the '=' */ |
|
366 |
CELL *cp ; /* pts at ENV[&c] */ |
|
367 |
||
368 |
c.type = C_STRING ; |
|
369 |
||
370 |
while (*p) |
|
371 |
{
|
|
372 |
if (s = strchr(*p, '=')) /* shouldn't fail */ |
|
3
by James Troup
* 08_fix-for-gcc3.3.dpatch: grossly hack configure to work around |
373 |
{
|
1
by James Troup
Import upstream version 1.3.3 |
374 |
int len = s - *p ; |
375 |
c.ptr = (PTR) new_STRING0(len) ; |
|
376 |
memcpy(string(&c)->str, *p, len) ; |
|
377 |
s++ ; |
|
378 |
||
379 |
cp = array_find(ENV, &c, CREATE) ; |
|
380 |
cp->type = C_MBSTRN ; |
|
381 |
cp->ptr = (PTR) new_STRING(s) ; |
|
382 |
||
383 |
free_STRING(string(&c)) ; |
|
384 |
}
|
|
385 |
p++ ; |
|
386 |
}
|
|
387 |
}
|
|
388 |