当ReadConsoleOutputCharacterW返回的字符串具有特定长度时,wcslen会静默退出

wcslen quits silently when string returned by the ReadConsoleOutputCharacterW has some particular length

本文关键字:wcslen 退出 静默 返回 ReadConsoleOutputCharacterW 字符串      更新时间:2023-10-16

编译器:http://sourceforge.net/projects/mingwbuilds/files/

#include <iostream>
#include <string.h>
#include <windows.h>
using namespace std;
  const wchar_t* readConsole(int chars_to_read) {
    wchar_t* wcharFromConsole = new wchar_t[chars_to_read+1];
    COORD pos = {0,0};
    DWORD dwChars;
    if (!ReadConsoleOutputCharacterW(
      GetStdHandle(STD_OUTPUT_HANDLE),
      wcharFromConsole,  // Buffer where store symbols
      chars_to_read,     // number of chars to read
      pos,    // Read from row=8, column=6
      &dwChars // How many symbols stored
    ))
    {
      printf("ReadConsoleOutputCharacterW failed %dn", GetLastError());
      abort();
    }
    wcharFromConsole [dwChars] = L''; // Terminate, so string functions can be used
    wstring ws = wcharFromConsole;
    return ws.c_str();
  }
int main() {
  for (int i = 1; i<=0x3000; i++) {
    printf("wcslen: %X n",wcslen(readConsole(i)));
  }
  system("pause");
}

此循环在0x1FF1处结束,并且不调用暂停。删除wstring似乎可以解决这个问题。但我需要它在这里用于修剪空白等功能。它在这里没有太大的相关性,但为什么调用wstring会导致这个问题呢?没有错误消息,程序简单地退出。

更新的代码,现在循环退出0x2BBF

#include <iostream>
#include <string.h>
#include <windows.h>
using namespace std;
  const wchar_t* readConsole(int chars_to_read) {
    wchar_t* wcharFromConsole = new wchar_t[chars_to_read+1];
    COORD pos = {0,0};
    DWORD dwChars;
    if (!ReadConsoleOutputCharacterW(
      GetStdHandle(STD_OUTPUT_HANDLE),
      wcharFromConsole,  // Buffer where store symbols
      chars_to_read,     // number of chars to read
      pos,    // Read from row=8, column=6
      &dwChars // How many symbols stored
    ))
    {
      printf("ReadConsoleOutputCharacterW failed %dn", GetLastError());
      abort();
    }
    wcharFromConsole [dwChars] = L''; // Terminate, so string functions can be used
    wstring ws = wcharFromConsole;
    delete [] wcharFromConsole;
    const wchar_t* wc = ws.c_str();
    return wc;
  }
int main() {
  for (int i = 1; i<=0x3000; i++) {
    printf("wcslen: %X n",wcslen(readConsole(i)));
  }
  system("pause");
}

哎哟。

wstring ws = wcharFromConsole;
return ws.c_str();

基本上,你在这里返回了一个死指针。字符串将在返回时被销毁,因此到达调用方的指针将无效。

编辑:你也在泄露内存,因为"新"永远不会被删除。但这通常不会引起明显的问题,只会增加程序的内存使用量。