ExternalSymbol¶
The ExternalSymbol is a symbol
node that represents a symbol declared in another module.
Declaration¶
Syntax¶
ExternalSymbol(symbol_table parent_symtab, identifier name,
symbol external, identifier module_name, identifier* scope_names,
identifier original_name, access access)
Arguments¶
Argument Name |
Denotes |
---|---|
|
the parent symbol table that contains the external symbol |
|
the name of the external symbol in the current symbol table |
|
pointer to the actual symbol definition |
|
the name of the module the symbol is in |
|
a list of names if the symbol is in a nested symbol table. For example if it is a local variable in a function |
|
the name of the symbol in the external symbol table |
|
access type |
Return values¶
None.
Description¶
ExternalSymbol represents symbols that cannot be looked up in the current scoped symbol table. As an example, if a variable is defined in a module, but used in a nested subroutine, that is not an external symbol because it can be resolved in the current symbol table (nested subroutine) by following the parents. However if a symbol is used from a different module, then it is an external symbol, because usual symbol resolution by going to the parents will not find the definition.
The ExternalSymbol
is the only way to reference a symbol that cannot be accessed in the scoped symbol table by visiting the parents. There is a special handling for it in the serialization and deserialization: the external
member is not serialized (since it is a pointer) and in deserialization the pointer is reconstructed from the original_name
and scope_names
.
The scope_names
contains the names of the external symbol table starting from the top how to get to the symbol. This approach allows to reference any nested symbol (such as a local variable in a function in a module). However, we might later change the design to only allow referencing top level module entities.
One can think of the ExternalSymbol
as the « import » statement in Python, or the « use » statement in Fortran.
Types¶
Examples¶
module module_num
integer :: my_num = 5
end module
program main
use module_num
print *, my_num
end program
ASR:
(TranslationUnit
(SymbolTable
1
{
main:
(Program
(SymbolTable
3
{
my_num:
(ExternalSymbol
3
my_num
2 my_num
module_num
[]
my_num
Public
)
})
main
[module_num]
[(Print
()
[(Var 3 my_num)]
()
()
)]
),
module_num:
(Module
(SymbolTable
2
{
my_num:
(Variable
2
my_num
[]
Local
(IntegerConstant 5 (Integer 4 []))
()
Save
(Integer 4 [])
Source
Public
Required
.false.
)
})
module_num
[]
.false.
.false.
)
})
[]
)