unofficial mirror of guix-devel@gnu.org 
 help / color / mirror / code / Atom feed
From: Jelle Licht <jlicht@fsfe.org>
To: "Liliana Marie Prikler" <liliana.prikler@gmail.com>,
	"Ludovic Courtès" <ludo@gnu.org>
Cc: guix-devel@gnu.org
Subject: Re: Using G-Expressions for public keys (substitutes and possibly more)
Date: Sun, 21 Nov 2021 01:12:27 +0100	[thread overview]
Message-ID: <86k0h2jris.fsf@fsfe.org> (raw)
In-Reply-To: <ef01e792bb56ecd9eb7ad4c63d9d40b7c356167d.camel@gmail.com>

Hey folks,

Liliana Marie Prikler <liliana.prikler@gmail.com> writes:

> Hi Ludo,
>
> Am Donnerstag, den 21.10.2021, 22:13 +0200 schrieb Ludovic Courtès:
>> Hi!
>> 
>> Liliana Marie Prikler <liliana.prikler@gmail.com> skribis:
>> 
>> > let's say I wanted to add my own substitute server to my
>> > config.scm. 
>> > At the time of writing, I would have to add said server's public
>> > key to
>> > the authorized-keys of my guix-configuration like so:
>> >   (cons* (local-file "my-key.pub") %default-authorized-guix-keys)
>> > or similarily with append.  This local-file incantation is however
>> > pretty weak.  It changes based on the current working directory and
>> > even if I were to use an absolute path, I'd have to copy both that
>> > file
>> > and the config.scm to a new machine were I to use the same
>> > configuration there as well.
>> 
>> Note that you could use ‘plain-file’ instead of ‘local-file’ and
>> inline the key canonical sexp in there.
> Yes, but for that I'd have to either write a (multi-line) string
> directly, which visibly "breaks" indentation of the rest of the file,
> or somehow generate a string which adds at least one layer of
> indentation.  The former is imo unacceptable, the latter merely
> inconvenient.

Would some arbitrary s-expression be a workable solution? See below for
an example for what I understood was your current use-case.

>> > However, it turns out that the format for said key files is some
>> > actually pretty readable Lisp-esque stuff.  For instance, an ECC
>> > key reads like
>> >   (public-key (ecc (curve CURVE) (q #Q#)))
>> > with spaces omitted for simplicity.
>> > Were it not for the (q #Q#) bit, we could construct it using
>> > scheme-file.  In fact, it is so simple that in my local config I
>> > now do exactly that.
>> 
>> Yeah it’s frustrating that canonical sexps are almost, but not quite,
>> Scheme sexps.  :-)
>> 
>> (gcrypt pk-crypto) has a ‘canonical-sexp->sexp’ procedure:
>> 
>> --8<---------------cut here---------------start------------->8---
>> scheme@(guile-user)> ,use(gcrypt pk-crypto)
>> scheme@(guile-user)> ,use(rnrs io ports)
>> scheme@(guile-user)> (string->canonical-sexp
>> 		      (call-with-input-file
>> "etc/substitutes/ci.guix.info.pub"
>> 			get-string-all))
>> $18 = #<canonical-sexp 7fce7f4e8b40 | 15d96a0>
>> scheme@(guile-user)> ,pp (canonical-sexp->sexp $18)
>> $19 = (public-key
>>   (ecc (curve Ed25519)
>>        (q #vu8(141 21 111 41 93 36 176 217 168 111 165 116 26 132 15
>> 242 210 79 96 247 182 196 19 72 20 173 85 98 89 113 179 148))))
>> --8<---------------cut here---------------end--------------->8---
>> 
>> > (define-record-type* <ecc-key> ...)
>> > (define-gexp-compiler (ecc-key-compiler (ecc-key <ecc-key>) ...)
>> > ...)
>> > 
>> > (ecc-key
>> >   (name "my-key.pub")
>> >   (curve 'Ed25519)
>> >   (q "ABCDE..."))
>> > 
>> > Could/should we support such formats out of the box?  WDYT?
>> 
>> With this approach, we’d end up mirroring all the canonical sexps
>> used by libgcrypt, which doesn’t sound great from a maintenance POV.
> Given that we can use canonical sexps, what about a single canonical-
> sexp compiler then?  I'd have to think about this a bit more when I
> have the time to, but having a way of writing the canonical sexp
> "directly" would imo be advantageous.

What about something such as the following?

--8<---------------cut here---------------start------------->8---
(use-modules (gcrypt base16)
             (gcrypt pk-crypto))

(define-record-type <canonical-sexp-wrapper>
  (canonical-sexp-wrapper name sexp)
  canonical-sexp-wrapper?
  (name canonical-sexp-wrapper-name)
  (sexp canonical-sexp-wrapper-sexp))

(define-gexp-compiler (canonical-sexp-wrapper-compiler
                       (wrapper <canonical-sexp-wrapper>) system target)
  (match wrapper
    (($ <canonical-sexp-wrapper> name sexp)
     (text-file name (canonical-sexp->string
                      (sexp->canonical-sexp sexp)) '()))))
--8<---------------cut here---------------end--------------->8---

This would still leave constructing your s-expression as an exercise to
the reader, which is definitely not amazing. In this specific instance,
I had to look at the output of canonical-sexp->sexp, which is of course
whatever the opposite of discoverable and good UX :).

For the Ed25519 key:
--8<---------------cut here---------------start------------->8---
(define my-public-key
  (canonical-sexp-wrapper
   "my-key.pub"
   `(public-key
     (ecc
      (curve Ed25519)
      (q ,(base16-string->bytevector
           (string-downcase
            "C9F307AE...")))))))
--8<---------------cut here---------------end--------------->8---

To improve on this, is one sexp-based-gexp-compiler + N helper functions
to construct the most-used value types a direction worth exploring?

 - Jelle


  reply	other threads:[~2021-11-21  0:12 UTC|newest]

Thread overview: 9+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-10-17 12:47 Using G-Expressions for public keys (substitutes and possibly more) Liliana Marie Prikler
2021-10-21 20:13 ` Ludovic Courtès
2021-10-22  4:47   ` Liliana Marie Prikler
2021-11-21  0:12     ` Jelle Licht [this message]
2021-11-21  8:28       ` Liliana Marie Prikler
2021-11-22 13:27         ` Ludovic Courtès
2021-11-22 14:32           ` Jelle Licht
2021-11-22 19:35           ` Liliana Marie Prikler
2021-11-23 17:14             ` Ludovic Courtès

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://guix.gnu.org/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=86k0h2jris.fsf@fsfe.org \
    --to=jlicht@fsfe.org \
    --cc=guix-devel@gnu.org \
    --cc=liliana.prikler@gmail.com \
    --cc=ludo@gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/guix.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).