~vcs-imports/gawk/master

« back to all changes in this revision

Viewing changes to gawkapi.h

  • Committer: Andrew J. Schorr
  • Date: 2014-08-03 18:44:47 UTC
  • mfrom: (408.7.1)
  • mto: (408.2.352)
  • mto: This revision was merged to the branch mainline in revision 507.
  • Revision ID: git-v1:ff21da5c7f072a69e9582f1a7ae2039f27f564cf
Merge branch 'gawk-4.1-stable' to get --profile to work with -M.

Show diffs side-by-side

added added

removed removed

Lines of Context:
2
2
 * gawkapi.h -- Definitions for use by extension functions calling into gawk.
3
3
 */
4
4
 
5
 
/*
6
 
 * copyright (c) 2012-2019, 2021-2024, the free software foundation, inc.
7
 
 *
 
5
/* 
 
6
 * Copyright (C) 2012-2014 the Free Software Foundation, Inc.
 
7
 * 
8
8
 * This file is part of GAWK, the GNU implementation of the
9
9
 * AWK Programming Language.
10
 
 *
 
10
 * 
11
11
 * GAWK is free software; you can redistribute it and/or modify
12
12
 * it under the terms of the GNU General Public License as published by
13
13
 * the Free Software Foundation; either version 3 of the License, or
14
14
 * (at your option) any later version.
15
 
 *
 
15
 * 
16
16
 * GAWK is distributed in the hope that it will be useful,
17
17
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18
18
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19
19
 * GNU General Public License for more details.
20
 
 *
 
20
 * 
21
21
 * You should have received a copy of the GNU General Public License
22
22
 * along with this program; if not, write to the Free Software
23
23
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
53
53
 * This API purposely restricts itself to ISO C 90 features.  In particular, no
54
54
 * bool, no // comments, no use of the restrict keyword, or anything else,
55
55
 * in order to provide maximal portability.
56
 
 *
 
56
 * 
57
57
 * Exception: the "inline" keyword is used below in the "constructor"
58
58
 * functions. If your compiler doesn't support it, you should either
59
59
 * -Dinline='' on your command line, or use the autotools and include a
98
98
 * for arrays that will have subarrays as elements; however it is
99
99
 * a good idea to always do this.  This restriction may be relaxed
100
100
 * in a subsequent revision of the API.
101
 
 *
102
 
 * 3. While each routine in the API has a few lines of summary for it
103
 
 * in this header, said summaries are not standalone, adequate documentation. You
104
 
 * should read the chapter in the gawk manual on writing extensions. Find it online
105
 
 * at https://www.gnu.org/software/gawk/manual/html_node/Dynamic-Extensions.html,
106
 
 * or in the Info files distributed with gawk.
107
101
 */
108
102
 
109
103
/* Allow use in C++ code.  */
123
117
        awk_true
124
118
} awk_bool_t;   /* we don't use <stdbool.h> on purpose */
125
119
 
126
 
/*
127
 
 * If an input parser would like to specify the field positions in the input
128
 
 * record, it may populate an awk_fieldwidth_info_t structure to indicate
129
 
 * the location of each field. The use_chars boolean controls whether the
130
 
 * field lengths are specified in terms of bytes or potentially multi-byte
131
 
 * characters. Performance will be better if the values are supplied in
132
 
 * terms of bytes. The fields[0].skip value indicates how many bytes (or
133
 
 * characters) to skip before $1, and fields[0].len is the length of $1, etc.
134
 
 */
135
 
 
136
 
typedef struct {
137
 
        awk_bool_t      use_chars;      /* false ==> use bytes */
138
 
        size_t          nf;
139
 
        struct awk_field_info {
140
 
                size_t  skip;   /* amount to skip before field starts */
141
 
                size_t  len;    /* length of field */
142
 
        } fields[1];            /* actual dimension should be nf */
143
 
} awk_fieldwidth_info_t;
144
 
 
145
 
/*
146
 
 * This macro calculates the total struct size needed. This is useful when
147
 
 * calling malloc or realloc.
148
 
 */
149
 
#define awk_fieldwidth_info_size(NF) (sizeof(awk_fieldwidth_info_t) + \
150
 
                        (((NF)-1) * sizeof(struct awk_field_info)))
151
 
 
152
120
/* The information about input files that input parsers need to know: */
153
121
typedef struct awk_input {
154
122
        const char *name;       /* filename */
155
123
        int fd;                 /* file descriptor */
156
124
#define INVALID_HANDLE (-1)
157
125
        void *opaque;           /* private data for input parsers */
158
 
 
159
126
        /*
160
127
         * The get_record function is called to read the next record of data.
161
128
         *
169
136
         * parser is responsible for managing its own memory buffer.
170
137
         * Similarly, gawk will make its own copy of RT, so the parser
171
138
         * is also responsible for managing this memory.
172
 
         *
 
139
         * 
173
140
         * It is guaranteed that errcode is a valid pointer, so there is
174
141
         * no need to test for a NULL value.  Gawk sets *errcode to 0,
175
142
         * so there is no need to set it unless an error occurs.
176
143
         *
177
144
         * If an error does occur, the function should return EOF and set
178
 
         * *errcode to a positive value.  In that case, if *errcode is greater
179
 
         * than zero, gawk will automatically update the ERRNO variable based
 
145
         * *errcode to a non-zero value.  In that case, if *errcode does not
 
146
         * equal -1, gawk will automatically update the ERRNO variable based
180
147
         * on the value of *errcode (e.g., setting *errcode = errno should do
181
148
         * the right thing).
182
 
         *
183
 
         * If field_width is non-NULL, then *field_width will be initialized
184
 
         * to NULL, and the function may set it to point to a structure
185
 
         * supplying field width information to override the default
186
 
         * gawk field parsing mechanism. Note that this structure will not
187
 
         * be copied by gawk; it must persist at least until the next call
188
 
         * to get_record or close_func. Note also that field_width will
189
 
         * be NULL when getline is assigning the results to a variable, thus
190
 
         * field parsing is not needed.
191
149
         */
192
150
        int (*get_record)(char **out, struct awk_input *iobuf, int *errcode,
193
 
                        char **rt_start, size_t *rt_len,
194
 
                        const awk_fieldwidth_info_t **field_width);
 
151
                        char **rt_start, size_t *rt_len);
195
152
 
196
153
        /*
197
 
         * This replaces the POSIX read() system call. Use it if you want to
198
 
         * manage reading raw bytes yourself, and let gawk parse the record.
 
154
         * No argument prototype on read_func to allow for older systems
 
155
         * whose headers are not up to date.
199
156
         */
200
 
        ssize_t (*read_func)(int, void *, size_t);
 
157
        ssize_t (*read_func)();
201
158
 
202
159
        /*
203
160
         * The close_func is called to allow the parser to free private data.
208
165
 
209
166
        /* put last, for alignment. bleah */
210
167
        struct stat sbuf;       /* stat buf */
211
 
 
 
168
                                                        
212
169
} awk_input_buf_t;
213
170
 
214
171
typedef struct awk_input_parser {
215
172
        const char *name;       /* name of parser */
216
173
 
217
174
        /*
218
 
         * The can_take_file function should return true if the parser
 
175
         * The can_take_file function should return non-zero if the parser
219
176
         * would like to parse this file.  It should not change any gawk
220
177
         * state!
221
178
         */
226
183
         * It can assume that a previous call to can_take_file was successful,
227
184
         * and no gawk state has changed since that call.  It should populate
228
185
         * the awk_input_buf_t's get_record, close_func, and opaque values as needed.
229
 
         * It should return true if successful.
 
186
         * It should return non-zero if successful.
230
187
         */
231
188
        awk_bool_t (*take_control_of)(awk_input_buf_t *iobuf);
232
189
 
261
218
        const char *name;       /* name of the wrapper */
262
219
 
263
220
        /*
264
 
         * The can_take_file function should return true if the wrapper
 
221
         * The can_take_file function should return non-zero if the wrapper
265
222
         * would like to process this file.  It should not change any gawk
266
223
         * state!
267
224
         */
272
229
         * It can assume that a previous call to can_take_file was successful,
273
230
         * and no gawk state has changed since that call.  It should populate
274
231
         * the awk_output_buf_t function pointers and opaque pointer as needed.
275
 
         * It should return true if successful.
 
232
         * It should return non-zero if successful.
276
233
         */
277
234
        awk_bool_t (*take_control_of)(awk_output_buf_t *outbuf);
278
235
 
284
241
        const char *name;       /* name of the two-way processor */
285
242
 
286
243
        /*
287
 
         * The can_take_file function should return true if the two-way
 
244
         * The can_take_file function should return non-zero if the two-way
288
245
         * processor would like to parse this file.  It should not change
289
246
         * any gawk state!
290
247
         */
295
252
         * It can assume that a previous call to can_take_file was successful,
296
253
         * and no gawk state has changed since that call.  It should populate
297
254
         * the awk_input_buf_t and awk_otuput_buf_t structures as needed.
298
 
         * It should return true if successful.
 
255
         * It should return non-zero if successful.
299
256
         */
300
257
        awk_bool_t (*take_control_of)(const char *name, awk_input_buf_t *inbuf,
301
258
                                        awk_output_buf_t *outbuf);
303
260
        awk_const struct awk_two_way_processor *awk_const next;  /* for use by gawk */
304
261
} awk_two_way_processor_t;
305
262
 
306
 
#define gawk_api_major_version 4
307
 
#define gawk_api_minor_version 0
308
 
 
309
263
/* Current version of the API. */
310
264
enum {
311
 
        GAWK_API_MAJOR_VERSION = gawk_api_major_version,
312
 
        GAWK_API_MINOR_VERSION = gawk_api_minor_version
 
265
        GAWK_API_MAJOR_VERSION = 1,
 
266
        GAWK_API_MINOR_VERSION = 1
313
267
};
314
268
 
315
269
/* A number of typedefs related to different types of values. */
321
275
 * The API deals exclusively with regular chars; these strings may
322
276
 * be multibyte encoded in the current locale's encoding and character
323
277
 * set. Gawk will convert internally to wide characters if necessary.
324
 
 *
325
 
 * Note that a string provided by gawk will always be terminated
326
 
 * with a '\0' character.
327
278
 */
328
279
typedef struct awk_string {
329
280
        char *str;      /* data */
330
281
        size_t len;     /* length thereof, in chars */
331
282
} awk_string_t;
332
283
 
333
 
enum AWK_NUMBER_TYPE {
334
 
        AWK_NUMBER_TYPE_DOUBLE,
335
 
        AWK_NUMBER_TYPE_MPFR,
336
 
        AWK_NUMBER_TYPE_MPZ
337
 
};
338
 
 
339
 
/*
340
 
 * When type is AWK_NUMBER_MPFR or AWK_NUMBER_MPZ, the memory pointed to
341
 
 * by the ptr member belongs to gawk if it came from gawk.  Otherwise the
342
 
 * memory belongs to the extension and gawk copies it when its received.
343
 
 * See the manual for further discussion.
344
 
 */
345
 
 
346
 
typedef struct awk_number {
347
 
        double d;       /* always populated in data received from gawk */
348
 
        enum AWK_NUMBER_TYPE type;
349
 
        void *ptr;      /* either NULL or mpfr_ptr or mpz_ptr */
350
 
} awk_number_t;
351
 
 
352
284
/* Arrays are represented as an opaque type. */
353
285
typedef void *awk_array_t;
354
286
 
369
301
        AWK_UNDEFINED,
370
302
        AWK_NUMBER,
371
303
        AWK_STRING,
372
 
        AWK_REGEX,
373
 
        AWK_STRNUM,
374
304
        AWK_ARRAY,
375
305
        AWK_SCALAR,             /* opaque access to a variable */
376
 
        AWK_VALUE_COOKIE,       /* for updating a previously created value */
377
 
        AWK_BOOL
 
306
        AWK_VALUE_COOKIE        /* for updating a previously created value */
378
307
} awk_valtype_t;
379
308
 
380
309
/*
385
314
        awk_valtype_t   val_type;
386
315
        union {
387
316
                awk_string_t    s;
388
 
                awk_number_t    n;
 
317
                double          d;
389
318
                awk_array_t     a;
390
319
                awk_scalar_t    scl;
391
320
                awk_value_cookie_t vc;
392
 
                awk_bool_t      b;
393
321
        } u;
394
322
#define str_value       u.s
395
 
#define strnum_value    str_value
396
 
#define regex_value     str_value
397
 
#define num_value       u.n.d
398
 
#define num_type        u.n.type
399
 
#define num_ptr         u.n.ptr
 
323
#define num_value       u.d
400
324
#define array_cookie    u.a
401
325
#define scalar_cookie   u.scl
402
326
#define value_cookie    u.vc
403
 
#define bool_value      u.b
404
327
} awk_value_t;
405
328
 
406
329
/*
419
342
                AWK_ELEMENT_DELETE = 1          /* set by extension if
420
343
                                                   should be deleted */
421
344
        } flags;
422
 
        awk_value_t     index;
 
345
        awk_value_t     index;                  /* guaranteed to be a string! */
423
346
        awk_value_t     value;
424
347
} awk_element_t;
425
348
 
439
362
 * loaded, the extension should pass in one of these to gawk for
440
363
 * each C function.
441
364
 *
442
 
 * Each called function must fill in the result with either a scalar
443
 
 * (number, string, or regex). Gawk takes ownership of any string memory.
 
365
 * Each called function must fill in the result with either a number
 
366
 * or string. Gawk takes ownership of any string memory.
444
367
 *
445
368
 * The called function must return the value of `result'.
446
369
 * This is for the convenience of the calling code inside gawk.
448
371
 * Each extension function may decide what to do if the number of
449
372
 * arguments isn't what it expected.  Following awk functions, it
450
373
 * is likely OK to ignore extra arguments.
451
 
 *
452
 
 * 'min_required_args' indicates how many arguments MUST be passed.
453
 
 * The API will throw a fatal error if not enough are passed.
454
 
 *
455
 
 * 'max_expected_args' is more benign; if more than that are passed,
456
 
 * the API prints a lint message (IFF lint is enabled, of course).
457
 
 *
458
 
 * In any case, the extension function itself need not compare the
459
 
 * actual number of arguments passed to those two values if it does
460
 
 * not want to.
461
374
 */
462
375
typedef struct awk_ext_func {
463
376
        const char *name;
464
 
        awk_value_t *(*const function)(int num_actual_args,
465
 
                                        awk_value_t *result,
466
 
                                        struct awk_ext_func *finfo);
467
 
        const size_t max_expected_args;
468
 
        const size_t min_required_args;
469
 
        awk_bool_t suppress_lint;
470
 
        void *data;             /* opaque pointer to any extra state */
 
377
        awk_value_t *(*function)(int num_actual_args, awk_value_t *result);
 
378
        size_t num_expected_args;
471
379
} awk_ext_func_t;
472
380
 
473
381
typedef void *awk_ext_id_t;     /* opaque type for extension id */
475
383
/*
476
384
 * The API into gawk. Lots of functions here. We hope that they are
477
385
 * logically organized.
478
 
 *
479
 
 * !!! If you make any changes to this structure, please remember to bump !!!
480
 
 * !!! gawk_api_major_version and/or gawk_api_minor_version.              !!!
481
386
 */
482
387
typedef struct gawk_api {
483
388
        /* First, data fields. */
486
391
        awk_const int major_version;
487
392
        awk_const int minor_version;
488
393
 
489
 
        /* GMP/MPFR versions, if extended-precision is available */
490
 
        awk_const int gmp_major_version;
491
 
        awk_const int gmp_minor_version;
492
 
        awk_const int mpfr_major_version;
493
 
        awk_const int mpfr_minor_version;
494
 
 
495
394
        /*
496
395
         * These can change on the fly as things happen within gawk.
497
396
         * Currently only do_lint is prone to change, but we reserve
498
397
         * the right to allow the others to do so also.
499
 
         *
500
 
         * N.B. If we ever again need to add an additional do_flags value,
501
 
         * it would be wise to convert this from an array to a bitmask. If
502
 
         * we add a new do_flags value and bump DO_FLAGS_SIZE, then it requires
503
 
         * us to increment the ABI version. If we use a bitmask instead, then
504
 
         * we will be free to add new flags without breaking ABI compatibility.
505
398
         */
506
 
#define DO_FLAGS_SIZE   7
 
399
#define DO_FLAGS_SIZE   6
507
400
        awk_const int do_flags[DO_FLAGS_SIZE];
508
401
/* Use these as indices into do_flags[] array to check the values */
509
402
#define gawk_do_lint            0
512
405
#define gawk_do_sandbox         3
513
406
#define gawk_do_debug           4
514
407
#define gawk_do_mpfr            5
515
 
#define gawk_do_csv             6
516
408
 
517
409
        /* Next, registration functions: */
518
410
 
519
 
        /*
520
 
         * Add a function to the interpreter, returns true upon success.
521
 
         * Gawk does not modify what func points to, but the extension
522
 
         * function itself receives this pointer and can modify what it
523
 
         * points to, thus it's not const.
524
 
         */
525
 
        awk_bool_t (*api_add_ext_func)(awk_ext_id_t id, const char *name_space,
526
 
                        awk_ext_func_t *func);
 
411
        /* Add a function to the interpreter, returns true upon success */
 
412
        awk_bool_t (*api_add_ext_func)(awk_ext_id_t id, const char *namespace,
 
413
                        const awk_ext_func_t *func);
527
414
 
528
415
        /* Register an input parser; for opening files read-only */
529
416
        void (*api_register_input_parser)(awk_ext_id_t id,
557
444
        void (*api_fatal)(awk_ext_id_t id, const char *format, ...);
558
445
        void (*api_warning)(awk_ext_id_t id, const char *format, ...);
559
446
        void (*api_lintwarn)(awk_ext_id_t id, const char *format, ...);
560
 
        void (*api_nonfatal)(awk_ext_id_t id, const char *format, ...);
561
447
 
562
448
        /* Functions to update ERRNO */
563
449
        void (*api_update_ERRNO_int)(awk_ext_id_t id, int errno_val);
570
456
         * behave in the same way.
571
457
         *
572
458
         * For a function parameter, the return is false if the argument
573
 
         * count is out of range, or if the actual parameter does not match
 
459
         * count is out of range, or if actual paramater does not match
574
460
         * what is specified in wanted. In that case,  result->val_type
575
461
         * will hold the actual type of what was passed.
576
462
         *
577
463
         * Similarly for symbol table access to variables and array elements,
578
464
         * the return is false if the actual variable or array element does
579
 
         * not match what was requested, and result->val_type will hold
 
465
         * not match what was requested, and the result->val_type will hold
580
466
         * the actual type.
581
467
 
582
468
        Table entry is type returned:
583
469
 
584
470
 
585
 
                                +----------------------------------------------------------------+
586
 
                                |                        Type of Actual Value:                   |
587
 
                                +--------+--------+--------+--------+--------+-------+-----------+
588
 
                                | String | Strnum | Number | Regex  | Bool   | Array | Undefined |
589
 
        +-----------+-----------+--------+--------+--------+--------+--------+-------+-----------+
590
 
        |           | String    | String | String | String | String | String | false | false     |
591
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
592
 
        |           | Strnum    | false  | Strnum | Strnum | false  | false  | false | false     |
593
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
594
 
        |           | Number    | Number | Number | Number | false  | Number | false | false     |
595
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
596
 
        |           | Regex     | false  | false  | false  | Regex  | false  | false | false     |
597
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
598
 
        |   Type    | Bool      | false  | false  | false  | false  | Bool   | false | false     |
599
 
        | Requested +-----------+--------+--------+--------+--------+--------+-------+-----------+
600
 
        |           | Array     | false  | false  | false  | false  | false  | Array | false     |
601
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
602
 
        |           | Scalar    | Scalar | Scalar | Scalar | Scalar | Scalar | false | false     |
603
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
604
 
        |           | Undefined | String | Strnum | Number | Regex  | Bool   | Array | Undefined |
605
 
        |           +-----------+--------+--------+--------+--------+--------+-------+-----------+
606
 
        |           | Value     | false  | false  | false  | false  | false  | false | false     |
607
 
        |           | Cookie    |        |        |        |        |        |       |           |
608
 
        +-----------+-----------+--------+--------+--------+--------+--------+-------+-----------+
 
471
                                +-------------------------------------------------+
 
472
                                |                Type of Actual Value:            |
 
473
                                +------------+------------+-----------+-----------+
 
474
                                |   String   |   Number   | Array     | Undefined |
 
475
        +-----------+-----------+------------+------------+-----------+-----------+
 
476
        |           | String    |   String   |   String   | false     | false     |
 
477
        |           |-----------+------------+------------+-----------+-----------+
 
478
        |           | Number    | Number if  |   Number   | false     | false     |
 
479
        |           |           | can be     |            |           |           |
 
480
        |           |           | converted, |            |           |           |
 
481
        |           |           | else false |            |           |           |
 
482
        |           |-----------+------------+------------+-----------+-----------+
 
483
        |   Type    | Array     |   false    |   false    | Array     | false     |
 
484
        | Requested |-----------+------------+------------+-----------+-----------+
 
485
        |           | Scalar    |   Scalar   |   Scalar   | false     | false     |
 
486
        |           |-----------+------------+------------+-----------+-----------+
 
487
        |           | Undefined |  String    |   Number   | Array     | Undefined |
 
488
        |           |-----------+------------+------------+-----------+-----------+
 
489
        |           | Value     |   false    |   false    | false     | false     |
 
490
        |           | Cookie    |            |            |           |           |
 
491
        +-----------+-----------+------------+------------+-----------+-----------+
609
492
        */
610
493
 
611
494
        /* Functions to handle parameters passed to the extension. */
612
495
 
613
496
        /*
614
 
         * Get the count'th parameter, zero-based.
615
 
         * Returns false if count is out of range, or if actual parameter
 
497
         * Get the count'th paramater, zero-based.
 
498
         * Returns false if count is out of range, or if actual paramater
616
499
         * does not match what is specified in wanted. In that case,
617
500
         * result->val_type is as described above.
618
501
         */
621
504
                                          awk_value_t *result);
622
505
 
623
506
        /*
624
 
         * Convert a parameter that was undefined into an array
 
507
         * Convert a paramter that was undefined into an array
625
508
         * (provide call-by-reference for arrays).  Returns false
626
509
         * if count is too big, or if the argument's type is
627
510
         * not undefined.
635
518
         *      - Read-only access to special variables (NF, etc.)
636
519
         *      - One special exception: PROCINFO.
637
520
         *      - Use sym_update() to change a value, including from UNDEFINED
638
 
         *        to scalar or array.
 
521
         *        to scalar or array. 
639
522
         */
640
523
        /*
641
524
         * Lookup a variable, fill in value. No messing with the value
642
525
         * returned.
643
 
         * Returns false if the variable doesn't exist or if the wrong type
 
526
         * Returns false if the variable doesn't exist* or if the wrong type
644
527
         * was requested.  In the latter case, vaule->val_type will have
645
528
         * the real type, as described above.
646
529
         *
652
535
         *      }
653
536
         */
654
537
        awk_bool_t (*api_sym_lookup)(awk_ext_id_t id,
655
 
                                const char *name_space,
656
538
                                const char *name,
657
539
                                awk_valtype_t wanted,
658
540
                                awk_value_t *result);
664
546
         * Such an attempt returns false.
665
547
         */
666
548
        awk_bool_t (*api_sym_update)(awk_ext_id_t id,
667
 
                                const char *name_space,
668
549
                                const char *name,
669
550
                                awk_value_t *value);
670
551
 
704
585
         *              use the scalar cookie
705
586
         *
706
587
         * Return will be false if the new value is not one of
707
 
         * AWK_STRING, AWK_NUMBER, AWK_REGEX.
 
588
         * AWK_STRING or AWK_NUMBER.
708
589
         *
709
590
         * Here too, the built-in variables may not be updated.
710
591
         */
714
595
        /* Cached values */
715
596
 
716
597
        /*
717
 
         * Create a cached string,regex, or numeric value for efficient later
 
598
         * Create a cached string or numeric value for efficient later
718
599
         * assignment. This improves performance when you want to assign
719
600
         * the same value to one or more variables repeatedly.  Only
720
 
         * AWK_NUMBER, AWK_STRING, AWK_REGEX and AWK_STRNUM values are allowed.
721
 
         * Any other type is rejected.  We disallow AWK_UNDEFINED since that
722
 
         * case would result in inferior performance.
 
601
         * AWK_NUMBER and AWK_STRING values are allowed.  Any other type
 
602
         * is rejected.  We disallow AWK_UNDEFINED since that case would
 
603
         * result in inferior performance.
723
604
         */
724
605
        awk_bool_t (*api_create_value)(awk_ext_id_t id, awk_value_t *value,
725
606
                    awk_value_cookie_t *result);
763
644
 
764
645
        /*
765
646
         * Remove the element with the given index.
766
 
         * Returns true if removed or false if element did not exist.
 
647
         * Returns success if removed or false if element did not exist.
767
648
         */
768
649
        awk_bool_t (*api_del_array_element)(awk_ext_id_t id,
769
650
                        awk_array_t a_cookie, const awk_value_t* const index);
770
651
 
771
 
        /* Create a new array cookie to which elements may be added. */
 
652
        /* Create a new array cookie to which elements may be added */
772
653
        awk_array_t (*api_create_array)(awk_ext_id_t id);
773
654
 
774
 
        /* Clear out an array. */
 
655
        /* Clear out an array */
775
656
        awk_bool_t (*api_clear_array)(awk_ext_id_t id, awk_array_t a_cookie);
776
657
 
777
 
        /*
778
 
         * Flatten out an array with type conversions as requested.
779
 
         * This supersedes the earlier api_flatten_array function that
780
 
         * did not allow the caller to specify the requested types.
781
 
         * (That API is still available as a macro, defined below.)
782
 
         */
783
 
        awk_bool_t (*api_flatten_array_typed)(awk_ext_id_t id,
 
658
        /* Flatten out an array so that it can be looped over easily. */
 
659
        awk_bool_t (*api_flatten_array)(awk_ext_id_t id,
784
660
                        awk_array_t a_cookie,
785
 
                        awk_flat_array_t **data,
786
 
                        awk_valtype_t index_type, awk_valtype_t value_type);
 
661
                        awk_flat_array_t **data);
787
662
 
788
663
        /* When done, delete any marked elements, release the memory. */
789
664
        awk_bool_t (*api_release_flattened_array)(awk_ext_id_t id,
799
674
        void *(*api_calloc)(size_t nmemb, size_t size);
800
675
        void *(*api_realloc)(void *ptr, size_t size);
801
676
        void (*api_free)(void *ptr);
802
 
 
803
 
        /*
804
 
         * Obsolete function, should not be used. It remains only
805
 
         * for binary compatibility.  Any value it returns should be
806
 
         * freed via api_free.
807
 
         */
808
 
        void *(*api_get_mpfr)(awk_ext_id_t id);
809
 
 
810
 
        /*
811
 
         * Obsolete function, should not be used. It remains only
812
 
         * for binary compatibility.  Any value it returns should be
813
 
         * freed via api_free.
814
 
         */
815
 
        void *(*api_get_mpz)(awk_ext_id_t id);
816
 
 
817
 
        /*
818
 
         * Look up a file.  If the name is NULL or name_len is 0, it returns
819
 
         * data for the currently open input file corresponding to FILENAME
820
 
         * (and it will not access the filetype argument, so that may be
821
 
         * undefined).
822
 
         *
823
 
         * If the file is not already open, try to open it.
824
 
         *
825
 
         * The "filetype" argument should be one of:
826
 
         *
827
 
         *    ">", ">>", "<", "|>", "|<", and "|&"
828
 
         *
829
 
         * If the file is not already open, and the fd argument is non-negative,
830
 
         * gawk will use that file descriptor instead of opening the file
831
 
         * in the usual way.
832
 
         *
833
 
         * If the fd is non-negative, but the file exists already, gawk
834
 
         * ignores the fd and returns the existing file.  It is the caller's
835
 
         * responsibility to notice that the fd in the returned
836
 
         * awk_input_buf_t does not match the requested value.
837
 
         *
838
 
         * Note that supplying a file descriptor is currently NOT supported
839
 
         * for pipes. It should work for input, output, append, and two-way
840
 
         * (coprocess) sockets.  If the filetype is two-way, we assume that
841
 
         * it is a socket!
842
 
         *
843
 
         * Note that in the two-way case, the input and output file descriptors
844
 
         * may differ.  To check for success, one must check that either of
845
 
         * them matches.
846
 
         *
847
 
         * ibufp and obufp point at gawk's internal copies of the
848
 
         * awk_input_buf_t and awk_output_t associated with the open
849
 
         * file.  Treat these data structures as read-only!
850
 
         */
851
 
        awk_bool_t (*api_get_file)(awk_ext_id_t id,
852
 
                        const char *name,
853
 
                        size_t name_len,
854
 
                        const char *filetype,
855
 
                        int fd,
856
 
                        /*
857
 
                         * Return values (on success, one or both should
858
 
                         * be non-NULL):
859
 
                         */
860
 
                        const awk_input_buf_t **ibufp,
861
 
                        const awk_output_buf_t **obufp);
862
 
 
863
 
        /* Destroy an array. */
864
 
        awk_bool_t (*api_destroy_array)(awk_ext_id_t id, awk_array_t a_cookie);
865
677
} gawk_api_t;
866
678
 
867
679
#ifndef GAWK    /* these are not for the gawk code itself! */
876
688
#define do_sandbox      (api->do_flags[gawk_do_sandbox])
877
689
#define do_debug        (api->do_flags[gawk_do_debug])
878
690
#define do_mpfr         (api->do_flags[gawk_do_mpfr])
879
 
#define do_csv          (api->do_flags[gawk_do_csv])
880
691
 
881
692
#define get_argument(count, wanted, result) \
882
693
        (api->api_get_argument(ext_id, count, wanted, result))
884
695
        (api->api_set_argument(ext_id, count, new_array))
885
696
 
886
697
#define fatal           api->api_fatal
887
 
#define nonfatal        api->api_nonfatal
888
698
#define warning         api->api_warning
889
699
#define lintwarn        api->api_lintwarn
890
700
 
902
712
#define awk_atexit(funcp, arg0) (api->api_awk_atexit(ext_id, funcp, arg0))
903
713
 
904
714
#define sym_lookup(name, wanted, result) \
905
 
        sym_lookup_ns("", name, wanted, result)
906
 
#define sym_update(name, value) \
907
 
        sym_update_ns("", name, value)
908
 
 
909
 
#define sym_lookup_ns(name_space, name, wanted, result) \
910
 
        (api->api_sym_lookup(ext_id, name_space, name, wanted, result))
911
 
#define sym_update_ns(name_space, name, value) \
912
 
        (api->api_sym_update(ext_id, name_space, name, value))
913
 
 
 
715
        (api->api_sym_lookup(ext_id, name, wanted, result))
914
716
#define sym_lookup_scalar(scalar_cookie, wanted, result) \
915
717
        (api->api_sym_lookup_scalar(ext_id, scalar_cookie, wanted, result))
 
718
#define sym_update(name, value) \
 
719
        (api->api_sym_update(ext_id, name, value))
916
720
#define sym_update_scalar(scalar_cookie, value) \
917
721
        (api->api_sym_update_scalar)(ext_id, scalar_cookie, value)
918
722
 
933
737
 
934
738
#define create_array()          (api->api_create_array(ext_id))
935
739
 
936
 
#define destroy_array(array)    (api->api_destroy_array(ext_id, array))
937
 
 
938
740
#define clear_array(array)      (api->api_clear_array(ext_id, array))
939
741
 
940
 
#define flatten_array_typed(array, data, index_type, value_type) \
941
 
        (api->api_flatten_array_typed(ext_id, array, data, index_type, value_type))
942
 
 
943
742
#define flatten_array(array, data) \
944
 
        flatten_array_typed(array, data, AWK_STRING, AWK_UNDEFINED)
 
743
        (api->api_flatten_array(ext_id, array, data))
945
744
 
946
745
#define release_flattened_array(array, data) \
947
746
        (api->api_release_flattened_array(ext_id, array, data))
957
756
#define release_value(value) \
958
757
        (api->api_release_value(ext_id, value))
959
758
 
960
 
#define get_file(name, namelen, filetype, fd, ibuf, obuf) \
961
 
        (api->api_get_file(ext_id, name, namelen, filetype, fd, ibuf, obuf))
962
 
 
963
 
/* These two are obsolete and should not be used. */
964
 
#define get_mpfr_ptr() (api->api_get_mpfr(ext_id))
965
 
#define get_mpz_ptr() (api->api_get_mpz(ext_id))
966
 
 
967
759
#define register_ext_version(version) \
968
760
        (api->api_register_ext_version(ext_id, version))
969
761
 
970
762
#define emalloc(pointer, type, size, message) \
971
763
        do { \
972
764
                if ((pointer = (type) gawk_malloc(size)) == 0) \
973
 
                        fatal(ext_id, "%s: malloc of %d bytes failed", message, size); \
974
 
        } while(0)
975
 
 
976
 
#define ezalloc(pointer, type, size, message) \
977
 
        do { \
978
 
                if ((pointer = (type) gawk_calloc(1, size)) == 0) \
979
 
                        fatal(ext_id, "%s: calloc of %d bytes failed", message, size); \
 
765
                        fatal(ext_id, "%s: malloc of %d bytes failed\n", message, size); \
980
766
        } while(0)
981
767
 
982
768
#define erealloc(pointer, type, size, message) \
983
769
        do { \
984
770
                if ((pointer = (type) gawk_realloc(pointer, size)) == 0) \
985
 
                        fatal(ext_id, "%s: realloc of %d bytes failed", message, size); \
 
771
                        fatal(ext_id, "%s: realloc of %d bytes failed\n", message, size); \
986
772
        } while(0)
987
773
 
988
774
/* Constructor functions */
989
775
 
990
 
/* r_make_string_type --- make a string or strnum or regexp value in result from the passed-in string */
 
776
/* r_make_string --- make a string value in result from the passed-in string */
991
777
 
992
778
static inline awk_value_t *
993
 
r_make_string_type(const gawk_api_t *api,       /* needed for emalloc */
994
 
                   awk_ext_id_t ext_id,         /* ditto */
995
 
                   const char *string,
996
 
                   size_t length,
997
 
                   awk_bool_t duplicate,
998
 
                   awk_value_t *result,
999
 
                   awk_valtype_t val_type)
 
779
r_make_string(const gawk_api_t *api,    /* needed for emalloc */
 
780
              awk_ext_id_t *ext_id,     /* ditto */
 
781
              const char *string,
 
782
              size_t length,
 
783
              awk_bool_t duplicate,
 
784
              awk_value_t *result)
1000
785
{
1001
786
        char *cp = NULL;
1002
787
 
1003
788
        memset(result, 0, sizeof(*result));
1004
789
 
1005
 
        result->val_type = val_type;
 
790
        result->val_type = AWK_STRING;
1006
791
        result->str_value.len = length;
1007
792
 
1008
793
        if (duplicate) {
1009
 
                emalloc(cp, char *, length + 1, "r_make_string");
 
794
                emalloc(cp, char *, length + 2, "r_make_string");
1010
795
                memcpy(cp, string, length);
1011
796
                cp[length] = '\0';
1012
797
                result->str_value.str = cp;
1017
802
        return result;
1018
803
}
1019
804
 
1020
 
/* r_make_string --- make a string value in result from the passed-in string */
1021
 
 
1022
 
static inline awk_value_t *
1023
 
r_make_string(const gawk_api_t *api,    /* needed for emalloc */
1024
 
              awk_ext_id_t ext_id,      /* ditto */
1025
 
              const char *string,
1026
 
              size_t length,
1027
 
              awk_bool_t duplicate,
1028
 
              awk_value_t *result)
1029
 
{
1030
 
        return r_make_string_type(api, ext_id, string, length, duplicate, result, AWK_STRING);
1031
 
}
1032
 
 
1033
 
#define make_const_string(str, len, result)     r_make_string(api, ext_id, str, len, awk_true, result)
1034
 
#define make_malloced_string(str, len, result)  r_make_string(api, ext_id, str, len, awk_false, result)
1035
 
 
1036
 
#define make_const_regex(str, len, result)      r_make_string_type(api, ext_id, str, len, awk_true, result, AWK_REGEX)
1037
 
#define make_malloced_regex(str, len, result)   r_make_string_type(api, ext_id, str, len, awk_false, result, AWK_REGEX)
1038
 
 
1039
 
/*
1040
 
 * Note: The caller may not create a STRNUM, but it can create a string that is
1041
 
 * flagged as user input that MAY be a STRNUM. Gawk will decide whether it's a
1042
 
 * STRNUM or a string by checking whether the string is numeric.
1043
 
 */
1044
 
#define make_const_user_input(str, len, result) r_make_string_type(api, ext_id, str, len, 1, result, AWK_STRNUM)
1045
 
#define make_malloced_user_input(str, len, result)      r_make_string_type(api, ext_id, str, len, 0, result, AWK_STRNUM)
 
805
#define make_const_string(str, len, result)     r_make_string(api, ext_id, str, len, 1, result)
 
806
#define make_malloced_string(str, len, result)  r_make_string(api, ext_id, str, len, 0, result)
1046
807
 
1047
808
/* make_null_string --- make a null string value */
1048
809
 
1060
821
static inline awk_value_t *
1061
822
make_number(double num, awk_value_t *result)
1062
823
{
 
824
        memset(result, 0, sizeof(*result));
 
825
 
1063
826
        result->val_type = AWK_NUMBER;
1064
827
        result->num_value = num;
1065
 
        result->num_type = AWK_NUMBER_TYPE_DOUBLE;
1066
 
        return result;
1067
 
}
1068
 
 
1069
 
/*
1070
 
 * make_number_mpz --- make an mpz number value in result.
1071
 
 * The mpz_ptr must be from a call to get_mpz_ptr.
1072
 
 */
1073
 
 
1074
 
static inline awk_value_t *
1075
 
make_number_mpz(void *mpz_ptr, awk_value_t *result)
1076
 
{
1077
 
        result->val_type = AWK_NUMBER;
1078
 
        result->num_type = AWK_NUMBER_TYPE_MPZ;
1079
 
        result->num_ptr = mpz_ptr;
1080
 
        return result;
1081
 
}
1082
 
 
1083
 
/*
1084
 
 * make_number_mpfr --- make an mpfr number value in result.
1085
 
 * The mpfr_ptr must be from a call to get_mpfr_ptr.
1086
 
 */
1087
 
 
1088
 
static inline awk_value_t *
1089
 
make_number_mpfr(void *mpfr_ptr, awk_value_t *result)
1090
 
{
1091
 
        result->val_type = AWK_NUMBER;
1092
 
        result->num_type = AWK_NUMBER_TYPE_MPFR;
1093
 
        result->num_ptr = mpfr_ptr;
1094
 
        return result;
1095
 
}
1096
 
 
1097
 
/* make_bool --- make a bool value in result */
1098
 
 
1099
 
static inline awk_value_t *
1100
 
make_bool(awk_bool_t boolval, awk_value_t *result)
1101
 
{
1102
 
        result->val_type = AWK_BOOL;
1103
 
        result->bool_value = boolval;
1104
 
        return result;
1105
 
}
1106
 
 
 
828
 
 
829
        return result;
 
830
}
1107
831
 
1108
832
/*
1109
833
 * Each extension must define a function with this prototype:
1122
846
extern int dl_load(const gawk_api_t *const api_p, awk_ext_id_t id);
1123
847
 
1124
848
#if 0
1125
 
/* Boilerplate code: */
 
849
/* Boiler plate code: */
1126
850
int plugin_is_GPL_compatible;
1127
851
 
1128
852
static gawk_api_t *const api;
1141
865
/* OR: */
1142
866
 
1143
867
static awk_bool_t
1144
 
init_my_extension(void)
 
868
init_my_module(void)
1145
869
{
1146
870
        ...
1147
871
}
1148
872
 
1149
 
static awk_bool_t (*init_func)(void) = init_my_extension;
 
873
static awk_bool_t (*init_func)(void) = init_my_module;
1150
874
 
1151
875
dl_load_func(func_table, some_name, "name_space_in_quotes")
1152
876
#endif
1153
877
 
1154
 
#define dl_load_func(func_table, extension, name_space) \
 
878
#define dl_load_func(func_table, module, name_space) \
1155
879
int dl_load(const gawk_api_t *const api_p, awk_ext_id_t id)  \
1156
880
{ \
1157
881
        size_t i, j; \
1158
882
        int errors = 0; \
1159
883
\
1160
884
        api = api_p; \
1161
 
        ext_id = (void **) id; \
 
885
        ext_id = id; \
1162
886
\
1163
887
        if (api->major_version != GAWK_API_MAJOR_VERSION \
1164
888
            || api->minor_version < GAWK_API_MINOR_VERSION) { \
1165
 
                fprintf(stderr, #extension ": version mismatch with gawk!\n"); \
1166
 
                fprintf(stderr, "\tmy version (API %d.%d), gawk version (API %d.%d)\n", \
 
889
                fprintf(stderr, #module ": version mismatch with gawk!\n"); \
 
890
                fprintf(stderr, "\tmy version (%d, %d), gawk version (%d, %d)\n", \
1167
891
                        GAWK_API_MAJOR_VERSION, GAWK_API_MINOR_VERSION, \
1168
892
                        api->major_version, api->minor_version); \
1169
893
                exit(1); \
1170
894
        } \
1171
895
\
1172
 
        check_mpfr_version(extension); \
1173
 
\
1174
896
        /* load functions */ \
1175
897
        for (i = 0, j = sizeof(func_table) / sizeof(func_table[0]); i < j; i++) { \
1176
898
                if (func_table[i].name == NULL) \
1177
899
                        break; \
1178
900
                if (! add_ext_func(name_space, & func_table[i])) { \
1179
 
                        warning(ext_id, #extension ": could not add %s", \
 
901
                        warning(ext_id, #module ": could not add %s\n", \
1180
902
                                        func_table[i].name); \
1181
903
                        errors++; \
1182
904
                } \
1184
906
\
1185
907
        if (init_func != NULL) { \
1186
908
                if (! init_func()) { \
1187
 
                        warning(ext_id, #extension ": initialization function failed"); \
 
909
                        warning(ext_id, #module ": initialization function failed\n"); \
1188
910
                        errors++; \
1189
911
                } \
1190
912
        } \
1195
917
        return (errors == 0); \
1196
918
}
1197
919
 
1198
 
#if defined __GNU_MP_VERSION && defined MPFR_VERSION_MAJOR
1199
 
#define check_mpfr_version(extension) do { \
1200
 
        if (api->gmp_major_version != __GNU_MP_VERSION \
1201
 
            || api->gmp_minor_version < __GNU_MP_VERSION_MINOR) { \
1202
 
                fprintf(stderr, #extension ": GMP version mismatch with gawk!\n"); \
1203
 
                fprintf(stderr, "\tmy version (%d, %d), gawk version (%d, %d)\n", \
1204
 
                        __GNU_MP_VERSION, __GNU_MP_VERSION_MINOR, \
1205
 
                        api->gmp_major_version, api->gmp_minor_version); \
1206
 
                exit(1); \
1207
 
        } \
1208
 
        if (api->mpfr_major_version != MPFR_VERSION_MAJOR \
1209
 
            || api->mpfr_minor_version < MPFR_VERSION_MINOR) { \
1210
 
                fprintf(stderr, #extension ": MPFR version mismatch with gawk!\n"); \
1211
 
                fprintf(stderr, "\tmy version (%d, %d), gawk version (%d, %d)\n", \
1212
 
                        MPFR_VERSION_MAJOR, MPFR_VERSION_MINOR, \
1213
 
                        api->mpfr_major_version, api->mpfr_minor_version); \
1214
 
                exit(1); \
1215
 
        } \
1216
 
} while (0)
1217
 
#else
1218
 
#define check_mpfr_version(extension) /* nothing */
1219
 
#endif
1220
 
 
1221
920
#endif /* GAWK */
1222
921
 
1223
922
#ifdef __cplusplus