BSD 4_1_snap release
[unix-history] / usr / src / cmd / lisp / franz / eval2.c
CommitLineData
4b9ccde7 1static char *sccsid = "@(#)eval2.c 35.2 5/18/81";
31cef89c 2
8cd657f4 3#include "global.h"
31cef89c
BJ
4
5/* Iarray - handle array call.
6 * fun - array object
7 * args - arguments to the array call , most likely subscripts.
8 * evalp - flag, if TRUE then the arguments should be evaluated when they
9 * are stacked.
10 */
8cd657f4 11lispval
31cef89c 12Iarray(fun,args,evalp)
8cd657f4
JF
13register lispval fun,args;
14{
15 register lispval reg, temp;
16 register struct argent *lbot, *np;
8cd657f4
JF
17
18 lbot = np;
31cef89c
BJ
19 protect(fun->ar.accfun);
20 for ( ; args != nil ; args = args->d.cdr) /* stack subscripts */
21 if(evalp) protect(eval(args->d.car));
22 else protect(args->d.car);
23 protect(fun);
8cd657f4 24 return(vtemp = Lfuncal());
8cd657f4 25}
8cd657f4 26
4b9ccde7
C
27/* Ifcall :: call foreign function/subroutine
28 * Ifcall is handed a binary object which is the function to call.
29 * This function has already been determined to be a foreign function
30 * by noticing that its discipline field is a string.
31 * The arguments to pass have already been evaluated and stacked. We
32 * create on the stack a 'callg' type argument list to give to the
33 * function. What is passed to the foreign function depends on the
34 * type of argument. Certain args are passes directly, others must be
35 * copied since the foreign function my want to change them.
36 * When the foreign function returns, we may have to box the result,
37 * depending on the type of foreign function.
38 */
8cd657f4
JF
39lispval
40Ifcall(a)
31cef89c 41lispval a;
8cd657f4
JF
42{
43 int *alloca();
44 register int *arglist;
45 register int index;
46 register struct argent *mynp;
47 register lispval ltemp;
48 register struct argent *lbot;
49 register struct argent *np;
31cef89c 50 int itemp;
8cd657f4
JF
51 int nargs = np - lbot;
52
53 arglist = alloca((nargs + 1) * sizeof(int));
54 mynp = lbot;
55 *arglist = nargs;
56 for(index = 1; index <= nargs; index++) {
31cef89c 57 switch(TYPE(ltemp=mynp->val)) {
4b9ccde7 58 /* fixnums and flonums must be reboxed */
8cd657f4
JF
59 case INT:
60 arglist[index] = sp();
61 stack(0);
31cef89c 62 *(int *) arglist[index] = ltemp->i;
8cd657f4
JF
63 break;
64 case DOUB:
65 stack(0);
66 arglist[index] = sp();
67 stack(0);
31cef89c
BJ
68 *(double *) arglist[index] = ltemp->r;
69 break;
4b9ccde7
C
70
71 /* these can all be sent directly */
31cef89c
BJ
72 case HUNK2:
73 case HUNK4:
74 case HUNK8:
75 case HUNK16:
76 case HUNK32:
77 case HUNK64:
78 case HUNK128:
79 case DTPR:
80 case ATOM:
81 case SDOT:
4b9ccde7 82 case STRNG:
31cef89c 83 arglist[index] = (int) ltemp;
8cd657f4 84 break;
4b9ccde7 85 /* these cause only part of the structure to be sent */
31cef89c 86
8cd657f4 87 case ARRAY:
31cef89c
BJ
88 arglist[index] = (int) ltemp->ar.data;
89 break;
90
91
92 case BCD:
93 arglist[index] = (int) ltemp->bcd.entry;
94 break;
95
96 default:
97 error("foreign call: illegal argument ",FALSE);
98 break;
8cd657f4
JF
99 }
100 mynp++;
101 }
31cef89c
BJ
102 switch(((char *)a->bcd.discipline)[0]) {
103 case 'i': /* integer-function */
104 ltemp = inewint(callg(a->bcd.entry,arglist));
8cd657f4
JF
105 break;
106
31cef89c 107 case 'r': /* real-function*/
8cd657f4 108 ltemp = newdoub();
31cef89c
BJ
109 ltemp->r = (* ((double (*)()) callg))(a->bcd.entry,arglist);
110 break;
111
112 case 'f': /* function */
113 ltemp = (lispval) callg(a->bcd.entry,arglist);
8cd657f4
JF
114 break;
115
116 default:
31cef89c
BJ
117 case 's': /* subroutine */
118 callg(a->bcd.entry,arglist);
8cd657f4
JF
119 ltemp = tatom;
120 }
31cef89c 121 return(ltemp);
8cd657f4 122}
4b9ccde7
C
123
124
8cd657f4
JF
125callg(funct,arglist)
126lispval (*funct)();
127int *arglist;
128{
129 asm(" callg *8(ap),*4(ap)");
130}