#ifndef _TCUTESTCASE_HPP
#define _TCUTESTCASE_HPP
/*-------------------------------------------------------------------------
 * drawElements Quality Program Tester Core
 * ----------------------------------------
 *
 * 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 Base class for a test case.
 *//*--------------------------------------------------------------------*/

#include "tcuDefs.hpp"
#include "tcuTestContext.hpp"

#include <string>
#include <vector>

namespace tcu
{

enum TestNodeType
{
	NODETYPE_ROOT = 0,		//!< Root for all test packages.
	NODETYPE_PACKAGE,		//!< Test case package -- same as group, but is omitted from XML dump.
	NODETYPE_GROUP,			//!< Test case container -- cannot be executed.
	NODETYPE_SELF_VALIDATE,	//!< Self-validating test case -- can be executed
	NODETYPE_PERFORMANCE,	//!< Performace test case -- can be executed
	NODETYPE_CAPABILITY,	//!< Capability score case -- can be executed
	NODETYPE_ACCURACY		//!< Accuracy test case -- can be executed
};

enum TestNodeClass
{
	NODECLASS_GROUP = 0,	//!< Root or non-leaf in the test hierarchy tree
	NODECLASS_EXECUTABLE,	//!< Non-root leaf in the test hierarchy tree

	NODECLASS_LAST
};

inline TestNodeClass getTestNodeTypeClass (TestNodeType type)
{
	switch (type)
	{
		case NODETYPE_ROOT:				return NODECLASS_GROUP;
		case NODETYPE_PACKAGE:			return NODECLASS_GROUP;
		case NODETYPE_GROUP:			return NODECLASS_GROUP;
		case NODETYPE_SELF_VALIDATE:	return NODECLASS_EXECUTABLE;
		case NODETYPE_PERFORMANCE:		return NODECLASS_EXECUTABLE;
		case NODETYPE_CAPABILITY:		return NODECLASS_EXECUTABLE;
		case NODETYPE_ACCURACY:			return NODECLASS_EXECUTABLE;
		default:
			DE_ASSERT(false);
			return NODECLASS_LAST;
	}
}

inline bool isTestNodeTypeExecutable (TestNodeType type)
{
	return getTestNodeTypeClass(type) == NODECLASS_EXECUTABLE;
}

inline bool isValidTestCaseNameChar (char c)
{
	return de::inRange(c, 'a', 'z') ||
		   de::inRange(c, 'A', 'Z') ||
		   de::inRange(c, '0', '9') ||
		   c == '_' || c == '-';
}

/*--------------------------------------------------------------------*//*!
 * \brief Test case hierarchy node
 *
 * Test node forms the backbone of the test case hierarchy. All objects
 * in the hierarchy are derived from this class.
 *
 * Each test node has a type and all except the root node have name and
 * description. Root and test group nodes have a list of children.
 *
 * During test execution TestExecutor iterates the hierarchy. Upon entering
 * the node (both groups and test cases) init() is called. When exiting the
 * node deinit() is called respectively.
 *//*--------------------------------------------------------------------*/
class TestNode
{
public:
	enum IterateResult
	{
		STOP		= 0,
		CONTINUE	= 1
	};

	// Methods.
							TestNode		(TestContext& testCtx, TestNodeType nodeType, const char* name, const char* description);
							TestNode		(TestContext& testCtx, TestNodeType nodeType, const char* name, const char* description, const std::vector<TestNode*>& children);
	virtual					~TestNode		(void);

	TestNodeType			getNodeType		(void) const	{ return m_nodeType;			}
	TestContext&			getTestContext	(void) const	{ return m_testCtx;				}
	const char*				getName			(void) const	{ return m_name.c_str();		}
	const char*				getDescription	(void) const	{ return m_description.c_str(); }
	void					getChildren		(std::vector<TestNode*>& children);
	void					addChild		(TestNode* node);

	virtual void			init			(void);
	virtual void			deinit			(void);
	virtual IterateResult	iterate			(void) = 0;

protected:
	TestContext&			m_testCtx;
	std::string				m_name;
	std::string				m_description;

private:
	const TestNodeType		m_nodeType;
	std::vector<TestNode*>	m_children;
};

/*--------------------------------------------------------------------*//*!
 * \brief Test case group node
 *
 * Test case group implementations must inherit this class. To save resources
 * during test execution the group must delay creation of any child groups
 * until init() is called.
 *
 * Default deinit() for test group will destroy all child nodes.
 *//*--------------------------------------------------------------------*/
class TestCaseGroup : public TestNode
{
public:
							TestCaseGroup	(TestContext& testCtx, const char* name, const char* description);
							TestCaseGroup	(TestContext& testCtx, const char* name, const char* description, const std::vector<TestNode*>& children);
	virtual					~TestCaseGroup	(void);

	virtual IterateResult	iterate			(void);
};

/*--------------------------------------------------------------------*//*!
 * \brief Test case class
 *
 * Test case implementations must inherit this class.
 *
 * Test case objects are usually constructed when TestExecutor enters parent
 * group. Allocating any non-parameter resources, especially target API objects
 * must be delayed to init().
 *
 * Upon entering the test case TestExecutor calls init(). If initialization
 * is successful (no exception is thrown) the executor will then call iterate()
 * until test case returns STOP. After that deinit() will be called.
 *
 * Before exiting the execution phase (i.e. at returning STOP from iterate())
 * the test case must set valid status code to test context (m_testCtx).
 *
 * Test case can also signal error condition by throwing an exception. In
 * that case the framework will set result code and details based on the
 * exception.
 *//*--------------------------------------------------------------------*/
class TestCase : public TestNode
{
public:
					TestCase			(TestContext& testCtx, const char* name, const char* description);
					TestCase			(TestContext& testCtx, TestNodeType nodeType, const char* name, const char* description);
	virtual			~TestCase			(void);
};

class TestStatus
{
public:
						TestStatus		(qpTestResult code, const std::string& description) : m_code(code), m_description(description) {}

	bool				isComplete		(void) const { return m_code != QP_TEST_RESULT_LAST;			}
	qpTestResult		getCode			(void) const { DE_ASSERT(isComplete()); return m_code;			}
	const std::string&	getDescription	(void) const { DE_ASSERT(isComplete()); return m_description;	}

	static TestStatus	pass			(const std::string& description)	{ return TestStatus(QP_TEST_RESULT_PASS,	description);	}
	static TestStatus	fail			(const std::string& description)	{ return TestStatus(QP_TEST_RESULT_FAIL,	description);	}
	static TestStatus	incomplete		(void)								{ return TestStatus(QP_TEST_RESULT_LAST,	"");			}

private:
	qpTestResult		m_code;
	std::string			m_description;
} DE_WARN_UNUSED_TYPE;

} // tcu

#endif // _TCUTESTCASE_HPP
