Hi I'm doing the PyPy backend for Cython Summer of Code project and I would like to know if there is a way of getting the AST Node responsible for the declaration of a variable. For example : def func(): def func(): pass func() In the situation where I'm currently traversing the function call, I would like to get the function declaration node. Is there already something to do that ? Cheers Romain
Romain Guillebert, 23.05.2011 20:33:
I'm doing the PyPy backend for Cython Summer of Code project and I would like to know if there is a way of getting the AST Node responsible for the declaration of a variable.
For example :
def func(): def func(): pass
func()
In the situation where I'm currently traversing the function call, I would like to get the function declaration node. Is there already something to do that ?
What for? What kind of information do you need from it? In Cython, the metadata about a name is stored in its symbol table entry. The call to "func" is a SimpleCallNode that holds a NameNode which has an "entry" attribute. The entry knows the name, type, signature, etc. of the function that is being called. Note, however, that you need to run both the "analyse declarations" step and the "analyse types/expression" step to figure out all information about the name. The declaration analysis will add the definition of "func" to the symbol table, so you can look it up ("env.lookup('func')") from that point on. Does that help? Stefan
On Tue, May 24, 2011 at 06:56:19AM +0200, Stefan Behnel wrote:
Romain Guillebert, 23.05.2011 20:33:
I'm doing the PyPy backend for Cython Summer of Code project and I would like to know if there is a way of getting the AST Node responsible for the declaration of a variable.
For example :
def func(): def func(): pass
func()
In the situation where I'm currently traversing the function call, I would like to get the function declaration node. Is there already something to do that ?
What for? What kind of information do you need from it?
In Cython, the metadata about a name is stored in its symbol table entry. The call to "func" is a SimpleCallNode that holds a NameNode which has an "entry" attribute. The entry knows the name, type, signature, etc. of the function that is being called.
Note, however, that you need to run both the "analyse declarations" step and the "analyse types/expression" step to figure out all information about the name. The declaration analysis will add the definition of "func" to the symbol table, so you can look it up ("env.lookup('func')") from that point on.
Does that help?
Stefan
I want to generate standard python function from "cdef extern from" function, but I need to annotate these function as they may require a special treatment (for passing value by reference), also, I may turn C macros into a call to a C function returning the macro itself. cdef extern from "stdio.h": cdef int BUFSIZ Will be turned into : def get_BUFSIZ(): # whatever So I need to turn every access to BUFSIZ into a function call. Cheers Romain
Romain Guillebert, 24.05.2011 19:22:
On Tue, May 24, 2011 at 06:56:19AM +0200, Stefan Behnel wrote:
Romain Guillebert, 23.05.2011 20:33:
I'm doing the PyPy backend for Cython Summer of Code project and I would like to know if there is a way of getting the AST Node responsible for the declaration of a variable.
For example :
def func(): def func(): pass
func()
In the situation where I'm currently traversing the function call, I would like to get the function declaration node. Is there already something to do that ?
What for? What kind of information do you need from it?
In Cython, the metadata about a name is stored in its symbol table entry. The call to "func" is a SimpleCallNode that holds a NameNode which has an "entry" attribute. The entry knows the name, type, signature, etc. of the function that is being called.
Note, however, that you need to run both the "analyse declarations" step and the "analyse types/expression" step to figure out all information about the name. The declaration analysis will add the definition of "func" to the symbol table, so you can look it up ("env.lookup('func')") from that point on.
Does that help?
Stefan
I want to generate standard python function from "cdef extern from" function, but I need to annotate these function as they may require a special treatment (for passing value by reference), also, I may turn C macros into a call to a C function returning the macro itself.
cdef extern from "stdio.h": cdef int BUFSIZ
Will be turned into :
def get_BUFSIZ(): # whatever
So I need to turn every access to BUFSIZ into a function call.
Sounds to me like you should attach the necessary information to the symbol table entry when analysing he "external" declaration. We currently store a "cname", so adding something like a property name or accessor information should fit your use case. We may want to reserve a separate namespace for Python output related information, though. Maybe something like "entry.pybackend.*"? Also, we considered having module level properties at some point. That may fall into the same bucket. What should happen for cimported declarations? Will they be handled in the same way as internally defined "external" declarations? I guess so, even if they may be shared between modules. Stefan
Sounds to me like you should attach the necessary information to the symbol table entry when analysing he "external" declaration.
That's what I wanted to do that's why I asked how I could access the external declaration node
We currently store a "cname", so adding something like a property name or accessor information should fit your use case. We may want to reserve a separate namespace for Python output related information, though. Maybe something like "entry.pybackend.*"?
This would be a clean way to do it
Also, we considered having module level properties at some point. That may fall into the same bucket.
Writing a transformation for that should be relatively straightforward.
What should happen for cimported declarations? Will they be handled in the same way as internally defined "external" declarations? I guess so, even if they may be shared between modules.
There's 2 possibilities I think : - For each file we generate the wrapping functions - For each pxd file, generate a file containing the wrapping functions Romain
Romain Guillebert, 24.05.2011 22:36:
Sounds to me like you should attach the necessary information to the symbol table entry when analysing he "external" declaration.
That's what I wanted to do that's why I asked how I could access the external declaration node
Then you should have asked that in the first place. There are declarator nodes for external declarations. You can traverse them just like any other node. However, they get removed after declaration analysis, so you need to have extracted all required information at that point. Maybe you can just replace them by new nodes that implement the C access for a specific external declaration?
We currently store a "cname", so adding something like a property name or accessor information should fit your use case. We may want to reserve a separate namespace for Python output related information, though. Maybe something like "entry.pybackend.*"?
This would be a clean way to do it
Also, we considered having module level properties at some point. That may fall into the same bucket.
Writing a transformation for that should be relatively straightforward.
Well, for the C code that Cython generates, it means that we first need to implement our own module type in order to support properties at all...
What should happen for cimported declarations? Will they be handled in the same way as internally defined "external" declarations? I guess so, even if they may be shared between modules.
There's 2 possibilities I think : - For each file we generate the wrapping functions - For each pxd file, generate a file containing the wrapping functions
Right. I don't see a problem with any of the two, nor a major advantage on either side. The first sounds a bit simpler. Stefan
participants (2)
-
Romain Guillebert -
Stefan Behnel