• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2014 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ART_COMPILER_UTILS_JNI_MACRO_ASSEMBLER_TEST_H_
18 #define ART_COMPILER_UTILS_JNI_MACRO_ASSEMBLER_TEST_H_
19 
20 #include "jni_macro_assembler.h"
21 
22 #include "assembler_test_base.h"
23 #include "common_runtime_test.h"  // For ScratchFile
24 
25 #include <sys/stat.h>
26 
27 #include <cstdio>
28 #include <cstdlib>
29 #include <fstream>
30 #include <iterator>
31 
32 namespace art {
33 
34 template<typename Ass>
35 class JNIMacroAssemblerTest : public testing::Test {
36  public:
GetAssembler()37   Ass* GetAssembler() {
38     return assembler_.get();
39   }
40 
41   typedef std::string (*TestFn)(JNIMacroAssemblerTest* assembler_test, Ass* assembler);
42 
DriverFn(TestFn f,const std::string & test_name)43   void DriverFn(TestFn f, const std::string& test_name) {
44     DriverWrapper(f(this, assembler_.get()), test_name);
45   }
46 
47   // This driver assumes the assembler has already been called.
DriverStr(const std::string & assembly_string,const std::string & test_name)48   void DriverStr(const std::string& assembly_string, const std::string& test_name) {
49     DriverWrapper(assembly_string, test_name);
50   }
51 
52   // This is intended to be run as a test.
CheckTools()53   bool CheckTools() {
54     return test_helper_->CheckTools();
55   }
56 
57  protected:
JNIMacroAssemblerTest()58   JNIMacroAssemblerTest() {}
59 
SetUp()60   void SetUp() OVERRIDE {
61     allocator_.reset(new ArenaAllocator(&pool_));
62     assembler_.reset(CreateAssembler(allocator_.get()));
63     test_helper_.reset(
64         new AssemblerTestInfrastructure(GetArchitectureString(),
65                                         GetAssemblerCmdName(),
66                                         GetAssemblerParameters(),
67                                         GetObjdumpCmdName(),
68                                         GetObjdumpParameters(),
69                                         GetDisassembleCmdName(),
70                                         GetDisassembleParameters(),
71                                         GetAssemblyHeader()));
72 
73     SetUpHelpers();
74   }
75 
TearDown()76   void TearDown() OVERRIDE {
77     test_helper_.reset();  // Clean up the helper.
78     assembler_.reset();
79     allocator_.reset();
80   }
81 
82   // Override this to set up any architecture-specific things, e.g., CPU revision.
CreateAssembler(ArenaAllocator * allocator)83   virtual Ass* CreateAssembler(ArenaAllocator* allocator) {
84     return new (allocator) Ass(allocator);
85   }
86 
87   // Override this to set up any architecture-specific things, e.g., register vectors.
SetUpHelpers()88   virtual void SetUpHelpers() {}
89 
90   // Get the typically used name for this architecture, e.g., aarch64, x86_64, ...
91   virtual std::string GetArchitectureString() = 0;
92 
93   // Get the name of the assembler, e.g., "as" by default.
GetAssemblerCmdName()94   virtual std::string GetAssemblerCmdName() {
95     return "as";
96   }
97 
98   // Switches to the assembler command. Default none.
GetAssemblerParameters()99   virtual std::string GetAssemblerParameters() {
100     return "";
101   }
102 
103   // Get the name of the objdump, e.g., "objdump" by default.
GetObjdumpCmdName()104   virtual std::string GetObjdumpCmdName() {
105     return "objdump";
106   }
107 
108   // Switches to the objdump command. Default is " -h".
GetObjdumpParameters()109   virtual std::string GetObjdumpParameters() {
110     return " -h";
111   }
112 
113   // Get the name of the objdump, e.g., "objdump" by default.
GetDisassembleCmdName()114   virtual std::string GetDisassembleCmdName() {
115     return "objdump";
116   }
117 
118   // Switches to the objdump command. As it's a binary, one needs to push the architecture and
119   // such to objdump, so it's architecture-specific and there is no default.
120   virtual std::string GetDisassembleParameters() = 0;
121 
122   // If the assembly file needs a header, return it in a sub-class.
GetAssemblyHeader()123   virtual const char* GetAssemblyHeader() {
124     return nullptr;
125   }
126 
127  private:
128   // Override this to pad the code with NOPs to a certain size if needed.
Pad(std::vector<uint8_t> & data ATTRIBUTE_UNUSED)129   virtual void Pad(std::vector<uint8_t>& data ATTRIBUTE_UNUSED) {
130   }
131 
DriverWrapper(const std::string & assembly_text,const std::string & test_name)132   void DriverWrapper(const std::string& assembly_text, const std::string& test_name) {
133     assembler_->FinalizeCode();
134     size_t cs = assembler_->CodeSize();
135     std::unique_ptr<std::vector<uint8_t>> data(new std::vector<uint8_t>(cs));
136     MemoryRegion code(&(*data)[0], data->size());
137     assembler_->FinalizeInstructions(code);
138     Pad(*data);
139     test_helper_->Driver(*data, assembly_text, test_name);
140   }
141 
142   ArenaPool pool_;
143   std::unique_ptr<ArenaAllocator> allocator_;
144   std::unique_ptr<Ass> assembler_;
145   std::unique_ptr<AssemblerTestInfrastructure> test_helper_;
146 
147   DISALLOW_COPY_AND_ASSIGN(JNIMacroAssemblerTest);
148 };
149 
150 }  // namespace art
151 
152 #endif  // ART_COMPILER_UTILS_JNI_MACRO_ASSEMBLER_TEST_H_
153