Skip to content
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

Add support for multiple out params #626

Open
wants to merge 7 commits into
base: master
Choose a base branch
from

Conversation

dfb
Copy link
Contributor

@dfb dfb commented Dec 12, 2018

See issue #621 - this patch makes it so that Python can properly call C++ or BP methods with one or more output parameters as well as C++ methods that have both output parameters and a return value. Further, it makes it so that in Python you can override and implement methods that have both return values and output parameters. A side effect of this patch is that so far it appears to have fixed #622.

Note that when combining out params and a return value, the return value needs to come last in the type annotation info, e.g. given a C++ base class method like this:

    UFUNCTION(BlueprintCallable, BlueprintNativeEvent) float Func(int i, int& oi);

you'd implement it in Python like this:

    def Func(self, i:int) -> (int, float):
        return 5, 12.34 # 5 is the out param, 12.34 is the return value

In terms of lines of code, the biggest change is moving property creation to new_property_from_pyobject since it is needed in more places (and was getting unwieldy anyway).

Given that this patch affects some pretty fundamental code, I also created a project that runs through a large set of test scenarios: https://github.com/dfb/uepy_test_prjs/tree/master/output_params

@dfb
Copy link
Contributor Author

dfb commented Dec 27, 2018

I've been using this patch for the past couple of weeks and overall it's worked well for me, but I did discover that in CallPythonCallable, stomping Stack.OutParms was the wrong thing to do (seems really obvious in retrospect, but oh well).

Basically, we do need to track the out param property addresses as we read them off the stack, but the caller's stack might have out params too, so it was wrong to null that list. But we can't just add to that list
either, since those FOutParmRec entries are stack-allocated, otherwise they would get garbled once CallPythonCallable exits.

In the latest commit I changed it so that inside of CallPythonCallable we make a "local" list of out params, and then when we go to look for out param we check Stack.OutParms, then our local list if it wasn't found.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Crash when Python method returns a string
1 participant