Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 1 | /* |
Nik Dewally | 298a804 | 2024-07-23 15:03:13 +0100 | [diff] [blame] | 2 | * Copyright (c) 2019-2024, Arm Limited. All rights reserved. |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 3 | * |
| 4 | * SPDX-License-Identifier: BSD-3-Clause |
| 5 | * |
| 6 | */ |
| 7 | |
Nik Dewally | bacae6c | 2024-07-30 16:58:14 +0100 | [diff] [blame] | 8 | #include <stdint.h> |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 9 | #include <string> |
Nik Dewally | bacae6c | 2024-07-30 16:58:14 +0100 | [diff] [blame] | 10 | #include <vector> |
Nik Dewally | bacae6c | 2024-07-30 16:58:14 +0100 | [diff] [blame] | 11 | |
| 12 | class psa_asset; |
| 13 | |
| 14 | enum class psa_asset_type; |
| 15 | class psa_call; |
| 16 | |
| 17 | enum class asset_search; |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 18 | |
| 19 | /* These classes "cut down the clutter" by grouping together related data and |
| 20 | associated methods (most importantly their constructors) used in template_ |
| 21 | line, psa_call, psa_asset (etc.). */ |
| 22 | |
| 23 | #ifndef DATA_BLOCKS_HPP |
| 24 | #define DATA_BLOCKS_HPP |
| 25 | |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 26 | using namespace std; |
| 27 | |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 28 | /// Possible values of return codes. |
| 29 | /// |
| 30 | /// Intended to be used primarily through [expect_info] |
| 31 | enum class expected_return_code_t { |
| 32 | /// This call should pass. |
| 33 | Pass, |
| 34 | /// This call should fail. |
| 35 | Fail, |
| 36 | /// This call should return a specific error code. |
| 37 | SpecificFail, |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 38 | |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 39 | /// The outcome of this call is unknown and should be simulated. |
| 40 | DontKnow, |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 41 | |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 42 | /// the return code does not matter, and checks for this should not take |
| 43 | /// place. |
| 44 | DontCare, |
| 45 | }; |
| 46 | |
| 47 | /** |
| 48 | * expect_info is all about expected data and expected pass / fail information. |
| 49 | * |
| 50 | * The possible types of expected values returned from a PSA call are modelled |
| 51 | * in [expected_return_codes]. |
| 52 | * |
| 53 | * Expected data refers to psa-asset data values, generally after reading |
| 54 | * them. Currently, they are limited to character strings, but that will |
| 55 | * probably be generalized in the future. |
| 56 | */ |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 57 | class expect_info |
| 58 | { |
| 59 | public: |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 60 | |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 61 | // (literal expected data specified) |
| 62 | bool data_specified; |
| 63 | |
| 64 | string data; // what test template expects data from reading an asset to be |
| 65 | string data_var; // name of variable containing expected data |
| 66 | int n_exp_vars; // how many check-value variables have been created |
| 67 | bool data_var_specified; // check against a variable |
| 68 | |
| 69 | /* This indicates whether expected results have or have not already been |
| 70 | copied to this call. It's a "one-shot," so to speak, to copy only |
| 71 | once when results are known good. Since calls can be inserted into |
| 72 | earlier points in the call sequence (not always appended), the call |
| 73 | sequence has to be gone over for this process multiple times. */ |
| 74 | bool expected_results_saved; |
| 75 | |
| 76 | expect_info (void); // (default constructor) |
| 77 | ~expect_info (void); // (destructor) |
| 78 | |
| 79 | /// Is simulation of the return code needed? |
| 80 | bool simulation_needed(void); |
| 81 | |
| 82 | /// Sets the expected return code of the call to a pass. |
| 83 | void expect_pass (void); |
| 84 | |
| 85 | /// Sets the expected return code of the call to a failure. |
| 86 | void expect_failure (void); |
| 87 | |
| 88 | /// Sets the expected return code of the call to a specific error code. |
| 89 | void expect_error_code (string error); |
| 90 | |
| 91 | /// Sets the expected return code of the call to "don't know". |
| 92 | /// |
| 93 | /// This will cause TF_Fuzz to later simulate this value. |
| 94 | void clear_expected_code(void); |
| 95 | |
| 96 | /// Gets the expected return code. |
| 97 | expected_return_code_t get_expected_return_code(void); |
| 98 | |
| 99 | /// When a specified error code is given, get that error code as a string. |
| 100 | /// When any other return code is expected, std::logic_error is thrown. |
| 101 | string get_expected_return_code_string(void); |
| 102 | |
| 103 | void disable_result_code_checking (void); |
| 104 | void enable_result_code_checking (void); |
| 105 | bool result_code_checking_enabled(void); |
| 106 | |
| 107 | void copy_expect_to_call (psa_call *the_call); |
| 108 | |
| 109 | private: |
| 110 | /* true if template specifies expected data, and that expected data |
| 111 | agrees with that in the asset */ |
| 112 | bool data_matches_asset; |
| 113 | string return_code_result_string; |
| 114 | |
| 115 | // The type of return code expected. |
| 116 | expected_return_code_t expected_return_code; |
| 117 | |
| 118 | // if false, the return code does not matter, and checks for this should not |
| 119 | // take place. |
| 120 | bool result_code_checking_enabled_f; |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 121 | }; |
| 122 | |
| 123 | |
| 124 | /********************************************************************************** |
| 125 | Class set_data_info addresses PSA-asset data values as affected, directly or |
| 126 | indirctly/implicitly, by the template-line content. "Directly," that is, by |
| 127 | virtue of the template line stating verbatim what to set data to, or indirectly |
| 128 | by virtue of telling TF-Fuzz to create random data for it. |
| 129 | **********************************************************************************/ |
| 130 | |
| 131 | class set_data_info |
| 132 | { |
| 133 | public: |
| 134 | // Data members: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 135 | bool string_specified; |
| 136 | // true if a string of data is specified in template file |
| 137 | bool random_data; // true to generate random data for the asset |
| 138 | bool file_specified; // true if a file of expected data was specified |
| 139 | bool literal_data_not_file; |
| 140 | // true to use data strings rather than files as data source |
| 141 | int n_set_vars; // how many implicit set variables have been created |
| 142 | string file_path; // path to file, if specified |
| 143 | string flags_string; |
| 144 | // creation flags, nominally for SST but have to be in a vector of base-class |
| 145 | uint32_t data_offset; // offset into asset data |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 146 | // Methods: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 147 | set_data_info (void); // (default constructor) |
| 148 | ~set_data_info (void); // (destructor) |
| 149 | void set (string set_val); |
| 150 | void set_calculated (string set_val); |
| 151 | void randomize (void); |
| 152 | string get (void); |
| 153 | bool set_file (string file_name); |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 154 | |
| 155 | protected: |
| 156 | // Data members: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 157 | string data; // String describing asset data. |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 158 | // Methods: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 159 | string rand_creation_flags (void); |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 160 | }; |
| 161 | |
| 162 | |
| 163 | /********************************************************************************** |
| 164 | Class asset_name_id_info groups together and acts upon all information related to the |
| 165 | human names (as reflected in the code variable names, etc.) for PSA assets. |
| 166 | **********************************************************************************/ |
| 167 | |
| 168 | class asset_name_id_info |
| 169 | { |
| 170 | public: |
| 171 | // Data members (not much value in "hiding" these behind getters) |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 172 | psa_asset *the_asset; |
| 173 | psa_asset_type asset_type; // SST vs. key vs. policy (etc.) |
| 174 | bool id_n_not_name; // true to create a PSA asset by ID |
| 175 | bool name_specified; // true iff template supplied human name |
| 176 | bool id_n_specified; // true iff template supplied ID # |
| 177 | vector<string> asset_name_vector; |
| 178 | vector<int> asset_id_n_vector; |
| 179 | long asset_ser_no; // unique ID for psa asset needed to find data string |
| 180 | /* Note: The original theory is that we can't save away iterators to |
Mate Toth-Pal | ffba10e | 2021-09-22 21:38:03 +0200 | [diff] [blame] | 181 | assets, because STL vectors could get relocated. However, |
| 182 | we've switched over to lists, which don't get moved around, so |
| 183 | we should be safe now. */ |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 184 | asset_search how_asset_found; |
| 185 | uint64_t id_n; // asset ID# (e.g., SST UID). |
| 186 | /* Note: This is just a holder to pass ID from template-line to call. The |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 187 | IDs for a given template line are in asset_info.asset_id_n_vector. */ |
| 188 | // Methods: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 189 | asset_name_id_info (void); // (default constructor) |
| 190 | ~asset_name_id_info (void); // (destructor) |
| 191 | void set_name (string set_val); |
| 192 | void set_calc_name (string set_val); |
| 193 | void set_just_name (string set_val); |
| 194 | string get_name (void); |
| 195 | void set_id_n (string set_val); |
| 196 | void set_id_n (uint64_t set_val); |
| 197 | string make_id_n_based_name (uint64_t id_n); |
| 198 | // create UID-based asset name |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 199 | |
| 200 | protected: |
| 201 | // Data members: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 202 | string asset_name; // parsed from template, assigned to psa_asset object |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 203 | }; |
| 204 | |
| 205 | |
| 206 | /********************************************************************************** |
| 207 | Class key_policy_info collects together the aspects of a Crypto key attributes |
| 208 | ("policies"). These include aspects that can affect TF-Fuzz's test-generation. |
| 209 | **********************************************************************************/ |
| 210 | |
| 211 | class key_policy_info |
| 212 | { |
| 213 | public: |
| 214 | // Data members: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 215 | // Digested info: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 216 | /* if true, then we must get policy info from a stated key; the asset |
Nik Dewally | abac0e5 | 2024-08-02 13:42:27 +0100 | [diff] [blame^] | 217 | here is a key that uses the policy, and not the policy itself. */ |
| 218 | bool get_policy_from_key; |
| 219 | |
| 220 | // If set, the policy asset specified should be used to fill in the policy |
| 221 | // at simulation time. This overwrites the other values in the object. |
| 222 | // |
| 223 | // If blank, the values in the object are used as-is. |
| 224 | // |
| 225 | // See `psa_call::copy_policy_to_call` |
| 226 | string get_policy_from_policy; |
| 227 | |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 228 | /* if true, then the key was defined with policy specifications, but not |
Nik Dewally | abac0e5 | 2024-08-02 13:42:27 +0100 | [diff] [blame^] | 229 | a named policy, meaning that we have to create an implicit policy. */ |
| 230 | bool implicit_policy; |
| 231 | bool copy_key = false; // true to indicate copying one key to another |
| 232 | bool exportable=false; // key data can be exported (viewed - fail exports if not). |
| 233 | bool copyable=false; // can be copied (fail key-copies if not). |
| 234 | bool can_encrypt=false; // OK for encryption (fail other uses). |
| 235 | bool can_decrypt=false; // OK for decryption (fail other uses). |
| 236 | bool can_sign=false; // OK for signing (fail other operations). |
| 237 | bool can_verify=false; // OK for verifying a message signature (fail other uses). |
| 238 | bool derivable=false; // OK for derive other keys (fail other uses). |
| 239 | bool persistent=false; // must be deleted at the end of test. |
| 240 | |
| 241 | |
| 242 | // no_<flag> denotes that <flag> must not be set in the key. |
| 243 | // |
| 244 | // For the above flags, truth means "must be set" and false means "don't care". |
| 245 | // Setting no_<flag> means "must not be set". no_<flag> takes presedence over <flag>. |
| 246 | |
| 247 | bool no_exportable=false; // true to indicate that exportable must not be set during randomisation |
| 248 | bool no_copyable=false; // true to indicate that copyable must not be set during randomisation |
| 249 | bool no_can_encrypt=false; // true to indicate that can_encrypt must not be set during randomisation |
| 250 | bool no_can_decrypt=false; // true to indicate that can_decrypt must not be set during randomisation |
| 251 | bool no_can_sign=false; // true to indicate that can_sign must not be set during randomisation |
| 252 | bool no_can_verify=false; // true to indicate that can_verify must not be set during randomisation |
| 253 | bool no_derivable=false; // true to indicate that derivable must not be set during randomisation |
| 254 | bool no_persistent=false; // true to indicate that persistent must not be set during randomisation |
| 255 | |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 256 | string usage_string; |
| 257 | /* This string is set to a PSA_KEY_USAGE_* value in the template |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 258 | immediately prior to making define_call<add_policy_usage_call>. |
| 259 | The copy_template_to_call() therein sets the corresponding string |
| 260 | in the call, and that is copied into the code in the fill_in_command() |
| 261 | invocation. */ |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 262 | string print_usage_true_string; |
| 263 | /* For printing out policy usage, this states how to describe the usage |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 264 | if it can be used this way. This is managed similarly with, and used |
| 265 | in conjunction with usage_string above. NOTE: THIS ALSO SERVES AS AN |
| 266 | INDICATOR WHETHER OR NOT TO PRINT ON A GET-USAGE CALL. "" means not |
| 267 | to print. */ |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 268 | string print_usage_false_string; |
| 269 | /* Also for printing out policy usage, this is how to describe usage if |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 270 | it cannot be used this way. */ |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 271 | string key_type; // AES, DES, RSA pair, DS public, etc. |
| 272 | string key_algorithm; |
| 273 | int n_bits; |
| 274 | // for get_key_info call (possibly others) exected key size in bits |
| 275 | string handle_str; // the text name of the key's "handle" |
| 276 | string key_data; // the key data as best we can know it. |
| 277 | string asset_2_name; |
| 278 | // if there's a 2nd asset, such as policy on key call, this is its name |
| 279 | string asset_3_name; // if there's a 3rd asset, then this is its name |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 280 | |
| 281 | // Methods: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 282 | key_policy_info (void); // (default constructor) |
| 283 | ~key_policy_info (void); // (destructor) |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 284 | |
| 285 | |
Nik Dewally | abac0e5 | 2024-08-02 13:42:27 +0100 | [diff] [blame^] | 286 | /** Creates a random, but not necessarily valid, policy */ |
| 287 | static key_policy_info create_random(); |
| 288 | |
| 289 | |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 290 | protected: |
Nik Dewally | abac0e5 | 2024-08-02 13:42:27 +0100 | [diff] [blame^] | 291 | |
| 292 | /* The following settings are not necessarily being randomized in mutually- |
| 293 | consistent ways, for two reasons: First, the template should set all that |
| 294 | matter, and second, testing TF response to nonsensical settings is also |
| 295 | valuable. */ |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 296 | // Data members: |
Nik Dewally | 6663dde | 2024-08-09 16:12:27 +0100 | [diff] [blame] | 297 | bool data_matches_asset; |
| 298 | /* true if template specifies expected data, and that expected data |
Karl Zhang | 3de5ab1 | 2021-05-31 11:45:48 +0800 | [diff] [blame] | 299 | agrees with that in the asset */ |
| 300 | }; |
| 301 | |
| 302 | |
| 303 | |
| 304 | #endif // DATA_BLOCKS_HPP |