1 /*-------------------------------------------------------------------------
2 * drawElements Quality Program Test Executor
3 * ------------------------------------------
5 * Copyright 2014 The Android Open Source Project
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
21 * \brief Extract shader programs from log.
22 *//*--------------------------------------------------------------------*/
24 #include "xeTestLogParser.hpp"
25 #include "xeTestResultParser.hpp"
26 #include "deFilePath.hpp"
27 #include "deStringUtil.hpp"
53 static const char* getShaderTypeSuffix (const xe::ri::Shader::ShaderType shaderType)
57 case xe::ri::Shader::SHADERTYPE_VERTEX: return "vert";
58 case xe::ri::Shader::SHADERTYPE_FRAGMENT: return "frag";
59 case xe::ri::Shader::SHADERTYPE_GEOMETRY: return "geom";
60 case xe::ri::Shader::SHADERTYPE_TESS_CONTROL: return "tesc";
61 case xe::ri::Shader::SHADERTYPE_TESS_EVALUATION: return "tese";
62 case xe::ri::Shader::SHADERTYPE_COMPUTE: return "comp";
64 throw xe::Error("Invalid shader type");
68 static void writeShaderProgram (const CommandLine& cmdLine, const std::string& casePath, const xe::ri::ShaderProgram& shaderProgram, int programNdx)
70 const string basePath = string(de::FilePath::join(cmdLine.dstPath, casePath).getPath()) + "." + de::toString(programNdx);
72 for (int shaderNdx = 0; shaderNdx < shaderProgram.shaders.getNumItems(); shaderNdx++)
74 const xe::ri::Shader& shader = dynamic_cast<const xe::ri::Shader&>(shaderProgram.shaders.getItem(shaderNdx));
75 const string shaderPath = basePath + "." + getShaderTypeSuffix(shader.shaderType);
77 if (de::FilePath(shaderPath).exists())
78 throw xe::Error("File '" + shaderPath + "' exists already");
81 std::ofstream out(shaderPath.c_str(), std::ifstream::binary|std::ifstream::out);
84 throw xe::Error("Failed to open '" + shaderPath + "'");
86 out.write(shader.source.source.c_str(), shader.source.source.size());
93 const xe::ri::List* list;
96 explicit StackEntry (const xe::ri::List* list_) : list(list_), curNdx(0) {}
99 static void extractShaderPrograms (const CommandLine& cmdLine, const std::string& casePath, const xe::TestCaseResult& result)
101 vector<StackEntry> itemListStack;
104 itemListStack.push_back(StackEntry(&result.resultItems));
106 while (!itemListStack.empty())
108 StackEntry& curEntry = itemListStack.back();
110 if (curEntry.curNdx < curEntry.list->getNumItems())
112 const xe::ri::Item& curItem = curEntry.list->getItem(curEntry.curNdx);
113 curEntry.curNdx += 1;
115 if (curItem.getType() == xe::ri::TYPE_SHADERPROGRAM)
117 writeShaderProgram(cmdLine, casePath, static_cast<const xe::ri::ShaderProgram&>(curItem), programNdx);
120 else if (curItem.getType() == xe::ri::TYPE_SECTION)
121 itemListStack.push_back(StackEntry(&static_cast<const xe::ri::Section&>(curItem).items));
124 itemListStack.pop_back();
128 std::cout << "WARNING: no shader programs found in '" << casePath << "'\n";
131 class ShaderProgramExtractHandler : public xe::TestLogHandler
134 ShaderProgramExtractHandler (const CommandLine& cmdLine)
139 void setSessionInfo (const xe::SessionInfo&)
144 xe::TestCaseResultPtr startTestCaseResult (const char* casePath)
146 return xe::TestCaseResultPtr(new xe::TestCaseResultData(casePath));
149 void testCaseResultUpdated (const xe::TestCaseResultPtr&)
154 void testCaseResultComplete (const xe::TestCaseResultPtr& caseData)
156 if (caseData->getDataSize() > 0)
158 xe::TestCaseResult fullResult;
159 xe::TestResultParser::ParseResult parseResult;
161 m_testResultParser.init(&fullResult);
162 parseResult = m_testResultParser.parse(caseData->getData(), caseData->getDataSize());
163 DE_UNREF(parseResult);
165 extractShaderPrograms(m_cmdLine, caseData->getTestCasePath(), fullResult);
170 const CommandLine& m_cmdLine;
171 xe::TestResultParser m_testResultParser;
174 static void extractShaderProgramsFromLogFile (const CommandLine& cmdLine)
176 std::ifstream in (cmdLine.filename.c_str(), std::ifstream::binary|std::ifstream::in);
177 ShaderProgramExtractHandler resultHandler (cmdLine);
178 xe::TestLogParser parser (&resultHandler);
183 throw std::runtime_error(string("Failed to open '") + cmdLine.filename + "'");
187 in.read((char*)&buf[0], DE_LENGTH_OF_ARRAY(buf));
188 numRead = (int)in.gcount();
193 parser.parse(&buf[0], numRead);
199 static void printHelp (const char* binName)
201 printf("%s: [filename] [dst path (optional)]\n", binName);
204 static bool parseCommandLine (CommandLine& cmdLine, int argc, const char* const* argv)
206 for (int argNdx = 1; argNdx < argc; argNdx++)
208 const char* arg = argv[argNdx];
210 if (!deStringBeginsWith(arg, "--"))
212 if (cmdLine.filename.empty())
213 cmdLine.filename = arg;
214 else if (cmdLine.dstPath.empty())
215 cmdLine.dstPath = arg;
223 if (cmdLine.filename.empty())
229 int main (int argc, const char* const* argv)
235 if (!parseCommandLine(cmdLine, argc, argv))
241 extractShaderProgramsFromLogFile(cmdLine);
243 catch (const std::exception& e)
245 printf("FATAL ERROR: %s\n", e.what());