refactor cs_value and related structures to contain state
this will allow us to intern strings inside cs_valuemaster
parent
8c77724f88
commit
c004db42c6
|
@ -42,6 +42,7 @@ enum {
|
|||
|
||||
struct cs_bcode;
|
||||
struct cs_value;
|
||||
struct cs_state;
|
||||
struct cs_shared_state;
|
||||
|
||||
struct OSTD_EXPORT cs_bcode_ref {
|
||||
|
@ -88,8 +89,8 @@ private:
|
|||
/* for internal use only */
|
||||
cs_strref(char const *p, cs_shared_state &cs);
|
||||
|
||||
char const *p_str;
|
||||
cs_shared_state *p_state;
|
||||
char const *p_str;
|
||||
};
|
||||
|
||||
enum class cs_value_type {
|
||||
|
@ -97,14 +98,17 @@ enum class cs_value_type {
|
|||
};
|
||||
|
||||
struct OSTD_EXPORT cs_value {
|
||||
cs_value();
|
||||
cs_value() = delete;
|
||||
~cs_value();
|
||||
|
||||
cs_value(cs_state &);
|
||||
cs_value(cs_shared_state &);
|
||||
|
||||
cs_value(cs_value const &);
|
||||
cs_value(cs_value &&);
|
||||
|
||||
cs_value &operator=(cs_value const &v);
|
||||
cs_value &operator=(cs_value &&v);
|
||||
cs_value &operator=(cs_value const &);
|
||||
cs_value &operator=(cs_value &&);
|
||||
|
||||
cs_value_type get_type() const;
|
||||
|
||||
|
@ -135,7 +139,22 @@ struct OSTD_EXPORT cs_value {
|
|||
bool code_is_empty() const;
|
||||
|
||||
private:
|
||||
std::aligned_union_t<1, cs_int, cs_float, void *> p_stor;
|
||||
template<typename T>
|
||||
struct stor_t {
|
||||
cs_shared_state *state;
|
||||
T val;
|
||||
};
|
||||
|
||||
cs_shared_state *state() const {
|
||||
return reinterpret_cast<stor_t<void *> const *>(&p_stor)->state;
|
||||
}
|
||||
|
||||
std::aligned_union_t<1,
|
||||
stor_t<cs_int>,
|
||||
stor_t<cs_float>,
|
||||
stor_t<void *>,
|
||||
cs_strref
|
||||
> p_stor;
|
||||
size_t p_len;
|
||||
cs_value_type p_type;
|
||||
};
|
||||
|
@ -143,6 +162,8 @@ private:
|
|||
struct cs_ident_stack {
|
||||
cs_value val_s;
|
||||
cs_ident_stack *next;
|
||||
|
||||
cs_ident_stack(cs_state &cs): val_s{cs}, next{nullptr} {}
|
||||
};
|
||||
|
||||
struct cs_error;
|
||||
|
@ -308,11 +329,11 @@ struct OSTD_EXPORT cs_alias: cs_ident {
|
|||
void get_cstr(cs_value &v) const;
|
||||
void get_cval(cs_value &v) const;
|
||||
private:
|
||||
cs_alias(ostd::string_range n, cs_string a, int flags);
|
||||
cs_alias(ostd::string_range n, cs_int a, int flags);
|
||||
cs_alias(ostd::string_range n, cs_float a, int flags);
|
||||
cs_alias(ostd::string_range n, int flags);
|
||||
cs_alias(ostd::string_range n, cs_value v, int flags);
|
||||
cs_alias(cs_state &cs, ostd::string_range n, cs_string a, int flags);
|
||||
cs_alias(cs_state &cs, ostd::string_range n, cs_int a, int flags);
|
||||
cs_alias(cs_state &cs, ostd::string_range n, cs_float a, int flags);
|
||||
cs_alias(cs_state &cs, ostd::string_range n, int flags);
|
||||
cs_alias(cs_state &cs, ostd::string_range n, cs_value v, int flags);
|
||||
|
||||
cs_bcode *p_acode;
|
||||
cs_ident_stack *p_astack;
|
||||
|
@ -362,6 +383,7 @@ static inline void *cs_default_alloc(void *, void *p, size_t, size_t ns) {
|
|||
struct OSTD_EXPORT cs_state {
|
||||
friend struct cs_error;
|
||||
friend struct cs_strman;
|
||||
friend struct cs_value;
|
||||
friend struct cs_gen_state;
|
||||
|
||||
cs_shared_state *p_state;
|
||||
|
@ -603,7 +625,7 @@ private:
|
|||
};
|
||||
|
||||
struct OSTD_EXPORT cs_stacked_value: cs_value {
|
||||
cs_stacked_value(cs_ident *id = nullptr);
|
||||
cs_stacked_value(cs_state &cs, cs_ident *id = nullptr);
|
||||
~cs_stacked_value();
|
||||
|
||||
cs_stacked_value(cs_stacked_value const &) = delete;
|
||||
|
|
|
@ -4,10 +4,16 @@
|
|||
|
||||
namespace cscript {
|
||||
|
||||
template<typename T>
|
||||
struct stor_priv_t {
|
||||
cs_shared_state *state;
|
||||
T val;
|
||||
};
|
||||
|
||||
template<typename T, typename U>
|
||||
static inline T &csv_get(U &stor) {
|
||||
/* ugly, but internal and unlikely to cause bugs */
|
||||
return const_cast<T &>(reinterpret_cast<T const &>(stor));
|
||||
return const_cast<T &>(reinterpret_cast<stor_priv_t<T> const &>(stor).val);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
|
@ -28,19 +34,23 @@ static inline void csv_cleanup(cs_value_type tv, T &stor) {
|
|||
}
|
||||
}
|
||||
|
||||
cs_value::cs_value():
|
||||
cs_value::cs_value(cs_state &st): cs_value(*st.p_state) {}
|
||||
|
||||
cs_value::cs_value(cs_shared_state &st):
|
||||
p_stor(), p_len(0), p_type(cs_value_type::Null)
|
||||
{}
|
||||
{
|
||||
reinterpret_cast<stor_priv_t<void *> *>(&p_stor)->state = &st;
|
||||
}
|
||||
|
||||
cs_value::~cs_value() {
|
||||
csv_cleanup(p_type, p_stor);
|
||||
}
|
||||
|
||||
cs_value::cs_value(cs_value const &v): cs_value() {
|
||||
cs_value::cs_value(cs_value const &v): cs_value(*v.state()) {
|
||||
*this = v;
|
||||
}
|
||||
|
||||
cs_value::cs_value(cs_value &&v): cs_value() {
|
||||
cs_value::cs_value(cs_value &&v): cs_value(*v.state()) {
|
||||
*this = std::move(v);
|
||||
}
|
||||
|
||||
|
@ -375,8 +385,8 @@ bool cs_value::get_bool() const {
|
|||
|
||||
/* stacked value for easy stack management */
|
||||
|
||||
cs_stacked_value::cs_stacked_value(cs_ident *id):
|
||||
cs_value(), p_a(nullptr), p_stack(), p_pushed(false)
|
||||
cs_stacked_value::cs_stacked_value(cs_state &cs, cs_ident *id):
|
||||
cs_value(cs), p_a(nullptr), p_stack{cs}, p_pushed(false)
|
||||
{
|
||||
set_alias(id);
|
||||
}
|
||||
|
|
88
src/cs_vm.cc
88
src/cs_vm.cc
|
@ -12,7 +12,7 @@ cs_strref::cs_strref(cs_shared_state &cs, ostd::string_range str):
|
|||
p_str = cs.strman->add(str);
|
||||
}
|
||||
|
||||
cs_strref::cs_strref(cs_strref const &ref): p_str{ref.p_str}, p_state{ref.p_state}
|
||||
cs_strref::cs_strref(cs_strref const &ref): p_state{ref.p_state}, p_str{ref.p_str}
|
||||
{
|
||||
p_state->strman->ref(p_str);
|
||||
}
|
||||
|
@ -55,9 +55,9 @@ struct cs_cmd_internal {
|
|||
}
|
||||
};
|
||||
|
||||
static inline void cs_push_alias(cs_ident *id, cs_ident_stack &st) {
|
||||
static inline void cs_push_alias(cs_state &cs, cs_ident *id, cs_ident_stack &st) {
|
||||
if (id->is_alias() && (id->get_index() >= MaxArguments)) {
|
||||
cs_value nv;
|
||||
cs_value nv{cs};
|
||||
cs_alias_internal::push_arg(static_cast<cs_alias *>(id), nv, st);
|
||||
}
|
||||
}
|
||||
|
@ -470,7 +470,7 @@ static inline void callcommand(
|
|||
i = std::max(i + 1, numargs);
|
||||
auto buf = ostd::appender<cs_string>();
|
||||
cscript::util::tvals_concat(buf, ostd::iter(args, args + i), " ");
|
||||
cs_value tv;
|
||||
cs_value tv{cs};
|
||||
tv.set_str(std::move(buf.get()));
|
||||
cs_cmd_internal::call(cs, id, cs_value_r(&tv, &tv + 1), res);
|
||||
return;
|
||||
|
@ -503,7 +503,7 @@ static inline void cs_call_alias(
|
|||
int callargs, int &nargs, int offset, int skip, uint32_t op
|
||||
) {
|
||||
cs_ivar *anargs = static_cast<cs_ivar *>(cs.p_state->identmap[NumargsIdx]);
|
||||
cs_ident_stack argstack[MaxArguments];
|
||||
cs_valarray<cs_ident_stack, MaxArguments> argstack{cs};
|
||||
for(int i = 0; i < callargs; i++) {
|
||||
cs_alias_internal::push_arg(
|
||||
static_cast<cs_alias *>(cs.p_state->identmap[i]),
|
||||
|
@ -515,7 +515,7 @@ static inline void cs_call_alias(
|
|||
int oldflags = cs.identflags;
|
||||
cs.identflags |= a->get_flags()&CS_IDF_OVERRIDDEN;
|
||||
cs_identLink aliaslink = {
|
||||
a, cs.p_callstack, (1<<callargs)-1, argstack
|
||||
a, cs.p_callstack, (1<<callargs)-1, &argstack[0]
|
||||
};
|
||||
cs.p_callstack = &aliaslink;
|
||||
uint32_t *codep = reinterpret_cast<uint32_t *>(
|
||||
|
@ -609,8 +609,8 @@ static inline int cs_get_lookupu_type(
|
|||
return CsIdFvar;
|
||||
case cs_ident_type::Command: {
|
||||
arg.set_null();
|
||||
cs_value buf[MaxArguments];
|
||||
callcommand(cs, static_cast<cs_command *>(id), buf, arg, 0, true);
|
||||
cs_valarray<cs_value, MaxArguments> buf{cs};
|
||||
callcommand(cs, static_cast<cs_command *>(id), &buf[0], arg, 0, true);
|
||||
force_arg(arg, op & CsCodeRetMask);
|
||||
return -2; /* ignore */
|
||||
}
|
||||
|
@ -625,7 +625,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
result.set_null();
|
||||
RunDepthRef level{cs}; /* incr and decr on scope exit */
|
||||
int numargs = 0;
|
||||
cs_value args[MaxArguments + MaxResults];
|
||||
cs_valarray<cs_value, MaxArguments + MaxResults> args{cs};
|
||||
auto &chook = cs.get_call_hook();
|
||||
if (chook) {
|
||||
chook(cs);
|
||||
|
@ -716,9 +716,9 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
|
||||
case CsCodeLocal: {
|
||||
int numlocals = op >> 8, offset = numargs - numlocals;
|
||||
cs_ident_stack locals[MaxArguments];
|
||||
cs_valarray<cs_ident_stack, MaxArguments> locals{cs};
|
||||
for (int i = 0; i < numlocals; ++i) {
|
||||
cs_push_alias(args[offset + i].get_ident(), locals[i]);
|
||||
cs_push_alias(cs, args[offset + i].get_ident(), locals[i]);
|
||||
}
|
||||
cs_do_and_cleanup([&]() {
|
||||
code = runcode(cs, code, result);
|
||||
|
@ -1002,7 +1002,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
cs.p_state->identmap[op >> 8]
|
||||
);
|
||||
if (!cs_is_arg_used(cs, a)) {
|
||||
cs_value nv;
|
||||
cs_value nv{cs};
|
||||
cs_alias_internal::push_arg(
|
||||
a, nv, cs.p_callstack->argstack[a->get_index()], false
|
||||
);
|
||||
|
@ -1022,7 +1022,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
id = cs.new_ident(arg.get_strr());
|
||||
}
|
||||
if ((id->get_index() < MaxArguments) && !cs_is_arg_used(cs, id)) {
|
||||
cs_value nv;
|
||||
cs_value nv{cs};
|
||||
cs_alias_internal::push_arg(
|
||||
static_cast<cs_alias *>(id), nv,
|
||||
cs.p_callstack->argstack[id->get_index()], false
|
||||
|
@ -1383,7 +1383,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
int offset = numargs - id->get_num_args();
|
||||
result.force_null();
|
||||
cs_cmd_internal::call(cs, id, cs_value_r(
|
||||
args + offset, args + offset + id->get_num_args()
|
||||
&args[0] + offset, &args[0] + offset + id->get_num_args()
|
||||
), result);
|
||||
force_arg(result, op & CsCodeRetMask);
|
||||
numargs = offset;
|
||||
|
@ -1420,7 +1420,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
cscript::util::tvals_concat(buf, ostd::iter(
|
||||
&args[offset], &args[offset + callargs]
|
||||
), " ");
|
||||
cs_value tv;
|
||||
cs_value tv{cs};
|
||||
tv.set_str(std::move(buf.get()));
|
||||
cs_cmd_internal::call(cs, id, cs_value_r(&tv, &tv + 1), result);
|
||||
}
|
||||
|
@ -1498,7 +1498,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
);
|
||||
}
|
||||
cs_call_alias(
|
||||
cs, static_cast<cs_alias *>(id), args, result, callargs,
|
||||
cs, static_cast<cs_alias *>(id), &args[0], result, callargs,
|
||||
numargs, offset, 0, op
|
||||
);
|
||||
continue;
|
||||
|
@ -1516,7 +1516,7 @@ static uint32_t *runcode(cs_state &cs, uint32_t *code, cs_value &result) {
|
|||
continue;
|
||||
}
|
||||
cs_call_alias(
|
||||
cs, static_cast<cs_alias *>(id), args, result, callargs,
|
||||
cs, static_cast<cs_alias *>(id), &args[0], result, callargs,
|
||||
numargs, offset, 0, op
|
||||
);
|
||||
continue;
|
||||
|
@ -1569,9 +1569,9 @@ noid:
|
|||
numargs = offset - 1;
|
||||
continue;
|
||||
case CsIdLocal: {
|
||||
cs_ident_stack locals[MaxArguments];
|
||||
cs_valarray<cs_ident_stack, MaxArguments> locals{cs};
|
||||
for (size_t j = 0; j < size_t(callargs); ++j) {
|
||||
cs_push_alias(cs.force_ident(
|
||||
cs_push_alias(cs, cs.force_ident(
|
||||
args[offset + j]
|
||||
), locals[j]);
|
||||
}
|
||||
|
@ -1634,7 +1634,7 @@ noid:
|
|||
goto noid;
|
||||
}
|
||||
cs_call_alias(
|
||||
cs, a, args, result, callargs, numargs,
|
||||
cs, a, &args[0], result, callargs, numargs,
|
||||
offset, 1, op
|
||||
);
|
||||
continue;
|
||||
|
@ -1684,10 +1684,10 @@ void cs_state::run(cs_ident *id, cs_value_r args, cs_value &ret) {
|
|||
/* fallthrough */
|
||||
case cs_ident_type::Command:
|
||||
if (nargs < static_cast<cs_command *>(id)->get_num_args()) {
|
||||
cs_value buf[MaxArguments];
|
||||
memcpy(buf, &args[0], args.size() * sizeof(cs_value));
|
||||
cs_valarray<cs_value, MaxArguments> buf{*this};
|
||||
memcpy(&buf[0], &args[0], args.size() * sizeof(cs_value));
|
||||
callcommand(
|
||||
*this, static_cast<cs_command *>(id), buf, ret,
|
||||
*this, static_cast<cs_command *>(id), &buf[0], ret,
|
||||
nargs, false
|
||||
);
|
||||
} else {
|
||||
|
@ -1743,89 +1743,89 @@ void cs_state::run(cs_ident *id, cs_value_r args, cs_value &ret) {
|
|||
}
|
||||
|
||||
cs_string cs_state::run_str(cs_bcode *code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_str();
|
||||
}
|
||||
|
||||
cs_string cs_state::run_str(ostd::string_range code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_str();
|
||||
}
|
||||
|
||||
cs_string cs_state::run_str(cs_ident *id, cs_value_r args) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(id, args, ret);
|
||||
return ret.get_str();
|
||||
}
|
||||
|
||||
cs_int cs_state::run_int(cs_bcode *code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_int();
|
||||
}
|
||||
|
||||
cs_int cs_state::run_int(ostd::string_range code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_int();
|
||||
}
|
||||
|
||||
cs_int cs_state::run_int(cs_ident *id, cs_value_r args) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(id, args, ret);
|
||||
return ret.get_int();
|
||||
}
|
||||
|
||||
cs_float cs_state::run_float(cs_bcode *code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_float();
|
||||
}
|
||||
|
||||
cs_float cs_state::run_float(ostd::string_range code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_float();
|
||||
}
|
||||
|
||||
cs_float cs_state::run_float(cs_ident *id, cs_value_r args) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(id, args, ret);
|
||||
return ret.get_float();
|
||||
}
|
||||
|
||||
bool cs_state::run_bool(cs_bcode *code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_bool();
|
||||
}
|
||||
|
||||
bool cs_state::run_bool(ostd::string_range code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
return ret.get_bool();
|
||||
}
|
||||
|
||||
bool cs_state::run_bool(cs_ident *id, cs_value_r args) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(id, args, ret);
|
||||
return ret.get_bool();
|
||||
}
|
||||
|
||||
void cs_state::run(cs_bcode *code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
}
|
||||
|
||||
void cs_state::run(ostd::string_range code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(code, ret);
|
||||
}
|
||||
|
||||
void cs_state::run(cs_ident *id, cs_value_r args) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
run(id, args, ret);
|
||||
}
|
||||
|
||||
|
@ -1847,7 +1847,7 @@ CsLoopState cs_state::run_loop(cs_bcode *code, cs_value &ret) {
|
|||
}
|
||||
|
||||
CsLoopState cs_state::run_loop(cs_bcode *code) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
return run_loop(code, ret);
|
||||
}
|
||||
|
||||
|
@ -1879,7 +1879,7 @@ static bool cs_run_file(
|
|||
}
|
||||
|
||||
std::optional<cs_string> cs_state::run_file_str(ostd::string_range fname) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
if (!cs_run_file(*this, fname, ret)) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
@ -1887,7 +1887,7 @@ std::optional<cs_string> cs_state::run_file_str(ostd::string_range fname) {
|
|||
}
|
||||
|
||||
std::optional<cs_int> cs_state::run_file_int(ostd::string_range fname) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
if (!cs_run_file(*this, fname, ret)) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
@ -1895,7 +1895,7 @@ std::optional<cs_int> cs_state::run_file_int(ostd::string_range fname) {
|
|||
}
|
||||
|
||||
std::optional<cs_float> cs_state::run_file_float(ostd::string_range fname) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
if (!cs_run_file(*this, fname, ret)) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
@ -1903,7 +1903,7 @@ std::optional<cs_float> cs_state::run_file_float(ostd::string_range fname) {
|
|||
}
|
||||
|
||||
std::optional<bool> cs_state::run_file_bool(ostd::string_range fname) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
if (!cs_run_file(*this, fname, ret)) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
@ -1915,7 +1915,7 @@ bool cs_state::run_file(ostd::string_range fname, cs_value &ret) {
|
|||
}
|
||||
|
||||
bool cs_state::run_file(ostd::string_range fname) {
|
||||
cs_value ret;
|
||||
cs_value ret{*this};
|
||||
if (!cs_run_file(*this, fname, ret)) {
|
||||
return false;
|
||||
}
|
||||
|
|
24
src/cs_vm.hh
24
src/cs_vm.hh
|
@ -6,6 +6,7 @@
|
|||
#include <cstdlib>
|
||||
#include <array>
|
||||
#include <vector>
|
||||
#include <type_traits>
|
||||
|
||||
#include "cs_util.hh"
|
||||
|
||||
|
@ -31,6 +32,27 @@ struct cs_identLink {
|
|||
cs_ident_stack *argstack;
|
||||
};
|
||||
|
||||
template<typename T, std::size_t N>
|
||||
struct cs_valarray {
|
||||
cs_valarray(cs_state &cs) {
|
||||
for (std::size_t i = 0; i < N; ++i) {
|
||||
new (&stor[i]) T{cs};
|
||||
}
|
||||
}
|
||||
|
||||
~cs_valarray() {
|
||||
for (std::size_t i = 0; i < N; ++i) {
|
||||
reinterpret_cast<T *>(&stor[i])->~T();
|
||||
}
|
||||
}
|
||||
|
||||
T &operator[](std::size_t i) {
|
||||
return *reinterpret_cast<T *>(&stor[i]);
|
||||
}
|
||||
|
||||
std::aligned_storage_t<sizeof(T), alignof(T)> stor[N];
|
||||
};
|
||||
|
||||
enum {
|
||||
CsValNull = 0, CsValInt, CsValFloat, CsValString,
|
||||
CsValAny, CsValCode, CsValMacro, CsValIdent, CsValCstring,
|
||||
|
@ -409,7 +431,7 @@ static void cs_do_args(cs_state &cs, F body) {
|
|||
body();
|
||||
return;
|
||||
}
|
||||
cs_ident_stack argstack[MaxArguments];
|
||||
cs_valarray<cs_ident_stack, MaxArguments> argstack{cs};
|
||||
int argmask1 = cs.p_callstack->usedargs;
|
||||
for (int i = 0; argmask1; argmask1 >>= 1, ++i) {
|
||||
if (argmask1 & 1) {
|
||||
|
|
|
@ -57,31 +57,32 @@ cs_svar::cs_svar(ostd::string_range name, cs_string v, cs_var_cb f, int fl):
|
|||
p_storage(std::move(v)), p_overrideval()
|
||||
{}
|
||||
|
||||
cs_alias::cs_alias(ostd::string_range name, cs_string a, int fl):
|
||||
cs_alias::cs_alias(cs_state &cs, ostd::string_range name, cs_string a, int fl):
|
||||
cs_ident(cs_ident_type::Alias, name, fl),
|
||||
p_acode(nullptr), p_astack(nullptr)
|
||||
p_acode(nullptr), p_astack(nullptr), p_val{cs}
|
||||
{
|
||||
p_val.set_str(std::move(a));
|
||||
}
|
||||
cs_alias::cs_alias(ostd::string_range name, cs_int a, int fl):
|
||||
cs_alias::cs_alias(cs_state &cs, ostd::string_range name, cs_int a, int fl):
|
||||
cs_ident(cs_ident_type::Alias, name, fl),
|
||||
p_acode(nullptr), p_astack(nullptr)
|
||||
p_acode(nullptr), p_astack(nullptr), p_val{cs}
|
||||
{
|
||||
p_val.set_int(a);
|
||||
}
|
||||
cs_alias::cs_alias(ostd::string_range name, cs_float a, int fl):
|
||||
cs_alias::cs_alias(cs_state &cs, ostd::string_range name, cs_float a, int fl):
|
||||
cs_ident(cs_ident_type::Alias, name, fl),
|
||||
p_acode(nullptr), p_astack(nullptr)
|
||||
p_acode(nullptr), p_astack(nullptr), p_val{cs}
|
||||
{
|
||||
p_val.set_float(a);
|
||||
}
|
||||
cs_alias::cs_alias(ostd::string_range name, int fl):
|
||||
cs_alias::cs_alias(cs_state &cs, ostd::string_range name, int fl):
|
||||
cs_ident(cs_ident_type::Alias, name, fl),
|
||||
p_acode(nullptr), p_astack(nullptr)
|
||||
p_acode(nullptr), p_astack(nullptr), p_val{cs}
|
||||
{
|
||||
p_val.set_null();
|
||||
}
|
||||
cs_alias::cs_alias(ostd::string_range name, cs_value v, int fl):
|
||||
/* FIXME: use cs rather than val's cs */
|
||||
cs_alias::cs_alias(cs_state &, ostd::string_range name, cs_value v, int fl):
|
||||
cs_ident(cs_ident_type::Alias, name, fl),
|
||||
p_acode(nullptr), p_astack(nullptr), p_val(std::move(v))
|
||||
{}
|
||||
|
@ -522,7 +523,7 @@ OSTD_EXPORT cs_ident *cs_state::new_ident(ostd::string_range name, int flags) {
|
|||
*this, "number %s is not a valid identifier name", name
|
||||
);
|
||||
}
|
||||
id = add_ident(p_state->create<cs_alias>(name, flags));
|
||||
id = add_ident(p_state->create<cs_alias>(*this, name, flags));
|
||||
}
|
||||
return id;
|
||||
}
|
||||
|
@ -650,7 +651,9 @@ OSTD_EXPORT void cs_state::set_alias(ostd::string_range name, cs_value v) {
|
|||
} else if (cs_check_num(name)) {
|
||||
throw cs_error(*this, "cannot alias number %s", name);
|
||||
} else {
|
||||
add_ident(p_state->create<cs_alias>(name, std::move(v), identflags));
|
||||
add_ident(p_state->create<cs_alias>(
|
||||
*this, name, std::move(v), identflags
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1028,7 +1031,7 @@ static inline void cs_do_loop(
|
|||
cs_state &cs, cs_ident &id, cs_int offset, cs_int n, cs_int step,
|
||||
cs_bcode *cond, cs_bcode *body
|
||||
) {
|
||||
cs_stacked_value idv{&id};
|
||||
cs_stacked_value idv{cs, &id};
|
||||
if (n <= 0 || !idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -1053,7 +1056,7 @@ static inline void cs_loop_conc(
|
|||
cs_state &cs, cs_value &res, cs_ident &id, cs_int offset, cs_int n,
|
||||
cs_int step, cs_bcode *body, bool space
|
||||
) {
|
||||
cs_stacked_value idv{&id};
|
||||
cs_stacked_value idv{cs, &id};
|
||||
if (n <= 0 || !idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -1061,7 +1064,7 @@ static inline void cs_loop_conc(
|
|||
for (cs_int i = 0; i < n; ++i) {
|
||||
idv.set_int(offset + i * step);
|
||||
idv.push();
|
||||
cs_value v;
|
||||
cs_value v{cs};
|
||||
switch (cs.run_loop(body, v)) {
|
||||
case CsLoopState::Break:
|
||||
goto end;
|
||||
|
@ -1091,7 +1094,7 @@ void cs_init_lib_base(cs_state &gcs) {
|
|||
ret.set_int(0);
|
||||
return;
|
||||
}
|
||||
cs_value result, tback;
|
||||
cs_value result{cs}, tback{cs};
|
||||
bool rc = true;
|
||||
try {
|
||||
cs.run(args[0].get_code(), result);
|
||||
|
@ -1171,7 +1174,7 @@ void cs_init_lib_base(cs_state &gcs) {
|
|||
});
|
||||
|
||||
gcs.new_command("pushif", "rTe", [](auto &cs, auto args, auto &res) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias() || (idv.get_alias()->get_index() < MaxArguments)) {
|
||||
return;
|
||||
}
|
||||
|
@ -1315,7 +1318,7 @@ end:
|
|||
});
|
||||
|
||||
gcs.new_command("push", "rTe", [](auto &cs, auto args, auto &res) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias() || (idv.get_alias()->get_index() < MaxArguments)) {
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -73,7 +73,7 @@ static void cs_loop_list_conc(
|
|||
cs_state &cs, cs_value &res, cs_ident *id, ostd::string_range list,
|
||||
cs_bcode *body, bool space
|
||||
) {
|
||||
cs_stacked_value idv{id};
|
||||
cs_stacked_value idv{cs, id};
|
||||
if (!idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -85,7 +85,7 @@ static void cs_loop_list_conc(
|
|||
if (n && space) {
|
||||
r += ' ';
|
||||
}
|
||||
cs_value v;
|
||||
cs_value v{cs};
|
||||
switch (cs.run_loop(body, v)) {
|
||||
case CsLoopState::Break:
|
||||
goto end;
|
||||
|
@ -197,7 +197,7 @@ void cs_init_lib_list(cs_state &gcs) {
|
|||
});
|
||||
|
||||
gcs.new_command("listfind", "rse", [](auto &cs, auto args, auto &res) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias()) {
|
||||
res.set_int(-1);
|
||||
return;
|
||||
|
@ -217,7 +217,7 @@ void cs_init_lib_list(cs_state &gcs) {
|
|||
});
|
||||
|
||||
gcs.new_command("listassoc", "rse", [](auto &cs, auto args, auto &res) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -284,7 +284,7 @@ void cs_init_lib_list(cs_state &gcs) {
|
|||
});
|
||||
|
||||
gcs.new_command("looplist", "rse", [](auto &cs, auto args, auto &) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -305,7 +305,8 @@ end:
|
|||
});
|
||||
|
||||
gcs.new_command("looplist2", "rrse", [](auto &cs, auto args, auto &) {
|
||||
cs_stacked_value idv1{args[0].get_ident()}, idv2{args[1].get_ident()};
|
||||
cs_stacked_value idv1{cs, args[0].get_ident()};
|
||||
cs_stacked_value idv2{cs, args[1].get_ident()};
|
||||
if (!idv1.has_alias() || !idv2.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -332,9 +333,9 @@ end:
|
|||
});
|
||||
|
||||
gcs.new_command("looplist3", "rrrse", [](auto &cs, auto args, auto &) {
|
||||
cs_stacked_value idv1{args[0].get_ident()};
|
||||
cs_stacked_value idv2{args[1].get_ident()};
|
||||
cs_stacked_value idv3{args[2].get_ident()};
|
||||
cs_stacked_value idv1{cs, args[0].get_ident()};
|
||||
cs_stacked_value idv2{cs, args[1].get_ident()};
|
||||
cs_stacked_value idv3{cs, args[2].get_ident()};
|
||||
if (!idv1.has_alias() || !idv2.has_alias() || !idv3.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -383,7 +384,7 @@ end:
|
|||
});
|
||||
|
||||
gcs.new_command("listfilter", "rse", [](auto &cs, auto args, auto &res) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -404,7 +405,7 @@ end:
|
|||
});
|
||||
|
||||
gcs.new_command("listcount", "rse", [](auto &cs, auto args, auto &res) {
|
||||
cs_stacked_value idv{args[0].get_ident()};
|
||||
cs_stacked_value idv{cs, args[0].get_ident()};
|
||||
if (!idv.has_alias()) {
|
||||
return;
|
||||
}
|
||||
|
@ -555,7 +556,7 @@ static void cs_list_sort(
|
|||
return;
|
||||
}
|
||||
|
||||
cs_stacked_value xval{xa}, yval{ya};
|
||||
cs_stacked_value xval{cs, xa}, yval{cs, ya};
|
||||
xval.set_null();
|
||||
yval.set_null();
|
||||
xval.push();
|
||||
|
|
|
@ -188,7 +188,7 @@ static void do_sigint(int n) {
|
|||
}
|
||||
|
||||
static bool do_call(cs_state &cs, ostd::string_range line, bool file = false) {
|
||||
cs_value ret;
|
||||
cs_value ret{cs};
|
||||
scs = &cs;
|
||||
signal(SIGINT, do_sigint);
|
||||
try {
|
||||
|
|
Loading…
Reference in New Issue