/*******************************************************************************
 * 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 <string>
#include <vector>

#include "SimpleRegistersService.h"

#include "DebugMonitor.h"
#include "ContextManager.h"
#include "TCFChannel.h"
#include "WinThread.h"

static const char * sServiceName = "SimpleRegisters";

SimpleRegistersService::SimpleRegistersService(Protocol * proto) :
	TCFService(proto) {
	AddCommand("get", command_get);
	AddCommand("set", command_set);
}

SimpleRegistersService::~SimpleRegistersService(void) {
}

const char* SimpleRegistersService::GetName() {
	return sServiceName;
}

/*
 * register values are passed as hex-string in big-endian
 */
void SimpleRegistersService::command_get(const char * token, Channel * c) {
	TCFChannel channel(c);
	std::vector<std::string> registerIDs;

	std::string exeContextID = channel.readString();
	channel.readZero();

	int ch = read_stream(&c->inp);
	if (ch == 'n') {
		if (read_stream(&c->inp) != 'u')
			exception(ERR_JSON_SYNTAX);
		if (read_stream(&c->inp) != 'l')
			exception(ERR_JSON_SYNTAX);
		if (read_stream(&c->inp) != 'l')
			exception(ERR_JSON_SYNTAX);
	} else {
		if (ch != '[')
			exception(ERR_PROTOCOL);
		if (peek_stream(&c->inp) == ']') {
			read_stream(&c->inp);
		} else {
			while (1) {
				int ch;
				std::string id = channel.readString();

				registerIDs.push_back(id);

				ch = read_stream(&c->inp);
				if (ch == ',')
					continue;
				if (ch == ']')
					break;
				exception(ERR_JSON_SYNTAX);
			}
		}
	}
	channel.readZero();
	channel.readComplete();

	WinThread* context = dynamic_cast<WinThread *>(ContextManager::findContext(exeContextID));

	if (context == NULL || !context->IsDebugging()) {
		// Return invalid-context-ID error.
		channel.writeCompleteReply(token, ERR_INV_CONTEXT, 1);
		return;
	}
	
	std::vector<std::string> registerValues = context->GetRegisterValues(
			registerIDs);

	if (registerValues.size() == 0) { 
		// no values got. Assuming target is running.
		// TODO: it's better the above context->GetRegisterValues() API return error code.
		channel.writeCompleteReply(token, ERR_IS_RUNNING, 1);
		return;
	}
	
	channel.writeError(0);
	channel.writeCharacter('[');

	std::vector<std::string>::iterator itVectorData;
	for (itVectorData = registerValues.begin(); itVectorData
			!= registerValues.end(); itVectorData++) 
	{
		if (itVectorData != registerValues.begin())
			write_stream(&c->out, ',');
		std::string value = *itVectorData;
		channel.writeString(value);
	}

	channel.writeCharacter(']');
	channel.writeZero();

	channel.writeComplete();
}

/*
 * register values are passed as hex-string in big-endian
 */
void SimpleRegistersService::command_set(const char * token, Channel * c) {
	TCFChannel channel(c);
	std::vector<std::string> registerIDs;
	std::vector<std::string> registerValues;

	std::string exeContextID = channel.readString();
	channel.readZero();

	int ch = read_stream(&c->inp);
	if (ch == 'n') {
		if (read_stream(&c->inp) != 'u')
			exception(ERR_JSON_SYNTAX);
		if (read_stream(&c->inp) != 'l')
			exception(ERR_JSON_SYNTAX);
		if (read_stream(&c->inp) != 'l')
			exception(ERR_JSON_SYNTAX);
	} else {
		// read register IDs
		if (ch != '[')
			exception(ERR_PROTOCOL);
		if (peek_stream(&c->inp) == ']') {
			read_stream(&c->inp);
		} else {
			while (1) {
				int ch;
				std::string id = channel.readString();

				registerIDs.push_back(id);

				ch = read_stream(&c->inp);
				if (ch == ',')
					continue;
				if (ch == ']')
					break;
				exception(ERR_JSON_SYNTAX);
			}
		}
		channel.readZero();

		// read register values
		ch = read_stream(&c->inp);
		if (ch != '[')
			exception(ERR_PROTOCOL);
		if (peek_stream(&c->inp) == ']') {
			read_stream(&c->inp);
		} else {
			while (1) {
				int ch;
				std::string value = channel.readString();

				registerValues.push_back(value);

				ch = read_stream(&c->inp);
				if (ch == ',')
					continue;
				if (ch == ']')
					break;
				exception(ERR_JSON_SYNTAX);
			}
		}
	}
	channel.readZero();
	channel.readComplete();

	WinThread* context = dynamic_cast<WinThread *>(ContextManager::findContext(exeContextID));

	if (context == NULL || !context->IsDebugging()) {
		// Return invalid-context-ID error.
		channel.writeCompleteReply(token, ERR_INV_CONTEXT, 1);
		return;
	}

	context->SetRegisterValues(registerIDs, registerValues);

	channel.writeReplyHeader(token);
	channel.writeZero();
	channel.writeComplete();
}
