1 /*
2 * Copyright (c) 2022 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <gtest/gtest.h>
17
18 #include "file_item_container.h"
19 #include "pgo.h"
20
21 namespace panda::panda_file::test {
22
CreateItems(ItemContainer & container)23 static void CreateItems(ItemContainer &container)
24 {
25 // Add classes
26 ClassItem *empty_class_item = container.GetOrCreateClassItem("LTest;");
27 ClassItem *class_item_a = container.GetOrCreateClassItem("LAA;");
28 class_item_a->SetSuperClass(empty_class_item);
29
30 // Add method1
31 StringItem *method_name_1 = container.GetOrCreateStringItem("foo1");
32 PrimitiveTypeItem *ret_type_1 = container.GetOrCreatePrimitiveTypeItem(Type::TypeId::VOID);
33 std::vector<MethodParamItem> params_1;
34 ProtoItem *proto_item_1 = container.GetOrCreateProtoItem(ret_type_1, params_1);
35 MethodItem *method_item_1 = class_item_a->AddMethod(method_name_1, proto_item_1, ACC_PUBLIC | ACC_STATIC, params_1);
36
37 // Set code_1
38 std::vector<uint8_t> instructions_1 {1, 2, 3, 4};
39 CodeItem *code_item_1 = container.CreateItem<CodeItem>(0, 2, instructions_1);
40 method_item_1->SetCode(code_item_1);
41 code_item_1->AddMethod(method_item_1);
42 }
43
CreateProfile(std::string & filePath)44 static void CreateProfile(std::string &filePath)
45 {
46 filePath = "TestParseProfileData_test_data.txt";
47 std::ofstream test_file;
48 test_file.open(filePath);
49 test_file << "" << std::endl;
50 test_file << "string_item:test_field" << std::endl;
51 test_file << "class_item:AA" << std::endl;
52 test_file << "XXXXXXX" << std::endl;
53 test_file << "code_item:AA::foo1" << std::endl;
54 test_file << "code_item:Test::foo4" << std::endl;
55 test_file.close();
56 }
57
58 HWTEST(Pgo, MarkProfileItem, testing::ext::TestSize.Level0)
59 {
60 ItemContainer container;
61 CreateItems(container);
62 panda::panda_file::pgo::ProfileOptimizer profile_opt;
63 for (auto &item : container.GetItems()) {
64 if (item->GetName() == CLASS_ITEM) {
65 profile_opt.MarkProfileItem(item, true);
66 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_CLASS_DEFAULT_COUNT + 1U); // 1 means set pgo
67 profile_opt.MarkProfileItem(item, false);
68 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_CLASS_DEFAULT_COUNT);
69 } else if (item->GetName() == STRING_ITEM) {
70 profile_opt.MarkProfileItem(item, true);
71 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_STRING_DEFAULT_COUNT + 1U); // 1 means set pgo
72 profile_opt.MarkProfileItem(item, false);
73 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_STRING_DEFAULT_COUNT);
74 } else if (item->GetName() == CODE_ITEM) {
75 profile_opt.MarkProfileItem(item, true);
76 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_CODE_DEFAULT_COUNT + 1U); // 1 means set pgo
77 profile_opt.MarkProfileItem(item, false);
78 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_CODE_DEFAULT_COUNT);
79 }
80 }
81 }
82
83 HWTEST(Pgo, ParseProfileData0, testing::ext::TestSize.Level0)
84 {
85 panda::panda_file::pgo::ProfileOptimizer profile_opt;
86 EXPECT_FALSE(profile_opt.ParseProfileData());
87 }
88
89 HWTEST(Pgo, ParseProfileData1, testing::ext::TestSize.Level0)
90 {
91 std::string profile_path;
92 CreateProfile(profile_path);
93
94 panda::panda_file::pgo::ProfileOptimizer profile_opt;
95 profile_opt.SetProfilePath(profile_path);
96 EXPECT_TRUE(profile_opt.ParseProfileData());
97 }
98
99 HWTEST(Pgo, ProfileGuidedRelayout, testing::ext::TestSize.Level0)
100 {
101 ItemContainer container;
102 CreateItems(container);
103
104 std::string profile_path;
105 CreateProfile(profile_path);
106
107 panda::panda_file::pgo::ProfileOptimizer profile_opt;
108 for (auto &item : container.GetItems()) {
109 item->SetNeedsEmit(false);
110 }
111 profile_opt.ProfileGuidedRelayout(container.GetItems());
112 for (auto &item : container.GetItems()) {
113 item->SetNeedsEmit(true);
114 }
115 profile_opt.ProfileGuidedRelayout(container.GetItems());
116 for (auto &item : container.GetItems()) {
117 if (item->GetName() == CLASS_ITEM) {
118 EXPECT_EQ(item->GetPGORank(), panda::panda_file::PGO_CLASS_DEFAULT_COUNT);
119 }
120 }
121 }
122
123 } // namespace panda::panda_file::test
124