吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 595|回复: 10
收起左侧

[已解决] C++ winapi 求助

[复制链接]
定位重构 发表于 2024-9-6 13:43
25吾爱币
请问大佬问什么 clion 会报错No matching function for call to 'CreateProcessA'
image.png

最佳答案

查看完整内容

不能是临时字符串,要先用一个变量存一下吧。 哦不对,应该是要求一个 char * 类型的,但是 s.c_str() 返回的是 const char * ,所以你要转成 char * 就行了。 (char *)(xxx + "xxx").c_str() 这样子应该可以。

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

DEATHTOUCH 发表于 2024-9-6 13:43
本帖最后由 DEATHTOUCH 于 2024-9-6 16:30 编辑
定位重构 发表于 2024-9-6 16:18
error C2664: “BOOL CreateProcessA(LPCSTR,LPSTR,LPSECURITY_ATTRIBUTES,LPSECURITY_ATTRIBUTES,BOOL,D ...

不能是临时字符串,要先用一个变量存一下吧。

哦不对,应该是要求一个 char * 类型的,但是 s.c_str() 返回的是 const char * ,所以你要转成 char * 就行了。

(char *)(xxx + "xxx").c_str()

这样子应该可以。
Eaglecad 发表于 2024-9-6 15:28
初步怀疑是字符集的问题,文件是 utf-8 也就是是参数大概率也是 utf-8。
CreateProcessA 最后一个A代表入参是 ASCII码。
使用CreateProcessW 试试 , 最后一个W代表宽字节 即unicode。或者通过转换编码实现参数合理化。
你好,再见 发表于 2024-9-6 15:29
 楼主| 定位重构 发表于 2024-9-6 15:38
Eaglecad 发表于 2024-9-6 15:28
初步怀疑是字符集的问题,文件是 utf-8 也就是是参数大概率也是 utf-8。
CreateProcessA 最后一个A代表入 ...

W之后依然报错
 楼主| 定位重构 发表于 2024-9-6 15:39
你好,再见 发表于 2024-9-6 15:29
你先把这个inject.cpp添加到cmakelists里面再说

已经添加了 还是报错
你好,再见 发表于 2024-9-6 16:05
定位重构 发表于 2024-9-6 15:39
已经添加了 还是报错

using namespace std去掉试试
编译器怎么报错的?

免费评分

参与人数 1吾爱币 +1 热心值 +1 收起 理由
定位重构 + 1 + 1 热心回复!

查看全部评分

 楼主| 定位重构 发表于 2024-9-6 16:18
你好,再见 发表于 2024-9-6 16:05
using namespace std去掉试试
编译器怎么报错的?

error C2664: “BOOL CreateProcessA(LPCSTR,LPSTR,LPSECURITY_ATTRIBUTES,LPSECURITY_ATTRIBUTES,BOOL,DWORD,LPVOID,LPCSTR,LPSTARTUPINFOA,LPPROCESS_INFORMATION)”: 无法将参数 2 从“const _Elem *”转换为“LPSTR”
        with
        [
            _Elem=char
        ]
 楼主| 定位重构 发表于 2024-9-6 17:20
DEATHTOUCH 发表于 2024-9-6 13:43
不能是临时字符串,要先用一个变量存一下吧。

哦不对,应该是要求一个 char * 类型的,但是 s.c_str() ...

请问 为什么是临时字符串 而下面第八个参数的c_str 却可以 是因为 字符串相加变成 const了吗
DEATHTOUCH 发表于 2024-9-6 17:40
本帖最后由 DEATHTOUCH 于 2024-9-6 17:43 编辑
定位重构 发表于 2024-9-6 17:20
请问 为什么是临时字符串 而下面第八个参数的c_str 却可以 是因为 字符串相加变成 const了吗

是这样的,我给你看一下 CreateProcessA 的函数签名:

[C++] 纯文本查看 复制代码
WINBASEAPI
BOOL
WINAPI
CreateProcessA(
    _In_opt_ LPCSTR lpApplicationName,
    _Inout_opt_ LPSTR lpCommandLine,
    _In_opt_ LPSECURITY_ATTRIBUTES lpProcessAttributes,
    _In_opt_ LPSECURITY_ATTRIBUTES lpThreadAttributes,
    _In_ BOOL bInheritHandles,
    _In_ DWORD dwCreationFlags,
    _In_opt_ LPVOID lpEnvironment,
    _In_opt_ LPCSTR lpCurrentDirectory,
    _In_ LPSTARTUPINFOA lpStartupInfo,
    _Out_ LPPROCESS_INFORMATION lpProcessInformation
    );


你看第一个和第二个和第八个有什么区别吗?
首先是标注,第一个和第八个都是 _In_opt_ ,表示可选输入参数,类型是 LPCSTR ,定义为 typedef _Null_terminated_ CONST CHAR *LPCSTR, *PCSTR;
看到了吧,是 const char* 类型的。

然后第二个是 _Inout_opt_ 的标注,说明是可选的输入/输出参数,类型则是 LPSTR ,即 typedef _Null_terminated_ CHAR *NPSTR, *LPSTR, *PSTR;
所以就是普通的 char* 类型。

看这个标注就说明了第二个参数是可变的,按照微软的文档内容 https://learn.microsoft.com/zh-c ... sapi-createprocessa
此函数的 Unicode 版本 CreateProcessW 可以修改此字符串的内容。 因此,此参数不能是指向只读内存 (的指针,例如 const 变量或文本字符串) 。 如果此参数是常量字符串,则函数可能会导致访问冲突。

你要明白,所有 A 结尾的 Windows API 函数都是内部调用了 W 结尾的 API,因为系统内部就是按照宽字符处理的。

由于 std::string 的 c_str() 返回的是 const char* ,这样就是为了防止出现被改变的情况。
如果强行把 (s + "aaa").c_str() 转成 char* ,反而不是很好,尤其是在临时字符串操作这个。
所以最合理的做法是搞一个 char 的数组,把你需要的参数拷贝到这个数组,然后再传递给 CreateProcessA 去。
当然,这还需要保证安全,不要贪图省事,以免出现数组溢出的经典问题。

您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-12-15 18:57

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表