1/*
2 * Copyright (C) 2015 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#include "read_elf.h"
18
19#include <gtest/gtest.h>
20
21#include <map>
22#include "get_test_data.h"
23
24TEST(read_elf, GetBuildIdFromElfFile) {
25  BuildId build_id;
26  ASSERT_TRUE(GetBuildIdFromElfFile(GetTestData(ELF_FILE), &build_id));
27  ASSERT_EQ(build_id, BuildId(elf_file_build_id));
28}
29
30TEST(read_elf, GetBuildIdFromEmbeddedElfFile) {
31  BuildId build_id;
32  ASSERT_TRUE(GetBuildIdFromEmbeddedElfFile(GetTestData(APK_FILE), NATIVELIB_OFFSET_IN_APK,
33                                            NATIVELIB_SIZE_IN_APK, &build_id));
34  ASSERT_EQ(build_id, native_lib_build_id);
35}
36
37void ParseSymbol(const ElfFileSymbol& symbol, std::map<std::string, ElfFileSymbol>* symbols) {
38  (*symbols)[symbol.name] = symbol;
39}
40
41void CheckElfFileSymbols(const std::map<std::string, ElfFileSymbol>& symbols) {
42  auto pos = symbols.find("GlobalVar");
43  ASSERT_NE(pos, symbols.end());
44  ASSERT_FALSE(pos->second.is_func);
45  pos = symbols.find("GlobalFunc");
46  ASSERT_NE(pos, symbols.end());
47  ASSERT_TRUE(pos->second.is_func);
48  ASSERT_TRUE(pos->second.is_in_text_section);
49}
50
51TEST(read_elf, parse_symbols_from_elf_file_with_correct_build_id) {
52  std::map<std::string, ElfFileSymbol> symbols;
53  ASSERT_TRUE(ParseSymbolsFromElfFile(GetTestData(ELF_FILE), elf_file_build_id,
54                                      std::bind(ParseSymbol, std::placeholders::_1, &symbols)));
55  CheckElfFileSymbols(symbols);
56}
57
58TEST(read_elf, parse_symbols_from_elf_file_without_build_id) {
59  std::map<std::string, ElfFileSymbol> symbols;
60  ASSERT_TRUE(ParseSymbolsFromElfFile(GetTestData(ELF_FILE), BuildId(),
61                                      std::bind(ParseSymbol, std::placeholders::_1, &symbols)));
62  CheckElfFileSymbols(symbols);
63}
64
65TEST(read_elf, parse_symbols_from_elf_file_with_wrong_build_id) {
66  BuildId build_id("01010101010101010101");
67  std::map<std::string, ElfFileSymbol> symbols;
68  ASSERT_FALSE(ParseSymbolsFromElfFile(GetTestData(ELF_FILE), build_id,
69                                       std::bind(ParseSymbol, std::placeholders::_1, &symbols)));
70}
71
72TEST(read_elf, ParseSymbolsFromEmbeddedElfFile) {
73  std::map<std::string, ElfFileSymbol> symbols;
74  ASSERT_TRUE(ParseSymbolsFromEmbeddedElfFile(GetTestData(APK_FILE), NATIVELIB_OFFSET_IN_APK,
75                                              NATIVELIB_SIZE_IN_APK, native_lib_build_id,
76                                              std::bind(ParseSymbol, std::placeholders::_1, &symbols)));
77  CheckElfFileSymbols(symbols);
78}
79
80TEST(read_elf, arm_mapping_symbol) {
81  ASSERT_TRUE(IsArmMappingSymbol("$a"));
82  ASSERT_FALSE(IsArmMappingSymbol("$b"));
83  ASSERT_TRUE(IsArmMappingSymbol("$a.anything"));
84  ASSERT_FALSE(IsArmMappingSymbol("$a_no_dot"));
85}
86
87TEST(read_elf, IsValidElfPath) {
88  ASSERT_FALSE(IsValidElfPath("/dev/zero"));
89  ASSERT_FALSE(IsValidElfPath("/sys/devices/system/cpu/online"));
90  ASSERT_TRUE(IsValidElfPath(GetTestData(ELF_FILE)));
91}
92