/* * NOTE: The init callback should never be called multiple times, * let alone called from multiple threads. Therefore, locking * is unnecessary here. */ int init (void) { int rc = SLURM_SUCCESS; /* * Need to dlopen() liblua.so with RTLD_GLOBAL in order to * ensure symbols from liblua are available to libs opened * by any lua scripts. */ if (!dlopen("liblua.so", RTLD_NOW | RTLD_GLOBAL) && !dlopen("liblua-5.1.so", RTLD_NOW | RTLD_GLOBAL) && !dlopen("liblua5.1.so", RTLD_NOW | RTLD_GLOBAL) && !dlopen("liblua5.1.so.0", RTLD_NOW | RTLD_GLOBAL)) { return (error("Failed to open liblua.so: %s", dlerror())); } /* * Initilize lua */ L = luaL_newstate(); luaL_openlibs(L); if (luaL_loadfile(L, lua_script_path)) { return error("lua: %s: %s", lua_script_path, lua_tostring(L, -1)); } /* * Register SLURM functions in lua state: * logging and slurm structure read/write functions */ _register_lua_slurm_output_functions(); _register_lua_slurm_struct_functions(); /* * Run the user script: */ if (lua_pcall(L, 0, 1, 0) != 0) { return error("job_submit/lua: %s: %s", lua_script_path, lua_tostring (L, -1)); } /* * Get any return code from the lua script */ rc = (int) lua_tonumber(L, -1); lua_pop (L, 1); if (rc != SLURM_SUCCESS) return rc; /* * Check for required lua script functions: */ return (_check_lua_script_functions()); }
static int _load_script(void) { int rc = SLURM_SUCCESS; struct stat st; lua_State *L_orig = L; if (stat(lua_script_path, &st) != 0) { if (L_orig) { (void) error("Unable to stat %s, " "using old script: %s", lua_script_path, strerror(errno)); return SLURM_SUCCESS; } return error("Unable to stat %s: %s", lua_script_path, strerror(errno)); } if (st.st_mtime <= lua_script_last_loaded) { return SLURM_SUCCESS; } /* * Initilize lua */ L = luaL_newstate(); luaL_openlibs(L); if (luaL_loadfile(L, lua_script_path)) { if (L_orig) { (void) error("lua: %s: %s, using previous script", lua_script_path, lua_tostring(L, -1)); lua_close(L); L = L_orig; return SLURM_SUCCESS; } rc = error("lua: %s: %s", lua_script_path, lua_tostring(L, -1)); lua_pop(L, 1); return rc; } /* * Register SLURM functions in lua state: * logging and slurm structure read/write functions */ _register_lua_slurm_output_functions(); _register_lua_slurm_struct_functions(); /* * Run the user script: */ if (lua_pcall(L, 0, 1, 0) != 0) { if (L_orig) { (void) error("job_submit/lua: %s: %s, " "using previous script", lua_script_path, lua_tostring(L, -1)); lua_close(L); L = L_orig; return SLURM_SUCCESS; } rc = error("job_submit/lua: %s: %s", lua_script_path, lua_tostring(L, -1)); lua_pop(L, 1); return rc; } /* * Get any return code from the lua script */ rc = (int) lua_tonumber(L, -1); if (rc != SLURM_SUCCESS) { if (L_orig) { (void) error("job_submit/lua: %s: returned %d " "on load, using previous script", lua_script_path, rc); lua_close(L); L = L_orig; return SLURM_SUCCESS; } (void) error("job_submit/lua: %s: returned %d on load", lua_script_path, rc); lua_pop (L, 1); return rc; } /* * Check for required lua script functions: */ rc = _check_lua_script_functions(); if (rc != SLURM_SUCCESS) { if (L_orig) { (void) error("job_submit/lua: %s: " "required function(s) not present, " "using previous script", lua_script_path); lua_close(L); L = L_orig; return SLURM_SUCCESS; } return rc; } if (L_orig) lua_close(L_orig); lua_script_last_loaded = time(NULL); return SLURM_SUCCESS; }