Home | History | Annotate | Line # | Download | only in tspi
      1 
      2 /*
      3  * Licensed Materials - Property of IBM
      4  *
      5  * trousers - An open source TCG Software Stack
      6  *
      7  * (C) Copyright International Business Machines Corp. 2004-2007
      8  *
      9  */
     10 
     11 
     12 #include <stdlib.h>
     13 #include <stdio.h>
     14 #include <string.h>
     15 
     16 #include "trousers/tss.h"
     17 #include "trousers/trousers.h"
     18 #include "trousers_types.h"
     19 #include "spi_utils.h"
     20 #include "capabilities.h"
     21 #include "tsplog.h"
     22 #include "obj.h"
     23 
     24 
     25 TSS_RESULT
     26 Tspi_Hash_TickStampBlob(TSS_HHASH       hHash,			/* in */
     27 			TSS_HKEY        hIdentKey,		/* in */
     28 			TSS_VALIDATION* pValidationData)	/* in */
     29 {
     30 	TSS_RESULT result;
     31 	TSS_HCONTEXT tspContext;
     32 	TCS_KEY_HANDLE tcsKey;
     33 	TSS_HPOLICY hPolicy;
     34 	TPM_DIGEST digest;
     35 	TSS_BOOL usesAuth;
     36 	TPM_AUTH auth, *pAuth;
     37 	UINT32 hashLen, sigLen, tcLen, signInfoLen;
     38 	BYTE *hash, *sig, *tc, *signInfo = NULL;
     39 	UINT64 offset;
     40 	Trspi_HashCtx hashCtx;
     41 
     42 	if (pValidationData == NULL)
     43 		return TSPERR(TSS_E_BAD_PARAMETER);
     44 
     45 	if ((result = obj_hash_get_tsp_context(hHash, &tspContext)))
     46 		return result;
     47 
     48 	if (pValidationData->ulExternalDataLength != sizeof(TPM_NONCE))
     49 		return TSPERR(TSS_E_BAD_PARAMETER);
     50 
     51 	if ((result = obj_hash_get_value(hHash, &hashLen, &hash)))
     52 		return result;
     53 
     54 	if (hashLen != sizeof(TPM_DIGEST)) {
     55 		free_tspi(tspContext, hash);
     56 		return TSPERR(TSS_E_HASH_INVALID_LENGTH);
     57 	}
     58 
     59 	if ((result = obj_rsakey_get_policy(hIdentKey, TSS_POLICY_USAGE, &hPolicy, &usesAuth)))
     60 		return result;
     61 
     62 	if ((result = obj_rsakey_get_tcs_handle(hIdentKey, &tcsKey)))
     63 		return result;
     64 
     65 	if (usesAuth) {
     66 		result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1);
     67 		result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_TickStampBlob);
     68 		result |= Trspi_HashUpdate(&hashCtx, sizeof(TPM_NONCE),
     69 					   pValidationData->rgbExternalData);
     70 		result |= Trspi_HashUpdate(&hashCtx, sizeof(TPM_DIGEST), hash);
     71 		if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) {
     72 			free_tspi(tspContext, hash);
     73 			return result;
     74 		}
     75 
     76 		if ((result = secret_PerformAuth_OIAP(hIdentKey, TPM_ORD_TickStampBlob, hPolicy,
     77 						      FALSE, &digest, &auth))) {
     78 			free_tspi(tspContext, hash);
     79 			return result;
     80 		}
     81 		pAuth = &auth;
     82 	} else
     83 		pAuth = NULL;
     84 
     85 	if ((result = TCS_API(tspContext)->TickStampBlob(tspContext, tcsKey,
     86 						(TPM_NONCE *)pValidationData->rgbExternalData,
     87 						(TPM_DIGEST *)hash, pAuth, &sigLen, &sig, &tcLen,
     88 						&tc))) {
     89 		free_tspi(tspContext, hash);
     90 		return result;
     91 	}
     92 
     93 	if (usesAuth) {
     94 		result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1);
     95 		result |= Trspi_Hash_UINT32(&hashCtx, result);
     96 		result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_TickStampBlob);
     97 		result |= Trspi_HashUpdate(&hashCtx, tcLen, tc);
     98 		result |= Trspi_Hash_UINT32(&hashCtx, sigLen);
     99 		result |= Trspi_HashUpdate(&hashCtx, sigLen, sig);
    100 		if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) {
    101 			free_tspi(tspContext, hash);
    102 			free(sig);
    103 			free(tc);
    104 			return result;
    105 		}
    106 
    107 		if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, pAuth))) {
    108 			free_tspi(tspContext, hash);
    109 			free(sig);
    110 			free(tc);
    111 			return result;
    112 		}
    113 	}
    114 
    115 	/*                 tag       fixed      replay          length(Data)                 Data        */
    116 	signInfoLen = sizeof(UINT16) + 4 + sizeof(TPM_NONCE) + sizeof(UINT32) + sizeof(TPM_DIGEST) + tcLen;
    117 	if ((signInfo = calloc_tspi(tspContext, signInfoLen)) == NULL) {
    118 		free_tspi(tspContext, hash);
    119 		free(sig);
    120 		free(tc);
    121 		return TSPERR(TSS_E_INTERNAL_ERROR);
    122 	}
    123 
    124 	offset = 0;
    125 	Trspi_LoadBlob_UINT16(&offset, TPM_TAG_SIGNINFO, signInfo);
    126 	Trspi_LoadBlob_BYTE(&offset, 'T', signInfo);
    127 	Trspi_LoadBlob_BYTE(&offset, 'S', signInfo);
    128 	Trspi_LoadBlob_BYTE(&offset, 'T', signInfo);
    129 	Trspi_LoadBlob_BYTE(&offset, 'P', signInfo);
    130 	Trspi_LoadBlob(&offset, sizeof(TPM_NONCE), signInfo, pValidationData->rgbExternalData);
    131 	Trspi_LoadBlob_UINT32(&offset, sizeof(TPM_DIGEST) + tcLen, signInfo);
    132 	Trspi_LoadBlob(&offset, sizeof(TPM_DIGEST), signInfo, hash);
    133 	Trspi_LoadBlob(&offset, (size_t)tcLen, signInfo, tc);
    134 
    135 	free(tc);
    136 	free_tspi(tspContext, hash);
    137 
    138 	pValidationData->rgbData = signInfo;
    139 	pValidationData->ulDataLength = signInfoLen;
    140 
    141 	/* tag sig so that it can be free'd by the app through Tspi_Context_FreeMemory */
    142 	if ((result = __tspi_add_mem_entry(tspContext, sig))) {
    143 		free_tspi(tspContext, signInfo);
    144 		free(sig);
    145 		return result;
    146 	}
    147 
    148 	pValidationData->rgbValidationData = sig;
    149 	pValidationData->ulValidationDataLength = sigLen;
    150 
    151 	return TSS_SUCCESS;
    152 }
    153 
    154 TSS_RESULT
    155 Tspi_TPM_ReadCurrentTicks(TSS_HTPM           hTPM,	/* in */
    156 			  TPM_CURRENT_TICKS* tickCount)	/* out */
    157 {
    158 	TSS_RESULT result;
    159 	TSS_HCONTEXT tspContext;
    160 	UINT32 tcLen;
    161 	BYTE *tc;
    162 	UINT64 offset;
    163 
    164 	if (tickCount == NULL)
    165 		return TSPERR(TSS_E_BAD_PARAMETER);
    166 
    167 	if ((result = obj_tpm_get_tsp_context(hTPM, &tspContext)))
    168 		return result;
    169 
    170 	if ((result = TCS_API(tspContext)->ReadCurrentTicks(tspContext, &tcLen, &tc)))
    171 		return result;
    172 
    173 	offset = 0;
    174 	Trspi_UnloadBlob_CURRENT_TICKS(&offset, tc, tickCount);
    175 	free(tc);
    176 
    177 	return result;
    178 }
    179