11 #include <floatingpoint.h>
20 #define tonumber(o) ((tag(o) != T_NUMBER) && (lua_tonumber(o) != 0))
21 #define tostring(o) ((tag(o) != T_STRING) && (lua_tostring(o) != 0))
26 static Object stack
[MAXSTACK
] = {{T_MARK
, {NULL
}}};
27 static Object
*top
=stack
+1, *base
=stack
+1;
31 ** Concatenate two given string, creating a mark space at the beginning.
32 ** Return the new string pointer.
34 static char *lua_strconc (char *l
, char *r
)
36 char *s
= calloc (strlen(l
)+strlen(r
)+2, sizeof(char));
39 lua_error ("not enough memory");
42 *s
++ = 0; /* create mark space */
43 return strcat(strcpy(s
,l
),r
);
47 ** Duplicate a string, creating a mark space at the beginning.
48 ** Return the new string pointer.
50 char *lua_strdup (char *l
)
52 char *s
= calloc (strlen(l
)+2, sizeof(char));
55 lua_error ("not enough memory");
58 *s
++ = 0; /* create mark space */
63 ** Convert, if possible, to a number tag.
64 ** Return 0 in success or not 0 on error.
66 static int lua_tonumber (Object
*obj
)
69 if (tag(obj
) != T_STRING
)
71 lua_reportbug ("unexpected type at conversion to number");
74 nvalue(obj
) = strtod(svalue(obj
), &ptr
);
77 lua_reportbug ("string to number convertion failed");
85 ** Test if is possible to convert an object to a number one.
86 ** If possible, return the converted object, otherwise return nil object.
88 static Object
*lua_convtonumber (Object
*obj
)
92 if (tag(obj
) == T_NUMBER
)
99 if (tag(obj
) == T_STRING
)
102 nvalue(&cvt
) = strtod(svalue(obj
), &ptr
);
104 tag(&cvt
) = T_NUMBER
;
112 ** Convert, if possible, to a string tag
113 ** Return 0 in success or not 0 on error.
115 static int lua_tostring (Object
*obj
)
118 if (tag(obj
) != T_NUMBER
)
120 lua_reportbug ("unexpected type at conversion to string");
123 if ((int) nvalue(obj
) == nvalue(obj
))
124 sprintf (s
, "%d", (int) nvalue(obj
));
126 sprintf (s
, "%g", nvalue(obj
));
127 svalue(obj
) = lua_createstring(lua_strdup(s
));
128 if (svalue(obj
) == NULL
)
136 ** Execute the given opcode. Return 0 in success or 1 on error.
138 int lua_execute (Byte
*pc
)
142 switch ((OpCode
)*pc
++)
146 case PUSHNIL
: tag(top
++) = T_NIL
; break;
148 case PUSH0
: tag(top
) = T_NUMBER
; nvalue(top
++) = 0; break;
149 case PUSH1
: tag(top
) = T_NUMBER
; nvalue(top
++) = 1; break;
150 case PUSH2
: tag(top
) = T_NUMBER
; nvalue(top
++) = 2; break;
152 case PUSHBYTE
: tag(top
) = T_NUMBER
; nvalue(top
++) = *pc
++; break;
155 tag(top
) = T_NUMBER
; nvalue(top
++) = *((Word
*)(pc
)); pc
+= sizeof(Word
);
159 tag(top
) = T_NUMBER
; nvalue(top
++) = *((float *)(pc
)); pc
+= sizeof(float);
163 int w
= *((Word
*)(pc
));
165 tag(top
) = T_STRING
; svalue(top
++) = lua_constant
[w
];
169 case PUSHLOCAL0
: *top
++ = *(base
+ 0); break;
170 case PUSHLOCAL1
: *top
++ = *(base
+ 1); break;
171 case PUSHLOCAL2
: *top
++ = *(base
+ 2); break;
172 case PUSHLOCAL3
: *top
++ = *(base
+ 3); break;
173 case PUSHLOCAL4
: *top
++ = *(base
+ 4); break;
174 case PUSHLOCAL5
: *top
++ = *(base
+ 5); break;
175 case PUSHLOCAL6
: *top
++ = *(base
+ 6); break;
176 case PUSHLOCAL7
: *top
++ = *(base
+ 7); break;
177 case PUSHLOCAL8
: *top
++ = *(base
+ 8); break;
178 case PUSHLOCAL9
: *top
++ = *(base
+ 9); break;
180 case PUSHLOCAL
: *top
++ = *(base
+ (*pc
++)); break;
183 *top
++ = s_object(*((Word
*)(pc
))); pc
+= sizeof(Word
);
188 if (tag(top
-1) != T_ARRAY
)
190 lua_reportbug ("indexed expression not a table");
194 Object
*h
= lua_hashdefine (avalue(top
-1), top
);
195 if (h
== NULL
) return 1;
200 case PUSHMARK
: tag(top
++) = T_MARK
; break;
202 case PUSHOBJECT
: *top
= *(top
-3); top
++; break;
204 case STORELOCAL0
: *(base
+ 0) = *(--top
); break;
205 case STORELOCAL1
: *(base
+ 1) = *(--top
); break;
206 case STORELOCAL2
: *(base
+ 2) = *(--top
); break;
207 case STORELOCAL3
: *(base
+ 3) = *(--top
); break;
208 case STORELOCAL4
: *(base
+ 4) = *(--top
); break;
209 case STORELOCAL5
: *(base
+ 5) = *(--top
); break;
210 case STORELOCAL6
: *(base
+ 6) = *(--top
); break;
211 case STORELOCAL7
: *(base
+ 7) = *(--top
); break;
212 case STORELOCAL8
: *(base
+ 8) = *(--top
); break;
213 case STORELOCAL9
: *(base
+ 9) = *(--top
); break;
215 case STORELOCAL
: *(base
+ (*pc
++)) = *(--top
); break;
218 s_object(*((Word
*)(pc
))) = *(--top
); pc
+= sizeof(Word
);
222 if (tag(top
-3) != T_ARRAY
)
224 lua_reportbug ("indexed expression not a table");
228 Object
*h
= lua_hashdefine (avalue(top
-3), top
-2);
229 if (h
== NULL
) return 1;
238 if (tag(top
-3-n
) != T_ARRAY
)
240 lua_reportbug ("indexed expression not a table");
244 Object
*h
= lua_hashdefine (avalue(top
-3-n
), top
-2-n
);
245 if (h
== NULL
) return 1;
253 if (tag(top
-3) != T_ARRAY
)
255 lua_error ("internal error - table expected");
258 *(lua_hashdefine (avalue(top
-3), top
-2)) = *(top
-1);
264 Object
*newtop
= base
+ *(pc
++);
267 while (top
< newtop
) tag(top
++) = T_NIL
;
274 if (tag(top
-1) == T_NIL
)
278 if (tonumber(top
-1)) return 1;
279 if (nvalue(top
-1) <= 0) nvalue(top
-1) = 101;
281 avalue(top
-1) = lua_createarray(lua_hashcreate(nvalue(top
-1)));
282 if (avalue(top
-1) == NULL
)
284 tag(top
-1) = T_ARRAY
;
292 if (tag(l
) != tag(r
))
298 case T_NIL
: tag(top
-1) = T_NUMBER
; break;
299 case T_NUMBER
: tag(top
-1) = (nvalue(l
) == nvalue(r
)) ? T_NUMBER
: T_NIL
; break;
300 case T_ARRAY
: tag(top
-1) = (avalue(l
) == avalue(r
)) ? T_NUMBER
: T_NIL
; break;
301 case T_FUNCTION
: tag(top
-1) = (bvalue(l
) == bvalue(r
)) ? T_NUMBER
: T_NIL
; break;
302 case T_CFUNCTION
: tag(top
-1) = (fvalue(l
) == fvalue(r
)) ? T_NUMBER
: T_NIL
; break;
303 case T_USERDATA
: tag(top
-1) = (uvalue(l
) == uvalue(r
)) ? T_NUMBER
: T_NIL
; break;
304 case T_STRING
: tag(top
-1) = (strcmp (svalue(l
), svalue(r
)) == 0) ? T_NUMBER
: T_NIL
; break;
305 case T_MARK
: return 1;
317 if (tag(l
) == T_NUMBER
&& tag(r
) == T_NUMBER
)
318 tag(top
-1) = (nvalue(l
) < nvalue(r
)) ? T_NUMBER
: T_NIL
;
321 if (tostring(l
) || tostring(r
))
323 tag(top
-1) = (strcmp (svalue(l
), svalue(r
)) < 0) ? T_NUMBER
: T_NIL
;
334 if (tag(l
) == T_NUMBER
&& tag(r
) == T_NUMBER
)
335 tag(top
-1) = (nvalue(l
) <= nvalue(r
)) ? T_NUMBER
: T_NIL
;
338 if (tostring(l
) || tostring(r
))
340 tag(top
-1) = (strcmp (svalue(l
), svalue(r
)) <= 0) ? T_NUMBER
: T_NIL
;
350 if (tonumber(r
) || tonumber(l
))
352 nvalue(l
) += nvalue(r
);
361 if (tonumber(r
) || tonumber(l
))
363 nvalue(l
) -= nvalue(r
);
372 if (tonumber(r
) || tonumber(l
))
374 nvalue(l
) *= nvalue(r
);
383 if (tonumber(r
) || tonumber(l
))
385 nvalue(l
) /= nvalue(r
);
394 if (tostring(r
) || tostring(l
))
396 svalue(l
) = lua_createstring (lua_strconc(svalue(l
),svalue(r
)));
397 if (svalue(l
) == NULL
)
406 nvalue(top
-1) = - nvalue(top
-1);
410 tag(top
-1) = tag(top
-1) == T_NIL
? T_NUMBER
: T_NIL
;
415 int n
= *((Word
*)(pc
));
417 if (tag(top
-1) != T_NIL
) pc
+= n
;
423 int n
= *((Word
*)(pc
));
425 if (tag(top
-1) == T_NIL
) pc
+= n
;
429 case JMP
: pc
+= *((Word
*)(pc
)) + sizeof(Word
); break;
431 case UPJMP
: pc
-= *((Word
*)(pc
)) - sizeof(Word
); break;
435 int n
= *((Word
*)(pc
));
438 if (tag(top
) == T_NIL
) pc
+= n
;
444 int n
= *((Word
*)(pc
));
447 if (tag(top
) == T_NIL
) pc
-= n
;
451 case POP
: --top
; break;
457 while (tag(b
) != T_MARK
) b
--;
458 if (tag(b
-1) == T_FUNCTION
)
460 lua_debugline
= 0; /* always reset debug flag */
462 bvalue(b
-1) = pc
; /* store return code */
463 nvalue(b
) = (base
-stack
); /* store base value */
466 if (MAXSTACK
-(base
-stack
) < STACKGAP
)
468 lua_error ("stack overflow");
472 else if (tag(b
-1) == T_CFUNCTION
)
475 lua_debugline
= 0; /* always reset debug flag */
476 nvalue(b
) = (base
-stack
); /* store base value */
478 nparam
= top
-base
; /* number of parameters */
479 (fvalue(b
-1))(); /* call C function */
481 /* shift returned values */
484 int nretval
= top
- base
- nparam
;
486 base
= stack
+ (int) nvalue(base
-1);
487 for (i
=0; i
<nretval
; i
++)
489 *top
= *(top
+nparam
+2);
496 lua_reportbug ("call expression not a function");
506 int nretval
= top
- base
- shift
;
509 base
= stack
+ (int) nvalue(base
-1);
510 for (i
=0; i
<nretval
; i
++)
512 *top
= *(top
+shift
+2);
519 return 0; /* success */
524 file
= *((Word
*)(pc
));
526 func
= *((Word
*)(pc
));
528 if (lua_pushfunction (file
, func
))
534 lua_debugline
= *((Word
*)(pc
));
543 lua_error ("internal error - opcode didn't match");
551 ** Mark all strings and arrays used by any object stored at stack.
553 void lua_markstack (void)
556 for (o
= top
-1; o
>= stack
; o
--)
561 ** Open file, generate opcode and execute global statement. Return 0 on
562 ** success or 1 on error.
564 int lua_dofile (char *filename
)
566 if (lua_openfile (filename
)) return 1;
567 if (lua_parse ()) { lua_closefile (); return 1; }
573 ** Generate opcode stored on string and execute global statement. Return 0 on
574 ** success or 1 on error.
576 int lua_dostring (char *string
)
578 if (lua_openstring (string
)) return 1;
579 if (lua_parse ()) return 1;
584 ** Execute the given function. Return 0 on success or 1 on error.
586 int lua_call (char *functionname
, int nparam
)
588 static Byte startcode
[] = {CALLFUNC
, HALT
};
590 Object func
= s_object(lua_findsymbol(functionname
));
591 if (tag(&func
) != T_FUNCTION
) return 1;
592 for (i
=1; i
<=nparam
; i
++)
593 *(top
-i
+2) = *(top
-i
);
595 tag(top
-nparam
-1) = T_MARK
;
596 *(top
-nparam
-2) = func
;
597 return (lua_execute (startcode
));
601 ** Get a parameter, returning the object handle or NULL on error.
602 ** 'number' must be 1 to get the first parameter.
604 Object
*lua_getparam (int number
)
606 if (number
<= 0 || number
> top
-base
) return NULL
;
607 return (base
+number
-1);
611 ** Given an object handle, return its number value. On error, return 0.0.
613 real
lua_getnumber (Object
*object
)
615 if (tonumber (object
)) return 0.0;
616 else return (nvalue(object
));
620 ** Given an object handle, return its string pointer. On error, return NULL.
622 char *lua_getstring (Object
*object
)
624 if (tostring (object
)) return NULL
;
625 else return (svalue(object
));
629 ** Given an object handle, return a copy of its string. On error, return NULL.
631 char *lua_copystring (Object
*object
)
633 if (tostring (object
)) return NULL
;
634 else return (strdup(svalue(object
)));
638 ** Given an object handle, return its cfuntion pointer. On error, return NULL.
640 lua_CFunction
lua_getcfunction (Object
*object
)
642 if (tag(object
) != T_CFUNCTION
) return NULL
;
643 else return (fvalue(object
));
647 ** Given an object handle, return its user data. On error, return NULL.
649 void *lua_getuserdata (Object
*object
)
651 if (tag(object
) != T_USERDATA
) return NULL
;
652 else return (uvalue(object
));
656 ** Given an object handle and a field name, return its field object.
657 ** On error, return NULL.
659 Object
*lua_getfield (Object
*object
, char *field
)
661 if (tag(object
) != T_ARRAY
)
666 tag(&ref
) = T_STRING
;
667 svalue(&ref
) = lua_createstring(lua_strdup(field
));
668 return (lua_hashdefine(avalue(object
), &ref
));
673 ** Given an object handle and an index, return its indexed object.
674 ** On error, return NULL.
676 Object
*lua_getindexed (Object
*object
, float index
)
678 if (tag(object
) != T_ARRAY
)
683 tag(&ref
) = T_NUMBER
;
684 nvalue(&ref
) = index
;
685 return (lua_hashdefine(avalue(object
), &ref
));
690 ** Get a global object. Return the object handle or NULL on error.
692 Object
*lua_getglobal (char *name
)
694 int n
= lua_findsymbol(name
);
695 if (n
< 0) return NULL
;
700 ** Pop and return an object
702 Object
*lua_pop (void)
704 if (top
<= base
) return NULL
;
712 int lua_pushnil (void)
714 if ((top
-stack
) >= MAXSTACK
-1)
716 lua_error ("stack overflow");
724 ** Push an object (tag=number) to stack. Return 0 on success or 1 on error.
726 int lua_pushnumber (real n
)
728 if ((top
-stack
) >= MAXSTACK
-1)
730 lua_error ("stack overflow");
733 tag(top
) = T_NUMBER
; nvalue(top
++) = n
;
738 ** Push an object (tag=string) to stack. Return 0 on success or 1 on error.
740 int lua_pushstring (char *s
)
742 if ((top
-stack
) >= MAXSTACK
-1)
744 lua_error ("stack overflow");
748 svalue(top
++) = lua_createstring(lua_strdup(s
));
753 ** Push an object (tag=cfunction) to stack. Return 0 on success or 1 on error.
755 int lua_pushcfunction (lua_CFunction fn
)
757 if ((top
-stack
) >= MAXSTACK
-1)
759 lua_error ("stack overflow");
762 tag(top
) = T_CFUNCTION
; fvalue(top
++) = fn
;
767 ** Push an object (tag=userdata) to stack. Return 0 on success or 1 on error.
769 int lua_pushuserdata (void *u
)
771 if ((top
-stack
) >= MAXSTACK
-1)
773 lua_error ("stack overflow");
776 tag(top
) = T_USERDATA
; uvalue(top
++) = u
;
781 ** Push an object to stack.
783 int lua_pushobject (Object
*o
)
785 if ((top
-stack
) >= MAXSTACK
-1)
787 lua_error ("stack overflow");
795 ** Store top of the stack at a global variable array field.
796 ** Return 1 on error, 0 on success.
798 int lua_storeglobal (char *name
)
800 int n
= lua_findsymbol (name
);
802 if (tag(top
-1) == T_MARK
) return 1;
803 s_object(n
) = *(--top
);
808 ** Store top of the stack at an array field. Return 1 on error, 0 on success.
810 int lua_storefield (lua_Object object
, char *field
)
812 if (tag(object
) != T_ARRAY
)
817 tag(&ref
) = T_STRING
;
818 svalue(&ref
) = lua_createstring(lua_strdup(field
));
819 h
= lua_hashdefine(avalue(object
), &ref
);
820 if (h
== NULL
) return 1;
821 if (tag(top
-1) == T_MARK
) return 1;
829 ** Store top of the stack at an array index. Return 1 on error, 0 on success.
831 int lua_storeindexed (lua_Object object
, float index
)
833 if (tag(object
) != T_ARRAY
)
838 tag(&ref
) = T_NUMBER
;
839 nvalue(&ref
) = index
;
840 h
= lua_hashdefine(avalue(object
), &ref
);
841 if (h
== NULL
) return 1;
842 if (tag(top
-1) == T_MARK
) return 1;
850 ** Given an object handle, return if it is nil.
852 int lua_isnil (Object
*object
)
854 return (object
!= NULL
&& tag(object
) == T_NIL
);
858 ** Given an object handle, return if it is a number one.
860 int lua_isnumber (Object
*object
)
862 return (object
!= NULL
&& tag(object
) == T_NUMBER
);
866 ** Given an object handle, return if it is a string one.
868 int lua_isstring (Object
*object
)
870 return (object
!= NULL
&& tag(object
) == T_STRING
);
874 ** Given an object handle, return if it is an array one.
876 int lua_istable (Object
*object
)
878 return (object
!= NULL
&& tag(object
) == T_ARRAY
);
882 ** Given an object handle, return if it is a cfunction one.
884 int lua_iscfunction (Object
*object
)
886 return (object
!= NULL
&& tag(object
) == T_CFUNCTION
);
890 ** Given an object handle, return if it is an user data one.
892 int lua_isuserdata (Object
*object
)
894 return (object
!= NULL
&& tag(object
) == T_USERDATA
);
898 ** Internal function: return an object type.
902 Object
*o
= lua_getparam(1);
903 lua_pushstring (lua_constant
[tag(o
)]);
907 ** Internal function: convert an object to a number
909 void lua_obj2number (void)
911 Object
*o
= lua_getparam(1);
912 lua_pushobject (lua_convtonumber(o
));
916 ** Internal function: print object values
918 void lua_print (void)
922 while ((obj
=lua_getparam (i
++)) != NULL
)
924 if (lua_isnumber(obj
)) printf("%g\n",lua_getnumber (obj
));
925 else if (lua_isstring(obj
)) printf("%s\n",lua_getstring (obj
));
926 else if (lua_iscfunction(obj
)) printf("cfunction: %p\n",lua_getcfunction (obj
));
927 else if (lua_isuserdata(obj
)) printf("userdata: %p\n",lua_getuserdata (obj
));
928 else if (lua_istable(obj
)) printf("table: %p\n",obj
);
929 else if (lua_isnil(obj
)) printf("nil\n");
930 else printf("invalid value to print\n");