/*******************************************************************************
 * Copyright (c) 2009 Nokia and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 * Nokia - Initial API and implementation
 *******************************************************************************/
#include "StdAfx.h"
#include "WinProcess.h"
#include "WinThread.h"
#include "EventClientNotifier.h"
#include "AgentUtils.h"
#include "Psapi.h"
#include "assert.h"
#include "WinDebugMonitor.h"
#include "TerminateProcessAction.h"
#include "ProtocolConstants.h"
#include "RunControlService.h"
#include "ContextManager.h"
#include "BreakpointsService.h"

std::map<int, WinProcess*> WinProcess::processIDMap;

WinProcess::WinProcess(WinDebugMonitor* monitor, DEBUG_EVENT& debugEvent) :
	ProcessContext(debugEvent.dwProcessId, ROOT_CONTEXT_ID, CreateInternalID(debugEvent.dwProcessId)),
	processHandle_(debugEvent.u.CreateProcessInfo.hProcess),
	monitor_(monitor)
{
	isRoot_ = true;
	processIDMap[debugEvent.dwProcessId] = this;

	// Get the name for the new process
	std::string moduleFileName = "unknown";
	int bufferSize = 32768;
	{
		LPTSTR processNameBuffer = new TCHAR[bufferSize];
		int nameLength = GetProcessImageFileName((HMODULE) processHandle_,
				processNameBuffer, bufferSize);
		if (nameLength > 0) {
			moduleFileName = AgentUtils::makeString(processNameBuffer);
		}
		delete[] processNameBuffer;
	}
	int lastSlash = moduleFileName.find_last_of("\\");
	if (lastSlash > 0)
		moduleFileName = moduleFileName.substr(lastSlash + 1);
	processName_ = moduleFileName;

	initialize();
}

WinProcess::WinProcess(DWORD procID, std::string procName) :
	ProcessContext(procID, ROOT_CONTEXT_ID, CreateInternalID(procID)),
	processHandle_(NULL),
	monitor_(NULL)
{
	processName_ = procName;

	initialize();
}

// Initialize process specific properties.
void WinProcess::initialize()
{
	SetProperty(PROP_NAME, PropertyValue(processName_));

	// do not support process stepping yet
	int supportedResumeModes = (1 << RM_RESUME);
	SetProperty(PROP_CAN_RESUME, PropertyValue(supportedResumeModes));

	SetProperty(PROP_CAN_TERMINATE, PropertyValue(true));
	SetProperty(PROP_CAN_SUSPEND, PropertyValue(true));
}

WinProcess::~WinProcess(void) {

	processIDMap.erase(GetOSID());

	GetMonitor()->ProcessDied(GetOSID());

	// Destructor of parent classes will be called which will
	// delete all children contexts (threads, registers, etc).
}

HANDLE WinProcess::GetProcessHandle() {
	return processHandle_;
}

WinProcess* WinProcess::GetProcessByID(int processID) {
	std::map<int, WinProcess*>::iterator iter = processIDMap.find(processID);
	if (iter == processIDMap.end())
		return NULL;
	else
		return iter->second;
}

int WinProcess::ReadMemory(const ReadWriteMemoryParams& params) throw (AgentException) {
	int result = 0;

	boolean success = ReadProcessMemory(processHandle_, (LPCVOID) params.address,
			params.memBuffer, params.size, params.sizeTransferred);
	if (!success)
		result = GetLastError();
	else
		BreakpointsService::RemoveBreakpointsFromMemoryRead(processHandle_, params.address, params.memBuffer, params.size);

	return result;
}

int WinProcess::WriteMemory(const ReadWriteMemoryParams& params) throw (AgentException) {
	// to do: handle breakpoints and watchpoints
	int result = 0;

	boolean success = WriteProcessMemory(processHandle_, (LPVOID) params.address,
			params.memBuffer, params.size, params.sizeTransferred);
	if (!success)
		result = GetLastError();
	else {
		BreakpointsService::ReInsertBreakpointsAfterMemoryWrite(processHandle_, params.address, params.memBuffer, params.size);
	}
	return result;
}

void WinProcess::Terminate(const AgentActionParams& params) throw (AgentException) {
	if (monitor_)
		monitor_->PostAction(new TerminateProcessAction(params, GetOSID()));
}

// TODO: if we report an error, DSF gets confused...
// just report success even though it's not implemented
void WinProcess::SingleStep(const AgentActionParams& params) throw (AgentException) {
	AgentActionReply::postReply(params.channel, params.token, 0);
	//AgentActionReply::postReply(params.channel, params.token, ERR_UNSUPPORTED);
};


WinDebugMonitor* WinProcess::GetMonitor() {
	return monitor_;
}

std::map<int, Properties>& WinProcess::GetExecutablesByAddress()
{
	return executablesByAddress_;
}

