clean a lot of stuff up and improve extension support. not sure that i still have thread safety though...

This commit is contained in:
Akash Mozumdar 2018-07-11 20:18:04 -04:00
parent 9da6875444
commit 423ee9efac
9 changed files with 61 additions and 263 deletions

View File

@ -30,11 +30,6 @@ extern HWND hMainWnd; // windows.cpp
extern bool MonitorFlag; // ProfileManager.cpp
extern ProfileManager* pfman; // ProfileManager.cpp
extern "C" {
BOOL IthInitSystemService();
void IthCloseSystemService();
}
HookManager* man;
Settings* setman;
LONG split_time, cyclic_remove, global_filter;
@ -43,27 +38,6 @@ auto_inject, auto_insert, clipboard_flag;
std::map<std::wstring, long> setting;
void RecordMBChar(WORD mb, PVOID f)
{
auto filter = (pugi::xml_node*)f;
DWORD m = mb;
WCHAR buffer[16];
std::swprintf(buffer, L"m%04X", m);
filter->append_attribute(buffer) = L"0";
}
void RecordUniChar(WORD uni, PVOID f)
{
auto filter = (pugi::xml_node*)f;
DWORD m = uni;
WCHAR buffer[16];
std::swprintf(buffer, L"u%04X", m);
filter->append_attribute(buffer) = L"0";
std::wstring text = filter->text().get();
text += (wchar_t)m;
filter->text().set(text.c_str());
}
void SaveSettings()
{
WINDOWPLACEMENT wndpl;

View File

@ -369,33 +369,14 @@ void ClickButton(HWND hWnd, HWND h)
}
}
DWORD ThreadOutput(TextThread* thread, BYTE* out, DWORD len, DWORD new_line)
DWORD ThreadOutput(TextThread* thread, const BYTE* out, DWORD len, DWORD new_line)
{
if (len == 0)
return len;
DWORD status = thread->Status();
if (status & CURRENT_SELECT)
{
if (new_line)
{
if (thread->Number() == 0)
texts->AddText(L"\r\n", 2, true);
else
texts->AddText(L"\r\n\r\n", 4, true);
}
else if (status & USING_UNICODE)
{
texts->AddText((LPWSTR)out, len / 2, false);
}
else
{
int uni_len = MB_WC_count((char*)out, len);
LPWSTR str = new WCHAR[uni_len + 1];
MB_WC((char*)out, str, uni_len + 1);
str[uni_len] = L'\0';
texts->AddText(str, uni_len, false);
delete str;
}
texts->AddText((LPWSTR)out, len / 2, false);
}
return len;
}
@ -493,24 +474,13 @@ DWORD ThreadReset(TextThread* thread)
texts->ClearBuffer();
man->SetCurrent(thread);
thread->LockVector();
DWORD uni = thread->Status() & USING_UNICODE;
if (uni)
{
DWORD len = 0;
LPWSTR wc = (LPWSTR)thread->GetStore(&len);
len /= 2;
wc[len] = L'\0';
SetEditText(wc);
}
else
{
DWORD len = MB_WC_count((char*)thread->Storage(), thread->Used());
LPWSTR wc = new WCHAR[len + 1];
MB_WC((char*)thread->Storage(), wc, len + 1);
wc[len] = L'\0';
SetEditText(wc);
delete wc;
}
DWORD len = 0;
LPWSTR wc = (LPWSTR)thread->GetStore(&len);
len /= 2;
wc[len] = L'\0';
SetEditText(wc);
WCHAR buffer[16];
std::swprintf(buffer, L"%04X", thread->Number());
DWORD tmp = ComboBox_FindString(hwndCombo, 0, buffer);

View File

@ -1,7 +1,7 @@
#include "Extensions.h"
#include <Windows.h>
#include <map>
typedef void(*ExtensionFunction)(LPCWSTR, DWORD64);
#include <vector>
std::map<DWORD, ExtensionFunction> extensionFunctions;
@ -16,23 +16,21 @@ void LoadExtensions()
HANDLE file = FindFirstFileW(path, &fileData);
do
{
if (fileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
{
}
else
if (!(fileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
{
if (wcsstr(fileData.cFileName, L"_nexthooker_extension.dll"))
{
extensionFunctions[wcstoul(fileData.cFileName, nullptr, 10)] = (ExtensionFunction)GetProcAddress(LoadLibraryW(fileData.cFileName), "OnSentence");
extensionFunctions[wcstoul(fileData.cFileName, nullptr, 10)] = (ExtensionFunction)GetProcAddress(LoadLibraryW(fileData.cFileName), "NewSentence");
}
}
} while (FindNextFileW(file, &fileData) != 0);
}
void DispatchSentenceToExtensions(LPCWSTR sentence, DWORD64 info)
std::wstring DispatchSentenceToExtensions(std::wstring sentence, DWORD64 info)
{
for (auto extension : extensionFunctions)
{
extension.second(sentence, info);
sentence = extension.second(sentence, info);
}
return sentence;
}

View File

@ -1,5 +1,6 @@
#include <Windows.h>
#include <string>
typedef void(*ExtensionFunction)(LPCWSTR, DWORD64);
typedef std::wstring (*ExtensionFunction)(std::wstring, DWORD64);
void LoadExtensions();
void DispatchSentenceToExtensions(LPCWSTR sentence, DWORD64 info);
std::wstring DispatchSentenceToExtensions(std::wstring sentence, DWORD64 info);

View File

@ -304,7 +304,7 @@ void HookManager::DispatchText(DWORD pid, const BYTE *text, DWORD hook, DWORD re
create(it);
}
}
it->AddText(text, len, false);
it->AddText(text, len);
}
void HookManager::AddConsoleOutput(LPCWSTR text)
@ -314,8 +314,7 @@ void HookManager::AddConsoleOutput(LPCWSTR text)
int len = wcslen(text) * 2;
TextThread *console = threadTable[{0, -1UL, -1UL, -1UL}];
//EnterCriticalSection(&hmcs);
console->AddText((BYTE*)text,len,false);
console->AddText((BYTE*)L"\r\n",4,false);
console->AddSentence(std::wstring(text));
//LeaveCriticalSection(&hmcs);
}
}

View File

@ -41,7 +41,7 @@ DWORD WINAPI TextReceiver(LPVOID lpThreadParameter)
Pipes* pipes = (Pipes*)lpThreadParameter;
ConnectNamedPipe(pipes->hookPipe, nullptr);
BYTE* buffer = new BYTE[PIPE_BUFFER_SIZE];
BYTE buffer[PIPE_BUFFER_SIZE] = {};
DWORD bytesRead, processId;
// Artikash 5/20/2018: Shouldn't Windows automatically close the handles when the host process stops running?
@ -111,7 +111,6 @@ DWORD WINAPI TextReceiver(LPVOID lpThreadParameter)
man->UnRegisterProcess(processId);
LeaveCriticalSection(&detachCs);
delete[] buffer;
delete pipes;
return 0;

View File

@ -33,86 +33,56 @@ DWORD GetHookName(LPSTR str, DWORD pid, DWORD hook_addr,DWORD max);
extern Settings *settings;
extern HWND dummyWindow;
void CALLBACK NewLineBuff(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
{
KillTimer(hwnd,idEvent);
TextThread *id=(TextThread*)idEvent;
id->DispatchLastSentence();
//id->SendLastToExtension();
id->SetNewLineFlag();
}
TextThread::TextThread(ThreadParameter tp, WORD num) :
//,tp
thread_number(num)
, output(nullptr)
//, comment(nullptr)
, timer(0)
, status (0)
, last_sentence(0)
, sentence_length(0)
, status(0)
, tp(tp)
, sentenceBuffer()
{
}
void TextThread::Reset()
{
//timer=0;
last_sentence = 0;
//if (comment) {
// delete[] comment;
// comment = nullptr;
//}
MyVector::Reset();
}
void TextThread::AddLineBreak()
void TextThread::AddSentence()
{
if (sentence_length == 0) return;
if (status&BUFF_NEWLINE)
{
sentence_length=0;
if (status & USING_UNICODE)
AddToStore((BYTE *)L"\r\n\r\n", 8);
else
AddToStore((BYTE *)"\r\n\r\n", 4);
if (output)
output(this, 0, 8, TRUE); // jichi 10/27/2013: space is false
last_sentence = used;
status &= ~BUFF_NEWLINE;
}
std::wstring sentence;
if (status & USING_UNICODE)
{
sentence = std::wstring((wchar_t*)sentenceBuffer.data(), sentenceBuffer.size() / 2);
}
else
{
wchar_t* converted = new wchar_t[sentenceBuffer.size()];
sentence = std::wstring(converted, MultiByteToWideChar(932, 0, sentenceBuffer.data(), sentenceBuffer.size(), converted, sentenceBuffer.size()));
delete[] converted;
}
AddSentence(DispatchSentenceToExtensions(sentence, status));
sentenceBuffer.clear();
}
void TextThread::AddText(const BYTE *con, int len, bool new_line)
void TextThread::AddSentence(std::wstring sentence)
{
sentence.append(L"\r\n\r\n");
if (output) output(this, (const BYTE*)sentence.c_str(), sentence.length() * 2, false);
AddToStore((const BYTE*)sentence.c_str(), sentence.length() * 2);
}
if (status & BUFF_NEWLINE)
AddLineBreak();
if (len)
if (new_line) {
last_sentence = used + 4;
if (status & USING_UNICODE)
last_sentence += 4;
sentence_length = 0;
} else {
SetNewLineTimer();
sentence_length += len;
}
if (len <= 0) return;
BYTE *data = const_cast<BYTE *>(con); // jichi 10/27/2013: TODO: Figure out where con is modified
if (output)
len = output(this, data, len, new_line);
if (AddToStore(data, len)) {
//sentence_length += len;
/*ResetRepeatStatus();
last_sentence=0;
prev_sentence=0;
sentence_length=len;
repeat_index=0;
status&=~REPEAT_DETECT|REPEAT_SUPPRESS; */
}
void TextThread::AddText(const BYTE *con, int len)
{
sentenceBuffer.insert(sentenceBuffer.end(), con, con+len);
SetTimer(dummyWindow, (UINT_PTR)this, settings->splittingInterval,
[](HWND hWnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
{
KillTimer(hWnd, idEvent);
((TextThread*)idEvent)->AddSentence();
});
}
void TextThread::GetEntryString(LPSTR buffer, DWORD max)
@ -121,114 +91,5 @@ void TextThread::GetEntryString(LPSTR buffer, DWORD max)
thread_number, tp. pid, tp.hook, tp.retn, tp.spl);
GetHookName(buffer + len, tp.pid, tp.hook, max - len);
}
// jichi 9/28/2013: removed
//void TextThread::CopyLastSentence(LPWSTR str)
//{
// int i,j,l;
// if (status&USING_UNICODE)
// {
// if (used>8)
// {
// j=used>0xF0?(used-0xF0):0;
// for (i=used-0xA;i>=j;i-=2)
// {
// if (*(DWORD*)(storage+i)==0xA000D) break;
// }
// if (i>=j)
// {
// l=used-i;
// if (i>j) l-=4;
// j=4;
// }
// else
// {
// i+=2;
// l=used-i;
// j=0;
// }
// memcpy(str,storage+i+j,l);
// str[l>>1]=0;
// }
// else
// {
// memcpy(str,storage,used);
// str[used>>1]=0;
// }
// }
// else
// {
// if (used>4)
// {
// j=used>0x80?(used-0x80):0;
// for (i=used-5;i>=j;i--)
// {
// if (*(DWORD*)(storage+i)==0xA0D0A0D) break;
// }
// if (i>=j)
// {
// l=used-i;
// if (i>j) l-=4;
// j=4;
// }
// else
// {
// i++;
// l=used-i;
// j=0;
// }
// size_t sz = (l|0xF) + 1;
// char *buff = new char[sz];
// //memset(buff, 0, sz); // jichi 9/26/2013: zero memory
// memcpy(buff, storage + i + j, l);
// buff[l] = 0;
// str[MB_WC(buff, str)] = 0;
// delete[] buff;
// } else {
// storage[used] = 0;
// str[MB_WC((char *)storage, str)] = 0;
// }
// }
//}
// jichi 8/25/2013: clipboard removed
void DispatchSentence(void* str,DWORD status, int len)
{
char sentenceBuffer[0x400];
if (str && len > 0)
{
int size=(len*2|0xF)+1;
if (len>=1022) return;
memcpy(sentenceBuffer,str,len);
*(WORD*)(sentenceBuffer+len)=0;
HGLOBAL hCopy;
wchar_t copy[0x400];
if (status&USING_UNICODE)
{
memcpy(copy, sentenceBuffer, len + 2);
}
else
{
MultiByteToWideChar(932, 0, sentenceBuffer, -1, copy, 0x400);
}
DispatchSentenceToExtensions(copy, status);
}
}
void TextThread::DispatchLastSentence()
{
// jichi 8/25/2013: clipboard removed
DispatchSentence(storage+last_sentence,status,used-last_sentence);
}
void TextThread::SetNewLineFlag() { status |= BUFF_NEWLINE; }
void TextThread::SetNewLineTimer()
{
if (thread_number == 0)
// jichi 10/27/2013: Not used
timer = 0; //SetTimer(dummyWindow,(UINT_PTR)this, settings->splittingInterval, NewLineConsole);
else
timer = SetTimer(dummyWindow, (UINT_PTR)this, settings->splittingInterval, NewLineBuff);
}
// EOF

View File

@ -6,6 +6,8 @@
#include "host/textthread_p.h"
#include <intrin.h> // require _InterlockedExchange
#include <string>
#include <vector>
struct RepeatCountNode {
short repeat;
@ -40,7 +42,7 @@ struct ThreadParameter {
class TextThread;
typedef void (* ConsoleCallback)(LPCSTR text);
typedef void (* ConsoleWCallback)(LPCWSTR text);
typedef DWORD (* ThreadOutputFilterCallback)(TextThread *, BYTE *, DWORD, DWORD);
typedef DWORD (* ThreadOutputFilterCallback)(TextThread *,const BYTE *, DWORD, DWORD);
typedef DWORD (* ThreadEventCallback)(TextThread *);
//extern DWORD split_time,repeat_count,global_filter,cyclic_remove;
@ -53,15 +55,11 @@ public:
virtual void GetEntryString(LPSTR buffer, DWORD max);
void Reset();
void AddText(const BYTE *con,int len, bool new_line); // jichi 10/27/2013: add const; remove console
void AddLineBreak();
void DispatchLastSentence();
void SetNewLineFlag();
void SetNewLineTimer();
void AddText(const BYTE *con,int len);
void AddSentence();
void AddSentence(std::wstring sentence);
BYTE *GetStore(DWORD *len) { if (len) *len = used; return storage; }
DWORD LastSentenceLen() { return used - last_sentence; }
DWORD PID() const { return tp.pid; }
DWORD Addr() const {return tp.hook; }
DWORD &Status() { return status; }
@ -77,12 +75,10 @@ public:
private:
ThreadParameter tp;
std::vector<char> sentenceBuffer;
WORD thread_number;
ThreadOutputFilterCallback output;
UINT_PTR timer;
DWORD status;
DWORD last_sentence,
sentence_length;
};
// EOF

View File

@ -69,7 +69,7 @@ protected:
LeaveCriticalSection(&cs_store);
//else __asm int 3
}
int AddToStore(T *con,int amount)
int AddToStore(const T *con,int amount)
{
if (amount <= 0 || con == 0)
return 0;