Пример #1
0
	bool Install(lua_State *L, std::vector<fs::path> const& include_path) {
		// set the module load path to include_path
		lua_getglobal(L, "package");
		push_value(L, "path");

		push_value(L, "");
		for (auto const& path : include_path) {
			lua_pushfstring(L, "%s/?.lua;%s/?/init.lua;", path.string().c_str(), path.string().c_str());
			lua_concat(L, 2);
		}

#ifndef _WIN32
		// No point in checking any of the default locations on Windows since
		// there won't be anything there
		push_value(L, "path");
		lua_gettable(L, -4);
		lua_concat(L, 2);
#endif

		lua_settable(L, -3);

		// Replace the default lua module loader with our unicode compatible one
		lua_getfield(L, -1, "loaders");
		push_value(L, exception_wrapper<module_loader>);
		lua_rawseti(L, -2, 2);
		lua_pop(L, 2); // loaders, package

		luaL_loadstring(L, "return require('moonscript').loadstring");
		if (lua_pcall(L, 0, 1, 0)) {
			return false; // leave error message
		}
		lua_setfield(L, LUA_REGISTRYINDEX, "moonscript");

		return true;
	}
Пример #2
0
static int moon_line(lua_State *L, int lua_line, std::string const& file) {
	if (luaL_dostring(L, "return require 'moonscript.line_tables'")) {
		lua_pop(L, 1); // pop error message
		return lua_line;
	}

	push_value(L, file);
	lua_rawget(L, -2);

	if (!lua_istable(L, -1)) {
		lua_pop(L, 2);
		return lua_line;
	}

	lua_rawgeti(L, -1, lua_line);
	if (!lua_isnumber(L, -1)) {
		lua_pop(L, 3);
		return lua_line;
	}

	auto char_pos = static_cast<size_t>(lua_tonumber(L, -1));
	lua_pop(L, 3);

	// The moonscript line tables give us a character offset into the file,
	// so now we need to map that to a line number
	lua_getfield(L, LUA_REGISTRYINDEX, ("raw moonscript: " + file).c_str());
	if (!lua_isstring(L, -1)) {
		lua_pop(L, 1);
		return lua_line;
	}

	size_t moon_len;
	auto moon = lua_tolstring(L, -1, &moon_len);
	return std::count(moon, moon + std::min(moon_len, char_pos), '\n') + 1;
}
Пример #3
0
void lambda(su_state *s, prototype_t *prot, int narg) {
	unsigned i, tmp;
	value_t v;
	function_t *func = su_allocate(s, NULL, sizeof(function_t));

	func->narg = narg;
	func->prot = prot;
	func->num_const = prot->num_const;
	func->num_ups = prot->num_ups;
	func->constants = su_allocate(s, NULL, sizeof(value_t) * prot->num_const);
	func->upvalues = su_allocate(s, NULL, sizeof(value_t) * prot->num_ups);

	for (i = 0; i < func->num_const; i++)
		func->constants[i] = create_value(s, &prot->constants[i]);

	for (i = 0; i < func->num_ups; i++) {
		tmp = s->frame_top - prot->upvalues[i].lv;
		tmp = s->frames[tmp].stack_top + prot->upvalues[i].idx + 1;
		func->upvalues[i] = s->stack[tmp];
	}

	gc_insert_object(s, (gc_t*)func, SU_FUNCTION);
	v.type = SU_FUNCTION;
	v.obj.func = func;
	push_value(s, &v);
}
Пример #4
0
	call_ret_t call(state_t &state, const function_ref_t &func, const Args &... args)
	{
		if( !func.is_valid() )
			throw fatal_error_t(state, "lua function invalid()");

		int top_beg = ::lua_gettop(state);

		func.get();
		if( state != func.state() )
			throw std::runtime_error("state not equal to function state");

		std::int32_t arg_cnt = sizeof...( args );
		push_value(state, args...);

		int error_index = 0;
		int base = ::lua_gettop(state) - arg_cnt;

		std::string error_msg;
		error_handler(state, error_msg);
		
		lua_insert(state, base);
		error_index = base;
		int error = lua_pcall(state, arg_cnt, LUA_MULTRET, error_index);

		if(error_index != 0)
			lua_remove(state, error_index);

		if( error != 0 )
			throw fatal_error_t(state, error_msg, error);


		int top_last = ::lua_gettop(state);

		return call_ret_t(state, top_last - top_beg);
	}
Пример #5
0
	call_ret_t call(state_t &state, const char *function_name, Args&&... args )
	{
		assert(function_name && "function_name not be empty");
		
		int top_beg = ::lua_gettop(state);

		::lua_getglobal(state, function_name);
		std::int32_t arg_cnt = sizeof...(args);

		push_value(state, std::forward<Args>(args)...);

		int base = ::lua_gettop(state) - arg_cnt;

		std::string error_msg;
		error_handler(state, error_msg);

		lua_insert(state, base);
		int error_index = base;

		int error = lua_pcall(state, arg_cnt, LUA_MULTRET, error_index);
		if( error_index != 0 )
			lua_remove(state, error_index);

		if( error != 0 )
			throw fatal_error_t(state, error_msg, error);

		int top_last = ::lua_gettop(state);

		return call_ret_t(state, top_last - top_beg);
	}
Пример #6
0
static void
eval_inc_dec_expression(SIMCAR_Interpreter *inter,
                        SIMCAR_LocalEnvironment *env, Expression *expr)
{
    SIMCAR_Value   *operand;
    SIMCAR_Value   result;
    int         old_value;
    
    operand = get_lvalue(inter, env, expr->u.inc_dec.operand);
    if (operand->type != SIMCAR_INT_VALUE) {
        crb_runtime_error(expr->line_number, INC_DEC_OPERAND_TYPE_ERR,
                          MESSAGE_ARGUMENT_END);
    }
    old_value = operand->u.int_value;
    if (expr->type == INCREMENT_EXPRESSION) {
        operand->u.int_value++;
    } else {
        DBG_assert(expr->type == DECREMENT_EXPRESSION,
                   ("expr->type..%d\n", expr->type));
        operand->u.int_value--;
    }

    result.type = SIMCAR_INT_VALUE;
    result.u.int_value = old_value;
    push_value(inter, &result);
}
Пример #7
0
static value_t* call_function_lua(language_t*li, const char*name, value_t*args)
{
    lua_internal_t*lua = (lua_internal_t*)li->internal;
    lua_State*l = lua->state;

    lua_getfield(l, LUA_GLOBALSINDEX, name);

    if(!lua_isfunction(l, -1)) {
        language_error(li, "%s is not a function", name);
        return NULL;
    }

    int i;
    for(i=0;i<args->length;i++) {
        push_value(l, args->data[i]);
    }

    int error = lua_pcall(l, /*nargs*/args->length, /*nresults*/1, 0);
    if(error) {
        show_error(li, l);
        language_error(li, "Error calling function %s: %d\n", name, error);
        return NULL;
    }

    value_t*ret = lua_to_value(li, -1);
    lua_pop(l, 1);

    return ret;
}
Пример #8
0
static void push_value(lua_State*l, value_t*value)
{
    int i;
    switch(value->type) {
        case TYPE_VOID:
            lua_pushnil(l);
        break;
        case TYPE_FLOAT32:
            lua_pushnumber(l, value->f32);
        break;
        case TYPE_INT32:
            lua_pushinteger(l, value->i32);
        break;
        case TYPE_BOOLEAN:
            lua_pushboolean(l, value->b);
        break;
        case TYPE_STRING: {
            lua_pushstring(l, value->str);
        }
        break;
        case TYPE_ARRAY: {
            lua_newtable(l);
            for(i=0;i<value->length;i++) {
                lua_pushinteger(l, i);
                push_value(l, value->data[i]);
                lua_settable(l, -3);
            }
        }
        break;
        default: {
            lua_pushnil(l);
        }
    }
}
Пример #9
0
			void pushFromPacket(const hexabus::ValuePacket<T>& packet)
			{
				std::ostringstream oss;
				oss << std::fixed << std::setprecision(1) << float(packet.value());

				push_value(packet.eid(), oss.str());
			}
Пример #10
0
void su_vector(su_state *s, int num) {
	int i;
	value_t vec = vector_create_empty(s);
	for (i = 0; i < num; i++)
		vec = vector_push(s, vec.obj.vec, STK(-(num - i)));
	s->stack_top -= num;
	push_value(s, &vec);
}
Пример #11
0
void su_vector_push(su_state *s, int idx, int num) {
	int i;
	value_t vec = *STK(TOP(idx));
	for (i = 0; i < num; i++)
		vec = vector_push(s, vec.obj.vec, STK(-(num - i)));
	s->stack_top -= num;
	push_value(s, &vec);
}
Пример #12
0
void su_vector_pop(su_state *s, int idx, int num) {
	int i;
	int n = (int)STK(TOP(num))->obj.num;
	value_t vec = *STK(TOP(idx));
	for (i = 0; i < n; i++)
		vec = vector_pop(s, vec.obj.vec);
	push_value(s, &vec);
}
Пример #13
0
int su_getglobal(su_state *s, const char *name) {
	int size = strlen(name);
	value_t v = get_global(s, name, murmur(name, size, 0), size);
	if (v.type == SU_INV)
		return 0;
	push_value(s, &v);
	return 1;
}
Пример #14
0
static void
eval_int_expression(SIMCAR_Interpreter *inter, int int_value)
{
    SIMCAR_Value   v;

    v.type = SIMCAR_INT_VALUE;
    v.u.int_value = int_value;
    push_value(inter, &v);
}
Пример #15
0
static void define_constant_lua(struct _language*li, const char*name, value_t*value)
{
    lua_internal_t*lua = (lua_internal_t*)li->internal;
    lua_State*l = lua->state;

    push_value(l, value);
    lua_setglobal(l, name);

}
Пример #16
0
static void
eval_null_expression(SIMCAR_Interpreter *inter)
{
    SIMCAR_Value   v;

    v.type = SIMCAR_NULL_VALUE;

    push_value(inter, &v);
}
Пример #17
0
static void
eval_string_expression(SIMCAR_Interpreter *inter, char *string_value)
{
    SIMCAR_Value   v;

    v.type = SIMCAR_STRING_VALUE;
    v.u.object = crb_literal_to_crb_string(inter, string_value);
    push_value(inter, &v);
}
Пример #18
0
static void
eval_double_expression(SIMCAR_Interpreter *inter, double double_value)
{
    SIMCAR_Value   v;

    v.type = SIMCAR_DOUBLE_VALUE;
    v.u.double_value = double_value;
    push_value(inter, &v);
}
Пример #19
0
static void
eval_boolean_expression(SIMCAR_Interpreter *inter, SIMCAR_Boolean boolean_value)
{
    SIMCAR_Value   v;

    v.type = SIMCAR_BOOLEAN_VALUE;
    v.u.boolean_value = boolean_value;
    push_value(inter, &v);
}
Пример #20
0
void su_string_push(su_state *s) {
	value_t v;
	assert(s->string_builder);
	v.type = SU_STRING;
	s->string_builder->hash = murmur(s->string_builder->str, s->string_builder->size, 0);
	v.obj.gc_object = string_build_from_cache(s);
	push_value(s, &v);
	s->string_builder = NULL;
}
Пример #21
0
void *su_newdata(su_state *s, unsigned size, const su_data_class_t *vt) {
	value_t v;
	v.type = SU_NATIVEDATA;
	v.obj.data = (native_data_t*)su_allocate(s, NULL, sizeof(native_data_t) + size - 1);
	v.obj.data->vt = (su_data_class_t*)vt;
	gc_insert_object(s, v.obj.gc_object, SU_NATIVEDATA);
	push_value(s, &v);
	return (void*)v.obj.data->data;
}
Пример #22
0
static void
eval_index_expression(SIMCAR_Interpreter *inter,
                      SIMCAR_LocalEnvironment *env, Expression *expr)
{
    SIMCAR_Value *left;

    left = get_array_element_lvalue(inter, env, expr);

    push_value(inter, left);
}
Пример #23
0
/*
	-3: function decode
	-2: table key
	-1:	table id
 */
static void
decode_cb(void *ud, int type, const char * type_name, union pbc_value *v, int id, const char *key) {
	lua_State *L = (lua_State *)ud;
	if (key == NULL) {
		// undefined field
		return;
	}
	if (type & PBC_REPEATED) {
		push_value(L, type & ~PBC_REPEATED, type_name, v);
		new_array(L, id , key);	// func.decode table.key table.id value array
		int n = (int)lua_rawlen(L,-1);
		lua_insert(L, -2);	// func.decode table.key table.id array value
		lua_rawseti(L, -2 , n+1);	// func.decode table.key table.id array
		lua_pop(L,1);
	} else {
		push_value(L, type, type_name, v);
		lua_setfield(L, -3 , key);
	}
}
Пример #24
0
int su_unpack_seq(su_state *s, int idx) {
	int num = 0;
	value_t tmp;
	value_t v = *STK(TOP(idx));
	while (isseq(s, &v)) {
		tmp = v.obj.q->vt->first(s, v.obj.q);
		push_value(s, &tmp);
		v = v.obj.q->vt->rest(s, v.obj.q);
		num++;
	}
	return num;
}
Пример #25
0
void su_map(su_state *s, int num) {
	int i;
	value_t k, v;
	value_t m = map_create_empty(s);
	for (i = num * 2; i > 0; i -= 2) {
		k = *STK(-i);
		v = *STK(-i + 1);
		m = map_insert(s, m.obj.m, &k, hash_value(&k), &v);
	}
	s->stack_top -= num * 2;
	push_value(s, &m);
}
Пример #26
0
Файл: node.c Проект: yipf/C-lisp
node_t hash_push_value(char* key,node_t value){
	node_t head,target,nvalue;
	head=HASH+key2hash(key,NUM);
	target=get_node(head->cdr,key);
	if(!target){
		target=alloc_node(key);
		target->cdr=head->cdr;
		head->cdr=target;
	}
	nvalue=alloc_node(key);
	nvalue->child=value;
	node->child=push_value(node->child,nvalue);
	return value;
}
Пример #27
0
void su_fork(su_state *s, int narg) {
	value_t v;
	su_state *ns;
 
	narg++;
	v.type = SU_BOOLEAN;
	su_thread_indisposable(s);
	spin_lock(&s->msi->thread_pool_lock);
	su_thread_disposable(s);
	ns = new_state(s);
	
	if (!ns) {
		s->stack_top -= narg;
		v.obj.b = 0;
		push_value(s, &v);
		spin_unlock(&s->msi->thread_pool_lock);
		return;
	}
	
	ns->interrupt = 0x0;
	ns->narg = narg - 1;
	ns->pc = 0xffff;
	
	ns->string_builder = NULL;
	ns->errtop = ns->ferrtop = -1;
	
	ns->stack[SU_GLOBAL_INDEX] = s->stack[SU_GLOBAL_INDEX];
	
	su_assert(s, !thread_init(&thread_boot, (void*)ns), "Could not create thread!");
	s->stack_top -= narg;
	
	v.obj.b = 1;
	push_value(s, &v);
	
	spin_unlock(&s->msi->thread_pool_lock);
}
Пример #28
0
	bool LoadFile(lua_State *L, agi::fs::path const& raw_filename) {
		auto filename = raw_filename;
		try {
			filename = agi::fs::Canonicalize(raw_filename);
		}
		catch (agi::fs::FileSystemUnknownError const& e) {
			LOG_E("auto4/lua") << "Error canonicalizing path: " << e.GetMessage();
		}

		agi::read_file_mapping file(filename);
		auto buff = file.read();
		size_t size = static_cast<size_t>(file.size());

		// Discard the BOM if present
		if (size >= 3 && buff[0] == -17 && buff[1] == -69 && buff[2] == -65) {
			buff += 3;
			size -= 3;
		}

		if (!agi::fs::HasExtension(filename, "moon"))
			return luaL_loadbuffer(L, buff, size, filename.string().c_str()) == 0;

		// We have a MoonScript file, so we need to load it with that
		// It might be nice to have a dedicated lua state for compiling
		// MoonScript to Lua
		lua_getfield(L, LUA_REGISTRYINDEX, "moonscript");

		// Save the text we'll be loading for the line number rewriting in the
		// error handling
		lua_pushlstring(L, buff, size);
		lua_pushvalue(L, -1);
		lua_setfield(L, LUA_REGISTRYINDEX, ("raw moonscript: " + filename.string()).c_str());

		push_value(L, filename);
		if (lua_pcall(L, 2, 2, 0))
			return false; // Leaves error message on stack

		// loadstring returns nil, error on error or a function on success
		if (lua_isnil(L, 1)) {
			lua_remove(L, 1);
			return false;
		}

		lua_pop(L, 1); // Remove the extra nil for the stackchecker
		return true;
	}
Пример #29
0
su_state *su_init(su_alloc alloc) {
	int i;
	value_t v;
	su_state *s;
	su_alloc mf;
	main_state_internal_t *msi;
	
	assert(sizeof(value_t) <= SU_VALUE_SIZE);
	assert(sizeof(value_t) > SU_VALUE_DATA_SIZE);
	
	mf = alloc ? alloc : default_alloc;
	msi = (main_state_internal_t*)mf(NULL, sizeof(main_state_internal_t));
	s = &msi->threads[0];
	memset(msi, 0, sizeof(main_state_internal_t));
	
	for (i = 0; i < SU_OPT_MAX_THREADS; i++)
		msi->threads[i].thread_finished.value = 1;
	
	s->alloc = mf;
	s->msi = msi;
	s->main_state = s;

	msi->gc_state = GC_STATE_SWEEP;

	s->fstdin = stdin;
	s->fstdout = stdout;
	s->fstderr = stderr;
	s->errtop = s->ferrtop = -1;

	s->pc = 0xffff;
	s->msi->ref_counter = 0x1;
	s->msi->tid_count.value = 1;
	s->msi->thread_count.value = 1;
	
	v = init_globals(s);
	
	su_pushnil(s);					/* SU_NIL_INDEX */
	push_value(s, &v);				/* SU_GLOBAL_INDEX */
	su_map(s, 0);					/* SU_REGISTRY_INDEX */
	
	rw_barrier();
	return s;
}
Пример #30
0
static void
call_crowbar_function(SIMCAR_Interpreter *inter, SIMCAR_LocalEnvironment *env,
                      SIMCAR_LocalEnvironment *caller_env,
                      Expression *expr, FunctionDefinition *func)
{
    SIMCAR_Value   value;
    StatementResult     result;
    ArgumentList        *arg_p;
    ParameterList       *param_p;


    for (arg_p = expr->u.function_call_expression.argument,
             param_p = func->u.crowbar_f.parameter;
         arg_p;
         arg_p = arg_p->next, param_p = param_p->next) {
        Variable *new_var;
        SIMCAR_Value arg_val;

         if (param_p == NULL) {
             crb_runtime_error(expr->line_number, ARGUMENT_TOO_MANY_ERR,
                               MESSAGE_ARGUMENT_END);
         }
         eval_expression(inter, caller_env, arg_p->expression);
         arg_val = pop_value(inter);
         new_var = crb_add_local_variable(env, param_p->name);
         new_var->value = arg_val;
    }
     if (param_p) {
         crb_runtime_error(expr->line_number, ARGUMENT_TOO_FEW_ERR,
                           MESSAGE_ARGUMENT_END);
     }
     result = crb_execute_statement_list(inter, env,
                                         func->u.crowbar_f.block
                                         ->statement_list);
     if (result.type == RETURN_STATEMENT_RESULT) {
         value = result.u.return_value;
     } else {
         value.type = SIMCAR_NULL_VALUE;
     }

     push_value(inter, &value);
}