Merge pull request #620 from nsacyber/v3_rim-validator-update

Update to the RIM Validator
This commit is contained in:
Cyrus 2023-11-01 06:48:48 -04:00 committed by GitHub
commit 316f3ec99e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 34 additions and 25 deletions

View File

@ -90,7 +90,7 @@ public class FirmwareScvValidator extends SupplyChainCredentialValidator {
// verify signatures
ReferenceManifestValidator referenceManifestValidator =
new ReferenceManifestValidator();
referenceManifestValidator.setRim(baseReferenceManifest);
referenceManifestValidator.setRim(baseReferenceManifest.getRimBytes());
//Validate signing cert
List<CertificateAuthorityCredential> allCerts = caCredentialRepository.findAll();
@ -99,23 +99,28 @@ public class FirmwareScvValidator extends SupplyChainCredentialValidator {
signingCert = cert;
KeyStore keyStore = ValidationService.getCaChain(signingCert,
caCredentialRepository);
if (referenceManifestValidator.validateXmlSignature(signingCert)) {
try {
if (!SupplyChainCredentialValidator.verifyCertificate(
try {
if (referenceManifestValidator.validateXmlSignature(signingCert.getX509Certificate().getPublicKey(),
signingCert.getSubjectKeyIdString(), signingCert.getEncodedPublicKey())) {
try {
if (!SupplyChainCredentialValidator.verifyCertificate(
signingCert.getX509Certificate(), keyStore)) {
passed = false;
passed = false;
fwStatus = new AppraisalStatus(FAIL,
"Firmware validation failed: invalid certificate path.");
validationObject = baseReferenceManifest;
}
} catch (IOException ioEx) {
log.error("Error getting X509 cert from manager: " + ioEx.getMessage());
} catch (SupplyChainValidatorException scvEx) {
log.error("Error validating cert against keystore: " + scvEx.getMessage());
fwStatus = new AppraisalStatus(FAIL,
"Firmware validation failed: invalid certificate path.");
validationObject = baseReferenceManifest;
}
} catch (IOException ioEx) {
log.error("Error getting X509 cert from manager: " + ioEx.getMessage());
} catch (SupplyChainValidatorException scvEx) {
log.error("Error validating cert against keystore: " + scvEx.getMessage());
fwStatus = new AppraisalStatus(FAIL,
"Firmware validation failed: invalid certificate path.");
break;
}
break;
} catch (IOException ioEx) {
log.error("Error getting X509 cert from manager: " + ioEx.getMessage());
}
}

View File

@ -272,7 +272,7 @@ public class ReferenceManifestDetailsPageController extends PageController<Refer
}
// going to have to pull the filename and grab that from the DB
// to get the id to make the link
RIM_VALIDATOR.setRim(baseRim);
RIM_VALIDATOR.setRim(baseRim.getRimBytes());
for (SwidResource swidRes : resources) {
if (support != null && swidRes.getHashValue()
.equalsIgnoreCase(support.getHexDecHash())) {
@ -300,7 +300,8 @@ public class ReferenceManifestDetailsPageController extends PageController<Refer
data.put("signatureValid", false);
for (CertificateAuthorityCredential cert : certificates) {
KeyStore keystore = ValidationService.getCaChain(cert, caCertificateRepository);
if (RIM_VALIDATOR.validateXmlSignature(cert)) {
if (RIM_VALIDATOR.validateXmlSignature(cert.getX509Certificate().getPublicKey(),
cert.getSubjectKeyIdString(), cert.getEncodedPublicKey())) {
try {
if (SupplyChainCredentialValidator.verifyCertificate(
cert.getX509Certificate(), keystore)) {

View File

@ -1,6 +1,5 @@
package hirs.utils.rim;
import hirs.utils.CertificateAuthorityCredential;
import jakarta.xml.bind.JAXBContext;
import jakarta.xml.bind.JAXBException;
import jakarta.xml.bind.UnmarshalException;
@ -78,12 +77,12 @@ public class ReferenceManifestValidator {
* Setter for the RIM to be validated. The ReferenceManifest object is converted into a
* Document for processing.
*
* @param rim ReferenceManifest object
* @param rimBytes ReferenceManifest object bytes
*/
public void setRim(final ReferenceManifest rim) {
public void setRim(final byte[] rimBytes) {
try {
Document doc = validateSwidtagSchema(removeXMLWhitespace(new StreamSource(
new ByteArrayInputStream(rim.getRimBytes()))));
new ByteArrayInputStream(rimBytes))));
this.rim = doc;
} catch (IOException e) {
log.error("Error while unmarshalling rim bytes: " + e.getMessage());
@ -152,11 +151,15 @@ public class ReferenceManifestValidator {
* or the RIM's subject key identifier. If the cert is matched then validation proceeds,
* otherwise validation ends.
*
* @param cert the cert to be checked against the RIM
* @param publicKey public key from the CA credential
* @param subjectKeyIdString string version of the subjet key id of the CA credential
* @param encodedPublicKey the encoded public key
* @return true if the signature element is validated, false otherwise
*/
@SuppressWarnings("magicnumber")
public boolean validateXmlSignature(final CertificateAuthorityCredential cert) {
public boolean validateXmlSignature(final PublicKey publicKey,
final String subjectKeyIdString,
final byte[] encodedPublicKey) {
DOMValidateContext context = null;
try {
NodeList nodes = rim.getElementsByTagNameNS(XMLSignature.XMLNS, "Signature");
@ -171,19 +174,19 @@ public class ReferenceManifestValidator {
if (embeddedCert != null) {
subjectKeyIdentifier = getCertificateSubjectKeyIdentifier(embeddedCert);
if (Arrays.equals(embeddedCert.getPublicKey().getEncoded(),
cert.getEncodedPublicKey())) {
encodedPublicKey)) {
context = new DOMValidateContext(new X509KeySelector(), nodes.item(0));
}
}
} else {
subjectKeyIdentifier = getKeyName(rim);
if (subjectKeyIdentifier.equals(cert.getSubjectKeyIdString())) {
context = new DOMValidateContext(cert.getX509Certificate().getPublicKey(),
if (subjectKeyIdentifier.equals(subjectKeyIdString)) {
context = new DOMValidateContext(publicKey,
nodes.item(0));
}
}
if (context != null) {
publicKey = cert.getX509Certificate().getPublicKey();
this.publicKey = publicKey;
signatureValid = validateSignedXMLDocument(context);
return signatureValid;
}