124 lines
3.8 KiB
C
124 lines
3.8 KiB
C
/*
|
|
* Copyright 2020 Google LLC. All Rights Reserved. This file and proprietary
|
|
* source code may only be used and distributed under the Widevine Master
|
|
* License Agreement.
|
|
*/
|
|
|
|
/*
|
|
* Support functions for the OEMCrypto API functions, related to
|
|
* message handling
|
|
*/
|
|
|
|
#include "OEMCryptoCENC.h"
|
|
#include "api_support.h"
|
|
#include "bump_allocator.h"
|
|
#include "message.h"
|
|
#include "shared_memory_allocator.h"
|
|
#include "shared_memory_interface.h"
|
|
#include "special_cases.h"
|
|
#include "transport_interface.h"
|
|
|
|
/*
|
|
* If true, the system has been invalidated due to a communications
|
|
* breakdown with the TEE. This is a persistent condition and will
|
|
* cause OEMCrypto_ERROR_SYSTEM_INVALIDATED to be returned from any
|
|
* function that returns an OEMCryptoResult until the transport
|
|
* interface is reinitialized.
|
|
*/
|
|
static bool system_invalidated;
|
|
|
|
/*
|
|
* This is the result code to be returned from any function that
|
|
* returns OEMCryptoResult code.
|
|
*/
|
|
OEMCryptoResult api_result;
|
|
|
|
/*
|
|
* odkitee OEMCrypto API is single threaded
|
|
*/
|
|
pthread_mutex_t api_lock;
|
|
|
|
/*
|
|
* Called at the beginning of every API function. Checks configuration
|
|
* state and if it is okay allocates a request message. Sets
|
|
* api_result based on the status of the operations, which will be
|
|
* returned from any API function that returns an OEMCryptoResult
|
|
* code. On exit, if api_result is not OEMCrypto_SUCCESS or NULL is
|
|
* returned, then any allocated messages will have been deallocated
|
|
* prior to returning.
|
|
*/
|
|
Message *API_InitializeRequest(void) {
|
|
api_result = OEMCrypto_SUCCESS;
|
|
|
|
SharedMemory_Reset();
|
|
BumpAllocator_Reset();
|
|
Message* request = ODK_Transport_AllocateMessage();
|
|
if (request == NULL) {
|
|
api_result = OEMCrypto_ERROR_INSUFFICIENT_RESOURCES;
|
|
} else if (GetStatus(request) != MESSAGE_STATUS_OK) {
|
|
/* The transport allocator must return initialized messages */
|
|
api_result = OEMCrypto_ERROR_SYSTEM_INVALIDATED;
|
|
}
|
|
if (api_result != OEMCrypto_SUCCESS) {
|
|
if (request != NULL) {
|
|
ODK_Transport_DeallocateMessage(request);
|
|
request = NULL;
|
|
}
|
|
}
|
|
return request;
|
|
}
|
|
|
|
/*
|
|
* Called to send the request message to the TEE and receive the
|
|
* response. Sets api_result based on the status of the
|
|
* operations. Returns either a valid response message or NULL. If
|
|
* NULL is returned or api_result != OEMCrypto_SUCCESS then any
|
|
* allocated messages will have been deallocated prior to returning.
|
|
*/
|
|
Message *API_Transact(Message* request) {
|
|
if (api_result != OEMCrypto_SUCCESS || request == NULL) {
|
|
return NULL;
|
|
}
|
|
ODK_Transport_Status transport_status = ODK_Transport_SendMessage(request);
|
|
Message* response = NULL;
|
|
if (transport_status == ODK_TRANSPORT_STATUS_IO_ERROR) {
|
|
api_result = OEMCrypto_ERROR_SYSTEM_INVALIDATED;
|
|
} else {
|
|
transport_status = ODK_Transport_ReceiveMessage(&response);
|
|
if (transport_status == ODK_TRANSPORT_STATUS_IO_ERROR || response == NULL) {
|
|
api_result = OEMCrypto_ERROR_SYSTEM_INVALIDATED;
|
|
} else if (GetStatus(response) != MESSAGE_STATUS_OK) {
|
|
api_result = OEMCrypto_ERROR_UNKNOWN_FAILURE;
|
|
}
|
|
}
|
|
if (api_result != OEMCrypto_SUCCESS) {
|
|
if (response) {
|
|
ODK_Transport_DeallocateMessage(response);
|
|
response = NULL;
|
|
}
|
|
}
|
|
return response;
|
|
}
|
|
|
|
/*
|
|
* Called at the end of every API function. Sets system_invalidated if
|
|
* the local api_result indicates a failure in the current
|
|
* function. Once system_invalidated is set, it will persist until
|
|
* reset by the next OEMCrypto_Inititalize/OEMCrypto_Terminate.
|
|
*/
|
|
OEMCryptoResult API_CheckResult(OEMCryptoResult unpacked_result) {
|
|
if (api_result == OEMCrypto_ERROR_SYSTEM_INVALIDATED) {
|
|
system_invalidated = true;
|
|
} else if (api_result == OEMCrypto_SUCCESS) {
|
|
api_result = unpacked_result;
|
|
}
|
|
return api_result;
|
|
}
|
|
|
|
/*
|
|
* Called by OEMCrypto_Terminate
|
|
*/
|
|
void API_Terminate(void) {
|
|
system_invalidated = false;
|
|
}
|