1e5c31af7Sopenharmony_ci/*-------------------------------------------------------------------------
2e5c31af7Sopenharmony_ci * drawElements Quality Program Execution Server
3e5c31af7Sopenharmony_ci * ---------------------------------------------
4e5c31af7Sopenharmony_ci *
5e5c31af7Sopenharmony_ci * Copyright 2014 The Android Open Source Project
6e5c31af7Sopenharmony_ci *
7e5c31af7Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
8e5c31af7Sopenharmony_ci * you may not use this file except in compliance with the License.
9e5c31af7Sopenharmony_ci * You may obtain a copy of the License at
10e5c31af7Sopenharmony_ci *
11e5c31af7Sopenharmony_ci *      http://www.apache.org/licenses/LICENSE-2.0
12e5c31af7Sopenharmony_ci *
13e5c31af7Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
14e5c31af7Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
15e5c31af7Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16e5c31af7Sopenharmony_ci * See the License for the specific language governing permissions and
17e5c31af7Sopenharmony_ci * limitations under the License.
18e5c31af7Sopenharmony_ci *
19e5c31af7Sopenharmony_ci *//*!
20e5c31af7Sopenharmony_ci * \file
21e5c31af7Sopenharmony_ci * \brief Execution Server Protocol.
22e5c31af7Sopenharmony_ci *//*--------------------------------------------------------------------*/
23e5c31af7Sopenharmony_ci
24e5c31af7Sopenharmony_ci#include "xsProtocol.hpp"
25e5c31af7Sopenharmony_ci
26e5c31af7Sopenharmony_ciusing std::string;
27e5c31af7Sopenharmony_ciusing std::vector;
28e5c31af7Sopenharmony_ci
29e5c31af7Sopenharmony_cinamespace xs
30e5c31af7Sopenharmony_ci{
31e5c31af7Sopenharmony_ci
32e5c31af7Sopenharmony_ciinline deUint32 swapEndianess (deUint32 value)
33e5c31af7Sopenharmony_ci{
34e5c31af7Sopenharmony_ci	deUint32 b0 = (value >>  0) & 0xFF;
35e5c31af7Sopenharmony_ci	deUint32 b1 = (value >>  8) & 0xFF;
36e5c31af7Sopenharmony_ci	deUint32 b2 = (value >> 16) & 0xFF;
37e5c31af7Sopenharmony_ci	deUint32 b3 = (value >> 24) & 0xFF;
38e5c31af7Sopenharmony_ci	return (b0 << 24) | (b1 << 16) | (b2 << 8) | b3;
39e5c31af7Sopenharmony_ci}
40e5c31af7Sopenharmony_ci
41e5c31af7Sopenharmony_citemplate <typename T> T networkToHost (T value);
42e5c31af7Sopenharmony_citemplate <typename T> T hostToNetwork (T value);
43e5c31af7Sopenharmony_ci
44e5c31af7Sopenharmony_citemplate <> int networkToHost (int value) { return (int)swapEndianess((deUint32)value); }
45e5c31af7Sopenharmony_citemplate <> int hostToNetwork (int value) { return (int)swapEndianess((deUint32)value); }
46e5c31af7Sopenharmony_ci
47e5c31af7Sopenharmony_ciclass MessageParser
48e5c31af7Sopenharmony_ci{
49e5c31af7Sopenharmony_cipublic:
50e5c31af7Sopenharmony_ci	MessageParser (const deUint8* data, size_t dataSize)
51e5c31af7Sopenharmony_ci		: m_data	(data)
52e5c31af7Sopenharmony_ci		, m_size	(dataSize)
53e5c31af7Sopenharmony_ci		, m_pos		(0)
54e5c31af7Sopenharmony_ci	{
55e5c31af7Sopenharmony_ci	}
56e5c31af7Sopenharmony_ci
57e5c31af7Sopenharmony_ci	template <typename T>
58e5c31af7Sopenharmony_ci	T get (void)
59e5c31af7Sopenharmony_ci	{
60e5c31af7Sopenharmony_ci		XS_CHECK_MSG(m_pos + sizeof(T) <= m_size, "Invalid payload size");
61e5c31af7Sopenharmony_ci		T netValue;
62e5c31af7Sopenharmony_ci		deMemcpy(&netValue, &m_data[m_pos], sizeof(T));
63e5c31af7Sopenharmony_ci		m_pos += sizeof(T);
64e5c31af7Sopenharmony_ci		return networkToHost(netValue);
65e5c31af7Sopenharmony_ci	}
66e5c31af7Sopenharmony_ci
67e5c31af7Sopenharmony_ci	void getString (std::string& dst)
68e5c31af7Sopenharmony_ci	{
69e5c31af7Sopenharmony_ci		// \todo [2011-09-30 pyry] We should really send a size parameter instead.
70e5c31af7Sopenharmony_ci		while (m_data[m_pos] != 0)
71e5c31af7Sopenharmony_ci		{
72e5c31af7Sopenharmony_ci			dst += (char)m_data[m_pos++];
73e5c31af7Sopenharmony_ci			XS_CHECK_MSG(m_pos < m_size, "Unterminated string payload");
74e5c31af7Sopenharmony_ci		}
75e5c31af7Sopenharmony_ci
76e5c31af7Sopenharmony_ci		m_pos += 1;
77e5c31af7Sopenharmony_ci	}
78e5c31af7Sopenharmony_ci
79e5c31af7Sopenharmony_ci	void assumEnd (void)
80e5c31af7Sopenharmony_ci	{
81e5c31af7Sopenharmony_ci		if (m_pos != m_size)
82e5c31af7Sopenharmony_ci			XS_FAIL("Invalid payload size");
83e5c31af7Sopenharmony_ci	}
84e5c31af7Sopenharmony_ci
85e5c31af7Sopenharmony_ciprivate:
86e5c31af7Sopenharmony_ci	const deUint8*	m_data;
87e5c31af7Sopenharmony_ci	size_t			m_size;
88e5c31af7Sopenharmony_ci	size_t			m_pos;
89e5c31af7Sopenharmony_ci};
90e5c31af7Sopenharmony_ci
91e5c31af7Sopenharmony_ciclass MessageWriter
92e5c31af7Sopenharmony_ci{
93e5c31af7Sopenharmony_cipublic:
94e5c31af7Sopenharmony_ci	MessageWriter (MessageType msgType, std::vector<deUint8>& buf)
95e5c31af7Sopenharmony_ci		: m_buf(buf)
96e5c31af7Sopenharmony_ci	{
97e5c31af7Sopenharmony_ci		// Place for size.
98e5c31af7Sopenharmony_ci		put<int>(0);
99e5c31af7Sopenharmony_ci
100e5c31af7Sopenharmony_ci		// Write message type.
101e5c31af7Sopenharmony_ci		put<int>(msgType);
102e5c31af7Sopenharmony_ci	}
103e5c31af7Sopenharmony_ci
104e5c31af7Sopenharmony_ci	~MessageWriter (void)
105e5c31af7Sopenharmony_ci	{
106e5c31af7Sopenharmony_ci		finalize();
107e5c31af7Sopenharmony_ci	}
108e5c31af7Sopenharmony_ci
109e5c31af7Sopenharmony_ci	void finalize (void)
110e5c31af7Sopenharmony_ci	{
111e5c31af7Sopenharmony_ci		DE_ASSERT(m_buf.size() >= MESSAGE_HEADER_SIZE);
112e5c31af7Sopenharmony_ci
113e5c31af7Sopenharmony_ci		// Write actual size.
114e5c31af7Sopenharmony_ci		int size = hostToNetwork((int)m_buf.size());
115e5c31af7Sopenharmony_ci		deMemcpy(&m_buf[0], &size, sizeof(int));
116e5c31af7Sopenharmony_ci	}
117e5c31af7Sopenharmony_ci
118e5c31af7Sopenharmony_ci	template <typename T>
119e5c31af7Sopenharmony_ci	void put (T value)
120e5c31af7Sopenharmony_ci	{
121e5c31af7Sopenharmony_ci		T netValue = hostToNetwork(value);
122e5c31af7Sopenharmony_ci		size_t curPos = m_buf.size();
123e5c31af7Sopenharmony_ci		m_buf.resize(curPos + sizeof(T));
124e5c31af7Sopenharmony_ci		deMemcpy(&m_buf[curPos], &netValue, sizeof(T));
125e5c31af7Sopenharmony_ci	}
126e5c31af7Sopenharmony_ci
127e5c31af7Sopenharmony_ciprivate:
128e5c31af7Sopenharmony_ci	std::vector<deUint8>& m_buf;
129e5c31af7Sopenharmony_ci};
130e5c31af7Sopenharmony_ci
131e5c31af7Sopenharmony_citemplate <>
132e5c31af7Sopenharmony_civoid MessageWriter::put<const char*> (const char* value)
133e5c31af7Sopenharmony_ci{
134e5c31af7Sopenharmony_ci	int curPos = (int)m_buf.size();
135e5c31af7Sopenharmony_ci	int strLen = (int)strlen(value);
136e5c31af7Sopenharmony_ci
137e5c31af7Sopenharmony_ci	m_buf.resize(curPos + strLen+1);
138e5c31af7Sopenharmony_ci	deMemcpy(&m_buf[curPos], &value[0], strLen+1);
139e5c31af7Sopenharmony_ci}
140e5c31af7Sopenharmony_ci
141e5c31af7Sopenharmony_civoid Message::parseHeader (const deUint8* data, size_t dataSize, MessageType& type, size_t& size)
142e5c31af7Sopenharmony_ci{
143e5c31af7Sopenharmony_ci	XS_CHECK_MSG(dataSize >= MESSAGE_HEADER_SIZE, "Incomplete header");
144e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
145e5c31af7Sopenharmony_ci	size	= (size_t)(MessageType)parser.get<int>();
146e5c31af7Sopenharmony_ci	type	= (MessageType)parser.get<int>();
147e5c31af7Sopenharmony_ci}
148e5c31af7Sopenharmony_ci
149e5c31af7Sopenharmony_civoid Message::writeHeader (MessageType type, size_t messageSize, deUint8* dst, size_t bufSize)
150e5c31af7Sopenharmony_ci{
151e5c31af7Sopenharmony_ci	XS_CHECK_MSG(bufSize >= MESSAGE_HEADER_SIZE, "Incomplete header");
152e5c31af7Sopenharmony_ci	int netSize = hostToNetwork((int)messageSize);
153e5c31af7Sopenharmony_ci	int netType = hostToNetwork((int)type);
154e5c31af7Sopenharmony_ci	deMemcpy(dst+0, &netSize, sizeof(netSize));
155e5c31af7Sopenharmony_ci	deMemcpy(dst+4, &netType, sizeof(netType));
156e5c31af7Sopenharmony_ci}
157e5c31af7Sopenharmony_ci
158e5c31af7Sopenharmony_civoid Message::writeNoData (vector<deUint8>& buf) const
159e5c31af7Sopenharmony_ci{
160e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
161e5c31af7Sopenharmony_ci}
162e5c31af7Sopenharmony_ci
163e5c31af7Sopenharmony_ciHelloMessage::HelloMessage (const deUint8* data, size_t dataSize)
164e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_HELLO)
165e5c31af7Sopenharmony_ci{
166e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
167e5c31af7Sopenharmony_ci	version = parser.get<int>();
168e5c31af7Sopenharmony_ci	parser.assumEnd();
169e5c31af7Sopenharmony_ci}
170e5c31af7Sopenharmony_ci
171e5c31af7Sopenharmony_civoid HelloMessage::write (vector<deUint8>& buf) const
172e5c31af7Sopenharmony_ci{
173e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
174e5c31af7Sopenharmony_ci	writer.put(version);
175e5c31af7Sopenharmony_ci}
176e5c31af7Sopenharmony_ci
177e5c31af7Sopenharmony_ciTestMessage::TestMessage (const deUint8* data, size_t dataSize)
178e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_TEST)
179e5c31af7Sopenharmony_ci{
180e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
181e5c31af7Sopenharmony_ci	parser.getString(test);
182e5c31af7Sopenharmony_ci	parser.assumEnd();
183e5c31af7Sopenharmony_ci}
184e5c31af7Sopenharmony_ci
185e5c31af7Sopenharmony_civoid TestMessage::write (vector<deUint8>& buf) const
186e5c31af7Sopenharmony_ci{
187e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
188e5c31af7Sopenharmony_ci	writer.put(test.c_str());
189e5c31af7Sopenharmony_ci}
190e5c31af7Sopenharmony_ci
191e5c31af7Sopenharmony_ciExecuteBinaryMessage::ExecuteBinaryMessage (const deUint8* data, size_t dataSize)
192e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_EXECUTE_BINARY)
193e5c31af7Sopenharmony_ci{
194e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
195e5c31af7Sopenharmony_ci	parser.getString(name);
196e5c31af7Sopenharmony_ci	parser.getString(params);
197e5c31af7Sopenharmony_ci	parser.getString(workDir);
198e5c31af7Sopenharmony_ci	parser.getString(caseList);
199e5c31af7Sopenharmony_ci	parser.assumEnd();
200e5c31af7Sopenharmony_ci}
201e5c31af7Sopenharmony_ci
202e5c31af7Sopenharmony_civoid ExecuteBinaryMessage::write (vector<deUint8>& buf) const
203e5c31af7Sopenharmony_ci{
204e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
205e5c31af7Sopenharmony_ci	writer.put(name.c_str());
206e5c31af7Sopenharmony_ci	writer.put(params.c_str());
207e5c31af7Sopenharmony_ci	writer.put(workDir.c_str());
208e5c31af7Sopenharmony_ci	writer.put(caseList.c_str());
209e5c31af7Sopenharmony_ci}
210e5c31af7Sopenharmony_ci
211e5c31af7Sopenharmony_ciProcessLogDataMessage::ProcessLogDataMessage (const deUint8* data, size_t dataSize)
212e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_PROCESS_LOG_DATA)
213e5c31af7Sopenharmony_ci{
214e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
215e5c31af7Sopenharmony_ci	parser.getString(logData);
216e5c31af7Sopenharmony_ci	parser.assumEnd();
217e5c31af7Sopenharmony_ci}
218e5c31af7Sopenharmony_ci
219e5c31af7Sopenharmony_civoid ProcessLogDataMessage::write (vector<deUint8>& buf) const
220e5c31af7Sopenharmony_ci{
221e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
222e5c31af7Sopenharmony_ci	writer.put(logData.c_str());
223e5c31af7Sopenharmony_ci}
224e5c31af7Sopenharmony_ci
225e5c31af7Sopenharmony_ciProcessLaunchFailedMessage::ProcessLaunchFailedMessage (const deUint8* data, size_t dataSize)
226e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_PROCESS_LAUNCH_FAILED)
227e5c31af7Sopenharmony_ci{
228e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
229e5c31af7Sopenharmony_ci	parser.getString(reason);
230e5c31af7Sopenharmony_ci	parser.assumEnd();
231e5c31af7Sopenharmony_ci}
232e5c31af7Sopenharmony_ci
233e5c31af7Sopenharmony_civoid ProcessLaunchFailedMessage::write (vector<deUint8>& buf) const
234e5c31af7Sopenharmony_ci{
235e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
236e5c31af7Sopenharmony_ci	writer.put(reason.c_str());
237e5c31af7Sopenharmony_ci}
238e5c31af7Sopenharmony_ci
239e5c31af7Sopenharmony_ciProcessFinishedMessage::ProcessFinishedMessage (const deUint8* data, size_t dataSize)
240e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_PROCESS_FINISHED)
241e5c31af7Sopenharmony_ci{
242e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
243e5c31af7Sopenharmony_ci	exitCode = parser.get<int>();
244e5c31af7Sopenharmony_ci	parser.assumEnd();
245e5c31af7Sopenharmony_ci}
246e5c31af7Sopenharmony_ci
247e5c31af7Sopenharmony_civoid ProcessFinishedMessage::write (vector<deUint8>& buf) const
248e5c31af7Sopenharmony_ci{
249e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
250e5c31af7Sopenharmony_ci	writer.put(exitCode);
251e5c31af7Sopenharmony_ci}
252e5c31af7Sopenharmony_ci
253e5c31af7Sopenharmony_ciInfoMessage::InfoMessage (const deUint8* data, size_t dataSize)
254e5c31af7Sopenharmony_ci	: Message(MESSAGETYPE_INFO)
255e5c31af7Sopenharmony_ci{
256e5c31af7Sopenharmony_ci	MessageParser parser(data, dataSize);
257e5c31af7Sopenharmony_ci	parser.getString(info);
258e5c31af7Sopenharmony_ci	parser.assumEnd();
259e5c31af7Sopenharmony_ci}
260e5c31af7Sopenharmony_ci
261e5c31af7Sopenharmony_civoid InfoMessage::write (vector<deUint8>& buf) const
262e5c31af7Sopenharmony_ci{
263e5c31af7Sopenharmony_ci	MessageWriter writer(type, buf);
264e5c31af7Sopenharmony_ci	writer.put(info.c_str());
265e5c31af7Sopenharmony_ci}
266e5c31af7Sopenharmony_ci
267e5c31af7Sopenharmony_ci} // xs
268