【问题标题】:How to get string from pointer如何从指针中获取字符串
【发布时间】:2014-04-11 06:50:21
【问题描述】:
GetWindowThreadProcessId(hwndFoundWindow, &dwTrayProcessID);
HANDLE  hTrayProc = OpenProcess(PROCESS_ALL_ACCESS, 0, dwTrayProcessID);
int iButtonsCount = SendMessage(hwndFoundWindow, TB_BUTTONCOUNT, 0, 0);
LPVOID  lpData = VirtualAllocEx(hTrayProc, NULL, sizeof(TBBUTTON), MEM_COMMIT, PAGE_READWRITE);
int         iButton;
DWORD       dwBytesRead;
TBBUTTON   buttonData;

dwBytesRead = -1;
int chk_data = (int)SendMessage(hwndFoundWindow, TB_GETBUTTON, iButton, (LPARAM)lpData);
ReadProcessMemory(hTrayProc, lpData, &buttonData, sizeof(TBBUTTON), &dwBytesRead);

int len_text = (int)SendMessage(hwndFoundWindow, TB_GETBUTTONTEXTW, buttonData.idCommand, (LPARAM)lpData);

到目前为止,我知道按钮文本的长度,但我还需要让文本显示在控制台上。 我的问题是我真的不知道如何从按钮中获取该文本。请帮忙。

我正在尝试的是...尝试访问 lpData 以获取其中的字符串,但无法做到。

【问题讨论】:

  • 如果缓冲区被'\0' 终止,那么您可以使用strcpy 将缓冲区内容复制到某个字符串。
  • 您的代码不完整,但显然是错误的。您没有显示调用 VirtualAlloc 以在其他进程中分配内存的代码。是你做的吗?您的代码完全错误。您要求一个以空字符结尾的字符串,然后尝试将其读入 TBBUTTON。您应该出示 SSCCE。
  • 我写了这个:LPVOID lpData = VirtualAllocEx(hTrayProc, NULL, sizeof(TBBUTTON), MEM_COMMIT, PAGE_READWRITE);
  • 你需要更加认真地对待我的 cmets。这是编辑问题所需的内容。 1. 明确说明您正在尝试做什么。 2. SSCCE。 3. 你解决问题的尝试如何失败的细节。
  • 我确实知道如何做我认为您正在尝试的事情。但我绝对不会帮助解决现在所处的状态。您需要按照我在上面 cmets 中概述的步骤来解决问题。你必须付出更多的努力。这是一个双向过程。你需要尽自己的一份力量。在您提出正确的问题之前,您不能希望问题得到解答。

标签: winapi


【解决方案1】:

我的第一条评论是您需要在代码中添加错误检查。据我所知,您没有检查返回值。您调用的任何 API 函数都可能失败。如果您不检查返回值是否有错误,那么您将无法诊断出哪里出错了。

例如,以GetWindowThreadProcessId开头,你需要这样写:

if (GetWindowThreadProcessId(hwndFoundWindow, &dwTrayProcessID) == 0)
{
    // handle error
}

对于所有其他功能,依此类推。请仔细查阅 MSDN,了解每个功能如何发出故障信号。

现在到问题的主要部分。我相信是TB_GETBUTTONTEXTW 消息给您带来了麻烦。你需要这样写:

LRESULT len = SendMessage(hwndFoundWindow, TB_GETBUTTONTEXTW, 
    buttonData.idCommand, NULL);
if (len == -1)
{
    // handle error
}

size_t size = sizeof(wchar_t)*(len+1);

LPVOID lpData = VirtualAllocEx(hTrayProc, NULL, size, MEM_COMMIT, PAGE_READWRITE);
if (lpData == NULL)
{
    // handle error
}

len = SendMessage(hwndFoundWindow, TB_GETBUTTONTEXTW, 
    buttonData.idCommand, (LPARAM)lpData);
if (len == -1)
{
    // handle error
}

wchar_t* str = new wchar_t[len+1];

if (!ReadProcessMemory(hTrayProc, lpData, (LPVOID)str, size, NULL))
{
    // handle error
}

// the text is now in str, as a null-terminated UTF-16 string

delete[] str;

【讨论】:

    【解决方案2】:

    你需要这个:(见documentation of TB_GETBUTTONTEXTW)。

    WCHAR *buffer ;
    int len_text = (int)SendMessage(hwndFoundWindow, TB_GETBUTTONTEXTW, 
                                    buttonData.idCommand, (LPARAM)NULL); 
    
    buffer = (WCHAR*)malloc(sizeof(WCHAR) * (len_text + 1)) ;
    SendMessage(hwndFoundWindow, TB_GETBUTTONTEXTW, 
                                    buttonData.idCommand, (LPARAM)buffer); 
    
    ....
    free(buffer) ;
    

    【讨论】:

    • 仔细看代码。内存处于不同的进程中。
    • @DavidHeffernan:我已经看到了,但我不确定这是否真的相关,因为我们对实际问题的信息很少。
    • Asker 正在尝试从 shell 进程中的通知图标中读取信息。赠品是 hTrayProc。问题严重不完整。提问者需要修复它。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-09-07
    • 1970-01-01
    • 1970-01-01
    • 2019-10-15
    • 2017-10-29
    • 1970-01-01
    • 2020-09-03
    相关资源
    最近更新 更多