From 9439a08d06e86e4469d69eac85bd6aa92aceda39 Mon Sep 17 00:00:00 2001 From: mingkuang Date: Thu, 9 May 2024 13:18:02 +0800 Subject: [PATCH] =?UTF-8?q?Opt,=20=E4=BD=BF=E7=94=A8cpuid=E9=87=8D?= =?UTF-8?q?=E6=96=B0=E5=AE=9E=E7=8E=B0GetCurrentProcessorNumber=EF=BC=8C?= =?UTF-8?q?=E8=AE=A9XP=E4=B8=8BSTL=E7=9A=84=E5=A4=9A=E7=BA=BF=E7=A8=8B?= =?UTF-8?q?=E8=B0=83=E5=BA=A6=E6=AD=A3=E5=B8=B8=E5=B7=A5=E4=BD=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ReadMe.md | 44 ++++++++++--------- ThunksList.md | 18 ++++---- src/Thunks/api-ms-win-core-processthreads.hpp | 21 +++++++-- 3 files changed, 50 insertions(+), 33 deletions(-) diff --git a/ReadMe.md b/ReadMe.md index 8c8bd44..a7b0d2f 100644 --- a/ReadMe.md +++ b/ReadMe.md @@ -1,12 +1,12 @@ # YY-Thunks - 让兼容 Windows 更轻松 -![license](https://img.shields.io/github/license/Chuyu-Team/YY-Thunks) -![downloads](https://img.shields.io/github/downloads/Chuyu-Team/YY-Thunks/total) -![contributors](https://img.shields.io/github/contributors-anon/Chuyu-Team/YY-Thunks) -![release](https://img.shields.io/github/v/release/Chuyu-Team/YY-Thunks?include_prereleases) -![nuget](https://img.shields.io/nuget/vpre/YY-Thunks) +[![license](https://img.shields.io/github/license/Chuyu-Team/YY-Thunks)](https://github.com/Chuyu-Team/YY-Thunks/blob/master/LICENSE) +[![downloads](https://img.shields.io/github/downloads/Chuyu-Team/YY-Thunks/total)](https://github.com/Chuyu-Team/YY-Thunks/releases) +[![contributors](https://img.shields.io/github/contributors-anon/Chuyu-Team/YY-Thunks)](https://github.com/Chuyu-Team/YY-Thunks/graphs/contributors) +[![release](https://img.shields.io/github/v/release/Chuyu-Team/YY-Thunks?include_prereleases)](https://github.com/Chuyu-Team/YY-Thunks/releases) +[![nuget](https://img.shields.io/nuget/vpre/YY-Thunks)](https://www.nuget.org/packages/YY-Thunks) [![Build&Test](https://github.com/Chuyu-Team/YY-Thunks/actions/workflows/Build&Test.yml/badge.svg)](https://github.com/Chuyu-Team/YY-Thunks/actions/workflows/Build&Test.yml) -## 关于 YY-Thunks +## 1. 关于 YY-Thunks 众所周知,从 Windows 的每次更新又会新增大量 API,这使得兼容不同版本的 Windows 需要花费很大精力。导致现在大量开源项目已经不再兼容一些早期的 Windows 版本,比如 @@ -19,12 +19,12 @@ YY-Thunks(鸭船),存在的目的就是抹平不同系统的差异,编 [ [鸭船交流群 633710173](https://shang.qq.com/wpa/qunwpa?idkey=21d51d8ad1d77b99ea9544b399e080ec347ca6a1bc04267fb59cebf22644a42a) ] -### 原理 +### 1.1. 原理 使用 `LoadLibrary` 以及 `GetProcAddress` 动态加载 API,不存在时做出补偿措施, 最大限度模拟原始 API 行为,让你的程序正常运行。 -### 亮点 +### 1.2. 亮点 * 更快!更安全!`鸭船`内建2级缓存以及按需加载机制,同时自动加密所有函数指针, 防止内存爆破攻击。最大程度减少不需要和不必要的 `LoadLibrary` 以及 @@ -32,19 +32,25 @@ YY-Thunks(鸭船),存在的目的就是抹平不同系统的差异,编 * 轻松兼容 Windows XP,让你安心专注于业务逻辑。 * 完全开源且广泛接受用户意见,希望大家能踊跃的创建 PR,为`鸭船`添砖加瓦。 -## 使用方法 +## 2. 使用方法 -大家可以在以下方案中任选一种,但是我们优先推荐 NuGet 方案。 - -### NuGet(推荐) +大家可以在以下方案中任选一种,但是我们优先推荐 NuGet 方案,因为NuGet采用傻瓜式设计,使用更便捷。 +### 2.1. NuGet(推荐) +#### 2.1.1. C++项目 1. 项目右键 “管理 NuGet 程序包”。 2. NuGet搜索框中输入:`YY-Thunks`,搜索后点击安装。 3. 项目右键 - 属性 - YY-Thunks 中,自行调整YY-Thunks等级,允许 Windows 2000, Windows XP 以及 Windows Vista(默认)。 4. 重新编译代码 -### 手工配置 +#### 2.1.2. .NET Native AOT项目 +1. 给`TargetFramework`添加`Windows`系统平台,比如修改为`net8.0-windows`或者`net9.0-windows`。 +2. 项目右键 `管理 NuGet 程序包`。 +3. NuGet搜索框中输入:`YY-Thunks`,搜索后点击安装。 +4. 默认兼容到Windows Vista(默认),如果需要兼容Windows XP可以将`WindowsSupportedOSPlatformVersion`调整为`5.1`。 + +### 2.2. 手工配置 1. 下载 [YY-Thunks-Binary](https://github.com/Chuyu-Team/YY-Thunks/releases), 然后解压到你的工程目录。 @@ -56,11 +62,9 @@ YY-Thunks(鸭船),存在的目的就是抹平不同系统的差异,编 > 温馨提示:如果需要兼容 Vista,【所需的最低版本】无需修改,但是【附加依赖项】请选择 `objs\$(PlatformShortName)\YY_Thunks_for_Vista.obj`。 -> 如果不清楚链接器相关配置,建议使用NuGet通道,它自动配置相关设置,降低使用门槛。 - -## 兼容性 +## 3. 兼容性 -### 支持的编译器 +### 3.1. 支持的编译器 全平台ABI兼容。 @@ -68,16 +72,16 @@ YY-Thunks(鸭船),存在的目的就是抹平不同系统的差异,编 (比如:VC6.0、VS2008、VS2010、VS2015、VS2017、VS2019、VS2022等等)。 * 所有运行库模式均支持(比如:`/MD`、`/MT`、`/MDd`、`/MTd`)。 -### SDK版本要求 +### 3.2. SDK版本要求 至少需要SDK 6.0(VS2008默认附带) > 温馨提示:VC6.0、VS2005用户请注意,由于这些编译器默认附带的SDK版本太低。请先将SDK升级到6.0或者更高版本,然后再使用YY-Thunks,否则将发生链接失败! 高版本的SDK不影响对老系统的兼容性,请坐和放宽,安心升级。 -### Thunks 清单 +### 3.3. Thunks 清单 请参阅 [ThunksList.md](ThunksList.md) -## 更新日志 +## 4. 更新日志 请参阅 [releases 更新日志](https://github.com/Chuyu-Team/YY-Thunks/releases) diff --git a/ThunksList.md b/ThunksList.md index 53184aa..d5a38d5 100644 --- a/ThunksList.md +++ b/ThunksList.md @@ -2,7 +2,7 @@ 此表展示了YY-Thunks(鸭船)可以解决的函数不存在问题,欢迎大家扩充! -> 开头带`*`的函数并不建议使用,仅用于编译通过处理,如果使用可能导致老版本系统无法充分发挥性能。 +> 开头带`*`的函数并不建议使用,存在一些较大负面影响,仅用于编译通过处理,具体负面影响可参考注释内容。 ## api-ms-win-core-path-l1-1-0.dll | 函数 | Fallback @@ -227,14 +227,14 @@ | WaitOnAddress | 不存在时,调用NtWaitForKeyedEvent。警告,此函数请勿跨模块使用!!! | WakeByAddressSingle | 不存在时,调用NtReleaseKeyedEvent。警告,此函数请勿跨模块使用!!! | WakeByAddressAll | 不存在时,调用NtReleaseKeyedEvent。警告,此函数请勿跨模块使用!!! -| *GetCurrentProcessorNumber | 不存在时,返回0。 -| *GetCurrentProcessorNumberEx | 不存在时,调用GetCurrentProcessorNumber。 -| *GetNumaNodeProcessorMask | 不存在时,假定所有CPU都在当前Numa。 -| *GetNumaNodeProcessorMaskEx | 不存在时,调用GetNumaNodeProcessorMask。 -| *GetThreadGroupAffinity | 不存在时,调用NtQueryInformationThread。 -| *SetThreadGroupAffinity | 不存在时,调用SetThreadAffinityMask。 -| *CancelIoEx | 不存在时,调用CancelIo(会把此句柄的所有IO操作取消掉!)。 -| *CancelSynchronousIo | 不存在时,仅返回失败。 +| GetCurrentProcessorNumber | 不存在时,调用cpuid。 +| GetCurrentProcessorNumberEx | 不存在时,调用GetCurrentProcessorNumber。 +| GetNumaNodeProcessorMask | 不存在时,假定所有CPU都在当前Numa。 +| GetNumaNodeProcessorMaskEx | 不存在时,调用GetNumaNodeProcessorMask。 +| GetThreadGroupAffinity | 不存在时,调用NtQueryInformationThread。 +| SetThreadGroupAffinity | 不存在时,调用SetThreadAffinityMask。 +| *CancelIoEx | 不存在时,调用CancelIo。警告,会把此句柄的所有IO操作取消掉! +| *CancelSynchronousIo | 不存在时,仅返回失败。警告,实际无法取消! | OpenFileById | 不存在时,调用NtCreateFile。 | CreateSymbolicLinkW(A) | 不存在时,返回FALSE,并设置 LastError = ERROR_INVALID_FUNCTION。 | ReOpenFile | 不存在时,调用NtCreateFile。 diff --git a/src/Thunks/api-ms-win-core-processthreads.hpp b/src/Thunks/api-ms-win-core-processthreads.hpp index 84aff14..27e3a6a 100644 --- a/src/Thunks/api-ms-win-core-processthreads.hpp +++ b/src/Thunks/api-ms-win-core-processthreads.hpp @@ -75,14 +75,27 @@ namespace YY VOID ) { - if (auto pGetCurrentProcessorNumber = try_get_GetCurrentProcessorNumber()) + if (const auto _pfnGetCurrentProcessorNumber = try_get_GetCurrentProcessorNumber()) { - return pGetCurrentProcessorNumber(); + return _pfnGetCurrentProcessorNumber(); } else { - //如果不支持此接口,那么假定是单核 - return 0; + // Reference: https://www.cs.tcd.ie/Jeremy.Jones/GetCurrentProcessorNumberXP.htm + // + // The GetCurrentProcessorNumber() function is not available in XP. + // Here is a VC++ version of the function that works with Windows XP on Intel x86 single, hyperthreaded, multicore + // and multi-socket systems. It makes use of the APIC ID returned by the CPUID instruction. + // This is in the range 0 .. N-1, where N is the number of logical CPUs. + + __asm + { + mov eax, 1 + cpuid + shr ebx, 24 + // eax 返回值 + mov eax, ebx + } } } #endif