From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mp10.migadu.com ([2001:41d0:8:6d80::]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) by ms5.migadu.com with LMTPS id qD2TJ2ti2mM6GQAAbAwnHQ (envelope-from ) for ; Wed, 01 Feb 2023 14:00:27 +0100 Received: from aspmx1.migadu.com ([2001:41d0:8:6d80::]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) by mp10.migadu.com with LMTPS id aGnLJmti2mMgQAAAG6o9tA (envelope-from ) for ; Wed, 01 Feb 2023 14:00:27 +0100 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by aspmx1.migadu.com (Postfix) with ESMTPS id 61DD9187A1 for ; Wed, 1 Feb 2023 14:00:26 +0100 (CET) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1pNCid-0003D5-UN; Wed, 01 Feb 2023 08:00:07 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1pNCiZ-0003Cj-Ft for guix-patches@gnu.org; Wed, 01 Feb 2023 08:00:04 -0500 Received: from debbugs.gnu.org ([209.51.188.43]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1pNCiZ-0006r1-5h for guix-patches@gnu.org; Wed, 01 Feb 2023 08:00:03 -0500 Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.84_2) (envelope-from ) id 1pNCiY-0005T4-Iy for guix-patches@gnu.org; Wed, 01 Feb 2023 08:00:02 -0500 X-Loop: help-debbugs@gnu.org Subject: [bug#60753] [PATCH] gnu: home: Add home-emacs-service-type. Resent-From: Jelle Licht Original-Sender: "Debbugs-submit" Resent-CC: guix-patches@gnu.org Resent-Date: Wed, 01 Feb 2023 13:00:02 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 60753 X-GNU-PR-Package: guix-patches X-GNU-PR-Keywords: patch To: Andrew Tropin , Ludovic =?UTF-8?Q?Court=C3=A8s?= Cc: "\(" , David Wilson , 60753@debbugs.gnu.org Received: via spool by 60753-submit@debbugs.gnu.org id=B60753.167525639420977 (code B ref 60753); Wed, 01 Feb 2023 13:00:02 +0000 Received: (at 60753) by debbugs.gnu.org; 1 Feb 2023 12:59:54 +0000 Received: from localhost ([127.0.0.1]:56811 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1pNCiP-0005SG-GH for submit@debbugs.gnu.org; Wed, 01 Feb 2023 07:59:54 -0500 Received: from mout01.posteo.de ([185.67.36.65]:46601) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1pNCiN-0005S3-DT for 60753@debbugs.gnu.org; Wed, 01 Feb 2023 07:59:52 -0500 Received: from submission (posteo.de [185.67.36.169]) by mout01.posteo.de (Postfix) with ESMTPS id 8D3362405FF for <60753@debbugs.gnu.org>; Wed, 1 Feb 2023 13:59:45 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=posteo.net; s=2017; t=1675256385; bh=9qbnzqCFFiLos99ujlRS6vefX/3EXQbOBH/NiG8FG+M=; h=From:To:Cc:Subject:Date:From; b=aUe8Dh17Q1gh0fQmeJwcByoppt8FCjN4sRhxnjL5Gcq9URpm5PcYq3fGQQG9FWxb3 R+n8i4Pifkp6scDjae2v5YETTJRQEHOgcQJ0Y+Nr2IzkcbI/JSFCFqAPqROBJqpzpP A++yiSo9dKqMmp2kgP3Fah+bkqj0QyEfSE6MAhxWviF55xFiI8sshEyXLHOMx79Rdy TKoOJ1ASdQMZhZKM8gwI6fc9EzBkZAAQRMZCGnVtQWhJygV4iamTBXCPan7n5ylBex wwsp0ZV3xGarY/00kuwIpFTCWCFtPuW+l0Gcb1iD2pZYAxztln0k5rWtq2EiZ5Rb6I eYvqwxhLB5Xug== Received: from customer (localhost [127.0.0.1]) by submission (posteo.de) with ESMTPSA id 4P6MSw2HFTz6tmX; Wed, 1 Feb 2023 13:59:43 +0100 (CET) From: Jelle Licht In-Reply-To: <87v8ktvq99.fsf@trop.in> References: <87edrzzw9w.fsf@daviwil.com> <87v8lby7jq.fsf@daviwil.com> <87k01p8086.fsf_-_@gnu.org> <87cz7g2pkz.fsf@trop.in> <87mt6hjzyx.fsf@gnu.org> <87wn5l8bhz.fsf@trop.in> <87ilgx4kqg.fsf@gnu.org> <87v8ktvq99.fsf@trop.in> Date: Wed, 01 Feb 2023 12:59:42 +0000 Message-ID: <87lelhils1.fsf@posteo.net> MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list X-BeenThere: guix-patches@gnu.org List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: guix-patches-bounces+larch=yhetil.org@gnu.org Sender: guix-patches-bounces+larch=yhetil.org@gnu.org X-Migadu-Flow: FLOW_IN X-Migadu-Country: US ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=yhetil.org; s=key1; t=1675256426; h=from:from:sender:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:cc:mime-version:mime-version: content-type:content-type: content-transfer-encoding:content-transfer-encoding:resent-cc: resent-from:resent-sender:resent-message-id:in-reply-to:in-reply-to: references:references:list-id:list-help:list-unsubscribe: list-subscribe:list-post:dkim-signature; bh=Z7ngueoXnIQmAoTHmYHvAmC20h6IbfNPqEMSInbqx5Q=; b=MFYH0eOxcuwYsdENd5zBaov9KEcij62YTPnJfzGnC9Q4B29P9zCOLxFcmH0JyJR0Wh4voO yENvUHPHi15n0PSRvZjZW32Yn2gkovULPCqxOzBfme4McbVbNLiPyJoUWczRvMKB9+BjK0 1AExJxtg1mzG0rFVrJ0hJz3U+6ccLCXJN7yPYghjribDwcHifOJmgeCFNjfiQ2F+ISDK00 PrDcn35JU1ENdBzhubpUvz/td+ooziXCKwDfUMLfJV/3/5Ilz9IKjzWaFMAqU2cDMJz9eg AVkZp+mA6FYlr5t8oKa3PaPoLIhAEWnBdrGMOOX0409uJ7+ki6bexpEVK6VH2A== ARC-Authentication-Results: i=1; aspmx1.migadu.com; dkim=fail ("headers rsa verify failed") header.d=posteo.net header.s=2017 header.b=aUe8Dh17; spf=pass (aspmx1.migadu.com: domain of "guix-patches-bounces+larch=yhetil.org@gnu.org" designates 209.51.188.17 as permitted sender) smtp.mailfrom="guix-patches-bounces+larch=yhetil.org@gnu.org"; dmarc=fail reason="SPF not aligned (strict)" header.from=posteo.net (policy=none) ARC-Seal: i=1; s=key1; d=yhetil.org; t=1675256426; a=rsa-sha256; cv=none; b=KpwihXwrbHdPWDWolhuL9VMfXRHgpYOCWNEe9en1x5P4M+Yx0Cv3sY8USTiuPYU2002X8O 4Lun+dxbZ+Hl1X0D4qIWEhQZHEah15C5Z7vZMkffC2lM/G0VzV1vQ0yAKUetx8rxPFwKrC cpO4JiCLiqB2/v/AMk9bOAKKdapiDBY9eV604SNav1AhI7NeKsk7o+5EKjVdrp/7FIZkjO fAN6R+VJmeQnCGtKpIPLLOs8boTIviy4VtgACebYZTsqLcFvRQZouQT3plr3BnWc5qQju0 YXdc3g4MIvle2J87UtcBSub3TE8xqec4j+4U0yYf0b4En3uuWeLxL/H6TcsUqA== Authentication-Results: aspmx1.migadu.com; dkim=fail ("headers rsa verify failed") header.d=posteo.net header.s=2017 header.b=aUe8Dh17; spf=pass (aspmx1.migadu.com: domain of "guix-patches-bounces+larch=yhetil.org@gnu.org" designates 209.51.188.17 as permitted sender) smtp.mailfrom="guix-patches-bounces+larch=yhetil.org@gnu.org"; dmarc=fail reason="SPF not aligned (strict)" header.from=posteo.net (policy=none) X-Migadu-Scanner: scn0.migadu.com X-Spam-Score: -0.98 X-Migadu-Queue-Id: 61DD9187A1 X-Migadu-Spam-Score: -0.98 X-TUID: KHYg4Nyl1a7t Andrew Tropin writes: > On 2023-01-23 11:18, Ludovic Court=C3=A8s wrote: > >> Hi, >> >> Andrew Tropin skribis: >> >>> On 2023-01-17 10:02, Ludovic Court=C3=A8s wrote: >>> >>>> Hi, >>>> >>>> Andrew Tropin skribis: >>>> >>>>>> What about accepting sexps (or gexps) instead of strings? As in: >>>>>> >>>>>> (init-file '((require 'whatever) (setq something t))) >>>>> >>>>> A quick minor note on this approach: it won't be possible to use >>>>> #'elisp-function inside such configuration because it will be >>>>> interpreted by guile reader, but actually rde lives without this >>>>> functionality completely ok. >>>> >>>> Specifically: >>>> >>>> (write '#'x) >>>> |=3D (syntax x) >>>> >>>> But we can use (guix read-print) and ensure that it prints #'. >>>> >>> >>> Do you have any links to docs/sample implementations on the topic of >>> extending guile reader, so we have an example to start with? >> >> It=E2=80=99s not the reader but rather the writer that we=E2=80=99d want= to tweak. > > Right, it already can read #'x as (syntax x) and we can print it > properly later, but AFAIK comments are ignored by the default reader. > So I would expect to do something (very roughly) like this: > > --8<---------------cut here---------------start------------->8--- > (parameterize (((@@ (guix gexp) read-procedure) read-with-comments)) > #~(list 'hello ; Comment I would like to preserve during serialization > 'guix)) > --8<---------------cut here---------------end--------------->8--- > > Of course it doesn't work, but I hope demonstrates the idea. > >> >> In (guix read-print), =E2=80=98pretty-print-with-comments=E2=80=99 alrea= dy special >> cases quasiquote etc. so that it prints =E2=80=98`=E2=80=99 (backtick) a= nd not >> =E2=80=98quasiquote'. We=E2=80=99d add clauses for =E2=80=98syntax=E2= =80=99 and =E2=80=98quasisyntax=E2=80=99. >> > > It seems ice-9 pretty-print also preserves backticks, but I see that > pretty-print-with-comments also preserves gexps, which is cool. Adding > syntax will make it even cooler. > >>> I think it will be cool to hook up a custom reader, ideally comment >>> preserving, for emacs lisp inside scheme files. >> >> (guix read-print) is what you want. :-) >> > > Can you give a hint on how to use it for preserving comments, please? > >>>>> Do we want something like this possible? >>>>> >>>>> (init-file `((require 'whatever) >>>>> (setq something t) >>>>> (load ,(local-file "old-init.el"))) >>>> >>>> It=E2=80=99d be nice. In that case, we=E2=80=99ll want it to be a gex= p though: >>>> >>>> #~((require 'whatever) (load #$(local-file =E2=80=A6))) >>>> >>> >>> gexps are nice, but do we really need/want them here? Do you have any >>> thoughts on what are the benifits over quasiquotes in this case? Maybe >>> some examples? >> >> The benefit in the example above is that the gexp would actually work >> whereas the sexp wouldn=E2=80=99t :-), unless there=E2=80=99s code somew= here to manually >> traverse the sexp adn replace the record with its store >> item (which is what gexps are about). >> >> I hope that makes sense! > > With this simple serializer we already achieved quite good results:=20 > https://git.sr.ht/~abcdw/rde/tree/388d3ad95e8607543df3dcdf26d058b610e7738= 9/src/rde/serializers/lisp.scm#L35 > > For this input > --8<---------------cut here---------------start------------->8--- > `((load ,(local-file "./feature-lists.scm")) > ,#~(format #f "hello") ; top level gexps are evaluated > (list ,#~(format #f "hello")) ; nested gexps are not > ,#~";; hacky comment" > ;; comment, which is not preserved > #'hi-fn ; incorrectly serialized, but fixable by alternative > ; pretty-print > ) > --8<---------------cut here---------------end--------------->8--- > > it provides quite satisfying results: > --8<---------------cut here---------------start------------->8--- > (load "/gnu/store/xb6ma0mcgg1zzq645s63arvy3qskmbiz-feature-lists.scm") > hello > (list (format #f "hello")) > ;; hacky comment > (syntax hi-fn) > --8<---------------cut here---------------end--------------->8--- > > It's a little incosistent (top level gexp are evaluated, but nested are > not), comments are not preserved and #' serialized incorrectly, but > other than that it works very good. > > WDYT about overall approach used here? or we can do it radically > better? Not saying it's better in any particular way, but I have had this locally for all my elisp-read-by-guile-written-back-to-elisp needs: --8<---------------cut here---------------start------------->8--- (define-module (jlicht build elisp-write) #:use-module (ice-9 match) #:use-module (srfi srfi-1) #:export (elisp-write)) (define (elisp-write in-list? exp port) "Stack-blowing implementation that writes guile's internal elisp representation to something that can be parsed by Emacs." ;; Definitions from (language elisp parser)'s quotation-symbols:=20 (define symbol-strings '((#{`}# . "`") (#{,}# . ",") (#{,@}# . ",@"))) (define (elisp-symbol? sym) (assq sym symbol-strings)) (define (write-elisp-symbol sym port) (format port "~A" (assq-ref symbol-strings sym))) =20=20 (match exp (((? elisp-symbol? sym) rest) (write-elisp-symbol sym port) (elisp-write in-list? rest port)) ;; Vector expression (#(vs ...) (format port "[") (elisp-write #t vs port) (format port "]")) ;; Guile elisp implementation detail ('(%set-lexical-binding-mode #f) 'skip) ;; List walker ((e ...) (when (not in-list?) (format port "(")) (unless (null? e) (elisp-write #f (car e) port) (for-each (lambda (v) (format port " ") (elisp-write #f v port)) (cdr e))) (when (not in-list?) (format port ")"))) ;; dotted pair ((and (? pair?) (? dotted-list? l)) (format port "(") (elisp-write #t (drop-right l 0) port) (format port " . ") (elisp-write #t (take-right l 0) port) (format port ")")) ;; Print simple primitives (_ (write exp port)))) --8<---------------cut here---------------end--------------->8--- On the reader side I just use guile's elisp reader: --8<---------------cut here---------------start------------->8--- (define-module (jlicht test elisp) #:use-module (language elisp parser) #:use-module (jlicht build elisp-write) #:use-module (srfi srfi-26) #:use-module (srfi srfi-64)) (eval-when (expand load eval) (read-hash-extend #\e (lambda (chr port) (read-elisp port)))) (set! test-log-to-file #f) (define (roundtrip expr) (let ((written (call-with-output-string (cut elisp-write #f expr <>)))) (call-with-input-string written read-elisp))) (define-syntax test-roundtrip-equals (syntax-rules () ((_ expr) (let ((e1 (roundtrip expr))) (test-equal e1 (roundtrip e1)))))) (define runner (test-runner-simple)) (test-with-runner runner (test-begin "roundtrip-elisp-fixed-point") (test-roundtrip-equals 12) (test-roundtrip-equals "hello") (test-roundtrip-equals '#e#'my-fn) (test-roundtrip-equals '#e[a b c]) (test-roundtrip-equals '#e`(+ 1 2 ,@(a b) ,c)) (test-end "roundtrip-elisp-fixed-point")) (exit (test-runner-fail-count runner)) --8<---------------cut here---------------end--------------->8--- I've also hooked it up in combination with a sequence of calls to `scheme-file' -> `computed-file' called `elisp-file', but that's a bit more hacky and less relevant to the current discussion. - Jelle