0

インジェクション用のDLLがあります。これは、CBT フックを介して注入されます。これで、CBT 経由で目的のプロセスに遭遇したときに、WinAPI の ExtTextOutW を自分のプロセスで迂回しました。ExtTextOutW の仕様は次のとおりです。


BOOL ExtTextOutW(HDC         hdc,
                 INT         x,
                 INT         y,
                 UINT        flags,
                 const RECT* lprect,
                 LPCWSTR     str,
                 UINT        count,
                 const INT*  lpDx)

回り道した ExtTextOutW で、次のコードを使用して str (LPCWSTR) をマルチバイトに変換しようとしています。


BOOL Mine_ExtTextOutW(HDC         hdc,
                      INT         x,
                      INT         y,
                      UINT        flags,
                      const RECT* lprect,
                      LPCWSTR     str,
                      UINT        count,
                      const INT*  lpDx)
{
        BOOL rv = Real_ExtTextOutW(hdc, x, y, flags, lprect, str, count, lpDx);

        HANDLE h = ::WindowFromDC(hdc);

        if (!h || !str)
                return ev;

        CHAR *buffer = (CHAR *)::LocalAlloc(count + 1);

        int l = ::WideCharToMultiByte(CP_APC, 0, str, count, buffer, count, NULL, NULL);

        if (l > -1) {
                buffer[l] = '\0';

                g_pClient->SendViaIPC(buffer);
        }

        ::LocalFree(buffer);

        return rv;
}

残念ながら、これは機能しません。WideCharToMultiByte は、挿入されたプロセスをハングさせます。なんで?

4

2 に答える 2

2

あなたのコードは少し奇妙に見えます、それはコンパイルされますか?

LocalAllocには2つのパラメーターが必要ですが、CP_ACPを意味しますか。とにかく代わりに私は:

  • 将来コードページを変更する場合に備えて、WideCharToMultiByteに正しいサイズを尋ねてください。
  • > 0をチェックします(失敗は-1ではなく0で表されます)
  • メモリリークや例外などがないことを確認するためだけにstd文字列を使用してください。

だからこのようなもの:

int nMultiByteSize = ::WideCharToMultiByte( CP_ACP, NULL, str, count, NULL, 0, NULL, NULL );
if ( nMultiByteSize > 0 )
{
    std:string strMulti;
    strMulti.resize( nMultiByteSize );

    if ( ::WideCharToMultiByte( CP_ACP, NULL, str, count, &strMulti[0], (int)strMulti.size(), NULL, NULL ) > 0)
    {
        g_pClient->SendViaIPC(strMulti.c_str());
    }
}
于 2009-09-06T16:34:36.013 に答える
0

なぜプロセスがハングしているのかわかりませんが、正しく動作するはずです。それを引き起こしているのは WC2MB 呼び出しであると確信していますか? いくつかの可能性:

  1. なぜ LocalAlloc を使用しているのですか? スタックでバッファを使用するだけでは十分ではありませんか?
  2. たぶん、ハングしているのは「SendViaIPC」ですか?
  3. 変換する文字列の大きさは? バッファのサイズが不足している可能性がありますか?

WC2MB の戻り値は?成功しなかった場合、関数は 0 を返します。

LocalAlloc からの戻り値は何ですか? おそらく、メモリの割り当てに失敗したことを示す割り当てが null を返しているのでしょうか? 次に、バッファに NULL を渡しますが、カウントに 0 より大きい数値を渡すと、クラッシュにつながる可能性があります。

于 2009-09-04T09:09:46.260 に答える