offload: Fix 'choose-build-machine' for several machines.
[jackhill/guix/guix.git] / guix / store.scm
CommitLineData
233e7676 1;;; GNU Guix --- Functional package management for GNU
021a201f 2;;; Copyright © 2012, 2013, 2014 Ludovic Courtès <ludo@gnu.org>
77d3cf08 3;;;
233e7676 4;;; This file is part of GNU Guix.
77d3cf08 5;;;
233e7676 6;;; GNU Guix is free software; you can redistribute it and/or modify it
77d3cf08
LC
7;;; under the terms of the GNU General Public License as published by
8;;; the Free Software Foundation; either version 3 of the License, or (at
9;;; your option) any later version.
10;;;
233e7676 11;;; GNU Guix is distributed in the hope that it will be useful, but
77d3cf08
LC
12;;; WITHOUT ANY WARRANTY; without even the implied warranty of
13;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14;;; GNU General Public License for more details.
15;;;
16;;; You should have received a copy of the GNU General Public License
233e7676 17;;; along with GNU Guix. If not, see <http://www.gnu.org/licenses/>.
77d3cf08
LC
18
19(define-module (guix store)
0f41c26f 20 #:use-module (guix nar)
82058eff 21 #:use-module (guix utils)
d8eea3d2 22 #:use-module (guix config)
0f41c26f 23 #:use-module (guix serialization)
77d3cf08
LC
24 #:use-module (rnrs bytevectors)
25 #:use-module (rnrs io ports)
26 #:use-module (srfi srfi-1)
27 #:use-module (srfi srfi-9)
bf8e7fc5 28 #:use-module (srfi srfi-9 gnu)
77d3cf08 29 #:use-module (srfi srfi-26)
e87088c9
LC
30 #:use-module (srfi srfi-34)
31 #:use-module (srfi srfi-35)
26bbbb95 32 #:use-module (srfi srfi-39)
77d3cf08 33 #:use-module (ice-9 match)
e3d74106 34 #:use-module (ice-9 regex)
3f1e6939 35 #:use-module (ice-9 vlist)
6bfec3ed 36 #:use-module (ice-9 popen)
9fd72fb1
LC
37 #:export (%daemon-socket-file
38
39 nix-server?
77d3cf08
LC
40 nix-server-major-version
41 nix-server-minor-version
42 nix-server-socket
43
e87088c9 44 &nix-error nix-error?
ef86c39f
LC
45 &nix-connection-error nix-connection-error?
46 nix-connection-error-file
47 nix-connection-error-code
e87088c9
LC
48 &nix-protocol-error nix-protocol-error?
49 nix-protocol-error-message
50 nix-protocol-error-status
51
26bbbb95
LC
52 hash-algo
53
77d3cf08 54 open-connection
3abaf0c4 55 close-connection
ce4a4829 56 with-store
77d3cf08 57 set-build-options
31ef99a8 58 valid-path?
82058eff 59 query-path-hash
77d3cf08
LC
60 add-text-to-store
61 add-to-store
26bbbb95 62 build-derivations
3259877d 63 add-temp-root
34811f02 64 add-indirect-root
26bbbb95 65
0f3d2504
LC
66 substitutable?
67 substitutable-path
68 substitutable-deriver
69 substitutable-references
70 substitutable-download-size
71 substitutable-nar-size
72 has-substitutes?
73 substitutable-paths
74 substitutable-path-info
75
fae31edc 76 references
3f1e6939 77 requisites
fae31edc 78 referrers
50add477 79 topologically-sorted
fae31edc
LC
80 valid-derivers
81 query-derivation-outputs
3259877d
LC
82 live-paths
83 dead-paths
84 collect-garbage
85 delete-paths
526382ff
LC
86 import-paths
87 export-paths
3259877d 88
dcee50c1
LC
89 current-build-output-port
90
6bfec3ed
LC
91 register-path
92
26bbbb95
LC
93 %store-prefix
94 store-path?
9336e5b5 95 direct-store-path?
e3d74106 96 derivation-path?
2c6ab6cc 97 store-path-package-name
eddd4077
LC
98 store-path-hash-part
99 log-file))
77d3cf08 100
63193ebf 101(define %protocol-version #x10c)
77d3cf08 102
d66b704b
LC
103(define %worker-magic-1 #x6e697863) ; "nixc"
104(define %worker-magic-2 #x6478696f) ; "dxio"
77d3cf08
LC
105
106(define (protocol-major magic)
107 (logand magic #xff00))
108(define (protocol-minor magic)
109 (logand magic #x00ff))
110
111(define-syntax define-enumerate-type
112 (syntax-rules ()
113 ((_ name->int (name id) ...)
114 (define-syntax name->int
115 (syntax-rules (name ...)
116 ((_ name) id) ...)))))
117
118(define-enumerate-type operation-id
119 ;; operation numbers from worker-protocol.hh
120 (quit 0)
121 (valid-path? 1)
122 (has-substitutes? 3)
123 (query-path-hash 4)
124 (query-references 5)
125 (query-referrers 6)
126 (add-to-store 7)
127 (add-text-to-store 8)
128 (build-derivations 9)
129 (ensure-path 10)
130 (add-temp-root 11)
131 (add-indirect-root 12)
132 (sync-with-gc 13)
133 (find-roots 14)
134 (export-path 16)
135 (query-deriver 18)
136 (set-options 19)
137 (collect-garbage 20)
63193ebf 138 ;;(query-substitutable-path-info 21) ; obsolete as of #x10c
77d3cf08 139 (query-derivation-outputs 22)
63193ebf 140 (query-all-valid-paths 23)
77d3cf08
LC
141 (query-failed-paths 24)
142 (clear-failed-paths 25)
143 (query-path-info 26)
144 (import-paths 27)
63193ebf
LC
145 (query-derivation-output-names 28)
146 (query-path-from-hash-part 29)
147 (query-substitutable-path-infos 30)
148 (query-valid-paths 31)
fae31edc
LC
149 (query-substitutable-paths 32)
150 (query-valid-derivers 33))
77d3cf08
LC
151
152(define-enumerate-type hash-algo
153 ;; hash.hh
154 (md5 1)
155 (sha1 2)
156 (sha256 3))
157
3259877d
LC
158(define-enumerate-type gc-action
159 ;; store-api.hh
160 (return-live 0)
161 (return-dead 1)
162 (delete-dead 2)
163 (delete-specific 3))
164
77d3cf08 165(define %default-socket-path
80d0447c 166 (string-append %state-directory "/daemon-socket/socket"))
77d3cf08 167
9fd72fb1
LC
168(define %daemon-socket-file
169 ;; File name of the socket the daemon listens too.
170 (make-parameter (or (getenv "GUIX_DAEMON_SOCKET")
171 %default-socket-path)))
172
173
77d3cf08 174\f
0f3d2504
LC
175;; Information about a substitutable store path.
176(define-record-type <substitutable>
177 (substitutable path deriver refs dl-size nar-size)
178 substitutable?
179 (path substitutable-path)
180 (deriver substitutable-deriver)
181 (refs substitutable-references)
182 (dl-size substitutable-download-size)
183 (nar-size substitutable-nar-size))
184
185(define (read-substitutable-path-list p)
186 (let loop ((len (read-int p))
187 (result '()))
188 (if (zero? len)
189 (reverse result)
190 (let ((path (read-store-path p))
191 (deriver (read-store-path p))
192 (refs (read-store-path-list p))
193 (dl-size (read-long-long p))
194 (nar-size (read-long-long p)))
195 (loop (- len 1)
196 (cons (substitutable path deriver refs dl-size nar-size)
197 result))))))
198
77d3cf08 199(define-syntax write-arg
6c20d1d0 200 (syntax-rules (integer boolean file string string-list string-pairs
3259877d 201 store-path store-path-list base16)
77d3cf08
LC
202 ((_ integer arg p)
203 (write-int arg p))
204 ((_ boolean arg p)
205 (write-int (if arg 1 0) p))
206 ((_ file arg p)
207 (write-file arg p))
208 ((_ string arg p)
209 (write-string arg p))
210 ((_ string-list arg p)
82058eff 211 (write-string-list arg p))
6c20d1d0
LC
212 ((_ string-pairs arg p)
213 (write-string-pairs arg p))
3259877d
LC
214 ((_ store-path arg p)
215 (write-store-path arg p))
216 ((_ store-path-list arg p)
217 (write-store-path-list arg p))
82058eff
LC
218 ((_ base16 arg p)
219 (write-string (bytevector->base16-string arg) p))))
77d3cf08
LC
220
221(define-syntax read-arg
0f3d2504
LC
222 (syntax-rules (integer boolean string store-path store-path-list
223 substitutable-path-list base16)
77d3cf08
LC
224 ((_ integer p)
225 (read-int p))
226 ((_ boolean p)
227 (not (zero? (read-int p))))
228 ((_ string p)
229 (read-string p))
230 ((_ store-path p)
82058eff 231 (read-store-path p))
3259877d
LC
232 ((_ store-path-list p)
233 (read-store-path-list p))
0f3d2504
LC
234 ((_ substitutable-path-list p)
235 (read-substitutable-path-list p))
236 ((_ base16 p)
82058eff 237 (base16-string->bytevector (read-string p)))))
77d3cf08
LC
238
239\f
240;; remote-store.cc
241
242(define-record-type <nix-server>
2c3f47ee 243 (%make-nix-server socket major minor
bdcf35a6 244 ats-cache atts-cache)
77d3cf08
LC
245 nix-server?
246 (socket nix-server-socket)
247 (major nix-server-major-version)
2c3f47ee
LC
248 (minor nix-server-minor-version)
249
250 ;; Caches. We keep them per-connection, because store paths build
251 ;; during the session are temporary GC roots kept for the duration of
252 ;; the session.
bdcf35a6
LC
253 (ats-cache nix-server-add-to-store-cache)
254 (atts-cache nix-server-add-text-to-store-cache))
77d3cf08 255
bf8e7fc5
LC
256(set-record-type-printer! <nix-server>
257 (lambda (obj port)
258 (format port "#<build-daemon ~a.~a ~a>"
259 (nix-server-major-version obj)
260 (nix-server-minor-version obj)
261 (number->string (object-address obj)
262 16))))
263
e87088c9
LC
264(define-condition-type &nix-error &error
265 nix-error?)
266
ef86c39f
LC
267(define-condition-type &nix-connection-error &nix-error
268 nix-connection-error?
269 (file nix-connection-error-file)
270 (errno nix-connection-error-code))
271
e87088c9
LC
272(define-condition-type &nix-protocol-error &nix-error
273 nix-protocol-error?
274 (message nix-protocol-error-message)
275 (status nix-protocol-error-status))
276
9fd72fb1 277(define* (open-connection #:optional (file (%daemon-socket-file))
e36a7172 278 #:key (reserve-space? #t))
e531ac2a
LC
279 "Connect to the daemon over the Unix-domain socket at FILE. When
280RESERVE-SPACE? is true, instruct it to reserve a little bit of extra
281space on the file system so that the garbage collector can still
282operate, should the disk become full. Return a server object."
77d3cf08
LC
283 (let ((s (with-fluids ((%default-port-encoding #f))
284 ;; This trick allows use of the `scm_c_read' optimization.
285 (socket PF_UNIX SOCK_STREAM 0)))
286 (a (make-socket-address PF_UNIX file)))
df1fab58 287
8c95b27c
LC
288 (catch 'system-error
289 (lambda ()
290 ;; Enlarge the receive buffer.
291 (setsockopt s SOL_SOCKET SO_RCVBUF (* 12 1024)))
292 (lambda args
293 ;; On the Hurd, the pflocal server's implementation of `socket_setopt'
294 ;; always returns ENOPROTOOPT. Ignore it.
295 (unless (= (system-error-errno args) ENOPROTOOPT)
296 (apply throw args))))
df1fab58 297
ef86c39f
LC
298 (catch 'system-error
299 (cut connect s a)
300 (lambda args
301 ;; Translate the error to something user-friendly.
302 (let ((errno (system-error-errno args)))
303 (raise (condition (&nix-connection-error
304 (file file)
305 (errno errno)))))))
306
77d3cf08
LC
307 (write-int %worker-magic-1 s)
308 (let ((r (read-int s)))
309 (and (eqv? r %worker-magic-2)
310 (let ((v (read-int s)))
311 (and (eqv? (protocol-major %protocol-version)
312 (protocol-major v))
313 (begin
314 (write-int %protocol-version s)
e36a7172
LC
315 (if (>= (protocol-minor v) 11)
316 (write-int (if reserve-space? 1 0) s))
77d3cf08
LC
317 (let ((s (%make-nix-server s
318 (protocol-major v)
2c3f47ee 319 (protocol-minor v)
fce2394e
LC
320 (make-hash-table 100)
321 (make-hash-table 100))))
34fcbe3a
LC
322 (let loop ((done? (process-stderr s)))
323 (or done? (process-stderr s)))
77d3cf08
LC
324 s))))))))
325
3abaf0c4
LC
326(define (close-connection server)
327 "Close the connection to SERVER."
328 (close (nix-server-socket server)))
329
ce4a4829
LC
330(define-syntax-rule (with-store store exp ...)
331 "Bind STORE to an open connection to the store and evaluate EXPs;
332automatically close the store when the dynamic extent of EXP is left."
333 (let ((store (open-connection)))
334 (dynamic-wind
335 (const #f)
336 (lambda ()
337 exp ...)
338 (lambda ()
339 (false-if-exception (close-connection store))))))
340
dcee50c1
LC
341(define current-build-output-port
342 ;; The port where build output is sent.
343 (make-parameter (current-error-port)))
344
526382ff
LC
345(define* (dump-port in out
346 #:optional len
347 #:key (buffer-size 16384))
348 "Read LEN bytes from IN (or as much as possible if LEN is #f) and write it
349to OUT, using chunks of BUFFER-SIZE bytes."
350 (define buffer
351 (make-bytevector buffer-size))
352
353 (let loop ((total 0)
354 (bytes (get-bytevector-n! in buffer 0
355 (if len
356 (min len buffer-size)
357 buffer-size))))
358 (or (eof-object? bytes)
359 (and len (= total len))
360 (let ((total (+ total bytes)))
361 (put-bytevector out buffer 0 bytes)
362 (loop total
363 (get-bytevector-n! in buffer 0
364 (if len
365 (min (- len total) buffer-size)
366 buffer-size)))))))
367
368(define* (process-stderr server #:optional user-port)
dcee50c1
LC
369 "Read standard output and standard error from SERVER, writing it to
370CURRENT-BUILD-OUTPUT-PORT. Return #t when SERVER is done sending data, and
371#f otherwise; in the latter case, the caller should call `process-stderr'
bbdb3ffa
LC
372again until #t is returned or an error is raised.
373
374Since the build process's output cannot be assumed to be UTF-8, we
375conservatively consider it to be Latin-1, thereby avoiding possible
376encoding conversion errors."
77d3cf08
LC
377 (define p
378 (nix-server-socket server))
379
380 ;; magic cookies from worker-protocol.hh
5674a3fd
LC
381 (define %stderr-next #x6f6c6d67) ; "olmg", build log
382 (define %stderr-read #x64617461) ; "data", data needed from source
383 (define %stderr-write #x64617416) ; "dat\x16", data for sink
384 (define %stderr-last #x616c7473) ; "alts", we're done
385 (define %stderr-error #x63787470) ; "cxtp", error reporting
77d3cf08
LC
386
387 (let ((k (read-int p)))
388 (cond ((= k %stderr-write)
526382ff
LC
389 ;; Write a byte stream to USER-PORT.
390 (let* ((len (read-int p))
391 (m (modulo len 8)))
392 (dump-port p user-port len)
393 (unless (zero? m)
394 ;; Consume padding, as for strings.
395 (get-bytevector-n p (- 8 m))))
dcee50c1 396 #f)
77d3cf08 397 ((= k %stderr-read)
526382ff
LC
398 ;; Read a byte stream from USER-PORT.
399 (let* ((max-len (read-int p))
400 (data (get-bytevector-n user-port max-len))
401 (len (bytevector-length data)))
402 (write-int len p)
403 (put-bytevector p data)
404 (write-padding len p)
dcee50c1 405 #f))
77d3cf08 406 ((= k %stderr-next)
526382ff 407 ;; Log a string.
bbdb3ffa 408 (let ((s (read-latin1-string p)))
dcee50c1
LC
409 (display s (current-build-output-port))
410 #f))
77d3cf08 411 ((= k %stderr-error)
526382ff 412 ;; Report an error.
bbdb3ffa 413 (let ((error (read-latin1-string p))
0ff3e3aa
LC
414 ;; Currently the daemon fails to send a status code for early
415 ;; errors like DB schema version mismatches, so check for EOF.
416 (status (if (and (>= (nix-server-minor-version server) 8)
417 (not (eof-object? (lookahead-u8 p))))
77d3cf08
LC
418 (read-int p)
419 1)))
e87088c9
LC
420 (raise (condition (&nix-protocol-error
421 (message error)
422 (status status))))))
77d3cf08 423 ((= k %stderr-last)
dcee50c1 424 ;; The daemon is done (see `stopWork' in `nix-worker.cc'.)
77d3cf08
LC
425 #t)
426 (else
e87088c9
LC
427 (raise (condition (&nix-protocol-error
428 (message "invalid error code")
429 (status k))))))))
77d3cf08
LC
430
431(define* (set-build-options server
c3eb878f 432 #:key keep-failed? keep-going? fallback?
77d3cf08
LC
433 (verbosity 0)
434 (max-build-jobs (current-processor-count))
6c20d1d0 435 timeout
77d3cf08
LC
436 (max-silent-time 3600)
437 (use-build-hook? #t)
438 (build-verbosity 0)
439 (log-type 0)
e036c31b
LC
440 (print-build-trace #t)
441 (build-cores 1)
63193ebf
LC
442 (use-substitutes? #t)
443 (binary-caches '())) ; client "untrusted" cache URLs
77d3cf08
LC
444 ;; Must be called after `open-connection'.
445
446 (define socket
447 (nix-server-socket server))
448
449 (let-syntax ((send (syntax-rules ()
e036c31b
LC
450 ((_ (type option) ...)
451 (begin
452 (write-arg type option socket)
453 ...)))))
454 (write-int (operation-id set-options) socket)
455 (send (boolean keep-failed?) (boolean keep-going?)
c3eb878f 456 (boolean fallback?) (integer verbosity)
e036c31b 457 (integer max-build-jobs) (integer max-silent-time))
371e87d2
LC
458 (when (>= (nix-server-minor-version server) 2)
459 (send (boolean use-build-hook?)))
460 (when (>= (nix-server-minor-version server) 4)
461 (send (integer build-verbosity) (integer log-type)
462 (boolean print-build-trace)))
463 (when (>= (nix-server-minor-version server) 6)
464 (send (integer build-cores)))
465 (when (>= (nix-server-minor-version server) 10)
466 (send (boolean use-substitutes?)))
467 (when (>= (nix-server-minor-version server) 12)
6c20d1d0
LC
468 (let ((pairs (if timeout
469 `(("build-timeout" . ,(number->string timeout))
470 ,@binary-caches)
471 binary-caches)))
472 (send (string-pairs pairs))))
dcee50c1
LC
473 (let loop ((done? (process-stderr server)))
474 (or done? (process-stderr server)))))
77d3cf08 475
fd060fd3 476(define-syntax operation
77d3cf08 477 (syntax-rules ()
fd060fd3 478 "Define a client-side RPC stub for the given operation."
3259877d 479 ((_ (name (type arg) ...) docstring return ...)
fd060fd3 480 (lambda (server arg ...)
77d3cf08
LC
481 docstring
482 (let ((s (nix-server-socket server)))
483 (write-int (operation-id name) s)
484 (write-arg type arg s)
485 ...
dcee50c1
LC
486 ;; Loop until the server is done sending error output.
487 (let loop ((done? (process-stderr server)))
488 (or done? (loop (process-stderr server))))
3259877d 489 (values (read-arg return s) ...))))))
77d3cf08 490
fd060fd3
LC
491(define-syntax-rule (define-operation (name args ...)
492 docstring return ...)
493 (define name
494 (operation (name args ...) docstring return ...)))
495
31ef99a8
LC
496(define-operation (valid-path? (string path))
497 "Return #t when PATH is a valid store path."
498 boolean)
499
63193ebf 500(define-operation (query-path-hash (store-path path))
82058eff
LC
501 "Return the SHA256 hash of PATH as a bytevector."
502 base16)
503
fd060fd3
LC
504(define add-text-to-store
505 ;; A memoizing version of `add-to-store', to avoid repeated RPCs with
506 ;; the very same arguments during a given session.
507 (let ((add-text-to-store
508 (operation (add-text-to-store (string name) (string text)
509 (string-list references))
510 #f
511 store-path)))
cfbf9160 512 (lambda* (server name text #:optional (references '()))
bdcf35a6
LC
513 "Add TEXT under file NAME in the store, and return its store path.
514REFERENCES is the list of store paths referred to by the resulting store
515path."
fce2394e 516 (let ((args `(,text ,name ,references))
bdcf35a6
LC
517 (cache (nix-server-add-text-to-store-cache server)))
518 (or (hash-ref cache args)
fd060fd3 519 (let ((path (add-text-to-store server name text references)))
bdcf35a6
LC
520 (hash-set! cache args path)
521 path))))))
522
fd060fd3 523(define add-to-store
a7b6ffee
LC
524 ;; A memoizing version of `add-to-store'. This is important because
525 ;; `add-to-store' leads to huge data transfers to the server, and
526 ;; because it's often called many times with the very same argument.
fd060fd3
LC
527 (let ((add-to-store (operation (add-to-store (string basename)
528 (boolean fixed?) ; obsolete, must be #t
529 (boolean recursive?)
530 (string hash-algo)
531 (file file-name))
532 #f
533 store-path)))
a9ebd9ef
LC
534 (lambda (server basename recursive? hash-algo file-name)
535 "Add the contents of FILE-NAME under BASENAME to the store. When
536RECURSIVE? is true and FILE-NAME designates a directory, the contents of
537FILE-NAME are added recursively; if FILE-NAME designates a flat file and
538RECURSIVE? is true, its contents are added, and its permission bits are
539kept. HASH-ALGO must be a string such as \"sha256\"."
2c3f47ee 540 (let* ((st (stat file-name #f))
fce2394e 541 (args `(,st ,basename ,recursive? ,hash-algo))
2c3f47ee 542 (cache (nix-server-add-to-store-cache server)))
a7b6ffee 543 (or (and st (hash-ref cache args))
a9ebd9ef 544 (let ((path (add-to-store server basename #t recursive?
a7b6ffee
LC
545 hash-algo file-name)))
546 (hash-set! cache args path)
547 path))))))
548
77d3cf08 549(define-operation (build-derivations (string-list derivations))
dcee50c1
LC
550 "Build DERIVATIONS, and return when the worker is done building them.
551Return #t on success."
77d3cf08 552 boolean)
26bbbb95 553
d3648e01
LC
554(define-operation (add-temp-root (store-path path))
555 "Make PATH a temporary root for the duration of the current session.
556Return #t."
557 boolean)
558
34811f02
LC
559(define-operation (add-indirect-root (string file-name))
560 "Make FILE-NAME an indirect root for the garbage collector; FILE-NAME
561can be anywhere on the file system, but it must be an absolute file
562name--it is the caller's responsibility to ensure that it is an absolute
563file name. Return #t on success."
564 boolean)
565
fae31edc
LC
566(define references
567 (operation (query-references (store-path path))
568 "Return the list of references of PATH."
569 store-path-list))
570
3f1e6939
LC
571(define* (fold-path store proc seed path
572 #:optional (relatives (cut references store <>)))
573 "Call PROC for each of the RELATIVES of PATH, exactly once, and return the
574result formed from the successive calls to PROC, the first of which is passed
575SEED."
576 (let loop ((paths (list path))
577 (result seed)
578 (seen vlist-null))
579 (match paths
580 ((path rest ...)
581 (if (vhash-assoc path seen)
582 (loop rest result seen)
583 (let ((seen (vhash-cons path #t seen))
584 (rest (append rest (relatives path)))
585 (result (proc path result)))
586 (loop rest result seen))))
587 (()
588 result))))
589
590(define (requisites store path)
591 "Return the requisites of PATH, including PATH---i.e., its closure (all its
592references, recursively)."
593 (fold-path store cons '() path))
594
50add477
LC
595(define (topologically-sorted store paths)
596 "Return a list containing PATHS and all their references sorted in
597topological order."
598 (define (traverse)
599 ;; Do a simple depth-first traversal of all of PATHS.
600 (let loop ((paths paths)
601 (visited vlist-null)
602 (result '()))
603 (define (visit n)
604 (vhash-cons n #t visited))
605
606 (define (visited? n)
607 (vhash-assoc n visited))
608
609 (match paths
610 ((head tail ...)
611 (if (visited? head)
612 (loop tail visited result)
613 (call-with-values
614 (lambda ()
615 (loop (references store head)
616 (visit head)
617 result))
618 (lambda (visited result)
619 (loop tail
620 visited
621 (cons head result))))))
622 (()
623 (values visited result)))))
624
625 (call-with-values traverse
626 (lambda (_ result)
627 (reverse result))))
628
fae31edc
LC
629(define referrers
630 (operation (query-referrers (store-path path))
631 "Return the list of path that refer to PATH."
632 store-path-list))
633
634(define valid-derivers
635 (operation (query-valid-derivers (store-path path))
636 "Return the list of valid \"derivers\" of PATH---i.e., all the
637.drv present in the store that have PATH among their outputs."
638 store-path-list))
639
640(define query-derivation-outputs ; avoid name clash with `derivation-outputs'
641 (operation (query-derivation-outputs (store-path path))
642 "Return the list of outputs of PATH, a .drv file."
643 store-path-list))
644
0f3d2504
LC
645(define-operation (has-substitutes? (store-path path))
646 "Return #t if binary substitutes are available for PATH, and #f otherwise."
647 boolean)
648
649(define substitutable-paths
650 (operation (query-substitutable-paths (store-path-list paths))
651 "Return the subset of PATHS that is substitutable."
652 store-path-list))
653
654(define substitutable-path-info
f65cf81a 655 (operation (query-substitutable-path-infos (store-path-list paths))
0f3d2504
LC
656 "Return information about the subset of PATHS that is
657substitutable. For each substitutable path, a `substitutable?' object is
658returned."
659 substitutable-path-list))
660
3259877d
LC
661(define (run-gc server action to-delete min-freed)
662 "Perform the garbage-collector operation ACTION, one of the
663`gc-action' values. When ACTION is `delete-specific', the TO-DELETE is
664the list of store paths to delete. IGNORE-LIVENESS? should always be
665#f. MIN-FREED is the minimum amount of disk space to be freed, in
666bytes, before the GC can stop. Return the list of store paths delete,
667and the number of bytes freed."
668 (let ((s (nix-server-socket server)))
669 (write-int (operation-id collect-garbage) s)
670 (write-int action s)
671 (write-store-path-list to-delete s)
672 (write-arg boolean #f s) ; ignore-liveness?
673 (write-long-long min-freed s)
674 (write-int 0 s) ; obsolete
675 (when (>= (nix-server-minor-version server) 5)
676 ;; Obsolete `use-atime' and `max-atime' parameters.
677 (write-int 0 s)
678 (write-int 0 s))
679
680 ;; Loop until the server is done sending error output.
681 (let loop ((done? (process-stderr server)))
682 (or done? (loop (process-stderr server))))
683
684 (let ((paths (read-store-path-list s))
685 (freed (read-long-long s))
686 (obsolete (read-long-long s)))
687 (values paths freed))))
688
689(define-syntax-rule (%long-long-max)
690 ;; Maximum unsigned 64-bit integer.
691 (- (expt 2 64) 1))
692
693(define (live-paths server)
694 "Return the list of live store paths---i.e., store paths still
695referenced, and thus not subject to being garbage-collected."
696 (run-gc server (gc-action return-live) '() (%long-long-max)))
697
698(define (dead-paths server)
699 "Return the list of dead store paths---i.e., store paths no longer
700referenced, and thus subject to being garbage-collected."
701 (run-gc server (gc-action return-dead) '() (%long-long-max)))
702
703(define* (collect-garbage server #:optional (min-freed (%long-long-max)))
704 "Collect garbage from the store at SERVER. If MIN-FREED is non-zero,
705then collect at least MIN-FREED bytes. Return the paths that were
706collected, and the number of bytes freed."
707 (run-gc server (gc-action delete-dead) '() min-freed))
708
709(define* (delete-paths server paths #:optional (min-freed (%long-long-max)))
710 "Delete PATHS from the store at SERVER, if they are no longer
711referenced. If MIN-FREED is non-zero, then stop after at least
712MIN-FREED bytes have been collected. Return the paths that were
713collected, and the number of bytes freed."
714 (run-gc server (gc-action delete-specific) paths min-freed))
715
526382ff
LC
716(define (import-paths server port)
717 "Import the set of store paths read from PORT into SERVER's store. An error
718is raised if the set of paths read from PORT is not signed (as per
719'export-path #:sign? #t'.) Return the list of store paths imported."
720 (let ((s (nix-server-socket server)))
721 (write-int (operation-id import-paths) s)
722 (let loop ((done? (process-stderr server port)))
723 (or done? (loop (process-stderr server port))))
724 (read-store-path-list s)))
725
726(define* (export-path server path port #:key (sign? #t))
727 "Export PATH to PORT. When SIGN? is true, sign it."
728 (let ((s (nix-server-socket server)))
729 (write-int (operation-id export-path) s)
730 (write-store-path path s)
731 (write-arg boolean sign? s)
732 (let loop ((done? (process-stderr server port)))
733 (or done? (loop (process-stderr server port))))
734 (= 1 (read-int s))))
735
736(define* (export-paths server paths port #:key (sign? #t))
99fbddf9
LC
737 "Export the store paths listed in PATHS to PORT, in topological order,
738signing them if SIGN? is true."
cafb92d8
LC
739 (define ordered
740 ;; Sort PATHS, but don't include their references.
741 (filter (cut member <> paths)
742 (topologically-sorted server paths)))
743
526382ff 744 (let ((s (nix-server-socket server)))
cafb92d8 745 (let loop ((paths ordered))
526382ff
LC
746 (match paths
747 (()
748 (write-int 0 port))
749 ((head tail ...)
750 (write-int 1 port)
751 (and (export-path server head port #:sign? sign?)
752 (loop tail)))))))
753
6bfec3ed
LC
754(define* (register-path path
755 #:key (references '()) deriver)
756 "Register PATH as a valid store file, with REFERENCES as its list of
757references, and DERIVER as its deriver (.drv that led to it.) Return #t on
758success.
759
760Use with care as it directly modifies the store! This is primarily meant to
761be used internally by the daemon's build hook."
762 ;; Currently this is implemented by calling out to the fine C++ blob.
763 (catch 'system-error
764 (lambda ()
765 (let ((pipe (open-pipe* OPEN_WRITE %guix-register-program)))
766 (and pipe
767 (begin
768 (format pipe "~a~%~a~%~a~%"
769 path (or deriver "") (length references))
770 (for-each (cut format pipe "~a~%" <>) references)
771 (zero? (close-pipe pipe))))))
772 (lambda args
773 ;; Failed to run %GUIX-REGISTER-PROGRAM.
774 #f)))
775
26bbbb95
LC
776\f
777;;;
778;;; Store paths.
779;;;
780
781(define %store-prefix
782 ;; Absolute path to the Nix store.
1d6816f9 783 (make-parameter %store-directory))
26bbbb95 784
f39bd08a
LC
785(define (store-path? path)
786 "Return #t if PATH is a store path."
787 ;; This is a lightweight check, compared to using a regexp, but this has to
788 ;; be fast as it's called often in `derivation', for instance.
789 ;; `isStorePath' in Nix does something similar.
790 (string-prefix? (%store-prefix) path))
26bbbb95 791
9336e5b5
LC
792(define (direct-store-path? path)
793 "Return #t if PATH is a store path, and not a sub-directory of a store path.
794This predicate is sometimes needed because files *under* a store path are not
795valid inputs."
796 (and (store-path? path)
797 (let ((len (+ 1 (string-length (%store-prefix)))))
798 (not (string-index (substring path len) #\/)))))
799
26bbbb95
LC
800(define (derivation-path? path)
801 "Return #t if PATH is a derivation path."
802 (and (store-path? path) (string-suffix? ".drv" path)))
e3d74106 803
5c0f1845
LC
804(define store-regexp*
805 ;; The substituter makes repeated calls to 'store-path-hash-part', hence
806 ;; this optimization.
807 (memoize
808 (lambda (store)
809 "Return a regexp matching a file in STORE."
810 (make-regexp (string-append "^" (regexp-quote store)
811 "/([0-9a-df-np-sv-z]{32})-([^/]+)$")))))
812
e3d74106
LC
813(define (store-path-package-name path)
814 "Return the package name part of PATH, a file name in the store."
5c0f1845
LC
815 (let ((path-rx (store-regexp* (%store-prefix))))
816 (and=> (regexp-exec path-rx path)
817 (cut match:substring <> 2))))
2c6ab6cc
LC
818
819(define (store-path-hash-part path)
820 "Return the hash part of PATH as a base32 string, or #f if PATH is not a
821syntactically valid store path."
5c0f1845 822 (let ((path-rx (store-regexp* (%store-prefix))))
2c6ab6cc
LC
823 (and=> (regexp-exec path-rx path)
824 (cut match:substring <> 1))))
eddd4077
LC
825
826(define (log-file store file)
827 "Return the build log file for FILE, or #f if none could be found. FILE
828must be an absolute store file name, or a derivation file name."
eddd4077 829 (cond ((derivation-path? file)
021a201f 830 (let* ((base (basename file))
80d0447c 831 (log (string-append (dirname %state-directory) ; XXX
f5768afa 832 "/log/guix/drvs/"
021a201f
LC
833 (string-take base 2) "/"
834 (string-drop base 2)))
835 (log.bz2 (string-append log ".bz2")))
836 (cond ((file-exists? log.bz2) log.bz2)
837 ((file-exists? log) log)
838 (else #f))))
eddd4077
LC
839 (else
840 (match (valid-derivers store file)
841 ((derivers ...)
842 ;; Return the first that works.
843 (any (cut log-file store <>) derivers))
844 (_ #f)))))