blob: e1f91488b32a355075beed20367f8dfba7744153 [file] [log] [blame]
Will Arthur54e04e42015-07-15 11:29:25 -04001//**********************************************************************;
Philip Tricca66f9b172016-09-27 16:07:34 -07002// Copyright (c) 2015, 2016 Intel Corporation
Will Arthur54e04e42015-07-15 11:29:25 -04003// All rights reserved.
Philip Tricca1ea84a52015-11-19 18:07:06 -08004//
5// Redistribution and use in source and binary forms, with or without
Will Arthur54e04e42015-07-15 11:29:25 -04006// modification, are permitted provided that the following conditions are met:
Philip Tricca1ea84a52015-11-19 18:07:06 -08007//
8// 1. Redistributions of source code must retain the above copyright notice,
Will Arthur54e04e42015-07-15 11:29:25 -04009// this list of conditions and the following disclaimer.
Philip Tricca1ea84a52015-11-19 18:07:06 -080010//
11// 2. Redistributions in binary form must reproduce the above copyright notice,
12// this list of conditions and the following disclaimer in the documentation
Will Arthur54e04e42015-07-15 11:29:25 -040013// and/or other materials provided with the distribution.
Philip Tricca1ea84a52015-11-19 18:07:06 -080014//
15// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
19// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
Will Arthur54e04e42015-07-15 11:29:25 -040025// THE POSSIBILITY OF SUCH DAMAGE.
26//**********************************************************************;
27
Will Arthur54e04e42015-07-15 11:29:25 -040028#include <stdio.h>
29#include <stdlib.h> // Needed for _wtoi
30
Philip Triccadd3b03c2017-03-05 11:38:08 -080031#include "sapi/tpm20.h"
32#include "tcti/tcti_socket.h"
Philip Triccac3dedc22016-01-15 13:47:22 -080033#include "sysapi_util.h"
Philip Triccadd3b03c2017-03-05 11:38:08 -080034#include "common/debug.h"
wcarthureedecd62015-11-20 16:59:45 -050035#include "commonchecks.h"
Philip Triccabcc73032016-03-30 19:50:54 -070036#include "logging.h"
Will Arthur54e04e42015-07-15 11:29:25 -040037
38#ifdef __cplusplus
39extern "C" {
40#endif
41
Philip Triccabcc73032016-03-30 19:50:54 -070042static TSS2_RC tctiRecvBytes( TSS2_TCTI_CONTEXT *tctiContext, SOCKET sock, unsigned char *data, int len )
Philip Triccaa06f2372016-03-30 17:13:11 -070043{
44 TSS2_RC result = 0;
45 result = recvBytes( sock, data, len);
wcarthur1e2e04182016-04-11 07:37:55 -070046 if ( (INT32)result == SOCKET_ERROR) {
Philip Triccabcc73032016-03-30 19:50:54 -070047 TCTI_LOG( tctiContext, NO_PREFIX, "In recvBytes, recv failed (socket: 0x%x) with error: %d\n", sock, WSAGetLastError() );
Philip Triccaa06f2372016-03-30 17:13:11 -070048 return TSS2_TCTI_RC_IO_ERROR;
49 }
50#ifdef DEBUG_SOCKETS
Philip Triccabcc73032016-03-30 19:50:54 -070051 TCTI_LOG( tctiContext, NO_PREFIX, "Receive Bytes from socket #0x%x: \n", sock );
Philip Tricca4eb2f352016-03-31 05:55:35 -070052 TCTI_LOG_BUFFER( tctiContext, NO_PREFIX, data, len );
Philip Triccaa06f2372016-03-30 17:13:11 -070053#endif
54
55 return TSS2_RC_SUCCESS;
56}
57
Philip Triccabcc73032016-03-30 19:50:54 -070058static TSS2_RC tctiSendBytes( TSS2_TCTI_CONTEXT *tctiContext, SOCKET sock, const unsigned char *data, int len )
Philip Tricca4ee284b2016-03-30 17:40:39 -070059{
60 TSS2_RC ret = TSS2_RC_SUCCESS;
61
62#ifdef DEBUG_SOCKETS
Philip Triccabcc73032016-03-30 19:50:54 -070063 TCTI_LOG( tctiContext, NO_PREFIX, "Send Bytes to socket #0x%x: \n", sock );
Philip Tricca4eb2f352016-03-31 05:55:35 -070064 TCTI_LOG_BUFFER( tctiContext, NO_PREFIX, (UINT8 *)data, len );
Philip Tricca4ee284b2016-03-30 17:40:39 -070065#endif
66
67 ret = sendBytes( sock, data, len);
68 if (ret != TSS2_RC_SUCCESS)
Philip Triccabcc73032016-03-30 19:50:54 -070069 TCTI_LOG( tctiContext, NO_PREFIX, "In recvBytes, recv failed (socket: 0x%x) with error: %d\n", sock, WSAGetLastError() );
Philip Tricca4ee284b2016-03-30 17:40:39 -070070 return ret;
71}
72
Philip Triccad1bbedb2016-02-14 20:39:59 -080073TSS2_RC SendSessionEndSocketTcti(
Will Arthur54e04e42015-07-15 11:29:25 -040074 TSS2_TCTI_CONTEXT *tctiContext, /* in */
75 UINT8 tpmCmdServer )
76{
77 UINT32 tpmSendCommand = TPM_SESSION_END; // Value for "send command" to MS simulator.
78 SOCKET sock;
wcarthureedecd62015-11-20 16:59:45 -050079 TSS2_RC rval = TSS2_RC_SUCCESS;
Philip Triccadfa41a52016-07-20 17:43:57 -070080
Will Arthur54e04e42015-07-15 11:29:25 -040081 if( tpmCmdServer )
82 {
83 sock = TCTI_CONTEXT_INTEL->tpmSock;
84 }
85 else
86 {
87 sock = TCTI_CONTEXT_INTEL->otherSock;
88 }
Philip Triccadfa41a52016-07-20 17:43:57 -070089
Will Arthur54e04e42015-07-15 11:29:25 -040090 tpmSendCommand = CHANGE_ENDIAN_DWORD(tpmSendCommand);
Philip Triccabcc73032016-03-30 19:50:54 -070091 rval = tctiSendBytes( tctiContext, sock, (char unsigned *)&tpmSendCommand, 4 );
Will Arthur54e04e42015-07-15 11:29:25 -040092
wcarthureedecd62015-11-20 16:59:45 -050093 return( rval );
Will Arthur54e04e42015-07-15 11:29:25 -040094}
95
Will Arthur54e04e42015-07-15 11:29:25 -040096TSS2_RC SocketSendTpmCommand(
97 TSS2_TCTI_CONTEXT *tctiContext, /* in */
98 size_t command_size, /* in */
99 uint8_t *command_buffer /* in */
100 )
101{
102 UINT32 tpmSendCommand = MS_SIM_TPM_SEND_COMMAND; // Value for "send command" to MS simulator.
103 UINT32 cnt, cnt1;
104 UINT8 locality;
wcarthureedecd62015-11-20 16:59:45 -0500105 TSS2_RC rval = TSS2_RC_SUCCESS;
Philip Triccadfa41a52016-07-20 17:43:57 -0700106
107#ifdef DEBUG
wcarthur1c827592016-04-27 11:07:51 -0400108 UINT32 commandCode;
109 printf_type rmPrefix;
wcarthur1aee953e2016-04-01 15:13:24 -0700110#endif
wcarthur1c827592016-04-27 11:07:51 -0400111
wcarthureedecd62015-11-20 16:59:45 -0500112 rval = CommonSendChecks( tctiContext, command_buffer );
113 if( rval != TSS2_RC_SUCCESS )
114 {
115 goto returnFromSocketSendTpmCommand;
116 }
Will-nuc3ebfeb92015-10-29 15:53:27 -0400117
Will Arthur54e04e42015-07-15 11:29:25 -0400118#ifdef DEBUG
wcarthur1c827592016-04-27 11:07:51 -0400119 if( ( ( TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.rmDebugPrefix == 1 )
120 rmPrefix = RM_PREFIX;
121 else
122 rmPrefix = NO_PREFIX;
123
124 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgEnabled == 1 )
125 {
126 TCTI_LOG( tctiContext, rmPrefix, "" );
wcarthur06befc02016-04-11 12:36:47 -0400127 commandCode = CHANGE_ENDIAN_DWORD( ( (TPM20_Header_In *)command_buffer )->commandCode );
Will Arthur54e04e42015-07-15 11:29:25 -0400128#ifdef DEBUG_SOCKETS
wcarthur06befc02016-04-11 12:36:47 -0400129 TCTI_LOG( tctiContext, NO_PREFIX, "Command sent on socket #0x%x: %s\n", TCTI_CONTEXT_INTEL->tpmSock, strTpmCommandCode( commandCode ) );
wcarthur1a10b0c92016-04-14 04:25:03 -0700130#else
131 TCTI_LOG( tctiContext, NO_PREFIX, "Cmd sent: %s\n", strTpmCommandCode( commandCode ) );
132#endif
Will Arthur54e04e42015-07-15 11:29:25 -0400133 }
wcarthur1c827592016-04-27 11:07:51 -0400134#endif
Will Arthur54e04e42015-07-15 11:29:25 -0400135 // Size TPM 1.2 and TPM 2.0 headers overlap exactly, we can use
136 // either 1.2 or 2.0 header to get the size.
137 cnt = CHANGE_ENDIAN_DWORD(((TPM20_Header_In *) command_buffer)->commandSize);
138
139 // Send TPM_SEND_COMMAND
140 tpmSendCommand = CHANGE_ENDIAN_DWORD(tpmSendCommand);
Philip Triccabcc73032016-03-30 19:50:54 -0700141 rval = tctiSendBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)&tpmSendCommand, 4 );
wcarthureedecd62015-11-20 16:59:45 -0500142 if( rval != TSS2_RC_SUCCESS )
143 goto returnFromSocketSendTpmCommand;
Philip Triccadfa41a52016-07-20 17:43:57 -0700144
Will Arthur54e04e42015-07-15 11:29:25 -0400145 // Send the locality
146 locality = (UINT8)( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.locality;
Philip Triccabcc73032016-03-30 19:50:54 -0700147 rval = tctiSendBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)&locality, 1 );
wcarthureedecd62015-11-20 16:59:45 -0500148 if( rval != TSS2_RC_SUCCESS )
149 goto returnFromSocketSendTpmCommand;
Will Arthur54e04e42015-07-15 11:29:25 -0400150
Will Arthur54e04e42015-07-15 11:29:25 -0400151#ifdef DEBUG
wcarthur1c827592016-04-27 11:07:51 -0400152 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgEnabled == 1 )
Will Arthur54e04e42015-07-15 11:29:25 -0400153 {
wcarthur1c827592016-04-27 11:07:51 -0400154 TCTI_LOG( tctiContext, rmPrefix, "Locality = %d", ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.locality );
Will Arthur54e04e42015-07-15 11:29:25 -0400155 }
156#endif
Philip Triccadfa41a52016-07-20 17:43:57 -0700157
Will Arthur54e04e42015-07-15 11:29:25 -0400158 // Send number of bytes.
159 cnt1 = cnt;
160 cnt = CHANGE_ENDIAN_DWORD(cnt);
Philip Triccabcc73032016-03-30 19:50:54 -0700161 rval = tctiSendBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)&cnt, 4 );
wcarthureedecd62015-11-20 16:59:45 -0500162 if( rval != TSS2_RC_SUCCESS )
163 goto returnFromSocketSendTpmCommand;
Philip Triccadfa41a52016-07-20 17:43:57 -0700164
Will Arthur54e04e42015-07-15 11:29:25 -0400165 // Send the TPM command buffer
Philip Triccabcc73032016-03-30 19:50:54 -0700166 rval = tctiSendBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)command_buffer, cnt1 );
wcarthureedecd62015-11-20 16:59:45 -0500167 if( rval != TSS2_RC_SUCCESS )
168 goto returnFromSocketSendTpmCommand;
Philip Triccadfa41a52016-07-20 17:43:57 -0700169
Will Arthur54e04e42015-07-15 11:29:25 -0400170#ifdef DEBUG
wcarthur1c827592016-04-27 11:07:51 -0400171 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgEnabled == 1 )
Will Arthur54e04e42015-07-15 11:29:25 -0400172 {
wcarthur1c827592016-04-27 11:07:51 -0400173 DEBUG_PRINT_BUFFER( rmPrefix, command_buffer, cnt1 );
Will Arthur54e04e42015-07-15 11:29:25 -0400174 }
175#endif
176 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.commandSent = 1;
177
wcarthureedecd62015-11-20 16:59:45 -0500178returnFromSocketSendTpmCommand:
179
180 if( rval == TSS2_RC_SUCCESS )
181 {
182 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->previousStage = TCTI_STAGE_SEND_COMMAND;
wcarthura05cdcc2015-12-04 18:07:16 -0500183 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.tagReceived = 0;
184 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.responseSizeReceived = 0;
185 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.protocolResponseSizeReceived = 0;
wcarthureedecd62015-11-20 16:59:45 -0500186 }
187
188 return rval;
Will Arthur54e04e42015-07-15 11:29:25 -0400189}
190
191TSS2_RC SocketCancel(
192 TSS2_TCTI_CONTEXT *tctiContext
193 )
194{
195 TSS2_RC rval = TSS2_RC_SUCCESS;
196
197 if( tctiContext == 0 )
198 {
199 rval = TSS2_TCTI_RC_BAD_REFERENCE;
200 }
201 else if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.commandSent != 1 )
202 {
203 rval = TSS2_TCTI_RC_BAD_SEQUENCE;
204 }
205 else
206 {
207 rval = (TSS2_RC)PlatformCommand( tctiContext, MS_SIM_CANCEL_ON );
208#if 0
209 if( rval == TSS2_RC_SUCCESS )
210 {
211 rval = (TSS2_RC)PlatformCommand( tctiContext, MS_SIM_CANCEL_OFF );
212 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgLevel == TSS2_TCTI_DEBUG_MSG_ENABLED )
213 {
Philip Triccabcc73032016-03-30 19:50:54 -0700214 TCTI_LOG( tctiContext, NO_PREFIX, "%s sent cancel ON command:\n", interfaceName );
Will Arthur54e04e42015-07-15 11:29:25 -0400215 }
216 }
Philip Triccadfa41a52016-07-20 17:43:57 -0700217#endif
Will Arthur54e04e42015-07-15 11:29:25 -0400218 }
219
220 return rval;
221}
222
223TSS2_RC SocketSetLocality(
224 TSS2_TCTI_CONTEXT *tctiContext, /* in */
225 uint8_t locality /* in */
226 )
227{
228 TSS2_RC rval = TSS2_RC_SUCCESS;
229
230 if( tctiContext == 0 )
231 {
232 rval = TSS2_TCTI_RC_BAD_REFERENCE;
233 }
234 else if( ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.locality != locality )
235 {
236 if ( ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.commandSent == 1 )
237 {
238 rval = TSS2_TCTI_RC_BAD_SEQUENCE;
239 }
240 else
241 {
242 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.locality = locality;
243 }
244 }
245
246 return rval;
247}
248
wcarthur35aa5392016-03-22 16:52:44 -0400249void SocketFinalize(
Will Arthur54e04e42015-07-15 11:29:25 -0400250 TSS2_TCTI_CONTEXT *tctiContext /* in */
251 )
252{
wcarthur35aa5392016-03-22 16:52:44 -0400253 if( tctiContext != NULL )
wcarthurf979e352015-11-24 17:34:44 -0500254 {
255 // Send session end messages to servers.
Philip Triccad1bbedb2016-02-14 20:39:59 -0800256 SendSessionEndSocketTcti( tctiContext, 1 );
257 SendSessionEndSocketTcti( tctiContext, 0 );
Will Arthur54e04e42015-07-15 11:29:25 -0400258
wcarthurf979e352015-11-24 17:34:44 -0500259 CloseSockets( TCTI_CONTEXT_INTEL->otherSock, TCTI_CONTEXT_INTEL->tpmSock );
wcarthurf979e352015-11-24 17:34:44 -0500260 }
Will Arthur54e04e42015-07-15 11:29:25 -0400261}
262
Will Arthur54e04e42015-07-15 11:29:25 -0400263TSS2_RC SocketReceiveTpmResponse(
264 TSS2_TCTI_CONTEXT *tctiContext, /* in */
265 size_t *response_size, /* out */
266 unsigned char *response_buffer, /* in */
267 int32_t timeout
268 )
269{
270 UINT32 trash;
Will Arthur54e04e42015-07-15 11:29:25 -0400271 TSS2_RC rval = TSS2_RC_SUCCESS;
272 fd_set readFds;
273 struct timeval tv, *tvPtr;
274 int32_t timeoutMsecs = timeout % 1000;
275 int iResult;
wcarthura05cdcc2015-12-04 18:07:16 -0500276 unsigned char responseSizeDelta = 0;
wcarthur1c827592016-04-27 11:07:51 -0400277 printf_type rmPrefix;
wcarthureedecd62015-11-20 16:59:45 -0500278
279 rval = CommonReceiveChecks( tctiContext, response_size, response_buffer );
280 if( rval != TSS2_RC_SUCCESS )
281 {
282 goto retSocketReceiveTpmResponse;
Philip Triccadfa41a52016-07-20 17:43:57 -0700283 }
284
wcarthur1c827592016-04-27 11:07:51 -0400285 if( ( ( TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.rmDebugPrefix == 1 )
286 rmPrefix = RM_PREFIX;
287 else
288 rmPrefix = NO_PREFIX;
289
wcarthur74a92a42015-12-07 16:02:12 -0500290 if( timeout == TSS2_TCTI_TIMEOUT_BLOCK )
Will Arthur54e04e42015-07-15 11:29:25 -0400291 {
wcarthur74a92a42015-12-07 16:02:12 -0500292 tvPtr = 0;
293 }
294 else
295 {
296 tv.tv_sec = timeout / 1000;
297 tv.tv_usec = timeoutMsecs * 1000;
298 tvPtr = &tv;
Will Arthur54e04e42015-07-15 11:29:25 -0400299 }
300
wcarthur74a92a42015-12-07 16:02:12 -0500301 FD_ZERO( &readFds );
302 FD_SET( TCTI_CONTEXT_INTEL->tpmSock, &readFds );
Will Arthur54e04e42015-07-15 11:29:25 -0400303
wcarthur74a92a42015-12-07 16:02:12 -0500304 iResult = select( TCTI_CONTEXT_INTEL->tpmSock+1, &readFds, 0, 0, tvPtr );
305 if( iResult == 0 )
Will Arthur54e04e42015-07-15 11:29:25 -0400306 {
wcarthur1c827592016-04-27 11:07:51 -0400307 TCTI_LOG( tctiContext, rmPrefix, "select failed due to timeout, socket #: 0x%x\n", TCTI_CONTEXT_INTEL->tpmSock );
wcarthur74a92a42015-12-07 16:02:12 -0500308 rval = TSS2_TCTI_RC_TRY_AGAIN;
309 goto retSocketReceiveTpmResponse;
310 }
311 else if( iResult == SOCKET_ERROR )
312 {
wcarthur1c827592016-04-27 11:07:51 -0400313 TCTI_LOG( tctiContext, rmPrefix, "select failed with socket error: %d\n", WSAGetLastError() );
wcarthur74a92a42015-12-07 16:02:12 -0500314 rval = TSS2_TCTI_RC_IO_ERROR;
315 goto retSocketReceiveTpmResponse;
316 }
317 else if ( iResult != 1 )
318 {
wcarthur1c827592016-04-27 11:07:51 -0400319 TCTI_LOG( tctiContext, rmPrefix, "select failed, read the wrong # of bytes: %d\n", iResult );
wcarthur74a92a42015-12-07 16:02:12 -0500320 rval = TSS2_TCTI_RC_IO_ERROR;
321 goto retSocketReceiveTpmResponse;
322 }
Will Arthur54e04e42015-07-15 11:29:25 -0400323
wcarthur74a92a42015-12-07 16:02:12 -0500324 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.protocolResponseSizeReceived != 1 )
Philip Triccadfa41a52016-07-20 17:43:57 -0700325 {
Will Arthur54e04e42015-07-15 11:29:25 -0400326 // Receive the size of the response.
Philip Triccabcc73032016-03-30 19:50:54 -0700327 rval = tctiRecvBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)& (((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize ), 4 );
wcarthureedecd62015-11-20 16:59:45 -0500328 if( rval != TSS2_RC_SUCCESS )
329 goto retSocketReceiveTpmResponse;
330
wcarthur74a92a42015-12-07 16:02:12 -0500331 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize = CHANGE_ENDIAN_DWORD( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize );
332 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.protocolResponseSizeReceived = 1;
Will Arthur54e04e42015-07-15 11:29:25 -0400333 }
334
wcarthur74a92a42015-12-07 16:02:12 -0500335 if( response_buffer == NULL )
Will Arthur54e04e42015-07-15 11:29:25 -0400336 {
wcarthur74a92a42015-12-07 16:02:12 -0500337 // In this case, just return the size
338 *response_size = ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize;
339 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.protocolResponseSizeReceived = 1;
340 goto retSocketReceiveTpmResponse;
341 }
342
343 if( *response_size < ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize )
344 {
345 *response_size = ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize;
Philip Triccadfa41a52016-07-20 17:43:57 -0700346 rval = TSS2_TCTI_RC_INSUFFICIENT_BUFFER;
wcarthur74a92a42015-12-07 16:02:12 -0500347
348
349 // If possible, receive tag from TPM.
350 if( *response_size >= sizeof( TPM_ST ) && ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.tagReceived == 0 )
Will Arthur54e04e42015-07-15 11:29:25 -0400351 {
Philip Triccabcc73032016-03-30 19:50:54 -0700352 if( TSS2_RC_SUCCESS != tctiRecvBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)&( ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->tag ), 2 ) )
wcarthur74a92a42015-12-07 16:02:12 -0500353 {
wcarthura05cdcc2015-12-04 18:07:16 -0500354 goto retSocketReceiveTpmResponse;
wcarthur2efe2912015-11-16 11:19:42 -0500355 }
wcarthur74a92a42015-12-07 16:02:12 -0500356 else
wcarthura05cdcc2015-12-04 18:07:16 -0500357 {
wcarthur74a92a42015-12-07 16:02:12 -0500358 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.tagReceived = 1;
wcarthura05cdcc2015-12-04 18:07:16 -0500359 }
Will Arthur54e04e42015-07-15 11:29:25 -0400360 }
wcarthura05cdcc2015-12-04 18:07:16 -0500361
wcarthur74a92a42015-12-07 16:02:12 -0500362 // If possible, receive response size from TPM
363 if( *response_size >= ( sizeof( TPM_ST ) + sizeof( TPM_RC ) ) && ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.responseSizeReceived == 0 )
364 {
Philip Triccabcc73032016-03-30 19:50:54 -0700365 if( TSS2_RC_SUCCESS != tctiRecvBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)&( ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->responseSize ), 4 ) )
wcarthura05cdcc2015-12-04 18:07:16 -0500366 {
wcarthureedecd62015-11-20 16:59:45 -0500367 goto retSocketReceiveTpmResponse;
wcarthur74a92a42015-12-07 16:02:12 -0500368 }
369 else
370 {
371 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize = CHANGE_ENDIAN_DWORD( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize );
372 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.responseSizeReceived = 1;
373 }
374 }
375 }
376 else
377 {
wcarthur1c827592016-04-27 11:07:51 -0400378 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgEnabled == 1 &&
Will-nuce0d3ec22015-12-09 15:09:49 -0500379 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize > 0 )
380 {
381#ifdef DEBUG
wcarthur1c827592016-04-27 11:07:51 -0400382 TCTI_LOG( tctiContext, rmPrefix, "Response Received: " );
Will-nuce0d3ec22015-12-09 15:09:49 -0500383#endif
384#ifdef DEBUG_SOCKETS
wcarthur1c827592016-04-27 11:07:51 -0400385 TCTI_LOG( tctiContext, rmPrefix, "from socket #0x%x:\n", TCTI_CONTEXT_INTEL->tpmSock );
Will-nuce0d3ec22015-12-09 15:09:49 -0500386#endif
387 }
Philip Triccadfa41a52016-07-20 17:43:57 -0700388
wcarthur74a92a42015-12-07 16:02:12 -0500389 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.tagReceived == 1 )
390 {
391 *(TPM_ST *)response_buffer = ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->tag;
392 responseSizeDelta += sizeof( TPM_ST );
393 response_buffer += sizeof( TPM_ST );
394 }
395
396 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.responseSizeReceived == 1 )
397 {
398 *(TPM_RC *)response_buffer = CHANGE_ENDIAN_DWORD( ( (TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->responseSize );
399 responseSizeDelta += sizeof( TPM_RC );
400 response_buffer += sizeof( TPM_RC );
401 }
402
403 // Receive the TPM response.
Philip Triccabcc73032016-03-30 19:50:54 -0700404 rval = tctiRecvBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)response_buffer, ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize - responseSizeDelta );
wcarthur74a92a42015-12-07 16:02:12 -0500405 if( rval != TSS2_RC_SUCCESS )
406 goto retSocketReceiveTpmResponse;
wcarthureedecd62015-11-20 16:59:45 -0500407
wcarthur2efe2912015-11-16 11:19:42 -0500408#ifdef DEBUG
wcarthur1c827592016-04-27 11:07:51 -0400409 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgEnabled == 1 )
wcarthur74a92a42015-12-07 16:02:12 -0500410 {
wcarthur1c827592016-04-27 11:07:51 -0400411 DEBUG_PRINT_BUFFER( rmPrefix, response_buffer, ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize );
wcarthur0651af22015-11-25 15:01:22 -0500412 }
wcarthur74a92a42015-12-07 16:02:12 -0500413#endif
wcarthur0651af22015-11-25 15:01:22 -0500414
wcarthur74a92a42015-12-07 16:02:12 -0500415 // Receive the appended four bytes of 0's
Philip Triccabcc73032016-03-30 19:50:54 -0700416 rval = tctiRecvBytes( tctiContext, TCTI_CONTEXT_INTEL->tpmSock, (unsigned char *)&trash, 4 );
wcarthur74a92a42015-12-07 16:02:12 -0500417 if( rval != TSS2_RC_SUCCESS )
418 goto retSocketReceiveTpmResponse;
Will Arthur54e04e42015-07-15 11:29:25 -0400419 }
420
wcarthura05cdcc2015-12-04 18:07:16 -0500421 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize < *response_size )
Will Arthur54e04e42015-07-15 11:29:25 -0400422 {
wcarthura05cdcc2015-12-04 18:07:16 -0500423 *response_size = ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->responseSize;
Will Arthur54e04e42015-07-15 11:29:25 -0400424 }
Philip Triccadfa41a52016-07-20 17:43:57 -0700425
Will Arthur54e04e42015-07-15 11:29:25 -0400426 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.commandSent = 0;
427
428 // Turn cancel off.
wcarthur2efe2912015-11-16 11:19:42 -0500429 if( rval == TSS2_RC_SUCCESS )
430 {
431 rval = (TSS2_RC)PlatformCommand( tctiContext, MS_SIM_CANCEL_OFF );
432 }
433 else
434 {
435 // Ignore return value so earlier error code is preserved.
436 PlatformCommand( tctiContext, MS_SIM_CANCEL_OFF );
437 }
Will Arthur54e04e42015-07-15 11:29:25 -0400438
wcarthur1c827592016-04-27 11:07:51 -0400439 if( ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext )->status.debugMsgEnabled== 1 )
Will Arthur54e04e42015-07-15 11:29:25 -0400440 {
Philip Triccabcc73032016-03-30 19:50:54 -0700441// TCTI_LOG( tctiContext, NO_PREFIX, "%s sent cancel OFF command:\n", interfaceName );
Will Arthur54e04e42015-07-15 11:29:25 -0400442 }
443
444retSocketReceiveTpmResponse:
Philip Triccadfa41a52016-07-20 17:43:57 -0700445 if( rval == TSS2_RC_SUCCESS &&
wcarthura05cdcc2015-12-04 18:07:16 -0500446 response_buffer != NULL )
wcarthureedecd62015-11-20 16:59:45 -0500447 {
448 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->previousStage = TCTI_STAGE_RECEIVE_RESPONSE;
449 }
Philip Triccadfa41a52016-07-20 17:43:57 -0700450
Will Arthur54e04e42015-07-15 11:29:25 -0400451 return rval;
452}
453
454#ifdef __cplusplus
455}
456#endif
457
Will Arthur54e04e42015-07-15 11:29:25 -0400458#define HOSTNAME_LENGTH 200
459#define PORT_LENGTH 4
460
Philip Tricca40e926d2016-09-22 20:37:28 -0700461/**
462 * This function sends the Microsoft simulator the MS_SIM_POWER_ON and
463 * MS_SIM_NV_ON commands using the PlatformCommand mechanism. Without
464 * these the simulator will respond with zero sized buffer which causes
465 * the TSS to freak out. Sending this command more than once is harmelss
466 * so it's advisable to call this function as part of the TCTI context
467 * initialization just to be sure.
468 *
469 * NOTE: The caller will still need to call Tss2_Sys_Startup. If they
470 * don't, an error will be returned from each call till they do but
471 * the error will at least be meaningful (TPM_RC_INITIALIZE).
472 */
473static TSS2_RC InitializeMsTpm2Simulator(
474 TSS2_TCTI_CONTEXT *tctiContext
475 )
476{
477 TSS2_TCTI_CONTEXT_INTEL *intel_tctiCtx;
478 TSS2_RC rval;
479
480 intel_tctiCtx = (TSS2_TCTI_CONTEXT_INTEL*)tctiContext;
481 rval = PlatformCommand( tctiContext ,MS_SIM_POWER_ON );
482 if( rval != TSS2_RC_SUCCESS ) {
483 CloseSockets( intel_tctiCtx->otherSock, intel_tctiCtx->tpmSock );
484 return rval;
485 }
486 rval = PlatformCommand( tctiContext, MS_SIM_NV_ON );
487 if( rval != TSS2_RC_SUCCESS )
488 CloseSockets( intel_tctiCtx->otherSock, intel_tctiCtx->tpmSock );
489
490 return rval;
491}
492
Philip Triccad1bbedb2016-02-14 20:39:59 -0800493TSS2_RC InitSocketTcti (
Will Arthur54e04e42015-07-15 11:29:25 -0400494 TSS2_TCTI_CONTEXT *tctiContext, // OUT
495 size_t *contextSize, // IN/OUT
Philip Tricca6feb9762016-02-23 10:44:09 -0800496 const TCTI_SOCKET_CONF *conf, // IN
Will Arthur54e04e42015-07-15 11:29:25 -0400497 const uint8_t serverSockets
498 )
499{
500 TSS2_RC rval = TSS2_RC_SUCCESS;
Will Arthur54e04e42015-07-15 11:29:25 -0400501 SOCKET otherSock;
502 SOCKET tpmSock;
503
504 if( tctiContext == NULL )
505 {
506 *contextSize = sizeof( TSS2_TCTI_CONTEXT_INTEL );
507 return TSS2_RC_SUCCESS;
508 }
509 else
510 {
Will Arthur54e04e42015-07-15 11:29:25 -0400511 // Init TCTI context.
Philip Tricca7b4948e2016-04-18 20:43:59 -0700512 TSS2_TCTI_MAGIC( tctiContext ) = TCTI_MAGIC;
513 TSS2_TCTI_VERSION( tctiContext ) = TCTI_VERSION;
514 TSS2_TCTI_TRANSMIT( tctiContext ) = SocketSendTpmCommand;
515 TSS2_TCTI_RECEIVE( tctiContext ) = SocketReceiveTpmResponse;
516 TSS2_TCTI_FINALIZE( tctiContext ) = SocketFinalize;
517 TSS2_TCTI_CANCEL( tctiContext ) = SocketCancel;
518 TSS2_TCTI_GET_POLL_HANDLES( tctiContext ) = 0;
519 TSS2_TCTI_SET_LOCALITY( tctiContext ) = SocketSetLocality;
wcarthur1c827592016-04-27 11:07:51 -0400520 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.debugMsgEnabled = 0;
Will Arthur54e04e42015-07-15 11:29:25 -0400521 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.locality = 3;
522 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.commandSent = 0;
523 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.rmDebugPrefix = 0;
wcarthura05cdcc2015-12-04 18:07:16 -0500524 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.tagReceived = 0;
525 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.responseSizeReceived = 0;
526 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->status.protocolResponseSizeReceived = 0;
wcarthur1c827592016-04-27 11:07:51 -0400527 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->currentTctiContext = 0;
528 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->previousStage = TCTI_STAGE_INITIALIZE;
Philip Triccabcc73032016-03-30 19:50:54 -0700529 TCTI_LOG_CALLBACK( tctiContext ) = conf->logCallback;
Philip Tricca4eb2f352016-03-31 05:55:35 -0700530 TCTI_LOG_BUFFER_CALLBACK( tctiContext ) = conf->logBufferCallback;
Philip Triccabcc73032016-03-30 19:50:54 -0700531 TCTI_LOG_DATA( tctiContext ) = conf->logData;
Will Arthur54e04e42015-07-15 11:29:25 -0400532
Philip Triccabcc73032016-03-30 19:50:54 -0700533 rval = (TSS2_RC) InitSockets( conf->hostname, conf->port, serverSockets, &otherSock, &tpmSock, TCTI_LOG_CALLBACK( tctiContext ), TCTI_LOG_DATA( tctiContext) );
Will Arthur54e04e42015-07-15 11:29:25 -0400534 if( rval == TSS2_RC_SUCCESS )
535 {
536 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->otherSock = otherSock;
537 ((TSS2_TCTI_CONTEXT_INTEL *)tctiContext)->tpmSock = tpmSock;
Philip Tricca40e926d2016-09-22 20:37:28 -0700538 rval = InitializeMsTpm2Simulator( tctiContext );
Will Arthur54e04e42015-07-15 11:29:25 -0400539 }
540 else
541 {
Will Arthurca8e7f32015-08-03 15:35:19 -0400542 CloseSockets( otherSock, tpmSock);
Philip Triccadfa41a52016-07-20 17:43:57 -0700543 }
Will Arthur54e04e42015-07-15 11:29:25 -0400544 }
545
546 return rval;
547}