Cling: Dynamic Scopes
The Problem
The objects from the current directory (gDirectory) are injected into a magic scope that is available to CINT:
Important constrain: To not break old code we need to continue to support this. Of course the code is invalid C++ and thus cannot be parsed by clang. Upon clang’s Sema complaining about undeclared identifiers we need to convert it into proper C++.
Use Cases
1. Simple use case:
2. Parameters
3. Function Overloading
An additional complication is function overload resolution required in this example:
N. Can we have smth else?
Solutions
Escaping to Late Evaluation
In use case 1: the code can be converted to:
This is now valid C++; the code hpx->Draw()
will be evaluated during runtime, when we
know all the necessary information. In this case we have:
In use case number 2: we need to pass the variable to the interpreter as well. We need to introduce a Context
In use case number 3: we don’t know the type of obj at compile time, we don’t know which
overload of Func()
to use.
Here we have several options:
- Let Cling decide which overload to use - We could pass the list of candidates that Sema found during overload resolution to the escaped interpreter, probably including a copy of the identifier table. This would require changes in Sema, because the escaped Sema needs to take an external identifier table and the candidates into account;
- Assume void* - One could argue that this is a rare case. We know that unknown identifiers
have to be pointers; we could simply select the void* overload of
Func()
, i.e. claim that obj is avoid*
; - Refuse the overloads - If we have problems determining the proper overload. By refusing to accept multiple overloads we can simplify the situation;
- Discontinue Support - We could detect the case of multiple overload candidates and issue an error. This should be in case no other options are possible.
The page is based on ClingDynamicScope at tWiki