Last active
October 26, 2015 18:32
-
-
Save retep998/604861ea06aa984ee6c7 to your computer and use it in GitHub Desktop.
stdcall
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
(1:56:14 PM) Retep998: I'd still really like a calling convention for stdcall methods because they aren't the same as stdcall functions | |
(1:56:21 PM) Retep998: who should I talk to about getting something like that? | |
(2:02:40 PM) jroelofs: Retep998: rnk maybe? | |
rnk rnsanchez | |
(2:03:27 PM) Retep998: rnk: Someone said I should talk to you about stdcall calling conventions | |
(2:04:49 PM) jroelofs: it might help to describe what you think is different between the two | |
(2:05:21 PM) Retep998: How values are returned from stdcall functions differs from stdcall methods | |
(2:05:40 PM) Retep998: Like if I return a struct containing two 32-bit integers | |
(2:06:04 PM) Retep998: fn foo(self) -> ThatType | |
(2:06:39 PM) Retep998: the stdcall calling convention currently does the function style, but to get the method style I have to use a hacky workaround to get it right | |
(2:06:59 PM) Retep998: which looks like fn foo(self, ret: *mut ThatType) -> *mut ThatType | |
(2:07:06 PM) rnk: Retep998, what about? | |
(2:07:29 PM) Retep998: rnk: I ran into this issue due to COM interfaces in Windows API | |
(2:07:35 PM) rnk: right, this is sret vs. this | |
(2:07:47 PM) rnk: clang handles this by swapping the order of the arguments | |
(2:07:54 PM) rnk: and moving the sret attribute to the second parameter | |
(2:08:30 PM) rnk: Retep998, basically MSVC has the invariant that 'this' always goes first, any implicit struct return parameter goes second. In some sense, this is true even for 'thiscall' | |
(2:09:16 PM) Retep998: rnk: What I need is a way to be able to represent the function pointers of COM interfaces in Rust | |
(2:09:59 PM) Retep998: Since function pointers in Rust are always just functions, "stdcall" can never do what I want, so I have to do that hackish work around | |
(2:11:14 PM) Retep998: Which funnily enough, means the C versions of such COM interfaces in the windows headers is actually wrong :P | |
(2:12:24 PM) Retep998: I tested it with the GetAdapterLuid method of ID3D12Device, and using the C bindings instead of the C++ version caused incorrect behavior | |
(2:13:52 PM) rnk: Retep998, so it sounds like rust interops with COM by filling out a table of function pointers as you would for C? | |
(2:13:59 PM) Retep998: rnk: yep | |
(2:14:10 PM) Retep998: Well, that's how I write the COM interop since I have no other choice really | |
(2:14:46 PM) rnk: Retep998, and essentially the Rust programmer needs to "know" that struct return actually needs to be prototyped as Sret* myfun(void* this, Sret *sret); | |
(2:14:58 PM) rnk: for COM methods | |
(2:15:13 PM) Retep998: yep | |
(2:15:27 PM) rnk: Retep998, so for a while we went down the path of having an x86stdcallmethodcc calling convention, which would hypothetically paper over the difference | |
(2:15:46 PM) rnk: Retep998, but MSVC has too many calling conventions, I think we're at 5 now | |
(2:15:53 PM) rnk: cdecl, vectorcall, stdcall, thiscall, fastcall | |
(2:16:05 PM) Retep998: and you don't want to have variations of each as well? | |
(2:16:06 PM) rnk: they would all need to have "C++ method" variants | |
(2:16:26 PM) rnk: so we decided that the frontend just has to "know" what's a method and what isn't | |
(2:17:03 PM) rnk: and the frontend would lower methods with 'this' before 'sret' | |
(2:17:05 PM) Retep998: So then Rust's compiler would need to add syntax for specifying this and implementing the proper LLVM support? | |
(2:17:34 PM) rnk: I don't think you need changes to LLVM, you just need to change what IR Rust generates | |
(2:17:47 PM) rnk: you can either do what you're currently doing, where you change the source-level rust prototype (right?) | |
(2:18:06 PM) rnk: or you can add some tag for "hey, this is a COM method, rust compiler, please do something different for struct return" | |
(2:18:24 PM) Retep998: Well, even if support was added to the Rust compiler, I'd have to wait at least half a year for it to stabilize and proliferate | |
(2:19:00 PM) rnk: Retep998, in the meantime, what's the problem with teaching users of COM about this awkwardness? | |
(2:19:25 PM) Retep998: rnk: Not much, all the COM interfaces are defined in my library anyway | |
(2:19:50 PM) Retep998: it's just a minor hassle having to make sure all the COM interface methods are checked and use the correct signature for struct returns | |
(2:20:00 PM) rnk: definitely | |
(2:21:20 PM) Retep998: reviewing PRs that regularly add thousands of lines of boring bindings and definitions is really mind-numbing | |
(2:21:22 PM) ***Retep998 sighs | |
(2:22:02 PM) rnk: If your only usage of stdcall is for interoperating with COM, you could audit the LLVM IR for functions with stdcall convention that have sret on the first parameter | |
(2:22:32 PM) rnk: we can't add a generalized check for that, since obviously there are stdcall free functions | |
(2:22:41 PM) rnk: anyway, sorry about that :( |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment