• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2020 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 // frame_capture_test_utils:
7 //   Helper functions for capture and replay of traces.
8 //
9 
10 #ifndef UTIL_FRAME_CAPTURE_TEST_UTILS_H_
11 #define UTIL_FRAME_CAPTURE_TEST_UTILS_H_
12 
13 #include <iostream>
14 #include <memory>
15 #include <sstream>
16 #include <type_traits>
17 #include <vector>
18 
19 #include "common/angleutils.h"
20 #include "common/system_utils.h"
21 
22 #define USE_SYSTEM_ZLIB
23 #include "compression_utils_portable.h"
24 
25 #define ANGLE_MACRO_STRINGIZE_AUX(a) #a
26 #define ANGLE_MACRO_STRINGIZE(a) ANGLE_MACRO_STRINGIZE_AUX(a)
27 #define ANGLE_MACRO_CONCAT_AUX(a, b) a##b
28 #define ANGLE_MACRO_CONCAT(a, b) ANGLE_MACRO_CONCAT_AUX(a, b)
29 
30 namespace angle
31 {
32 
DecompressBinaryData(const std::vector<uint8_t> & compressedData)33 inline uint8_t *DecompressBinaryData(const std::vector<uint8_t> &compressedData)
34 {
35     uint32_t uncompressedSize =
36         zlib_internal::GetGzipUncompressedSize(compressedData.data(), compressedData.size());
37 
38     std::unique_ptr<uint8_t[]> uncompressedData(new uint8_t[uncompressedSize]);
39     uLong destLen = uncompressedSize;
40     int zResult =
41         zlib_internal::GzipUncompressHelper(uncompressedData.get(), &destLen, compressedData.data(),
42                                             static_cast<uLong>(compressedData.size()));
43 
44     if (zResult != Z_OK)
45     {
46         std::cerr << "Failure to decompressed binary data: " << zResult << "\n";
47         return nullptr;
48     }
49 
50     return uncompressedData.release();
51 }
52 
53 using DecompressCallback = uint8_t *(*)(const std::vector<uint8_t> &);
54 
55 using SetBinaryDataDecompressCallbackFunc = void (*)(DecompressCallback);
56 using SetBinaryDataDirFunc                = void (*)(const char *);
57 using SetupReplayFunc                     = void (*)();
58 using ReplayFrameFunc                     = void (*)(uint32_t);
59 using ResetReplayFunc                     = void (*)();
60 using FinishReplayFunc                    = void (*)();
61 using GetSerializedContextStateFunc       = const char *(*)(uint32_t);
62 
63 class TraceLibrary
64 {
65   public:
TraceLibrary(const char * traceNameIn)66     TraceLibrary(const char *traceNameIn)
67     {
68         std::stringstream traceNameStr;
69 #if !defined(ANGLE_PLATFORM_WINDOWS)
70         traceNameStr << "lib";
71 #endif  // !defined(ANGLE_PLATFORM_WINDOWS)
72         traceNameStr << traceNameIn;
73 #if defined(ANGLE_PLATFORM_ANDROID) && defined(COMPONENT_BUILD)
74         // Added to shared library names in Android component builds in
75         // https://chromium.googlesource.com/chromium/src/+/9bacc8c4868cc802f69e1e858eea6757217a508f/build/toolchain/toolchain.gni#56
76         traceNameStr << ".cr";
77 #endif  // defined(ANGLE_PLATFORM_ANDROID) && defined(COMPONENT_BUILD)
78         std::string traceName = traceNameStr.str();
79         mTraceLibrary.reset(OpenSharedLibrary(traceName.c_str(), SearchType::ModuleDir));
80     }
81 
valid()82     bool valid() const { return mTraceLibrary != nullptr; }
83 
setBinaryDataDir(const char * dataDir)84     void setBinaryDataDir(const char *dataDir)
85     {
86         callFunc<SetBinaryDataDirFunc>("SetBinaryDataDir", dataDir);
87     }
88 
setBinaryDataDecompressCallback(DecompressCallback callback)89     void setBinaryDataDecompressCallback(DecompressCallback callback)
90     {
91         callFunc<SetBinaryDataDecompressCallbackFunc>("SetBinaryDataDecompressCallback", callback);
92     }
93 
replayFrame(uint32_t frameIndex)94     void replayFrame(uint32_t frameIndex) { callFunc<ReplayFrameFunc>("ReplayFrame", frameIndex); }
95 
setupReplay()96     void setupReplay() { callFunc<SetupReplayFunc>("SetupReplay"); }
97 
resetReplay()98     void resetReplay() { callFunc<ResetReplayFunc>("ResetReplay"); }
99 
finishReplay()100     void finishReplay() { callFunc<FinishReplayFunc>("FinishReplay"); }
101 
getSerializedContextState(uint32_t frameIndex)102     const char *getSerializedContextState(uint32_t frameIndex)
103     {
104         return callFunc<GetSerializedContextStateFunc>("GetSerializedContextState", frameIndex);
105     }
106 
107   private:
108     template <typename FuncT, typename... ArgsT>
callFunc(const char * funcName,ArgsT...args)109     typename std::result_of<FuncT(ArgsT...)>::type callFunc(const char *funcName, ArgsT... args)
110     {
111         void *untypedFunc = mTraceLibrary->getSymbol(funcName);
112         if (!untypedFunc)
113         {
114             fprintf(stderr, "Error loading function: %s\n", funcName);
115             ASSERT(untypedFunc);
116         }
117         auto typedFunc = reinterpret_cast<FuncT>(untypedFunc);
118         return typedFunc(args...);
119     }
120 
121     std::unique_ptr<Library> mTraceLibrary;
122 };
123 
124 }  // namespace angle
125 
126 #endif  // UTIL_FRAME_CAPTURE_TEST_UTILS_H_
127