diff src/except.c @ 0:4b915342e2a8

LuaSocket 2.0.2 + CMake build description.
author Eric Wing <ewing . public |-at-| gmail . com>
date Tue, 26 Aug 2008 18:40:01 -0700
parents
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/except.c	Tue Aug 26 18:40:01 2008 -0700
@@ -0,0 +1,99 @@
+/*=========================================================================*\
+* Simple exception support
+* LuaSocket toolkit
+*
+* RCS ID: $Id: except.c,v 1.8 2005/09/29 06:11:41 diego Exp $
+\*=========================================================================*/
+#include <stdio.h>
+
+#include "lua.h"
+#include "lauxlib.h"
+
+#include "except.h"
+
+/*=========================================================================*\
+* Internal function prototypes.
+\*=========================================================================*/
+static int global_protect(lua_State *L);
+static int global_newtry(lua_State *L);
+static int protected_(lua_State *L);
+static int finalize(lua_State *L);
+static int do_nothing(lua_State *L);
+
+/* except functions */
+static luaL_reg func[] = {
+    {"newtry",    global_newtry},
+    {"protect",   global_protect},
+    {NULL,        NULL}
+};
+
+/*-------------------------------------------------------------------------*\
+* Try factory
+\*-------------------------------------------------------------------------*/
+static void wrap(lua_State *L) {
+    lua_newtable(L);
+    lua_pushnumber(L, 1);
+    lua_pushvalue(L, -3);
+    lua_settable(L, -3);
+    lua_insert(L, -2);
+    lua_pop(L, 1);
+}
+
+static int finalize(lua_State *L) {
+    if (!lua_toboolean(L, 1)) {
+        lua_pushvalue(L, lua_upvalueindex(1));
+        lua_pcall(L, 0, 0, 0);
+        lua_settop(L, 2);
+        wrap(L);
+        lua_error(L);
+        return 0;
+    } else return lua_gettop(L);
+}
+
+static int do_nothing(lua_State *L) { 
+    (void) L;
+    return 0; 
+}
+
+static int global_newtry(lua_State *L) {
+    lua_settop(L, 1);
+    if (lua_isnil(L, 1)) lua_pushcfunction(L, do_nothing);
+    lua_pushcclosure(L, finalize, 1);
+    return 1;
+}
+
+/*-------------------------------------------------------------------------*\
+* Protect factory
+\*-------------------------------------------------------------------------*/
+static int unwrap(lua_State *L) {
+    if (lua_istable(L, -1)) {
+        lua_pushnumber(L, 1);
+        lua_gettable(L, -2);
+        lua_pushnil(L);
+        lua_insert(L, -2);
+        return 1;
+    } else return 0;
+}
+
+static int protected_(lua_State *L) {
+    lua_pushvalue(L, lua_upvalueindex(1));
+    lua_insert(L, 1);
+    if (lua_pcall(L, lua_gettop(L) - 1, LUA_MULTRET, 0) != 0) {
+        if (unwrap(L)) return 2;
+        else lua_error(L);
+        return 0;
+    } else return lua_gettop(L);
+}
+
+static int global_protect(lua_State *L) {
+    lua_pushcclosure(L, protected_, 1);
+    return 1;
+}
+
+/*-------------------------------------------------------------------------*\
+* Init module
+\*-------------------------------------------------------------------------*/
+int except_open(lua_State *L) {
+    luaL_openlib(L, NULL, func, 0);
+    return 0;
+}