mirror of
https://github.com/nsacyber/HIRS.git
synced 2025-04-11 05:10:26 +00:00
This code changes how the ACA handles a pcr list provided by the provisioner. The provisioner also is changed to send all supported algorithms and no longer delimits them with a + sign. The ACA is now set up to cycle through the entire list until is matches the baseline found in the rim associated log file. Currently the code is having issues saving the larger list of pcr values. It is too big for the database.
This commit is contained in:
parent
d10e7f1ebd
commit
3e9d26f598
HIRS_AttestationCA/src/main/java/hirs/attestationca
HIRS_AttestationCAPortal/src/test/java/hirs/attestationca/portal/page/controllers
HIRS_ProvisionerTPM2
HIRS_Utils/src/main/java/hirs/data/persist/certificate
@ -508,6 +508,7 @@ public abstract class AbstractAttestationCertificateAuthority
|
||||
}
|
||||
if (request.getPcrslist() != null && !request.getPcrslist().isEmpty()) {
|
||||
this.pcrValues = request.getPcrslist().toStringUtf8();
|
||||
LOG.error(this.pcrValues);
|
||||
}
|
||||
|
||||
// Get device name and device
|
||||
|
108
HIRS_AttestationCA/src/main/java/hirs/attestationca/service/SupplyChainValidationServiceImpl.java
108
HIRS_AttestationCA/src/main/java/hirs/attestationca/service/SupplyChainValidationServiceImpl.java
@ -1,6 +1,9 @@
|
||||
package hirs.attestationca.service;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.security.KeyStore;
|
||||
import java.security.KeyStoreException;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
@ -313,6 +316,18 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
|
||||
return subPlatformScv;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* For some reason the code isn't creating the directory it needs or saving
|
||||
* the info to that file.
|
||||
* I'm probably going to have to move the setting of the pcr values
|
||||
* from the abstract ACA class, and then
|
||||
* save the filename to the data base. Then have just this pull that
|
||||
* file name and open it. the ACA class saves.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
private SupplyChainValidation validateFirmware(final Device device,
|
||||
final PCRPolicy pcrPolicy) {
|
||||
|
||||
@ -330,6 +345,8 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
|
||||
.byManufacturer(manufacturer)
|
||||
.getRIM();
|
||||
|
||||
fwStatus = new AppraisalStatus(PASS,
|
||||
SupplyChainCredentialValidator.FIRMWARE_VALID);
|
||||
if (rim == null) {
|
||||
fwStatus = new AppraisalStatus(FAIL,
|
||||
String.format("Firmware validation failed: "
|
||||
@ -344,43 +361,70 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
|
||||
pcrPolicy.setBaselinePcrs(baseline);
|
||||
|
||||
if (attCert != null) {
|
||||
String[] pcrsSet = attCert.getPcrValues().split("\\+");
|
||||
String[] pcrs1 = pcrsSet[0].split("\\n");
|
||||
String[] pcrs256 = pcrsSet[1].split("\\n");
|
||||
String[] quote = new String[TPMMeasurementRecord.MAX_PCR_ID + 1];
|
||||
int offset = 0;
|
||||
|
||||
fwStatus = new AppraisalStatus(PASS,
|
||||
SupplyChainCredentialValidator.FIRMWARE_VALID);
|
||||
|
||||
if (baseline[0].length() == TPMMeasurementRecord.SHA_BYTE_LENGTH) {
|
||||
// quote from provisioner is formated to indicate the encryption
|
||||
if (pcrs1[0].split(":")[0].contains("sha")) {
|
||||
offset = 1;
|
||||
}
|
||||
for (int i = 0; i <= TPMMeasurementRecord.MAX_PCR_ID; i++) {
|
||||
//update quote with the pcr only, based on offset
|
||||
quote[i] = pcrs1[i + offset].split(":")[1].trim();
|
||||
}
|
||||
} else if (baseline[0].length() == TPMMeasurementRecord.SHA_256_BYTE_LENGTH) {
|
||||
// quote from provisioner is formated to indicate the encryption
|
||||
if (pcrs256[0].split(":")[0].contains("sha")) {
|
||||
offset = 1;
|
||||
}
|
||||
for (int i = 0; i <= TPMMeasurementRecord.MAX_PCR_ID; i++) {
|
||||
//update quote with the pcr only, based on offset
|
||||
quote[i] = pcrs256[i + offset].split(":")[1].trim();
|
||||
Path pcrPath = Paths.get(attCert.getPcrValues());
|
||||
String pcrContent = "";
|
||||
if (Files.exists(pcrPath)) {
|
||||
try {
|
||||
pcrContent = new String(Files.readAllBytes(pcrPath), "UTF8");
|
||||
} catch (IOException ioEx) {
|
||||
LOGGER.error(ioEx);
|
||||
}
|
||||
}
|
||||
LOGGER.error(pcrContent);
|
||||
String[] pcrSet = null;
|
||||
String[] quote = null;
|
||||
int algorithmLength = baseline[0].length();
|
||||
|
||||
StringBuilder sb = pcrPolicy.validatePcrs(quote);
|
||||
if (sb.length() > 0) {
|
||||
level = Level.ERROR;
|
||||
fwStatus = new AppraisalStatus(FAIL, sb.toString());
|
||||
if (pcrContent.isEmpty()) {
|
||||
fwStatus = new AppraisalStatus(FAIL,
|
||||
"Firmware validation failed: Client did not "
|
||||
+ "provide pcr values.");
|
||||
LOGGER.warn(String.format(
|
||||
"Firmware validation failed: Client (%s) did not "
|
||||
+ "provide pcr values.", attCert.getDevice().getName()));
|
||||
} else {
|
||||
level = Level.INFO;
|
||||
// we have a full set of PCR values
|
||||
pcrSet = pcrContent.split("\\n");
|
||||
quote = new String[TPMMeasurementRecord.MAX_PCR_ID + 1];
|
||||
|
||||
// we need to scroll through the entire list until we find
|
||||
// a matching hash length
|
||||
int offset = 1;
|
||||
|
||||
// TDM : I wonder if I can split on the sha line itself
|
||||
for (int i = 0; i < pcrSet.length; i++) {
|
||||
if (pcrSet[i].contains("sha")) {
|
||||
// entered a new set, check size
|
||||
if (pcrSet[i + offset].split(":")[1].trim().length()
|
||||
== algorithmLength) {
|
||||
// found the matching set
|
||||
for (int j = 0; j <= TPMMeasurementRecord.MAX_PCR_ID; j++) {
|
||||
quote[j] = pcrSet[++i];
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
LOGGER.error(quote[offset]);
|
||||
|
||||
if (quote[0].isEmpty()) {
|
||||
// validation fail
|
||||
fwStatus = new AppraisalStatus(FAIL,
|
||||
"Firmware validation failed: "
|
||||
+ "Client provided PCR "
|
||||
+ "values are not the same algorithm "
|
||||
+ "as associated RIM.");
|
||||
} else {
|
||||
StringBuilder sb = pcrPolicy.validatePcrs(quote);
|
||||
if (sb.length() > 0) {
|
||||
level = Level.ERROR;
|
||||
fwStatus = new AppraisalStatus(FAIL, sb.toString());
|
||||
} else {
|
||||
level = Level.INFO;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (fwStatus != null) {
|
||||
} else {
|
||||
fwStatus = new AppraisalStatus(FAIL, "Associated Issued Attestation"
|
||||
+ " Certificate can not be found.");
|
||||
}
|
||||
|
@ -144,7 +144,7 @@ public class IssuedCertificatesPageControllerTest extends PageControllerTest {
|
||||
.andReturn();
|
||||
}
|
||||
|
||||
/**
|
||||
/**
|
||||
* Tests downloading the certificate.
|
||||
* @throws java.lang.Exception when getting raw report
|
||||
*/
|
||||
|
@ -61,8 +61,6 @@ class CommandTpm2 {
|
||||
static const char* const kTpm2ToolsGetQuoteCommand;
|
||||
static const char* const kTpm2DefaultQuoteFilename;
|
||||
static const char* const kTpm2DefaultSigFilename;
|
||||
static const char* const kTpm2Sha1SigAlgorithm;
|
||||
static const char* const kTpm2Sha256SigAlgorithm;
|
||||
static const char* const kTpm2ToolsPcrListCommand;
|
||||
|
||||
const hirs::tpm2_tools_utils::Tpm2ToolsVersion version;
|
||||
@ -138,8 +136,7 @@ class CommandTpm2 {
|
||||
std::string getQuote(const std::string& pcr_selection,
|
||||
const std::string& nonce);
|
||||
|
||||
std::string getPcrsList();
|
||||
std::string getPcrs256List();
|
||||
std::string getPcrList();
|
||||
};
|
||||
|
||||
} // namespace tpm2
|
||||
|
@ -123,8 +123,6 @@ const char* const CommandTpm2::kDefaultActivatedIdentityFilename
|
||||
= "activatedIdentity.secret";
|
||||
const char* const CommandTpm2::kTpm2DefaultQuoteFilename = "/tmp/quote.bin";
|
||||
const char* const CommandTpm2::kTpm2DefaultSigFilename = "/tmp/sig.bin";
|
||||
const char* const CommandTpm2::kTpm2Sha1SigAlgorithm = "sha1";
|
||||
const char* const CommandTpm2::kTpm2Sha256SigAlgorithm = "sha256";
|
||||
|
||||
/**
|
||||
* Constructor to create an interface to TPM 2.0 devices.
|
||||
@ -559,37 +557,17 @@ string CommandTpm2::getQuote(const string& pcr_selection,
|
||||
* Method to get the full list of pcrs from the TPM.
|
||||
*
|
||||
*/
|
||||
string CommandTpm2::getPcrsList() {
|
||||
string CommandTpm2::getPcrList() {
|
||||
string pcrslist;
|
||||
stringstream argsStream;
|
||||
|
||||
argsStream << " -g " << kTpm2Sha1SigAlgorithm
|
||||
<< endl;
|
||||
argsStream << endl;
|
||||
|
||||
LOGGER.info("Running tpm2_pcrlist with arguments: " + argsStream.str());
|
||||
pcrslist = runTpm2CommandWithRetry(kTpm2ToolsPcrListCommand,
|
||||
argsStream.str(),
|
||||
__LINE__);
|
||||
LOGGER.info("TPM PCRS List successful");
|
||||
|
||||
return pcrslist;
|
||||
}
|
||||
|
||||
/**
|
||||
* Method to get the full list of pcrs from the TPM as SHA256. *
|
||||
*/
|
||||
string CommandTpm2::getPcrs256List() {
|
||||
string pcrslist;
|
||||
stringstream argsStream;
|
||||
|
||||
argsStream << " -g " << kTpm2Sha256SigAlgorithm
|
||||
<< endl;
|
||||
|
||||
LOGGER.info("Running tpm2_pcrlist with arguments: " + argsStream.str());
|
||||
pcrslist = runTpm2CommandWithRetry(kTpm2ToolsPcrListCommand,
|
||||
argsStream.str(),
|
||||
__LINE__);
|
||||
LOGGER.info("TPM PCRS (SHA 256) List successful");
|
||||
LOGGER.info("TPM PCR List successful");
|
||||
|
||||
return pcrslist;
|
||||
}
|
||||
|
@ -106,9 +106,7 @@ int provision() {
|
||||
"14,15,16,17,18,19,20,21,22,23",
|
||||
decryptedNonce));
|
||||
|
||||
stringstream pcrStream;
|
||||
pcrStream << tpm2.getPcrsList() << "\n+\n" << tpm2.getPcrs256List();
|
||||
certificateRequest.set_pcrslist(pcrStream.str());
|
||||
certificateRequest.set_pcrslist(tpm2.getPcrList());
|
||||
const string& akCertificateByteString
|
||||
= provisioner.sendAttestationCertificateRequest(certificateRequest);
|
||||
|
||||
|
@ -2,9 +2,14 @@ package hirs.data.persist.certificate;
|
||||
|
||||
import hirs.persist.CertificateManager;
|
||||
import hirs.persist.CertificateSelector;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.nio.file.NoSuchFileException;
|
||||
import java.util.Collections;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
@ -21,7 +26,14 @@ import javax.persistence.ManyToOne;
|
||||
@Entity
|
||||
public class IssuedAttestationCertificate extends DeviceAssociatedCertificate {
|
||||
|
||||
private static final int MAX_CERT_LENGTH_BYTES = 4096;
|
||||
private static final Logger LOGGER = LogManager.getLogger(IssuedAttestationCertificate.class);
|
||||
|
||||
private static final int MAX_CERT_LENGTH_BYTES = 1024;
|
||||
private static final String CATALINA_HOME = System.getProperty("catalina.base");
|
||||
private static final String TOMCAT_UPLOAD_DIRECTORY
|
||||
= "/webapps/HIRS_AttestationCAPortal/upload/device_pcrs/";
|
||||
private static final String PCR_UPLOAD_FOLDER
|
||||
= CATALINA_HOME + TOMCAT_UPLOAD_DIRECTORY;
|
||||
|
||||
/**
|
||||
* AIC label that must be used.
|
||||
@ -143,6 +155,29 @@ public class IssuedAttestationCertificate extends DeviceAssociatedCertificate {
|
||||
* @param pcrValues to be stored.
|
||||
*/
|
||||
public void setPcrValues(final String pcrValues) {
|
||||
this.pcrValues = pcrValues;
|
||||
this.pcrValues = savePcrValues(pcrValues);
|
||||
}
|
||||
|
||||
private String savePcrValues(final String pcrValues) {
|
||||
try {
|
||||
if (Files.notExists(Paths.get(PCR_UPLOAD_FOLDER))) {
|
||||
Files.createDirectory(Paths.get(PCR_UPLOAD_FOLDER));
|
||||
}
|
||||
Path pcrPath = Paths.get(String.format("%s/%s",
|
||||
PCR_UPLOAD_FOLDER, this.getDevice().getName()));
|
||||
if (Files.notExists(pcrPath)) {
|
||||
Files.createFile(pcrPath);
|
||||
}
|
||||
Files.write(pcrPath, pcrValues.getBytes("UTF8"));
|
||||
return pcrPath.toString();
|
||||
} catch (NoSuchFileException nsfEx) {
|
||||
LOGGER.error(String.format("File Not found!: %s",
|
||||
this.getDevice().getName()));
|
||||
LOGGER.error(nsfEx);
|
||||
} catch (IOException ioEx) {
|
||||
LOGGER.error(ioEx);
|
||||
}
|
||||
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user