Merge pull request #305 from nsacyber/client-eventlog

[#238] Client eventlog upload
This commit is contained in:
Cyrus 2020-10-14 10:46:37 -04:00 committed by GitHub
commit 9d793f50e6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 140 additions and 20 deletions

View File

@ -8,8 +8,11 @@ import hirs.attestationca.exceptions.IdentityProcessingException;
import hirs.attestationca.exceptions.UnexpectedServerException;
import hirs.attestationca.service.SupplyChainValidationService;
import hirs.data.persist.AppraisalStatus;
import hirs.data.persist.BaseReferenceManifest;
import hirs.data.persist.Device;
import hirs.data.persist.DeviceInfoReport;
import hirs.data.persist.ReferenceManifest;
import hirs.data.persist.SupportReferenceManifest;
import hirs.data.persist.info.FirmwareInfo;
import hirs.data.persist.info.HardwareInfo;
import hirs.data.persist.info.NetworkInfo;
@ -36,6 +39,7 @@ import hirs.structs.elements.tpm.IdentityProof;
import hirs.structs.elements.tpm.IdentityRequest;
import hirs.structs.elements.tpm.SymmetricKey;
import hirs.structs.elements.tpm.SymmetricKeyParams;
import hirs.tpm.eventlog.TCGEventLog;
import hirs.utils.HexUtils;
import org.apache.commons.codec.binary.Hex;
import org.apache.commons.lang3.ArrayUtils;
@ -719,10 +723,64 @@ public abstract class AbstractAttestationCertificateAuthority
hwProto.getProductVersion(), hwProto.getSystemSerialNumber(),
firstChassisSerialNumber, firstBaseboardSerialNumber);
if (dv.getPcrslist() != null && !dv.getPcrslist().isEmpty()) {
if (dv.hasPcrslist()) {
this.pcrValues = dv.getPcrslist().toStringUtf8();
}
// check for RIM Base and Support files, if they don't exists in the database, load them
String clientName;
if (dv.hasLogfile()) {
try {
ReferenceManifest support = ReferenceManifest.select(referenceManifestManager)
.includeArchived()
.byHashCode(dv.getSwidfile().hashCode())
.getRIM();
if (support == null) {
clientName = String.format("%s_%s.rimel",
dv.getHw().getManufacturer(),
dv.getHw().getProductName());
this.referenceManifestManager.save(
new SupportReferenceManifest(clientName,
dv.getLogfile().toByteArray()));
} else {
LOG.info("Client provided Support RIM already loaded in database.");
}
TCGEventLog tcgEventLog = new TCGEventLog(dv.getLogfile().toByteArray());
LOG.error(tcgEventLog.toString(true, true, true));
} catch (CertificateException cEx) {
LOG.error(cEx);
} catch (NoSuchAlgorithmException noSaEx) {
LOG.error(noSaEx);
} catch (IOException ioEx) {
LOG.error(ioEx);
}
}
if (dv.hasSwidfile()) {
try {
ReferenceManifest baseRim = ReferenceManifest.select(referenceManifestManager)
.includeArchived()
.byHashCode(dv.getSwidfile().hashCode())
.getRIM();
if (baseRim == null) {
clientName = String.format("%s_%s.swidtag",
dv.getHw().getManufacturer(),
dv.getHw().getProductName());
this.referenceManifestManager.save(
new BaseReferenceManifest(clientName,
dv.getSwidfile().toByteArray()));
} else {
LOG.info("Client provided Base RIM already loaded in database.");
}
} catch (IOException ioEx) {
LOG.error(ioEx);
}
}
if (dv.hasLivelog()) {
LOG.error("Live Log Exists");
}
// Get TPM info, currently unimplemented
TPMInfo tpm;
try {

View File

@ -59,7 +59,7 @@ public class ReferenceManifestPageController
extends PageController<NoPageParams> {
private static final String BIOS_RELEASE_DATE_FORMAT = "yyyy-MM-dd";
private static final String LOG_FILE_PATTERN = "([^\\s]+(\\.(?i)(rim|rimel|bin|log))$)";
private static final String LOG_FILE_PATTERN = "([^\\s]+(\\.(?i)(rimpcr|rimel|bin|log))$)";
private final BiosDateValidator biosValidator;
private final ReferenceManifestManager referenceManifestManager;

View File

@ -32,3 +32,7 @@ DEFAULT_SITE_CONFIG_FILE
echo "Set your site configuration manually in $HIRS_SITE_CONFIG, then run 'hirs-provisioner-tpm2 provision' to provision this system"
fi
ln -s -f /etc/hirs/provisioner/hirs-provisioner.sh /usr/sbin/hirs-provisioner
if ! [ -f "set_tcg_properties.sh" ]; then
sh ./set_tcg_properties.sh
fi

View File

@ -39,3 +39,24 @@ DEFAULT_SITE_CONFIG_FILE
echo "Set your site configuration manually in $HIRS_SITE_CONFIG, then run 'hirs-provisioner-tpm2 provision' to provision this system"
fi
ln -s -f /etc/hirs/provisioner/hirs-provisioner.sh /usr/sbin/hirs-provisioner
TCG_BOOT_FILE="/etc/hirs/tcg_boot.properties"
MAINFEST_DIRECTORY="/boot/tcg/manifest"
LOG_FILE_LOCATION="$MAINFEST_DIRECTORY/rim/"
TAG_FILE_LOCATION="$MAINFEST_DIRECTORY/swidtag/"
if [ ! -f "$TCG_BOOT_FILE" ]; then
touch "$TCG_BOOT_FILE"
fi
if [ -d "$LOG_FILE_LOCATION" ]; then
RIM_FILE=$(find "$LOG_FILE_LOCATION" -name '*.rimel' -or -name '*.bin' -or -name '*.rimpcr' -or -name '*.log')
echo "tcg.rim.file=$RIM_FILE" > "$TCG_BOOT_FILE"
fi
if [ -d "$TAG_FILE_LOCATION" ]; then
SWID_FILE=$(find "$TAG_FILE_LOCATION" -name '*.swidtag')
echo "tcg.swidtag.file=$SWID_FILE" >> "$TCG_BOOT_FILE"
fi
chmod -w "$TCG_BOOT_FILE"

View File

@ -243,4 +243,3 @@ hirs::pb::OsInfo DeviceInfoCollector::collectOsInfo() {
return info;
}

View File

@ -58,6 +58,9 @@ message DeviceInfo {
required NetworkInfo nw = 3;
required OsInfo os = 4;
optional bytes pcrslist = 5;
optional bytes logfile = 6;
optional bytes swidfile = 7;
optional bytes livelog = 8;
}
message IdentityClaim {

View File

@ -13,6 +13,8 @@
#include <string>
#include <vector>
#include <Process.h>
#include <Properties.h>
#include <regex>
#include "log4cplus/configurator.h"
@ -31,6 +33,7 @@ using hirs::tpm2::AsymmetricKeyType;
using hirs::tpm2::CommandTpm2;
using hirs::tpm2_tools_utils::Tpm2ToolsVersion;
using hirs::utils::Process;
using hirs::properties::Properties;
using std::cout;
using std::cerr;
using std::endl;
@ -65,6 +68,18 @@ int provision() {
cout << "----> Collecting device information" << endl;
hirs::pb::DeviceInfo dv = DeviceInfoCollector::collectDeviceInfo();
dv.set_pcrslist(tpm2.getPcrList());
// collect TCG Boot files
Properties props("/etc/hirs/tcg_boot.properties");
const std::string& rim_file = props.get("tcg.rim.file", "");
const std::string& swid_file = props.get("tcg.swidtag.file", "");
try {
dv.set_logfile(hirs::file_utils::fileToString(rim_file));
dv.set_swidfile(hirs::file_utils::fileToString(swid_file));
dv.set_livelog(hirs::file_utils::fileToString(
"/sys/kernel/security/tpm0/binary_bios_measurements"));
} catch (HirsRuntimeException& hirsRuntimeException) {
logger.error(hirsRuntimeException.what());
}
// send identity claim
cout << "----> Sending identity claim to Attestation CA" << endl;

View File

@ -297,6 +297,24 @@ public final class TCGEventLog {
sb.append("Event Log processing completed.\n");
return sb.toString();
}
/**
* Human readable string representing the contents of the Event Log.
* @param bEvent flag to set
* @param bHexEvent flag to set
* @param bContent flag to set
* @return Description of the log.
*/
public String toString(final boolean bEvent,
final boolean bHexEvent,
final boolean bContent) {
this.bEvent = bEvent;
this.bHexEvent = bHexEvent;
this.bContent = bContent;
return this.toString();
}
/**
* Returns the TCG Algorithm Registry defined string for the Digest Algorithm
* used in the event log.

View File

@ -109,7 +109,7 @@ UefiSignatureList(final ByteArrayInputStream lists)
/**
* Method for processing a set of EFI SignatureList(s).
* @param sigData Byte array holding one or more SignatureLists
* @param efiSigData Byte array holding one or more SignatureLists
* @throws CertificateException If there's a problem parsing the X509 certificate.
* @throws NoSuchAlgorithmException if there's a problem hashing the certificate.
* @throws IOException If there's a problem parsing the signature data.
@ -131,7 +131,7 @@ private void processSignatureList(final byte[] efiSigData)
/**
* Method for processing a set of EFI SignatureList(s).
* @param sigData Byte array holding one or more SignatureLists.
* @param sigDataIS Byte array holding one or more SignatureLists.
* @throws CertificateException If there's a problem parsing the X509 certificate.
* @throws NoSuchAlgorithmException if there's a problem hashing the certificate.
* @throws IOException If there's a problem parsing the signature data.
@ -173,12 +173,14 @@ public int getNumberOfCerts() {
*/
public boolean isValidSigListGUID(final UefiGuid guid) {
switch (guid.getVendorTableReference()) {
case "EFI_CERT_SHA256_GUID": return true;
case "EFI_CERT_X509_SHA256": return true;
case "EFI_CERT_X509_SHA384": return true;
case "EFI_CERT_X509_SHA512": return true;
case "EFI_CERT_X509_GUID": return true;
default: return false;
case "EFI_CERT_SHA256_GUID":
case "EFI_CERT_X509_SHA256":
case "EFI_CERT_X509_SHA384":
case "EFI_CERT_X509_SHA512":
case "EFI_CERT_X509_GUID":
return true;
default:
return false;
}
}
@ -193,7 +195,7 @@ public String toString() {
sigInfo.append("Number if items = " + numberOfItems + "\n");
sigList.iterator();
for (int i = 0; i < sigList.size(); i++) {
UefiSignatureData certData = (UefiSignatureData) sigList.get(i);
UefiSignatureData certData = sigList.get(i);
sigInfo.append(certData.toString());
}
if (!valid) {

View File

@ -40,12 +40,12 @@ public class UefiVariable {
* EFIVariable constructor.
* The UEFI_VARIABLE_DATA contains a "VariableName" field which is used to determine
* the class used to parse the data within the "VariableData".
* @param varibaleData byte array holding the UEFI Variable.
* @param variableData byte array holding the UEFI Variable.
* @throws CertificateException If there a problem parsing the X509 certificate.
* @throws NoSuchAlgorithmException if there's a problem hashing the certificate.
* @throws IOException If there's a problem parsing the signature data.
*/
public UefiVariable(final byte[] varibaleData)
public UefiVariable(final byte[] variableData)
throws CertificateException, NoSuchAlgorithmException, IOException {
byte[] guid = new byte[UefiConstants.SIZE_16];
byte[] nameLength = new byte[UefiConstants.SIZE_8];
@ -54,21 +54,21 @@ public UefiVariable(final byte[] varibaleData)
byte[] name = null;
int variableLength = 0;
System.arraycopy(varibaleData, 0, guid, 0, UefiConstants.SIZE_16);
System.arraycopy(variableData, 0, guid, 0, UefiConstants.SIZE_16);
uefiGuid = new UefiGuid(guid);
System.arraycopy(varibaleData, UefiConstants.SIZE_16, nameLength, 0, UefiConstants.SIZE_8);
System.arraycopy(variableData, UefiConstants.SIZE_16, nameLength, 0, UefiConstants.SIZE_8);
int nlength = HexUtils.leReverseInt(nameLength);
System.arraycopy(varibaleData, UefiConstants.OFFSET_24, dataLength, 0, UefiConstants.SIZE_8);
System.arraycopy(variableData, UefiConstants.OFFSET_24, dataLength, 0, UefiConstants.SIZE_8);
nameTemp = new byte[nlength * UefiConstants.SIZE_2];
System.arraycopy(varibaleData, UefiConstants.OFFSET_32,
System.arraycopy(variableData, UefiConstants.OFFSET_32,
nameTemp, 0, nlength * UefiConstants.SIZE_2);
byte[] name1 = UefiDevicePath.convertChar16tobyteArray(nameTemp);
name = new byte[nlength];
System.arraycopy(name1, 0, name, 0, nlength);
variableLength = HexUtils.leReverseInt(dataLength);
uefiVaribelData = new byte[variableLength];
System.arraycopy(varibaleData, UefiConstants.OFFSET_32
System.arraycopy(variableData, UefiConstants.OFFSET_32
+ nlength * UefiConstants.SIZE_2, uefiVaribelData, 0, variableLength);
varName = new String(name, "UTF-8");
String tmpName = varName;