diff --git a/src/modules/Parser/initstuff.h b/src/modules/Parser/initstuff.h new file mode 100644 index 0000000000000000000000000000000000000000..a9d50a1e18258f94f32619dc69c1d1a6b3923e12 --- /dev/null +++ b/src/modules/Parser/initstuff.h @@ -0,0 +1,21 @@ +#ifndef PARSER_INITER +#define PARSER_CLASS(a,b,c,what) extern struct program *what; +#define PARSER_SUBMODULE(a,b,c) +#define PARSER_SUBMODMAG(a,b,c) +#define PARSER_FUNCTION(a,name,c,d) void name(INT32 args); +#endif + +PARSER_CLASS("HTML", init_parser_html, exit_parser_html, + parser_html_program ) + + /* +for documentation purpose: + +PARSER_SUBMODULE("ANY", init_parser_any, exit_parser_any ) +PARSER_SUBMODMAG("PNG", init_parser_png, exit_parser_png ) + +PARSER_FUNCTION("lay",parser_lay, + tOr(tFunc(tArr(tOr(tObj,tLayerMap)),tObj), + tFunc(tArr(tOr(tObj,tLayerMap)) + tInt tInt tInt tInt,tObj)),0) + */ diff --git a/src/modules/Parser/parser.c b/src/modules/Parser/parser.c index a97f04045378b037e5180cb41c1520f5875c3bd4..eb368c7057a4526974c19dda9e44d8af0ade5080 100644 --- a/src/modules/Parser/parser.c +++ b/src/modules/Parser/parser.c @@ -1,42 +1,220 @@ -/* - * $Id: parser.c,v 1.2 1999/02/19 19:37:13 mirar Exp $ - */ - #include "global.h" -#include "config.h" - +#include "stralloc.h" +#include "global.h" +RCSID("$Id: parser.c,v 1.3 1999/06/12 13:42:42 mirar Exp $"); +#include "pike_macros.h" +#include "interpret.h" #include "program.h" +#include "object.h" +#include "operators.h" #include "parser.h" -/*** module init & exit & stuff *****************************************/ +#define PARSER_INITER -/* add other parsers here */ +/*#define DEBUG*/ + +#define PARSER_CLASS(name,init,exit,prog) \ + void init(void); void exit(void); struct program *prog; +#define PARSER_SUBMODULE(name,init,exit) \ + void init(void); void exit(void); +#define PARSER_SUBMODMAG(name,init,exit) \ + void init(void); void exit(void); +#define PARSER_FUNCTION(name,func,def0,def1) \ + void func(INT32 args); +#include "initstuff.h" + +static struct +{ + char *name; + void (*init)(void); + void (*exit)(void); + struct program **dest; +} initclass[]= +{ +#undef PARSER_CLASS +#undef PARSER_SUBMODULE +#undef PARSER_FUNCTION +#undef PARSER_SUBMODMAG +#define PARSER_SUBMODMAG(a,b,c) +#define PARSER_FUNCTION(a,b,c,d) +#define PARSER_CLASS(name,init,exit,prog) { name,init,exit,&prog }, +#define PARSER_SUBMODULE(a,b,c) +#include "initstuff.h" +}; + +static struct +{ + char *name; + void (*init)(void); + void (*exit)(void); +} initsubmodule[]= +{ +#undef PARSER_CLASS +#undef PARSER_SUBMODULE +#define PARSER_CLASS(name,init,exit,prog) +#define PARSER_SUBMODULE(name,init,exit) { name,init,exit }, +#include "initstuff.h" +}; -static struct parser_class +static struct { char *name; - void (*func)(void); -} sub[] = { - {"HTML",init_parser_html}, + void (*init)(void); + void (*exit)(void); + struct pike_string *ps; + struct object *o; +} submagic[]= +{ +#undef PARSER_SUBMODULE +#undef PARSER_SUBMODMAG +#define PARSER_SUBMODULE(a,b,c) +#define PARSER_SUBMODMAG(name,init,exit) { name,init,exit,NULL,NULL }, +#include "initstuff.h" }; -void pike_module_exit(void) +#ifdef PIKE_DEBUG +#define PARSER_CHECK_STACK(X) do { if (save_sp != sp) { fatal("%s:%d: %d droppings on stack! previous init: %s\n", __FILE__, __LINE__, sp - save_sp,X); } } while(0) +#else +#define PARSER_CHECK_STACK(X) +#endif /* PIKE_DEBUG */ + + +static void parser_magic_index(INT32 args) { + struct svalue tmp; + int i; + + if (args!=1) + error("Parser.`[]: Too few or too many arguments\n"); + if (sp[-1].type!=T_STRING) + error("Parser.`[]: Illegal type of argument\n"); + + for (i=0; i<(int)NELEM(submagic); i++) + if (sp[-1].u.string==submagic[i].ps) + { +#ifdef PIKE_DEBUG + struct svalue *save_sp; +#endif + pop_stack(); + +#ifdef PIKE_DEBUG + save_sp = sp; +#endif + + if (!submagic[i].o) + { + struct program *p; + start_new_program(); + (submagic[i].init)(); + PARSER_CHECK_STACK(submagic[i].name); + p=end_program(); + submagic[i].o=clone_object(p,0); + free_program(p); + } + + ref_push_object(submagic[i].o); + return; + } + + stack_dup(); + ref_push_object(fp->current_object); + stack_swap(); + f_arrow(2); + + if (sp[-1].type==T_INT) + { + pop_stack(); + stack_dup(); + push_text("_Parser_"); + stack_swap(); + f_add(2); + push_int(0); + SAFE_APPLY_MASTER("resolv",2); + } + if (sp[-1].type==T_INT) + { + pop_stack(); + stack_dup(); + push_text("_Parser"); + push_int(0); + SAFE_APPLY_MASTER("resolv",2); + stack_swap(); + f_index(2); + } + stack_swap(); + pop_stack(); } void pike_module_init(void) { +#ifdef PIKE_DEBUG + struct svalue *save_sp = sp; +#endif + int i; - - for (i=0; i<(int)(sizeof(sub)/sizeof(sub[0])); i++) + for (i=0; i<(int)NELEM(initclass); i++) + { + start_new_program(); + +#ifdef DEBUG + fprintf(stderr,"Parser: initiating class \"Parser.%s\"...\n", + initclass[i].name); +#endif + + (initclass[i].init)(); + PARSER_CHECK_STACK(initclass[i].name); + initclass[i].dest[0]=end_program(); + add_program_constant(initclass[i].name,initclass[i].dest[0],0); + } + + for (i=0; i<(int)NELEM(initsubmodule); i++) { struct program *p; + struct pike_string *s; +#ifdef DEBUG + fprintf(stderr,"Parser: initiating submodule \"Parser.%s\"...\n", + initsubmodule[i].name); +#endif + start_new_program(); - sub[i].func(); + (initsubmodule[i].init)(); + PARSER_CHECK_STACK(initsubmodule[i].name); p=end_program(); - add_program_constant(sub[i].name,p,0); + push_object(clone_object(p,0)); + s=make_shared_string(initsubmodule[i].name); + add_constant(s,sp-1,0); + free_string(s); free_program(p); + pop_stack(); + } + + for (i=0; i<(int)NELEM(submagic); i++) + submagic[i].ps=make_shared_string(submagic[i].name); + +#undef PARSER_FUNCTION +#define PARSER_FUNCTION(name,func,def0,def1) ADD_FUNCTION(name,func,def0,def1); +#include "initstuff.h" + + ADD_FUNCTION("`[]",parser_magic_index, + tFunc(tString,tMixed),0); +} + +void pike_module_exit(void) +{ + int i; + for (i=0; i<(int)NELEM(initclass); i++) + { + (initclass[i].exit)(); + free_program(initclass[i].dest[0]); } + for (i=0; i<(int)NELEM(initsubmodule); i++) + (initsubmodule[i].exit)(); + for (i=0; i<(int)NELEM(submagic); i++) + if (submagic[i].o) + { + (submagic[i].exit)(); + free_object(submagic[i].o); + } }