• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2023 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 #include <android-base/file.h>
17 #include <gflags/gflags.h>
18 
19 #include <stdio.h>
20 #include <fstream>
21 #include <string>
22 #include <unordered_set>
23 
24 #include "common/libs/utils/files.h"
25 #include "common/libs/utils/flags_validator.h"
26 #include "common/libs/utils/json.h"
27 #include "host/commands/cvd/parser/cf_configs_common.h"
28 
29 namespace cuttlefish {
30 
31 // json main parameters definitions
32 static std::map<std::string, Json::ValueType> kConfigsKeyMap = {
33     {"credential", Json::ValueType::stringValue},
34     {"netsim_bt", Json::ValueType::booleanValue},
35     {"instances", Json::ValueType::arrayValue}};
36 
37 // instance object parameters definitions
38 static std::map<std::string, Json::ValueType> kInstanceKeyMap = {
39     {"@import", Json::ValueType::stringValue},
40     {"vm", Json::ValueType::objectValue},
41     {"boot", Json::ValueType::objectValue},
42     {"security", Json::ValueType::objectValue},
43     {"disk", Json::ValueType::objectValue},
44     {"graphics", Json::ValueType::objectValue},
45     {"camera", Json::ValueType::objectValue},
46     {"connectivity", Json::ValueType::objectValue},
47     {"audio", Json::ValueType::objectValue},
48     {"streaming", Json::ValueType::objectValue},
49     {"adb", Json::ValueType::objectValue},
50     {"vehicle", Json::ValueType::objectValue},
51     {"location", Json::ValueType::objectValue}};
52 
53 // supported import values for @import key
54 static std::unordered_set<std::string> kSupportedImportValues = {
55     "phone", "tablet", "tv", "wearable", "auto", "slim", "go", "foldable"};
56 
57 // supported import values for vm category and crosvm subcategory
58 static std::map<std::string, Json::ValueType> kVmKeyMap = {
59     {"cpus", Json::ValueType::uintValue},
60     {"memory_mb", Json::ValueType::uintValue},
61     {"use_sdcard", Json::ValueType::booleanValue},
62     {"setupwizard_mode", Json::ValueType::stringValue},
63     {"uuid", Json::ValueType::stringValue},
64     {"crosvm", Json::ValueType::objectValue},
65     {"qemu", Json::ValueType::objectValue},
66     {"gem5", Json::ValueType::objectValue},
67     {"custom_actions", Json::ValueType::arrayValue},
68 };
69 static std::map<std::string, Json::ValueType> kCrosvmKeyMap = {
70     {"enable_sandbox", Json::ValueType::booleanValue},
71 };
72 
73 // supported import values for boot category and kernel subcategory
74 static std::map<std::string, Json::ValueType> kBootKeyMap = {
75     {"extra_bootconfig_args", Json::ValueType::stringValue},
76     {"kernel", Json::ValueType::objectValue},
77     {"enable_bootanimation", Json::ValueType::booleanValue},
78 };
79 static std::map<std::string, Json::ValueType> kernelkeyMap = {
80     {"extra_kernel_cmdline", Json::ValueType::stringValue},
81 };
82 
83 // supported import values for graphics category and displays subcategory
84 static std::map<std::string, Json::ValueType> kGraphicsKeyMap = {
85     {"displays", Json::ValueType::arrayValue},
86 };
87 static std::map<std::string, Json::ValueType> kDisplayKeyMap = {
88     {"width", Json::ValueType::uintValue},
89     {"height", Json::ValueType::uintValue},
90     {"dpi", Json::ValueType::uintValue},
91     {"refresh_rate_hertz", Json::ValueType::uintValue},
92 };
93 
94 // supported import values for security category
95 static std::map<std::string, Json::ValueType> kSecurityKeyMap = {
96     {"serial_number", Json::ValueType::stringValue},
97     {"guest_enforce_security", Json::ValueType::booleanValue},
98 };
99 
100 // supported import values for disk category
101 static std::map<std::string, Json::ValueType> kDiskKeyMap = {
102     {"default_build", Json::ValueType::stringValue},
103     {"system_build", Json::ValueType::stringValue},
104     {"kernel_build", Json::ValueType::stringValue},
105 };
106 
107 // Validate the security json parameters
ValidateSecurityConfigs(const Json::Value & root)108 Result<void> ValidateSecurityConfigs(const Json::Value& root) {
109   CF_EXPECT(ValidateTypo(root, kSecurityKeyMap),
110             "ValidateSecurityConfigs ValidateTypo fail");
111   return {};
112 }
ValidateDiskConfigs(const Json::Value & root)113 Result<void> ValidateDiskConfigs(const Json::Value& root) {
114   CF_EXPECT(ValidateTypo(root, kDiskKeyMap),
115             "ValidateDiskConfigs ValidateTypo fail");
116   return {};
117 }
118 
119 // Validate the displays json parameters
ValidateDisplaysConfigs(const Json::Value & root)120 Result<void> ValidateDisplaysConfigs(const Json::Value& root) {
121   CF_EXPECT(ValidateTypo(root, kDisplayKeyMap),
122             "ValidateDisplaysConfigs ValidateTypo fail");
123   return {};
124 }
125 
126 // Validate the graphics json parameters
ValidateGraphicsConfigs(const Json::Value & root)127 Result<void> ValidateGraphicsConfigs(const Json::Value& root) {
128   CF_EXPECT(ValidateTypo(root, kGraphicsKeyMap),
129             "ValidateGraphicsConfigs ValidateTypo fail");
130 
131   if (root.isMember("displays") && root["displays"].size() != 0) {
132     int num_displays = root["displays"].size();
133     for (int i = 0; i < num_displays; i++) {
134       CF_EXPECT(ValidateDisplaysConfigs(root["displays"][i]),
135                 "ValidateDisplaysConfigs fail");
136     }
137   }
138 
139   return {};
140 }
141 
142 // Validate the vm json parameters
ValidateVmConfigs(const Json::Value & root)143 Result<void> ValidateVmConfigs(const Json::Value& root) {
144   CF_EXPECT(ValidateTypo(root, kVmKeyMap),
145             "ValidateVmConfigs ValidateTypo fail");
146   if (root.isMember("crosvm")) {
147     CF_EXPECT(ValidateTypo(root["crosvm"], kCrosvmKeyMap),
148               "ValidateVmConfigs ValidateTypo crosvm fail");
149   }
150   return {};
151 }
152 
153 // Validate the kernel json parameters
ValidateKernelConfigs(const Json::Value & root)154 Result<void> ValidateKernelConfigs(const Json::Value& root) {
155   CF_EXPECT(ValidateTypo(root, kernelkeyMap),
156             "ValidateKernelConfigs ValidateTypo fail");
157   return {};
158 }
159 
160 // Validate the boot json parameters
ValidateBootConfigs(const Json::Value & root)161 Result<void> ValidateBootConfigs(const Json::Value& root) {
162   CF_EXPECT(ValidateTypo(root, kBootKeyMap),
163             "ValidateBootConfigs ValidateTypo fail");
164 
165   if (root.isMember("kernel")) {
166     CF_EXPECT(ValidateKernelConfigs(root["kernel"]),
167               "ValidateKernelConfigs fail");
168   }
169 
170   return {};
171 }
172 
173 // Validate the instances json parameters
ValidateInstancesConfigs(const Json::Value & root)174 Result<void> ValidateInstancesConfigs(const Json::Value& root) {
175   int num_instances = root.size();
176   for (unsigned int i = 0; i < num_instances; i++) {
177     CF_EXPECT(ValidateTypo(root[i], kInstanceKeyMap), "vm ValidateTypo fail");
178 
179     if (root[i].isMember("vm")) {
180       CF_EXPECT(ValidateVmConfigs(root[i]["vm"]), "ValidateVmConfigs fail");
181     }
182 
183     // Validate @import flag values are supported or not
184     if (root[i].isMember("@import")) {
185       CF_EXPECT(kSupportedImportValues.count(root[i]["@import"].asString()) > 0,
186                 "@Import flag values are not supported");
187     }
188 
189     if (root[i].isMember("boot")) {
190       CF_EXPECT(ValidateBootConfigs(root[i]["boot"]),
191                 "ValidateBootConfigs fail");
192     }
193     if (root[i].isMember("security")) {
194       CF_EXPECT(ValidateSecurityConfigs(root[i]["security"]),
195                 "ValidateSecurityConfigs fail");
196     }
197     if (root[i].isMember("disk")) {
198       CF_EXPECT(ValidateDiskConfigs(root[i]["disk"]),
199                 "ValidateDiskConfigs fail");
200     }
201     if (root[i].isMember("graphics")) {
202       CF_EXPECT(ValidateGraphicsConfigs(root[i]["graphics"]),
203                 "ValidateGraphicsConfigs fail");
204     }
205   }
206   CF_EXPECT(ValidateStringConfig(root, "vm", "setupwizard_mode",
207                                  ValidateStupWizardMode),
208             "Invalid value for setupwizard_mode flag");
209 
210   return {};
211 }
212 
213 // Validate cuttlefish config json parameters
ValidateCfConfigs(const Json::Value & root)214 Result<void> ValidateCfConfigs(const Json::Value& root) {
215   CF_EXPECT(ValidateTypo(root, kConfigsKeyMap),
216             "Typo in config main parameters");
217   CF_EXPECT(root.isMember("instances"), "instances object is missing");
218   CF_EXPECT(ValidateInstancesConfigs(root["instances"]),
219             "ValidateInstancesConfigs failed");
220 
221   return {};
222 }
223 
224 }  // namespace cuttlefish
225