summary refs log tree commit diff
diff options
context:
space:
mode:
authorLudovic Courtès <ludo@gnu.org>2013-12-28 00:42:07 +0100
committerLudovic Courtès <ludo@gnu.org>2013-12-29 15:57:23 +0100
commit6df1fb8991bc7323dd4974a55d37f249a4e9c4a0 (patch)
tree599841214479f1b49c7c1422bb92e008d7b2f805
parentb0a33ac157ce99688b6d668124377fdd81bf413e (diff)
downloadguix-6df1fb8991bc7323dd4974a55d37f249a4e9c4a0.tar.gz
authenticate: Store the public key as part of the signature.
* guix/scripts/authenticate.scm (signature-sexp): New procedure.
  (guix-authenticate): Use it to produce the signature.  Adjust
  verification code accordingly.
* tests/store.scm ("import corrupt path"): Adjust test accordingly.
-rw-r--r--guix/scripts/authenticate.scm26
-rw-r--r--tests/store.scm4
2 files changed, 22 insertions, 8 deletions
diff --git a/guix/scripts/authenticate.scm b/guix/scripts/authenticate.scm
index 70ba7cb88e..7e1c2a4671 100644
--- a/guix/scripts/authenticate.scm
+++ b/guix/scripts/authenticate.scm
@@ -44,6 +44,17 @@
          (bv  (base16-string->bytevector (string-trim-both hex))))
     (bytevector->hash-data bv)))
 
+(define (signature-sexp data secret-key public-key)
+  "Return a SPKI-style sexp for the signature of DATA with SECRET-KEY that
+includes DATA, the actual signature value (with a 'sig-val' tag), and
+PUBLIC-KEY (see <http://theworld.com/~cme/spki.txt> for examples.)"
+  (string->canonical-sexp
+   (format #f
+           "(signature ~a ~a ~a)"
+           (canonical-sexp->string data)
+           (canonical-sexp->string (sign data secret-key))
+           (canonical-sexp->string public-key))))
+
 
 ;;;
 ;;; Entry point with 'openssl'-compatible interface.  We support this
@@ -57,18 +68,21 @@
      ;; Sign the hash in HASH-FILE with KEY, and return an sexp that includes
      ;; both the hash and the actual signature.
      (let* ((secret-key (read-canonical-sexp key))
-            (data       (read-hash-data hash-file)))
-       (format #t
-               "(guix-signature ~a (payload ~a))"
-               (canonical-sexp->string (sign data secret-key))
-               (canonical-sexp->string data))
+            (public-key (if (string-suffix? ".sec" key)
+                            (read-canonical-sexp
+                             (string-append (string-drop-right key 4) ".pub"))
+                            (leave (_ "cannot find public key for secret key '~a'")
+                                   key)))
+            (data       (read-hash-data hash-file))
+            (signature  (signature-sexp data secret-key public-key)))
+       (display (canonical-sexp->string signature))
        #t))
     (("rsautl" "-verify" "-inkey" key "-pubin" "-in" signature-file)
      ;; Read the signature as produced above, check it against KEY, and print
      ;; the signed data to stdout upon success.
      (let* ((public-key (read-canonical-sexp key))
             (sig+data   (read-canonical-sexp signature-file))
-            (data       (find-sexp-token sig+data 'payload))
+            (data       (find-sexp-token sig+data 'data))
             (signature  (find-sexp-token sig+data 'sig-val)))
        (if (and data signature)
            (if (verify signature data public-key)
diff --git a/tests/store.scm b/tests/store.scm
index 6834ebc5e9..4bd739e7f6 100644
--- a/tests/store.scm
+++ b/tests/store.scm
@@ -373,8 +373,8 @@ Deriver: ~a~%"
                 (cut export-paths %store (list file) <>))))
     (delete-paths %store (list file))
 
-    ;; Flip a bit in the middle of the stream.
-    (let* ((index (quotient (bytevector-length dump) 3))
+    ;; Flip a bit in the stream's payload.
+    (let* ((index (quotient (bytevector-length dump) 4))
            (byte  (bytevector-u8-ref dump index)))
       (bytevector-u8-set! dump index (logxor #xff byte)))