| Summary: | Invalid QString conversion in TreeModel.data.fieldname | ||
|---|---|---|---|
| Product: | [Unmaintained] rust-qt-binding-generator | Reporter: | kdebuac.rhn |
| Component: | general | Assignee: | Jos van den Oever <jos> |
| Status: | RESOLVED FIXED | ||
| Severity: | normal | ||
| Priority: | NOR | ||
| Version First Reported In: | unspecified | ||
| Target Milestone: | --- | ||
| Platform: | Other | ||
| OS: | Linux | ||
| Latest Commit: | Version Fixed/Implemented In: | ||
| Sentry Crash Report: | |||
| Attachments: | Workaround | ||
Created attachment 111974 [details]
Workaround
This works around the issue, and fixes failing test cases. Untested with rustByValue.
I'm not sure if the patch is actually the right place to tackle this problem.
I would try to fix the behaviour of "rustByValue", but the way it's used seems opposite to me and I dare not touch it:
{
let data = (&*ptr).%3();
set(p, %5data.into());
}
)").arg(o.name, base, snakeCase(p.name), p.type.name,
p.rustByValue ?"&" :"");
In the above snippet, the generated code will use a *reference* &data.into() iff rustByValue is *true*. Is this reversed?
This issue is fixed as of 57d557378ee629496b4a6afc58022f0677cdff06. The struct qstring_t is not present anymore. QString data is now passed as two pieces of data: the pointer to the characters and the length. |
Trying to implement an object backing a tree model, I found that QString contents of a requested field (Bookmarks::data() -> String) were passed in an invalid way across the C/C++ boundary. The issue was that interface::QString was converted wrong into qstring_t, with mismatched pointer dereferences. The object in question: "Bookmarks": { "type": "Tree", "itemProperties": { "type_": { "type": "quint32", "roles": [ ["toolTip"] ] }, "name": { "type": "QString", "roles": [ ["display"] ] }, "count": { "type": "quint32", "roles": [ [], ["display"] ] } } } The affected field was `name`, thus the invalid function to read it: #[no_mangle] pub unsafe extern "C" fn bookmarks_data_name( ptr: *const Bookmarks, item: usize, d: *mut c_void, set: fn(*mut c_void, QString), ) { let data = (&*ptr).name(item); set(d, (data).into()); } The fixed function: #[no_mangle] pub unsafe extern "C" fn bookmarks_data_name( ptr: *const Bookmarks, item: usize, d: *mut c_void, set: fn(*mut c_void, &QString), // added pointer ) { let data = (&*ptr).name(item); let qs = (data).into(); set(d, &qs); // should be safe; a copy is made on the other side } The code to generate this is around line 360 in src/rust.cpp. The other side is line 932 in src/cpp.cpp