static int db_exec(lua_State *T) { struct db *db; const char *sql; size_t len; unsigned int bind; luaL_checktype(T, 1, LUA_TUSERDATA); sql = luaL_checklstring(T, 2, &len); bind = lua_gettop(T) > 2; if (bind) { luaL_checktype(T, 3, LUA_TTABLE); lua_settop(T, 3); lua_replace(T, 2); } db = db_unbox(T, 1); if (db == NULL) return db_closed(T); if (db->T != NULL) return db_busy(T); db->T = T; db->req.prep.sql = sql; db->req.prep.len = len+1; lem_async_do(&db->a, db_prepare_work, db_exec_prepare_reap); return lua_yield(T, bind ? 2 : 1); }
static int stmt_column_names(lua_State *T) { struct stmt *stmt; int columns; int i; luaL_checktype(T, 1, LUA_TUSERDATA); stmt = lua_touserdata(T, 1); if (stmt->handle == NULL) return stmt_finalized(T); if (stmt->db->T != NULL) return db_busy(T); columns = sqlite3_column_count(stmt->handle); lua_createtable(T, columns, 0); for (i = 0; i < columns;) { const char *name = sqlite3_column_name(stmt->handle, i++); if (name == NULL) return luaL_error(T, "out of memory"); lua_pushstring(T, name); lua_rawseti(T, -2, i); } return 1; }
static int db_prepare(lua_State *T) { struct db *db; const char *sql; size_t len; luaL_checktype(T, 1, LUA_TUSERDATA); sql = luaL_checklstring(T, 2, &len); db = db_unbox(T, 1); if (db == NULL) return db_closed(T); if (db->T != NULL) return db_busy(T); db->T = T; db->refs++; db->req.prep.sql = sql; db->req.prep.len = len+1; lem_async_do(&db->a, db_prepare_work, db_prepare_reap); lua_settop(T, 2); lua_pushvalue(T, lua_upvalueindex(1)); return lua_yield(T, 3); }
static int stmt_finalize(lua_State *T) { struct stmt *stmt; struct db *db; int ret; luaL_checktype(T, 1, LUA_TUSERDATA); stmt = lua_touserdata(T, 1); if (stmt->handle == NULL) return stmt_finalized(T); db = stmt->db; if (db->T != NULL) return db_busy(T); if (sqlite3_finalize(stmt->handle) == SQLITE_OK) { lua_pushboolean(T, 1); ret = 1; } else { lua_pushnil(T); lua_pushstring(T, sqlite3_errmsg(db->handle)); ret = 2; } stmt->handle = NULL; db_unref(db); return ret; }
static int db_autocommit(lua_State *T) { struct db *db; luaL_checktype(T, 1, LUA_TUSERDATA); db = db_unbox(T, 1); if (db == NULL) return db_closed(T); if (db->T != NULL) return db_busy(T); lua_pushboolean(T, sqlite3_get_autocommit(db->handle)); return 1; }
static int db_changes(lua_State *T) { struct db *db; luaL_checktype(T, 1, LUA_TUSERDATA); db = db_unbox(T, 1); if (db == NULL) return db_closed(T); if (db->T != NULL) return db_busy(T); lua_pushinteger(T, sqlite3_changes(db->handle)); return 1; }
static int db_last_insert_rowid(lua_State *T) { struct db *db; luaL_checktype(T, 1, LUA_TUSERDATA); db = db_unbox(T, 1); if (db == NULL) return db_closed(T); if (db->T != NULL) return db_busy(T); lua_pushnumber(T, sqlite3_last_insert_rowid(db->handle)); return 1; }
static int db_close(lua_State *T) { struct box *box; struct db *db; luaL_checktype(T, 1, LUA_TUSERDATA); box = lua_touserdata(T, 1); db = box->db; if (db == NULL) return db_closed(T); if (db->T != NULL) return db_busy(T); db_unref(db); box->db = NULL; lua_pushboolean(T, 1); return 1; }
static int stmt_bind(lua_State *T) { struct stmt *stmt; luaL_checktype(T, 1, LUA_TUSERDATA); stmt = lua_touserdata(T, 1); if (stmt->handle == NULL) return stmt_finalized(T); if (stmt->db->T != NULL) return db_busy(T); if (lua_type(T, 2) == LUA_TTABLE) { if (bindtable(T, stmt->handle)) return lua_error(T); return 0; } return bindargs(T, stmt->handle); }
static int stmt_step(lua_State *T) { struct stmt *stmt; struct db *db; luaL_checktype(T, 1, LUA_TUSERDATA); stmt = lua_touserdata(T, 1); if (stmt->handle == NULL) return stmt_finalized(T); db = stmt->db; if (db->T != NULL) return db_busy(T); db->T = T; db->req.prep.stmt = stmt->handle; lem_async_do(&db->a, db_step_work, stmt_step_reap); lua_settop(T, 1); return lua_yield(T, 1); }
static int stmt_reset(lua_State *T) { struct stmt *stmt; int ret; luaL_checktype(T, 1, LUA_TUSERDATA); stmt = lua_touserdata(T, 1); if (stmt->handle == NULL) return stmt_finalized(T); if (stmt->db->T != NULL) return db_busy(T); ret = sqlite3_reset(stmt->handle); (void)sqlite3_clear_bindings(stmt->handle); if (ret != SQLITE_OK) { lua_pushnil(T); lua_pushstring(T, sqlite3_errmsg(sqlite3_db_handle(stmt->handle))); return 2; } lua_pushboolean(T, 1); return 1; }