• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* SPDX-License-Identifier: BSD-2-Clause */
2 /*******************************************************************************
3  * Copyright 2017-2018, Fraunhofer SIT sponsored by Infineon Technologies AG
4  * All rights reserved.
5  *******************************************************************************/
6 
7 #ifdef HAVE_CONFIG_H
8 #include <config.h>
9 #endif
10 
11 #include <stdlib.h>
12 #include <stdio.h>
13 #include <inttypes.h>
14 #include <string.h>
15 #include <errno.h>
16 #include <fcntl.h>
17 #include <unistd.h>
18 
19 
20 #include "tss2_fapi.h"
21 #include "tss2_esys.h"
22 #include "tss2_tcti.h"
23 
24 #include "test-fapi.h"
25 
26 #define LOGMODULE test
27 #include "util/log.h"
28 #include "util/aux_util.h"
29 
30 #define NV_SIZE 34
31 #define PASSWORD ""
32 #define SIGN_TEMPLATE  "sign"
33 
34 static TSS2_RC
check_tpm_cmd(FAPI_CONTEXT * context,TPM2_CC command_code)35 check_tpm_cmd(FAPI_CONTEXT *context, TPM2_CC command_code)
36 {
37     TSS2_RC r;
38     TSS2_TCTI_CONTEXT *tcti;
39     ESYS_CONTEXT *esys;
40     TPMS_CAPABILITY_DATA *cap_data;
41 
42     r = Fapi_GetTcti(context, &tcti);
43     goto_if_error(r, "Error Fapi_GetTcti", error);
44 
45     r = Esys_Initialize(&esys, tcti, NULL);
46     goto_if_error(r, "Error Fapi_GetTcti", error);
47 
48     r = Esys_GetCapability(esys,
49                            ESYS_TR_NONE, ESYS_TR_NONE, ESYS_TR_NONE,
50                            TPM2_CAP_COMMANDS, command_code, 1, NULL, &cap_data);
51     Esys_Finalize(&esys);
52     return_if_error(r, "Error: GetCapabilities");
53 
54     if ((cap_data->data.command.commandAttributes[0] & TPMA_CC_COMMANDINDEX_MASK) ==
55             command_code) {
56         free(cap_data);
57         return TSS2_RC_SUCCESS;
58     } else {
59         free(cap_data);
60         return TSS2_FAPI_RC_NOT_IMPLEMENTED;
61     }
62 
63 error:
64     return r;
65 }
66 
67 static char *
read_policy(FAPI_CONTEXT * context,char * policy_name)68 read_policy(FAPI_CONTEXT *context, char *policy_name)
69 {
70     FILE *stream = NULL;
71     long policy_size;
72     char *json_policy = NULL;
73     char policy_file[1024];
74 
75     if (snprintf(&policy_file[0], 1023, TOP_SOURCEDIR "/test/data/fapi/%s.json", policy_name) < 0)
76         return NULL;
77 
78     stream = fopen(policy_file, "r");
79     if (!stream) {
80         LOG_ERROR("File %s does not exist", policy_file);
81         return NULL;
82     }
83     fseek(stream, 0L, SEEK_END);
84     policy_size = ftell(stream);
85     fclose(stream);
86     json_policy = malloc(policy_size + 1);
87     stream = fopen(policy_file, "r");
88     ssize_t ret = read(fileno(stream), json_policy, policy_size);
89     if (ret != policy_size) {
90         LOG_ERROR("IO error %s.", policy_file);
91         return NULL;
92     }
93     json_policy[policy_size] = '\0';
94     return json_policy;
95 }
96 
97 /** Test the FAPI key signing with PolicyAuthorizeNV.
98  *
99  * Tested FAPI commands:
100  *  - Fapi_GetTcti()
101  *  - Fapi_Provision()
102  *  - Fapi_CreateNv()
103  *  - Fapi_Import()
104  *  - Fapi_WriteAuthorizeNv()
105  *  - Fapi_CreateKey()
106  *  - Fapi_Sign()
107  *  - Fapi_Delete()
108  *
109  * Tested Policies:
110  *  - PolicyAuthorizeNv
111  *
112  * @param[in,out] context The FAPI_CONTEXT.
113  * @retval EXIT_FAILURE
114  * @retval EXIT_SUCCESS
115  */
116 int
test_fapi_key_create_policy_authorize_nv(FAPI_CONTEXT * context)117 test_fapi_key_create_policy_authorize_nv(FAPI_CONTEXT *context)
118 {
119     TSS2_RC r;
120     char *nvPathPolicy = "/nv/Owner/myNV";
121     char *policy_authorize_nv = "/policy/pol_authorize_nv";
122     char *policy_pcr2 = "/policy/pol_pcr16_0";
123     char *json_policy = NULL;
124 
125     uint8_t *signature = NULL;
126     char    *publicKey = NULL;
127 
128     if (check_tpm_cmd(context, TPM2_CC_PolicyAuthorizeNV) != TPM2_RC_SUCCESS) {
129         LOG_WARNING("Command PolicyAuthorizeNV not available.");
130         return EXIT_SKIP;
131     }
132 
133     r = Fapi_Provision(context, NULL, NULL, NULL);
134     goto_if_error(r, "Error Fapi_Provision", error);
135 
136     /* Create NV object for storing the policy */
137     r = Fapi_CreateNv(context, nvPathPolicy, "noda", 34, "", "");
138     goto_if_error(r, "Error Fapi_CreateNv", error);
139 
140     r = pcr_reset(context, 16);
141     goto_if_error(r, "Error pcr_reset", error);
142 
143     json_policy = read_policy(context, policy_authorize_nv);
144     if (!json_policy)
145         goto error;
146 
147     r = Fapi_Import(context, policy_authorize_nv, json_policy);
148     goto_if_error(r, "Error Fapi_Import", error);
149     SAFE_FREE(json_policy);
150 
151     json_policy = read_policy(context, policy_pcr2);
152     if (!json_policy)
153         goto error;
154 
155     r = Fapi_Import(context, policy_pcr2, json_policy);
156     goto_if_error(r, "Error Fapi_Import", error);
157 
158     r = Fapi_WriteAuthorizeNv(context,nvPathPolicy, policy_pcr2);
159     goto_if_error(r, "Error Fapi_WriteAuthorizeNv", error);
160 
161     r = Fapi_CreateKey(context, "/HS/SRK/myPolicySignKey", "sign",
162                        "", PASSWORD);
163     goto_if_error(r, "Error Fapi_CreateKey", error);
164 
165     r = Fapi_CreateKey(context, "/HS/SRK/mySignKey", SIGN_TEMPLATE,
166                        policy_authorize_nv, PASSWORD);
167     goto_if_error(r, "Error Fapi_CreateKey", error);
168 
169     size_t signatureSize = 0;
170 
171     TPM2B_DIGEST digest = {
172         .size = 20,
173         .buffer = {
174             0x67, 0x68, 0x03, 0x3e, 0x21, 0x64, 0x68, 0x24, 0x7b, 0xd0,
175             0x31, 0xa0, 0xa2, 0xd9, 0x87, 0x6d, 0x79, 0x81, 0x8f, 0x8f,
176             0x31, 0xa0, 0xa2, 0xd9, 0x87, 0x6d, 0x79, 0x81, 0x8f, 0x8f,
177             0x41, 0x42
178         }
179     };
180 
181     r = Fapi_Sign(context, "/HS/SRK/mySignKey", NULL,
182                   &digest.buffer[0], digest.size, &signature, &signatureSize,
183                   &publicKey, NULL);
184     goto_if_error(r, "Error Fapi_Sign", error);
185 
186     r = Fapi_Delete(context, nvPathPolicy);
187     goto_if_error(r, "Error Fapi_NV_Undefine", error);
188 
189     r = Fapi_Delete(context, "/");
190     goto_if_error(r, "Error Fapi_Delete", error);
191 
192     SAFE_FREE(json_policy);
193     SAFE_FREE(signature);
194     SAFE_FREE(publicKey);
195     return EXIT_SUCCESS;
196 
197 error:
198     SAFE_FREE(json_policy);
199     SAFE_FREE(signature);
200     SAFE_FREE(publicKey);
201     return EXIT_FAILURE;
202 }
203 
204 int
test_invoke_fapi(FAPI_CONTEXT * context)205 test_invoke_fapi(FAPI_CONTEXT *context)
206 {
207     return test_fapi_key_create_policy_authorize_nv(context);
208 }
209