• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*############################################################################
2   # Copyright 2017 Intel Corporation
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 /// Member private exponentiation implementation
17 /*! \file */
18 
19 #include "epid/member/src/privateexp.h"
20 
21 #include "epid/common/math/ecgroup.h"
22 #include "epid/common/src/epid2params.h"
23 #include "epid/common/src/hashsize.h"
24 #include "epid/common/src/memory.h"
25 #include "epid/common/types.h"
26 #include "epid/member/src/context.h"
27 #include "epid/member/tpm2/commit.h"
28 #include "epid/member/tpm2/sign.h"
29 
30 /// Handle Intel(R) EPID Error with Break
31 #define BREAK_ON_EPID_ERROR(ret) \
32   if (kEpidNoErr != (ret)) {     \
33     break;                       \
34   }
35 
EpidPrivateExp(MemberCtx * ctx,EcPoint const * a,EcPoint * r)36 EpidStatus EpidPrivateExp(MemberCtx* ctx, EcPoint const* a, EcPoint* r) {
37   EpidStatus sts = kEpidErr;
38 
39   BigNumStr tmp_ff_str = {0};
40   uint16_t counter = 0;
41 
42   EcPoint* k_pt = NULL;
43   EcPoint* l_pt = NULL;
44   EcPoint* e_pt = NULL;
45   EcPoint* t1 = NULL;
46   EcPoint* h = NULL;
47 
48   FfElement* k = NULL;
49   FfElement* s = NULL;
50 
51   size_t digest_len = 0;
52   uint8_t* digest = NULL;
53 
54   if (!ctx || !ctx->epid2_params || !a || !r) {
55     return kEpidBadArgErr;
56   }
57 
58   digest_len = EpidGetHashSize(ctx->hash_alg);
59   digest = SAFE_ALLOC(digest_len);
60   if (!digest) {
61     return kEpidMemAllocErr;
62   }
63 
64   memset(digest, 0, digest_len);
65   digest[digest_len - 1] = 1;
66 
67   do {
68     FiniteField* Fp = ctx->epid2_params->Fp;
69     EcGroup* G1 = ctx->epid2_params->G1;
70 
71     if (!ctx->is_provisioned && !ctx->is_initially_provisioned) {
72       sts = EpidMemberInitialProvision(ctx);
73       BREAK_ON_EPID_ERROR(sts);
74     }
75 
76     // (K_PT, L_PT, E_PT, counter) = TPM2_Commit(P1=B')
77     sts = NewEcPoint(G1, &k_pt);
78     BREAK_ON_EPID_ERROR(sts);
79     sts = NewEcPoint(G1, &l_pt);
80     BREAK_ON_EPID_ERROR(sts);
81     sts = NewEcPoint(G1, &e_pt);
82     BREAK_ON_EPID_ERROR(sts);
83     sts = NewEcPoint(G1, &t1);
84     BREAK_ON_EPID_ERROR(sts);
85     sts = NewEcPoint(G1, &h);
86     BREAK_ON_EPID_ERROR(sts);
87 
88     sts =
89         Tpm2Commit(ctx->tpm2_ctx, a, NULL, 0, NULL, k_pt, l_pt, e_pt, &counter);
90     BREAK_ON_EPID_ERROR(sts);
91 
92     // (k, s) = TPM2_Sign(c=1, counter)
93     sts = NewFfElement(Fp, &k);
94     BREAK_ON_EPID_ERROR(sts);
95     sts = NewFfElement(Fp, &s);
96     BREAK_ON_EPID_ERROR(sts);
97 
98     sts = Tpm2Sign(ctx->tpm2_ctx, digest, digest_len, counter, k, s);
99     BREAK_ON_EPID_ERROR(sts);
100 
101     // k = Fq.inv(k)
102     sts = FfInv(Fp, k, k);
103     BREAK_ON_EPID_ERROR(sts);
104 
105     // t1 = G1.sscmExp(B', s)
106     sts = WriteFfElement(Fp, s, &tmp_ff_str, sizeof(tmp_ff_str));
107     BREAK_ON_EPID_ERROR(sts);
108     sts = EcSscmExp(G1, a, &tmp_ff_str, t1);
109     BREAK_ON_EPID_ERROR(sts);
110 
111     // E_PT = G1.inv(E_PT)
112     sts = EcInverse(G1, e_pt, e_pt);
113     BREAK_ON_EPID_ERROR(sts);
114 
115     // h = G1.mul(t1, E_PT)
116     sts = EcMul(G1, t1, e_pt, h);
117     BREAK_ON_EPID_ERROR(sts);
118 
119     // h = G1.sscmExp(h, k)
120     sts = WriteFfElement(Fp, k, &tmp_ff_str, sizeof(tmp_ff_str));
121     BREAK_ON_EPID_ERROR(sts);
122     sts = EcSscmExp(G1, h, &tmp_ff_str, r);
123     BREAK_ON_EPID_ERROR(sts);
124   } while (0);
125 
126   if (sts != kEpidNoErr) {
127     (void)Tpm2ReleaseCounter(ctx->tpm2_ctx, counter);
128   }
129   DeleteFfElement(&s);
130   DeleteFfElement(&k);
131 
132   DeleteEcPoint(&e_pt);
133   DeleteEcPoint(&l_pt);
134   DeleteEcPoint(&k_pt);
135   DeleteEcPoint(&t1);
136   DeleteEcPoint(&h);
137 
138   EpidZeroMemory(&tmp_ff_str, sizeof(tmp_ff_str));
139   SAFE_FREE(digest);
140   return sts;
141 }
142