emacs: Fix 'guix-devel-setup-repl'.
[jackhill/guix/guix.git] / emacs / guix-guile.el
1 ;;; guix-guile.el --- Auxiliary tools for working with guile code -*- lexical-binding: t -*-
2
3 ;; Copyright © 2015 Alex Kost <alezost@gmail.com>
4
5 ;; This file is part of GNU Guix.
6
7 ;; GNU Guix is free software; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation, either version 3 of the License, or
10 ;; (at your option) any later version.
11
12 ;; GNU Guix is distributed in the hope that it will be useful,
13 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 ;; GNU General Public License for more details.
16
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with this program. If not, see <http://www.gnu.org/licenses/>.
19
20 ;;; Commentary:
21
22 ;; This file provides functions for parsing guile code, making guile
23 ;; expressions, etc.
24
25 ;;; Code:
26
27 (require 'geiser-guile)
28
29 (defvar guix-guile-definition-regexp
30 (rx bol "(define"
31 (zero-or-one "*")
32 (zero-or-one "-public")
33 (one-or-more space)
34 (zero-or-one "(")
35 (group (one-or-more (or word (syntax symbol)))))
36 "Regexp used to find the guile definition.")
37
38 (defun guix-guile-current-definition ()
39 "Return string with name of the current top-level guile definition."
40 (save-excursion
41 (beginning-of-defun)
42 (if (looking-at guix-guile-definition-regexp)
43 (match-string-no-properties 1)
44 (error "Couldn't find the current definition"))))
45
46 (defun guix-guile-current-module ()
47 "Return a string with the current guile module.
48 Return nil, if current buffer does not define a module."
49 ;; Modified version of `geiser-guile--get-module'.
50 (save-excursion
51 (geiser-syntax--pop-to-top)
52 (when (or (re-search-backward geiser-guile--module-re nil t)
53 (looking-at geiser-guile--library-re)
54 (re-search-forward geiser-guile--module-re nil t))
55 (match-string-no-properties 1))))
56
57 (defun guix-guile-boolean (arg)
58 "Return a string with guile boolean value.
59 Transform elisp ARG (nil or non-nil) to the guile boolean (#f or #t)."
60 (concat "#" (prin1-to-string (if arg 't 'f))))
61
62 (defun guix-guile-keyword-regexp (keyword)
63 "Return regexp to find guile KEYWORD."
64 (format "(\\(%s\\)\\_>" keyword))
65
66 (defun guix-guile-make-call-expression (proc &rest args)
67 "Return \"(PROC ARGS ...)\" string.
68 PROC and ARGS should be strings."
69 (format "(%s %s)"
70 proc
71 (mapconcat #'identity args " ")))
72
73 (defun guix-make-guile-expression (fun &rest args)
74 "Return string containing a guile expression for calling FUN with ARGS."
75 (format "(%S %s)" fun
76 (mapconcat
77 (lambda (arg)
78 (cond
79 ((null arg) "'()")
80 ((or (eq arg t)
81 ;; An ugly hack to separate 'false' from nil.
82 (equal arg 'f)
83 (keywordp arg))
84 (concat "#" (prin1-to-string arg t)))
85 ((or (symbolp arg) (listp arg))
86 (concat "'" (prin1-to-string arg)))
87 (t (prin1-to-string arg))))
88 args
89 " ")))
90
91 (defun guix-guile-prompt? (string)
92 "Return non-nil, if STRING contains a Guile prompt."
93 (or (string-match-p geiser-guile--prompt-regexp string)
94 (string-match-p geiser-guile--debugger-prompt-regexp string)))
95
96 (provide 'guix-guile)
97
98 ;;; guix-guile.el ends here