Skip to content

Commit

Permalink
Use Ref and OutRef for C++ delegates (#3447)
Browse files Browse the repository at this point in the history
  • Loading branch information
kennykerr authored Jan 15, 2025
1 parent 0a2c0b9 commit 68b029e
Show file tree
Hide file tree
Showing 39 changed files with 303 additions and 128 deletions.
34 changes: 28 additions & 6 deletions crates/libs/bindgen/src/types/cpp_delegate.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,11 @@ impl CppDelegate {
let method = self.method();
let signature = method.signature(type_name.namespace(), &[]);

let params = signature.params.iter().map(|(ty, param)| {
let name = to_ident(&param.name().to_lowercase());
let ty = ty.write_default(writer);
quote! { #name: #ty }
});
let mut params = quote! {};

for (ty, param) in &signature.params {
params.combine(write_param(writer, ty, *param));
}

let return_sig = writer.write_return_sig(method, &signature, false);
let arches = write_arches(self.def);
Expand All @@ -62,7 +62,7 @@ impl CppDelegate {
quote! {
#arches
#cfg
pub type #name = Option<unsafe extern "system" fn(#(#params),*) #return_sig>;
pub type #name = Option<unsafe extern "system" fn(#params) #return_sig>;
}
}

Expand All @@ -72,3 +72,25 @@ impl CppDelegate {
.dependencies(dependencies);
}
}

fn write_param(writer: &Writer, ty: &Type, param: Param) -> TokenStream {
let name = to_ident(&param.name().to_lowercase());
let type_name = ty.write_name(writer);

if writer.config.sys {
return quote! { #name: #type_name, };
}

if param.flags().contains(ParamAttributes::Out) {
if ty.deref().is_interface() {
let type_name = ty.deref().write_name(writer);
quote! { #name: windows_core::OutRef<'_, #type_name>, }
} else {
quote! { #name: #type_name, }
}
} else if ty.is_copyable() {
quote! { #name: #type_name, }
} else {
quote! { #name: windows_core::Ref<#type_name>, }
}
}
6 changes: 1 addition & 5 deletions crates/libs/bindgen/src/types/cpp_interface.rs
Original file line number Diff line number Diff line change
Expand Up @@ -402,11 +402,7 @@ impl CppInterface {
}

pub fn write_name(&self, writer: &Writer) -> TokenStream {
if writer.config.sys {
quote! { *mut core::ffi::c_void }
} else {
self.type_name().write(writer, &[])
}
self.type_name().write(writer, &[])
}

fn write_vtbl_name(&self, writer: &Writer) -> TokenStream {
Expand Down
6 changes: 1 addition & 5 deletions crates/libs/bindgen/src/types/interface.rs
Original file line number Diff line number Diff line change
Expand Up @@ -500,11 +500,7 @@ impl Interface {
}

pub fn write_name(&self, writer: &Writer) -> TokenStream {
if writer.config.sys {
quote! { *mut core::ffi::c_void }
} else {
self.type_name().write(writer, &self.generics)
}
self.type_name().write(writer, &self.generics)
}

fn write_vtbl_name(&self, writer: &Writer) -> TokenStream {
Expand Down
28 changes: 14 additions & 14 deletions crates/libs/bindgen/src/types/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -365,6 +365,10 @@ impl Type {
}

pub fn write_name(&self, writer: &Writer) -> TokenStream {
if writer.config.sys && self.is_interface() {
return quote! { *mut core::ffi::c_void };
}

match self {
Self::Void => quote! { core::ffi::c_void },
Self::Bool => quote! { bool },
Expand All @@ -386,12 +390,8 @@ impl Type {
quote! { #name BSTR }
}
Self::IUnknown => {
if writer.config.sys {
quote! { *mut core::ffi::c_void }
} else {
let name = writer.write_core();
quote! { #name IUnknown }
}
let name = writer.write_core();
quote! { #name IUnknown }
}
Self::GUID => {
let name = writer.write_core();
Expand All @@ -410,12 +410,8 @@ impl Type {
quote! { #name HSTRING }
}
Self::Object => {
if writer.config.sys {
quote! { *mut core::ffi::c_void }
} else {
let name = writer.write_core();
quote! { #name IInspectable }
}
let name = writer.write_core();
quote! { #name IInspectable }
}
Self::PSTR => {
let name = writer.write_core();
Expand Down Expand Up @@ -475,14 +471,18 @@ impl Type {
}

pub fn write_default(&self, writer: &Writer) -> TokenStream {
if writer.config.sys {
return self.write_name(writer);
}

if let Self::Array(ty) = self {
ty.write_default(writer)
} else {
let tokens = self.write_name(writer);

if matches!(self, Self::Param(_)) {
quote! { <#tokens as windows_core::Type<#tokens>>::Default }
} else if self.is_interface() && !writer.config.sys {
} else if self.is_interface() {
quote! { Option<#tokens> }
} else {
tokens
Expand All @@ -504,7 +504,7 @@ impl Type {

pub fn write_abi(&self, writer: &Writer) -> TokenStream {
if writer.config.sys {
return self.write_default(writer);
return self.write_name(writer);
}

match self {
Expand Down
6 changes: 6 additions & 0 deletions crates/libs/core/src/out_ref.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,3 +23,9 @@ impl<T: Type<T>> OutRef<'_, T> {
}
}
}

impl<'a, T: Type<T>> From<&'a mut T::Default> for OutRef<'a, T> {
fn from(from: &'a mut T::Default) -> Self {
unsafe { core::mem::transmute(from) }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7235,12 +7235,12 @@ pub const KEY_TERMSRV_SHADOW: u32 = 16u32;
pub const KEY_TERMSRV_VKPACKET: u32 = 32u32;
pub const KEY_UNICODE_SEQUENCE_END: u32 = 512u32;
pub const KEY_UNICODE_SEQUENCE_ITEM: u32 = 256u32;
pub type LPDICONFIGUREDEVICESCALLBACK = Option<unsafe extern "system" fn(param0: Option<windows_core::IUnknown>, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMCREATEDEFFECTOBJECTSCALLBACK = Option<unsafe extern "system" fn(param0: Option<IDirectInputEffect>, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDICONFIGUREDEVICESCALLBACK = Option<unsafe extern "system" fn(param0: windows_core::Ref<windows_core::IUnknown>, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMCREATEDEFFECTOBJECTSCALLBACK = Option<unsafe extern "system" fn(param0: windows_core::Ref<IDirectInputEffect>, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICEOBJECTSCALLBACKA = Option<unsafe extern "system" fn(param0: *mut DIDEVICEOBJECTINSTANCEA, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICEOBJECTSCALLBACKW = Option<unsafe extern "system" fn(param0: *mut DIDEVICEOBJECTINSTANCEW, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICESBYSEMANTICSCBA = Option<unsafe extern "system" fn(param0: *mut DIDEVICEINSTANCEA, param1: Option<IDirectInputDevice8A>, param2: u32, param3: u32, param4: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICESBYSEMANTICSCBW = Option<unsafe extern "system" fn(param0: *mut DIDEVICEINSTANCEW, param1: Option<IDirectInputDevice8W>, param2: u32, param3: u32, param4: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICESBYSEMANTICSCBA = Option<unsafe extern "system" fn(param0: *mut DIDEVICEINSTANCEA, param1: windows_core::Ref<IDirectInputDevice8A>, param2: u32, param3: u32, param4: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICESBYSEMANTICSCBW = Option<unsafe extern "system" fn(param0: *mut DIDEVICEINSTANCEW, param1: windows_core::Ref<IDirectInputDevice8W>, param2: u32, param3: u32, param4: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICESCALLBACKA = Option<unsafe extern "system" fn(param0: *mut DIDEVICEINSTANCEA, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMDEVICESCALLBACKW = Option<unsafe extern "system" fn(param0: *mut DIDEVICEINSTANCEW, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
pub type LPDIENUMEFFECTSCALLBACKA = Option<unsafe extern "system" fn(param0: *mut DIEFFECTINFOA, param1: *mut core::ffi::c_void) -> windows_core::BOOL>;
Expand Down
6 changes: 3 additions & 3 deletions crates/libs/windows/src/Windows/Win32/Devices/Tapi/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20237,11 +20237,11 @@ pub const LM_STEADY: PHONE_LAMP_MODE = PHONE_LAMP_MODE(4i32);
pub const LM_UNKNOWN: PHONE_LAMP_MODE = PHONE_LAMP_MODE(128i32);
pub const LM_WINK: PHONE_LAMP_MODE = PHONE_LAMP_MODE(8i32);
#[cfg(feature = "Win32_System_Com")]
pub type LPGETTNEFSTREAMCODEPAGE = Option<unsafe extern "system" fn(lpstream: Option<super::super::System::Com::IStream>, lpulcodepage: *mut u32, lpulsubcodepage: *mut u32) -> windows_core::HRESULT>;
pub type LPGETTNEFSTREAMCODEPAGE = Option<unsafe extern "system" fn(lpstream: windows_core::Ref<super::super::System::Com::IStream>, lpulcodepage: *mut u32, lpulsubcodepage: *mut u32) -> windows_core::HRESULT>;
#[cfg(all(feature = "Win32_System_AddressBook", feature = "Win32_System_Com"))]
pub type LPOPENTNEFSTREAM = Option<unsafe extern "system" fn(lpvsupport: *mut core::ffi::c_void, lpstream: Option<super::super::System::Com::IStream>, lpszstreamname: *const i8, ulflags: u32, lpmessage: Option<super::super::System::AddressBook::IMessage>, wkeyval: u16, lpptnef: *mut Option<ITnef>) -> windows_core::HRESULT>;
pub type LPOPENTNEFSTREAM = Option<unsafe extern "system" fn(lpvsupport: *mut core::ffi::c_void, lpstream: windows_core::Ref<super::super::System::Com::IStream>, lpszstreamname: *const i8, ulflags: u32, lpmessage: windows_core::Ref<super::super::System::AddressBook::IMessage>, wkeyval: u16, lpptnef: windows_core::OutRef<'_, ITnef>) -> windows_core::HRESULT>;
#[cfg(all(feature = "Win32_System_AddressBook", feature = "Win32_System_Com"))]
pub type LPOPENTNEFSTREAMEX = Option<unsafe extern "system" fn(lpvsupport: *mut core::ffi::c_void, lpstream: Option<super::super::System::Com::IStream>, lpszstreamname: *const i8, ulflags: u32, lpmessage: Option<super::super::System::AddressBook::IMessage>, wkeyval: u16, lpadressbook: Option<super::super::System::AddressBook::IAddrBook>, lpptnef: *mut Option<ITnef>) -> windows_core::HRESULT>;
pub type LPOPENTNEFSTREAMEX = Option<unsafe extern "system" fn(lpvsupport: *mut core::ffi::c_void, lpstream: windows_core::Ref<super::super::System::Com::IStream>, lpszstreamname: *const i8, ulflags: u32, lpmessage: windows_core::Ref<super::super::System::AddressBook::IMessage>, wkeyval: u16, lpadressbook: windows_core::Ref<super::super::System::AddressBook::IAddrBook>, lpptnef: windows_core::OutRef<'_, ITnef>) -> windows_core::HRESULT>;
pub const ME_ADDRESS_EVENT: MSP_EVENT = MSP_EVENT(0i32);
pub const ME_ASR_TERMINAL_EVENT: MSP_EVENT = MSP_EVENT(4i32);
pub const ME_CALL_EVENT: MSP_EVENT = MSP_EVENT(1i32);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3781,7 +3781,7 @@ pub const OpOneOrMore: WSDXML_OP = WSDXML_OP(18i32);
pub const OpOptional: WSDXML_OP = WSDXML_OP(19i32);
pub const OpProcess_: WSDXML_OP = WSDXML_OP(43i32);
pub const OpQualifiedAttribute_: WSDXML_OP = WSDXML_OP(44i32);
pub type PWSD_SOAP_MESSAGE_HANDLER = Option<unsafe extern "system" fn(thisunknown: Option<windows_core::IUnknown>, event: *mut WSD_EVENT) -> windows_core::HRESULT>;
pub type PWSD_SOAP_MESSAGE_HANDLER = Option<unsafe extern "system" fn(thisunknown: windows_core::Ref<windows_core::IUnknown>, event: *mut WSD_EVENT) -> windows_core::HRESULT>;
#[repr(C)]
#[derive(Clone, Copy, Debug, PartialEq)]
pub struct REQUESTBODY_GetStatus {
Expand Down Expand Up @@ -4662,7 +4662,7 @@ impl Default for WSD_SOAP_MESSAGE {
unsafe { core::mem::zeroed() }
}
}
pub type WSD_STUB_FUNCTION = Option<unsafe extern "system" fn(server: Option<windows_core::IUnknown>, session: Option<IWSDServiceMessaging>, event: *mut WSD_EVENT) -> windows_core::HRESULT>;
pub type WSD_STUB_FUNCTION = Option<unsafe extern "system" fn(server: windows_core::Ref<windows_core::IUnknown>, session: windows_core::Ref<IWSDServiceMessaging>, event: *mut WSD_EVENT) -> windows_core::HRESULT>;
#[repr(C)]
#[derive(Clone, Debug, PartialEq)]
pub struct WSD_SYNCHRONOUS_RESPONSE_CONTEXT {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -457,6 +457,6 @@ pub const KmdModelVersion: DXCoreAdapterProperty = DXCoreAdapterProperty(4u32);
pub const Local: DXCoreSegmentGroup = DXCoreSegmentGroup(0u32);
pub const MinimumPower: DXCoreAdapterPreference = DXCoreAdapterPreference(1u32);
pub const NonLocal: DXCoreSegmentGroup = DXCoreSegmentGroup(1u32);
pub type PFN_DXCORE_NOTIFICATION_CALLBACK = Option<unsafe extern "system" fn(notificationtype: DXCoreNotificationType, object: Option<windows_core::IUnknown>, context: *const core::ffi::c_void)>;
pub type PFN_DXCORE_NOTIFICATION_CALLBACK = Option<unsafe extern "system" fn(notificationtype: DXCoreNotificationType, object: windows_core::Ref<windows_core::IUnknown>, context: *const core::ffi::c_void)>;
pub const SharedSystemMemory: DXCoreAdapterProperty = DXCoreAdapterProperty(9u32);
pub const _FACDXCORE: u32 = 2176u32;
Original file line number Diff line number Diff line change
Expand Up @@ -14848,6 +14848,6 @@ impl ID2D1VertexBuffer_Vtbl {
}
}
impl windows_core::RuntimeName for ID2D1VertexBuffer {}
pub type PD2D1_EFFECT_FACTORY = Option<unsafe extern "system" fn(effectimpl: *mut Option<windows_core::IUnknown>) -> windows_core::HRESULT>;
pub type PD2D1_PROPERTY_GET_FUNCTION = Option<unsafe extern "system" fn(effect: Option<windows_core::IUnknown>, data: *mut u8, datasize: u32, actualsize: *mut u32) -> windows_core::HRESULT>;
pub type PD2D1_PROPERTY_SET_FUNCTION = Option<unsafe extern "system" fn(effect: Option<windows_core::IUnknown>, data: *const u8, datasize: u32) -> windows_core::HRESULT>;
pub type PD2D1_EFFECT_FACTORY = Option<unsafe extern "system" fn(effectimpl: windows_core::OutRef<'_, windows_core::IUnknown>) -> windows_core::HRESULT>;
pub type PD2D1_PROPERTY_GET_FUNCTION = Option<unsafe extern "system" fn(effect: windows_core::Ref<windows_core::IUnknown>, data: *mut u8, datasize: u32, actualsize: *mut u32) -> windows_core::HRESULT>;
pub type PD2D1_PROPERTY_SET_FUNCTION = Option<unsafe extern "system" fn(effect: windows_core::Ref<windows_core::IUnknown>, data: *const u8, datasize: u32) -> windows_core::HRESULT>;
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ impl Default for DxcBuffer {
}
}
#[cfg(feature = "Win32_System_Com")]
pub type DxcCreateInstance2Proc = Option<unsafe extern "system" fn(pmalloc: Option<super::super::super::System::Com::IMalloc>, rclsid: *const windows_core::GUID, riid: *const windows_core::GUID, ppv: *mut *mut core::ffi::c_void) -> windows_core::HRESULT>;
pub type DxcCreateInstance2Proc = Option<unsafe extern "system" fn(pmalloc: windows_core::Ref<super::super::super::System::Com::IMalloc>, rclsid: *const windows_core::GUID, riid: *const windows_core::GUID, ppv: *mut *mut core::ffi::c_void) -> windows_core::HRESULT>;
pub type DxcCreateInstanceProc = Option<unsafe extern "system" fn(rclsid: *const windows_core::GUID, riid: *const windows_core::GUID, ppv: *mut *mut core::ffi::c_void) -> windows_core::HRESULT>;
#[repr(C)]
#[derive(Clone, Copy, Debug, PartialEq)]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -295,6 +295,6 @@ impl Default for D3D_SHADER_DATA {
unsafe { core::mem::zeroed() }
}
}
pub type pD3DCompile = Option<unsafe extern "system" fn(psrcdata: *const core::ffi::c_void, srcdatasize: usize, pfilename: windows_core::PCSTR, pdefines: *const super::D3D_SHADER_MACRO, pinclude: Option<super::ID3DInclude>, pentrypoint: windows_core::PCSTR, ptarget: windows_core::PCSTR, flags1: u32, flags2: u32, ppcode: *mut Option<super::ID3DBlob>, pperrormsgs: *mut Option<super::ID3DBlob>) -> windows_core::HRESULT>;
pub type pD3DDisassemble = Option<unsafe extern "system" fn(psrcdata: *const core::ffi::c_void, srcdatasize: usize, flags: u32, szcomments: windows_core::PCSTR, ppdisassembly: *mut Option<super::ID3DBlob>) -> windows_core::HRESULT>;
pub type pD3DPreprocess = Option<unsafe extern "system" fn(psrcdata: *const core::ffi::c_void, srcdatasize: usize, pfilename: windows_core::PCSTR, pdefines: *const super::D3D_SHADER_MACRO, pinclude: Option<super::ID3DInclude>, ppcodetext: *mut Option<super::ID3DBlob>, pperrormsgs: *mut Option<super::ID3DBlob>) -> windows_core::HRESULT>;
pub type pD3DCompile = Option<unsafe extern "system" fn(psrcdata: *const core::ffi::c_void, srcdatasize: usize, pfilename: windows_core::PCSTR, pdefines: *const super::D3D_SHADER_MACRO, pinclude: windows_core::Ref<super::ID3DInclude>, pentrypoint: windows_core::PCSTR, ptarget: windows_core::PCSTR, flags1: u32, flags2: u32, ppcode: windows_core::OutRef<'_, super::ID3DBlob>, pperrormsgs: windows_core::OutRef<'_, super::ID3DBlob>) -> windows_core::HRESULT>;
pub type pD3DDisassemble = Option<unsafe extern "system" fn(psrcdata: *const core::ffi::c_void, srcdatasize: usize, flags: u32, szcomments: windows_core::PCSTR, ppdisassembly: windows_core::OutRef<'_, super::ID3DBlob>) -> windows_core::HRESULT>;
pub type pD3DPreprocess = Option<unsafe extern "system" fn(psrcdata: *const core::ffi::c_void, srcdatasize: usize, pfilename: windows_core::PCSTR, pdefines: *const super::D3D_SHADER_MACRO, pinclude: windows_core::Ref<super::ID3DInclude>, ppcodetext: windows_core::OutRef<'_, super::ID3DBlob>, pperrormsgs: windows_core::OutRef<'_, super::ID3DBlob>) -> windows_core::HRESULT>;
Original file line number Diff line number Diff line change
Expand Up @@ -9174,7 +9174,7 @@ impl ID3D10View_Vtbl {
}
impl windows_core::RuntimeName for ID3D10View {}
#[cfg(feature = "Win32_Graphics_Dxgi")]
pub type PFN_D3D10_CREATE_DEVICE1 = Option<unsafe extern "system" fn(param0: Option<super::Dxgi::IDXGIAdapter>, param1: D3D10_DRIVER_TYPE, param2: super::super::Foundation::HMODULE, param3: u32, param4: D3D10_FEATURE_LEVEL1, param5: u32, param6: *mut Option<ID3D10Device1>) -> windows_core::HRESULT>;
pub type PFN_D3D10_CREATE_DEVICE1 = Option<unsafe extern "system" fn(param0: windows_core::Ref<super::Dxgi::IDXGIAdapter>, param1: D3D10_DRIVER_TYPE, param2: super::super::Foundation::HMODULE, param3: u32, param4: D3D10_FEATURE_LEVEL1, param5: u32, param6: windows_core::OutRef<'_, ID3D10Device1>) -> windows_core::HRESULT>;
#[cfg(feature = "Win32_Graphics_Dxgi_Common")]
pub type PFN_D3D10_CREATE_DEVICE_AND_SWAP_CHAIN1 = Option<unsafe extern "system" fn(param0: Option<super::Dxgi::IDXGIAdapter>, param1: D3D10_DRIVER_TYPE, param2: super::super::Foundation::HMODULE, param3: u32, param4: D3D10_FEATURE_LEVEL1, param5: u32, param6: *mut super::Dxgi::DXGI_SWAP_CHAIN_DESC, param7: *mut Option<super::Dxgi::IDXGISwapChain>, param8: *mut Option<ID3D10Device1>) -> windows_core::HRESULT>;
pub type PFN_D3D10_CREATE_DEVICE_AND_SWAP_CHAIN1 = Option<unsafe extern "system" fn(param0: windows_core::Ref<super::Dxgi::IDXGIAdapter>, param1: D3D10_DRIVER_TYPE, param2: super::super::Foundation::HMODULE, param3: u32, param4: D3D10_FEATURE_LEVEL1, param5: u32, param6: *mut super::Dxgi::DXGI_SWAP_CHAIN_DESC, param7: windows_core::OutRef<'_, super::Dxgi::IDXGISwapChain>, param8: windows_core::OutRef<'_, ID3D10Device1>) -> windows_core::HRESULT>;
pub const _FACD3D10: u32 = 2169u32;
Loading

0 comments on commit 68b029e

Please sign in to comment.