/*-------------------------------------------------------------------------
 * drawElements Quality Program Test Executor
 * ------------------------------------------
 *
 * Copyright 2014 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 *//*!
 * \file
 * \brief Test log writer.
 *//*--------------------------------------------------------------------*/

#include "xeTestLogWriter.hpp"
#include "xeXMLWriter.hpp"
#include "deStringUtil.hpp"

#include <fstream>

namespace xe
{

static const char* TEST_LOG_VERSION = "0.3.3";

/* Batch result writer. */

struct ContainerValue
{
	ContainerValue (const std::string& value_)	: value(value_) {}
	ContainerValue (const char* value_)			: value(value_) {}
	std::string value;
};

std::ostream& operator<< (std::ostream& stream, const ContainerValue& value)
{
	if (value.value.find(' ') != std::string::npos)
	{
		// Escape.
		stream << '"';
		for (std::string::const_iterator i = value.value.begin(); i != value.value.end(); i++)
		{
			if (*i == '"' || *i == '\\')
				stream << '\\';
			stream << *i;
		}
		stream << '"';
	}
	else
		stream << value.value;

	return stream;
}

static void writeSessionInfo (const SessionInfo& info, std::ostream& stream)
{
	if (!info.releaseName.empty())
		stream << "#sessionInfo releaseName " << ContainerValue(info.releaseName) << "\n";

	if (!info.releaseId.empty())
		stream << "#sessionInfo releaseId " << ContainerValue(info.releaseId) << "\n";

	if (!info.targetName.empty())
		stream << "#sessionInfo targetName " << ContainerValue(info.targetName) << "\n";

	if (!info.candyTargetName.empty())
		stream << "#sessionInfo candyTargetName " << ContainerValue(info.candyTargetName) << "\n";

	if (!info.configName.empty())
		stream << "#sessionInfo configName " << ContainerValue(info.configName) << "\n";

	if (!info.resultName.empty())
		stream << "#sessionInfo resultName " << ContainerValue(info.resultName) << "\n";

	// \note Current format uses unescaped timestamps for some stupid reason.
	if (!info.timestamp.empty())
		stream << "#sessionInfo timestamp " << info.timestamp << "\n";
}

static void writeTestCase (const TestCaseResultData& caseData, std::ostream& stream)
{
	stream << "\n#beginTestCaseResult " << caseData.getTestCasePath() << "\n";

	if (caseData.getDataSize() > 0)
	{
		stream.write((const char*)caseData.getData(), caseData.getDataSize());

		deUint8 lastCh = caseData.getData()[caseData.getDataSize()-1];
		if (lastCh != '\n' && lastCh != '\r')
			stream << "\n";
	}

	TestStatusCode dataCode = caseData.getStatusCode();
	if (dataCode == TESTSTATUSCODE_CRASH	||
		dataCode == TESTSTATUSCODE_TIMEOUT	||
		dataCode == TESTSTATUSCODE_TERMINATED)
		stream << "#terminateTestCaseResult " << getTestStatusCodeName(dataCode) << "\n";
	else
		stream << "#endTestCaseResult\n";
}

void writeTestLog (const BatchResult& result, std::ostream& stream)
{
	writeSessionInfo(result.getSessionInfo(), stream);

	stream << "#beginSession\n";

	for (int ndx = 0; ndx < result.getNumTestCaseResults(); ndx++)
	{
		ConstTestCaseResultPtr caseData = result.getTestCaseResult(ndx);
		writeTestCase(*caseData, stream);
	}

	stream << "\n#endSession\n";
}

void writeBatchResultToFile (const BatchResult& result, const char* filename)
{
	std::ofstream str(filename, std::ofstream::binary|std::ofstream::trunc);
	writeTestLog(result, str);
	str.close();
}

/* Test result log writer. */

static const char* getImageFormatName (ri::Image::Format format)
{
	switch (format)
	{
		case ri::Image::FORMAT_RGB888:		return "RGB888";
		case ri::Image::FORMAT_RGBA8888:	return "RGBA8888";
		default:
			DE_ASSERT(false);
			return DE_NULL;
	}
}

static const char* getImageCompressionName (ri::Image::Compression compression)
{
	switch (compression)
	{
		case ri::Image::COMPRESSION_NONE:	return "None";
		case ri::Image::COMPRESSION_PNG:	return "PNG";
		default:
			DE_ASSERT(false);
			return DE_NULL;
	}
}

static const char* getSampleValueTagName (ri::ValueInfo::ValueTag tag)
{
	switch (tag)
	{
		case ri::ValueInfo::VALUETAG_PREDICTOR:	return "Predictor";
		case ri::ValueInfo::VALUETAG_RESPONSE:	return "Response";
		default:
			DE_ASSERT(false);
			return DE_NULL;
	}
}

inline const char* getBoolName (bool val)
{
	return val ? "True" : "False";
}

// \todo [2012-09-07 pyry] Move to tcutil?
class Base64Formatter
{
public:
	const deUint8*	data;
	int				numBytes;

	Base64Formatter (const deUint8* data_, int numBytes_) : data(data_), numBytes(numBytes_) {}
};

std::ostream& operator<< (std::ostream& str, const Base64Formatter& fmt)
{
	static const char s_base64Table[64] =
	{
		'A','B','C','D','E','F','G','H','I','J','K','L','M',
		'N','O','P','Q','R','S','T','U','V','W','X','Y','Z',
		'a','b','c','d','e','f','g','h','i','j','k','l','m',
		'n','o','p','q','r','s','t','u','v','w','x','y','z',
		'0','1','2','3','4','5','6','7','8','9','+','/'
	};

	const deUint8*	data		= fmt.data;
	int				numBytes	= fmt.numBytes;
	int				srcNdx		= 0;

	DE_ASSERT(data && (numBytes > 0));

	/* Loop all input chars. */
	while (srcNdx < numBytes)
	{
		int		numRead	= de::min(3, numBytes - srcNdx);
		deUint8	s0		= data[srcNdx];
		deUint8	s1		= (numRead >= 2) ? data[srcNdx+1] : 0;
		deUint8	s2		= (numRead >= 3) ? data[srcNdx+2] : 0;
		char	d[4];

		srcNdx += numRead;

		d[0] = s_base64Table[s0 >> 2];
		d[1] = s_base64Table[((s0&0x3)<<4) | (s1>>4)];
		d[2] = s_base64Table[((s1&0xF)<<2) | (s2>>6)];
		d[3] = s_base64Table[s2&0x3F];

		if (numRead < 3) d[3] = '=';
		if (numRead < 2) d[2] = '=';

		/* Write data. */
		str.write(&d[0], sizeof(d));
	}

	return str;
}

inline Base64Formatter toBase64 (const deUint8* bytes, int numBytes) { return Base64Formatter(bytes, numBytes); }

static const char* getStatusName (bool value)
{
	return value ? "OK" : "Fail";
}

static void writeResultItem (const ri::Item& item, xml::Writer& dst)
{
	using xml::Writer;

	switch (item.getType())
	{
		case ri::TYPE_RESULT:
			// Ignored here, written at end.
			break;

		case ri::TYPE_TEXT:
			dst << Writer::BeginElement("Text") << static_cast<const ri::Text&>(item).text << Writer::EndElement;
			break;

		case ri::TYPE_NUMBER:
		{
			const ri::Number& number = static_cast<const ri::Number&>(item);
			dst << Writer::BeginElement("Number")
				<< Writer::Attribute("Name",		number.name)
				<< Writer::Attribute("Description",	number.description)
				<< Writer::Attribute("Unit",		number.unit)
				<< Writer::Attribute("Tag",			number.tag)
				<< number.value
				<< Writer::EndElement;
			break;
		}

		case ri::TYPE_IMAGE:
		{
			const ri::Image& image = static_cast<const ri::Image&>(item);
			dst << Writer::BeginElement("Image")
				<< Writer::Attribute("Name",			image.name)
				<< Writer::Attribute("Description",		image.description)
				<< Writer::Attribute("Width",			de::toString(image.width))
				<< Writer::Attribute("Height",			de::toString(image.height))
				<< Writer::Attribute("Format",			getImageFormatName(image.format))
				<< Writer::Attribute("CompressionMode",	getImageCompressionName(image.compression))
				<< toBase64(&image.data[0], (int)image.data.size())
				<< Writer::EndElement;
			break;
		}

		case ri::TYPE_IMAGESET:
		{
			const ri::ImageSet& imageSet = static_cast<const ri::ImageSet&>(item);
			dst << Writer::BeginElement("ImageSet")
				<< Writer::Attribute("Name",		imageSet.name)
				<< Writer::Attribute("Description",	imageSet.description);

			for (int ndx = 0; ndx < imageSet.images.getNumItems(); ndx++)
				writeResultItem(imageSet.images.getItem(ndx), dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SHADER:
		{
			const ri::Shader&	shader		= static_cast<const ri::Shader&>(item);
			const char*			tagName		= DE_NULL;

			switch (shader.shaderType)
			{
				case ri::Shader::SHADERTYPE_VERTEX:				tagName = "VertexShader";			break;
				case ri::Shader::SHADERTYPE_FRAGMENT:			tagName = "FragmentShader";			break;
				case ri::Shader::SHADERTYPE_GEOMETRY:			tagName = "GeometryShader";			break;
				case ri::Shader::SHADERTYPE_TESS_CONTROL:		tagName = "TessControlShader";		break;
				case ri::Shader::SHADERTYPE_TESS_EVALUATION:	tagName = "TessEvaluationShader";	break;
				case ri::Shader::SHADERTYPE_COMPUTE:			tagName = "ComputeShader";			break;
				default:
					throw Error("Unknown shader type");
			}

			dst << Writer::BeginElement(tagName)
				<< Writer::Attribute("CompileStatus",	getStatusName(shader.compileStatus));

			writeResultItem(shader.source, dst);
			writeResultItem(shader.infoLog, dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SHADERPROGRAM:
		{
			const ri::ShaderProgram& program = static_cast<const ri::ShaderProgram&>(item);
			dst << Writer::BeginElement("ShaderProgram")
				<< Writer::Attribute("LinkStatus",	getStatusName(program.linkStatus));

			writeResultItem(program.linkInfoLog, dst);

			for (int ndx = 0; ndx < program.shaders.getNumItems(); ndx++)
				writeResultItem(program.shaders.getItem(ndx), dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SHADERSOURCE:
			dst << Writer::BeginElement("ShaderSource") << static_cast<const ri::ShaderSource&>(item).source << Writer::EndElement;
			break;

		case ri::TYPE_SPIRVSOURCE:
			dst << Writer::BeginElement("SpirVAssemblySource") << static_cast<const ri::SpirVSource&>(item).source << Writer::EndElement;
			break;

		case ri::TYPE_INFOLOG:
			dst << Writer::BeginElement("InfoLog") << static_cast<const ri::InfoLog&>(item).log << Writer::EndElement;
			break;

		case ri::TYPE_SECTION:
		{
			const ri::Section& section = static_cast<const ri::Section&>(item);
			dst << Writer::BeginElement("Section")
				<< Writer::Attribute("Name",		section.name)
				<< Writer::Attribute("Description",	section.description);

			for (int ndx = 0; ndx < section.items.getNumItems(); ndx++)
				writeResultItem(section.items.getItem(ndx), dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_KERNELSOURCE:
			dst << Writer::BeginElement("KernelSource") << static_cast<const ri::KernelSource&>(item).source << Writer::EndElement;
			break;

		case ri::TYPE_COMPILEINFO:
		{
			const ri::CompileInfo& compileInfo = static_cast<const ri::CompileInfo&>(item);
			dst << Writer::BeginElement("CompileInfo")
				<< Writer::Attribute("Name",			compileInfo.name)
				<< Writer::Attribute("Description",		compileInfo.description)
				<< Writer::Attribute("CompileStatus",	getStatusName(compileInfo.compileStatus));

			writeResultItem(compileInfo.infoLog, dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_EGLCONFIG:
		{
			const ri::EglConfig& config = static_cast<const ri::EglConfig&>(item);
			dst << Writer::BeginElement("EglConfig")
				<< Writer::Attribute("BufferSize",				de::toString(config.bufferSize))
				<< Writer::Attribute("RedSize",					de::toString(config.redSize))
				<< Writer::Attribute("GreenSize",				de::toString(config.greenSize))
				<< Writer::Attribute("BlueSize",				de::toString(config.blueSize))
				<< Writer::Attribute("LuminanceSize",			de::toString(config.luminanceSize))
				<< Writer::Attribute("AlphaSize",				de::toString(config.alphaSize))
				<< Writer::Attribute("AlphaMaskSize",			de::toString(config.alphaMaskSize))
				<< Writer::Attribute("BindToTextureRGB",		getBoolName(config.bindToTextureRGB))
				<< Writer::Attribute("BindToTextureRGBA",		getBoolName(config.bindToTextureRGBA))
				<< Writer::Attribute("ColorBufferType",			config.colorBufferType)
				<< Writer::Attribute("ConfigCaveat",			config.configCaveat)
				<< Writer::Attribute("ConfigID",				de::toString(config.configID))
				<< Writer::Attribute("Conformant",				config.conformant)
				<< Writer::Attribute("DepthSize",				de::toString(config.depthSize))
				<< Writer::Attribute("Level",					de::toString(config.level))
				<< Writer::Attribute("MaxPBufferWidth",			de::toString(config.maxPBufferWidth))
				<< Writer::Attribute("MaxPBufferHeight",		de::toString(config.maxPBufferHeight))
				<< Writer::Attribute("MaxPBufferPixels",		de::toString(config.maxPBufferPixels))
				<< Writer::Attribute("MaxSwapInterval",			de::toString(config.maxSwapInterval))
				<< Writer::Attribute("MinSwapInterval",			de::toString(config.minSwapInterval))
				<< Writer::Attribute("NativeRenderable",		getBoolName(config.nativeRenderable))
				<< Writer::Attribute("RenderableType",			config.renderableType)
				<< Writer::Attribute("SampleBuffers",			de::toString(config.sampleBuffers))
				<< Writer::Attribute("Samples",					de::toString(config.samples))
				<< Writer::Attribute("StencilSize",				de::toString(config.stencilSize))
				<< Writer::Attribute("SurfaceTypes",			config.surfaceTypes)
				<< Writer::Attribute("TransparentType",			config.transparentType)
				<< Writer::Attribute("TransparentRedValue",		de::toString(config.transparentRedValue))
				<< Writer::Attribute("TransparentGreenValue",	de::toString(config.transparentGreenValue))
				<< Writer::Attribute("TransparentBlueValue",	de::toString(config.transparentBlueValue))
				<< Writer::EndElement;
			break;
		}

		case ri::TYPE_EGLCONFIGSET:
		{
			const ri::EglConfigSet& configSet = static_cast<const ri::EglConfigSet&>(item);
			dst << Writer::BeginElement("EglConfigSet")
				<< Writer::Attribute("Name",			configSet.name)
				<< Writer::Attribute("Description",		configSet.description);

			for (int ndx = 0; ndx < configSet.configs.getNumItems(); ndx++)
				writeResultItem(configSet.configs.getItem(ndx), dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SAMPLELIST:
		{
			const ri::SampleList& list = static_cast<const ri::SampleList&>(item);
			dst << Writer::BeginElement("SampleList")
				<< Writer::Attribute("Name",		list.name)
				<< Writer::Attribute("Description",	list.description);

			writeResultItem(list.sampleInfo, dst);

			for (int ndx = 0; ndx < list.samples.getNumItems(); ndx++)
				writeResultItem(list.samples.getItem(ndx), dst);

			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SAMPLEINFO:
		{
			const ri::SampleInfo& info = static_cast<const ri::SampleInfo&>(item);
			dst << Writer::BeginElement("SampleInfo");
			for (int ndx = 0; ndx < info.valueInfos.getNumItems(); ndx++)
				writeResultItem(info.valueInfos.getItem(ndx), dst);
			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_VALUEINFO:
		{
			const ri::ValueInfo& info = static_cast<const ri::ValueInfo&>(item);
			dst << Writer::BeginElement("ValueInfo")
				<< Writer::Attribute("Name",		info.name)
				<< Writer::Attribute("Description",	info.description)
				<< Writer::Attribute("Tag",			getSampleValueTagName(info.tag));
			if (!info.unit.empty())
				dst << Writer::Attribute("Unit", info.unit);
			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SAMPLE:
		{
			const ri::Sample& sample = static_cast<const ri::Sample&>(item);
			dst << Writer::BeginElement("Sample");
			for (int ndx = 0; ndx < sample.values.getNumItems(); ndx++)
				writeResultItem(sample.values.getItem(ndx), dst);
			dst << Writer::EndElement;
			break;
		}

		case ri::TYPE_SAMPLEVALUE:
		{
			const ri::SampleValue& value = static_cast<const ri::SampleValue&>(item);
			dst << Writer::BeginElement("Value")
				<< value.value
				<< Writer::EndElement;
			break;
		}

		default:
			XE_FAIL("Unsupported result item");
	}
}

void writeTestResult (const TestCaseResult& result, xe::xml::Writer& xmlWriter)
{
	using xml::Writer;

	xmlWriter << Writer::BeginElement("TestCaseResult")
			  << Writer::Attribute("Version", TEST_LOG_VERSION)
			  << Writer::Attribute("CasePath", result.casePath)
			  << Writer::Attribute("CaseType", getTestCaseTypeName(result.caseType));

	for (int ndx = 0; ndx < result.resultItems.getNumItems(); ndx++)
		writeResultItem(result.resultItems.getItem(ndx), xmlWriter);

	// Result item is not logged until end.
	xmlWriter << Writer::BeginElement("Result")
			  << Writer::Attribute("StatusCode", getTestStatusCodeName(result.statusCode))
			  << result.statusDetails
			  << Writer::EndElement;

	xmlWriter << Writer::EndElement;
}

void writeTestResult (const TestCaseResult& result, std::ostream& stream)
{
	xml::Writer xmlWriter(stream);
	stream << "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n";
	writeTestResult(result, xmlWriter);
}

void writeTestResultToFile (const TestCaseResult& result, const char* filename)
{
	std::ofstream str(filename, std::ofstream::binary|std::ofstream::trunc);
	writeTestResult(result, str);
	str.close();
}

} // xe
