diff --git a/include/cubescript/cubescript.hh b/include/cubescript/cubescript.hh index c088302..54060e4 100644 --- a/include/cubescript/cubescript.hh +++ b/include/cubescript/cubescript.hh @@ -73,7 +73,6 @@ enum { IDENT_FLAG_ARG = 1 << 6 }; -struct bcode; struct internal_state; struct thread_state; struct ident_impl; @@ -82,7 +81,7 @@ struct LIBCUBESCRIPT_EXPORT bcode_ref { bcode_ref(): p_code(nullptr) {} - bcode_ref(bcode *v); + bcode_ref(struct bcode *v); bcode_ref(bcode_ref const &v); bcode_ref(bcode_ref &&v): p_code(v.p_code) @@ -95,15 +94,15 @@ struct LIBCUBESCRIPT_EXPORT bcode_ref { bcode_ref &operator=(bcode_ref const &v); bcode_ref &operator=(bcode_ref &&v); - operator bool() const { return p_code != nullptr; } - operator bcode *() const { return p_code; } + bool empty() const; + + operator bool() const; + operator struct bcode *() const; private: - bcode *p_code; + struct bcode *p_code; }; -LIBCUBESCRIPT_EXPORT bool code_is_empty(bcode *code); - struct LIBCUBESCRIPT_EXPORT string_ref { friend struct any_value; friend struct string_pool; @@ -165,13 +164,13 @@ struct LIBCUBESCRIPT_EXPORT any_value { void set_str(std::string_view val); void set_str(string_ref const &val); void set_none(); - void set_code(bcode *val); + void set_code(bcode_ref const &val); void set_ident(ident *val); string_ref get_str() const; integer_type get_int() const; float_type get_float() const; - bcode *get_code() const; + bcode_ref get_code() const; ident *get_ident() const; void get_val(any_value &r) const; @@ -181,11 +180,9 @@ struct LIBCUBESCRIPT_EXPORT any_value { float_type force_float(); integer_type force_int(); std::string_view force_str(); - bcode *force_code(state &cs); + bcode_ref force_code(state &cs); ident *force_ident(state &cs); - bool code_is_empty() const; - private: template struct stor_t { @@ -440,18 +437,18 @@ struct LIBCUBESCRIPT_EXPORT state { void reset_var(std::string_view name); void touch_var(std::string_view name); - void run(bcode *code, any_value &ret); + void run(bcode_ref const &code, any_value &ret); void run(std::string_view code, any_value &ret); void run(std::string_view code, any_value &ret, std::string_view source); void run(ident *id, std::span args, any_value &ret); - any_value run(bcode *code); + any_value run(bcode_ref const &code); any_value run(std::string_view code); any_value run(std::string_view code, std::string_view source); any_value run(ident *id, std::span args); - loop_state run_loop(bcode *code, any_value &ret); - loop_state run_loop(bcode *code); + loop_state run_loop(bcode_ref const &code, any_value &ret); + loop_state run_loop(bcode_ref const &code); bool is_in_loop() const; diff --git a/src/cs_bcode.cc b/src/cs_bcode.cc index 7312ee2..80a3410 100644 --- a/src/cs_bcode.cc +++ b/src/cs_bcode.cc @@ -34,6 +34,21 @@ LIBCUBESCRIPT_EXPORT bcode_ref &bcode_ref::operator=(bcode_ref &&v) { return *this; } +LIBCUBESCRIPT_EXPORT bool bcode_ref::empty() const { + if (!p_code) { + return true; + } + return (*p_code->get_raw() & BC_INST_OP_MASK) == BC_INST_EXIT; +} + +LIBCUBESCRIPT_EXPORT bcode_ref::operator bool() const { + return p_code != nullptr; +} + +LIBCUBESCRIPT_EXPORT bcode_ref::operator bcode *() const { + return p_code; +} + /* private funcs */ struct bcode_hdr { diff --git a/src/cs_state.cc b/src/cs_state.cc index 175de22..d645c01 100644 --- a/src/cs_state.cc +++ b/src/cs_state.cc @@ -126,7 +126,7 @@ state::state(alloc_func func, void *data) { res.set_int(1); } else { for (size_t i = 0; i < args.size(); ++i) { - bcode *code = args[i].get_code(); + auto code = args[i].get_code(); if (code) { cs.run(code, res); } else { @@ -145,7 +145,7 @@ state::state(alloc_func func, void *data) { res.set_int(0); } else { for (size_t i = 0; i < args.size(); ++i) { - bcode *code = args[i].get_code(); + auto code = args[i].get_code(); if (code) { cs.run(code, res); } else { @@ -780,8 +780,9 @@ LIBCUBESCRIPT_EXPORT void state::init_libs(int libs) { } } -LIBCUBESCRIPT_EXPORT void state::run(bcode *code, any_value &ret) { - vm_exec(*p_tstate, reinterpret_cast(code), ret); +LIBCUBESCRIPT_EXPORT void state::run(bcode_ref const &code, any_value &ret) { + bcode *p = code; + vm_exec(*p_tstate, reinterpret_cast(p), ret); } static void do_run( @@ -897,7 +898,7 @@ LIBCUBESCRIPT_EXPORT void state::run( } } -LIBCUBESCRIPT_EXPORT any_value state::run(bcode *code) { +LIBCUBESCRIPT_EXPORT any_value state::run(bcode_ref const &code) { any_value ret{*this}; run(code, ret); return ret; @@ -925,7 +926,9 @@ LIBCUBESCRIPT_EXPORT any_value state::run( return ret; } -LIBCUBESCRIPT_EXPORT loop_state state::run_loop(bcode *code, any_value &ret) { +LIBCUBESCRIPT_EXPORT loop_state state::run_loop( + bcode_ref const &code, any_value &ret +) { ++p_tstate->loop_level; try { run(code, ret); @@ -942,7 +945,7 @@ LIBCUBESCRIPT_EXPORT loop_state state::run_loop(bcode *code, any_value &ret) { return loop_state::NORMAL; } -LIBCUBESCRIPT_EXPORT loop_state state::run_loop(bcode *code) { +LIBCUBESCRIPT_EXPORT loop_state state::run_loop(bcode_ref const &code) { any_value ret{*this}; return run_loop(code, ret); } diff --git a/src/cs_val.cc b/src/cs_val.cc index f5dab58..32823c2 100644 --- a/src/cs_val.cc +++ b/src/cs_val.cc @@ -168,11 +168,12 @@ void any_value::set_none() { p_type = value_type::NONE; } -void any_value::set_code(bcode *val) { +void any_value::set_code(bcode_ref const &val) { + bcode *p = val; csv_cleanup(p_type, &p_stor); p_type = value_type::CODE; - bcode_addref(val->get_raw()); - csv_get(&p_stor) = val; + bcode_addref(p->get_raw()); + csv_get(&p_stor) = p; } void any_value::set_ident(ident *val) { @@ -250,10 +251,10 @@ std::string_view any_value::force_str() { )); } -bcode *any_value::force_code(state &cs) { +bcode_ref any_value::force_code(state &cs) { switch (get_type()) { case value_type::CODE: - return csv_get(&p_stor); + return bcode_ref{csv_get(&p_stor)}; default: break; } @@ -265,7 +266,7 @@ bcode *any_value::force_code(state &cs) { std::memcpy(cbuf, gs.code.data(), gs.code.size() * sizeof(std::uint32_t)); auto *bc = reinterpret_cast(cbuf + 1); set_code(bc); - return bc; + return bcode_ref{bc}; } ident *any_value::force_ident(state &cs) { @@ -312,11 +313,11 @@ float_type any_value::get_float() const { return 0.0f; } -bcode *any_value::get_code() const { +bcode_ref any_value::get_code() const { if (get_type() != value_type::CODE) { - return nullptr; + return bcode_ref{}; } - return csv_get(&p_stor); + return bcode_ref{csv_get(&p_stor)}; } ident *any_value::get_ident() const { @@ -365,20 +366,6 @@ void any_value::get_val(any_value &r) const { } } -LIBCUBESCRIPT_EXPORT bool code_is_empty(bcode *code) { - if (!code) { - return true; - } - return (*code->get_raw() & BC_INST_OP_MASK) == BC_INST_EXIT; -} - -bool any_value::code_is_empty() const { - if (get_type() != value_type::CODE) { - return true; - } - return cubescript::code_is_empty(csv_get(&p_stor)); -} - bool any_value::get_bool() const { switch (get_type()) { case value_type::FLOAT: diff --git a/src/lib_base.cc b/src/lib_base.cc index 72fbe11..ee55e3e 100644 --- a/src/lib_base.cc +++ b/src/lib_base.cc @@ -9,7 +9,7 @@ namespace cubescript { static inline void do_loop( state &cs, ident &id, integer_type offset, integer_type n, integer_type step, - bcode *cond, bcode *body + bcode_ref &&cond, bcode_ref &&body ) { if (n <= 0) { return; @@ -34,7 +34,7 @@ static inline void do_loop( static inline void do_loop_conc( state &cs, any_value &res, ident &id, integer_type offset, integer_type n, - integer_type step, bcode *body, bool space + integer_type step, bcode_ref &&body, bool space ) { if (n <= 0) { return; @@ -228,7 +228,8 @@ void init_lib_base(state &gcs) { }); gcs.new_command("while", "ee", [](auto &cs, auto args, auto &) { - bcode *cond = args[0].get_code(), *body = args[1].get_code(); + auto cond = args[0].get_code(); + auto body = args[1].get_code(); while (cs.run(cond).get_bool()) { switch (cs.run_loop(body)) { case loop_state::BREAK: diff --git a/src/lib_list.cc b/src/lib_list.cc index 947eacb..9a5f47c 100644 --- a/src/lib_list.cc +++ b/src/lib_list.cc @@ -74,7 +74,7 @@ static inline void list_assoc( static void loop_list_conc( state &cs, any_value &res, ident *id, std::string_view list, - bcode *body, bool space + bcode_ref &&body, bool space ) { if (alias_stack st{cs, id}; st) { any_value idv{cs}; @@ -519,7 +519,7 @@ struct ListSortItem { struct ListSortFun { state &cs; alias_stack &xst, &yst; - bcode *body; + bcode_ref const *body; bool operator()(ListSortItem const &xval, ListSortItem const &yval) { any_value v{cs}; @@ -527,13 +527,13 @@ struct ListSortFun { xst.set(std::move(v)); v.set_str(yval.str); yst.set(std::move(v)); - return cs.run(body).get_bool(); + return cs.run(*body).get_bool(); } }; static void list_sort( state &cs, any_value &res, std::string_view list, - ident *x, ident *y, bcode *body, bcode *unique + ident *x, ident *y, bcode_ref &&body, bcode_ref &&unique ) { if (x == y) { return; @@ -561,10 +561,10 @@ static void list_sort( size_t totaluniq = total; size_t nuniq = items.size(); if (body) { - ListSortFun f = { cs, xst, yst, body }; + ListSortFun f = { cs, xst, yst, &body }; std::sort(items.buf.begin(), items.buf.end(), f); - if (!code_is_empty(unique)) { - f.body = unique; + if (!unique.empty()) { + f.body = &unique; totaluniq = items[0].quote.size(); nuniq = 1; for (size_t i = 1; i < items.size(); i++) { @@ -578,7 +578,7 @@ static void list_sort( } } } else { - ListSortFun f = { cs, xst, yst, unique }; + ListSortFun f = { cs, xst, yst, &unique }; totaluniq = items[0].quote.size(); nuniq = 1; for (size_t i = 1; i < items.size(); i++) {