Mercurial > octave
changeset 33333:66a5438cc405
Make "symbol_scope_rep" a sub-class of "symbol_scope".
* libinterp/corefcn/symscope.h (octave::symbol_scope::symbol_scope_rep): Make
"symbol_scope_rep" a sub-class of "symbol_scope" so that both are complete
classes when used in the context of each other. This fixes a compilation error
with clang++ in C++20 mode.
* libinterp/corefcn/symscope.cc: Adapt for that change.
* libinterp/corefcn/symrec.h: Remove forward declaration of "class
symbol_scope_rep".
See: https://octave.discourse.group/t/5337
author | Markus Mützel <markus.muetzel@gmx.de> |
---|---|
date | Sun, 31 Mar 2024 13:46:25 +0200 |
parents | d7f1aae5be0f |
children | 000e4454fbcc |
files | libinterp/corefcn/symrec.h libinterp/corefcn/symscope.cc libinterp/corefcn/symscope.h |
diffstat | 3 files changed, 315 insertions(+), 317 deletions(-) [+] |
line wrap: on
line diff
--- a/libinterp/corefcn/symrec.h Thu Apr 04 22:50:56 2024 -0400 +++ b/libinterp/corefcn/symrec.h Sun Mar 31 13:46:25 2024 +0200 @@ -40,9 +40,7 @@ OCTAVE_BEGIN_NAMESPACE(octave) -class symbol_scope_rep; - -class symbol_record +class OCTINTERP_API symbol_record { public:
--- a/libinterp/corefcn/symscope.cc Thu Apr 04 22:50:56 2024 -0400 +++ b/libinterp/corefcn/symscope.cc Sun Mar 31 13:46:25 2024 +0200 @@ -42,7 +42,7 @@ OCTAVE_BEGIN_NAMESPACE(octave) -symbol_record symbol_scope_rep::insert_local (const std::string& name) +symbol_record symbol_scope::symbol_scope_rep::insert_local (const std::string& name) { symbol_record sym (name); @@ -52,7 +52,7 @@ } void -symbol_scope_rep::insert_symbol_record (symbol_record& sr) +symbol_scope::symbol_scope_rep::insert_symbol_record (symbol_record& sr) { std::size_t data_offset = num_symbols (); std::string name = sr.name (); @@ -63,7 +63,7 @@ } symbol_record -symbol_scope_rep::insert (const std::string& name) +symbol_scope::symbol_scope_rep::insert (const std::string& name) { table_iterator p = m_symbols.find (name); @@ -95,7 +95,7 @@ } std::list<octave_value> -symbol_scope_rep::localfunctions () const +symbol_scope::symbol_scope_rep::localfunctions () const { std::list<octave_value> retval; @@ -133,7 +133,7 @@ } octave_value -symbol_scope_rep::dump () const +symbol_scope::symbol_scope_rep::dump () const { std::map<std::string, octave_value> m = {{ "name", m_name }, @@ -148,7 +148,7 @@ } octave_value -symbol_scope_rep::dump_symbols_map () const +symbol_scope::symbol_scope_rep::dump_symbols_map () const { std::map<std::string, octave_value> info_map; @@ -163,7 +163,7 @@ } std::list<symbol_record> -symbol_scope_rep::symbol_list () const +symbol_scope::symbol_scope_rep::symbol_list () const { std::list<symbol_record> retval; @@ -174,7 +174,7 @@ } octave_value -symbol_scope_rep::find_subfunction (const std::string& name) const +symbol_scope::symbol_scope_rep::find_subfunction (const std::string& name) const { subfunctions_const_iterator p = m_subfunctions.find (name); @@ -190,7 +190,7 @@ } void -symbol_scope_rep::mark_subfunctions_in_scope_as_private (const std::string& class_name) +symbol_scope::symbol_scope_rep::mark_subfunctions_in_scope_as_private (const std::string& class_name) { for (auto& nm_sf : m_subfunctions) { @@ -202,7 +202,7 @@ } std::list<std::string> -symbol_scope_rep::parent_fcn_names () const +symbol_scope::symbol_scope_rep::parent_fcn_names () const { std::list<std::string> retval; @@ -219,25 +219,25 @@ } void -symbol_scope_rep::set_parent (const std::shared_ptr<symbol_scope_rep>& parent) +symbol_scope::symbol_scope_rep::set_parent (const std::shared_ptr<symbol_scope::symbol_scope_rep>& parent) { - m_parent = std::weak_ptr<symbol_scope_rep> (parent); + m_parent = std::weak_ptr<symbol_scope::symbol_scope_rep> (parent); } void -symbol_scope_rep::set_primary_parent (const std::shared_ptr<symbol_scope_rep>& parent) +symbol_scope::symbol_scope_rep::set_primary_parent (const std::shared_ptr<symbol_scope::symbol_scope_rep>& parent) { - m_primary_parent = std::weak_ptr<symbol_scope_rep> (parent); + m_primary_parent = std::weak_ptr<symbol_scope::symbol_scope_rep> (parent); } void -symbol_scope_rep::cache_dir_name (const std::string& name) +symbol_scope::symbol_scope_rep::cache_dir_name (const std::string& name) { m_dir_name = sys::canonicalize_file_name (name); } bool -symbol_scope_rep::is_relative (const std::shared_ptr<symbol_scope_rep>& scope) const +symbol_scope::symbol_scope_rep::is_relative (const std::shared_ptr<symbol_scope::symbol_scope_rep>& scope) const { if (is_nested ()) { @@ -276,7 +276,7 @@ } void -symbol_scope_rep::mark_as_variable (const std::string& nm) +symbol_scope::symbol_scope_rep::mark_as_variable (const std::string& nm) { table_iterator p = m_symbols.find (nm); @@ -285,14 +285,14 @@ } void -symbol_scope_rep::mark_as_variables (const std::list<std::string>& lst) +symbol_scope::symbol_scope_rep::mark_as_variables (const std::list<std::string>& lst) { for (const auto& nm : lst) mark_as_variable (nm); } bool -symbol_scope_rep::is_variable (const std::string& nm) const +symbol_scope::symbol_scope_rep::is_variable (const std::string& nm) const { table_const_iterator p = m_symbols.find (nm); @@ -312,7 +312,7 @@ } void -symbol_scope_rep::update_nest () +symbol_scope::symbol_scope_rep::update_nest () { auto t_parent = m_parent.lock (); @@ -344,9 +344,9 @@ } bool -symbol_scope_rep::look_nonlocal (const std::string& name, - std::size_t offset, - symbol_record& result) +symbol_scope::symbol_scope_rep::look_nonlocal (const std::string& name, + std::size_t offset, + symbol_record& result) { offset++; @@ -388,7 +388,7 @@ if (is_primary_fcn_scope ()) return m_rep->localfunctions (); - std::shared_ptr<symbol_scope_rep> ppsr + std::shared_ptr<symbol_scope::symbol_scope_rep> ppsr = m_rep->primary_parent_scope_rep (); if (! ppsr)
--- a/libinterp/corefcn/symscope.h Thu Apr 04 22:50:56 2024 -0400 +++ b/libinterp/corefcn/symscope.h Sun Mar 31 13:46:25 2024 +0200 @@ -48,327 +48,327 @@ OCTAVE_BEGIN_NAMESPACE(octave) -class symbol_scope; - -class symbol_scope_rep - : public std::enable_shared_from_this<symbol_scope_rep> +class OCTINTERP_API symbol_scope { -public: - - typedef std::map<std::string, symbol_record>::const_iterator - table_const_iterator; - typedef std::map<std::string, symbol_record>::iterator - table_iterator; - - typedef std::map<std::string, octave_value>::const_iterator - subfunctions_const_iterator; - typedef std::map<std::string, octave_value>::iterator - subfunctions_iterator; - - symbol_scope_rep (const std::string& name = "", bool add_ans = true) - : m_name (name), m_symbols (), m_subfunctions (), - m_persistent_values (), m_code (nullptr), m_fcn_name (), - m_fcn_file_name (), m_dir_name (), m_parent (), - m_primary_parent (), m_children (), m_nesting_depth (0), - m_is_static (false), m_is_primary_fcn_scope (false) - { - // Most scopes have ans as the first symbol, initially undefined. - if (add_ans) - insert_local ("ans"); - } - - OCTAVE_DISABLE_COPY_MOVE (symbol_scope_rep) - - ~symbol_scope_rep () = default; - - std::size_t num_symbols () const { return m_symbols.size (); } - - // Simply inserts symbol. No non-local searching. - - symbol_record insert_local (const std::string& name); - - void insert_symbol_record (symbol_record& sr); - - bool is_nested () const { return m_nesting_depth > 0; } - - std::size_t nesting_depth () const { return m_nesting_depth; } - - void set_nesting_depth (std::size_t depth) { m_nesting_depth = depth; } - - bool is_parent () const { return ! m_children.empty (); } - - bool is_static () const { return m_is_static; } - - void mark_static () { m_is_static = true; } - - std::shared_ptr<symbol_scope_rep> parent_scope_rep () const - { - return m_parent.lock (); - } - - std::shared_ptr<symbol_scope_rep> primary_parent_scope_rep () const - { - return m_primary_parent.lock (); - } - - std::shared_ptr<symbol_scope_rep> dup () const - { - std::shared_ptr<symbol_scope_rep> new_sid - = std::shared_ptr<symbol_scope_rep> (new symbol_scope_rep (m_name)); - - for (const auto& nm_sr : m_symbols) - new_sid->m_symbols[nm_sr.first] = nm_sr.second.dup (); - - new_sid->m_subfunctions = m_subfunctions; - new_sid->m_persistent_values = m_persistent_values; - new_sid->m_subfunction_names = m_subfunction_names; - new_sid->m_code = m_code; - new_sid->m_fcn_name = m_fcn_name; - new_sid->m_fcn_file_name = m_fcn_file_name; - new_sid->m_dir_name = m_dir_name; - new_sid->m_parent = m_parent; - new_sid->m_primary_parent = m_primary_parent; - new_sid->m_children = m_children; - new_sid->m_nesting_depth = m_nesting_depth; - new_sid->m_is_static = m_is_static; - new_sid->m_is_primary_fcn_scope = m_is_primary_fcn_scope; - - return new_sid; - } - - octave_value& persistent_varref (std::size_t data_offset) - { - return m_persistent_values[data_offset]; - } - - octave_value persistent_varval (std::size_t data_offset) const - { - auto p = m_persistent_values.find (data_offset); - - return p == m_persistent_values.end () ? octave_value () : p->second; - } - - symbol_record find_symbol (const std::string& name) - { - auto p = m_symbols.find (name); - - if (p == m_symbols.end ()) - return insert (name); - else - return p->second; - } - - symbol_record lookup_symbol (const std::string& name) const - { - auto p = m_symbols.find (name); - - return p == m_symbols.end () ? symbol_record () : p->second; - } - - symbol_record insert (const std::string& name); - - void rename (const std::string& old_name, const std::string& new_name) - { - auto p = m_symbols.find (old_name); - - if (p != m_symbols.end ()) - { - symbol_record sr = p->second; - - sr.rename (new_name); - - m_symbols.erase (p); - - m_symbols[new_name] = sr; - } - } - - void install_subfunction (const std::string& name, - const octave_value& fval) - { - m_subfunctions[name] = fval; - } - - void install_nestfunction (const std::string& name, - const octave_value& fval, - const symbol_scope& fcn_scope) - { - m_subfunctions[name] = fval; - - m_children.push_back (fcn_scope); - } - - octave_value find_subfunction (const std::string& name) const; - - void lock_subfunctions () - { - for (auto& nm_sf : m_subfunctions) - nm_sf.second.lock (); - } - - void unlock_subfunctions () - { - for (auto& nm_sf : m_subfunctions) - nm_sf.second.unlock (); - } - - // Pairs of name, function objects. - std::map<std::string, octave_value> subfunctions () const - { - return m_subfunctions; - } - - void erase_subfunctions () - { - m_subfunctions.clear (); - } - - void mark_subfunctions_in_scope_as_private (const std::string& class_name); - - bool has_subfunctions () const - { - return ! m_subfunction_names.empty (); - } - - void stash_subfunction_names (const std::list<std::string>& names) - { - m_subfunction_names = names; - } - - std::list<std::string> subfunction_names () const - { - return m_subfunction_names; - } - - std::list<octave_value> localfunctions () const; - - octave_value dump () const; - - std::string name () const { return m_name; } - - void cache_name (const std::string& name) { m_name = name; } - - std::string fcn_name () const { return m_fcn_name; } - - void cache_fcn_name (const std::string& name) { m_fcn_name = name; } - - std::list<std::string> parent_fcn_names () const; - - octave_user_code * user_code () const { return m_code; } - - void set_user_code (octave_user_code *code) { m_code = code; } - - void set_parent (const std::shared_ptr<symbol_scope_rep>& parent); - - void set_primary_parent (const std::shared_ptr<symbol_scope_rep>& parent); - - void cache_fcn_file_name (const std::string& name) - { - m_fcn_file_name = name; - } - - std::string fcn_file_name () const { return m_fcn_file_name; } - - void cache_dir_name (const std::string& name); - - std::string dir_name () const { return m_dir_name; } - - void mark_primary_fcn_scope () { m_is_primary_fcn_scope = true; } - - bool is_primary_fcn_scope () const { return m_is_primary_fcn_scope; } - - bool is_relative (const std::shared_ptr<symbol_scope_rep>& scope) const; - - void mark_as_variable (const std::string& nm); - void mark_as_variables (const std::list<std::string>& lst); - - bool is_variable (const std::string& nm) const; - - void update_nest (); - - bool look_nonlocal (const std::string& name, std::size_t offset, - symbol_record& result); - - octave_value dump_symbols_map () const; - - const std::map<std::string, symbol_record>& symbols () const - { - return m_symbols; - } - - std::map<std::string, symbol_record>& symbols () - { - return m_symbols; - } - - std::list<symbol_record> symbol_list () const; - private: - //! Name for this scope (usually the corresponding filename of the - //! function corresponding to the scope). + class symbol_scope_rep + : public std::enable_shared_from_this<symbol_scope_rep> + { + public: + + typedef std::map<std::string, symbol_record>::const_iterator + table_const_iterator; + typedef std::map<std::string, symbol_record>::iterator + table_iterator; + + typedef std::map<std::string, octave_value>::const_iterator + subfunctions_const_iterator; + typedef std::map<std::string, octave_value>::iterator + subfunctions_iterator; - std::string m_name; + symbol_scope_rep (const std::string& name = "", bool add_ans = true) + : m_name (name), m_symbols (), m_subfunctions (), + m_persistent_values (), m_code (nullptr), m_fcn_name (), + m_fcn_file_name (), m_dir_name (), m_parent (), + m_primary_parent (), m_children (), m_nesting_depth (0), + m_is_static (false), m_is_primary_fcn_scope (false) + { + // Most scopes have ans as the first symbol, initially undefined. + if (add_ans) + insert_local ("ans"); + } + + OCTAVE_DISABLE_COPY_MOVE (symbol_scope_rep) + + ~symbol_scope_rep () = default; + + std::size_t num_symbols () const { return m_symbols.size (); } - //! Map from symbol names to symbol info. + // Simply inserts symbol. No non-local searching. + + symbol_record insert_local (const std::string& name); + + void insert_symbol_record (symbol_record& sr); + + bool is_nested () const { return m_nesting_depth > 0; } - std::map<std::string, symbol_record> m_symbols; + std::size_t nesting_depth () const { return m_nesting_depth; } + + void set_nesting_depth (std::size_t depth) { m_nesting_depth = depth; } + + bool is_parent () const { return ! m_children.empty (); } + + bool is_static () const { return m_is_static; } + + void mark_static () { m_is_static = true; } - //! Map from symbol names to subfunctions. + std::shared_ptr<symbol_scope_rep> parent_scope_rep () const + { + return m_parent.lock (); + } - std::map<std::string, octave_value> m_subfunctions; + std::shared_ptr<symbol_scope_rep> primary_parent_scope_rep () const + { + return m_primary_parent.lock (); + } + + std::shared_ptr<symbol_scope_rep> dup () const + { + std::shared_ptr<symbol_scope_rep> new_sid + = std::shared_ptr<symbol_scope_rep> (new symbol_scope_rep (m_name)); + + for (const auto& nm_sr : m_symbols) + new_sid->m_symbols[nm_sr.first] = nm_sr.second.dup (); - //! Map from data offset to persistent values in this scope. - std::map<std::size_t, octave_value> m_persistent_values; + new_sid->m_subfunctions = m_subfunctions; + new_sid->m_persistent_values = m_persistent_values; + new_sid->m_subfunction_names = m_subfunction_names; + new_sid->m_code = m_code; + new_sid->m_fcn_name = m_fcn_name; + new_sid->m_fcn_file_name = m_fcn_file_name; + new_sid->m_dir_name = m_dir_name; + new_sid->m_parent = m_parent; + new_sid->m_primary_parent = m_primary_parent; + new_sid->m_children = m_children; + new_sid->m_nesting_depth = m_nesting_depth; + new_sid->m_is_static = m_is_static; + new_sid->m_is_primary_fcn_scope = m_is_primary_fcn_scope; + + return new_sid; + } - //! The list of subfunctions (if any) in the order they appear in - //! the function file. + octave_value& persistent_varref (std::size_t data_offset) + { + return m_persistent_values[data_offset]; + } + + octave_value persistent_varval (std::size_t data_offset) const + { + auto p = m_persistent_values.find (data_offset); + + return p == m_persistent_values.end () ? octave_value () : p->second; + } - std::list<std::string> m_subfunction_names; + symbol_record find_symbol (const std::string& name) + { + auto p = m_symbols.find (name); + + if (p == m_symbols.end ()) + return insert (name); + else + return p->second; + } + + symbol_record lookup_symbol (const std::string& name) const + { + auto p = m_symbols.find (name); - //! The associated user code (may be null). + return p == m_symbols.end () ? symbol_record () : p->second; + } + + symbol_record insert (const std::string& name); + + void rename (const std::string& old_name, const std::string& new_name) + { + auto p = m_symbols.find (old_name); - octave_user_code *m_code; + if (p != m_symbols.end ()) + { + symbol_record sr = p->second; + + sr.rename (new_name); + + m_symbols.erase (p); + + m_symbols[new_name] = sr; + } + } - //! Simple name of the function corresponding to this scope. + void install_subfunction (const std::string& name, + const octave_value& fval) + { + m_subfunctions[name] = fval; + } - std::string m_fcn_name; + void install_nestfunction (const std::string& name, + const octave_value& fval, + const symbol_scope& fcn_scope) + { + m_subfunctions[name] = fval; - //! The file name associated with m_code. + m_children.push_back (fcn_scope); + } + + octave_value find_subfunction (const std::string& name) const; + + void lock_subfunctions () + { + for (auto& nm_sf : m_subfunctions) + nm_sf.second.lock (); + } - std::string m_fcn_file_name; + void unlock_subfunctions () + { + for (auto& nm_sf : m_subfunctions) + nm_sf.second.unlock (); + } - //! The directory associated with m_code. + // Pairs of name, function objects. + std::map<std::string, octave_value> subfunctions () const + { + return m_subfunctions; + } + + void erase_subfunctions () + { + m_subfunctions.clear (); + } + + void mark_subfunctions_in_scope_as_private (const std::string& class_name); - std::string m_dir_name; + bool has_subfunctions () const + { + return ! m_subfunction_names.empty (); + } + + void stash_subfunction_names (const std::list<std::string>& names) + { + m_subfunction_names = names; + } - //! Parent of nested function (may be null). + std::list<std::string> subfunction_names () const + { + return m_subfunction_names; + } + + std::list<octave_value> localfunctions () const; + + octave_value dump () const; + + std::string name () const { return m_name; } - std::weak_ptr<symbol_scope_rep> m_parent; + void cache_name (const std::string& name) { m_name = name; } + + std::string fcn_name () const { return m_fcn_name; } + + void cache_fcn_name (const std::string& name) { m_fcn_name = name; } + + std::list<std::string> parent_fcn_names () const; + + octave_user_code * user_code () const { return m_code; } + + void set_user_code (octave_user_code *code) { m_code = code; } + + void set_parent (const std::shared_ptr<symbol_scope_rep>& parent); + + void set_primary_parent (const std::shared_ptr<symbol_scope_rep>& parent); - //! Primary (top) parent of nested function (may be null). Used - //! to determine whether two nested functions are related. + void cache_fcn_file_name (const std::string& name) + { + m_fcn_file_name = name; + } + + std::string fcn_file_name () const { return m_fcn_file_name; } + + void cache_dir_name (const std::string& name); + + std::string dir_name () const { return m_dir_name; } - std::weak_ptr<symbol_scope_rep> m_primary_parent; + void mark_primary_fcn_scope () { m_is_primary_fcn_scope = true; } + + bool is_primary_fcn_scope () const { return m_is_primary_fcn_scope; } + + bool is_relative (const std::shared_ptr<symbol_scope_rep>& scope) const; - //! Child nested functions. + void mark_as_variable (const std::string& nm); + void mark_as_variables (const std::list<std::string>& lst); + + bool is_variable (const std::string& nm) const; + + void update_nest (); - std::vector<symbol_scope> m_children; + bool look_nonlocal (const std::string& name, std::size_t offset, + symbol_record& result); + + octave_value dump_symbols_map () const; - //! If true, then this scope belongs to a nested function. + const std::map<std::string, symbol_record>& symbols () const + { + return m_symbols; + } + + std::map<std::string, symbol_record>& symbols () + { + return m_symbols; + } + + std::list<symbol_record> symbol_list () const; + + private: - std::size_t m_nesting_depth; + //! Name for this scope (usually the corresponding filename of the + //! function corresponding to the scope). + + std::string m_name; + + //! Map from symbol names to symbol info. + + std::map<std::string, symbol_record> m_symbols; - //! If true then no variables can be added. + //! Map from symbol names to subfunctions. + + std::map<std::string, octave_value> m_subfunctions; + + //! Map from data offset to persistent values in this scope. + std::map<std::size_t, octave_value> m_persistent_values; + + //! The list of subfunctions (if any) in the order they appear in + //! the function file. + + std::list<std::string> m_subfunction_names; - bool m_is_static; + //! The associated user code (may be null). + + octave_user_code *m_code; + + //! Simple name of the function corresponding to this scope. + + std::string m_fcn_name; + + //! The file name associated with m_code. + + std::string m_fcn_file_name; + + //! The directory associated with m_code. + + std::string m_dir_name; + + //! Parent of nested function (may be null). + + std::weak_ptr<symbol_scope_rep> m_parent; - //! If true, this is the scope of a primary function. - bool m_is_primary_fcn_scope; -}; + //! Primary (top) parent of nested function (may be null). Used + //! to determine whether two nested functions are related. + + std::weak_ptr<symbol_scope_rep> m_primary_parent; + + //! Child nested functions. + + std::vector<symbol_scope> m_children; + + //! If true, then this scope belongs to a nested function. -class symbol_scope -{ + std::size_t m_nesting_depth; + + //! If true then no variables can be added. + + bool m_is_static; + + //! If true, this is the scope of a primary function. + bool m_is_primary_fcn_scope; + }; + public: symbol_scope () = delete;