-
Notifications
You must be signed in to change notification settings - Fork 42
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Segmentation Fault when trying to access an object's property #17
Comments
Sorry, that was the wrong stacktrace, although it has some interesting info actually, so I am not going to get rid of it. Here is the one for accessing the segmentation fault
|
Neither seems to make sense: the access of a data member would be a pointer lookup, not a function call (as each of the tracebacks show). Is it not the |
Actually yes that is true. At the interactive prompt if I just type >>> instance.body.name
<cppyy.gbl.std.basic_string_view<char> object at 0x55621d8ef398> But if I try to print it or convert it to a string or otherwise access the contents, that is where it crashes. I have used those conversions on other string_views without issue previously. >>> instance.name
<cppyy.gbl.std.basic_string_view<char> object at 0x55621d8ef348>
>>> str(instance.name)
'foo'
''' |
Most likely cause is then that the Long chains of data member accesses should be okay, as cppyy places lifelines if the accessed member falls inside the instance its accessed in. Nevertheless, can you see whether this:
makes a difference? I'm thinking that there is a temporary |
|
It might be an issue in the library. I tried creating the same code in C++ and I got a "terminate called without an active exception. Aborted" error at about the same point. I am talking with the library maintainer to get his thoughts on the issue. |
Slightly unrelated, but possibly not - how does cppyy handle custom class iterators? The iterator object holds a pointer to the class object, so would I just need to cast to the original type to get the underlying type? In C++, I am able to do for (auto& member: elem.members()) { } Where /// Gets an iterator to the members contained in the scope.
iterator_range<iterator> members() const {
return { firstMember, nullptr };
} But on the Python side, I don't think I can call class iterator : public iterator_facade<iterator, std::forward_iterator_tag, const Symbol> {
public:
iterator() : current(nullptr) {}
iterator(const Symbol* firstSymbol) : current(firstSymbol) {}
iterator(const iterator& other) : current(other.current) {}
iterator& operator=(const iterator& other) {
current = other.current;
return *this;
}
bool operator==(const iterator& other) const { return current == other.current; }
const Symbol& operator*() const { return *current; }
const Symbol& operator*() { return *current; }
iterator& operator++();
iterator operator++(int) {
iterator tmp = *this;
++(*this);
return tmp;
}
private:
const Symbol* current;
}; |
One more segfault, for record keeping segmentation fault
|
According to the cppyy docs, this should work, right?: >>> import cppyy.ll
>>> cppyy.set_debug()
>>> cppyy.ll.static_cast['const void*'](body)
input_line_105:7:41: error: cannot cast from type 'slang::InstanceBodySymbol' to pointer type 'const void *'
T cppyy_static_cast(U val) { return static_cast<T>(val); }
^~~~~~~~~~~~~~~~~~~
note: in instantiation of function template specialization '__cppyy_internal::cppyy_static_cast<const void *, slang::InstanceBodySymbol>' requested here
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: Could not find "cppyy_static_cast<const void*>" (set cppyy.set_debug() for C++ errors):
Failed to instantiate "cppyy_static_cast<const void*>(slang::InstanceBodySymbol&)" I am trying to walk further into the library and see if I can figure out the exact line that is failing. |
For the iterator to work, the code is expecting That cast fails b/c you can't cast a reference (default choice for object argument in templates if no other information is available) to a
But I think what you really want is simply:
|
>>> comp.getRoot().members()
<cppyy.gbl.slang.iterator_range<slang::Scope::iterator> object at 0x55e973ff8540>
>>> comp.getRoot().members()[0]
<cppyy.gbl.slang.Scope.iterator object at 0x55e9747f2f40>
>>> comp.getRoot().members()[1]
<cppyy.gbl.slang.Scope.iterator object at 0x55e9744242f0>
>>> comp.getRoot().members()[2]
<cppyy.gbl.slang.Scope.iterator object at 0x55e9746812d0>
>>> comp.getRoot().members().size()
2
>>> for x in comp.getRoot().members():
... print(x)
...
>>>
>>> comp.getRoot().members().begin()
<cppyy.gbl.slang.Scope.iterator object at 0x55e9747e8f20>
>>> comp.getRoot().members().end()
<cppyy.gbl.slang.Scope.iterator object at 0x55e97436a1c0> Thanks for the cast instructions, they worked, although in the end I think I was actually able to pass the object directly and it handled the conversion, the function just didn't return anything usable. |
Okay, I had a bug in my C++ version but after getting that resolved, it is working fine on that side, so there is something wrong in the conversion to Python I think. Here are a couple snippets for comparison: auto& root = comp.getRoot();
auto& elem = root.members()[1]->as<InstanceSymbol>();
auto& body = elem.body;
std::cout << body.name << '\n'; // outputs 'foo' root = comp.getRoot()
elem = bind_object(root.members()[1].__deref__(), InstanceSymbol)
body = elem.body
print(body.name) # segmentation fault Both of these are created with parallel setup code preceding these lines, and up to accessing the properties of body, everything appears to be the same. segmentation fault
|
For the iterator container, since it returns iterators, instead of their pointees, that seems the correct behavior. Note that dereferencing is automatic if you access something on the iterator that does not exist on it but does exit on the pointee. For the crash, below is a standalone reproducer. The problem is purely to do with having a
|
Awesome, it is nice knowing there is an identified issue. So is this something that needs to be changed in the C++, or in my python code? Or is it a bug in cppyy? I am not familiar with why this would cause an incorrect address so I apologize if the solution might be obvious. |
It's a bug in cppyy. It has an easy fix, but that breaks some other behavior that relies on things being the way they are. The two uses seem incompatible: when passing an object by reference through JITed code, it is a single pointer ( |
Okay, I will wait for resolution then. |
This should do it: |
It works! Thanks a lot, I will keep moving forward and hopefully don't hit any more issues. How did you identify the problem? Just curious. Also, to close out the iterator topic, since it is a container, that means I won't be able to do a |
I finally had the time to click on the link above. The cppyy tests are extensive, but there was no test for const-ref data members, so that was a logical thing to try. After all: what isn't tested, is broken. I'm not understanding why the iterator loop doesn't work. The code in Pythonize.cxx to figure this out is a bit elaborate: there are a couple of things that need to cooperate for the iterator protocol in Python to work, and somehow this case fails at least one of them. What I think is different here than otherwise, is that the result of |
Okay thanks. That is not as big of an issue since I have a reasonable workaround, but for the sake of the project I assume it would be a good fix to have eventually. Thanks for the hard work, this is an extremely impressive tool. |
Fixed in repo: wlav/CPyCppyy@d0bc640 It's indeed only for this particular case. |
Awesome 2-for-1, thanks! |
I am working with the MikePopoloski/slang library. I am trying to walk an AST generated after compiling some code with it. If I call the built-in functions, it is able to walk the tree completely, so I know all the data is there and able to be referenced. When I attempt to walk the tree manually, I get a couple layers deep before hitting a segfault when attempting to check a simple string_view attached to an object. Unfortunately, creating a standalone reproducer of this would be challenging.
https://github.com/MikePopoloski/slang/blob/3ae64c22f38ce0797b96c41041d1f75c00bf0377/include/slang/symbols/InstanceSymbols.h#L99
This is the object I eventually crash on. The hierarchy would be:
Compilation > DesignTree > Instances[0] > InstanceSymbol > InstancyBodySymbol
Then, when I try to call
str(body.name)
, I get a stack trace. Most of the information looks pretty generic to me, but here it is anyway:segmentation fault
Debian 10, python 3.9.7 with debug options installed, cppyy 2.1.0
If you are feeling up to installing slang, I would be happy to assist and provide a reproducer. Otherwise, any help would be appreciated.
The text was updated successfully, but these errors were encountered: