Merge branch 'master' into fw_sys_test

This commit is contained in:
lareine 2022-03-09 14:49:52 -05:00
commit a071682477
33 changed files with 950 additions and 490 deletions

View File

@ -460,8 +460,8 @@ public abstract class AbstractAttestationCertificateAuthority
ProvisionerTpm2.IdentityClaimResponse response
= ProvisionerTpm2.IdentityClaimResponse.newBuilder()
.setCredentialBlob(blobStr).setPcrMask(pcrQuoteMask)
.setStatus(ProvisionerTpm2.ResponseStatus.PASS)
.build();
return response.toByteArray();
} else {
LOG.error("Supply chain validation did not succeed. Result is: "
@ -470,6 +470,7 @@ public abstract class AbstractAttestationCertificateAuthority
ProvisionerTpm2.IdentityClaimResponse response
= ProvisionerTpm2.IdentityClaimResponse.newBuilder()
.setCredentialBlob(blobStr)
.setStatus(ProvisionerTpm2.ResponseStatus.FAIL)
.build();
return response.toByteArray();
}
@ -640,6 +641,7 @@ public abstract class AbstractAttestationCertificateAuthority
.copyFrom(derEncodedAttestationCertificate);
ProvisionerTpm2.CertificateResponse response = ProvisionerTpm2.CertificateResponse
.newBuilder().setCertificate(certificateBytes)
.setStatus(ProvisionerTpm2.ResponseStatus.PASS)
.build();
saveAttestationCertificate(derEncodedAttestationCertificate, endorsementCredential,
@ -651,7 +653,9 @@ public abstract class AbstractAttestationCertificateAuthority
+ "Firmware Quote Validation failed. Result is: "
+ validationResult);
ProvisionerTpm2.CertificateResponse response = ProvisionerTpm2.CertificateResponse
.newBuilder().setCertificate(ByteString.EMPTY).build();
.newBuilder()
.setStatus(ProvisionerTpm2.ResponseStatus.FAIL)
.build();
return response.toByteArray();
}
} else {
@ -840,7 +844,8 @@ public abstract class AbstractAttestationCertificateAuthority
}
}
} else {
LOG.warn("Device did not send support RIM file...");
LOG.warn(String.format("%s did not send support RIM file...",
dv.getNw().getHostname()));
}
if (dv.getSwidfileCount() > 0) {
@ -876,7 +881,8 @@ public abstract class AbstractAttestationCertificateAuthority
}
}
} else {
LOG.warn("Device did not send swid tag file...");
LOG.warn(String.format("%s did not send swid tag file...",
dv.getNw().getHostname()));
}
//update Support RIMs and Base RIMs.
@ -948,11 +954,21 @@ public abstract class AbstractAttestationCertificateAuthority
this.referenceManifestManager.update(rim);
}
}
for (BaseReferenceManifest baseRim : BaseReferenceManifest
.select(referenceManifestManager).getRIMs()) {
if (baseRim.getPlatformManufacturer().equals(dv.getHw().getManufacturer())
&& baseRim.getPlatformModel().equals(dv.getHw().getProductName())) {
baseRim.setEventLogHash(temp.getHexDecHash());
this.referenceManifestManager.update(baseRim);
}
}
} catch (IOException ioEx) {
LOG.error(ioEx);
}
} else {
LOG.warn("Device did not send bios measurement log...");
LOG.warn(String.format("%s did not send bios measurement log...",
dv.getNw().getHostname()));
}
// Get TPM info, currently unimplemented
@ -994,14 +1010,15 @@ public abstract class AbstractAttestationCertificateAuthority
rdr = referenceDigestManager.saveRecord(dbObj);
} // right now this will not deal with updating
if (this.referenceEventManager.getValuesByRecordId(rdr).isEmpty()) {
if (this.referenceEventManager.getValuesByRimId(dbSupport).isEmpty()) {
try {
TCGEventLog logProcessor = new TCGEventLog(dbSupport.getRimBytes());
ReferenceDigestValue rdv;
for (TpmPcrEvent tpe : logProcessor.getEventList()) {
rdv = new ReferenceDigestValue(rdr.getId(), tpe.getPcrIndex(),
rdv = new ReferenceDigestValue(dbSupport.getAssociatedRim(),
dbSupport.getId(), manufacturer, model, tpe.getPcrIndex(),
tpe.getEventDigestStr(), tpe.getEventTypeStr(),
false, false);
false, false, tpe.getEventContent());
this.referenceEventManager.saveValue(rdv);
}
} catch (CertificateException cEx) {
@ -1033,25 +1050,22 @@ public abstract class AbstractAttestationCertificateAuthority
}
}
} else if (dbSupport.isSwidSupplemental() && !dbSupport.isProcessed()) {
if (rdr != null) {
try {
TCGEventLog logProcessor = new TCGEventLog(dbSupport.getRimBytes());
ReferenceDigestValue rdv;
for (TpmPcrEvent tpe : logProcessor.getEventList()) {
rdv = new ReferenceDigestValue(rdr.getId(), tpe.getPcrIndex(),
tpe.getEventDigestStr(), tpe.getEventTypeStr(),
false, false);
this.referenceEventManager.saveValue(rdv);
}
dbSupport.setProcessed(true);
this.referenceManifestManager.update(dbSupport);
} catch (CertificateException cEx) {
LOG.error(cEx);
} catch (NoSuchAlgorithmException noSaEx) {
LOG.error(noSaEx);
} catch (IOException ioEx) {
LOG.error(ioEx);
try {
TCGEventLog logProcessor = new TCGEventLog(dbSupport.getRimBytes());
ReferenceDigestValue rdv;
for (TpmPcrEvent tpe : logProcessor.getEventList()) {
rdv = new ReferenceDigestValue(dbSupport.getAssociatedRim(),
dbSupport.getId(), manufacturer, model, tpe.getPcrIndex(),
tpe.getEventDigestStr(), tpe.getEventTypeStr(),
false, false, tpe.getEventContent());
this.referenceEventManager.saveValue(rdv);
}
} catch (CertificateException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
@ -1885,7 +1899,7 @@ public abstract class AbstractAttestationCertificateAuthority
generateCertificate = scp.isIssueAttestationCertificate();
if (issuedAc != null && scp.isGenerateOnExpiration()) {
if (issuedAc.getEndValidity().after(currentDate)) {
// so the issued AC is expired
// so the issued AC is not expired
// however are we within the threshold
days = daysBetween(currentDate, issuedAc.getEndValidity());
if (days < Integer.parseInt(scp.getReissueThreshold())) {

View File

@ -9,7 +9,6 @@ import hirs.data.persist.Device;
import hirs.data.persist.DeviceInfoReport;
import hirs.data.persist.EventLogMeasurements;
import hirs.data.persist.PCRPolicy;
import hirs.data.persist.ReferenceDigestRecord;
import hirs.data.persist.ReferenceDigestValue;
import hirs.data.persist.ReferenceManifest;
import hirs.data.persist.SupplyChainPolicy;
@ -389,14 +388,14 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
Set<BaseReferenceManifest> baseReferenceManifests = null;
BaseReferenceManifest baseReferenceManifest = null;
ReferenceManifest supportReferenceManifest = null;
ReferenceManifest measurement = null;
ReferenceDigestRecord digestRecord = null;
EventLogMeasurements measurement = null;
baseReferenceManifests = BaseReferenceManifest.select(referenceManifestManager)
.byDeviceName(device.getDeviceInfo().getNetworkInfo().getHostname()).getRIMs();
.byModel(model).getRIMs();
for (BaseReferenceManifest bRim : baseReferenceManifests) {
if (!bRim.isSwidSupplemental() && !bRim.isSwidPatch()) {
if (bRim.getPlatformManufacturer().equals(manufacturer)
&& !bRim.isSwidSupplemental() && !bRim.isSwidPatch()) {
baseReferenceManifest = bRim;
}
}
@ -408,6 +407,11 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
} else {
measurement = EventLogMeasurements.select(referenceManifestManager)
.byHexDecHash(baseReferenceManifest.getEventLogHash()).getRIM();
if (measurement == null) {
measurement = EventLogMeasurements.select(referenceManifestManager)
.byModel(baseReferenceManifest.getPlatformModel()).getRIM();
}
}
if (measurement == null) {
@ -456,12 +460,10 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
for (SwidResource swidRes : resources) {
supportReferenceManifest = SupportReferenceManifest.select(referenceManifestManager)
.byHexDecHash(swidRes.getHashValue()).getRIM();
if (supportReferenceManifest != null
&& swidRes.getName().equals(supportReferenceManifest.getFileName())) {
if (supportReferenceManifest != null) {
// Removed the filename check from this if statement
referenceManifestValidator.validateSupportRimHash(
supportReferenceManifest.getRimBytes(), swidRes.getHashValue());
} else {
supportReferenceManifest = null;
}
}
@ -473,7 +475,7 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
if (passed && supportReferenceManifest == null) {
fwStatus = new AppraisalStatus(FAIL,
"Support Reference Integrity Manifest can not be found\n");
"Support Reference Integrity Manifest can not be found");
passed = false;
}
@ -528,7 +530,6 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
// vs baseline tcg event log
// find the measurement
TCGEventLog tcgMeasurementLog;
digestRecord = this.referenceDigestManager.getRecord(manufacturer, model);
LinkedList<TpmPcrEvent> tpmPcrEvents = new LinkedList<>();
List<ReferenceDigestValue> eventValue;
HashMap<String, ReferenceDigestValue> eventValueMap = new HashMap<>();
@ -536,7 +537,7 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
if (measurement.getPlatformManufacturer().equals(manufacturer)) {
tcgMeasurementLog = new TCGEventLog(measurement.getRimBytes());
eventValue = this.referenceEventManager
.getValuesByRecordId(digestRecord);
.getValuesByRimId(supportReferenceManifest);
for (ReferenceDigestValue rdv : eventValue) {
eventValueMap.put(rdv.getDigestValue(), rdv);
}
@ -581,9 +582,10 @@ public class SupplyChainValidationServiceImpl implements SupplyChainValidationSe
} else {
fwStatus = new AppraisalStatus(FAIL, String.format("Firmware Validation failed: "
+ "%s for %s can not be found", failedString, manufacturer));
EventLogMeasurements eventLog = (EventLogMeasurements) measurement;
eventLog.setOverallValidationResult(fwStatus.getAppStatus());
this.referenceManifestManager.update(eventLog);
if (measurement != null) {
measurement.setOverallValidationResult(fwStatus.getAppStatus());
this.referenceManifestManager.update(measurement);
}
}
return buildValidationRecord(SupplyChainValidation.ValidationType.FIRMWARE,

View File

@ -54,6 +54,10 @@ public enum Page {
*/
RIM_DETAILS("Reference Integrity Manifest Details",
"", null, true, false, null, null),
/**
* Page to display RIM event digest table.
*/
RIM_DATABASE("RIM Database", "ic_important_devices", "first"),
/**
* Page that manages Attestation CA Policy.
*/

View File

@ -473,13 +473,14 @@ public class PolicyPageController extends PageController<NoPageParams> {
if (generateCertificateEnabled) {
threshold = ppModel.getThresholdValue();
if (threshold == null) {
threshold = SupplyChainPolicy.YEAR;
}
} else {
threshold = ppModel.getReissueThreshold();
}
if (threshold == null || threshold.isEmpty()) {
threshold = SupplyChainPolicy.YEAR;
}
policy.setReissueThreshold(threshold);
} else {
generateCertificateEnabled = false;
@ -542,13 +543,14 @@ public class PolicyPageController extends PageController<NoPageParams> {
if (generateDevIdCertificateEnabled) {
threshold = ppModel.getDevIdThresholdValue();
if (threshold == null) {
threshold = SupplyChainPolicy.YEAR;
}
} else {
threshold = ppModel.getDevIdReissueThreshold();
}
if (threshold == null || threshold.isEmpty()) {
threshold = SupplyChainPolicy.YEAR;
}
policy.setDevIdReissueThreshold(threshold);
} else {
generateDevIdCertificateEnabled = false;

View File

@ -7,7 +7,6 @@ import hirs.attestationca.portal.page.params.ReferenceManifestDetailsPageParams;
import hirs.attestationca.service.SupplyChainValidationServiceImpl;
import hirs.data.persist.BaseReferenceManifest;
import hirs.data.persist.EventLogMeasurements;
import hirs.data.persist.ReferenceDigestRecord;
import hirs.data.persist.ReferenceDigestValue;
import hirs.data.persist.ReferenceManifest;
import hirs.data.persist.SupportReferenceManifest;
@ -118,9 +117,6 @@ public class ReferenceManifestDetailsPageController
LOGGER.error(uuidError, iaEx);
} catch (Exception ioEx) {
LOGGER.error(ioEx);
for (StackTraceElement ste : ioEx.getStackTrace()) {
LOGGER.error(ste.toString());
}
}
if (data.isEmpty()) {
String notFoundMessage = "Unable to find RIM with ID: " + params.getId();
@ -522,7 +518,6 @@ public class ReferenceManifestDetailsPageController
BaseReferenceManifest base = null;
List<SupportReferenceManifest> supports = new ArrayList<>();
SupportReferenceManifest baseSupport = null;
List<ReferenceDigestRecord> digestRecords = new LinkedList<>();
data.put("supportFilename", "Blank");
data.put("supportId", "");
@ -532,9 +527,8 @@ public class ReferenceManifestDetailsPageController
data.put("validationResult", measurements.getOverallValidationResult());
data.put("swidBase", true);
List<ReferenceDigestValue> eventValues = new ArrayList<>();
if (measurements.getDeviceName() != null) {
digestRecords = referenceDigestManager
.getRecordsByDeviceName(measurements.getDeviceName());
supports.addAll(SupportReferenceManifest
.select(referenceManifestManager)
.byDeviceName(measurements
@ -558,24 +552,20 @@ public class ReferenceManifestDetailsPageController
if (base != null) {
data.put("associatedRim", base.getId());
}
eventValues.addAll(referenceEventManager.getValuesByRimId(base));
}
}
TCGEventLog measurementLog = new TCGEventLog(measurements.getRimBytes());
List<ReferenceDigestValue> eventValue = new ArrayList<>();
Map<String, ReferenceDigestValue> eventValueMap = new HashMap<>();
if (!digestRecords.isEmpty()) {
for (ReferenceDigestRecord rdr : digestRecords) {
eventValue.addAll(referenceEventManager
.getValuesByRecordId(rdr));
}
for (ReferenceDigestValue rdv : eventValue) {
eventValueMap.put(rdv.getDigestValue(), rdv);
}
for (TpmPcrEvent measurementEvent : measurementLog.getEventList()) {
if (!eventValueMap.containsKey(measurementEvent.getEventDigestStr())) {
livelogEvents.add(measurementEvent);
}
for (ReferenceDigestValue rdv : eventValues) {
eventValueMap.put(rdv.getDigestValue(), rdv);
}
for (TpmPcrEvent measurementEvent : measurementLog.getEventList()) {
if (!eventValueMap.containsKey(measurementEvent.getEventDigestStr())) {
livelogEvents.add(measurementEvent);
}
}

View File

@ -10,13 +10,17 @@ import hirs.attestationca.portal.page.PageController;
import hirs.attestationca.portal.page.PageMessages;
import hirs.attestationca.portal.page.params.NoPageParams;
import hirs.data.persist.BaseReferenceManifest;
import hirs.data.persist.ReferenceDigestValue;
import hirs.data.persist.ReferenceManifest;
import hirs.data.persist.SupportReferenceManifest;
import hirs.data.persist.SwidResource;
import hirs.data.persist.certificate.Certificate;
import hirs.persist.CriteriaModifier;
import hirs.persist.DBManagerException;
import hirs.persist.ReferenceEventManager;
import hirs.persist.ReferenceManifestManager;
import hirs.tpm.eventlog.TCGEventLog;
import hirs.tpm.eventlog.TpmPcrEvent;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.codec.binary.Hex;
import org.apache.logging.log4j.LogManager;
@ -42,6 +46,7 @@ import java.io.IOException;
import java.net.URISyntaxException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
@ -69,6 +74,7 @@ public class ReferenceManifestPageController
private final BiosDateValidator biosValidator;
private final ReferenceManifestManager referenceManifestManager;
private final ReferenceEventManager referenceEventManager;
private static final Logger LOGGER
= LogManager.getLogger(ReferenceManifestPageController.class);
@ -118,12 +124,15 @@ public class ReferenceManifestPageController
* Constructor providing the Page's display and routing specification.
*
* @param referenceManifestManager the reference manifest manager
* @param referenceEventManager this is the reference event manager
*/
@Autowired
public ReferenceManifestPageController(
final ReferenceManifestManager referenceManifestManager) {
final ReferenceManifestManager referenceManifestManager,
final ReferenceEventManager referenceEventManager) {
super(Page.REFERENCE_MANIFESTS);
this.referenceManifestManager = referenceManifestManager;
this.referenceEventManager = referenceEventManager;
this.biosValidator = new BiosDateValidator(BIOS_RELEASE_DATE_FORMAT);
}
@ -173,6 +182,29 @@ public class ReferenceManifestPageController
referenceManifestManager,
input, orderColumnName, criteriaModifier);
SupportReferenceManifest support;
// List<ReferenceDigestValue> events;
// for (ReferenceManifest rim : records) {
// if (rim instanceof SupportReferenceManifest) {
// support = (SupportReferenceManifest) rim;
// events = referenceEventManager.getValuesByRimId(support);
//
// for (ReferenceDigestValue rdv : events) {
// // the selector isn't giving me what I want
// if (support.getPlatformManufacturer() != null) {
// rdv.setManufacturer(support.getPlatformManufacturer());
// }
// if (support.getPlatformModel() != null) {
// rdv.setModel(support.getPlatformModel());
// }
// if (support.getAssociatedRim() != null) {
// rdv.setBaseRimId(support.getAssociatedRim());
// }
// referenceEventManager.updateRecord(rdv);
// }
// }
// }
LOGGER.debug("Returning list of size: " + records.size());
return new DataTableResponse<>(records, input);
}
@ -207,34 +239,42 @@ public class ReferenceManifestPageController
//Parse reference manifests
ReferenceManifest rim = parseRIM(file, supportRIM, messages);
// store first then update
ReferenceManifest referenceManifest = storeManifest(file.getOriginalFilename(),
messages,
rim,
supportRIM);
//Store only if it was parsed
if (rim != null) {
if (supportRIM) {
// look for associated base/support
// if I am the support rim, my hash is in the meta data of the swidtag
Set<BaseReferenceManifest> rims = BaseReferenceManifest
.select(referenceManifestManager).getRIMs();
support = (SupportReferenceManifest) rim;
// update information for associated support rim
for (BaseReferenceManifest dbRim : rims) {
for (SwidResource swid : dbRim.parseResource()) {
if (swid.getName().equals(rim.getFileName())) {
support.setSwidTagVersion(dbRim.getSwidTagVersion());
support.setPlatformManufacturer(dbRim.getPlatformManufacturer());
support.setPlatformModel(dbRim.getPlatformModel());
support.setTagId(dbRim.getTagId());
support.setAssociatedRim(dbRim.getId());
support.setUpdated(true);
break;
for (BaseReferenceManifest bRim : rims) {
for (SwidResource swid : bRim.parseResource()) {
if (support.getHexDecHash().equals(swid.getHashValue())) {
updateSupportRimInfo(bRim, support);
referenceManifestManager.update(support);
}
}
if (support.isUpdated()) {
for (ReferenceDigestValue rdv : referenceEventManager
.getValuesByRimId(support)) {
rdv.updateInfo(support);
referenceEventManager.updateRecord(rdv);
}
break;
}
}
} else {
base = (BaseReferenceManifest) rim;
base = (BaseReferenceManifest) referenceManifest;
// the base can find the support rim by the meta data hash
for (SwidResource swid : base.parseResource()) {
support = SupportReferenceManifest.select(referenceManifestManager)
.byFileName(swid.getName()).getRIM();
.byHexDecHash(swid.getHashValue()).getRIM();
if (support != null) {
base.setAssociatedRim(support.getId());
if (support.isUpdated()) {
@ -242,27 +282,17 @@ public class ReferenceManifestPageController
// instead of finding it, it is uptodate but still search
break;
} else {
support.setSwidTagVersion(base.getSwidTagVersion());
support.setPlatformManufacturer(base.getPlatformManufacturer());
support.setPlatformModel(base.getPlatformModel());
support.setTagId(base.getTagId());
support.setUpdated(true);
updateSupportRimInfo(base, support);
updateTpmEvents(support);
try {
referenceManifestManager.update(support);
} catch (DBManagerException dbmEx) {
LOGGER.error(String.format("Couldn't update Support RIM "
+ "%s with associated UUID %s", rim.getTagId(),
support.getId()), dbmEx);
LOGGER.warn("Failed to update Support RIM");
}
}
}
}
}
storeManifest(file.getOriginalFilename(),
messages,
rim,
supportRIM);
}
}
@ -304,6 +334,17 @@ public class ReferenceManifestPageController
String deleteCompletedMessage = "RIM successfully deleted";
messages.addInfo(deleteCompletedMessage);
LOGGER.info(deleteCompletedMessage);
// if support rim, update associated events
if (referenceManifest instanceof SupportReferenceManifest) {
List<ReferenceDigestValue> rdvs = referenceEventManager
.getValuesByRimId(referenceManifest);
for (ReferenceDigestValue rdv : rdvs) {
rdv.archive("Support RIM was deleted");
referenceEventManager.updateRecord(rdv);
}
}
}
} catch (IllegalArgumentException ex) {
String uuidError = "Failed to parse ID from: " + id;
@ -486,7 +527,7 @@ public class ReferenceManifestPageController
* @param supportRim boolean flag indicating if this is a support RIM
* process.
*/
private void storeManifest(
private ReferenceManifest storeManifest(
final String fileName,
final PageMessages messages,
final ReferenceManifest referenceManifest,
@ -529,25 +570,26 @@ public class ReferenceManifestPageController
+ "failed (%s): ", fileName);
messages.addError(failMessage + e.getMessage());
LOGGER.error(failMessage, e);
return;
return null;
}
try {
// save the new certificate if no match is found
if (existingManifest == null) {
referenceManifestManager.save(referenceManifest);
saveTpmEvents(referenceManifestManager.save(referenceManifest));
final String successMsg = String.format("RIM successfully uploaded (%s): ",
fileName);
messages.addSuccess(successMsg);
LOGGER.info(successMsg);
return;
return referenceManifest;
}
} catch (DBManagerException dbmEx) {
final String failMessage = String.format("Storing RIM failed (%s): ", fileName);
messages.addError(failMessage + dbmEx.getMessage());
LOGGER.error(failMessage, dbmEx);
return;
return null;
}
try {
@ -562,12 +604,98 @@ public class ReferenceManifestPageController
= String.format("Pre-existing RIM found and unarchived (%s): ", fileName);
messages.addSuccess(successMsg);
LOGGER.info(successMsg);
return existingManifest;
}
} catch (DBManagerException dbmEx) {
final String failMessage = String.format("Found an identical pre-existing RIM in the "
+ "archive, but failed to unarchive it (%s): ", fileName);
messages.addError(failMessage + dbmEx.getMessage());
LOGGER.error(failMessage, dbmEx);
return null;
}
return referenceManifest;
}
private void updateSupportRimInfo(final BaseReferenceManifest dbBaseRim,
final SupportReferenceManifest supportRim) {
// I have to assume the baseRim is from the database
// Updating the id values, manufacturer, model
if (supportRim != null) {
supportRim.setSwidTagVersion(dbBaseRim.getSwidTagVersion());
supportRim.setPlatformManufacturer(dbBaseRim.getPlatformManufacturer());
supportRim.setPlatformModel(dbBaseRim.getPlatformModel());
supportRim.setTagId(dbBaseRim.getTagId());
supportRim.setAssociatedRim(dbBaseRim.getId());
supportRim.setUpdated(true);
}
}
private void updateTpmEvents(final ReferenceManifest referenceManifest) {
String manufacturer;
String model;
if (referenceManifest.getPlatformManufacturer() == null) {
manufacturer = "";
} else {
manufacturer = referenceManifest.getPlatformManufacturer();
}
if (referenceManifest.getPlatformModel() == null) {
model = "";
} else {
model = referenceManifest.getPlatformModel();
}
List<ReferenceDigestValue> rdvs = referenceEventManager
.getValuesByRimId(referenceManifest);
for (ReferenceDigestValue rdv : rdvs) {
rdv.setModel(model);
rdv.setManufacturer(manufacturer);
rdv.setBaseRimId(referenceManifest.getAssociatedRim());
referenceEventManager.updateRecord(rdv);
}
}
private void saveTpmEvents(final ReferenceManifest referenceManifest) {
SupportReferenceManifest dbSupport;
String manufacturer;
String model;
if (referenceManifest instanceof SupportReferenceManifest) {
dbSupport = (SupportReferenceManifest) referenceManifest;
} else {
return;
}
TCGEventLog logProcessor = null;
if (dbSupport.getPlatformManufacturer() == null) {
manufacturer = "";
} else {
manufacturer = dbSupport.getPlatformManufacturer();
}
if (dbSupport.getPlatformModel() == null) {
model = "";
} else {
model = dbSupport.getPlatformModel();
}
try {
logProcessor = new TCGEventLog(dbSupport.getRimBytes());
ReferenceDigestValue rdv;
for (TpmPcrEvent tpe : logProcessor.getEventList()) {
rdv = new ReferenceDigestValue(dbSupport.getAssociatedRim(),
dbSupport.getId(), manufacturer,
model, tpe.getPcrIndex(),
tpe.getEventDigestStr(), tpe.getEventTypeStr(),
false, false, tpe.getEventContent());
this.referenceEventManager.saveValue(rdv);
}
} catch (CertificateException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}

View File

@ -0,0 +1,186 @@
package hirs.attestationca.portal.page.controllers;
import hirs.FilteredRecordsList;
import hirs.attestationca.portal.datatables.DataTableInput;
import hirs.attestationca.portal.datatables.DataTableResponse;
import hirs.attestationca.portal.datatables.OrderedListQueryDataTableAdapter;
import hirs.attestationca.portal.page.Page;
import hirs.attestationca.portal.page.PageController;
import hirs.attestationca.portal.page.params.NoPageParams;
import hirs.data.persist.ReferenceDigestValue;
import hirs.data.persist.SupportReferenceManifest;
import hirs.data.persist.certificate.Certificate;
import hirs.persist.CriteriaModifier;
import hirs.persist.DBManagerException;
import hirs.persist.DBReferenceDigestManager;
import hirs.persist.DBReferenceEventManager;
import hirs.persist.DBReferenceManifestManager;
import hirs.persist.ReferenceDigestManager;
import hirs.persist.ReferenceEventManager;
import hirs.persist.ReferenceManifestManager;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.hibernate.Criteria;
import org.hibernate.criterion.Restrictions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
/**
* Controller for the TPM Events page.
*/
@Controller
@RequestMapping("/rim-database")
public class RimDatabasePageController
extends PageController<NoPageParams> {
private static final String BIOS_RELEASE_DATE_FORMAT = "yyyy-MM-dd";
private final BiosDateValidator biosValidator;
private final ReferenceManifestManager referenceManifestManager;
private final ReferenceDigestManager referenceDigestManager;
private final ReferenceEventManager referenceEventManager;
private static final Logger LOGGER
= LogManager.getLogger(RimDatabasePageController.class);
/**
* This class was created for the purposes of avoiding findbugs message: As
* the JavaDoc states, DateFormats are inherently unsafe for multi-threaded
* use. The detector has found a call to an instance of DateFormat that has
* been obtained via a static field. This looks suspicious.
* <p>
* This class can have uses elsewhere but for now it will remain here.
*/
private static final class BiosDateValidator {
private final String dateFormat;
/**
* Default constructor that sets the format to parse against.
*
* @param dateFormat
*/
public BiosDateValidator(final String dateFormat) {
this.dateFormat = dateFormat;
}
/**
* Validates a date by attempting to parse based on format provided.
*
* @param date string of the given date
* @return true if the format matches
*/
public boolean isValid(final String date) {
DateFormat validFormat = new SimpleDateFormat(this.dateFormat);
boolean result = true;
validFormat.setLenient(false);
try {
validFormat.parse(date);
} catch (ParseException pEx) {
result = false;
}
return result;
}
}
/**
* Constructor providing the Page's display and routing specification.
*
* @param referenceManifestManager the ReferenceManifestManager object
* @param referenceDigestManager the ReferenceDigestManager object
* @param referenceEventManager the referenceEventManager object
*/
@Autowired
public RimDatabasePageController(
final DBReferenceManifestManager referenceManifestManager,
final DBReferenceDigestManager referenceDigestManager,
final DBReferenceEventManager referenceEventManager) {
super(Page.RIM_DATABASE);
this.referenceManifestManager = referenceManifestManager;
this.referenceDigestManager = referenceDigestManager;
this.referenceEventManager = referenceEventManager;
this.biosValidator = new BiosDateValidator(BIOS_RELEASE_DATE_FORMAT);
}
/**
* Returns the filePath for the view and the data model for the page.
*
* @param params The object to map url parameters into.
* @param model The data model for the request. Can contain data from
* redirect.
* @return the filePath for the view and data model for the page.
*/
@Override
public ModelAndView initPage(final NoPageParams params,
final Model model) {
return getBaseModelAndView();
}
/**
* Returns the list of TPM Events using the data table input for paging, ordering,
* and filtering.
*
* @param input the data tables input
* @return the data tables response, including the result set and paging
* information
*/
@ResponseBody
@RequestMapping(value = "/list",
produces = MediaType.APPLICATION_JSON_VALUE,
method = RequestMethod.GET)
public DataTableResponse<ReferenceDigestValue> getTableData(
final DataTableInput input) {
LOGGER.info("Handling request for summary list: " + input);
String orderColumnName = input.getOrderColumnName();
LOGGER.info("Ordering on column: " + orderColumnName);
// check that the alert is not archived and that it is in the specified report
CriteriaModifier criteriaModifier = new CriteriaModifier() {
@Override
public void modify(final Criteria criteria) {
criteria.add(Restrictions.isNull(Certificate.ARCHIVE_FIELD));
}
};
LOGGER.info("Querying with the following datatableinput: " + input.toString());
FilteredRecordsList<ReferenceDigestValue> referenceDigestValues =
OrderedListQueryDataTableAdapter.getOrderedList(
ReferenceDigestValue.class,
referenceEventManager,
input, orderColumnName, criteriaModifier);
SupportReferenceManifest support;
for (ReferenceDigestValue rdv : referenceDigestValues) {
// We are updating the base rim ID field if necessary and
if (rdv.getBaseRimId() == null) {
support = SupportReferenceManifest.select(referenceManifestManager)
.byEntityId(rdv.getSupportRimId()).getRIM();
if (support != null) {
rdv.setBaseRimId(support.getAssociatedRim());
try {
referenceEventManager.updateRecord(rdv);
} catch (DBManagerException e) {
LOGGER.error("Failed to update TPM Event with Base RIM ID");
LOGGER.error(rdv);
}
}
}
}
return new DataTableResponse<>(referenceDigestValues, input);
}
}

View File

@ -67,6 +67,10 @@
<a href="${portal}/devices"><img src="${icons}/ic_devices_black_24dp.png" /> Devices</a>
</h3>
<h4>View devices covered by this CA for supply chain validation.</h4>
<h3>
<a href="${portal}/rim-database"><img src="${icons}/ic_devices_black_24dp.png" /> RIM Database</a>
</h3>
<h4>View a list of TPM events </h4>
</div>
</div>
</div>

View File

@ -0,0 +1,75 @@
<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%-- JSP TAGS --%>
<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%@taglib prefix="spring" uri="http://www.springframework.org/tags"%>
<%@taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<%@taglib prefix="my" tagdir="/WEB-INF/tags"%>
<%-- CONTENT --%>
<my:page>
<jsp:attribute name="script">
<script type="text/javascript" src="${lib}/jquery.spring-friendly/jquery.spring-friendly.js"></script>
</jsp:attribute>
<jsp:attribute name="pageHeaderTitle">RIM Database</jsp:attribute>
<jsp:body>
<br/>
<div class="aca-data-table">
<table id="digestValueTable" class="display" width="100%">
<thead>
<tr>
<th>Manufacturer</th>
<th>Model</th>
<th>Event Type</th>
<th>PCR Index</th>
<th>Digest Value</th>
<th>Base RIM</th>
<th>Support RIM</th>
</tr>
</thead>
</table>
</div>
<script>
$(document).ready(function() {
var url = pagePath +'/list';
var columns = [
{data: 'manufacturer',
orderable: true,
searchable:false},
{data: 'model',
orderable: false,
searchable:false},
{data: 'eventType',
orderable: false,
searchable:false,},
{data: 'pcrIndex',
orderable: true,
searchable:false},
{data: 'digestValue',
orderable: false,
searchable:false},
{data: 'baseRimId',
orderable: false,
searchable: false,
render: function(data, type, full, meta) {
return rimDetailsLink(full.baseRimId);
}
},
{data: 'supportRimId',
orderable: false,
searchable: false,
render: function(data, type, full, meta) {
return rimDetailsLink(full.supportRimId);
}
}
];
//Set data tables
setDataTables("#digestValueTable", url, columns);
});
</script>
</jsp:body>
</my:page>

View File

@ -1,108 +0,0 @@
package hirs.attestationca.portal.page.controllers;
import hirs.data.persist.BaseReferenceManifest;
import hirs.data.persist.ReferenceManifest;
import hirs.persist.DBReferenceManifestManager;
import hirs.attestationca.portal.page.Page;
import hirs.attestationca.portal.page.PageController;
import hirs.attestationca.portal.page.PageControllerTest;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.Files;
import java.util.Map;
import static org.hamcrest.Matchers.hasItem;
import static org.hamcrest.Matchers.hasProperty;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.annotation.Rollback;
import org.springframework.test.web.servlet.MvcResult;
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.model;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
import org.testng.Assert;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
/**
* Integration tests that test the URL End Points of
* EndorsementKeyCredentialsPageController.
*/
@DirtiesContext(classMode = DirtiesContext.ClassMode.AFTER_CLASS)
public class ReferenceManifestDetailsPageControllerTest extends PageControllerTest {
private static final String GOOD_RIM_FILE = "/rims/generated_good.swidtag";
private static final String ID = "046b6c7f-0b8a-43b9-b35d-6489e6daee91";
@Autowired
private DBReferenceManifestManager referenceManifestManager;
private ReferenceManifest referenceManifest;
/**
* Prepares tests.
*
* @throws IOException if test resources are not found
*/
@BeforeClass
public void prepareTests() throws IOException {
Path fPath;
try {
fPath = Paths.get(this.getClass().getResource(GOOD_RIM_FILE).toURI());
} catch (URISyntaxException e) {
throw new IOException("Could not resolve path URI", e);
}
referenceManifest = new BaseReferenceManifest(Files.readAllBytes(fPath));
referenceManifestManager.save(referenceManifest);
}
/**
* Constructor.
*/
public ReferenceManifestDetailsPageControllerTest() {
super(Page.RIM_DETAILS);
}
/**
* Tests initial page when the Reference Integrity Manifest
* was not found.
* @throws Exception if an exception occurs
*/
@Test
public void testInitPage() throws Exception {
// Get error message
getMockMvc()
.perform(MockMvcRequestBuilders.get("/" + getPage().getViewName())
.param("id", ID))
.andExpect(status().isOk())
.andExpect(model().attribute(PageController.MESSAGES_ATTRIBUTE,
hasProperty("error", hasItem("Unable to find RIM with ID: " + ID))))
.andReturn();
}
/**
* Tests initial page for an Reference Integrity Manifest.
*
* @throws Exception if an exception occurs
*/
@Test
@Rollback
@SuppressWarnings("unchecked")
public void testInitPageRim() throws Exception {
MvcResult result = getMockMvc()
.perform(MockMvcRequestBuilders.get("/" + getPage().getViewName())
.param("id", referenceManifest.getId().toString())
.param("swidTagId", referenceManifest.getTagId()))
.andExpect(status().isOk())
.andExpect(model().attributeExists(PolicyPageController.INITIAL_DATA))
.andReturn();
// Obtain initialData HashMap
Map<String, String> initialData = (Map<String, String>) result
.getModelAndView()
.getModel()
.get(PolicyPageController.INITIAL_DATA);
Assert.assertEquals(initialData.get("swidTagId"), referenceManifest.getTagId());
}
}

View File

@ -1,191 +0,0 @@
package hirs.attestationca.portal.page.controllers;
import hirs.data.persist.BaseReferenceManifest;
import hirs.data.persist.ReferenceManifest;
import hirs.persist.ReferenceManifestManager;
import hirs.attestationca.portal.page.Page;
import hirs.attestationca.portal.page.PageControllerTest;
import hirs.attestationca.portal.page.PageMessages;
import java.io.IOException;
import java.util.Set;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.mock.web.MockMultipartFile;
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.annotation.Rollback;
import org.springframework.test.web.servlet.MvcResult;
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
import org.springframework.web.servlet.FlashMap;
import org.testng.Assert;
import org.testng.annotations.BeforeMethod;
import org.testng.annotations.Test;
/**
* Integration tests that test the URL End Points of
* ReferenceManifestPageController.
*/
@DirtiesContext(classMode = DirtiesContext.ClassMode.AFTER_EACH_TEST_METHOD)
public class ReferenceManifestPageControllerTest extends PageControllerTest {
private static final String GOOD_RIM_FILE = "generated_good.swidtag";
private static final String BAD_RIM_FILE = "generated_bad.swidtag";
@Autowired
private ReferenceManifestManager referenceManifestManager;
private MockMultipartFile validRimFile;
private MockMultipartFile nonValidRimFile;
/**
* Constructor.
*/
public ReferenceManifestPageControllerTest() {
super(Page.REFERENCE_MANIFESTS);
}
/**
* Prepares tests.
*
* @throws IOException if test resources are not found
*/
@BeforeMethod
public void prepareTests() throws IOException {
// create a multi part file for the controller upload
validRimFile = new MockMultipartFile("file", GOOD_RIM_FILE, "",
new ClassPathResource("rims/" + GOOD_RIM_FILE).getInputStream());
nonValidRimFile = new MockMultipartFile("file", BAD_RIM_FILE, "",
new ClassPathResource("rims/" + BAD_RIM_FILE).getInputStream());
}
private void archiveTestCert(final ReferenceManifest referenceManifest) throws Exception {
// now, archive the record
getMockMvc().perform(MockMvcRequestBuilders
.post("/reference-manifests/delete")
.param("id", referenceManifest.getId().toString()))
.andExpect(status().is3xxRedirection())
.andReturn();
Set<ReferenceManifest> records
= referenceManifestManager.get(BaseReferenceManifest
.select(referenceManifestManager).includeArchived());
Assert.assertEquals(records.size(), 1);
Assert.assertTrue(records.iterator().next().isArchived());
}
/**
* Tests uploading a RIM that is a Reference Integrity Manifest, and
* archiving it.
*
* @throws Exception if an exception occurs
*/
@Test
@Rollback
public void uploadAndArchiveValidRim() throws Exception {
ReferenceManifest rim = uploadTestRim();
archiveTestRim(rim);
}
/**
* Tests uploading a rim that is not a valid Reference Integrity Manifest,
* which results in failure.
*
* @throws Exception if an exception occurs
*/
@Test
@Rollback
public void uploadNonValidRim() throws Exception {
MvcResult result = getMockMvc().perform(MockMvcRequestBuilders
.fileUpload("/reference-manifests/upload")
.file(nonValidRimFile))
.andExpect(status().is3xxRedirection())
.andReturn();
// verify redirection messages
FlashMap flashMap = result.getFlashMap();
PageMessages pageMessages = (PageMessages) flashMap.get("messages");
Assert.assertEquals(pageMessages.getSuccess().size(), 0);
Assert.assertEquals(pageMessages.getError().size(), 1);
}
/**
* Tests that uploading a RIM when an identical RIM is archived will cause
* the existing RIM to be unarchived and updated.
*
* @throws Exception if an exception occurs
*/
@Test
@Rollback
public void uploadCausesUnarchive() throws Exception {
ReferenceManifest rim = uploadTestRim();
archiveTestCert(rim);
// upload the same cert again
MvcResult result = getMockMvc().perform(MockMvcRequestBuilders
.fileUpload("/reference-manifests/upload")
.file(validRimFile))
.andExpect(status().is3xxRedirection())
.andReturn();
// verify redirection messages
FlashMap flashMap = result.getFlashMap();
PageMessages pageMessages = (PageMessages) flashMap.get("messages");
Assert.assertEquals(pageMessages.getSuccess().size(), 1);
Assert.assertEquals(pageMessages.getError().size(), 0);
Assert.assertEquals(pageMessages.getSuccess().get(0),
"Pre-existing RIM found and unarchived (generated_good.swidtag): ");
// verify the cert was actually stored
Set<ReferenceManifest> records = referenceManifestManager.get(BaseReferenceManifest.select(
referenceManifestManager));
Assert.assertEquals(records.size(), 1);
ReferenceManifest newRim = records.iterator().next();
// verify that the rim was unarchived
Assert.assertFalse(newRim.isArchived());
// verify that the createTime was updated
Assert.assertTrue(newRim.getCreateTime().getTime() > rim.getCreateTime().getTime());
}
private ReferenceManifest uploadTestRim() throws Exception {
MvcResult result = getMockMvc().perform(MockMvcRequestBuilders
.fileUpload("/reference-manifests/upload")
.file(validRimFile))
.andExpect(status().is3xxRedirection())
.andReturn();
// verify redirection messages
FlashMap flashMap = result.getFlashMap();
PageMessages pageMessages = (PageMessages) flashMap.get("messages");
Assert.assertEquals(pageMessages.getSuccess().size(), 1);
Assert.assertEquals(pageMessages.getError().size(), 0);
// verify the cert was actually stored
Set<ReferenceManifest> records
= referenceManifestManager.get(BaseReferenceManifest
.select(referenceManifestManager));
Assert.assertEquals(records.size(), 1);
ReferenceManifest rim = records.iterator().next();
Assert.assertFalse(rim.isArchived());
return rim;
}
private void archiveTestRim(final ReferenceManifest rim) throws Exception {
// now, archive the record
getMockMvc().perform(MockMvcRequestBuilders
.post("/reference-manifests/delete")
.param("id", rim.getId().toString()))
.andExpect(status().is3xxRedirection())
.andReturn();
Set<ReferenceManifest> records
= referenceManifestManager.get(BaseReferenceManifest
.select(referenceManifestManager).includeArchived());
Assert.assertEquals(records.size(), 1);
Assert.assertTrue(records.iterator().next().isArchived());
}
}

View File

@ -48,27 +48,12 @@ SWIDTAG_FILE_LOCATION="$TCG_DIRECTORY/manifest/swidtag/"
CREDENTIALS_LOCATION="$TCG_DIRECTORY/cert/platform/"
BINARY_BIOS_MEASUREMENTS="/sys/kernel/security/tpm0/binary_bios_measurements"
touch "$TCG_TEMP_FILE"
if [ -d "$RIM_FILE_LOCATION" ]; then
echo "tcg.rim.dir=$RIM_FILE_LOCATION" > "$TCG_TEMP_FILE"
fi
if [ -d "$SWIDTAG_FILE_LOCATION" ]; then
echo "tcg.swidtag.dir=$SWIDTAG_FILE_LOCATION" >> "$TCG_TEMP_FILE"
fi
if [ -d "$CREDENTIALS_LOCATION" ]; then
echo "tcg.cert.dir=$CREDENTIALS_LOCATION" >> "$TCG_TEMP_FILE"
fi
if [ -f "$BINARY_BIOS_MEASUREMENTS" ]; then
echo "tcg.event.file=$BINARY_BIOS_MEASUREMENTS" >> "$TCG_TEMP_FILE"
fi
if [ ! -f "$TCG_BOOT_FILE" ]; then
touch "$TCG_TEMP_FILE"
echo "tcg.rim.dir=$RIM_FILE_LOCATION" > "$TCG_TEMP_FILE"
echo "tcg.swidtag.dir=$SWIDTAG_FILE_LOCATION" >> "$TCG_TEMP_FILE"
echo "tcg.cert.dir=$CREDENTIALS_LOCATION" >> "$TCG_TEMP_FILE"
echo "tcg.event.file=$BINARY_BIOS_MEASUREMENTS" >> "$TCG_TEMP_FILE"
install -m 644 $TCG_TEMP_FILE $TCG_BOOT_FILE
else
echo $TCG_TEMP_FILE > $TCG_BOOT_FILE
fi

View File

@ -77,9 +77,15 @@ message TpmQuote {
required string success = 1;
}
enum ResponseStatus {
PASS = 0;
FAIL = 1;
}
message IdentityClaimResponse {
required bytes credential_blob = 1;
optional bytes credential_blob = 1;
optional string pcr_mask = 2;
optional ResponseStatus status = 3 [default = FAIL];
}
message CertificateRequest {
@ -88,6 +94,7 @@ message CertificateRequest {
}
message CertificateResponse {
required bytes certificate = 1;
optional bytes certificate = 1;
optional ResponseStatus status = 2 [default = FAIL];
}

View File

@ -144,7 +144,8 @@ string RestfulClientProvisioner::sendAttestationCertificateRequest(
}
// Return the public attestation certificate
return response.certificate();
// return response.certificate();
return response.SerializeAsString();
} else {
stringstream errormsg;

View File

@ -144,7 +144,21 @@ int provision() {
string response = provisioner.sendIdentityClaim(identityClaim);
hirs::pb::IdentityClaimResponse icr;
if (!icr.ParseFromString(response) || !icr.has_credential_blob()) {
if (!icr.ParseFromString(response) || !icr.has_status()) {
logger.error("The ACA did not send a provisioning status.");
cout << "----> Provisioning failed." << endl;
cout << "Please refer to the Attestation CA for details." << endl;
return 0;
}
if (icr.status() == hirs::pb::ResponseStatus::FAIL) {
logger.error("The ACA responded with a FAIL status.");
cout << "----> Provisioning failed." << endl;
cout << "Please refer to the Attestation CA for details." << endl;
return 0;
}
if (!icr.has_credential_blob()) {
logger.error("The ACA did not send make credential blob.");
cout << "----> Provisioning failed." << endl;
cout << "The ACA did not send make credential information." << endl;
@ -183,6 +197,15 @@ int provision() {
const string& akCertificateByteString
= provisioner.sendAttestationCertificateRequest(certificateRequest);
hirs::pb::CertificateResponse cr;
if (!cr.ParseFromString(akCertificateByteString) && cr.has_status()) {
if (cr.status() == hirs::pb::ResponseStatus::FAIL) {
cout << "----> Provisioning the quote failed.";
cout << "Please refer to the Attestation CA for details." << endl;
return 0;
}
}
if (akCertificateByteString == "") {
cout << "----> Provisioning the quote failed.";
cout << "Please refer to the Attestation CA for details." << endl;

View File

@ -110,6 +110,17 @@ public class BaseReferenceManifest extends ReferenceManifest {
return this;
}
/**
* Specify the platform model that rims must have to be considered
* as matching.
* @param model string for the model
* @return this instance
*/
public Selector byModel(final String model) {
setFieldValue(PLATFORM_MODEL, model);
return this;
}
/**
* Specify the device name that rims must have to be considered
* as matching.

View File

@ -61,6 +61,17 @@ public class EventLogMeasurements extends ReferenceManifest {
return this;
}
/**
* Specify the platform model that rims must have to be considered
* as matching.
* @param model string for the model
* @return this instance
*/
public Selector byModel(final String model) {
setFieldValue(PLATFORM_MODEL, model);
return this;
}
/**
* Specify the device name that rims must have to be considered
* as matching.

View File

@ -30,7 +30,7 @@ public class ReferenceDigestRecord extends ArchivableEntity {
private String model;
@Column(nullable = false)
private String deviceName;
@Column(columnDefinition = "blob", nullable = true)
@Column(columnDefinition = "mediumblob", nullable = true)
private byte[] valueBlob;
/**

View File

@ -1,11 +1,16 @@
package hirs.data.persist;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.bouncycastle.util.Arrays;
import org.hibernate.annotations.Type;
import javax.persistence.Access;
import javax.persistence.AccessType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Table;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlRootElement;
import java.util.Objects;
import java.util.UUID;
@ -14,70 +19,144 @@ import java.util.UUID;
* Digest Value, Event Type, index, RIM Tagid
*/
@Entity
public class ReferenceDigestValue extends AbstractEntity {
@Table(name = "ReferenceDigestValue")
@XmlRootElement(name = "ReferenceDigestValue")
@XmlAccessorType(XmlAccessType.FIELD)
@Access(AccessType.FIELD)
public class ReferenceDigestValue extends ArchivableEntity {
private static final Logger LOGGER = LogManager.getLogger(ReferenceDigestValue.class);
@Type(type = "uuid-char")
@Column
private UUID digestRecordId;
private UUID baseRimId;
@Type(type = "uuid-char")
@Column
private UUID supportRimId;
@Column(nullable = false)
private String manufacturer;
@Column(nullable = false)
private String model;
@Column(nullable = false)
private int pcrIndex;
@Column(nullable = false)
private String digestValue;
@Column(nullable = false)
private String eventType;
@Column(columnDefinition = "blob", nullable = true)
private byte[] contentBlob;
@Column(nullable = false)
private boolean matchFail;
@Column(nullable = false)
private boolean patched = false;
/**
* Default Constructor.
* Default constructor necessary for Hibernate.
*/
public ReferenceDigestValue() {
protected ReferenceDigestValue() {
super();
this.digestRecordId = UUID.randomUUID();
this.baseRimId = null;
this.supportRimId = null;
this.manufacturer = "";
this.model = "";
this.pcrIndex = -1;
this.digestValue = "";
this.eventType = "";
this.matchFail = false;
this.patched = false;
this.contentBlob = null;
}
/**
* Default Constructor with parameters for all associated data.
* @param digestRecordId the UUID of the associated record
* @param baseRimId the UUID of the associated record
* @param supportRimId the UUID of the associated record
* @param manufacturer associated creator for this information
* @param model the specific device type
* @param pcrIndex the event number
* @param digestValue the key digest value
* @param eventType the event type to store
* @param matchFail the status of the baseline check
* @param patched the status of the value being updated to to patch
* @param contentBlob the data value of the content
*/
public ReferenceDigestValue(final UUID digestRecordId, final int pcrIndex,
final String digestValue, final String eventType,
final boolean matchFail, final boolean patched) {
this.digestRecordId = digestRecordId;
public ReferenceDigestValue(final UUID baseRimId, final UUID supportRimId,
final String manufacturer, final String model,
final int pcrIndex, final String digestValue,
final String eventType, final boolean matchFail,
final boolean patched, final byte[] contentBlob) {
this.baseRimId = baseRimId;
this.supportRimId = supportRimId;
this.manufacturer = manufacturer;
this.model = model;
this.pcrIndex = pcrIndex;
this.digestValue = digestValue;
this.eventType = eventType;
this.matchFail = matchFail;
this.patched = patched;
this.contentBlob = Arrays.clone(contentBlob);
}
/**
* Getter for the digest record UUID.
* @return the string of the UUID
*/
public UUID getDigestRecordId() {
return digestRecordId;
public UUID getBaseRimId() {
return baseRimId;
}
/**
* Setter for the digest record UUID.
* @param digestRecordId the value to store
* @param baseRimId the value to store
*/
public void setDigestRecordId(final UUID digestRecordId) {
this.digestRecordId = digestRecordId;
public void setBaseRimId(final UUID baseRimId) {
this.baseRimId = baseRimId;
}
/**
* Getter for the digest record UUID.
* @return the string of the UUID
*/
public UUID getSupportRimId() {
return supportRimId;
}
/**
* Setter for the digest record UUID.
* @param supportRimId the value to store
*/
public void setSupportRimId(final UUID supportRimId) {
this.supportRimId = supportRimId;
}
/**
* Getter for the manufacturer value.
* @return the stored value
*/
public String getManufacturer() {
return manufacturer;
}
/**
* Setter for the manufacturer value.
* @param manufacturer the value to store
*/
public void setManufacturer(final String manufacturer) {
this.manufacturer = manufacturer;
}
/**
* Getter for the model value.
* @return the stored value
*/
public String getModel() {
return model;
}
/**
* Setter for the model value.
* @param model the value to store
*/
public void setModel(final String model) {
this.model = model;
}
/**
@ -160,6 +239,36 @@ public class ReferenceDigestValue extends AbstractEntity {
this.patched = patched;
}
/**
* Getter for the byte array of event values.
* @return a clone of the byte array
*/
public byte[] getContentBlob() {
return contentBlob.clone();
}
/**
* Setter for the byte array of values.
* @param contentBlob non-null array.
*/
public void setContentBlob(final byte[] contentBlob) {
if (contentBlob != null) {
this.contentBlob = contentBlob.clone();
}
}
/**
* Helper method to update the attributes of this object.
* @param support the associated RIM.
*/
public void updateInfo(final SupportReferenceManifest support) {
if (support != null && support.getId().equals(getSupportRimId())) {
setBaseRimId(support.getAssociatedRim());
setManufacturer(support.getPlatformManufacturer());
setModel(support.getPlatformModel());
}
}
@Override
public boolean equals(final Object obj) {
if (this == obj) {
@ -171,13 +280,14 @@ public class ReferenceDigestValue extends AbstractEntity {
ReferenceDigestValue that = (ReferenceDigestValue) obj;
return pcrIndex == that.pcrIndex && matchFail == that.matchFail
&& Objects.equals(digestValue, that.digestValue)
&& Objects.equals(digestRecordId, that.digestRecordId)
&& Objects.equals(baseRimId, that.baseRimId)
&& Objects.equals(supportRimId, that.supportRimId)
&& Objects.equals(eventType, that.eventType);
}
@Override
public int hashCode() {
int result = Objects.hash(pcrIndex, digestValue, digestRecordId,
int result = Objects.hash(pcrIndex, digestValue, manufacturer, model,
eventType, matchFail, patched);
return result;
}
@ -187,7 +297,7 @@ public class ReferenceDigestValue extends AbstractEntity {
* @return a string
*/
public String toString() {
return String.format("ReferenceDigestValue: {%d, %s, %s, %b}",
pcrIndex, digestValue, eventType, matchFail);
return String.format("ReferenceDigestValue: {%s, %d, %s, %s, %b}",
model, pcrIndex, digestValue, eventType, matchFail);
}
}

View File

@ -68,7 +68,7 @@ public abstract class ReferenceManifest extends ArchivableEntity {
private static final Logger LOGGER = LogManager.getLogger(ReferenceManifest.class);
@Column(columnDefinition = "blob", nullable = false)
@Column(columnDefinition = "mediumblob", nullable = false)
@JsonIgnore
private byte[] rimBytes;
@Column(nullable = false)

View File

@ -25,6 +25,9 @@ public class CertificateAuthorityCredential extends Certificate {
*/
public static final String SUBJECT_KEY_IDENTIFIER_FIELD = "subjectKeyIdentifier";
private static final int CA_BYTE_SIZE = 20;
private static final int PREFIX_BYTE_SIZE = 4;
@Column
private final byte[] subjectKeyIdentifier;
@ -85,8 +88,16 @@ public class CertificateAuthorityCredential extends Certificate {
public CertificateAuthorityCredential(final byte[] certificateBytes)
throws IOException {
super(certificateBytes);
this.subjectKeyIdentifier =
getX509Certificate().getExtensionValue(SUBJECT_KEY_IDENTIFIER_EXTENSION);
byte[] tempBytes = getX509Certificate()
.getExtensionValue(SUBJECT_KEY_IDENTIFIER_EXTENSION);
if (tempBytes != null && tempBytes.length > CA_BYTE_SIZE) {
this.subjectKeyIdentifier = truncatePrefixBytes(tempBytes);
} else {
this.subjectKeyIdentifier =
getX509Certificate().getExtensionValue(SUBJECT_KEY_IDENTIFIER_EXTENSION);
}
if (this.subjectKeyIdentifier != null) {
this.subjectKeyIdString = Hex.encodeHexString(this.subjectKeyIdentifier);
}
@ -103,8 +114,18 @@ public class CertificateAuthorityCredential extends Certificate {
public CertificateAuthorityCredential(final Path certificatePath)
throws IOException {
super(certificatePath);
this.subjectKeyIdentifier =
getX509Certificate().getExtensionValue(SUBJECT_KEY_IDENTIFIER_EXTENSION);
byte[] tempBytes = getX509Certificate()
.getExtensionValue(SUBJECT_KEY_IDENTIFIER_EXTENSION);
if (tempBytes.length > CA_BYTE_SIZE) {
this.subjectKeyIdentifier = truncatePrefixBytes(tempBytes);
} else {
this.subjectKeyIdentifier =
getX509Certificate().getExtensionValue(SUBJECT_KEY_IDENTIFIER_EXTENSION);
}
if (this.subjectKeyIdentifier != null) {
this.subjectKeyIdString = Hex.encodeHexString(this.subjectKeyIdentifier);
}
}
/**
@ -141,6 +162,13 @@ public class CertificateAuthorityCredential extends Certificate {
return this.subjectKeyIdString;
}
private byte[] truncatePrefixBytes(final byte[] certificateBytes) {
byte[] temp = new byte[CA_BYTE_SIZE];
System.arraycopy(certificateBytes, PREFIX_BYTE_SIZE, temp, 0, CA_BYTE_SIZE);
return temp;
}
@Override
@SuppressWarnings("checkstyle:avoidinlineconditionals")
public boolean equals(final Object o) {

View File

@ -35,6 +35,7 @@ import java.io.Serializable;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
import java.util.List;
@ -766,6 +767,12 @@ public abstract class AbstractDbManager<T> implements CrudManager<T> {
searchClass = this.clazz;
}
if (searchableColumns != null) {
LOGGER.info(searchClass.getName() + " querying for "
+ Arrays.toString(searchableColumns.entrySet().toArray())
+ " with search strings \"" + search + "\"");
}
//Object that will store query values
FilteredRecordsList<T> aqr = new FilteredRecordsList<>();
@ -786,8 +793,9 @@ public abstract class AbstractDbManager<T> implements CrudManager<T> {
Long recordsFiltered = totalResultCount;
Conjunction and = Restrictions.conjunction();
if (totalResultCount != 0) {
LOGGER.info("Total result count greater than 0");
//Builds the search criteria from all of the searchable columns
if (searchableColumns != null) {
if (searchableColumns != null && !searchableColumns.isEmpty()) {
// Search for all words in all searchable columns
String[] searchWords = search.split(" ");
for (String word : searchWords) {
@ -804,10 +812,16 @@ public abstract class AbstractDbManager<T> implements CrudManager<T> {
}
}
LOGGER.info("Search columns filtered");
//Retrieves a count of all the records after being filtered
criteria.setProjection(Projections.countDistinct("id"))
.add(and);
recordsFiltered = (Long) criteria.uniqueResult();
try {
LOGGER.info("Get unique result from criteria object");
recordsFiltered = (Long) criteria.uniqueResult();
} catch (HibernateException e) {
LOGGER.error(e.getMessage());
}
}
if (recordsFiltered != 0) {
@ -867,6 +881,7 @@ public abstract class AbstractDbManager<T> implements CrudManager<T> {
}
throw e;
}
LOGGER.info(searchClass.getName() + " found " + aqr.getRecordsTotal() + " records");
return aqr;
}

View File

@ -1,7 +1,10 @@
package hirs.persist;
import hirs.data.persist.BaseReferenceManifest;
import hirs.data.persist.ReferenceDigestRecord;
import hirs.data.persist.ReferenceDigestValue;
import hirs.data.persist.ReferenceManifest;
import hirs.data.persist.SupportReferenceManifest;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.hibernate.Session;
@ -10,7 +13,9 @@ import org.hibernate.Transaction;
import org.hibernate.criterion.Restrictions;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.UUID;
/**
@ -30,6 +35,7 @@ public class DBReferenceEventManager extends DBManager<ReferenceDigestValue>
public DBReferenceEventManager(final SessionFactory sessionFactory) {
super(ReferenceDigestValue.class, sessionFactory);
}
@Override
public ReferenceDigestValue saveValue(final ReferenceDigestValue referenceDigestValue) {
LOGGER.debug("saving event digest value: {}", referenceDigestValue);
@ -48,7 +54,7 @@ public class DBReferenceEventManager extends DBManager<ReferenceDigestValue>
return null;
}
if (referenceDigestValue.getDigestRecordId() == null
if (referenceDigestValue.getSupportRimId() == null
|| referenceDigestValue.getDigestValue() == null
|| referenceDigestValue.getPcrIndex() == -1) {
LOGGER.error("No reference to get record from db {}", referenceDigestValue);
@ -62,8 +68,8 @@ public class DBReferenceEventManager extends DBManager<ReferenceDigestValue>
LOGGER.debug("retrieving referenceDigestValue from db");
tx = session.beginTransaction();
dbRecord = (ReferenceDigestValue) session.createCriteria(ReferenceDigestValue.class)
.add(Restrictions.eq("digestRecordId",
referenceDigestValue.getDigestRecordId()))
.add(Restrictions.eq("supportRimId",
referenceDigestValue.getSupportRimId()))
.add(Restrictions.eq("digestValue",
referenceDigestValue.getDigestValue()))
.add(Restrictions.eq("eventNumber",
@ -82,6 +88,18 @@ public class DBReferenceEventManager extends DBManager<ReferenceDigestValue>
return dbRecord;
}
@Override
public final Set<ReferenceDigestValue> getEventList() throws DeviceManagerException {
LOGGER.debug("getting ReferenceDigestValue list");
try {
final List<ReferenceDigestValue> events = super.getList(ReferenceDigestValue.class);
return new HashSet<>(events);
} catch (DBManagerException e) {
throw new DeviceManagerException(e);
}
}
@Override
public ReferenceDigestValue getValueById(final ReferenceDigestValue referenceDigestValue) {
LOGGER.debug("Getting record for {}", referenceDigestValue);
@ -118,24 +136,108 @@ public class DBReferenceEventManager extends DBManager<ReferenceDigestValue>
}
@Override
public List<ReferenceDigestValue> getValuesByRecordId(
final ReferenceDigestRecord referenceDigestRecord) {
LOGGER.debug("Getting digest values for {}", referenceDigestRecord);
if (referenceDigestRecord == null) {
LOGGER.error("null referenceDigestRecord argument");
throw new NullPointerException("null referenceDigestRecord");
}
if (referenceDigestRecord.getId() == null) {
LOGGER.error("null referenceDigestRecord ID argument");
throw new NullPointerException("null referenceDigestRecord ID");
public List<ReferenceDigestValue> getValueByManufacturer(final String manufacturer) {
if (manufacturer == null) {
LOGGER.error("null manufacturer argument");
throw new NullPointerException("null manufacturer parameter");
}
List<ReferenceDigestValue> dbDigestValues = new ArrayList<>();
UUID uuid = referenceDigestRecord.getId();
try {
List<ReferenceDigestValue> dbTempList = super.getList(ReferenceDigestValue.class);
for (ReferenceDigestValue rdv : dbTempList) {
if (rdv.getDigestRecordId().equals(uuid)) {
if (rdv.getManufacturer().equals(manufacturer)) {
dbDigestValues.add(rdv);
}
}
} catch (DBManagerException dbMEx) {
throw new RuntimeException(dbMEx);
}
return dbDigestValues;
}
@Override
public List<ReferenceDigestValue> getValueByModel(final String model) {
if (model == null) {
LOGGER.error("null model argument");
throw new NullPointerException("null model parameter");
}
List<ReferenceDigestValue> dbDigestValues = new ArrayList<>();
try {
List<ReferenceDigestValue> dbTempList = super.getList(ReferenceDigestValue.class);
for (ReferenceDigestValue rdv : dbTempList) {
if (rdv.getModel().equals(model)) {
dbDigestValues.add(rdv);
}
}
} catch (DBManagerException dbMEx) {
throw new RuntimeException(dbMEx);
}
return dbDigestValues;
}
@Override
public List<ReferenceDigestValue> getValueByManufacturerModel(
final String manufacturer, final String model) {
if (model == null) {
LOGGER.error("null model argument");
throw new NullPointerException("null model parameter");
}
if (manufacturer == null) {
LOGGER.error("null manufacturer argument");
throw new NullPointerException("null manufacturer parameter");
}
List<ReferenceDigestValue> dbDigestValues = new ArrayList<>();
try {
List<ReferenceDigestValue> dbTempList = super.getList(ReferenceDigestValue.class);
for (ReferenceDigestValue rdv : dbTempList) {
if (rdv.getManufacturer().equals(manufacturer)
&& rdv.getModel().equals(model)) {
dbDigestValues.add(rdv);
}
}
} catch (DBManagerException dbMEx) {
throw new RuntimeException(dbMEx);
}
return dbDigestValues;
}
@Override
public List<ReferenceDigestValue> getValuesByRecordId(
final ReferenceDigestRecord referenceDigestRecord) {
List<ReferenceDigestValue> dbDigestValues = new ArrayList<>(0);
return dbDigestValues;
}
@Override
public List<ReferenceDigestValue> getValuesByRimId(
final ReferenceManifest referenceManifest) {
LOGGER.debug("Getting digest values for {}", referenceManifest);
if (referenceManifest == null) {
LOGGER.error("null referenceManifest argument");
throw new NullPointerException("null referenceManifest");
}
if (referenceManifest.getId() == null) {
LOGGER.error("null referenceManifest ID argument");
throw new NullPointerException("null referenceManifest ID");
}
List<ReferenceDigestValue> dbDigestValues = new ArrayList<>();
UUID uuid = referenceManifest.getId();
UUID rdvUuid = UUID.randomUUID();
try {
final List<ReferenceDigestValue> dbTempList
= super.getList(ReferenceDigestValue.class);
for (ReferenceDigestValue rdv : dbTempList) {
if (referenceManifest instanceof BaseReferenceManifest) {
rdvUuid = rdv.getBaseRimId();
} else if (referenceManifest instanceof SupportReferenceManifest) {
rdvUuid = rdv.getSupportRimId();
}
if (rdvUuid.equals(uuid)) {
dbDigestValues.add(rdv);
}
}
@ -155,7 +257,8 @@ public class DBReferenceEventManager extends DBManager<ReferenceDigestValue>
List<ReferenceDigestValue> dbDigestValues = new ArrayList<>();
try {
List<ReferenceDigestValue> dbTempList = super.getList(ReferenceDigestValue.class);
final List<ReferenceDigestValue> dbTempList
= super.getList(ReferenceDigestValue.class);
for (ReferenceDigestValue rdv : dbTempList) {
if (rdv.getEventType().equals(eventType)) {
dbDigestValues.add(rdv);

View File

@ -10,7 +10,7 @@ import java.util.UUID;
* This class facilitates the persistence of {@link hirs.data.persist.ReferenceDigestRecord}s
* including storage, retrieval, and deletion.
*/
public interface ReferenceDigestManager {
public interface ReferenceDigestManager extends OrderedListQuerier<ReferenceDigestRecord> {
/**
* Persists a new Reference Digest.

View File

@ -2,14 +2,16 @@ package hirs.persist;
import hirs.data.persist.ReferenceDigestRecord;
import hirs.data.persist.ReferenceDigestValue;
import hirs.data.persist.ReferenceManifest;
import java.util.List;
import java.util.Set;
/**
* This class facilitates the persistence of {@link hirs.data.persist.ReferenceDigestValue}s
* including storage, retrieval, and deletion.
*/
public interface ReferenceEventManager {
public interface ReferenceEventManager extends OrderedListQuerier<ReferenceDigestValue> {
/**
* Persists a new Reference Digest value.
*
@ -34,6 +36,31 @@ public interface ReferenceEventManager {
*/
ReferenceDigestValue getValueById(ReferenceDigestValue referenceDigestValue);
/**
* Persists a new Reference Digest Value.
*
* @param manufacturer the string value to search for
* @return the persisted ReferenceDigestValue
*/
List<ReferenceDigestValue> getValueByManufacturer(String manufacturer);
/**
* Persists a new Reference Digest.
*
* @param model the string value to search for
* @return the persisted ReferenceDigestValue
*/
List<ReferenceDigestValue> getValueByModel(String model);
/**
* Persists a new Reference Digest.
*
* @param manufacturer the string value to search for
* @param model the string value to search for
* @return the persisted ReferenceDigestValue
*/
List<ReferenceDigestValue> getValueByManufacturerModel(String manufacturer, String model);
/**
* Persists a new Reference Digest value.
*
@ -42,6 +69,14 @@ public interface ReferenceEventManager {
*/
List<ReferenceDigestValue> getValuesByRecordId(ReferenceDigestRecord referenceDigestRecord);
/**
* Persists a new Reference Digest value.
*
* @param referenceManifest the referenceManifest
* @return the persisted list of ReferenceDigestValue
*/
List<ReferenceDigestValue> getValuesByRimId(ReferenceManifest referenceManifest);
/**
* Persists a new Reference Digest value.
*
@ -50,6 +85,15 @@ public interface ReferenceEventManager {
*/
List<ReferenceDigestValue> getValueByEventType(String eventType);
/**
* Returns a list of all <code>ReferenceDigestValue</code>s that are ordered by a column
* and direction (ASC, DESC) that is provided by the user. This method
* helps support the server-side processing in the JQuery DataTables.
*
* @return FilteredRecordsList object with fields for DataTables
*/
Set<ReferenceDigestValue> getEventList();
/**
* Updates an existing ReferenceDigestRecord.
* @param referenceDigestValue the Reference Event update

View File

@ -180,7 +180,7 @@ public class ReferenceManifestValidator {
}
} else {
subjectKeyIdentifier = getKeyName(rim);
if (subjectKeyIdentifier.equals(cert.getSubjectKeyIdString().substring(8))) {
if (subjectKeyIdentifier.equals(cert.getSubjectKeyIdString())) {
context = new DOMValidateContext(cert.getX509Certificate().getPublicKey(),
nodes.item(0));
}

View File

@ -77,7 +77,7 @@ public class CertificateTest {
* Hex-encoded subject key identifier for the FAKE_ROOT_CA_FILE.
*/
public static final String FAKE_ROOT_CA_SUBJECT_KEY_IDENTIFIER_HEX =
"0416041458ec313a1699f94c1c8c4e2c6412402b258f0177";
"58ec313a1699f94c1c8c4e2c6412402b258f0177";
/**
* Location of a test STM endorsement credential.

View File

@ -1 +1 @@
2.1.1
2.1.2

View File

@ -1,12 +1,11 @@
apply plugin: 'java'
version = '2.1.0'
repositories {
mavenCentral()
}
dependencies {
compile 'javax.json:javax.json-api:1.1.4', 'org.glassfish:javax.json:1.1.4', 'com.beust:jcommander:1.72', 'org.bouncycastle:bcmail-jdk15on:1.59'
compile 'javax.json:javax.json-api:1.1.4', 'org.glassfish:javax.json:1.1.4', 'com.beust:jcommander:1.72', 'org.bouncycastle:bcmail-jdk15on:1.59'
testCompile 'org.testng:testng:6.8.8'
}

View File

@ -1,17 +1,20 @@
#!/bin/bash
VERSION=2.1.0
GIT_HASH=`git rev-parse HEAD | head -c6`
GIT_COMMIT_UNIX_TIMESTAMP=`git show -s --format=%ct | xargs echo -n`
RELEASE="$((GIT_COMMIT_UNIX_TIMESTAMP)).$GIT_HASH"
name="tcg_rim_tool"
# Enter package directory
SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
pushd $SCRIPT_DIR
name="tcg_rim_tool"
tar -cf $name.tar build.gradle gradle* src/ docs/ rim_fields.json keystore.jks scripts/
gzip -f $name.tar
tar -cf "$name-$VERSION.$RELEASE".tar build.gradle gradle* src/ docs/ rim_fields.json keystore.jks scripts/
gzip -f "$name-$VERSION.$RELEASE".tar
if [ -d rpmbuild ]; then
rm -rf rpmbuild
fi
mkdir -p rpmbuild/BUILD rpmbuild/BUILDROOT rpmbuild/SOURCES rpmbuild/RPMS rpmbuild/SPECS rpmbuild/SRPMS
rpmbuild -bb $name.spec --define "_sourcedir $PWD" --define "_topdir $PWD/rpmbuild"
rpmbuild -bb $name.spec --define "_sourcedir $PWD" --define "_topdir $PWD/rpmbuild" --define 'RELEASE '$RELEASE --define 'VERSION '$VERSION
popd

View File

@ -49,6 +49,7 @@ public class Main {
String jksTruststoreFile = commander.getTruststoreFile();
String certificateFile = commander.getPublicCertificate();
String privateKeyFile = commander.getPrivateKeyFile();
boolean defaultKey = commander.isDefaultKey();
String rimEventLog = commander.getRimEventLog();
switch (createType) {
case "BASE":
@ -62,9 +63,13 @@ public class Main {
gateway.setDefaultCredentials(false);
gateway.setPemCertificateFile(certificateFile);
gateway.setPemPrivateKeyFile(privateKeyFile);
} else {
} else if (defaultKey){
gateway.setDefaultCredentials(true);
gateway.setJksTruststoreFile(SwidTagConstants.DEFAULT_KEYSTORE_FILE);
} else {
System.out.println("A private key (-k) and public certificate (-p) " +
"are required, or the default key (-d) must be indicated.");
System.exit(1);
}
if (rimEventLog.isEmpty()) {
System.out.println("Error: a support RIM is required!");

View File

@ -36,6 +36,9 @@ public class Commander {
description = "The public key certificate to embed in the base RIM created by "
+ "this tool.")
private String publicCertificate = "";
@Parameter(names = {"-d", "--default-key"},
description = "Use default signing credentials.")
private boolean defaultKey = false;
@Parameter(names = {"-l", "--rimel <path>"}, order = 7,
description = "The TCG eventlog file to use as a support RIM.")
private String rimEventLog = "";
@ -70,14 +73,16 @@ public class Commander {
return publicCertificate;
}
public boolean isDefaultKey() { return defaultKey; }
public String getRimEventLog() { return rimEventLog; }
public String printHelpExamples() {
StringBuilder sb = new StringBuilder();
sb.append("Create a base RIM using the values in attributes.json; " +
"sign it with the default keystore, alias, and password;\n");
"sign it with the default keystore; ");
sb.append("and write the data to base_rim.swidtag:\n\n");
sb.append("\t\t-c base -a attributes.json -l support_rim.bin -o base_rim.swidtag\n\n\n");
sb.append("\t\t-c base -a attributes.json -d -l support_rim.bin -o base_rim.swidtag\n\n\n");
sb.append("Create a base RIM using the default attribute values; ");
sb.append("sign it using privateKey.pem; embed cert.pem in the signature block; ");
sb.append("and write the data to console output:\n\n");
@ -103,9 +108,11 @@ public class Commander {
!this.getPublicCertificate().isEmpty()) {
sb.append("Private key file: " + this.getPrivateKeyFile() + System.lineSeparator());
sb.append("Public certificate: " + this.getPublicCertificate() + System.lineSeparator());
} else {
} else if (this.isDefaultKey()){
sb.append("Truststore file: default (" + SwidTagConstants.DEFAULT_KEYSTORE_FILE + ")"
+ System.lineSeparator());
} else {
sb.append("Signing credential: (none given)" + System.lineSeparator());
}
sb.append("Event log support RIM: " + this.getRimEventLog() + System.lineSeparator());
return sb.toString();

View File

@ -1,17 +1,19 @@
Name: tcg_rim_tool
Version: 2.1.0
Release: 1%{?dist}
Version: %{?VERSION}
Release: %{?RELEASE}
Summary: A java command-line tool to create PC client root RIM
License: ASL 2.0
URL: https://github.com/nsacyber/HIRS
Source0: %{name}.tar.gz
Source0: %{name}-%{version}.%{release}.tar.gz
BuildRequires: java-headless >= 1:1.8.0
%description
This tool will generate a base RIM file for PC clients in accordance with the schema located at http://standards.iso.org/iso/19770/-2/2015/schema.xsd. The generated RIM can either be empty if no arguments are given, or contain a payload if an input file is provided. The tool can also verify a given RIMfile against the schema. Use -h or --help to see a list of commands and uses.
%global __os_install_post %{nil}
%prep
%setup -q -c -n %{name}
@ -19,7 +21,7 @@ This tool will generate a base RIM file for PC clients in accordance with the sc
rm -f /opt/hirs/rimtool/%{name}*.jar
%build
./gradlew build
./gradlew -Pversion=%{version} build
%install
mkdir -p %{buildroot}/opt/hirs/rimtool/ %{buildroot}/usr/local/bin