Andrew Boyson / crypto

Dependents:   oldheating gps motorhome heating

Committer:
andrewboyson
Date:
Wed Jul 31 15:12:34 2019 +0000
Revision:
2:82268409e83f
Child:
4:6a1d887f1cad
A lot of tidying. Not working yet.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
andrewboyson 2:82268409e83f 1 #include "tls.h"
andrewboyson 2:82268409e83f 2 #include "tls-defs.h"
andrewboyson 2:82268409e83f 3 #include "tls-state.h"
andrewboyson 2:82268409e83f 4 #include "tls-session.h"
andrewboyson 2:82268409e83f 5 #include "tls-log.h"
andrewboyson 2:82268409e83f 6 #include "mstimer.h"
andrewboyson 2:82268409e83f 7 #include "random.h"
andrewboyson 2:82268409e83f 8 #include "log.h"
andrewboyson 2:82268409e83f 9 #include "pri-key.h"
andrewboyson 2:82268409e83f 10
andrewboyson 2:82268409e83f 11 static int handleClientHello(int length, char* pBuffer, struct TlsState* pState) //returns 0 on success; -1 on error
andrewboyson 2:82268409e83f 12 {
andrewboyson 2:82268409e83f 13 //Check things look ok
andrewboyson 2:82268409e83f 14 char* p = pBuffer;
andrewboyson 2:82268409e83f 15 if (length < 100)
andrewboyson 2:82268409e83f 16 {
andrewboyson 2:82268409e83f 17 LogF("TLS - %d byte client hello message is not at least 100 bytes long\r\n", length);
andrewboyson 2:82268409e83f 18 return -1;
andrewboyson 2:82268409e83f 19 }
andrewboyson 2:82268409e83f 20
andrewboyson 2:82268409e83f 21 //Read in the parameters
andrewboyson 2:82268409e83f 22 char versionH = *p++;
andrewboyson 2:82268409e83f 23 char versionL = *p++;
andrewboyson 2:82268409e83f 24
andrewboyson 2:82268409e83f 25 char* pRandom = p;
andrewboyson 2:82268409e83f 26 p += 32;
andrewboyson 2:82268409e83f 27
andrewboyson 2:82268409e83f 28 int sessionIdLength = *p++;
andrewboyson 2:82268409e83f 29 char* pSessionId = p;
andrewboyson 2:82268409e83f 30
andrewboyson 2:82268409e83f 31 //Handle the parameters
andrewboyson 2:82268409e83f 32 pState->session = -1;
andrewboyson 2:82268409e83f 33 if (sessionIdLength == 1) pState->session = *pSessionId;
andrewboyson 2:82268409e83f 34 struct TlsSession* pSession = TlsSessionGetFromIndex(pState->session);
andrewboyson 2:82268409e83f 35 if (!pSession || pSession->state != TLS_SESSION_STATE_VALID)
andrewboyson 2:82268409e83f 36 {
andrewboyson 2:82268409e83f 37 pSession = TlsSessionGetOldest();
andrewboyson 2:82268409e83f 38 pSession->state = TLS_SESSION_STATE_STARTED;
andrewboyson 2:82268409e83f 39 }
andrewboyson 2:82268409e83f 40 pState->session = TlsSessionGetIndex(pSession);
andrewboyson 2:82268409e83f 41
andrewboyson 2:82268409e83f 42 pSession->lastUsed = MsTimerCount;
andrewboyson 2:82268409e83f 43 for (int i = 0; i < 32; i++) pSession->clientRandom[i] = *pRandom++;
andrewboyson 2:82268409e83f 44 for (int i = 0; i < 32; i++) pSession->serverRandom[i] = RandomGetByte();
andrewboyson 2:82268409e83f 45
andrewboyson 2:82268409e83f 46 //Log the parameters
andrewboyson 2:82268409e83f 47 if (TlsTrace)
andrewboyson 2:82268409e83f 48 {
andrewboyson 2:82268409e83f 49 LogF("- client version HH:LL: %02x:%02x\r\n", versionH, versionL);
andrewboyson 2:82268409e83f 50 Log ("- client random:\r\n"); LogBytesAsHex(pRandom, 32); Log("\r\n");
andrewboyson 2:82268409e83f 51 Log ("- client session id:\r\n"); LogBytesAsHex(pSessionId, sessionIdLength); Log("\r\n");
andrewboyson 2:82268409e83f 52 LogF("- session index: %d\r\n", pState->session);
andrewboyson 2:82268409e83f 53 }
andrewboyson 2:82268409e83f 54 return 0;
andrewboyson 2:82268409e83f 55 }
andrewboyson 2:82268409e83f 56 static int handleClientKeyExchange(int length, char* pBuffer, struct TlsState* pState) //returns 0 on success; -1 on error
andrewboyson 2:82268409e83f 57 {
andrewboyson 2:82268409e83f 58 struct TlsSession* pSession = TlsSessionGetFromIndex(pState->session);
andrewboyson 2:82268409e83f 59
andrewboyson 2:82268409e83f 60 if (length != 130)
andrewboyson 2:82268409e83f 61 {
andrewboyson 2:82268409e83f 62 LogF("TLS - %d byte client key exchange message is not 130 bytes long\r\n", length);
andrewboyson 2:82268409e83f 63 return -1;
andrewboyson 2:82268409e83f 64 }
andrewboyson 2:82268409e83f 65 int premasterLength = pBuffer[0] << 8 | pBuffer[1]; //Overall length 2 bytes
andrewboyson 2:82268409e83f 66 if (premasterLength != 128)
andrewboyson 2:82268409e83f 67 {
andrewboyson 2:82268409e83f 68 LogF("TLS - %d byte encrypted pre master secret is not 128 bytes long\r\n", length);
andrewboyson 2:82268409e83f 69 return -1;
andrewboyson 2:82268409e83f 70 }
andrewboyson 2:82268409e83f 71 char* pEncryptedPreMasterSecret = pBuffer + 2;
andrewboyson 2:82268409e83f 72 pSession->slotPriKeyDecryption = PriKeyDecryptStart(pEncryptedPreMasterSecret);
andrewboyson 2:82268409e83f 73
andrewboyson 2:82268409e83f 74 if (TlsTrace)
andrewboyson 2:82268409e83f 75 {
andrewboyson 2:82268409e83f 76 LogF("- encrypted pre master\r\n", premasterLength);
andrewboyson 2:82268409e83f 77 LogBytesAsHex(pEncryptedPreMasterSecret, 128);
andrewboyson 2:82268409e83f 78 Log("\r\n");
andrewboyson 2:82268409e83f 79 }
andrewboyson 2:82268409e83f 80
andrewboyson 2:82268409e83f 81 return 0;
andrewboyson 2:82268409e83f 82 }
andrewboyson 2:82268409e83f 83 static void handleHandshake(int length, char* pBuffer, struct TlsState* pState)
andrewboyson 2:82268409e83f 84 {
andrewboyson 2:82268409e83f 85 char* p = pBuffer;
andrewboyson 2:82268409e83f 86 while (p < pBuffer + length)
andrewboyson 2:82268409e83f 87 {
andrewboyson 2:82268409e83f 88 char handshakeType = *p++;
andrewboyson 2:82268409e83f 89 int handshakeLength = *p++ << 16;
andrewboyson 2:82268409e83f 90 handshakeLength |= *p++ << 8;
andrewboyson 2:82268409e83f 91 handshakeLength |= *p++ ; //Handshake length 3 bytes
andrewboyson 2:82268409e83f 92
andrewboyson 2:82268409e83f 93 if (TlsTrace)
andrewboyson 2:82268409e83f 94 {
andrewboyson 2:82268409e83f 95 Log ("- handshake type: "); TlsLogHandshakeType(handshakeType); Log("\r\n");
andrewboyson 2:82268409e83f 96 LogF("- handshake length: %d\r\n", handshakeLength);
andrewboyson 2:82268409e83f 97 }
andrewboyson 2:82268409e83f 98
andrewboyson 2:82268409e83f 99 int r = -1;
andrewboyson 2:82268409e83f 100 switch (handshakeType)
andrewboyson 2:82268409e83f 101 {
andrewboyson 2:82268409e83f 102 case TLS_HANDSHAKE_ClientHello:
andrewboyson 2:82268409e83f 103 r = handleClientHello(handshakeLength, p, pState);
andrewboyson 2:82268409e83f 104 pState->toDo = r ? DO_SEND_ALERT_ILLEGAL_PARAMETER : DO_SEND_SERVER_HELLO;
andrewboyson 2:82268409e83f 105 break;
andrewboyson 2:82268409e83f 106
andrewboyson 2:82268409e83f 107 case TLS_HANDSHAKE_ClientKeyExchange:
andrewboyson 2:82268409e83f 108 r = handleClientKeyExchange(handshakeLength, p, pState);
andrewboyson 2:82268409e83f 109 pState->toDo = r ? DO_SEND_ALERT_ILLEGAL_PARAMETER : DO_WAIT_DECRYPT_MASTER_SECRET;
andrewboyson 2:82268409e83f 110 break;
andrewboyson 2:82268409e83f 111
andrewboyson 2:82268409e83f 112 default:
andrewboyson 2:82268409e83f 113 LogF("TLS - ignoring untreated %d byte handshake type ", handshakeLength);
andrewboyson 2:82268409e83f 114 TlsLogHandshakeType(handshakeType);
andrewboyson 2:82268409e83f 115 Log("\r\n");
andrewboyson 2:82268409e83f 116 break;
andrewboyson 2:82268409e83f 117 }
andrewboyson 2:82268409e83f 118 p += handshakeLength;
andrewboyson 2:82268409e83f 119 }
andrewboyson 2:82268409e83f 120 }
andrewboyson 2:82268409e83f 121 static void handleAlert(int length, char* pBuffer)
andrewboyson 2:82268409e83f 122 {
andrewboyson 2:82268409e83f 123 char level = pBuffer[0];
andrewboyson 2:82268409e83f 124 char description = pBuffer[1];
andrewboyson 2:82268409e83f 125 if (TlsTrace)
andrewboyson 2:82268409e83f 126 {
andrewboyson 2:82268409e83f 127 Log("- alert level: "); TlsLogAlertLevel (level); Log("\r\n");
andrewboyson 2:82268409e83f 128 Log("- alert description: "); TlsLogAlertDescription(description); Log("\r\n");
andrewboyson 2:82268409e83f 129 }
andrewboyson 2:82268409e83f 130 }
andrewboyson 2:82268409e83f 131 static void handleApplication(int length, char* pBuffer)
andrewboyson 2:82268409e83f 132 {
andrewboyson 2:82268409e83f 133 if (TlsTrace)
andrewboyson 2:82268409e83f 134 {
andrewboyson 2:82268409e83f 135 Log("- application data:\r\n");
andrewboyson 2:82268409e83f 136 LogBytesAsHex(pBuffer, length);
andrewboyson 2:82268409e83f 137 Log("\r\n");
andrewboyson 2:82268409e83f 138 }
andrewboyson 2:82268409e83f 139 }
andrewboyson 2:82268409e83f 140 void TlsRequest(char* pTlsState, char* pWebState, int size, char* pRequestStream, uint32_t positionInRequestStream)
andrewboyson 2:82268409e83f 141 {
andrewboyson 2:82268409e83f 142 struct TlsState* pState = (struct TlsState*)pTlsState;
andrewboyson 2:82268409e83f 143
andrewboyson 2:82268409e83f 144 if (TlsTrace) LogF("TLS <<< %d (%u)\r\n", size, positionInRequestStream);
andrewboyson 2:82268409e83f 145
andrewboyson 2:82268409e83f 146 if (size == 0) return;
andrewboyson 2:82268409e83f 147 //if (positionInRequestStream != 0) return;
andrewboyson 2:82268409e83f 148 char contentType = pRequestStream[0];
andrewboyson 2:82268409e83f 149 char versionH = pRequestStream[1];
andrewboyson 2:82268409e83f 150 char versionL = pRequestStream[2];
andrewboyson 2:82268409e83f 151 int length = pRequestStream[3] << 8 | pRequestStream[4]; //Length (2 bytes)
andrewboyson 2:82268409e83f 152 if (TlsTrace)
andrewboyson 2:82268409e83f 153 {
andrewboyson 2:82268409e83f 154 Log ("- content type: "); TlsLogContentType(contentType); Log("\r\n");
andrewboyson 2:82268409e83f 155 LogF("- legacy HH:LL: %02x:%02x\r\n", versionH, versionL);
andrewboyson 2:82268409e83f 156 LogF("- length : %d\r\n" , length);
andrewboyson 2:82268409e83f 157 }
andrewboyson 2:82268409e83f 158 switch (contentType)
andrewboyson 2:82268409e83f 159 {
andrewboyson 2:82268409e83f 160 case TLS_CONTENT_TYPE_Handshake:
andrewboyson 2:82268409e83f 161 {
andrewboyson 2:82268409e83f 162 handleHandshake(length, pRequestStream + 5, pState);
andrewboyson 2:82268409e83f 163 return;
andrewboyson 2:82268409e83f 164 }
andrewboyson 2:82268409e83f 165 case TLS_CONTENT_TYPE_ALERT:
andrewboyson 2:82268409e83f 166 {
andrewboyson 2:82268409e83f 167 handleAlert(length, pRequestStream + 5);
andrewboyson 2:82268409e83f 168 return;
andrewboyson 2:82268409e83f 169 }
andrewboyson 2:82268409e83f 170 case TLS_CONTENT_TYPE_Application:
andrewboyson 2:82268409e83f 171 {
andrewboyson 2:82268409e83f 172 handleApplication(length, pRequestStream + 5);
andrewboyson 2:82268409e83f 173 pState->toDo = DO_APPLICATION;
andrewboyson 2:82268409e83f 174 return;
andrewboyson 2:82268409e83f 175 }
andrewboyson 2:82268409e83f 176
andrewboyson 2:82268409e83f 177 default:
andrewboyson 2:82268409e83f 178 Log("TLS - untreated content type "); TlsLogContentType(contentType); Log("\r\n");
andrewboyson 2:82268409e83f 179 pState->toDo = DO_WAIT_CLIENT_HELLO;
andrewboyson 2:82268409e83f 180 return;
andrewboyson 2:82268409e83f 181 }
andrewboyson 2:82268409e83f 182 }