123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145 |
- /* Copyright (C) 1991, 1995, 1998, 1999 artofcode LLC. All rights reserved.
-
- This file is part of AFPL Ghostscript.
-
- AFPL Ghostscript is distributed with NO WARRANTY OF ANY KIND. No author or
- distributor accepts any responsibility for the consequences of using it, or
- for whether it serves any particular purpose or works at all, unless he or
- she says so in writing. Refer to the Aladdin Free Public License (the
- "License") for full details.
-
- Every copy of AFPL Ghostscript must include a copy of the License, normally
- in a plain ASCII text file named PUBLIC. The License grants you the right
- to copy, modify and redistribute AFPL Ghostscript, but only under certain
- conditions described in the License. Among other things, the License
- requires that the copyright notice and this notice be preserved on all
- copies.
- */
- /*$Id: opdef.h,v 1.3 2001/08/28 03:28:08 giles Exp $ */
- /* Operator definition interface for Ghostscript */
- #ifndef opdef_INCLUDED
- # define opdef_INCLUDED
- /*
- * Define the structure for initializing the operator table. Each operator
- * file zxxx.c declares an array of these as follows:
- const op_def * const zxxx_op_defs[] = {
- {"1name", zname},
- ...
- op_def_end(iproc)
- };
- * where iproc is an initialization procedure for the file or 0, and, for
- * each operator defined, the initial digit of the name string indicates
- * the number of arguments and zname is the address of the associated C
- * function to invoke.
- *
- * The array definition always appears at the END of the file, to avoid
- * the need for forward declarations for all the operator procedures.
- *
- * Operators may be stored in dictionaries other than systemdict.
- * We support this with op_def entries of a special form:
- op_def_begin_dict("dictname"),
- */
- typedef struct {
- const char *oname;
- op_proc_t proc;
- } op_def;
- #define op_def_begin_dict(dname) {dname, 0}
- #define op_def_begin_filter() op_def_begin_dict("filterdict")
- #define op_def_begin_level2() op_def_begin_dict("level2dict")
- #define op_def_begin_ll3() op_def_begin_dict("ll3dict")
- #define op_def_is_begin_dict(def) ((def)->proc == 0)
- #define op_def_end(iproc) {0, iproc}
- /*
- * NOTE: for implementation reasons, a single table of operator definitions
- * is limited to 16 entries, including op_def_begin_xxx entries. If a file
- * defines more operators than this, it must split them into multiple
- * tables and have multiple -oper entries in the makefile. Currently,
- * only 4 out of 85 operator files require this.
- */
- #define OP_DEFS_LOG2_MAX_SIZE 4
- #define OP_DEFS_MAX_SIZE (1 << OP_DEFS_LOG2_MAX_SIZE)
- /*
- * Define the table of pointers to all operator definition tables.
- */
- extern const op_def *const op_defs_all[];
- /*
- * Internal operators whose names begin with %, such as continuation
- * operators, do not appear in systemdict. Ghostscript assumes
- * that these operators cannot appear anywhere (in executable form)
- * except on the e-stack; to maintain this invariant, the execstack
- * operator converts them to literal form, and cvx refuses to convert
- * them back. As a result of this invariant, they do not need to
- * push themselves back on the e-stack when executed, since the only
- * place they could have come from was the e-stack.
- */
- #define op_def_is_internal(def) ((def)->oname[1] == '%')
- /*
- * All operators are catalogued in a table; this is necessary because
- * they must have a short packed representation for the sake of 'bind'.
- * The `size' of an operator is normally its index in this table;
- * however, internal operators have a `size' of 0, and their true index
- * must be found by searching the table for their procedure address.
- */
- ushort op_find_index(P1(const ref *));
- #define op_index(opref)\
- (r_size(opref) == 0 ? op_find_index(opref) : r_size(opref))
- /*
- * There are actually two kinds of operators: the real ones (t_operator),
- * and ones defined by procedures (t_oparray). The catalog for t_operators
- * is (indirectly) op_defs_all, and their index is in the range
- * [1..op_def_count-1].
- */
- #define op_index_is_operator(index) ((index) < op_def_count)
- extern const uint op_def_count;
- #define op_index_def(index)\
- (&op_defs_all[(index) >> OP_DEFS_LOG2_MAX_SIZE]\
- [(index) & (OP_DEFS_MAX_SIZE - 1)])
- #define op_num_args(opref) (op_index_def(op_index(opref))->oname[0] - '0')
- #define op_index_proc(index) (op_index_def(index)->proc)
- /*
- * There are two catalogs for t_oparrays, one global and one local.
- * Operator indices for the global table are in the range
- * [op_def_count..op_def_count+op_array_global.count-1]
- * Operator indices for the local table are in the range
- * [op_def_count+r_size(&op_array_global.table)..
- * op_def_count+r_size(&op_array_global.table)+op_array_local.count-1]
- */
- typedef struct op_array_table_s {
- ref table; /* t_array */
- ushort *nx_table; /* name indices */
- uint count; /* # of occupied entries */
- uint base_index; /* operator index of first entry */
- uint attrs; /* ref attrs of ops in this table */
- ref *root_p; /* self-pointer for GC root */
- } op_array_table;
- extern op_array_table
- op_array_table_global, op_array_table_local;
- #define op_index_op_array_table(index)\
- ((index) < op_array_table_local.base_index ?\
- &op_array_table_global : &op_array_table_local)
- /*
- * Convert an operator index to an operator or oparray ref.
- * This is only used for debugging and for 'get' from packed arrays,
- * so it doesn't have to be very fast.
- */
- void op_index_ref(P2(uint, ref *));
- #endif /* opdef_INCLUDED */
|