aboutsummaryrefslogtreecommitdiff
path: root/lauxlib.c
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2024-06-12 15:50:31 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2024-06-12 15:50:31 -0300
commitbb7bb5944c9b3c868c6ab9cbe7d11b611251066b (patch)
treefe7f5e8def79d5a3c253a2f39c4557fc20d204e6 /lauxlib.c
parent94b503d95ef00f1e38b58b024ef45bf8973a8746 (diff)
downloadlua-bb7bb5944c9b3c868c6ab9cbe7d11b611251066b.tar.gz
lua-bb7bb5944c9b3c868c6ab9cbe7d11b611251066b.tar.bz2
lua-bb7bb5944c9b3c868c6ab9cbe7d11b611251066b.zip
More disciplined use of 'errno'
Set errno to zero before calling any function where we may use its errno, and check errno for zero before using it (as functions may not set it even in error). The code assumes that no function will put garbage on errno (although ISO C allows that): If any function during an operation set errno, and the operation result in an error, assume that errno has something to say.
Diffstat (limited to 'lauxlib.c')
-rw-r--r--lauxlib.c16
1 files changed, 12 insertions, 4 deletions
diff --git a/lauxlib.c b/lauxlib.c
index fec834d3..d742fd27 100644
--- a/lauxlib.c
+++ b/lauxlib.c
@@ -249,11 +249,13 @@ LUALIB_API int luaL_fileresult (lua_State *L, int stat, const char *fname) {
249 return 1; 249 return 1;
250 } 250 }
251 else { 251 else {
252 const char *msg;
252 luaL_pushfail(L); 253 luaL_pushfail(L);
254 msg = (en != 0) ? strerror(en) : "(no extra info)";
253 if (fname) 255 if (fname)
254 lua_pushfstring(L, "%s: %s", fname, strerror(en)); 256 lua_pushfstring(L, "%s: %s", fname, msg);
255 else 257 else
256 lua_pushstring(L, strerror(en)); 258 lua_pushstring(L, msg);
257 lua_pushinteger(L, en); 259 lua_pushinteger(L, en);
258 return 3; 260 return 3;
259 } 261 }
@@ -750,9 +752,12 @@ static const char *getF (lua_State *L, void *ud, size_t *size) {
750 752
751 753
752static int errfile (lua_State *L, const char *what, int fnameindex) { 754static int errfile (lua_State *L, const char *what, int fnameindex) {
753 const char *serr = strerror(errno); 755 int err = errno;
754 const char *filename = lua_tostring(L, fnameindex) + 1; 756 const char *filename = lua_tostring(L, fnameindex) + 1;
755 lua_pushfstring(L, "cannot %s %s: %s", what, filename, serr); 757 if (err != 0)
758 lua_pushfstring(L, "cannot %s %s: %s", what, filename, strerror(err));
759 else
760 lua_pushfstring(L, "cannot %s %s", what, filename);
756 lua_remove(L, fnameindex); 761 lua_remove(L, fnameindex);
757 return LUA_ERRFILE; 762 return LUA_ERRFILE;
758} 763}
@@ -805,6 +810,7 @@ LUALIB_API int luaL_loadfilex (lua_State *L, const char *filename,
805 } 810 }
806 else { 811 else {
807 lua_pushfstring(L, "@%s", filename); 812 lua_pushfstring(L, "@%s", filename);
813 errno = 0;
808 lf.f = fopen(filename, "r"); 814 lf.f = fopen(filename, "r");
809 if (lf.f == NULL) return errfile(L, "open", fnameindex); 815 if (lf.f == NULL) return errfile(L, "open", fnameindex);
810 } 816 }
@@ -814,6 +820,7 @@ LUALIB_API int luaL_loadfilex (lua_State *L, const char *filename,
814 if (c == LUA_SIGNATURE[0]) { /* binary file? */ 820 if (c == LUA_SIGNATURE[0]) { /* binary file? */
815 lf.n = 0; /* remove possible newline */ 821 lf.n = 0; /* remove possible newline */
816 if (filename) { /* "real" file? */ 822 if (filename) { /* "real" file? */
823 errno = 0;
817 lf.f = freopen(filename, "rb", lf.f); /* reopen in binary mode */ 824 lf.f = freopen(filename, "rb", lf.f); /* reopen in binary mode */
818 if (lf.f == NULL) return errfile(L, "reopen", fnameindex); 825 if (lf.f == NULL) return errfile(L, "reopen", fnameindex);
819 skipcomment(lf.f, &c); /* re-read initial portion */ 826 skipcomment(lf.f, &c); /* re-read initial portion */
@@ -823,6 +830,7 @@ LUALIB_API int luaL_loadfilex (lua_State *L, const char *filename,
823 lf.buff[lf.n++] = c; /* 'c' is the first character of the stream */ 830 lf.buff[lf.n++] = c; /* 'c' is the first character of the stream */
824 status = lua_load(L, getF, &lf, lua_tostring(L, -1), mode); 831 status = lua_load(L, getF, &lf, lua_tostring(L, -1), mode);
825 readstatus = ferror(lf.f); 832 readstatus = ferror(lf.f);
833 errno = 0; /* no useful error number until here */
826 if (filename) fclose(lf.f); /* close file (even in case of errors) */ 834 if (filename) fclose(lf.f); /* close file (even in case of errors) */
827 if (readstatus) { 835 if (readstatus) {
828 lua_settop(L, fnameindex); /* ignore results from 'lua_load' */ 836 lua_settop(L, fnameindex); /* ignore results from 'lua_load' */