#include <iostream>
#include <Windows.h>
#include "nozzle.hpp"

int __cdecl main(int argc, char** argv)
{
	if (argc < 3)
	{
		std::cerr << "[!] please specify a executable path and a dll path" << std::endl;
		return -1;
	}

	SECURITY_ATTRIBUTES sec_attr{};
	STARTUPINFOA start_info{};
	PROCESS_INFORMATION process_info;

	auto result = CreateProcessA(
		argv[1],
		NULL, 
		&sec_attr,
		&sec_attr,
		FALSE,
		CREATE_NEW_CONSOLE,
		NULL,
		NULL,
		&start_info,
		&process_info
	);

	if (!result)
		return -1;

	Sleep(1000);
	SuspendThread(process_info.hThread);

	std::cout << "[+] started new process, pid: " << process_info.dwProcessId << std::endl;
	std::cout << "[+] injecting into: " << process_info.dwProcessId << std::endl;
	nozzle::injector injector(argv[2], process_info.dwProcessId);

	const auto base_addr = 
		util::get_module_base(
			process_info.dwProcessId,
			"loader.exe"
		);
	std::cout << "[+] base address of loader: " << base_addr << std::endl;
	std::cin.get();

	//
	// inject into suspended process and run entry.
	//
	std::cout << "[+] injected into: " << injector.inject() << std::endl;
	std::cout << "[+] thread handle: " << injector.call_entry(base_addr) << std::endl;

	//
	// resume process.
	//
	ResumeThread(process_info.hThread);
	std::cin.get();
}
