diff --git a/src/Type.cc b/src/Type.cc index 9db32d6ae9..f38a03564b 100644 --- a/src/Type.cc +++ b/src/Type.cc @@ -1981,6 +1981,22 @@ detail::TraversalCode VectorType::Traverse(detail::TraversalCallback* cb) const HANDLE_TC_TYPE_POST(tc); } +TypeManager::TypeManager() + { + for ( auto i = 0u; i < base_list_types.size(); ++i ) + { + TypeTag tag = static_cast(i); + TypePtr pure_type = tag == TYPE_ANY ? nullptr : base_type(tag); + base_list_types[tag] = make_intrusive(pure_type); + } + } + +const TypeListPtr& TypeManager::TypeList(TypeTag t) const + { + assert(t >= 0 && t < NUM_TYPES); + return base_list_types[t]; + } + // Returns true if t1 is initialization-compatible with t2 (i.e., if an // initializer with type t1 can be used to initialize a value with type t2), // false otherwise. Assumes that t1's tag is different from t2's. Note diff --git a/src/Type.h b/src/Type.h index cbdc4a3602..b967524be4 100644 --- a/src/Type.h +++ b/src/Type.h @@ -2,6 +2,7 @@ #pragma once +#include #include #include #include @@ -866,6 +867,21 @@ protected: TypePtr yield_type; }; +// Holds pre-allocated Type objects. +class TypeManager + { +public: + TypeManager(); + + // Get a Typelist instance with the given type tag. + const TypeListPtr& TypeList(TypeTag t) const; + +private: + std::array base_list_types; + }; + +extern TypeManager* type_mgr; + // True if the two types are equivalent. If is_init is true then the test is // done in the context of an initialization. If match_record_field_names is // true then for record types the field names have to match, too. diff --git a/src/Val.cc b/src/Val.cc index 208c564bf6..28c2dcbad7 100644 --- a/src/Val.cc +++ b/src/Val.cc @@ -1188,10 +1188,7 @@ ValPtr PatternVal::DoClone(CloneState* state) return state->NewClone(this, make_intrusive(re)); } -ListVal::ListVal(TypeTag t) : Val(make_intrusive(t == TYPE_ANY ? nullptr : base_type(t))) - { - tag = t; - } +ListVal::ListVal(TypeTag t) : Val(type_mgr->TypeList(t)), tag(t) { } ListVal::~ListVal() { } diff --git a/src/zeek-setup.cc b/src/zeek-setup.cc index 98e87cfcbf..8a3fedbedb 100644 --- a/src/zeek-setup.cc +++ b/src/zeek-setup.cc @@ -172,6 +172,7 @@ void do_ssl_deinit() } // namespace #endif +zeek::TypeManager* zeek::type_mgr = nullptr; zeek::ValManager* zeek::val_mgr = nullptr; zeek::packet_analysis::Manager* zeek::packet_mgr = nullptr; zeek::analyzer::Manager* zeek::analyzer_mgr = nullptr; @@ -437,6 +438,7 @@ static void terminate_zeek() delete session_mgr; delete fragment_mgr; delete telemetry_mgr; + delete type_mgr; // free the global scope pop_scope(); @@ -593,6 +595,7 @@ SetupResult setup(int argc, char** argv, Options* zopts) run_state::zeek_start_time = util::current_time(true); + type_mgr = new TypeManager(); val_mgr = new ValManager(); reporter = new Reporter(options.abort_on_scripting_errors); thread_mgr = new threading::Manager();