Skip to content
This repository has been archived by the owner on Sep 11, 2024. It is now read-only.

Incompatible with Windows-rs #237

Closed
MolotovCherry opened this issue Mar 2, 2022 · 4 comments
Closed

Incompatible with Windows-rs #237

MolotovCherry opened this issue Mar 2, 2022 · 4 comments

Comments

@MolotovCherry
Copy link

MolotovCherry commented Mar 2, 2022

Because this is a Microsoft crate, I expected it to be compatible with Windows-rs as well, but alas it was not.

Using the standard examples

com::interfaces! {
    #[uuid("...")]
    pub unsafe interface IWbemObjectSink: com::interfaces::IUnknown {
        ...
    }
}

com::class! {
    // ... some implementation
}

Then with windows-rs, use the code (I was converting this example over)

let pUnsecApp: IUnsecuredApartment = CoCreateInstance(&UnsecuredApartment, None, CLSCTX_LOCAL_SERVER)?;

let event_sink = EventSink::allocate(Some(tx));
let event_sink_h = IWbemObjectSink::from(&**event_sink); // IWbemObjectSink is our custom implementation, NOT from windows-rs

// error here
pUnsecApp.CreateObjectStub(event_sink_h)?;

The error we get is

the trait bound `event_sink::IWbemObjectSink: IntoParam<'_, windows::core::IUnknown>` is not satisfied
the trait `IntoParam<'_, windows::core::IUnknown>` is not implemented for `event_sink::IWbemObjectSink`

So, com doesn't implement anything to be able to work with windows-rs, making the API calls impossible (unless I re-do this in winapi crate to avoid these problems). I tried to convert it over with transmute and such, but I'm afraid I'll probably get it wrong since I don't know how compatible the types are and how to do it properly.

.... The same problem will occur later on when we try to execute a query.

pSvc = pLoc.ConnectServer(
    BSTR::from(r"ROOT\CIMV2"),
    None,
    None,
    None,
    0,
    None,
    None
)?;

// ...
event_sink = EventSink::allocate(Some(tx));
let event_sink_h = IWbemObjectSink::from(&**event_sink);

// this fn requires IWbemObjectSink, but it is the windows-rs type, NOT our custom type
pSvc.ExecNotificationQueryAsync(..., event_sink_h);
the trait bound `event_sink::IWbemObjectSink: IntoParam<'_, windows::Win32::System::Wmi::IWbemObjectSink>` is not satisfied
the trait `IntoParam<'_, windows::Win32::System::Wmi::IWbemObjectSink>` is not implemented for `event_sink::IWbemObjectSink`

... Of course, the reason I had to use this crate was because the windows-rs IWbemObjectSink type doesn't provide any way to implement it at all, which makes calling the API functions impossible, hence my need to use this crate for it.

I'm unsure whether this should be fixed in windows-rs or com-rs, but perhaps this might require a collaboration of the two if we want to make windows-rs crate a little more friendly towards it.

... If you need full code examples, just let me know.

@kennykerr
Copy link
Collaborator

We're in the process of adding support for declaring COM interfaces using only the windows crate. microsoft/windows-rs#1486

@MolotovCherry
Copy link
Author

MolotovCherry commented Mar 2, 2022

We're in the process of adding support for declaring COM interfaces using only the windows crate. microsoft/windows-rs#1486

This is wonderful news! That'd definitely solve everything. Thanks a lot ❤️

Sorry if this is an obvious question, but will this also work for my latter example of having the ExecNotificationQueryAsync call work with the custom com interface, in this case the type IWbemObjectSink?

Edit: I saw the example code from the pull request. I like how clean the proposed API to do this is! Much cleaner than this crate even. Great job!

@kennykerr
Copy link
Collaborator

Yes, that should work but we'll know more once I'm further along with the new interface macro. I hope to get started with that this week.

@MolotovCherry
Copy link
Author

Closing as solved, since windows-rs new interface macro is more than usable to do this

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

No branches or pull requests

2 participants