richardphibel / rpms / rpm

Forked from rpms/rpm 2 years ago
Clone
45afda
From 3669fecaba2858aeca44d1bfc265760611ea8834 Mon Sep 17 00:00:00 2001
45afda
From: Jes Sorensen <jsorensen@fb.com>
45afda
Date: Wed, 10 Jun 2020 12:30:54 -0400
45afda
Subject: [PATCH 32/33] rpmsign: Add argument to specify algorithm for fsverity
45afda
 signatures
45afda
45afda
The argument --verity-algo can be used to specify the algorithm for
45afda
the fsverity signatures. If nothing is specified, this will default to
45afda
sha256. The available algorithms depend on libfsverity, currently
45afda
sha256 and sha512 are supported.
45afda
45afda
Signed-off-by: Jes Sorensen <jsorensen@fb.com>
45afda
---
45afda
 doc/rpmsign.8        |  3 +++
45afda
 rpmsign.c            |  7 +++++++
45afda
 sign/rpmgensig.c     | 22 ++++++++++++++++++++--
45afda
 sign/rpmsignverity.c |  6 +++---
45afda
 sign/rpmsignverity.h |  2 +-
45afda
 5 files changed, 34 insertions(+), 6 deletions(-)
45afda
45afda
diff --git a/doc/rpmsign.8 b/doc/rpmsign.8
45afda
index a212746fe..5165e39f9 100644
45afda
--- a/doc/rpmsign.8
45afda
+++ b/doc/rpmsign.8
45afda
@@ -55,6 +55,9 @@ Used with \fB--signfiles\fR, use file signing key \fIKey\fR.
45afda
 \fB--certpath \fICERT\fB\fR
45afda
 Used with \fB--signverity\fR, use file signing certificate \fICert\fR.
45afda
 .TP
45afda
+\fB--verityalgo \fIALG\fB\fR
45afda
+Used with \fB--signverity\fR, to specify the signing algorithm. sha256 and sha512 are supported, with sha256 being the default if this argument is not specified. This can also be specified with the macro %_verity_algorithm
45afda
+.TP
45afda
 \fB--signfiles\fR
45afda
 Sign package files. The macro \fB%_binary_filedigest_algorithm\fR must
45afda
 be set to a supported algorithm before building the package. The
45afda
diff --git a/rpmsign.c b/rpmsign.c
45afda
index e43811e9f..12299379c 100644
45afda
--- a/rpmsign.c
45afda
+++ b/rpmsign.c
45afda
@@ -25,6 +25,7 @@ static char * fileSigningKey = NULL;
45afda
 #endif
45afda
 #ifdef WITH_FSVERITY
45afda
 static char * fileSigningCert = NULL;
45afda
+static char * verityAlgorithm = NULL;
45afda
 #endif
45afda
 
45afda
 static struct rpmSignArgs sargs = {NULL, 0, 0};
45afda
@@ -52,6 +53,9 @@ static struct poptOption signOptsTable[] = {
45afda
     { "signverity", '\0', (POPT_ARG_VAL|POPT_ARGFLAG_OR),
45afda
 	&sargs.signflags, RPMSIGN_FLAG_FSVERITY,
45afda
 	N_("generate fsverity signatures for package(s) files"), NULL},
45afda
+    { "verityalgo", '\0', POPT_ARG_STRING, &verityAlgorithm, 0,
45afda
+	N_("algorithm to use for verity signatures, default sha256"),
45afda
+	N_("<algorithm>") },
45afda
     { "certpath", '\0', POPT_ARG_STRING, &fileSigningCert, 0,
45afda
 	N_("use file signing cert <cert>"),
45afda
 	N_("<cert>") },
45afda
@@ -138,6 +142,9 @@ static int doSign(poptContext optCon, struct rpmSignArgs *sargs)
45afda
     if (fileSigningCert) {
45afda
 	rpmPushMacro(NULL, "_file_signing_cert", NULL, fileSigningCert, RMIL_GLOBAL);
45afda
     }
45afda
+    if (verityAlgorithm) {
45afda
+	rpmPushMacro(NULL, "_verity_algorithm", NULL, verityAlgorithm, RMIL_GLOBAL);
45afda
+    }
45afda
 #endif
45afda
 
45afda
     if (flags_sign_files(sargs->signflags)) {
45afda
diff --git a/sign/rpmgensig.c b/sign/rpmgensig.c
45afda
index 02cf0bc62..b3b02828a 100644
45afda
--- a/sign/rpmgensig.c
45afda
+++ b/sign/rpmgensig.c
45afda
@@ -8,6 +8,10 @@
45afda
 #include <errno.h>
45afda
 #include <sys/wait.h>
45afda
 #include <popt.h>
45afda
+#include <fcntl.h>
45afda
+#ifdef WITH_FSVERITY
45afda
+#include <libfsverity.h>
45afda
+#endif
45afda
 
45afda
 #include <rpm/rpmlib.h>			/* RPMSIGTAG & related */
45afda
 #include <rpm/rpmmacro.h>
45afda
@@ -458,23 +462,37 @@ static rpmRC includeFileSignatures(Header *sigp, Header *hdrp)
45afda
 static rpmRC includeVeritySignatures(FD_t fd, Header *sigp, Header *hdrp)
45afda
 {
45afda
 #ifdef WITH_FSVERITY
45afda
-    rpmRC rc;
45afda
+    rpmRC rc = RPMRC_OK;
45afda
     char *key = rpmExpand("%{?_file_signing_key}", NULL);
45afda
     char *keypass = rpmExpand("%{?_file_signing_key_password}", NULL);
45afda
     char *cert = rpmExpand("%{?_file_signing_cert}", NULL);
45afda
+    char *algorithm = rpmExpand("%{?_verity_algorithm}", NULL);
45afda
+    uint16_t algo = 0;
45afda
 
45afda
     if (rstreq(keypass, "")) {
45afda
 	free(keypass);
45afda
 	keypass = NULL;
45afda
     }
45afda
 
45afda
+    if (algorithm && strlen(algorithm) > 0) {
45afda
+	    algo = libfsverity_find_hash_alg_by_name(algorithm);
45afda
+	    rpmlog(RPMLOG_DEBUG, _("Searching for algorithm %s got %i\n"),
45afda
+		   algorithm, algo);
45afda
+	    if (!algo) {
45afda
+		    rpmlog(RPMLOG_ERR, _("Unsupported fsverity algorithm %s\n"),
45afda
+			   algorithm);
45afda
+		    rc = RPMRC_FAIL;
45afda
+		    goto out;
45afda
+	    }
45afda
+    }
45afda
     if (key && cert) {
45afda
-	rc = rpmSignVerity(fd, *sigp, *hdrp, key, keypass, cert);
45afda
+	    rc = rpmSignVerity(fd, *sigp, *hdrp, key, keypass, cert, algo);
45afda
     } else {
45afda
 	rpmlog(RPMLOG_ERR, _("fsverity signatures requires a key and a cert\n"));
45afda
 	rc = RPMRC_FAIL;
45afda
     }
45afda
 
45afda
+ out:
45afda
     free(keypass);
45afda
     free(key);
45afda
     free(cert);
45afda
diff --git a/sign/rpmsignverity.c b/sign/rpmsignverity.c
45afda
index 55096e732..e6c830cdc 100644
45afda
--- a/sign/rpmsignverity.c
45afda
+++ b/sign/rpmsignverity.c
45afda
@@ -95,7 +95,7 @@ static char *rpmVeritySignFile(rpmfi fi, size_t *sig_size, char *key,
45afda
 }
45afda
 
45afda
 rpmRC rpmSignVerity(FD_t fd, Header sigh, Header h, char *key,
45afda
-		    char *keypass, char *cert)
45afda
+		    char *keypass, char *cert, uint16_t algo)
45afda
 {
45afda
     int rc;
45afda
     FD_t gzdi;
45afda
@@ -111,7 +111,6 @@ rpmRC rpmSignVerity(FD_t fd, Header sigh, Header h, char *key,
45afda
     char **signatures = NULL;
45afda
     size_t sig_size;
45afda
     int nr_files, idx;
45afda
-    uint16_t algo;
45afda
     uint32_t algo32;
45afda
 
45afda
     Fseek(fd, 0, SEEK_SET);
45afda
@@ -156,7 +155,8 @@ rpmRC rpmSignVerity(FD_t fd, Header sigh, Header h, char *key,
45afda
     nr_files = rpmfiFC(hfi);
45afda
     signatures = xcalloc(nr_files, sizeof(char *));
45afda
 
45afda
-    algo = FS_VERITY_HASH_ALG_SHA256;
45afda
+    if (!algo)
45afda
+	    algo = FS_VERITY_HASH_ALG_SHA256;
45afda
 
45afda
     rpmlog(RPMLOG_DEBUG, _("file count - header: %i, payload %i\n"),
45afda
 	   nr_files, rpmfiFC(fi));
45afda
diff --git a/sign/rpmsignverity.h b/sign/rpmsignverity.h
45afda
index 69bbaf7f7..d869e8d8e 100644
45afda
--- a/sign/rpmsignverity.h
45afda
+++ b/sign/rpmsignverity.h
45afda
@@ -27,7 +27,7 @@ extern "C" {
45afda
  */
45afda
 RPM_GNUC_INTERNAL
45afda
 rpmRC rpmSignVerity(FD_t fd, Header sigh, Header h, char *key,
45afda
-		    char *keypass, char *cert);
45afda
+		    char *keypass, char *cert, uint16_t algo);
45afda
 
45afda
 #ifdef _cplusplus
45afda
 }
45afda
-- 
45afda
2.27.0
45afda