Branch: Tag:

1996-09-22

1996-09-22 19:40:33 by Fredrik Hübinette (Hubbe) <hubbe@hubbe.net>

Pike

Rev: .cvsignore:1.1.1.1
Rev: README:1.1.1.1
Rev: bin/export.pike:1.1.1.1
Rev: bin/fixdepends.sh:1.1.1.1
Rev: bin/hilfe:1.1.1.1
Rev: bin/htmlify_docs.pike:1.1.1.1
Rev: bin/httpd.pike:1.1.1.1
Rev: bin/metatest:1.1.1.1
Rev: bin/mkpeep.pike:1.1.1.1
Rev: bin/rsif:1.1.1.1
Rev: doc/README:1.1.1.1
Rev: doc/builtin/_verify_internals:1.1.1.1
Rev: doc/builtin/add_constant:1.1.1.1
Rev: doc/builtin/aggregage_multiset:1.1.1.1
Rev: doc/builtin/aggregate:1.1.1.1
Rev: doc/builtin/aggregate_mapping:1.1.1.1
Rev: doc/builtin/alarm:1.1.1.1
Rev: doc/builtin/all_constants:1.1.1.1
Rev: doc/builtin/allocate:1.1.1.1
Rev: doc/builtin/arrayp:1.1.1.1
Rev: doc/builtin/backtrace:1.1.1.1
Rev: doc/builtin/call_function:1.1.1.1
Rev: doc/builtin/clone:1.1.1.1
Rev: doc/builtin/column:1.1.1.1
Rev: doc/builtin/combine_path:1.1.1.1
Rev: doc/builtin/compile_file:1.1.1.1
Rev: doc/builtin/compile_string:1.1.1.1
Rev: doc/builtin/copy_value:1.1.1.1
Rev: doc/builtin/crypt:1.1.1.1
Rev: doc/builtin/ctime:1.1.1.1
Rev: doc/builtin/destruct:1.1.1.1
Rev: doc/builtin/equal:1.1.1.1
Rev: doc/builtin/exit:1.1.1.1
Rev: doc/builtin/floatp:1.1.1.1
Rev: doc/builtin/function_name:1.1.1.1
Rev: doc/builtin/function_object:1.1.1.1
Rev: doc/builtin/functionp:1.1.1.1
Rev: doc/builtin/gc:1.1.1.1
Rev: doc/builtin/getpid:1.1.1.1
Rev: doc/builtin/glob:1.1.1.1
Rev: doc/builtin/hash:1.1.1.1
Rev: doc/builtin/indices:1.1.1.1
Rev: doc/builtin/intp:1.1.1.1
Rev: doc/builtin/kill:1.1.1.1
Rev: doc/builtin/localtime:1.1.1.1
Rev: doc/builtin/lower_case:1.1.1.1
Rev: doc/builtin/m_delete:1.1.1.1
Rev: doc/builtin/mappingp:1.1.1.1
Rev: doc/builtin/mkmapping:1.1.1.1
Rev: doc/builtin/multisetp:1.1.1.1
Rev: doc/builtin/next_object:1.1.1.1
Rev: doc/builtin/object_program:1.1.1.1
Rev: doc/builtin/objectp:1.1.1.1
Rev: doc/builtin/programp:1.1.1.1
Rev: doc/builtin/query_host_name:1.1.1.1
Rev: doc/builtin/query_num_arg:1.1.1.1
Rev: doc/builtin/random:1.1.1.1
Rev: doc/builtin/random_seed:1.1.1.1
Rev: doc/builtin/replace:1.1.1.1
Rev: doc/builtin/reverse:1.1.1.1
Rev: doc/builtin/rows:1.1.1.1
Rev: doc/builtin/rusage:1.1.1.1
Rev: doc/builtin/search:1.1.1.1
Rev: doc/builtin/signal:1.1.1.1
Rev: doc/builtin/signame:1.1.1.1
Rev: doc/builtin/signum:1.1.1.1
Rev: doc/builtin/sizeof:1.1.1.1
Rev: doc/builtin/sleep:1.1.1.1
Rev: doc/builtin/sort:1.1.1.1
Rev: doc/builtin/stringp:1.1.1.1
Rev: doc/builtin/this_object:1.1.1.1
Rev: doc/builtin/throw:1.1.1.1
Rev: doc/builtin/time:1.1.1.1
Rev: doc/builtin/trace:1.1.1.1
Rev: doc/builtin/ualarm:1.1.1.1
Rev: doc/builtin/upper_case:1.1.1.1
Rev: doc/builtin/values:1.1.1.1
Rev: doc/builtin/zero_type:1.1.1.1
Rev: doc/index.bmml:1.1.1.1
Rev: doc/manual/example1:1.1.1.1
Rev: doc/manual/example2:1.1.1.1
Rev: doc/manual/example3:1.1.1.1
Rev: doc/manual/tutorial:1.1.1.1
Rev: doc/operators/and:1.1.1.1
Rev: doc/operators/complement:1.1.1.1
Rev: doc/operators/divide:1.1.1.1
Rev: doc/operators/index:1.1.1.1
Rev: doc/operators/is_equal:1.1.1.1
Rev: doc/operators/is_greater_or_equal:1.1.1.1
Rev: doc/operators/is_greater_than:1.1.1.1
Rev: doc/operators/is_lesser_or_equal:1.1.1.1
Rev: doc/operators/is_lesser_than:1.1.1.1
Rev: doc/operators/logical_and:1.1.1.1
Rev: doc/operators/logical_or:1.1.1.1
Rev: doc/operators/minus:1.1.1.1
Rev: doc/operators/modulo:1.1.1.1
Rev: doc/operators/mult:1.1.1.1
Rev: doc/operators/not:1.1.1.1
Rev: doc/operators/not_equal:1.1.1.1
Rev: doc/operators/operators:1.1.1.1
Rev: doc/operators/or:1.1.1.1
Rev: doc/operators/plus:1.1.1.1
Rev: doc/operators/range:1.1.1.1
Rev: doc/operators/shift_left:1.1.1.1
Rev: doc/operators/shift_right:1.1.1.1
Rev: doc/operators/xor:1.1.1.1
Rev: doc/pike/all.bmml:1.1.1.1
Rev: doc/pike/cast:1.1.1.1
Rev: doc/pike/catch:1.1.1.1
Rev: doc/pike/class:1.1.1.1
Rev: doc/pike/command_line_options:1.1.1.1
Rev: doc/pike/control_structures/break:1.1.1.1
Rev: doc/pike/control_structures/catch:1.1.1.1
Rev: doc/pike/control_structures/continue:1.1.1.1
Rev: doc/pike/control_structures/do-while:1.1.1.1
Rev: doc/pike/control_structures/for:1.1.1.1
Rev: doc/pike/control_structures/foreach:1.1.1.1
Rev: doc/pike/control_structures/if-else:1.1.1.1
Rev: doc/pike/control_structures/return:1.1.1.1
Rev: doc/pike/control_structures/switch:1.1.1.1
Rev: doc/pike/control_structures/while:1.1.1.1
Rev: doc/pike/efuns.bmml:1.1.1.1
Rev: doc/pike/functions:1.1.1.1
Rev: doc/pike/gauge:1.1.1.1
Rev: doc/pike/hilfe:1.1.1.1
Rev: doc/pike/how_to_make_modules:1.1.1.1
Rev: doc/pike/inherit:1.1.1.1
Rev: doc/pike/lambda:1.1.1.1
Rev: doc/pike/modifier:1.1.1.1
Rev: doc/pike/preprocessor:1.1.1.1
Rev: doc/pike/reserved.bmml:1.1.1.1
Rev: doc/pike/sscanf:1.1.1.1
Rev: doc/pike/typeof:1.1.1.1
Rev: doc/pike/variables:1.1.1.1
Rev: doc/simulated/PI:1.1.1.1
Rev: doc/simulated/add_efun:1.1.1.1
Rev: doc/simulated/aggregage_list:1.1.1.1
Rev: doc/simulated/all_efuns:1.1.1.1
Rev: doc/simulated/capitalize:1.1.1.1
Rev: doc/simulated/describe_backtrace:1.1.1.1
Rev: doc/simulated/exec:1.1.1.1
Rev: doc/simulated/explode:1.1.1.1
Rev: doc/simulated/file_size:1.1.1.1
Rev: doc/simulated/filter:1.1.1.1
Rev: doc/simulated/filter_array:1.1.1.1
Rev: doc/simulated/get_function:1.1.1.1
Rev: doc/simulated/getenv:1.1.1.1
Rev: doc/simulated/implode:1.1.1.1
Rev: doc/simulated/l_sizeof:1.1.1.1
Rev: doc/simulated/listp:1.1.1.1
Rev: doc/simulated/m_indices:1.1.1.1
Rev: doc/simulated/m_sizeof:1.1.1.1
Rev: doc/simulated/m_values:1.1.1.1
Rev: doc/simulated/map:1.1.1.1
Rev: doc/simulated/map_array:1.1.1.1
Rev: doc/simulated/master:1.1.1.1
Rev: doc/simulated/member_array:1.1.1.1
Rev: doc/simulated/mklist:1.1.1.1
Rev: doc/simulated/mkmultiset:1.1.1.1
Rev: doc/simulated/perror:1.1.1.1
Rev: doc/simulated/popen:1.1.1.1
Rev: doc/simulated/previous_object:1.1.1.1
Rev: doc/simulated/putenv:1.1.1.1
Rev: doc/simulated/read_bytes:1.1.1.1
Rev: doc/simulated/regexp:1.1.1.1
Rev: doc/simulated/search_array:1.1.1.1
Rev: doc/simulated/sort_array:1.1.1.1
Rev: doc/simulated/spawn:1.1.1.1
Rev: doc/simulated/strlen:1.1.1.1
Rev: doc/simulated/strstr:1.1.1.1
Rev: doc/simulated/sum:1.1.1.1
Rev: doc/simulated/sum_arrays:1.1.1.1
Rev: doc/simulated/system:1.1.1.1
Rev: doc/simulated/this_function:1.1.1.1
Rev: doc/simulated/version:1.1.1.1
Rev: doc/simulated/write:1.1.1.1
Rev: doc/simulated/write_file:1.1.1.1
Rev: doc/types/array:1.1.1.1
Rev: doc/types/float:1.1.1.1
Rev: doc/types/function:1.1.1.1
Rev: doc/types/int:1.1.1.1
Rev: doc/types/mapping:1.1.1.1
Rev: doc/types/mixed:1.1.1.1
Rev: doc/types/multiset:1.1.1.1
Rev: doc/types/object:1.1.1.1
Rev: doc/types/program:1.1.1.1
Rev: doc/types/string:1.1.1.1
Rev: lib/include/array.h:1.1.1.1
Rev: lib/include/array.pre.pike:1.1.1.1
Rev: lib/include/process.h:1.1.1.1
Rev: lib/include/process.pre.pike:1.1.1.1
Rev: lib/include/simulate.h:1.1.1.1
Rev: lib/include/simulate.pre.pike:1.1.1.1
Rev: lib/include/stdio.h:1.1.1.1
Rev: lib/include/stdio.pre.pike:1.1.1.1
Rev: lib/master.pike:1.1.1.1
Rev: src/.cvsignore:1.1.1.1
Rev: src/BUGS:1.1.1.1
Rev: src/COPYING:1.1.1.1
Rev: src/COPYRIGHT:1.1.1.1
Rev: src/ChangeLog:1.1.1.1
Rev: src/DISCLAIMER:1.1.1.1
Rev: src/Makefile.src:1.1.1.1
Rev: src/README:1.1.1.1
Rev: src/alloca.c:1.1.1.1
Rev: src/array.c:1.1.1.1
Rev: src/array.h:1.1.1.1
Rev: src/backend.c:1.1.1.1
Rev: src/backend.h:1.1.1.1
Rev: src/build_modlist_h:1.1.1.1
Rev: src/builtin_functions.c:1.1.1.1
Rev: src/builtin_functions.h:1.1.1.1
Rev: src/callback.c:1.1.1.1
Rev: src/callback.h:1.1.1.1
Rev: src/compilation.h:1.1.1.1
Rev: src/config.cache:1.1.1.1
Rev: src/config.h:1.1.1.1
Rev: src/config.log:1.1.1.1
Rev: src/configure.in:1.1.1.1
Rev: src/constants.c:1.1.1.1
Rev: src/constants.h:1.1.1.1
Rev: src/docode.c:1.1.1.1
Rev: src/docode.h:1.1.1.1
Rev: src/dynamic_buffer.c:1.1.1.1
Rev: src/dynamic_buffer.h:1.1.1.1
Rev: src/efun.h:1.1.1.1
Rev: src/error.c:1.1.1.1
Rev: src/error.h:1.1.1.1
Rev: src/fd_control.c:1.1.1.1
Rev: src/fd_control.h:1.1.1.1
Rev: src/fsort.c:1.1.1.1
Rev: src/fsort.h:1.1.1.1
Rev: src/gc.c:1.1.1.1
Rev: src/gc.h:1.1.1.1
Rev: src/global.h:1.1.1.1
Rev: src/hashtable.c:1.1.1.1
Rev: src/hashtable.h:1.1.1.1
Rev: src/install-sh:1.1.1.1
Rev: src/interpret.c:1.1.1.1
Rev: src/interpret.h:1.1.1.1
Rev: src/language.y:1.1.1.1
Rev: src/las.c:1.1.1.1
Rev: src/las.h:1.1.1.1
Rev: src/lex.c:1.1.1.1
Rev: src/lex.h:1.1.1.1
Rev: src/machine.h.in:1.1.1.1
Rev: src/macros.h:1.1.1.1
Rev: src/main.c:1.1.1.1
Rev: src/main.h:1.1.1.1
Rev: src/mapping.c:1.1.1.1
Rev: src/mapping.h:1.1.1.1
Rev: src/memory.c:1.1.1.1
Rev: src/memory.h:1.1.1.1
Rev: src/module.c:1.1.1.1
Rev: src/module.h:1.1.1.1
Rev: src/modules/.cvsignore:1.1.1.1
Rev: src/modules/Makefile.src:1.1.1.1
Rev: src/modules/call_out/.cvsignore:1.1.1.1
Rev: src/modules/call_out/Makefile.src:1.1.1.1
Rev: src/modules/call_out/call_out.c:1.1.1.1
Rev: src/modules/call_out/configure.in:1.1.1.1
Rev: src/modules/call_out/doc/call_out:1.1.1.1
Rev: src/modules/call_out/doc/call_out_info:1.1.1.1
Rev: src/modules/call_out/doc/find_call_out:1.1.1.1
Rev: src/modules/call_out/doc/remove_call_out:1.1.1.1
Rev: src/modules/configure.in:1.1.1.1
Rev: src/modules/files/.cvsignore:1.1.1.1
Rev: src/modules/files/Makefile.src:1.1.1.1
Rev: src/modules/files/configure.in:1.1.1.1
Rev: src/modules/files/datagram.c:1.1.1.1
Rev: src/modules/files/doc/cd:1.1.1.1
Rev: src/modules/files/doc/errno:1.1.1.1
Rev: src/modules/files/doc/exece:1.1.1.1
Rev: src/modules/files/doc/file:1.1.1.1
Rev: src/modules/files/doc/file_stat:1.1.1.1
Rev: src/modules/files/doc/fork:1.1.1.1
Rev: src/modules/files/doc/get_dir:1.1.1.1
Rev: src/modules/files/doc/getcwd:1.1.1.1
Rev: src/modules/files/doc/mkdir:1.1.1.1
Rev: src/modules/files/doc/mv:1.1.1.1
Rev: src/modules/files/doc/port:1.1.1.1
Rev: src/modules/files/doc/rm:1.1.1.1
Rev: src/modules/files/doc/strerror:1.1.1.1
Rev: src/modules/files/doc/werror:1.1.1.1
Rev: src/modules/files/efuns.c:1.1.1.1
Rev: src/modules/files/file.c:1.1.1.1
Rev: src/modules/files/file.h:1.1.1.1
Rev: src/modules/files/file_machine.h.in:1.1.1.1
Rev: src/modules/files/socket.c:1.1.1.1
Rev: src/modules/gdbmmod/.cvsignore:1.1.1.1
Rev: src/modules/gdbmmod/Makefile.src:1.1.1.1
Rev: src/modules/gdbmmod/configure.in:1.1.1.1
Rev: src/modules/gdbmmod/doc/gdbm:1.1.1.1
Rev: src/modules/gdbmmod/gdbm_machine.h.in:1.1.1.1
Rev: src/modules/gdbmmod/gdbmmod.c:1.1.1.1
Rev: src/modules/gmpmod/.cvsignore:1.1.1.1
Rev: src/modules/gmpmod/Makefile.src:1.1.1.1
Rev: src/modules/gmpmod/configure.in:1.1.1.1
Rev: src/modules/gmpmod/doc/mpz:1.1.1.1
Rev: src/modules/gmpmod/gmp_machine.h.in:1.1.1.1
Rev: src/modules/gmpmod/mpz_glue.c:1.1.1.1
Rev: src/modules/image/Makefile.in:1.1.1.1
Rev: src/modules/image/Makefile.src:1.1.1.1
Rev: src/modules/image/configure:1.1.1.1
Rev: src/modules/image/configure.in:1.1.1.1
Rev: src/modules/image/dependencies:1.1.1.1
Rev: src/modules/image/doc.txt:1.1.1.1
Rev: src/modules/image/doc/image.html:1.1.1.1
Rev: src/modules/image/font.c:1.1.1.1
Rev: src/modules/image/image.c:1.1.1.1
Rev: src/modules/image/image.h:1.1.1.1
Rev: src/modules/image/lzw.c:1.1.1.1
Rev: src/modules/image/lzw.h:1.1.1.1
Rev: src/modules/image/quant.c:1.1.1.1
Rev: src/modules/image/togif.c:1.1.1.1
Rev: src/modules/math/.cvsignore:1.1.1.1
Rev: src/modules/math/Makefile.src:1.1.1.1
Rev: src/modules/math/configure.in:1.1.1.1
Rev: src/modules/math/doc/acos:1.1.1.1
Rev: src/modules/math/doc/asin:1.1.1.1
Rev: src/modules/math/doc/atan:1.1.1.1
Rev: src/modules/math/doc/ceil:1.1.1.1
Rev: src/modules/math/doc/cos:1.1.1.1
Rev: src/modules/math/doc/exp:1.1.1.1
Rev: src/modules/math/doc/floor:1.1.1.1
Rev: src/modules/math/doc/log:1.1.1.1
Rev: src/modules/math/doc/pow:1.1.1.1
Rev: src/modules/math/doc/sin:1.1.1.1
Rev: src/modules/math/doc/sqrt:1.1.1.1
Rev: src/modules/math/doc/tan:1.1.1.1
Rev: src/modules/math/math.c:1.1.1.1
Rev: src/modules/module_dir_marker:1.1.1.1
Rev: src/modules/pipe/Makefile.in:1.1.1.1
Rev: src/modules/pipe/Makefile.src:1.1.1.1
Rev: src/modules/pipe/config.h:1.1.1.1
Rev: src/modules/pipe/configure:1.1.1.1
Rev: src/modules/pipe/configure.in:1.1.1.1
Rev: src/modules/pipe/dependencies:1.1.1.1
Rev: src/modules/pipe/pipe.c:1.1.1.1
Rev: src/modules/readlinemod/.cvsignore:1.1.1.1
Rev: src/modules/readlinemod/Makefile.src:1.1.1.1
Rev: src/modules/readlinemod/configure.in:1.1.1.1
Rev: src/modules/readlinemod/doc/readline:1.1.1.1
Rev: src/modules/readlinemod/readline_machine.h.in:1.1.1.1
Rev: src/modules/readlinemod/readlinemod.c:1.1.1.1
Rev: src/modules/regexp/.cvsignore:1.1.1.1
Rev: src/modules/regexp/Makefile.src:1.1.1.1
Rev: src/modules/regexp/configure.in:1.1.1.1
Rev: src/modules/regexp/doc/regexp:1.1.1.1
Rev: src/modules/regexp/glue.c:1.1.1.1
Rev: src/modules/regexp/regexp.c:1.1.1.1
Rev: src/modules/regexp/regexp.h:1.1.1.1
Rev: src/modules/spider/Makefile.in:1.1.1.1
Rev: src/modules/spider/Makefile.src:1.1.1.1
Rev: src/modules/spider/configure:1.1.1.1
Rev: src/modules/spider/configure.in:1.1.1.1
Rev: src/modules/spider/defs.h:1.1.1.1
Rev: src/modules/spider/dependencies:1.1.1.1
Rev: src/modules/spider/discdate.c:1.1.1.1
Rev: src/modules/spider/encode_decode.c:1.1.1.1
Rev: src/modules/spider/http_parse.c:1.1.1.1
Rev: src/modules/spider/lock.c:1.1.1.1
Rev: src/modules/spider/lock.h:1.1.1.1
Rev: src/modules/spider/sdebug.c:1.1.1.1
Rev: src/modules/spider/shared_mem_mapping.c:1.1.1.1
Rev: src/modules/spider/sharedmem.c:1.1.1.1
Rev: src/modules/spider/sharedmem.h:1.1.1.1
Rev: src/modules/spider/spider.c:1.1.1.1
Rev: src/modules/spider/spider.h.in:1.1.1.1
Rev: src/modules/spider/stardate.c:1.1.1.1
Rev: src/modules/spider/streamed_parser.c:1.1.1.1
Rev: src/modules/spider/streamed_parser.h:1.1.1.1
Rev: src/modules/spider/tree.c:1.1.1.1
Rev: src/modules/sprintf/.cvsignore:1.1.1.1
Rev: src/modules/sprintf/Makefile.src:1.1.1.1
Rev: src/modules/sprintf/configure.in:1.1.1.1
Rev: src/modules/sprintf/doc/sprintf:1.1.1.1
Rev: src/modules/sprintf/sprintf.c:1.1.1.1
Rev: src/multiset.c:1.1.1.1
Rev: src/multiset.h:1.1.1.1
Rev: src/object.c:1.1.1.1
Rev: src/object.h:1.1.1.1
Rev: src/opcodes.c:1.1.1.1
Rev: src/opcodes.h:1.1.1.1
Rev: src/operators.c:1.1.1.1
Rev: src/operators.h:1.1.1.1
Rev: src/otable.h:1.1.1.1
Rev: src/peep.c:1.1.1.1
Rev: src/peep.h:1.1.1.1
Rev: src/peep.in:1.1.1.1
Rev: src/pike_types.c:1.1.1.1
Rev: src/pike_types.h:1.1.1.1
Rev: src/port.c:1.1.1.1
Rev: src/port.h:1.1.1.1
Rev: src/program.c:1.1.1.1
Rev: src/program.h:1.1.1.1
Rev: src/run_autoconfig:1.1.1.1
Rev: src/rusage.c:1.1.1.1
Rev: src/rusage.h:1.1.1.1
Rev: src/signal_handler.c:1.1.1.1
Rev: src/signal_handler.h:1.1.1.1
Rev: src/stamp-h:1.1.1.1
Rev: src/stralloc.c:1.1.1.1
Rev: src/stralloc.h:1.1.1.1
Rev: src/stuff.c:1.1.1.1
Rev: src/stuff.h:1.1.1.1
Rev: src/svalue.c:1.1.1.1
Rev: src/svalue.h:1.1.1.1
Rev: src/test/.cvsignore:1.1.1.1
Rev: src/test/create_testsuite:1.1.1.1
Rev: src/test/test_pike.pike:1.1.1.1
Rev: src/time_stuff.h:1.1.1.1
Rev: src/todo:1.1.1.1
Rev: src/types.h:1.1.1.1
Rev: src/ualarm.c:1.1.1.1

1: + /*\ + ||| This file a part of Pike, and is copyright by Fredrik Hubinette + ||| Pike is distributed as GPL (General Public License) + ||| See the files COPYING and DISCLAIMER for more information. + \*/ + #include "global.h" + #include <ctype.h> + #include "svalue.h" + #include "pike_types.h" + #include "stralloc.h" + #include "stuff.h" + #include "array.h" + #include "program.h" + #include "constants.h" + #include "object.h" + #include "multiset.h" + #include "mapping.h" + #include "macros.h" + #include "error.h"    -  + static void internal_parse_type(char **s); +  + /* +  * basic types are represented by just their value in a string +  * basic type are string, int, float, object and program +  * arrays are coded like by the value T_ARRAY followed by the +  * data type, if the type is not known it is T_MIXED, ie: +  * T_ARRAY <data type> +  * mappings are followed by two arguments, the first is the type +  * for the indices, and the second is the type of the data, ie: +  * T_MAPPING <indice type> <data type> +  * multiset works similarly to arrays. +  * functions are _very_ special: +  * they are coded like this: +  * T_FUNCTION <arg type> <arg type> ... <arg type> T_MANY <arg type> <return type> +  * note that the type after T_MANY can be T_VOID +  * T_MIXED matches anything except T_VOID +  * T_UNKNOWN only matches T_MIXED and T_UNKNOWN +  */ +  + struct pike_string *string_type_string; + struct pike_string *int_type_string; + struct pike_string *float_type_string; + struct pike_string *function_type_string; + struct pike_string *object_type_string; + struct pike_string *program_type_string; + struct pike_string *array_type_string; + struct pike_string *multiset_type_string; + struct pike_string *mapping_type_string; + struct pike_string *mixed_type_string; + struct pike_string *void_type_string; + struct pike_string *any_type_string; +  + void init_types() + { +  string_type_string=parse_type("string"); +  int_type_string=parse_type("int"); +  object_type_string=parse_type("object"); +  program_type_string=parse_type("program"); +  float_type_string=parse_type("float"); +  mixed_type_string=parse_type("mixed"); +  array_type_string=parse_type("array"); +  multiset_type_string=parse_type("multiset"); +  mapping_type_string=parse_type("mapping"); +  function_type_string=parse_type("function"); +  void_type_string=parse_type("void"); +  any_type_string=parse_type("void|mixed"); + } +  + static int type_length(char *t) + { +  char *q=t; +  switch(EXTRACT_UCHAR(t++)) +  { +  default: +  fatal("error in type string.\n"); +  /*NOTREACHED*/ +  +  case T_FUNCTION: +  while(EXTRACT_UCHAR(t)!=T_MANY) t+=type_length(t); /* skip arguments */ +  t++; +  +  case T_MAPPING: +  case T_OR: +  case T_AND: +  t+=type_length(t); +  +  case T_ARRAY: +  case T_MULTISET: +  case T_NOT: +  t+=type_length(t); +  +  case T_INT: +  case T_FLOAT: +  case T_STRING: +  case T_OBJECT: +  case T_PROGRAM: +  case T_MIXED: +  case T_VOID: +  case T_UNKNOWN: +  break; +  } +  return t-q; + } +  +  + #define STACK_SIZE 100000 + static unsigned char type_stack[STACK_SIZE]; + static unsigned char *type_stackp=type_stack; + static unsigned char *mark_stack[STACK_SIZE/4]; + static unsigned char **mark_stackp=mark_stack; +  + void reset_type_stack() + { +  type_stackp=type_stack; +  mark_stackp=mark_stack; + } +  + void type_stack_mark() + { +  *mark_stackp=type_stackp; +  mark_stackp++; +  if(mark_stackp > mark_stack + NELEM(mark_stack)) +  yyerror("Type mark stack overflow."); + } +  + unsigned char *pop_stack_mark() + { +  mark_stackp--; +  if(mark_stackp<mark_stack) +  fatal("Type mark stack underflow\n"); +  +  return *mark_stackp; + } +  + void pop_type_stack() + { +  type_stackp--; +  if(type_stackp<type_stack) +  fatal("Type stack underflow\n"); + } +  + void type_stack_pop_to_mark() + { +  type_stackp=pop_stack_mark(); + } +  + void type_stack_reverse() + { +  unsigned char *a,*b,tmp; +  a=pop_stack_mark(); +  b=type_stackp-1; +  while(b>a) { tmp=*a; *a=*b; *b=tmp; b--; a++; } + } +  + void push_type(unsigned char tmp) + { +  *type_stackp=tmp; +  type_stackp++; +  if(type_stackp > type_stack + sizeof(type_stack)) +  yyerror("Type stack overflow."); + } +  + void push_unfinished_type(char *s) + { +  int e; +  e=type_length(s); +  for(e--;e>=0;e--) push_type(s[e]); + } +  + void push_finished_type(struct pike_string *type) + { +  int e; +  for(e=type->len-1;e>=0;e--) push_type(type->str[e]); + } +  + struct pike_string *pop_unfinished_type() + { +  int len,e; +  struct pike_string *s; +  len=type_stackp - pop_stack_mark(); +  s=begin_shared_string(len); +  for(e=0;e<len;e++) s->str[e] = *--type_stackp; +  return end_shared_string(s); + } +  + struct pike_string *pop_type() + { +  int len,e; +  struct pike_string *s; +  len=type_stackp - type_stack; +  s=begin_shared_string(len); +  for(e=0;e<len;e++) s->str[e] = *--type_stackp; +  s=end_shared_string(s); +  reset_type_stack(); +  return s; + } +  +  +  + static void internal_parse_typeA(char **s) + { +  char buf[80]; +  unsigned int len; +  +  while(isspace(**s)) ++*s; +  +  len=0; +  for(len=0;isidchar(s[0][len]);len++) +  { +  if(len>=sizeof(buf)) error("Buffer overflow in parse_type\n"); +  buf[len] = s[0][len]; +  } +  buf[len]=0; +  *s += len; +  +  if(!strcmp(buf,"int")) push_type(T_INT); +  else if(!strcmp(buf,"float")) push_type(T_FLOAT); +  else if(!strcmp(buf,"object")) push_type(T_OBJECT); +  else if(!strcmp(buf,"program")) push_type(T_PROGRAM); +  else if(!strcmp(buf,"string")) push_type(T_STRING); +  else if(!strcmp(buf,"void")) push_type(T_VOID); +  else if(!strcmp(buf,"mixed")) push_type(T_MIXED); +  else if(!strcmp(buf,"unknown")) push_type(T_UNKNOWN); +  else if(!strcmp(buf,"function")) +  { +  while(isspace(**s)) ++*s; +  if(**s == '(') +  { +  ++*s; +  while(isspace(**s)) ++*s; +  type_stack_mark(); +  while(1) +  { +  if(**s == ':') +  { +  push_type(T_MANY); +  push_type(T_VOID); +  break; +  } +  +  type_stack_mark(); +  type_stack_mark(); +  type_stack_mark(); +  internal_parse_type(s); +  type_stack_reverse(); +  if(**s==',') +  { +  ++*s; +  while(isspace(**s)) ++*s; +  } +  else if(s[0][0]=='.' && s[0][1]=='.' && s[0][2]=='.') +  { +  type_stack_reverse(); +  push_type(T_MANY); +  type_stack_reverse(); +  *s+=3; +  while(isspace(**s)) ++*s; +  if(**s != ':') error("Missing ':' after ... in function type.\n"); +  break; +  } +  pop_stack_mark(); +  pop_stack_mark(); +  } +  ++*s; +  type_stack_mark(); +  internal_parse_type(s); /* return type */ +  type_stack_reverse(); +  if(**s != ')') error("Missing ')' in function type.\n"); +  ++*s; +  type_stack_reverse(); +  }else{ +  push_type(T_MIXED); +  push_type(T_MIXED); +  push_type(T_MANY); +  } +  push_type(T_FUNCTION); +  } +  else if(!strcmp(buf,"mapping")) +  { +  while(isspace(**s)) ++*s; +  if(**s == '(') +  { +  type_stack_mark(); +  ++*s; +  type_stack_mark(); +  internal_parse_type(s); +  type_stack_reverse(); +  if(**s != ':') error("Expecting ':'.\n"); +  ++*s; +  type_stack_mark(); +  internal_parse_type(s); +  type_stack_reverse(); +  if(**s != ')') error("Expecting ')'.\n"); +  ++*s; +  type_stack_reverse(); +  }else{ +  push_type(T_MIXED); +  push_type(T_MIXED); +  } +  push_type(T_MAPPING); +  } +  else if(!strcmp(buf,"array")) +  { +  while(isspace(**s)) ++*s; +  if(**s == '(') +  { +  ++*s; +  internal_parse_type(s); +  if(**s != ')') error("Expecting ')'.\n"); +  ++*s; +  }else{ +  push_type(T_MIXED); +  } +  push_type(T_ARRAY); +  } +  else if(!strcmp(buf,"multiset")) +  { +  while(isspace(**s)) ++*s; +  if(**s == '(') +  { +  ++*s; +  internal_parse_type(s); +  if(**s != ')') error("Expecting ')'.\n"); +  ++*s; +  }else{ +  push_type(T_MIXED); +  } +  push_type(T_MULTISET); +  } +  else +  error("Couldn't parse type. (%s)\n",buf); +  +  while(isspace(**s)) ++*s; + } +  +  + static void internal_parse_typeB(char **s) + { +  while(isspace(**s)) ++*s; +  switch(**s) +  { +  case '!': +  ++*s; +  internal_parse_typeB(s); +  push_type(T_NOT); +  break; +  +  case '(': +  ++*s; +  internal_parse_typeB(s); +  while(isspace(**s)) ++*s; +  if(**s != ')') error("Expecting ')'.\n"); +  break; +  +  default: +  +  internal_parse_typeA(s); +  } + } +  + static void internal_parse_typeCC(char **s) + { +  internal_parse_typeB(s); +  +  while(isspace(**s)) ++*s; +  +  while(**s == '*') +  { +  ++*s; +  while(isspace(**s)) ++*s; +  push_type(T_ARRAY); +  } + } +  + static void internal_parse_typeC(char **s) + { +  type_stack_mark(); +  +  type_stack_mark(); +  internal_parse_typeCC(s); +  type_stack_reverse(); +  +  while(isspace(**s)) ++*s; +  +  if(**s == '&') +  { +  ++*s; +  type_stack_mark(); +  internal_parse_typeC(s); +  type_stack_reverse(); +  type_stack_reverse(); +  push_type(T_AND); +  }else{ +  type_stack_reverse(); +  } + } +  + static void internal_parse_type(char **s) + { +  internal_parse_typeC(s); +  +  while(isspace(**s)) ++*s; +  +  while(**s == '|') +  { +  ++*s; +  internal_parse_typeC(s); +  push_type(T_OR); +  } + } +  + /* This function is used when adding simul efuns so that +  * the types for the functions can be easily stored in strings. +  * It takes a string on the exact same format as Pike and returns a type +  * struct. +  */ + struct pike_string *parse_type(char *s) + { +  internal_parse_type(&s); +  +  if( *s ) +  fatal("Extra junk at end of type definition.\n"); +  +  return pop_type(); + } +  + #ifdef DEBUG + void stupid_describe_type(char *a,INT32 len) + { +  INT32 e; +  for(e=0;e<len;e++) +  { +  if(e) printf(" "); +  switch(EXTRACT_UCHAR(a+e)) +  { +  case T_INT: printf("int"); break; +  case T_FLOAT: printf("float"); break; +  case T_STRING: printf("string"); break; +  case T_PROGRAM: printf("program"); break; +  case T_OBJECT: printf("object"); break; +  case T_FUNCTION: printf("function"); break; +  case T_ARRAY: printf("array"); break; +  case T_MAPPING: printf("mapping"); break; +  case T_MULTISET: printf("multiset"); break; +  +  case T_UNKNOWN: printf("unknown"); break; +  case T_MANY: printf("many"); break; +  case T_OR: printf("or"); break; +  case T_AND: printf("and"); break; +  case T_NOT: printf("not"); break; +  case T_VOID: printf("void"); break; +  case T_MIXED: printf("mixed"); break; +  +  default: printf("%d",EXTRACT_UCHAR(a+e)); break; +  } +  } +  printf("\n"); + } +  + void simple_describe_type(struct pike_string *s) + { +  stupid_describe_type(s->str,s->len); + } + #endif +  + char *low_describe_type(char *t) + { +  switch(EXTRACT_UCHAR(t++)) +  { +  case T_VOID: my_strcat("void"); break; +  case T_MIXED: my_strcat("mixed"); break; +  case T_UNKNOWN: my_strcat("unknown"); break; +  case T_INT: my_strcat("int"); break; +  case T_FLOAT: my_strcat("float"); break; +  case T_PROGRAM: my_strcat("program"); break; +  case T_OBJECT: my_strcat("object"); break; +  case T_STRING: my_strcat("string"); break; +  +  case T_FUNCTION: +  { +  int s; +  my_strcat("function("); +  s=0; +  while(EXTRACT_UCHAR(t) != T_MANY) +  { +  if(s++) my_strcat(", "); +  t=low_describe_type(t); +  } +  t++; +  if(EXTRACT_UCHAR(t) == T_VOID) +  { +  t++; +  }else{ +  if(s++) my_strcat(", "); +  t=low_describe_type(t); +  my_strcat(" ..."); +  } +  my_strcat(" : "); +  t=low_describe_type(t); +  my_strcat(")"); +  break; +  } +  +  case T_ARRAY: +  if(EXTRACT_UCHAR(t)==T_MIXED) +  { +  my_strcat("array"); +  t++; +  }else{ +  t=low_describe_type(t); +  my_strcat("*"); +  } +  break; +  +  case T_MULTISET: +  my_strcat("multiset"); +  if(EXTRACT_UCHAR(t)!=T_MIXED) +  { +  my_strcat("("); +  t=low_describe_type(t); +  my_strcat(")"); +  }else{ +  t++; +  } +  break; +  +  case T_NOT: +  my_strcat("!"); +  t=low_describe_type(t); +  break; +  +  case T_OR: +  t=low_describe_type(t); +  my_strcat(" | "); +  t=low_describe_type(t); +  break; +  +  case T_AND: +  t=low_describe_type(t); +  my_strcat(" & "); +  t=low_describe_type(t); +  break; +  +  case T_MAPPING: +  my_strcat("mapping"); +  if(EXTRACT_UCHAR(t)==T_MIXED && EXTRACT_UCHAR(t+1)==T_MIXED) +  { +  t+=2; +  }else{ +  my_strcat("("); +  t=low_describe_type(t); +  my_strcat(":"); +  t=low_describe_type(t); +  my_strcat(")"); +  } +  break; +  } +  return t; + } +  + struct pike_string *describe_type(struct pike_string *type) + { +  if(!type) return make_shared_string("mixed"); +  init_buf(); +  low_describe_type(type->str); +  return free_buf(); + } +  + static TYPE_T low_compile_type_to_runtime_type(char *t) + { +  TYPE_T tmp; +  switch(EXTRACT_UCHAR(t)) +  { +  case T_OR: +  t++; +  tmp=low_compile_type_to_runtime_type(t); +  if(tmp == low_compile_type_to_runtime_type(t+type_length(t))) +  return tmp; +  +  case T_MANY: +  case T_UNKNOWN: +  case T_AND: +  case T_NOT: +  return T_MIXED; +  +  default: +  return EXTRACT_UCHAR(t); +  } + } +  + TYPE_T compile_type_to_runtime_type(struct pike_string *s) + { +  return low_compile_type_to_runtime_type(s->str); + } +  + #define A_EXACT 1 + #define B_EXACT 2 +  + /* +  * match two type strings, return zero if they don't match, and return +  * the part of 'a' that _did_ match if it did. +  */ + static char *low_match_types(char *a,char *b, int flags) + { +  char *ret; +  if(a == b) return a; +  +  switch(EXTRACT_UCHAR(a)) +  { +  case T_AND: +  a++; +  ret=low_match_types(a,b,flags); +  if(!ret) return 0; +  a+=type_length(a); +  return low_match_types(a,b,flags); +  +  case T_OR: +  a++; +  ret=low_match_types(a,b,flags); +  if(ret) return ret; +  a+=type_length(a); +  return low_match_types(a,b,flags); +  +  case T_NOT: +  if(low_match_types(a+1,b,flags | B_EXACT)) +  return 0; +  return a; +  } +  +  switch(EXTRACT_UCHAR(b)) +  { +  case T_AND: +  b++; +  ret=low_match_types(a,b,flags); +  if(!ret) return 0; +  b+=type_length(b); +  return low_match_types(a,b,flags); +  +  case T_OR: +  b++; +  ret=low_match_types(a,b,flags); +  if(ret) return ret; +  b+=type_length(b); +  return low_match_types(a,b,flags); +  +  case T_NOT: +  if(low_match_types(a,b+1, flags | A_EXACT)) +  return 0; +  return a; +  } +  +  /* 'mixed' matches anything */ +  if(EXTRACT_UCHAR(a) == T_MIXED && !(flags & A_EXACT)) return a; +  if(EXTRACT_UCHAR(b) == T_MIXED && !(flags & B_EXACT)) return a; +  if(EXTRACT_UCHAR(a) != EXTRACT_UCHAR(b)) return 0; +  +  ret=a; +  switch(EXTRACT_UCHAR(a)) +  { +  case T_FUNCTION: +  a++; +  b++; +  while(EXTRACT_UCHAR(a)!=T_MANY || EXTRACT_UCHAR(b)!=T_MANY) +  { +  char *a_tmp,*b_tmp; +  if(EXTRACT_UCHAR(a)==T_MANY) +  { +  a_tmp=a+1; +  }else{ +  a_tmp=a; +  a+=type_length(a); +  } +  +  if(EXTRACT_UCHAR(b)==T_MANY) +  { +  b_tmp=b+1; +  }else{ +  b_tmp=b; +  b+=type_length(b); +  } +  +  if(!low_match_types(a_tmp, b_tmp, flags)) return 0; +  } +  /* check the 'many' type */ +  a++; +  b++; +  if(EXTRACT_UCHAR(b)==T_VOID || EXTRACT_UCHAR(a)==T_VOID) +  { +  a+=type_length(a); +  b+=type_length(b); +  }else{ +  if(!low_match_types(a,b,flags)) return 0; +  } +  /* check the returntype */ +  if(!low_match_types(a,b,flags)) return 0; +  break; +  +  case T_MAPPING: +  if(!low_match_types(++a,++b,flags)) return 0; +  if(!low_match_types(a+type_length(a),b+type_length(b),flags)) return 0; +  break; +  +  case T_MULTISET: +  case T_ARRAY: +  if(!low_match_types(++a,++b,flags)) return 0; +  +  case T_INT: +  case T_FLOAT: +  case T_STRING: +  case T_OBJECT: +  case T_PROGRAM: +  case T_VOID: +  case T_MIXED: +  break; +  +  default: +  fatal("error in type string.\n"); +  } +  return ret; + } +  + /* +  * Return the return type from a function call. +  */ + static int low_get_return_type(char *a,char *b) + { +  int tmp; +  switch(EXTRACT_UCHAR(a)) +  { +  case T_OR: +  { +  struct pike_string *o1,*o2; +  a++; +  o1=o2=0; +  +  type_stack_mark(); +  if(low_get_return_type(a,b)) +  { +  o1=pop_unfinished_type(); +  type_stack_mark(); +  } +  +  if(low_get_return_type(a+type_length(a),b)) +  o2=pop_unfinished_type(); +  else +  pop_stack_mark(); +  +  if(o1 == o2) +  { +  if(!o1) +  { +  return 0; +  }else{ +  push_finished_type(o1); +  } +  } +  else if(o1 == mixed_type_string || o2 == mixed_type_string) +  { +  push_type(T_MIXED); +  } +  else +  { +  if(o1) push_finished_type(o1); +  if(o2) push_finished_type(o2); +  if(o1 && o2) push_type(T_OR); +  } +  +  if(o1) free_string(o1); +  if(o2) free_string(o2); +  +  return 1; +  } +  +  case T_AND: +  a++; +  type_stack_mark(); +  tmp=low_get_return_type(a,b); +  type_stack_pop_to_mark(); +  if(!tmp) return 0; +  return low_get_return_type(a+type_length(a),b); +  +  case T_ARRAY: +  a++; +  tmp=low_get_return_type(a,b); +  if(!tmp) return 0; +  push_type(T_ARRAY); +  return 1; +  } +  +  a=low_match_types(a,b,0); +  if(a) +  { +  switch(EXTRACT_UCHAR(a)) +  { +  case T_FUNCTION: +  a++; +  while(EXTRACT_UCHAR(a)!=T_MANY) a+=type_length(a); +  a++; +  a+=type_length(a); +  push_unfinished_type(a); +  return 1; +  +  default: +  push_type(T_MIXED); +  return 1; +  } +  } +  return 0; + } +  +  + int match_types(struct pike_string *a,struct pike_string *b) + { +  return 0!=low_match_types(a->str, b->str,0); + } +  +  +  + /* FIXME, add the index */ + static struct pike_string *low_index_type(char *t) + { +  switch(EXTRACT_UCHAR(t++)) +  { +  default: +  reference_shared_string(mixed_type_string); +  return mixed_type_string; +  +  case T_OR: +  { +  struct pike_string *a,*b; +  a=low_index_type(t); +  t+=type_length(t); +  b=low_index_type(t); +  if(!b) return a; +  if(!a) return b; +  push_finished_type(b); +  push_finished_type(a); +  push_type(T_OR); +  return pop_type(); +  } +  +  case T_AND: +  return low_index_type(t+type_length(t)); +  +  case T_STRING: /* always int */ +  case T_MULTISET: /* always int */ +  reference_shared_string(int_type_string); +  return int_type_string; +  +  case T_MAPPING: +  t+=type_length(t); +  +  case T_ARRAY: +  return make_shared_binary_string(t, type_length(t)); +  } + } +  + struct pike_string *index_type(struct pike_string *type) + { +  struct pike_string *t; +  t=low_index_type(type->str); +  if(!t) copy_shared_string(t,mixed_type_string); +  return t; + } +  + static int low_check_indexing(char *type, char *index_type) + { +  switch(EXTRACT_UCHAR(type++)) +  { +  case T_OR: +  return low_check_indexing(type,index_type) || +  low_check_indexing(type+type_length(type),index_type); +  +  case T_AND: +  return low_check_indexing(type,index_type) && +  low_check_indexing(type+type_length(type),index_type); +  +  case T_NOT: +  return !low_check_indexing(type,index_type); +  +  case T_STRING: +  case T_ARRAY: +  return !!low_match_types(int_type_string->str, index_type,0); +  +  case T_OBJECT: +  return !!low_match_types(string_type_string->str, index_type,0); +  +  case T_MULTISET: +  case T_MAPPING: +  return !!low_match_types(type,index_type,0); +  +  case T_MIXED: +  return 1; +  +  default: +  return 0; +  } + } +  + int check_indexing(struct pike_string *type, +  struct pike_string *index_type) + { +  return low_check_indexing(type->str, index_type->str); + } +  + /* Count the number of arguments for a funciton type. +  * return -1-n if the function can take number of arguments +  * >= n (varargs) +  */ + int count_arguments(struct pike_string *s) + { +  int num; +  char *q; +  +  q=s->str; +  if(EXTRACT_UCHAR(q) != T_FUNCTION) return MAX_LOCAL; +  q++; +  num=0; +  while(EXTRACT_UCHAR(q)!=T_MANY) +  { +  num++; +  q+=type_length(q); +  } +  q++; +  if(EXTRACT_UCHAR(q)!=T_VOID) return ~num; +  return num; + } +  + struct pike_string *check_call(struct pike_string *args, +  struct pike_string *type) + { +  reset_type_stack(); +  if(low_get_return_type(type->str,args->str)) +  { +  return pop_type(); +  }else{ +  return 0; +  } + } +  + void check_array_type(struct array *a) + { +  push_type(T_MIXED); + } +  + struct pike_string *get_type_of_svalue(struct svalue *s) + { +  struct pike_string *ret; +  switch(s->type) +  { +  case T_FUNCTION: +  if(s->subtype == -1) +  { +  ret=s->u.efun->type; +  }else{ +  struct program *p; +  +  p=s->u.object->prog; +  if(!p) +  { +  ret=int_type_string; +  }else{ +  ret=ID_FROM_INT(p,s->subtype)->type; +  } +  } +  reference_shared_string(ret); +  return ret; +  +  case T_ARRAY: +  check_array_type(s->u.array); +  push_type(T_ARRAY); +  return pop_type(); +  +  case T_MULTISET: +  check_array_type(s->u.multiset->ind); +  push_type(T_MULTISET); +  return pop_type(); +  +  case T_MAPPING: +  push_type(T_MIXED); +  push_type(T_MIXED); +  push_type(T_MAPPING); +  return pop_type(); +  +  default: +  push_type(s->type); +  return pop_type(); +  } + } +  +  + char *get_name_of_type(int t) + { +  switch(t) +  { +  case T_LVALUE: return "lvalue"; +  case T_INT: return "int"; +  case T_STRING: return "string"; +  case T_ARRAY: return "array"; +  case T_OBJECT: return "object"; +  case T_MAPPING: return "mapping"; +  case T_MULTISET: return "multiset"; +  case T_FUNCTION: return "function"; +  case T_FLOAT: return "float"; +  default: return "unknown"; +  } + } +  + void cleanup_pike_types() + { +  free_string(string_type_string); +  free_string(int_type_string); +  free_string(float_type_string); +  free_string(function_type_string); +  free_string(object_type_string); +  free_string(program_type_string); +  free_string(array_type_string); +  free_string(multiset_type_string); +  free_string(mapping_type_string); +  free_string(mixed_type_string); +  free_string(void_type_string); +  free_string(any_type_string); + }   Newline at end of file added.