2403d,d的com哪里错了
原文
感谢任意见解.细节:
>dmd --version
DMD64 D Compiler v2.107.0
参考:
ComObject类
IUnknown接口
我只使用了ComObject类和隐式继承了IUnknown接口,用用ImportC编译并包含以下内容的comheaders.c编写了一些COM测试代码.
#define WINVER 0x0A00
#define _WIN32_WINNT 0x0A00
#define _WIN32_DCOM
#include <wtypes.h>
#include <oleauto.h>
#include <oaidl.h>
用来编译的main.d文件如下.
import std.stdio;
import comheaders;
static import com = core.sys.windows.com;
pragma(lib, "onecore"); //修复两个不相关符号的链接
void main() {auto COMobject = new com.ComObject();//auto COMobject = new ComObject();IUnknown* ip = cast(IUnknown*)COMobject;writeln(COMobject.count);writeln(" ip 虚表: ", ip.lpVtbl);auto 虚表 = COMobject.__vptr;writeln("COMobject 虚表: ", 虚表);writeln("ip &AddRef: ", &ip.lpVtbl.AddRef);writeln("ip offset: ", cast(void*)&ip.lpVtbl.AddRef - cast(void*)ip.lpVtbl);auto ipaddref = cast(void*)ip.lpVtbl.AddRef;writeln(" ip AddRef: ", ipaddref);auto addref = cast(void*)(&COMobject.AddRef).funcptr;writeln("COMobject AddRef: ", addref);writeln("COMobject AddRef : ip AddRef offset: ", addref - ipaddref);COMobject.AddRef();writeln(COMobject.count);ip.lpVtbl.AddRef(ip);writeln(COMobject.count);
}
在此,我从静态导入的core.sys.windows.com创建了一个ComObject,但避免使用D窗口库中的其他内容.该对象包含一个应调用AddRef递增的引用计数.输出如下.
0ip 虚表: 7FF756091A30
COMobject 虚表: 7FF756091A30
ip &AddRef: 7FF756091A38
ip offset: 8ip AddRef: 7FF756027970
COMobject AddRef: 7FF756022EC0
COMobject AddRef : ip AddRef offset: -19120
1
1
即,正确偏移的AddRef调用未干活,且与com.ComObject中AddRef的函数指针不同.因此,无法同外部世界代码正常工作.用
dmd main.d comheaders.c vcintrinsics.lib -P/wd5105
编译,vcintrinsics.lib是我构建的解决DMD不知道一系列MSVC内部函数的问题的一个库,即按此处满足链接器的,而-P/wd5105是在ImportC用作C预处理器时,用来抑制MSVC警告.
我在unknwn.d中,复制了不方便命名的IUnknown接口的源码,并从com.d复制了ComObject类的源码,两者都在C:\D\dmd2\src\druntime\src\core\sys\windows\中.
进入main.d的底部并实验.我用上面活动的注释行,新建了个本地ComObject.一项更改解决了该问题:使用extern(C++),其他链接属性不工作.
这是工作代码.我不得不编辑IUnknown接口,但现在是comheaders.c中的一个结构,在QueryInterface中,并编辑到IUnknown*,并把E_NOINTERFACE编辑到com.E_NOINTERFACE.
并用与IUnknown结构不同的名字定义D接口,所以我设置它为_IUnknown_,但除此外,除了不使用extern(Windows)并以extern(C++)为前缀外,源码不变.
这是main.d的其余部分.
import core.atomic;
extern(C++):
interface _IUnknown_ {HRESULT QueryInterface(IID* riid, void** pvObject);ULONG AddRef();ULONG Release();
}
class ComObject : _IUnknown_
{HRESULT QueryInterface(const(IID)* riid, void** ppv){if (*riid == IID_IUnknown){*ppv = cast(void*)cast(IUnknown*)this;AddRef();return S_OK;}else{ *ppv = null;return com.E_NOINTERFACE;}}ULONG AddRef(){return atomicOp!"+="(*cast(shared)&count, 1);}ULONG Release(){LONG lRef = atomicOp!"-="(*cast(shared)&count, 1);if (lRef == 0){//`free`对象,如果删除该对象,则从`Release()`返回时调用的`postinvariant`将失败.让`GC`收获吧.`删 本;`return 0;}return cast(ULONG)lRef;}LONG count = 0;//对象引用计数
}
现在如下输出:
0ip 虚表: 7FF76B9C0360
COMobject 虚表: 7FF76B9C0360
ip &AddRef: 7FF76B9C0368
ip offset: 8ip AddRef: 7FF76B951580
COMobject AddRef: 7FF76B951580
COMobject AddRef : ip AddRef offset: 0
1
2
显示在ComObjects虚表中,查找AddRef会生成与通过COM接口相同的函数指针,且两者都工作.
工作假设:通过导入core.sys.windows.com引入的ComObject和IUnknown都被破坏了,这是Phobos中对COM的所有支持.请确认或拒绝.
你错误地声明了接口变量.试试如下:
auto COMobject = new com.ComObject();
//auto COMobject = new ComObject();
IUnknown ip = COMobject;
writeln(COMobject.count);
writeln(" ip 虚表: ", ip.lpVtbl);
auto 虚表 = COMobject.__vptr;
writeln("COMobject 虚表: ", 虚表);
writeln("ip &AddRef: ", &ip.lpVtbl.AddRef);
writeln("ip offset: ", cast(void*)&ip.lpVtbl.AddRef - cast(void*)ip.lpVtbl);
auto ipaddref = cast(void*)ip.lpVtbl.AddRef;
writeln(" ip AddRef: ", ipaddref);
auto addref = cast(void*)(&COMobject.AddRef).funcptr;
writeln("COMobject AddRef: ", addref);
writeln("COMobject AddRef : ip AddRef offset: ", addref - ipaddref);
COMobject.AddRef();
writeln(COMobject.count);
ip.lpVtbl.AddRef(ip);
writeln(COMobject.count);
相关文章:
2403d,d的com哪里错了
原文 感谢任意见解.细节: >dmd --version DMD64 D Compiler v2.107.0参考: ComObject类 IUnknown接口 我只使用了ComObject类和隐式继承了IUnknown接口,用用ImportC编译并包含以下内容的comheaders.c编写了一些COM测试代码. #define WINVER 0x0A00 #define _WIN32_WINNT…...
LeetCode151:反转字符串中的单词
题目描述 给你一个字符串 s ,请你反转字符串中 单词 的顺序。 单词 是由非空格字符组成的字符串。s 中使用至少一个空格将字符串中的 单词 分隔开。 返回 单词 顺序颠倒且 单词 之间用单个空格连接的结果字符串。 注意:输入字符串 s中可能会存在前导空…...
Linux入门-常见指令及权限理解
目录 1、Linux背景 1.1、发展历史 1.2、开源 1.3Linux企业应用现状 2、Linux下的基本命令 2.1、ls 指令 2.2、pwd 命令 2.3、cd 命令 2.4、touch命令 2.5、mkdir 命令 2.6、rmdir 指令和 rm指令 2.7 man 指令 2.8、cp指令 2.9、mv 指令 2.10 cat 2.11 more 2…...
找工作的经验总结一——渠道与简历
关于简历与面试的经验总结,也可以说是关于找工作的方法论。 这里我们用第一性原理的方法论来分析找工作这件事。 首先,我们的目的是什么? 当然是找工作,不论你是大学刚毕业,还是创业失败,或者是在家闲着…...
第 126 场 LeetCode 双周赛题解
A 求出加密整数的和 模拟 class Solution { public:int sumOfEncryptedInt(vector<int> &nums) {int res 0;for (auto x: nums) {string s to_string(x);char ch *max_element(s.begin(), s.end());for (auto &c: s)c ch;res stoi(s);}return res;} };B 执行…...
固态浸压计
Solid State Dip Meter(固态浸没仪/固态浸压计) 是真空管栅极浸入式仪表的固态半导体版本。它是一种用于测量 LC 电路谐振频率的仪器。LC 电路是由电感 (L) 和电容 (C) 组成的电路。当电感的感抗与电容的容抗相互抵消时,这些元件可以谐振于特定频率。 固态浸入式仪…...
Ubuntu上搭建TFTP服务
Ubuntu上搭建TFTP服务 TFTP服务简介搭建TFTP服务安装TFTP服务修改配置文件 重启服务 TFTP服务简介 TFTP是一个基于UDP协议实现的用于在客户机和服务器之间进行简单文件传输的协议,适用于开销不大、不复杂的应用场合。TFTP协议专门为小文件传输而设计,只…...
SpringBoot3框架,事件和监听器、SPI
事件和监听器 生命周期监听 自定义监听器的步骤: 编写SpringApplicationRunListener实现类(各个实现方法的功能写在其sout内) public class MyAppListener implements SpringApplicationRunListener {Overridepublic void starting(Configu…...
sadtalker-api/
———— 下载sadtalker工程文件,包括844个模型 。。。。。。。。。。。。。。。。 配置环境: pip源,设置: pip config set global.index-url https://pypi.tuna.tsinghua.edu.cn/simple anaconda prompt, 进入命令行 how在 …...
vue+elementUI实现指定列的单元格可编辑
template中的代码如下: <div v-if"(item.label 高压侧 || item.label 低压侧)&&coloumnHeader.label 单柱片数"><div class"editableCell"><div v-if"item.label 高压侧" dblclick"changeValue(sco…...
RK3568平台开发系列讲解(基础篇)内核是如何发送事件到用户空间
🚀返回专栏总目录 文章目录 一、相关接口函数二、udevadm 命令三、实验沉淀、分享、成长,让自己和他人都能有所收获!😄 一、相关接口函数 kobject_uevent 是 Linux 内核中的一个函数, 用于生成和发送 uevent 事件。 它是 udev 和其他设备管理工具与内核通信的一种方式。…...
力扣---打家劫舍---动态规划
思路 1: 我将res[i]定义为:一定要取第 i 个房子的前提下,能获取的最大金额。那么直接用cnt从头记录到尾,每个房子的res最大值即是答案。那么递推公式是什么?res[i]max(res[i-2],res[i-1],...,res[0])nums[i]。数组初始…...
mac安装rust环境
mac安装rust环境 老规矩官方文档 1. mac官网使用的是脚本安装, 至于为啥没使用brew也没推荐俺也不太清楚 curl --proto https --tlsv1.2 -sSf https://sh.rustup.rs | sh2. 一般来说中途会遇见有一个选择我这里选择直接回车默认安装(如果以后我研究明白的话会进行更新, 现在是…...
1058:求一元二次方程
【题目描述】 利用公式 求一元二次方程axbxc0的根,其中a不等于0。结果要求精确到小数点后5位。 【输入】 输入一行,包含三个浮点数a,b,c(它们之间以一个空格分开),分别表示方程axbxc0的系数。 【输出】 输出一行&…...
GraphQL入门之一对多关联查询
创建 Node.js 的工程 mkdir myapp cd myapp npm init (一路回车)安装依赖包 npm install apollo/server graphql定义 Schema 创建 schema.graphql 文件,内容如下: type Book {title: String!author: Author! }type Author {name: String!books: [Boo…...
MATLAB和Python数值和符号计算可视化物理学气体动能和粒子速度
要点 Python物理学差分数值和符号计算 热动力学计算:统计力学,分子动力学模型 Python寻找弹性物体的运动,LAMMPS 分子动力学模拟器模拟2D气体分子,Python原子模拟绘图,Python数值计算原子平衡性,Python绘制…...
阿里云-零基础入门NLP【基于机器学习的文本分类】
文章目录 学习过程赛题理解学习目标赛题数据数据标签评测指标解题思路TF-IDF介绍TF-IDF 机器学习分类器TF-IDF LinearSVCTF-IDF LGBMClassifier 学习过程 20年当时自身功底是比较零基础(会写些基础的Python[三个科学计算包]数据分析),一开始看这块其实挺懵的&am…...
蓝桥杯模块综合——高质量讲解AT24C02,BS18B20,BS1302,AD/DA(PCF8591),超声波模块
AT24C02——就是一个存储的东西,可以给他写东西,掉电不丢失。 void EEPROM_Write(unsigned char * EEPROM_String,unsigned char addr , unsigned char num) {IIC_Start();IIC_SendByte(0xA0);IIC_WaitAck();IIC_SendByte(addr);IIC_WaitAck();while(nu…...
前端跨平台开发框架:简化多端开发的利器
🤍 前端开发工程师、技术日更博主、已过CET6 🍨 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 🕠 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》 🍚 蓝桥云课签约作者、上架课程《Vue.js 和 E…...
cesium.js加载模型后,重新设置旋转角度属性值
// 加载模型var position Cesium.Cartesian3.fromDegrees(longitude, latitude, height);// 计算矩阵var rollAngleDegrees 15; // 设置翻滚角度var rollAngleRadians Cesium.Math.toRadians(rollAngleDegrees); // 将角度转换为弧度var orientation Cesium.Transforms.eas…...
Python|GIF 解析与构建(5):手搓截屏和帧率控制
目录 Python|GIF 解析与构建(5):手搓截屏和帧率控制 一、引言 二、技术实现:手搓截屏模块 2.1 核心原理 2.2 代码解析:ScreenshotData类 2.2.1 截图函数:capture_screen 三、技术实现&…...
多模态2025:技术路线“神仙打架”,视频生成冲上云霄
文|魏琳华 编|王一粟 一场大会,聚集了中国多模态大模型的“半壁江山”。 智源大会2025为期两天的论坛中,汇集了学界、创业公司和大厂等三方的热门选手,关于多模态的集中讨论达到了前所未有的热度。其中,…...
2.Vue编写一个app
1.src中重要的组成 1.1main.ts // 引入createApp用于创建应用 import { createApp } from "vue"; // 引用App根组件 import App from ./App.vue;createApp(App).mount(#app)1.2 App.vue 其中要写三种标签 <template> <!--html--> </template>…...
工程地质软件市场:发展现状、趋势与策略建议
一、引言 在工程建设领域,准确把握地质条件是确保项目顺利推进和安全运营的关键。工程地质软件作为处理、分析、模拟和展示工程地质数据的重要工具,正发挥着日益重要的作用。它凭借强大的数据处理能力、三维建模功能、空间分析工具和可视化展示手段&…...
微服务商城-商品微服务
数据表 CREATE TABLE product (id bigint(20) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT 商品id,cateid smallint(6) UNSIGNED NOT NULL DEFAULT 0 COMMENT 类别Id,name varchar(100) NOT NULL DEFAULT COMMENT 商品名称,subtitle varchar(200) NOT NULL DEFAULT COMMENT 商…...
JDK 17 新特性
#JDK 17 新特性 /**************** 文本块 *****************/ python/scala中早就支持,不稀奇 String json “”" { “name”: “Java”, “version”: 17 } “”"; /**************** Switch 语句 -> 表达式 *****************/ 挺好的ÿ…...
WEB3全栈开发——面试专业技能点P4数据库
一、mysql2 原生驱动及其连接机制 概念介绍 mysql2 是 Node.js 环境中广泛使用的 MySQL 客户端库,基于 mysql 库改进而来,具有更好的性能、Promise 支持、流式查询、二进制数据处理能力等。 主要特点: 支持 Promise / async-await…...
向量几何的二元性:叉乘模长与内积投影的深层联系
在数学与物理的空间世界中,向量运算构成了理解几何结构的基石。叉乘(外积)与点积(内积)作为向量代数的两大支柱,表面上呈现出截然不同的几何意义与代数形式,却在深层次上揭示了向量间相互作用的…...
SQL进阶之旅 Day 22:批处理与游标优化
【SQL进阶之旅 Day 22】批处理与游标优化 文章简述(300字左右) 在数据库开发中,面对大量数据的处理任务时,单条SQL语句往往无法满足性能需求。本篇文章聚焦“批处理与游标优化”,深入探讨如何通过批量操作和游标技术提…...
python基础语法Ⅰ
python基础语法Ⅰ 常量和表达式变量是什么变量的语法1.定义变量使用变量 变量的类型1.整数2.浮点数(小数)3.字符串4.布尔5.其他 动态类型特征注释注释是什么注释的语法1.行注释2.文档字符串 注释的规范 常量和表达式 我们可以把python当作一个计算器,来进行一些算术…...
