Annotation of OpenXM_contrib2/asir2000/io/ox_asir.c, Revision 1.44
1.15 noro 1: /*
2: * Copyright (c) 1994-2000 FUJITSU LABORATORIES LIMITED
3: * All rights reserved.
4: *
5: * FUJITSU LABORATORIES LIMITED ("FLL") hereby grants you a limited,
6: * non-exclusive and royalty-free license to use, copy, modify and
7: * redistribute, solely for non-commercial and non-profit purposes, the
8: * computer program, "Risa/Asir" ("SOFTWARE"), subject to the terms and
9: * conditions of this Agreement. For the avoidance of doubt, you acquire
10: * only a limited right to use the SOFTWARE hereunder, and FLL or any
11: * third party developer retains all rights, including but not limited to
12: * copyrights, in and to the SOFTWARE.
13: *
14: * (1) FLL does not grant you a license in any way for commercial
15: * purposes. You may use the SOFTWARE only for non-commercial and
16: * non-profit purposes only, such as academic, research and internal
17: * business use.
18: * (2) The SOFTWARE is protected by the Copyright Law of Japan and
19: * international copyright treaties. If you make copies of the SOFTWARE,
20: * with or without modification, as permitted hereunder, you shall affix
21: * to all such copies of the SOFTWARE the above copyright notice.
22: * (3) An explicit reference to this SOFTWARE and its copyright owner
23: * shall be made on your publication or presentation in any form of the
24: * results obtained by use of the SOFTWARE.
25: * (4) In the event that you modify the SOFTWARE, you shall notify FLL by
1.16 noro 26: * e-mail at risa-admin@sec.flab.fujitsu.co.jp of the detailed specification
1.15 noro 27: * for such modification or the source code of the modified part of the
28: * SOFTWARE.
29: *
30: * THE SOFTWARE IS PROVIDED AS IS WITHOUT ANY WARRANTY OF ANY KIND. FLL
31: * MAKES ABSOLUTELY NO WARRANTIES, EXPRESSED, IMPLIED OR STATUTORY, AND
32: * EXPRESSLY DISCLAIMS ANY IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS
33: * FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT OF THIRD PARTIES'
34: * RIGHTS. NO FLL DEALER, AGENT, EMPLOYEES IS AUTHORIZED TO MAKE ANY
35: * MODIFICATIONS, EXTENSIONS, OR ADDITIONS TO THIS WARRANTY.
36: * UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, TORT, CONTRACT,
37: * OR OTHERWISE, SHALL FLL BE LIABLE TO YOU OR ANY OTHER PERSON FOR ANY
38: * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, PUNITIVE OR CONSEQUENTIAL
39: * DAMAGES OF ANY CHARACTER, INCLUDING, WITHOUT LIMITATION, DAMAGES
40: * ARISING OUT OF OR RELATING TO THE SOFTWARE OR THIS AGREEMENT, DAMAGES
41: * FOR LOSS OF GOODWILL, WORK STOPPAGE, OR LOSS OF DATA, OR FOR ANY
42: * DAMAGES, EVEN IF FLL SHALL HAVE BEEN INFORMED OF THE POSSIBILITY OF
43: * SUCH DAMAGES, OR FOR ANY CLAIM BY ANY OTHER PARTY. EVEN IF A PART
44: * OF THE SOFTWARE HAS BEEN DEVELOPED BY A THIRD PARTY, THE THIRD PARTY
45: * DEVELOPER SHALL HAVE NO LIABILITY IN CONNECTION WITH THE USE,
46: * PERFORMANCE OR NON-PERFORMANCE OF THE SOFTWARE.
1.44 ! noro 47: * $OpenXM: OpenXM_contrib2/asir2000/io/ox_asir.c,v 1.43 2003/03/07 06:39:57 noro Exp $
1.15 noro 48: */
1.1 noro 49: #include "ca.h"
50: #include "parse.h"
1.6 noro 51: #include "signal.h"
1.1 noro 52: #include "ox.h"
53: #include "version.h"
1.41 ohara 54: #if defined(PARI)
1.6 noro 55: #include "genpari.h"
56: #endif
1.1 noro 57:
58: void ox_usr1_handler();
1.13 noro 59: int asir_ox_init();
1.1 noro 60:
1.36 noro 61: /* environement is defined in libpari.a */
62: extern jmp_buf environnement;
1.1 noro 63:
64: extern int do_message;
65: extern int ox_flushing;
1.35 noro 66: extern JMP_BUF ox_env;
1.1 noro 67: extern MATHCAP my_mathcap;
68:
1.11 noro 69: extern int little_endian,ox_sock_id;
70:
1.1 noro 71: int ox_sock_id;
1.11 noro 72: int lib_ox_need_conv;
1.1 noro 73:
1.19 noro 74: void create_error(ERR *,unsigned int ,char *);
75:
1.20 noro 76: int asir_OperandStackSize;
77: Obj *asir_OperandStack;
78: int asir_OperandStackPtr = -1;
79:
80: void ox_io_init();
1.40 noro 81: void ox_asir_init(int,char **,char *);
1.20 noro 82: Obj asir_pop_one();
83: Obj asir_peek_one();
84: void asir_push_one(Obj);
85: void asir_end_flush();
86: int asir_executeString();
87: void asir_evalName(unsigned int);
88: void asir_setName(unsigned int);
89: void asir_pops();
90: void asir_popString();
91: void asir_popCMO(unsigned int);
92: void asir_popSerializedLocalObject();
93: void asir_pushCMOtag(unsigned int);
94: LIST asir_GetErrorList();
95: char *name_of_cmd(int);
96: char *name_of_id(int);
97:
98: static void asir_do_cmd(int,unsigned int);
1.1 noro 99: static void asir_executeFunction(int);
100:
1.43 noro 101: #if defined(MPI)
1.14 noro 102: /* XXX : currently MPI version supports only a homogeneous cluster. */
103:
1.1 noro 104: extern int mpi_nprocs,mpi_myid;
105:
106: void ox_mpi_master_init() {
1.14 noro 107: int i,idx;
1.1 noro 108:
1.14 noro 109: for ( i = 0; i < mpi_nprocs; i++ ) {
110: /* ordering information is not exchanged */
111: /* idx should be equal to i */
1.1 noro 112: idx = get_iofp(i,0,0);
1.14 noro 113: register_server(0,idx,idx);
1.1 noro 114: }
115: }
116:
117: void ox_mpi_slave_init() {
1.14 noro 118: int i,idx;
119:
1.1 noro 120: endian_init();
121: fclose(stdin);
1.14 noro 122: for ( i = 0; i < mpi_nprocs; i++ ) {
123: /* ordering information is not exchanged */
124: /* idx should be equal to i */
125: idx = get_iofp(i,0,0);
126: register_server(0,idx,idx);
127: }
1.1 noro 128: asir_OperandStackSize = BUFSIZ;
129: asir_OperandStack = (Obj *)CALLOC(asir_OperandStackSize,sizeof(Obj));
130: asir_OperandStackPtr = -1;
131: }
132: #endif
133:
134: void ox_main(int argc,char **argv) {
135: int id;
1.13 noro 136: int cmd;
1.1 noro 137: Obj obj;
138: ERR err;
139: unsigned int serial;
140: int ret;
141: extern char LastError[];
142:
1.40 noro 143: ox_asir_init(argc,argv,"ox_asir");
1.1 noro 144: if ( do_message )
145: fprintf(stderr,"I'm an ox_asir, Version %d.\n",ASIR_VERSION);
1.35 noro 146: if ( SETJMP(ox_env) ) {
1.1 noro 147: while ( NEXT(asir_infile) )
148: closecurrentinput();
149: ox_send_sync(0);
150: }
151: while ( 1 ) {
152: extern int recv_intr;
153:
154: serial = ox_recv(0,&id,&obj);
155: #if defined(VISUAL)
156: if ( recv_intr ) {
157: if ( recv_intr == 1 ) {
158: recv_intr = 0;
159: int_handler(SIGINT);
160: } else {
161: recv_intr = 0;
162: ox_usr1_handler(0);
163: }
164: }
165: #endif
166: if ( do_message )
167: fprintf(stderr,"#%d Got %s",serial,name_of_id(id));
168: switch ( id ) {
169: case OX_COMMAND:
170: cmd = ((USINT)obj)->body;
171: if ( ox_flushing )
172: break;
173: if ( do_message )
174: fprintf(stderr," %s\n",name_of_cmd(cmd));
1.35 noro 175: if ( ret = SETJMP(main_env) ) {
1.1 noro 176: if ( ret == 1 ) {
177: create_error(&err,serial,LastError);
178: asir_push_one((Obj)err);
179: }
180: break;
181: }
182: asir_do_cmd(cmd,serial);
183: break;
184: case OX_DATA:
185: case OX_LOCAL_OBJECT_ASIR:
186: if ( ox_flushing )
187: break;
188: if ( do_message )
189: fprintf(stderr," -> data pushed");
190: asir_push_one(obj);
191: break;
192: case OX_SYNC_BALL:
193: asir_end_flush();
194: break;
195: default:
196: break;
197: }
198: if ( do_message )
199: fprintf(stderr,"\n");
200: }
201: }
202:
1.13 noro 203: static void asir_do_cmd(int cmd,unsigned int serial)
1.1 noro 204: {
205: MATHCAP client_mathcap;
206: Q q;
207: int i;
208: LIST list;
209:
210: switch ( cmd ) {
211: case SM_dupErrors:
212: list = asir_GetErrorList();
213: asir_push_one((Obj)list);
214: break;
215: case SM_getsp:
216: i = asir_OperandStackPtr+1;
217: STOQ(i,q);
218: asir_push_one((Obj)q);
219: break;
220: case SM_popSerializedLocalObject:
221: asir_popSerializedLocalObject();
222: break;
223: case SM_popCMO:
224: asir_popCMO(serial);
225: break;
226: case SM_popString:
227: asir_popString();
228: break;
229: case SM_setName:
230: asir_setName(serial);
231: break;
232: case SM_evalName:
233: asir_evalName(serial);
234: break;
235: case SM_executeStringByLocalParser:
236: asir_executeString();
237: break;
238: case SM_executeStringByLocalParserInBatchMode:
239: asir_executeString();
240: asir_pop_one();
241: break;
242: case SM_executeFunction:
243: asir_executeFunction(serial);
244: break;
245: case SM_shutdown:
246: asir_terminate(2);
247: break;
248: case SM_pops:
249: asir_pops();
250: break;
251: case SM_mathcap:
252: asir_push_one((Obj)my_mathcap);
253: break;
254: case SM_setMathcap:
255: client_mathcap = (MATHCAP)asir_pop_one();
256: store_remote_mathcap(0,client_mathcap);
257: break;
1.18 noro 258: case SM_pushCMOtag:
259: asir_pushCMOtag(serial);
260: break;
1.1 noro 261: case SM_nop:
262: default:
263: break;
264: }
265: }
266:
1.20 noro 267: char *name_of_id(int id)
1.1 noro 268: {
269: switch ( id ) {
270: case OX_COMMAND:
271: return "OX_COMMAND";
272: break;
273: case OX_DATA:
274: return "OX_DATA";
275: break;
276: case OX_LOCAL_OBJECT_ASIR:
277: return "OX_LOCAL_OBJECT_ASIR";
278: break;
279: case OX_SYNC_BALL:
280: return "OX_SYNC_BALL";
281: break;
282: default:
283: return "Unknown id";
284: break;
285: }
286: }
287:
1.20 noro 288: char *name_of_cmd(int cmd)
1.1 noro 289: {
290: switch ( cmd ) {
291: case SM_popSerializedLocalObject:
292: return "SM_popSerializedLocalObject";
293: break;
294: case SM_popCMO:
295: return "SM_popCMO";
296: break;
297: case SM_popString:
298: return "SM_popString";
299: break;
300: case SM_pops:
301: return "SM_pops";
302: break;
303: case SM_setName:
304: return "SM_setName";
305: break;
306: case SM_evalName:
307: return "SM_evalName";
308: break;
309: case SM_executeStringByLocalParser:
310: return "SM_executeString";
311: break;
312: case SM_executeFunction:
313: return "SM_executeFunction";
314: break;
315: case SM_shutdown:
316: return "SM_shutdown";
317: break;
318: case SM_beginBlock:
319: return "SM_beginBlock";
320: break;
321: case SM_endBlock:
322: return "SM_endBlock";
323: break;
324: case SM_mathcap:
325: return "SM_mathcap";
326: break;
327: case SM_setMathcap:
328: return "SM_setMathcap";
329: break;
330: case SM_getsp:
331: return "SM_setMathcap";
332: break;
333: case SM_dupErrors:
334: return "SM_dupErrors";
335: break;
336: case SM_nop:
337: return "SM_nop";
1.18 noro 338: case SM_pushCMOtag:
339: return "SM_pushCMOtag";
1.1 noro 340: default:
341: return "Unknown cmd";
342: break;
343: }
344: }
345:
1.20 noro 346: LIST asir_GetErrorList()
1.1 noro 347: {
348: int i;
349: NODE n,n0;
350: LIST err;
351: Obj obj;
352:
353: for ( i = 0, n0 = 0; i <= asir_OperandStackPtr; i++ )
354: if ( (obj = asir_OperandStack[i]) && (OID(obj) == O_ERR) ) {
355: NEXTNODE(n0,n); BDY(n) = (pointer)obj;
356: }
357: if ( n0 )
358: NEXT(n) = 0;
359: MKLIST(err,n0);
360: return err;
361: }
362:
1.20 noro 363: void asir_popSerializedLocalObject()
1.1 noro 364: {
365: Obj obj;
366: VL t,vl;
367:
368: obj = asir_pop_one();
369: get_vars_recursive(obj,&vl);
370: for ( t = vl; t; t = NEXT(t) )
371: if ( t->v->attr == (pointer)V_UC )
372: error("bsave : not implemented");
373: ox_send_cmd(0,SM_beginBlock);
374: ox_send_local_ring(0,vl);
375: ox_send_local_data(0,obj);
376: ox_send_cmd(0,SM_endBlock);
377: }
378:
1.20 noro 379: void asir_popCMO(unsigned int serial)
1.1 noro 380: {
381: Obj obj;
382: ERR err;
383:
384: obj = asir_pop_one();
385: if ( valid_as_cmo(obj) )
386: ox_send_data(0,obj);
387: else {
388: create_error(&err,serial,"cannot convert to CMO object");
389: ox_send_data(0,err);
390: asir_push_one(obj);
391: }
392: }
393:
1.20 noro 394: void asir_pushCMOtag(unsigned int serial)
1.18 noro 395: {
396: Obj obj;
397: ERR err;
398: USINT ui;
399: int tag;
400:
401: obj = asir_peek_one();
402: if ( cmo_tag(obj,&tag) ) {
403: MKUSINT(ui,tag);
404: asir_push_one((Obj)ui);
405: } else {
406: create_error(&err,serial,"cannot convert to CMO object");
407: asir_push_one((Obj)err);
408: }
409: }
410:
1.20 noro 411: void asir_popString()
1.1 noro 412: {
413: Obj val;
414: char *buf,*obuf;
415: int l;
416: STRING str;
417:
418: val = asir_pop_one();
419: if ( !val )
1.24 noro 420: obuf = "0";
1.1 noro 421: else {
422: l = estimate_length(CO,val);
423: buf = (char *)ALLOCA(l+1);
424: soutput_init(buf);
425: sprintexpr(CO,val);
426: l = strlen(buf);
427: obuf = (char *)MALLOC(l+1);
428: strcpy(obuf,buf);
429: }
430: MKSTR(str,obuf);
431: ox_send_data(0,str);
432: }
433:
1.20 noro 434: void asir_pops()
1.1 noro 435: {
436: int n;
437:
438: n = (int)(((USINT)asir_pop_one())->body);
439: asir_OperandStackPtr = MAX(asir_OperandStackPtr-n,-1);
440: }
441:
1.20 noro 442: void asir_setName(unsigned int serial)
1.1 noro 443: {
444: char *name;
445: int l,n;
446: char *dummy = "=0;";
447: SNODE snode;
448: ERR err;
449:
450: name = ((STRING)asir_pop_one())->body;
451: l = strlen(name);
452: n = l+strlen(dummy)+1;
453: parse_strp = (char *)ALLOCA(n);
454: sprintf(parse_strp,"%s%s",name,dummy);
455: if ( mainparse(&snode) ) {
456: create_error(&err,serial,"cannot set to variable");
457: asir_push_one((Obj)err);
458: } else {
459: FA1((FNODE)FA0(snode)) = (pointer)mkfnode(1,I_FORMULA,asir_pop_one());
460: evalstat(snode);
461: }
462: }
463:
1.20 noro 464: void asir_evalName(unsigned int serial)
1.1 noro 465: {
466: char *name;
467: int l,n;
468: SNODE snode;
469: ERR err;
470: pointer val;
471:
472: name = ((STRING)asir_pop_one())->body;
473: l = strlen(name);
474: n = l+2;
475: parse_strp = (char *)ALLOCA(n);
476: sprintf(parse_strp,"%s;",name);
477: if ( mainparse(&snode) ) {
478: create_error(&err,serial,"no such variable");
479: val = (pointer)err;
480: } else
481: val = evalstat(snode);
482: asir_push_one(val);
483: }
484:
1.20 noro 485: int asir_executeString()
1.1 noro 486: {
487: SNODE snode;
488: pointer val;
489: char *cmd;
1.41 ohara 490: #if defined(PARI)
1.1 noro 491: recover(0);
1.36 noro 492: /* environement is defined in libpari.a */
493: if ( setjmp(environnement) ) {
1.1 noro 494: avma = top; recover(1);
495: resetenv("");
496: }
497: #endif
498: cmd = ((STRING)asir_pop_one())->body;
499: parse_strp = cmd;
500: if ( mainparse(&snode) ) {
501: return -1;
502: }
503: val = evalstat(snode);
504: if ( NEXT(asir_infile) ) {
505: while ( NEXT(asir_infile) ) {
506: if ( mainparse(&snode) ) {
507: asir_push_one(val);
508: return -1;
509: }
510: nextbp = 0;
511: val = evalstat(snode);
512: }
513: }
514: asir_push_one(val);
515: return 0;
516: }
517:
518: static void asir_executeFunction(int serial)
519: {
520: char *func;
521: int argc;
522: FUNC f;
523: Obj result;
524: NODE n,n1;
525: STRING fname;
526: char *path;
527: ERR err;
1.5 noro 528: Obj arg;
1.1 noro 529: static char buf[BUFSIZ];
530:
1.5 noro 531: arg = asir_pop_one();
532: if ( !arg || OID(arg) != O_STR ) {
533: sprintf(buf,"executeFunction : invalid function name");
534: goto error;
535: } else
536: func = ((STRING)arg)->body;
537:
538: arg = asir_pop_one();
539: if ( !arg || OID(arg) != O_USINT ) {
540: sprintf(buf,"executeFunction : invalid argc");
541: goto error;
542: } else
543: argc = (int)(((USINT)arg)->body);
1.1 noro 544:
545: for ( n = 0; argc; argc-- ) {
546: NEXTNODE(n,n1);
547: BDY(n1) = (pointer)asir_pop_one();
548: }
549: if ( n )
550: NEXT(n1) = 0;
551:
552: if ( !strcmp(func,"load") ) {
553: fname = (STRING)BDY(n);
554: if ( OID(fname) == O_STR ) {
555: searchasirpath(BDY(fname),&path);
556: if ( path ) {
557: if ( do_message )
558: fprintf(stderr,"loading %s\n",path);
559: execasirfile(path);
560: } else
561: if ( do_message )
562: fprintf(stderr,"load : %s not found in the search path\n",BDY(fname));
563: }
564: result = 0;
565: } else {
566: searchf(noargsysf,func,&f);
567: if ( !f )
568: searchf(sysf,func,&f);
569: if ( !f )
570: searchf(ubinf,func,&f);
571: if ( !f )
572: searchf(usrf,func,&f);
573: if ( !f ) {
574: sprintf(buf,"executeFunction : the function %s not found",func);
1.5 noro 575: goto error;
1.1 noro 576: } else {
577: result = (Obj)bevalf(f,n);
578: }
579: }
1.5 noro 580: asir_push_one(result);
581: return;
582:
583: error:
584: create_error(&err,serial,buf);
585: result = (Obj)err;
1.1 noro 586: asir_push_one(result);
587: }
588:
1.20 noro 589: void asir_end_flush()
1.1 noro 590: {
591: ox_flushing = 0;
592: }
593:
594: /*
595: asir_OperandStackPtr points to the surface of the stack.
596: That is, the data at the stack top is
597: asir_OperandStack[asir_OperandStackPtr].
598: */
599:
600:
1.20 noro 601: void asir_push_one(Obj obj)
1.1 noro 602: {
603: if ( !obj || OID(obj) != O_VOID ) {
604: asir_OperandStackPtr++;
605: if ( asir_OperandStackPtr >= asir_OperandStackSize ) {
606: asir_OperandStackSize += BUFSIZ;
607: asir_OperandStack
608: = (Obj *)REALLOC(asir_OperandStack,
609: asir_OperandStackSize*sizeof(Obj));
610: }
611: asir_OperandStack[asir_OperandStackPtr] = obj;
612: }
613: }
614:
1.20 noro 615: Obj asir_pop_one() {
1.1 noro 616: if ( asir_OperandStackPtr < 0 ) {
617: if ( do_message )
618: fprintf(stderr,"OperandStack underflow");
619: return 0;
620: } else {
621: if ( do_message )
622: fprintf(stderr,"pop at %d\n",asir_OperandStackPtr);
623: return asir_OperandStack[asir_OperandStackPtr--];
1.18 noro 624: }
625: }
626:
1.20 noro 627: Obj asir_peek_one() {
1.18 noro 628: if ( asir_OperandStackPtr < 0 ) {
629: if ( do_message )
630: fprintf(stderr,"OperandStack underflow");
631: return 0;
632: } else {
633: if ( do_message )
634: fprintf(stderr,"peek at %d\n",asir_OperandStackPtr);
635: return asir_OperandStack[asir_OperandStackPtr];
1.1 noro 636: }
637: }
638:
1.40 noro 639: void ox_asir_init(int argc,char **argv,char *servername)
1.1 noro 640: {
641: char ifname[BUFSIZ];
642: extern int GC_dont_gc;
643: extern int read_exec_file;
644: extern int do_asirrc;
645: extern int do_server_in_X11;
1.37 noro 646: extern char displayname[];
1.1 noro 647: char *getenv();
648: static ox_asir_initialized = 0;
649: FILE *ifp;
1.4 noro 650: char *homedir;
651: char *ptr;
1.32 noro 652: #if !defined(VISUAL)
653: int tmp;
654: #endif
1.1 noro 655:
1.43 noro 656: #if !defined(VISUAL) && !defined(MPI)
1.1 noro 657: do_server_in_X11 = 1; /* XXX */
658: #endif
659: asir_save_handler();
1.41 ohara 660: #if defined(PARI)
1.1 noro 661: risa_pari_init();
662: #endif
663: srandom((int)get_current_time());
664:
665: rtime_init();
666: env_init();
667: endian_init();
668: GC_init();
1.44 ! noro 669: cppname_init();
1.1 noro 670: process_args(--argc,++argv);
1.37 noro 671: #if defined(__CYGWIN__)
672: if ( !displayname[0] )
673: do_server_in_X11 = 0; /* XXX */
674: #endif
1.1 noro 675: output_init();
676: arf_init();
677: nglob_init();
678: glob_init();
679: sig_init();
680: tty_init();
681: debug_init();
682: pf_init();
683: sysf_init();
684: parif_init();
685: #if defined(VISUAL)
686: init_socket();
687: #endif
688: #if defined(UINIT)
689: reg_sysf();
690: #endif
1.4 noro 691: /* if ASIR_CONFIG is set, execute it; else execute .asirrc */
692: if ( ptr = getenv("ASIR_CONFIG") )
693: strcpy(ifname,ptr);
694: else {
695: homedir = getenv("HOME");
696: if ( !homedir ) {
697: char rootname[BUFSIZ];
698:
699: get_rootdir(rootname,sizeof(rootname));
700: homedir = rootname;
701: }
702: sprintf(ifname,"%s/.asirrc",homedir);
703: }
1.1 noro 704: if ( do_asirrc && (ifp = fopen(ifname,"r")) ) {
705: input_init(ifp,ifname);
1.35 noro 706: if ( !SETJMP(main_env) ) {
1.1 noro 707: read_exec_file = 1;
708: read_eval_loop();
709: read_exec_file = 0;
710: }
711: fclose(ifp);
712: }
713: input_init(0,"string");
1.30 noro 714: /* XXX Windows compatibility */
715: ox_io_init();
1.40 noro 716: create_my_mathcap(servername);
1.1 noro 717: }
718:
1.20 noro 719: void ox_io_init() {
1.1 noro 720: unsigned char c,rc;
1.21 noro 721: extern int I_am_server;
1.26 noro 722:
1.33 noro 723: /* XXX : ssh forwards stdin to a remote host on PC Unix */
724: #if defined(linux)
725: #include <sys/param.h>
1.32 noro 726: int i;
727:
728: close(0);
729: for ( i = 5; i < NOFILE; i++ )
730: close(i);
1.33 noro 731: #elif defined(__FreeBSD__)
1.27 noro 732: #include <sys/resource.h>
1.33 noro 733: int i;
1.32 noro 734: struct rlimit rl;
1.27 noro 735:
1.32 noro 736: getrlimit(RLIMIT_NOFILE,&rl);
737: close(0);
738: for ( i = 5; i < rl.rlim_cur; i++ )
739: close(i);
1.27 noro 740: #endif
1.1 noro 741:
1.21 noro 742: I_am_server = 1;
1.1 noro 743: endian_init();
744: #if defined(VISUAL)
745: if ( !ox_sock_id )
746: exit(0);
747: iofp[0].in = WSIO_open(ox_sock_id,"r");
748: iofp[0].out = WSIO_open(ox_sock_id,"w");
749: #else
750: iofp[0].in = fdopen(3,"r");
751: iofp[0].out = fdopen(4,"w");
752:
1.34 noro 753: #if !defined(__CYGWIN__)
1.1 noro 754: setbuffer(iofp[0].in,(char *)malloc(LBUFSIZ),LBUFSIZ);
755: setbuffer(iofp[0].out,(char *)malloc(LBUFSIZ),LBUFSIZ);
1.34 noro 756: #endif
1.1 noro 757: signal(SIGUSR1,ox_usr1_handler);
758: #endif
759: asir_OperandStackSize = BUFSIZ;
760: asir_OperandStack = (Obj *)CALLOC(asir_OperandStackSize,sizeof(Obj));
761: asir_OperandStackPtr = -1;
762: if ( little_endian )
763: c = 1;
764: else
765: c = 0xff;
766: /* server : write -> read */
767: write_char(iofp[0].out,&c); ox_flush_stream_force(0);
768: read_char(iofp[0].in,&rc);
769: iofp[0].conv = c == rc ? 0 : 1;
1.14 noro 770: /* XXX; for raw I/O */
771: register_server(0,0,0);
1.3 noro 772: }
773:
1.17 noro 774: #if !defined(VISUAL)
1.3 noro 775: /*
776: * Library mode functions
777: */
778:
779: /*
780: * Converts a binary encoded CMO into a risa object
781: * and pushes it onto the stack.
782: */
783:
784: void asir_ox_push_cmo(void *cmo)
785: {
786: Obj obj;
787:
788: ox_copy_init(cmo);
789: ox_buf_to_obj_as_cmo(&obj);
790: asir_push_one(obj);
791: }
792:
793: /*
794: * Pop an object from the stack and converts it
1.28 noro 795: * into a binary encoded CMO.
1.3 noro 796: */
797:
798: int asir_ox_pop_cmo(void *cmo, int limit)
799: {
800: Obj obj;
801: int len;
1.11 noro 802: ERR err;
1.3 noro 803:
804: obj = asir_pop_one();
1.10 noro 805: if ( !valid_as_cmo(obj) ) {
1.11 noro 806: asir_push_one(obj);
807: create_error(&err,0,"The object at the stack top is invalid as a CMO.");
808: obj = (Obj)err;
1.10 noro 809: }
1.3 noro 810: len = count_as_cmo(obj);
811: if ( len <= limit ) {
812: ox_copy_init(cmo);
813: ox_obj_to_buf_as_cmo(obj);
814: return len;
815: } else
816: return -1;
1.28 noro 817: }
818:
819: int asir_ox_pop_string(void *string, int limit)
820: {
821: Obj val;
822: int l;
823:
824: val = asir_pop_one();
825: if ( !val ) {
826: if ( limit >= 2 ) {
827: sprintf(string,"0");
828: l = strlen(string);
829: } else
830: l = -1;
831: } else {
832: l = estimate_length(CO,val);
833: if ( l+1 <= limit ) {
834: soutput_init(string);
835: sprintexpr(CO,val);
836: l = strlen(string);
837: } else
838: l = -1;
839: }
840: return l;
1.3 noro 841: }
842:
843: /*
844: * Executes an SM command.
845: */
846:
1.13 noro 847: void asir_ox_push_cmd(int cmd)
1.3 noro 848: {
1.7 noro 849: int ret;
850: ERR err;
851: extern char LastError[];
852:
1.35 noro 853: if ( ret = SETJMP(main_env) ) {
1.12 noro 854: asir_reset_handler();
1.7 noro 855: if ( ret == 1 ) {
856: create_error(&err,0,LastError); /* XXX */
857: asir_push_one((Obj)err);
858: }
1.12 noro 859: } else {
860: asir_save_handler();
861: asir_set_handler();
1.7 noro 862: asir_do_cmd(cmd,0);
1.12 noro 863: asir_reset_handler();
864: }
1.3 noro 865: }
866:
867: /*
868: * Executes a string written in Asir.
869: */
870:
871: void asir_ox_execute_string(char *s)
872: {
873: STRING str;
1.8 noro 874: int ret;
875: ERR err;
876: extern char LastError[];
1.3 noro 877:
878: MKSTR(str,s);
879: asir_push_one((Obj)str);
1.35 noro 880: if ( ret = SETJMP(main_env) ) {
1.12 noro 881: asir_reset_handler();
1.8 noro 882: if ( ret == 1 ) {
883: create_error(&err,0,LastError); /* XXX */
884: asir_push_one((Obj)err);
885: }
1.12 noro 886: } else {
887: asir_save_handler();
888: asir_set_handler();
1.8 noro 889: asir_executeString();
1.12 noro 890: asir_reset_handler();
891: }
1.3 noro 892: }
893:
894: /*
895: * Returns the size as a CMO of the object
896: * at the top of the stack.
897: */
898:
899: int asir_ox_peek_cmo_size()
900: {
901: Obj obj;
902: int len;
903:
1.38 noro 904: obj = asir_peek_one();
1.10 noro 905: if ( !valid_as_cmo(obj) ) {
906: fprintf(stderr,"The object at the stack top is invalid as a CMO.\n");
907: return 0;
908: }
1.3 noro 909: len = count_as_cmo(obj);
1.38 noro 910: return len;
911: }
912:
913: int asir_ox_peek_cmo_string_length()
914: {
915: Obj obj;
916: int len;
917:
918: obj = asir_peek_one();
919: if ( !valid_as_cmo(obj) ) {
920: fprintf(stderr,"The object at the stack top is invalid as a CMO.\n");
921: return 0;
922: }
923: len = estimate_length(CO,obj);
1.39 noro 924: return len+1;
1.3 noro 925: }
926:
927: /*
928: * Initialization.
1.11 noro 929: * byteorder=0 => native
930: * =1 => network byte order
1.3 noro 931: */
932:
1.13 noro 933: int asir_ox_init(int byteorder)
1.3 noro 934: {
935: int tmp;
936: char ifname[BUFSIZ];
937: extern int GC_dont_gc;
938: extern int read_exec_file;
939: extern int do_asirrc;
940: extern int do_server_in_X11;
941: char *getenv();
942: static ox_asir_initialized = 0;
943: FILE *ifp;
944:
1.43 noro 945: #if !defined(VISUAL) && !defined(MPI)
1.9 noro 946: do_server_in_X11 = 0; /* XXX */
1.3 noro 947: #endif
948: asir_save_handler();
1.41 ohara 949: #if defined(PARI)
1.3 noro 950: risa_pari_init();
951: #endif
952: srandom((int)get_current_time());
953:
954: rtime_init();
955: env_init();
956: endian_init();
957: GC_init();
958: /* process_args(argc,argv); */
959: output_init();
960: arf_init();
961: nglob_init();
962: glob_init();
963: sig_init();
964: tty_init();
965: debug_init();
966: pf_init();
967: sysf_init();
968: parif_init();
969: #if defined(VISUAL)
970: init_socket();
971: #endif
972: #if defined(UINIT)
973: reg_sysf();
974: #endif
975: sprintf(ifname,"%s/.asirrc",getenv("HOME"));
976: if ( do_asirrc && (ifp = fopen(ifname,"r")) ) {
977: input_init(ifp,ifname);
1.35 noro 978: if ( !SETJMP(main_env) ) {
1.3 noro 979: read_exec_file = 1;
980: read_eval_loop();
981: read_exec_file = 0;
982: }
983: fclose(ifp);
984: }
985: input_init(0,"string");
986:
987: asir_OperandStackSize = BUFSIZ;
988: asir_OperandStack = (Obj *)CALLOC(asir_OperandStackSize,sizeof(Obj));
989: asir_OperandStackPtr = -1;
1.11 noro 990: if ( little_endian && byteorder )
991: lib_ox_need_conv = 1;
1.3 noro 992: else
1.11 noro 993: lib_ox_need_conv = 0;
1.3 noro 994: do_message = 0;
1.11 noro 995: create_my_mathcap("ox_asir");
1.12 noro 996: asir_reset_handler();
1.13 noro 997: return 0;
1.1 noro 998: }
1.17 noro 999: #endif
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>