aboutsummaryrefslogtreecommitdiff
path: root/liolib.c
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2000-09-05 16:33:32 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2000-09-05 16:33:32 -0300
commit6e80c1cde193b767d63d2cc30ebd71d65512e061 (patch)
treecb599bdc956c0dc9b3d469bb01de47185db3e4e2 /liolib.c
parentf67f324377aff66d78479eaaffbb94a6b092ae45 (diff)
downloadlua-6e80c1cde193b767d63d2cc30ebd71d65512e061.tar.gz
lua-6e80c1cde193b767d63d2cc30ebd71d65512e061.tar.bz2
lua-6e80c1cde193b767d63d2cc30ebd71d65512e061.zip
new version for API
Diffstat (limited to 'liolib.c')
-rw-r--r--liolib.c75
1 files changed, 47 insertions, 28 deletions
diff --git a/liolib.c b/liolib.c
index 46d619c1..885db9bd 100644
--- a/liolib.c
+++ b/liolib.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: liolib.c,v 1.75 2000/08/31 13:30:10 roberto Exp roberto $ 2** $Id: liolib.c,v 1.76 2000/08/31 20:23:40 roberto Exp roberto $
3** Standard I/O (and system) library 3** Standard I/O (and system) library
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -107,7 +107,7 @@ static FILE *getfilebyref (lua_State *L, IOCtrl *ctrl, int inout) {
107 FILE *f; 107 FILE *f;
108 lua_getglobals(L); 108 lua_getglobals(L);
109 lua_getref(L, ctrl->ref[inout]); 109 lua_getref(L, ctrl->ref[inout]);
110 lua_rawget(L); 110 lua_rawget(L, -2);
111 f = gethandle(L, ctrl, -1); 111 f = gethandle(L, ctrl, -1);
112 if (f == NULL) 112 if (f == NULL)
113 luaL_verror(L, "global variable `%.10s' is not a file handle", 113 luaL_verror(L, "global variable `%.10s' is not a file handle",
@@ -564,58 +564,77 @@ static int io_debug (lua_State *L) {
564} 564}
565 565
566 566
567 567#define LEVELS1 12 /* size of the first part of the stack */
568#define MESSAGESIZE 150 568#define LEVELS2 10 /* size of the second part of the stack */
569#define MAXMESSAGE (MESSAGESIZE*10)
570
571 569
572static int errorfb (lua_State *L) { 570static int errorfb (lua_State *L) {
573 char buff[MAXMESSAGE];
574 int level = 1; /* skip level 0 (it's this function) */ 571 int level = 1; /* skip level 0 (it's this function) */
572 int firstpart = 1; /* still before eventual `...' */
575 lua_Debug ar; 573 lua_Debug ar;
576 sprintf(buff, "error: %.200s\n", lua_tostring(L, 1)); 574 lua_settop(L, 1);
575 luaL_checktype(L, 1, "string");
576 lua_pushstring(L, "error: ");
577 lua_insert(L, 1);
578 lua_pushstring(L, "\nstack traceback:\n");
579 lua_concat(L, 3);
577 while (lua_getstack(L, level++, &ar)) { 580 while (lua_getstack(L, level++, &ar)) {
581 char buff[120]; /* enough to fit following `sprintf's */
578 char buffchunk[60]; 582 char buffchunk[60];
583 int toconcat = 1; /* number of strings in the stack to concat */
584 if (level > LEVELS1 && firstpart) {
585 /* no more than `LEVELS2' more levels? */
586 if (!lua_getstack(L, level+LEVELS2, &ar))
587 level--; /* keep going */
588 else {
589 lua_pushstring(L, " ...\n"); /* too many levels */
590 lua_concat(L, 2);
591 while (lua_getstack(L, level+LEVELS2, &ar)) /* get last levels */
592 level++;
593 }
594 firstpart = 0;
595 continue;
596 }
597 sprintf(buff, "%4d: ", level-1);
598 lua_pushstring(L, buff); toconcat++;
579 lua_getinfo(L, "Snl", &ar); 599 lua_getinfo(L, "Snl", &ar);
580 luaL_chunkid(buffchunk, ar.source, sizeof(buffchunk)); 600 luaL_chunkid(buffchunk, ar.source, sizeof(buffchunk));
581 if (level == 2) strcat(buff, "stack traceback:\n");
582 strcat(buff, " ");
583 if (strlen(buff) > MAXMESSAGE-MESSAGESIZE) {
584 strcat(buff, "...\n");
585 break; /* buffer is full */
586 }
587 switch (*ar.namewhat) { 601 switch (*ar.namewhat) {
588 case 'g': case 'l': /* global, local */ 602 case 'g': case 'l': /* global, local */
589 sprintf(buff+strlen(buff), "function `%.50s'", ar.name); 603 sprintf(buff, "function `%.50s'", ar.name);
590 break; 604 break;
591 case 'f': /* field */ 605 case 'f': /* field */
592 sprintf(buff+strlen(buff), "method `%.50s'", ar.name); 606 sprintf(buff, "method `%.50s'", ar.name);
593 break; 607 break;
594 case 't': /* tag method */ 608 case 't': /* tag method */
595 sprintf(buff+strlen(buff), "`%.50s' tag method", ar.name); 609 sprintf(buff, "`%.50s' tag method", ar.name);
596 break; 610 break;
597 default: { 611 default: {
598 if (*ar.what == 'm') /* main? */ 612 if (*ar.what == 'm') /* main? */
599 sprintf(buff+strlen(buff), "main of %.70s", buffchunk); 613 sprintf(buff, "main of %.70s", buffchunk);
600 else if (*ar.what == 'C') /* C function? */ 614 else if (*ar.what == 'C') /* C function? */
601 sprintf(buff+strlen(buff), "%.70s", buffchunk); 615 sprintf(buff, "%.70s", buffchunk);
602 else 616 else
603 sprintf(buff+strlen(buff), "function <%d:%.70s>", 617 sprintf(buff, "function <%d:%.70s>", ar.linedefined, buffchunk);
604 ar.linedefined, buffchunk);
605 ar.source = NULL; 618 ar.source = NULL;
606 } 619 }
607 } 620 }
608 if (ar.currentline > 0) 621 lua_pushstring(L, buff); toconcat++;
609 sprintf(buff+strlen(buff), " at line %d", ar.currentline); 622 if (ar.currentline > 0) {
610 if (ar.source) 623 sprintf(buff, " at line %d", ar.currentline);
611 sprintf(buff+strlen(buff), " [%.70s]", buffchunk); 624 lua_pushstring(L, buff); toconcat++;
612 strcat(buff, "\n"); 625 }
626 if (ar.source) {
627 sprintf(buff, " [%.70s]", buffchunk);
628 lua_pushstring(L, buff); toconcat++;
629 }
630 lua_pushstring(L, "\n"); toconcat++;
631 lua_concat(L, toconcat);
613 } 632 }
614 lua_getglobals(L); 633 lua_getglobals(L);
615 lua_pushstring(L, LUA_ALERT); 634 lua_pushstring(L, LUA_ALERT);
616 lua_rawget(L); 635 lua_rawget(L, -2);
617 if (lua_isfunction(L, -1)) { /* avoid loop if _ALERT is not defined */ 636 if (lua_isfunction(L, -1)) { /* avoid loop if _ALERT is not defined */
618 lua_pushstring(L, buff); 637 lua_pushvalue(L, -3); /* error message */
619 lua_call(L, 1, 0); 638 lua_call(L, 1, 0);
620 } 639 }
621 return 0; 640 return 0;