tncc.c revision 8d520ff1dc2da35cdca849e982051b86468016d8
18d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* 28d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * EAP-TNC - TNCC (IF-IMC and IF-TNCCS) 38d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Copyright (c) 2007, Jouni Malinen <j@w1.fi> 48d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 58d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This program is free software; you can redistribute it and/or modify 68d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * it under the terms of the GNU General Public License version 2 as 78d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * published by the Free Software Foundation. 88d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 98d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Alternatively, this software may be distributed under the terms of BSD 108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * license. 118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * See README and COPYING for more details. 138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "includes.h" 168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifndef CONFIG_NATIVE_WINDOWS 178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include <dlfcn.h> 188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NATIVE_WINDOWS */ 198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "common.h" 218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "base64.h" 228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "tncc.h" 238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "eap_common/eap_tlv_common.h" 248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "eap_common/eap_defs.h" 258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef UNICODE 288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TSTR "%S" 298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* UNICODE */ 308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TSTR "%s" 318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* UNICODE */ 328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONFIG_FILE "/etc/tnc_config" 358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_WINREG_PATH TEXT("SOFTWARE\\Trusted Computing Group\\TNC\\IMCs") 368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define IF_TNCCS_START \ 378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"<?xml version=\"1.0\"?>\n" \ 388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"<TNCCS-Batch BatchId=\"%d\" Recipient=\"TNCS\" " \ 398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"xmlns=\"http://www.trustedcomputinggroup.org/IWG/TNC/1_0/IF_TNCCS#\" " \ 408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" " \ 418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"xsi:schemaLocation=\"http://www.trustedcomputinggroup.org/IWG/TNC/1_0/" \ 428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt"IF_TNCCS# https://www.trustedcomputinggroup.org/XML/SCHEMA/TNCCS_1.0.xsd\">\n" 438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define IF_TNCCS_END "\n</TNCCS-Batch>" 448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* TNC IF-IMC */ 468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef unsigned long TNC_UInt32; 488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef unsigned char *TNC_BufferReference; 498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_IMCID; 518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_ConnectionID; 528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_ConnectionState; 538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_RetryReason; 548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_MessageType; 558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_MessageType *TNC_MessageTypeList; 568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_VendorID; 578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_MessageSubtype; 588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_Version; 598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_UInt32 TNC_Result; 608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidttypedef TNC_Result (*TNC_TNCC_BindFunctionPointer)( 628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *functionName, 648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt void **pOutfunctionPointer); 658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_SUCCESS 0 678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_NOT_INITIALIZED 1 688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_ALREADY_INITIALIZED 2 698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_NO_COMMON_VERSION 3 708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_CANT_RETRY 4 718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_WONT_RETRY 5 728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_INVALID_PARAMETER 6 738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_CANT_RESPOND 7 748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_ILLEGAL_OPERATION 8 758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_OTHER 9 768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_RESULT_FATAL 10 778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONNECTION_STATE_CREATE 0 798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONNECTION_STATE_HANDSHAKE 1 808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONNECTION_STATE_ACCESS_ALLOWED 2 818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONNECTION_STATE_ACCESS_ISOLATED 3 828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONNECTION_STATE_ACCESS_NONE 4 838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_CONNECTION_STATE_DELETE 5 848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_IFIMC_VERSION_1 1 868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_VENDORID_ANY ((TNC_VendorID) 0xffffff) 888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_SUBTYPE_ANY ((TNC_MessageSubtype) 0xff) 898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* TNCC-TNCS Message Types */ 918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_TNCCS_RECOMMENDATION 0x00000001 928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_TNCCS_ERROR 0x00000002 938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_TNCCS_PREFERREDLANGUAGE 0x00000003 948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_TNCCS_REASONSTRINGS 0x00000004 958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* IF-TNCCS-SOH - SSoH and SSoHR Attributes */ 988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtenum { 998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_MACHINE_INVENTORY = 1, 1008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_QUARANTINE_STATE = 2, 1018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_PACKET_INFO = 3, 1028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_SYSTEMGENERATED_IDS = 4, 1038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_MACHINENAME = 5, 1048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_CORRELATIONID = 6, 1058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_INSTALLED_SHVS = 7, 1068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt SSOH_MS_MACHINE_INVENTORY_EX = 8 1078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt}; 1088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct tnc_if_imc { 1108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *next; 1118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *name; 1128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *path; 1138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt void *dlhandle; /* from dlopen() */ 1148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID; 1158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID; 1168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_MessageTypeList supported_types; 1178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t num_supported_types; 1188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 *imc_send; 1198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t imc_send_len; 1208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Functions implemented by IMCs (with TNC_IMC_ prefix) */ 1228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*Initialize)( 1238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Version minVersion, 1258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Version maxVersion, 1268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Version *pOutActualVersion); 1278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*NotifyConnectionChange)( 1288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID, 1308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionState newState); 1318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*BeginHandshake)( 1328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID); 1348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*ReceiveMessage)( 1358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID, 1378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_BufferReference messageBuffer, 1388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_UInt32 messageLength, 1398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_MessageType messageType); 1408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*BatchEnding)( 1418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID); 1438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*Terminate)(TNC_IMCID imcID); 1448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result (*ProvideBindFunction)( 1458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_TNCC_BindFunctionPointer bindFunction); 1478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt}; 1488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct tncc_data { 1508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 1518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int last_batchid; 1528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt}; 1538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#define TNC_MAX_IMC_ID 10 1558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic struct tnc_if_imc *tnc_imc[TNC_MAX_IMC_ID] = { NULL }; 1568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* TNCC functions that IMCs can call */ 1598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1608d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTNC_Result TNC_TNCC_ReportMessageTypes( 1618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_MessageTypeList supportedTypes, 1638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_UInt32 typeCount) 1648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_UInt32 i; 1668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 1678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_TNCC_ReportMessageTypes(imcID=%lu " 1698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "typeCount=%lu)", 1708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) imcID, (unsigned long) typeCount); 1718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < typeCount; i++) { 1738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: supportedTypes[%lu] = %lu", 1748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt i, supportedTypes[i]); 1758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imcID >= TNC_MAX_IMC_ID || tnc_imc[imcID] == NULL) 1788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_INVALID_PARAMETER; 1798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = tnc_imc[imcID]; 1818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->supported_types); 1828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->supported_types = 1838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_malloc(typeCount * sizeof(TNC_MessageType)); 1848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->supported_types == NULL) 1858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_FATAL; 1868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(imc->supported_types, supportedTypes, 1878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt typeCount * sizeof(TNC_MessageType)); 1888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->num_supported_types = typeCount; 1898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_SUCCESS; 1918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1948d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTNC_Result TNC_TNCC_SendMessage( 1958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 1968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID, 1978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_BufferReference message, 1988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_UInt32 messageLength, 1998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_MessageType messageType) 2008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 2028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned char *b64; 2038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t b64len; 2048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_TNCC_SendMessage(imcID=%lu " 2068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "connectionID=%lu messageType=%lu)", 2078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imcID, connectionID, messageType); 2088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump_ascii(MSG_DEBUG, "TNC: TNC_TNCC_SendMessage", 2098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt message, messageLength); 2108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imcID >= TNC_MAX_IMC_ID || tnc_imc[imcID] == NULL) 2128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_INVALID_PARAMETER; 2138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt b64 = base64_encode(message, messageLength, &b64len); 2158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (b64 == NULL) 2168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_FATAL; 2178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = tnc_imc[imcID]; 2198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->imc_send); 2208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send_len = 0; 2218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send = os_zalloc(b64len + 100); 2228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->imc_send == NULL) { 2238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(b64); 2248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_OTHER; 2258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send_len = 2288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_snprintf((char *) imc->imc_send, b64len + 100, 2298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "<IMC-IMV-Message><Type>%08X</Type>" 2308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "<Base64>%s</Base64></IMC-IMV-Message>", 2318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned int) messageType, b64); 2328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(b64); 2348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_SUCCESS; 2368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2398d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTNC_Result TNC_TNCC_RequestHandshakeRetry( 2408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 2418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionID connectionID, 2428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_RetryReason reason) 2438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_TNCC_RequestHandshakeRetry"); 2458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imcID >= TNC_MAX_IMC_ID || tnc_imc[imcID] == NULL) 2478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_INVALID_PARAMETER; 2488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 2508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * TODO: trigger a call to eapol_sm_request_reauth(). This would 2518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * require that the IMC continues to be loaded in memory afer 2528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * authentication.. 2538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_SUCCESS; 2568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2598d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTNC_Result TNC_9048_LogMessage(TNC_IMCID imcID, TNC_UInt32 severity, 2608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *message) 2618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_9048_LogMessage(imcID=%lu " 2638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "severity==%lu message='%s')", 2648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imcID, severity, message); 2658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_SUCCESS; 2668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2698d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTNC_Result TNC_9048_UserMessage(TNC_IMCID imcID, TNC_ConnectionID connectionID, 2708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *message) 2718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_9048_UserMessage(imcID=%lu " 2738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "connectionID==%lu message='%s')", 2748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imcID, connectionID, message); 2758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_SUCCESS; 2768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2798d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTNC_Result TNC_TNCC_BindFunction( 2808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IMCID imcID, 2818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *functionName, 2828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt void **pOutfunctionPointer) 2838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_TNCC_BindFunction(imcID=%lu, " 2858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "functionName='%s')", (unsigned long) imcID, functionName); 2868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imcID >= TNC_MAX_IMC_ID || tnc_imc[imcID] == NULL) 2888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_INVALID_PARAMETER; 2898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pOutfunctionPointer == NULL) 2918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_INVALID_PARAMETER; 2928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strcmp(functionName, "TNC_TNCC_ReportMessageTypes") == 0) 2948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pOutfunctionPointer = TNC_TNCC_ReportMessageTypes; 2958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (os_strcmp(functionName, "TNC_TNCC_SendMessage") == 0) 2968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pOutfunctionPointer = TNC_TNCC_SendMessage; 2978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (os_strcmp(functionName, "TNC_TNCC_RequestHandshakeRetry") == 2988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 0) 2998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pOutfunctionPointer = TNC_TNCC_RequestHandshakeRetry; 3008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (os_strcmp(functionName, "TNC_9048_LogMessage") == 0) 3018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pOutfunctionPointer = TNC_9048_LogMessage; 3028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (os_strcmp(functionName, "TNC_9048_UserMessage") == 0) 3038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pOutfunctionPointer = TNC_9048_UserMessage; 3048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 3058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pOutfunctionPointer = NULL; 3068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNC_RESULT_SUCCESS; 3088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void * tncc_get_sym(void *handle, char *func) 3128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt void *fptr; 3148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_NATIVE_WINDOWS 3168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef _WIN32_WCE 3178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt fptr = GetProcAddressA(handle, func); 3188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* _WIN32_WCE */ 3198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt fptr = GetProcAddress(handle, func); 3208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* _WIN32_WCE */ 3218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* CONFIG_NATIVE_WINDOWS */ 3228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt fptr = dlsym(handle, func); 3238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NATIVE_WINDOWS */ 3248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return fptr; 3268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_imc_resolve_funcs(struct tnc_if_imc *imc) 3308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt void *handle = imc->dlhandle; 3328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Mandatory IMC functions */ 3348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->Initialize = tncc_get_sym(handle, "TNC_IMC_Initialize"); 3358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->Initialize == NULL) { 3368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: IMC does not export " 3378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "TNC_IMC_Initialize"); 3388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 3398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->BeginHandshake = tncc_get_sym(handle, "TNC_IMC_BeginHandshake"); 3428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->BeginHandshake == NULL) { 3438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: IMC does not export " 3448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "TNC_IMC_BeginHandshake"); 3458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 3468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->ProvideBindFunction = 3498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_get_sym(handle, "TNC_IMC_ProvideBindFunction"); 3508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->ProvideBindFunction == NULL) { 3518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: IMC does not export " 3528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "TNC_IMC_ProvideBindFunction"); 3538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 3548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Optional IMC functions */ 3578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->NotifyConnectionChange = 3588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_get_sym(handle, "TNC_IMC_NotifyConnectionChange"); 3598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->ReceiveMessage = tncc_get_sym(handle, "TNC_IMC_ReceiveMessage"); 3608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->BatchEnding = tncc_get_sym(handle, "TNC_IMC_BatchEnding"); 3618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->Terminate = tncc_get_sym(handle, "TNC_IMC_Terminate"); 3628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 3648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_imc_initialize(struct tnc_if_imc *imc) 3688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result res; 3708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Version imc_ver; 3718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Calling TNC_IMC_Initialize for IMC '%s'", 3738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name); 3748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = imc->Initialize(imc->imcID, TNC_IFIMC_VERSION_1, 3758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_IFIMC_VERSION_1, &imc_ver); 3768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_IMC_Initialize: res=%lu imc_ver=%lu", 3778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) res, (unsigned long) imc_ver); 3788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return res == TNC_RESULT_SUCCESS ? 0 : -1; 3808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_imc_terminate(struct tnc_if_imc *imc) 3848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result res; 3868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->Terminate == NULL) 3888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 3898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Calling TNC_IMC_Terminate for IMC '%s'", 3918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name); 3928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = imc->Terminate(imc->imcID); 3938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_IMC_Terminate: %lu", 3948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) res); 3958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return res == TNC_RESULT_SUCCESS ? 0 : -1; 3978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_imc_provide_bind_function(struct tnc_if_imc *imc) 4018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 4028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result res; 4038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Calling TNC_IMC_ProvideBindFunction for " 4058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "IMC '%s'", imc->name); 4068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = imc->ProvideBindFunction(imc->imcID, TNC_TNCC_BindFunction); 4078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_IMC_ProvideBindFunction: res=%lu", 4088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) res); 4098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return res == TNC_RESULT_SUCCESS ? 0 : -1; 4118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 4128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_imc_notify_connection_change(struct tnc_if_imc *imc, 4158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionState state) 4168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 4178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result res; 4188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->NotifyConnectionChange == NULL) 4208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 4218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Calling TNC_IMC_NotifyConnectionChange(%d)" 4238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt " for IMC '%s'", (int) state, imc->name); 4248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = imc->NotifyConnectionChange(imc->imcID, imc->connectionID, 4258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt state); 4268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_IMC_NotifyConnectionChange: %lu", 4278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) res); 4288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return res == TNC_RESULT_SUCCESS ? 0 : -1; 4308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 4318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_imc_begin_handshake(struct tnc_if_imc *imc) 4348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 4358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result res; 4368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Calling TNC_IMC_BeginHandshake for IMC " 4388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "'%s'", imc->name); 4398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = imc->BeginHandshake(imc->imcID, imc->connectionID); 4408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNC_IMC_BeginHandshake: %lu", 4418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) res); 4428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return res == TNC_RESULT_SUCCESS ? 0 : -1; 4448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 4458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_load_imc(struct tnc_if_imc *imc) 4488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 4498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->path == NULL) { 4508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: No IMC configured"); 4518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 4528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Opening IMC: %s (%s)", 4558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name, imc->path); 4568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_NATIVE_WINDOWS 4578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef UNICODE 4588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt { 4598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TCHAR *lib = wpa_strdup_tchar(imc->path); 4608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (lib == NULL) 4618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 4628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->dlhandle = LoadLibrary(lib); 4638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(lib); 4648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* UNICODE */ 4668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->dlhandle = LoadLibrary(imc->path); 4678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* UNICODE */ 4688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->dlhandle == NULL) { 4698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Failed to open IMC '%s' (%s): %d", 4708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name, imc->path, (int) GetLastError()); 4718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 4728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* CONFIG_NATIVE_WINDOWS */ 4748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->dlhandle = dlopen(imc->path, RTLD_LAZY); 4758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->dlhandle == NULL) { 4768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Failed to open IMC '%s' (%s): %s", 4778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name, imc->path, dlerror()); 4788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 4798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NATIVE_WINDOWS */ 4818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_imc_resolve_funcs(imc) < 0) { 4838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Failed to resolve IMC functions"); 4848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 4858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_imc_initialize(imc) < 0 || 4888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_imc_provide_bind_function(imc) < 0) { 4898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Failed to initialize IMC"); 4908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 4918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 4928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 4948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 4958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 4978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void tncc_unload_imc(struct tnc_if_imc *imc) 4988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 4998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_imc_terminate(imc); 5008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tnc_imc[imc->imcID] = NULL; 5018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->dlhandle) { 5038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_NATIVE_WINDOWS 5048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt FreeLibrary(imc->dlhandle); 5058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* CONFIG_NATIVE_WINDOWS */ 5068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt dlclose(imc->dlhandle); 5078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NATIVE_WINDOWS */ 5088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 5098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->name); 5108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->path); 5118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->supported_types); 5128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->imc_send); 5138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_supported_type(struct tnc_if_imc *imc, unsigned int type) 5178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 5188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t i; 5198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int vendor, subtype; 5208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc == NULL || imc->supported_types == NULL) 5228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 5238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt vendor = type >> 8; 5258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt subtype = type & 0xff; 5268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < imc->num_supported_types; i++) { 5288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int svendor, ssubtype; 5298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt svendor = imc->supported_types[i] >> 8; 5308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssubtype = imc->supported_types[i] & 0xff; 5318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if ((vendor == svendor || svendor == TNC_VENDORID_ANY) && 5328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (subtype == ssubtype || ssubtype == TNC_SUBTYPE_ANY)) 5338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 1; 5348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 5358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 5378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void tncc_send_to_imcs(struct tncc_data *tncc, unsigned int type, 5418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *msg, size_t len) 5428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 5438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 5448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_Result res; 5458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump_ascii(MSG_MSGDUMP, "TNC: Message to IMC(s)", msg, len); 5478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (imc = tncc->imc; imc; imc = imc->next) { 5498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->ReceiveMessage == NULL || 5508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt !tncc_supported_type(imc, type)) 5518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 5528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Call ReceiveMessage for IMC '%s'", 5548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name); 5558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = imc->ReceiveMessage(imc->imcID, imc->connectionID, 5568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (TNC_BufferReference) msg, len, 5578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt type); 5588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: ReceiveMessage: %lu", 5598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned long) res); 5608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 5618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid tncc_init_connection(struct tncc_data *tncc) 5658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 5668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 5678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (imc = tncc->imc; imc; imc = imc->next) { 5698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_imc_notify_connection_change( 5708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc, TNC_CONNECTION_STATE_CREATE); 5718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_imc_notify_connection_change( 5728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc, TNC_CONNECTION_STATE_HANDSHAKE); 5738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->imc_send); 5758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send = NULL; 5768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send_len = 0; 5778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_imc_begin_handshake(imc); 5798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 5808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtsize_t tncc_total_send_len(struct tncc_data *tncc) 5848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 5858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 5868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t len = 0; 5888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (imc = tncc->imc; imc; imc = imc->next) 5898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt len += imc->imc_send_len; 5908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return len; 5918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 5928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtu8 * tncc_copy_send_buf(struct tncc_data *tncc, u8 *pos) 5958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 5968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 5978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 5988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (imc = tncc->imc; imc; imc = imc->next) { 5998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc->imc_send == NULL) 6008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 6018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(pos, imc->imc_send, imc->imc_send_len); 6038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += imc->imc_send_len; 6048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->imc_send); 6058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send = NULL; 6068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imc_send_len = 0; 6078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 6088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return pos; 6108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtchar * tncc_if_tnccs_start(struct tncc_data *tncc) 6148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *buf = os_malloc(1000); 6168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (buf == NULL) 6178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 6188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc->last_batchid++; 6198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_snprintf(buf, 1000, IF_TNCCS_START, tncc->last_batchid); 6208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return buf; 6218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtchar * tncc_if_tnccs_end(void) 6258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *buf = os_malloc(100); 6278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (buf == NULL) 6288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 6298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_snprintf(buf, 100, IF_TNCCS_END); 6308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return buf; 6318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic void tncc_notify_recommendation(struct tncc_data *tncc, 6358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt enum tncc_process_res res) 6368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TNC_ConnectionState state; 6388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 6398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt switch (res) { 6418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case TNCCS_RECOMMENDATION_ALLOW: 6428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt state = TNC_CONNECTION_STATE_ACCESS_ALLOWED; 6438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 6448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case TNCCS_RECOMMENDATION_NONE: 6458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt state = TNC_CONNECTION_STATE_ACCESS_NONE; 6468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 6478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt case TNCCS_RECOMMENDATION_ISOLATE: 6488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt state = TNC_CONNECTION_STATE_ACCESS_ISOLATED; 6498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 6508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt default: 6518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt state = TNC_CONNECTION_STATE_ACCESS_NONE; 6528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 6538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 6548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (imc = tncc->imc; imc; imc = imc->next) 6568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_imc_notify_connection_change(imc, state); 6578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_get_type(char *start, unsigned int *type) 6618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *pos = os_strstr(start, "<Type>"); 6638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) 6648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 6658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 6; 6668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *type = strtoul(pos, NULL, 16); 6678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 6688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic unsigned char * tncc_get_base64(char *start, size_t *decoded_len) 6728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *pos, *pos2; 6748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned char *decoded; 6758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(start, "<Base64>"); 6778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) 6788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 6798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 8; 6818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos2 = os_strstr(pos, "</Base64>"); 6828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos2 == NULL) 6838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 6848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pos2 = '\0'; 6858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt decoded = base64_decode((unsigned char *) pos, os_strlen(pos), 6878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt decoded_len); 6888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pos2 = '<'; 6898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (decoded == NULL) { 6908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Failed to decode Base64 data"); 6918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 6928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return decoded; 6948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 6958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 6978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic enum tncc_process_res tncc_get_recommendation(char *start) 6988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 6998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *pos, *pos2, saved; 7008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int recom; 7018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(start, "<TNCCS-Recommendation "); 7038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) 7048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_RECOMMENDATION_ERROR; 7058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 21; 7078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(pos, " type="); 7088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) 7098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_RECOMMENDATION_ERROR; 7108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 6; 7118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (*pos == '"') 7138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 7148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos2 = pos; 7168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*pos2 != '\0' && *pos2 != '"' && *pos2 != '>') 7178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos2++; 7188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (*pos2 == '\0') 7208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_RECOMMENDATION_ERROR; 7218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt saved = *pos2; 7238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pos2 = '\0'; 7248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNCCS-Recommendation: '%s'", pos); 7258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt recom = TNCCS_RECOMMENDATION_ERROR; 7278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strcmp(pos, "allow") == 0) 7288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt recom = TNCCS_RECOMMENDATION_ALLOW; 7298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (os_strcmp(pos, "none") == 0) 7308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt recom = TNCCS_RECOMMENDATION_NONE; 7318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else if (os_strcmp(pos, "isolate") == 0) 7328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt recom = TNCCS_RECOMMENDATION_ISOLATE; 7338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pos2 = saved; 7358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return recom; 7378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 7388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtenum tncc_process_res tncc_process_if_tnccs(struct tncc_data *tncc, 7418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *msg, size_t len) 7428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 7438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *buf, *start, *end, *pos, *pos2, *payload; 7448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int batch_id; 7458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned char *decoded; 7468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t decoded_len; 7478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt enum tncc_process_res res = TNCCS_PROCESS_OK_NO_RECOMMENDATION; 7488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int recommendation_msg = 0; 7498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt buf = os_malloc(len + 1); 7518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (buf == NULL) 7528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_PROCESS_ERROR; 7538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(buf, msg, len); 7558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt buf[len] = '\0'; 7568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = os_strstr(buf, "<TNCCS-Batch "); 7578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end = os_strstr(buf, "</TNCCS-Batch>"); 7588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (start == NULL || end == NULL || start > end) { 7598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(buf); 7608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_PROCESS_ERROR; 7618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start += 13; 7648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*start == ' ') 7658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start++; 7668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *end = '\0'; 7678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(start, "BatchId="); 7698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) { 7708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(buf); 7718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_PROCESS_ERROR; 7728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 8; 7758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (*pos == '"') 7768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 7778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt batch_id = atoi(pos); 7788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Received IF-TNCCS BatchId=%u", 7798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt batch_id); 7808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (batch_id != tncc->last_batchid + 1) { 7818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Unexpected IF-TNCCS BatchId " 7828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "%u (expected %u)", 7838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt batch_id, tncc->last_batchid + 1); 7848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(buf); 7858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_PROCESS_ERROR; 7868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc->last_batchid = batch_id; 7888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*pos != '\0' && *pos != '>') 7908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 7918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (*pos == '\0') { 7928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(buf); 7938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return TNCCS_PROCESS_ERROR; 7948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 7958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 7968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt payload = start; 7978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 7988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 7998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <IMC-IMV-Message> 8008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <Type>01234567</Type> 8018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <Base64>foo==</Base64> 8028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * </IMC-IMV-Message> 8038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 8048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*start) { 8068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *endpos; 8078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int type; 8088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(start, "<IMC-IMV-Message>"); 8108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) 8118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 8128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = pos + 17; 8138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end = os_strstr(start, "</IMC-IMV-Message>"); 8148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (end == NULL) 8158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 8168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *end = '\0'; 8178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt endpos = end; 8188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end += 18; 8198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_get_type(start, &type) < 0) { 8218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *endpos = '<'; 8228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 8238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 8248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: IMC-IMV-Message Type 0x%x", type); 8268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt decoded = tncc_get_base64(start, &decoded_len); 8288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (decoded == NULL) { 8298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *endpos = '<'; 8308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 8318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 8328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_send_to_imcs(tncc, type, decoded, decoded_len); 8358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(decoded); 8378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 8398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 8428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <TNCC-TNCS-Message> 8438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <Type>01234567</Type> 8448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <XML><TNCCS-Foo type="foo"></TNCCS-Foo></XML> 8458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <Base64>foo==</Base64> 8468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * </TNCC-TNCS-Message> 8478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 8488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = payload; 8508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*start) { 8518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt unsigned int type; 8528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *xml, *xmlend, *endpos; 8538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(start, "<TNCC-TNCS-Message>"); 8558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos == NULL) 8568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 8578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = pos + 19; 8588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end = os_strstr(start, "</TNCC-TNCS-Message>"); 8598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (end == NULL) 8608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 8618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *end = '\0'; 8628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt endpos = end; 8638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end += 20; 8648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_get_type(start, &type) < 0) { 8668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *endpos = '<'; 8678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 8688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 8698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: TNCC-TNCS-Message Type 0x%x", 8718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt type); 8728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Base64 OR XML */ 8748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt decoded = NULL; 8758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt xml = NULL; 8768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt xmlend = NULL; 8778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = os_strstr(start, "<XML>"); 8788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos) { 8798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 5; 8808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos2 = os_strstr(pos, "</XML>"); 8818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos2 == NULL) { 8828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *endpos = '<'; 8838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 8848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 8858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt xmlend = pos2; 8878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt xml = pos; 8888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 8898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt decoded = tncc_get_base64(start, &decoded_len); 8908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (decoded == NULL) { 8918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *endpos = '<'; 8928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 8938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 8948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 8968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 8978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (decoded) { 8988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump_ascii(MSG_MSGDUMP, 8998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "TNC: TNCC-TNCS-Message Base64", 9008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt decoded, decoded_len); 9018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(decoded); 9028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (xml) { 9058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump_ascii(MSG_MSGDUMP, 9068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "TNC: TNCC-TNCS-Message XML", 9078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned char *) xml, 9088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt xmlend - xml); 9098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (type == TNC_TNCCS_RECOMMENDATION && xml) { 9128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 9138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * <TNCCS-Recommendation type="allow"> 9148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * </TNCCS-Recommendation> 9158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 9168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *xmlend = '\0'; 9178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt res = tncc_get_recommendation(xml); 9188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *xmlend = '<'; 9198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt recommendation_msg = 1; 9208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt start = end; 9238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(buf); 9268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (recommendation_msg) 9288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_notify_recommendation(tncc, res); 9298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return res; 9318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 9328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_NATIVE_WINDOWS 9358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_read_config_reg(struct tncc_data *tncc, HKEY hive) 9368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 9378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt HKEY hk, hk2; 9388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt LONG ret; 9398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt DWORD i; 9408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc, *last; 9418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int j; 9428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last = tncc->imc; 9448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (last && last->next) 9458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last = last->next; 9468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = RegOpenKeyEx(hive, TNC_WINREG_PATH, 0, KEY_ENUMERATE_SUB_KEYS, 9488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt &hk); 9498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret != ERROR_SUCCESS) 9508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 9518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; ; i++) { 9538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TCHAR name[255], *val; 9548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt DWORD namelen, buflen; 9558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt namelen = 255; 9578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = RegEnumKeyEx(hk, i, name, &namelen, NULL, NULL, NULL, 9588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt NULL); 9598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret == ERROR_NO_MORE_ITEMS) 9618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 9628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret != ERROR_SUCCESS) { 9648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: RegEnumKeyEx failed: 0x%x", 9658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (unsigned int) ret); 9668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 9678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (namelen >= 255) 9708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt namelen = 255 - 1; 9718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt name[namelen] = '\0'; 9728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: IMC '" TSTR "'", name); 9748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = RegOpenKeyEx(hk, name, 0, KEY_QUERY_VALUE, &hk2); 9768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret != ERROR_SUCCESS) { 9778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "Could not open IMC key '" TSTR 9788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "'", name); 9798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 9808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = RegQueryValueEx(hk2, TEXT("Path"), NULL, NULL, NULL, 9838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt &buflen); 9848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret != ERROR_SUCCESS) { 9858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Could not read Path from " 9868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "IMC key '" TSTR "'", name); 9878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt RegCloseKey(hk2); 9888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 9898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt val = os_malloc(buflen); 9928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (val == NULL) { 9938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt RegCloseKey(hk2); 9948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 9958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 9968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 9978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = RegQueryValueEx(hk2, TEXT("Path"), NULL, NULL, 9988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt (LPBYTE) val, &buflen); 9998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret != ERROR_SUCCESS) { 10008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(val); 10018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt RegCloseKey(hk2); 10028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 10038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt RegCloseKey(hk2); 10068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_unicode2ascii_inplace(val); 10088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: IMC Path '%s'", (char *) val); 10098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (j = 0; j < TNC_MAX_IMC_ID; j++) { 10118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tnc_imc[j] == NULL) 10128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 10138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (j >= TNC_MAX_IMC_ID) { 10158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Too many IMCs"); 10168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(val); 10178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt continue; 10188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = os_zalloc(sizeof(*imc)); 10218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc == NULL) { 10228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(val); 10238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 10248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imcID = j; 10278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_unicode2ascii_inplace(name); 10298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name = os_strdup((char *) name); 10308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->path = os_strdup((char *) val); 10318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(val); 10338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (last == NULL) 10358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc->imc = imc; 10368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 10378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last->next = imc; 10388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last = imc; 10398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tnc_imc[imc->imcID] = imc; 10418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt RegCloseKey(hk); 10448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 10468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 10478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_read_config(struct tncc_data *tncc) 10508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 10518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_read_config_reg(tncc, HKEY_LOCAL_MACHINE) < 0 || 10528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_read_config_reg(tncc, HKEY_CURRENT_USER) < 0) 10538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 10548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 10558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 10568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* CONFIG_NATIVE_WINDOWS */ 10588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic struct tnc_if_imc * tncc_parse_imc(char *start, char *end, int *error) 10608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 10618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 10628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *pos, *pos2; 10638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 10648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < TNC_MAX_IMC_ID; i++) { 10668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tnc_imc[i] == NULL) 10678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 10688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (i >= TNC_MAX_IMC_ID) { 10708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Too many IMCs"); 10718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 10728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = os_zalloc(sizeof(*imc)); 10758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc == NULL) { 10768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *error = 1; 10778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 10788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->imcID = i; 10818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = start; 10838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Configured IMC: %s", pos); 10848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos + 1 >= end || *pos != '"') { 10858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Ignoring invalid IMC line '%s' " 10868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "(no starting quotation mark)", start); 10878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc); 10888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 10898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 10908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 10918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 10928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos2 = pos; 10938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (pos2 < end && *pos2 != '"') 10948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos2++; 10958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos2 >= end) { 10968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Ignoring invalid IMC line '%s' " 10978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "(no ending quotation mark)", start); 10988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc); 10998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 11008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pos2 = '\0'; 11028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: Name: '%s'", pos); 11038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name = os_strdup(pos); 11048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = pos2 + 1; 11068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (pos >= end || *pos != ' ') { 11078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Ignoring invalid IMC line '%s' " 11088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "(no space after name)", start); 11098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc->name); 11108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(imc); 11118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 11128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 11158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: IMC file: '%s'", pos); 11168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->path = os_strdup(pos); 11178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tnc_imc[imc->imcID] = imc; 11188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return imc; 11208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 11218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int tncc_read_config(struct tncc_data *tncc) 11248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 11258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *config, *end, *pos, *line_end; 11268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t config_len; 11278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc, *last; 11288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last = NULL; 11308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt config = os_readfile(TNC_CONFIG_FILE, &config_len); 11328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (config == NULL) { 11338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Could not open TNC configuration " 11348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt "file '%s'", TNC_CONFIG_FILE); 11358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 11368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end = config + config_len; 11398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (pos = config; pos < end; pos = line_end + 1) { 11408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt line_end = pos; 11418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*line_end != '\n' && *line_end != '\r' && 11428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt line_end < end) 11438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt line_end++; 11448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *line_end = '\0'; 11458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strncmp(pos, "IMC ", 4) == 0) { 11478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int error = 0; 11488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = tncc_parse_imc(pos + 4, line_end, &error); 11508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (error) 11518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 11528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (imc) { 11538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (last == NULL) 11548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc->imc = imc; 11558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt else 11568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last->next = imc; 11578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt last = imc; 11588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(config); 11638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 11658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 11668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NATIVE_WINDOWS */ 11688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct tncc_data * tncc_init(void) 11718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 11728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tncc_data *tncc; 11738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc; 11748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc = os_zalloc(sizeof(*tncc)); 11768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc == NULL) 11778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 11788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TODO: 11808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * move loading and Initialize() to a location that is not 11818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * re-initialized for every EAP-TNC session (?) 11828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 11838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_read_config(tncc) < 0) { 11858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Failed to read TNC configuration"); 11868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt goto failed; 11878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (imc = tncc->imc; imc; imc = imc->next) { 11908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (tncc_load_imc(imc)) { 11918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "TNC: Failed to load IMC '%s'", 11928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc->name); 11938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt goto failed; 11948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 11968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return tncc; 11988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 11998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtfailed: 12008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_deinit(tncc); 12018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 12028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 12038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid tncc_deinit(struct tncc_data *tncc) 12068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 12078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct tnc_if_imc *imc, *prev; 12088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = tncc->imc; 12108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (imc) { 12118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tncc_unload_imc(imc); 12128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt prev = imc; 12148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt imc = imc->next; 12158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(prev); 12168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 12178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_free(tncc); 12198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 12208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic struct wpabuf * tncc_build_soh(int ver) 12238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 12248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct wpabuf *buf; 12258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 *tlv_len, *tlv_len2, *outer_len, *inner_len, *ssoh_len, *end; 12268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 correlation_id[24]; 12278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TODO: get correct name */ 12288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *machinename = "wpa_supplicant@w1.fi"; 12298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_get_random(correlation_id, sizeof(correlation_id))) 12318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 12328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump(MSG_DEBUG, "TNC: SoH Correlation ID", 12338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt correlation_id, sizeof(correlation_id)); 12348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt buf = wpabuf_alloc(200); 12368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (buf == NULL) 12378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 12388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Vendor-Specific TLV (Microsoft) - SoH */ 12408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, EAP_TLV_VENDOR_SPECIFIC_TLV); /* TLV Type */ 12418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tlv_len = wpabuf_put(buf, 2); /* Length */ 12428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, EAP_VENDOR_MICROSOFT); /* Vendor_Id */ 12438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 0x01); /* TLV Type - SoH TLV */ 12448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tlv_len2 = wpabuf_put(buf, 2); /* Length */ 12458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* SoH Header */ 12478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, EAP_TLV_VENDOR_SPECIFIC_TLV); /* Outer Type */ 12488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt outer_len = wpabuf_put(buf, 2); 12498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, EAP_VENDOR_MICROSOFT); /* IANA SMI Code */ 12508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, ver); /* Inner Type */ 12518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt inner_len = wpabuf_put(buf, 2); 12528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ver == 2) { 12548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* SoH Mode Sub-Header */ 12558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Outer Type */ 12568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, EAP_TLV_VENDOR_SPECIFIC_TLV); 12578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 4 + 24 + 1 + 1); /* Length */ 12588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, EAP_VENDOR_MICROSOFT); /* IANA SMI Code */ 12598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Value: */ 12608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_data(buf, correlation_id, sizeof(correlation_id)); 12618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, 0x01); /* Intent Flag - Request */ 12628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, 0x00); /* Content-Type Flag */ 12638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 12648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* SSoH TLV */ 12668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* System-Health-Id */ 12678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 0x0002); /* Type */ 12688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 4); /* Length */ 12698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 79616); 12708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Vendor-Specific Attribute */ 12718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, EAP_TLV_VENDOR_SPECIFIC_TLV); 12728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssoh_len = wpabuf_put(buf, 2); 12738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, EAP_VENDOR_MICROSOFT); /* IANA SMI Code */ 12748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MS-Packet-Info */ 12768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, SSOH_MS_PACKET_INFO); 12778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Note: IF-TNCCS-SOH v1.0 r8 claims this field to be: 12788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Reserved(4 bits) r(1 bit) Vers(3 bits), but Windows XP 12798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * SP3 seems to be sending 0x11 for SSoH, i.e., r(request/response) bit 12808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * would not be in the specified location. 12818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * [MS-SOH] 4.0.2: Reserved(3 bits) r(1 bit) Vers(4 bits) 12828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 12838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, 0x11); /* r=request, vers=1 */ 12848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MS-Machine-Inventory */ 12868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TODO: get correct values; 0 = not applicable for OS */ 12878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, SSOH_MS_MACHINE_INVENTORY); 12888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 0); /* osVersionMajor */ 12898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 0); /* osVersionMinor */ 12908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 0); /* osVersionBuild */ 12918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 0); /* spVersionMajor */ 12928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 0); /* spVersionMinor */ 12938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 0); /* procArch */ 12948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 12958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MS-MachineName */ 12968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, SSOH_MS_MACHINENAME); 12978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, os_strlen(machinename) + 1); 12988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_data(buf, machinename, os_strlen(machinename) + 1); 12998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MS-CorrelationId */ 13018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, SSOH_MS_CORRELATIONID); 13028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_data(buf, correlation_id, sizeof(correlation_id)); 13038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MS-Quarantine-State */ 13058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, SSOH_MS_QUARANTINE_STATE); 13068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 1); /* Flags: ExtState=0, f=0, qState=1 */ 13078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 0xffffffff); /* ProbTime (hi) */ 13088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 0xffffffff); /* ProbTime (lo) */ 13098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be16(buf, 1); /* urlLenInBytes */ 13108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, 0); /* null termination for the url */ 13118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* MS-Machine-Inventory-Ex */ 13138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, SSOH_MS_MACHINE_INVENTORY_EX); 13148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_be32(buf, 0); /* Reserved 13158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * (note: Windows XP SP3 uses 0xdecafbad) */ 13168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpabuf_put_u8(buf, 1); /* ProductType: Client */ 13178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Update SSoH Length */ 13198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end = wpabuf_put(buf, 0); 13208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_PUT_BE16(ssoh_len, end - ssoh_len - 2); 13218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TODO: SoHReportEntry TLV (zero or more) */ 13238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Update length fields */ 13258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end = wpabuf_put(buf, 0); 13268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_PUT_BE16(tlv_len, end - tlv_len - 2); 13278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_PUT_BE16(tlv_len2, end - tlv_len2 - 2); 13288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_PUT_BE16(outer_len, end - outer_len - 2); 13298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt WPA_PUT_BE16(inner_len, end - inner_len - 2); 13308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return buf; 13328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 13338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstruct wpabuf * tncc_process_soh_request(int ver, const u8 *data, size_t len) 13368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 13378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const u8 *pos; 13388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_hexdump(MSG_DEBUG, "TNC: SoH Request", data, len); 13408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (len < 12) 13428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 13438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* SoH Request */ 13458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos = data; 13468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TLV Type */ 13488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (WPA_GET_BE16(pos) != EAP_TLV_VENDOR_SPECIFIC_TLV) 13498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 13508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 2; 13518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Length */ 13538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (WPA_GET_BE16(pos) < 8) 13548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 13558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 2; 13568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Vendor_Id */ 13588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (WPA_GET_BE32(pos) != EAP_VENDOR_MICROSOFT) 13598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 13608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += 4; 13618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* TLV Type */ 13638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (WPA_GET_BE16(pos) != 0x02 /* SoH request TLV */) 13648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 13658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_DEBUG, "TNC: SoH Request TLV received"); 13678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 13688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return tncc_build_soh(2); 13698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1370