Skip to content

Commit e45740f

Browse files
authored
Add optional support for raw-dylib (#2164)
1 parent a46eaa3 commit e45740f

File tree

14 files changed

+114
-24
lines changed

14 files changed

+114
-24
lines changed

.cargo/config.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
[build]
22
rustflags = [
33
# "--cfg", "windows_debugger_visualizer",
4+
# "--cfg", "windows_raw_dylib",
45
]

.github/workflows/raw_dylib.yml

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
name: raw_dylib
2+
3+
on:
4+
pull_request:
5+
push:
6+
branches:
7+
- master
8+
9+
env:
10+
RUSTFLAGS: -Dwarnings --cfg windows_raw_dylib
11+
12+
jobs:
13+
test:
14+
name: Test
15+
runs-on: windows-2019
16+
17+
strategy:
18+
matrix:
19+
include:
20+
- target: x86_64-pc-windows-msvc
21+
- target: i686-pc-windows-msvc
22+
- target: x86_64-pc-windows-gnu
23+
steps:
24+
- name: Checkout
25+
uses: actions/checkout@v3
26+
- name: Update toolchain
27+
run: rustup update --no-self-update nightly && rustup default nightly-${{ matrix.target }}
28+
- name: Add toolchain target
29+
run: rustup target add ${{ matrix.target }}
30+
31+
- name: Test
32+
run: cargo test -p test_calling_convention

crates/libs/sys/Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ default-target = "x86_64-pc-windows-msvc"
1515
targets = []
1616
all-features = true
1717

18-
[dependencies]
18+
[target.'cfg(not(windows_raw_dylib))'.dependencies]
1919
windows-targets = { path = "../targets", version = "0.43.0" }
2020

2121
[features]

crates/libs/sys/src/core/mod.rs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,29 @@ impl GUID {
3535
}
3636
}
3737

38+
#[cfg(all(windows_raw_dylib, target_arch = "x86"))]
39+
#[macro_export]
40+
macro_rules! link {
41+
($library:literal $abi:literal $(#[$($doc:tt)*])* fn $name:ident($($arg:ident: $argty:ty),*)->$ret:ty) => (
42+
#[link(name = $library, kind = "raw-dylib", modifiers = "+verbatim", import_name_type = "undecorated")]
43+
extern $abi {
44+
pub fn $name($($arg: $argty),*) -> $ret;
45+
}
46+
)
47+
}
48+
49+
#[cfg(all(windows_raw_dylib, not(target_arch = "x86")))]
50+
#[macro_export]
51+
macro_rules! link {
52+
($library:literal $abi:literal $(#[$($doc:tt)*])* fn $name:ident($($arg:ident: $argty:ty),*)->$ret:ty) => (
53+
#[link(name = $library, kind = "raw-dylib", modifiers = "+verbatim")]
54+
extern "system" {
55+
pub fn $name($($arg: $argty),*) -> $ret;
56+
}
57+
)
58+
}
59+
60+
#[cfg(not(windows_raw_dylib))]
3861
#[macro_export]
3962
macro_rules! link {
4063
($library:literal $abi:literal $(#[$($doc:tt)*])* fn $name:ident($($arg:ident: $argty:ty),*)->$ret:ty) => (

crates/libs/sys/src/lib.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ Learn more about Rust for Windows here: <https://github.com/microsoft/windows-rs
55
#![no_std]
66
#![doc(html_no_source)]
77
#![allow(non_snake_case, clashing_extern_declarations)]
8+
#![cfg_attr(windows_raw_dylib, feature(raw_dylib, native_link_modifiers_verbatim))]
89

910
extern crate self as windows_sys;
1011
mod Windows;

crates/libs/windows/Cargo.toml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,10 @@ rust-version = "1.64"
1515
default-target = "x86_64-pc-windows-msvc"
1616
targets = []
1717

18-
[dependencies]
18+
[target.'cfg(not(windows_raw_dylib))'.dependencies]
1919
windows-targets = { path = "../targets", version = "0.43.0" }
20+
21+
[dependencies]
2022
windows-implement = { path = "../implement", version = "0.43.0", optional = true }
2123
windows-interface = { path = "../interface", version = "0.43.0", optional = true }
2224

crates/libs/windows/src/core/bindings.rs

Lines changed: 15 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,28 @@
11
use super::*;
22
use std::ffi::c_void;
33

4-
link!("kernel32.dll""system" fn CloseHandle(handle: isize) -> i32);
5-
link!("kernel32.dll" "system" fn GetLastError() -> u32);
6-
link!("oleaut32.dll" "system" fn SysAllocStringLen(input: *const u16, len: u32) -> *const u16);
7-
link!("oleaut32.dll" "system" fn SysFreeString(bstr: *const u16) -> ());
8-
link!("oleaut32.dll" "system" fn SysStringLen(bstr: *const u16) -> u32);
9-
link!("ole32.dll" "system" fn CoCreateGuid(guid: *mut GUID) -> HRESULT);
10-
link!("ole32.dll" "system" fn CoTaskMemAlloc(len: usize) -> *mut c_void);
11-
link!("ole32.dll" "system" fn CoTaskMemFree(ptr: *const c_void) -> ());
12-
link!("oleaut32.dll" "system" fn GetErrorInfo(reserved: u32, info: *mut *mut c_void) -> HRESULT);
13-
link!("oleaut32.dll" "system" fn SetErrorInfo(reserved: u32, info: *const c_void) -> HRESULT);
4+
link!("kernel32.dll" "system" fn CreateEventW(attributes: *const c_void, manual_reset: i32, initial_state: i32, name: *const c_void) -> isize);
145
link!("kernel32.dll" "system" fn EncodePointer(ptr: *const c_void) -> *mut c_void);
156
link!("kernel32.dll" "system" fn FormatMessageW(flags: u32, source: *const c_void, code: u32, lang: u32, buffer: PWSTR, len: u32, args: *const *const i8) -> u32);
7+
link!("kernel32.dll" "system" fn FreeLibrary(library: isize) -> i32);
8+
link!("kernel32.dll" "system" fn GetLastError() -> u32);
9+
link!("kernel32.dll" "system" fn GetProcAddress(library: isize, name: PCSTR) -> *const std::ffi::c_void);
1610
link!("kernel32.dll" "system" fn GetProcessHeap() -> isize);
1711
link!("kernel32.dll" "system" fn HeapAlloc(heap: isize, flags: u32, len: usize) -> *mut c_void);
1812
link!("kernel32.dll" "system" fn HeapFree(heap: isize, flags: u32, ptr: *const c_void) -> i32);
19-
link!("kernel32.dll" "system" fn CreateEventW(attributes: *const c_void, manual_reset: i32, initial_state: i32, name: *const c_void) -> isize);
20-
link!("kernel32.dll" "system" fn WaitForSingleObject(handle: isize, milliseconds: u32) -> u32);
13+
link!("kernel32.dll" "system" fn LoadLibraryA(name: PCSTR) -> isize);
2114
link!("kernel32.dll" "system" fn SetEvent(handle: isize) -> i32);
15+
link!("kernel32.dll" "system" fn WaitForSingleObject(handle: isize, milliseconds: u32) -> u32);
16+
link!("kernel32.dll""system" fn CloseHandle(handle: isize) -> i32);
17+
link!("ole32.dll" "system" fn CoCreateGuid(guid: *mut GUID) -> HRESULT);
18+
link!("ole32.dll" "system" fn CoTaskMemAlloc(len: usize) -> *mut c_void);
19+
link!("ole32.dll" "system" fn CoTaskMemFree(ptr: *const c_void) -> ());
2220
link!("ole32.dll" "system" fn RoGetAgileReference(options: i32, iid: &GUID, object: *const c_void, reference: *mut *mut c_void) -> HRESULT);
21+
link!("oleaut32.dll" "system" fn GetErrorInfo(reserved: u32, info: *mut *mut c_void) -> HRESULT);
22+
link!("oleaut32.dll" "system" fn SetErrorInfo(reserved: u32, info: *const c_void) -> HRESULT);
23+
link!("oleaut32.dll" "system" fn SysAllocStringLen(input: *const u16, len: u32) -> *const u16);
24+
link!("oleaut32.dll" "system" fn SysFreeString(bstr: *const u16) -> ());
25+
link!("oleaut32.dll" "system" fn SysStringLen(bstr: *const u16) -> u32);
2326

2427
pub const FORMAT_MESSAGE_ALLOCATE_BUFFER: u32 = 256;
2528
pub const FORMAT_MESSAGE_FROM_SYSTEM: u32 = 4096;

crates/libs/windows/src/core/delay_load.rs

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
use super::*;
2+
use bindings::*;
23

34
/// Attempts to load a function from a given library.
45
///
@@ -23,10 +24,3 @@ pub unsafe fn delay_load<T>(library: PCSTR, function: PCSTR) -> Option<T> {
2324
FreeLibrary(library);
2425
None
2526
}
26-
27-
#[link(name = "windows")]
28-
extern "system" {
29-
fn GetProcAddress(library: isize, name: PCSTR) -> *const std::ffi::c_void;
30-
fn LoadLibraryA(name: PCSTR) -> isize;
31-
fn FreeLibrary(library: isize) -> i32;
32-
}

crates/libs/windows/src/core/mod.rs

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ pub use array::*;
3434
#[doc(hidden)]
3535
pub use as_impl::*;
3636
pub use borrowed::*;
37-
pub(crate) use delay_load::*;
37+
pub use delay_load::*;
3838
pub use error::*;
3939
pub use event::*;
4040
pub use factory_cache::*;
@@ -125,6 +125,29 @@ macro_rules! interface_hierarchy {
125125
#[doc(hidden)]
126126
pub use interface_hierarchy;
127127

128+
#[cfg(all(windows_raw_dylib, target_arch = "x86"))]
129+
#[macro_export]
130+
macro_rules! link {
131+
($library:literal $abi:literal fn $name:ident($($arg:ident: $argty:ty),*)->$ret:ty) => (
132+
#[link(name = $library, kind = "raw-dylib", modifiers = "+verbatim", import_name_type = "undecorated")]
133+
extern $abi {
134+
pub fn $name($($arg: $argty),*) -> $ret;
135+
}
136+
)
137+
}
138+
139+
#[cfg(all(windows_raw_dylib, not(target_arch = "x86")))]
140+
#[macro_export]
141+
macro_rules! link {
142+
($library:literal $abi:literal fn $name:ident($($arg:ident: $argty:ty),*)->$ret:ty) => (
143+
#[link(name = $library, kind = "raw-dylib", modifiers = "+verbatim")]
144+
extern "system" {
145+
pub fn $name($($arg: $argty),*) -> $ret;
146+
}
147+
)
148+
}
149+
150+
#[cfg(not(windows_raw_dylib))]
128151
#[macro_export]
129152
macro_rules! link {
130153
($library:literal $abi:literal fn $name:ident($($arg:ident: $argty:ty),*)->$ret:ty) => (

crates/libs/windows/src/lib.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ Learn more about Rust for Windows here: <https://github.com/microsoft/windows-rs
55
#![doc(html_no_source)]
66
#![allow(non_snake_case, clashing_extern_declarations)]
77
#![cfg_attr(windows_debugger_visualizer, feature(debugger_visualizer), debugger_visualizer(natvis_file = "../windows.natvis"))]
8+
#![cfg_attr(windows_raw_dylib, feature(raw_dylib, native_link_modifiers_verbatim))]
89

910
extern crate self as windows;
1011
mod Windows;

0 commit comments

Comments
 (0)