Move base32 code to (guix base32).
[jackhill/guix/guix.git] / distro / packages / bootstrap.scm
CommitLineData
18633d4f
LC
1;;; Guix --- Nix package management from Guile. -*- coding: utf-8 -*-
2;;; Copyright (C) 2012 Ludovic Courtès <ludo@gnu.org>
3;;;
4;;; This file is part of Guix.
5;;;
6;;; Guix is free software; you can redistribute it and/or modify it
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;;;
11;;; Guix is distributed in the hope that it will be useful, but
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
17;;; along with Guix. If not, see <http://www.gnu.org/licenses/>.
18
19(define-module (distro packages bootstrap)
20 #:use-module (distro)
21 #:use-module (guix packages)
22 #:use-module (guix ftp)
23 #:use-module (guix http)
24 #:use-module (guix build-system)
25 #:use-module (guix build-system gnu)
26 #:use-module (guix build-system trivial)
27 #:use-module ((guix store) #:select (add-to-store add-text-to-store))
28 #:use-module ((guix derivations) #:select (derivation))
29 #:use-module (guix utils)
30 #:use-module (srfi srfi-1)
31 #:use-module (srfi srfi-26)
32 #:use-module (ice-9 match)
33 #:export (bootstrap-origin
34 package-with-bootstrap-guile
35 glibc-dynamic-linker
36
37 %bootstrap-guile
38 %bootstrap-coreutils&co
39 %bootstrap-binutils
40 %bootstrap-gcc
41 %bootstrap-glibc
42 %bootstrap-inputs))
43
44;;; Commentary:
45;;;
46;;; Pre-built packages that are used to bootstrap the
47;;; distribution--i.e., to build all the core packages from scratch.
48;;;
49;;; Code:
50
51
52\f
53;;;
54;;; Helper procedures.
55;;;
56
57(define (bootstrap-origin source)
58 "Return a variant of SOURCE, an <origin> instance, whose method uses
59%BOOTSTRAP-GUILE to do its job."
60 (define (boot fetch)
61 (lambda* (store url hash-algo hash
62 #:optional name #:key system)
63 (fetch store url hash-algo hash
64 #:guile %bootstrap-guile
65 #:system system)))
66
67 (let ((orig-method (origin-method source)))
68 (origin (inherit source)
69 (method (cond ((eq? orig-method http-fetch)
70 (boot http-fetch))
71 ((eq? orig-method ftp-fetch)
72 (boot ftp-fetch))
73 (else orig-method))))))
74
75(define (package-from-tarball name* source* program-to-test description*)
76 "Return a package that correspond to the extraction of SOURCE*.
77PROGRAM-TO-TEST is a program to run after extraction of SOURCE*, to
78check whether everything is alright."
79 (package
80 (name name*)
81 (version "0")
82 (source #f)
83 (build-system trivial-build-system)
84 (arguments
85 `(#:guile ,%bootstrap-guile
86 #:modules ((guix build utils))
87 #:builder
88 (let ((out (assoc-ref %outputs "out"))
89 (tar (assoc-ref %build-inputs "tar"))
90 (xz (assoc-ref %build-inputs "xz"))
91 (tarball (assoc-ref %build-inputs "tarball")))
92 (use-modules (guix build utils))
93
94 (mkdir out)
95 (copy-file tarball "binaries.tar.xz")
96 (system* xz "-d" "binaries.tar.xz")
97 (let ((builddir (getcwd)))
98 (with-directory-excursion out
99 (and (zero? (system* tar "xvf"
100 (string-append builddir "/binaries.tar")))
101 (zero? (system* (string-append "bin/" ,program-to-test)
102 "--version"))))))))
103 (inputs
104 `(("tar" ,(lambda (system)
105 (search-bootstrap-binary "tar" system)))
106 ("xz" ,(lambda (system)
107 (search-bootstrap-binary "xz" system)))
108 ("tarball" ,(lambda (system)
109 (bootstrap-origin (source* system))))))
110 (synopsis description*)
111 (description #f)
112 (home-page #f)))
113
114(define package-with-bootstrap-guile
115 (memoize
116 (lambda (p)
117 "Return a variant of P such that all its origins are fetched with
118%BOOTSTRAP-GUILE."
119 (define rewritten-input
120 (match-lambda
121 ((name (? origin? o))
122 `(,name ,(bootstrap-origin o)))
123 ((name (? package? p) sub-drvs ...)
124 `(,name ,(package-with-bootstrap-guile p) ,@sub-drvs))
125 (x x)))
126
127 (package (inherit p)
128 (source (match (package-source p)
129 ((? origin? o) (bootstrap-origin o))
130 (s s)))
131 (inputs (map rewritten-input
132 (package-inputs p)))
133 (native-inputs (map rewritten-input
134 (package-native-inputs p)))
135 (propagated-inputs (map rewritten-input
136 (package-propagated-inputs p)))))))
137
138(define (glibc-dynamic-linker system)
139 "Return the name of Glibc's dynamic linker for SYSTEM."
140 (cond ((string=? system "x86_64-linux") "/lib/ld-linux-x86-64.so.2")
141 ((string=? system "i686-linux") "/lib/ld-linux.so.2")
142 (else (error "dynamic linker name not known for this system"
143 system))))
144
145\f
146;;;
147;;; Bootstrap packages.
148;;;
149
150(define %bootstrap-guile
151 ;; The Guile used to run the build scripts of the initial derivations.
152 ;; It is just unpacked from a tarball containing a pre-built binary.
153 ;; This is typically built using %GUILE-BOOTSTRAP-TARBALL below.
154 ;;
155 ;; XXX: Would need libc's `libnss_files2.so' for proper `getaddrinfo'
156 ;; support (for /etc/services).
157 (let ((raw (build-system
158 (name "raw")
159 (description "Raw build system with direct store access")
160 (build (lambda* (store name source inputs #:key outputs system)
161 (define (->store file)
162 (add-to-store store file #t #t "sha256"
163 (or (search-bootstrap-binary file
164 system)
165 (error "bootstrap binary not found"
166 file system))))
167
168 (let* ((tar (->store "tar"))
169 (xz (->store "xz"))
170 (mkdir (->store "mkdir"))
171 (bash (->store "bash"))
172 (guile (->store "guile-bootstrap-2.0.6.tar.xz"))
173 (builder
174 (add-text-to-store store
175 "build-bootstrap-guile.sh"
176 (format #f "
177echo \"unpacking bootstrap Guile to '$out'...\"
178~a $out
179cd $out
180~a -dc < ~a | ~a xv
181
182# Sanity check.
183$out/bin/guile --version~%"
184 mkdir xz guile tar)
185 (list mkdir xz guile tar))))
186 (derivation store name system
187 bash `(,builder) '()
188 `((,bash) (,builder)))))))))
189 (package
190 (name "guile-bootstrap")
191 (version "2.0")
192 (source #f)
193 (build-system raw)
194 (synopsis "Bootstrap Guile")
195 (description "Pre-built Guile for bootstrapping purposes.")
196 (home-page #f)
197 (license "LGPLv3+"))))
198
199(define %bootstrap-base-url
200 ;; This is where the initial binaries come from.
201 "http://www.fdn.fr/~lcourtes/software/guix/packages")
202
203(define %bootstrap-coreutils&co
204 (package-from-tarball "bootstrap-binaries"
205 (lambda (system)
206 (origin
207 (method http-fetch)
208 (uri (string-append
209 %bootstrap-base-url "/"
210 system "/static-binaries.tar.xz"))
211 (sha256
212 (match system
213 ("x86_64-linux"
214 (base32
215 "0azisn8l2b3cvgni9k0ahzsxs5cxrj0hmf38zgpq3k6pggk3zbfm"))
216 ("i686-linux"
217 (base32
218 "16v60frbh0naccanwxcxz0z3444dd8salbg8p7cp7vwz8245nhfk"))))))
219 "true" ; the program to test
220 "Bootstrap binaries of Coreutils, Awk, etc."))
221
222(define %bootstrap-binutils
223 (package-from-tarball "binutils-bootstrap"
224 (lambda (system)
225 (origin
226 (method http-fetch)
227 (uri (string-append
228 %bootstrap-base-url "/"
229 system "/binutils-2.22.tar.xz"))
230 (sha256
231 (match system
232 ("x86_64-linux"
233 (base32
234 "1cz1rwqhswgrr14kzbkaj3k32kzgv2b6mmzvc6ssbbz8k2m8jmqa"))
235 ("i686-linux"
236 (base32
237 "1crg5xsf4cxk249sg90h6fjhfkwj1s5dxvhwbym79g79ygbww1br"))))))
238 "ld" ; the program to test
239 "Bootstrap binaries of the GNU Binutils"))
240
241(define %bootstrap-glibc
242 ;; The initial libc.
243 (package
244 (name "glibc-bootstrap")
245 (version "0")
246 (source #f)
247 (build-system trivial-build-system)
248 (arguments
249 `(#:guile ,%bootstrap-guile
250 #:modules ((guix build utils))
251 #:builder
252 (let ((out (assoc-ref %outputs "out"))
253 (tar (assoc-ref %build-inputs "tar"))
254 (xz (assoc-ref %build-inputs "xz"))
255 (tarball (assoc-ref %build-inputs "tarball")))
256 (use-modules (guix build utils))
257
258 (mkdir out)
259 (copy-file tarball "binaries.tar.xz")
260 (system* xz "-d" "binaries.tar.xz")
261 (let ((builddir (getcwd)))
262 (with-directory-excursion out
263 (system* tar "xvf"
264 (string-append builddir
265 "/binaries.tar"))
266 (chmod "lib" #o755)
267
268 ;; Patch libc.so so it refers to the right path.
269 (substitute* "lib/libc.so"
270 (("/[^ ]+/lib/(libc|ld)" _ prefix)
271 (string-append out "/lib/" prefix))))))))
272 (inputs
273 `(("tar" ,(lambda (system)
274 (search-bootstrap-binary "tar" system)))
275 ("xz" ,(lambda (system)
276 (search-bootstrap-binary "xz" system)))
277 ("tarball" ,(lambda (system)
278 (bootstrap-origin
279 (origin
280 (method http-fetch)
281 (uri (string-append %bootstrap-base-url "/"
282 system "/glibc-2.16.0.tar.xz"))
283 (sha256
284 (match system
285 ("x86_64-linux"
286 (base32
287 "1cz587p3scrrx0zgqnmp4nnfj0vvf01zdqdgkz445dnbfh64nl0v"))
288 ("i686-linux"
289 (base32
290 "0vzybz1577vflm0p0zg1slqj32carj5102b45k7iskkj46viy14z"))))))))))
291 (synopsis "Bootstrap binaries and headers of the GNU C Library")
292 (description #f)
293 (home-page #f)))
294
295(define %bootstrap-gcc
296 ;; The initial GCC. Uses binaries from a tarball typically built by
297 ;; %GCC-BOOTSTRAP-TARBALL.
298 (package
299 (name "gcc-bootstrap")
300 (version "0")
301 (source #f)
302 (build-system trivial-build-system)
303 (arguments
304 (lambda (system)
305 `(#:guile ,%bootstrap-guile
306 #:modules ((guix build utils))
307 #:builder
308 (let ((out (assoc-ref %outputs "out"))
309 (tar (assoc-ref %build-inputs "tar"))
310 (xz (assoc-ref %build-inputs "xz"))
311 (bash (assoc-ref %build-inputs "bash"))
312 (libc (assoc-ref %build-inputs "libc"))
313 (tarball (assoc-ref %build-inputs "tarball")))
314 (use-modules (guix build utils)
315 (ice-9 popen))
316
317 (mkdir out)
318 (copy-file tarball "binaries.tar.xz")
319 (system* xz "-d" "binaries.tar.xz")
320 (let ((builddir (getcwd))
321 (bindir (string-append out "/bin")))
322 (with-directory-excursion out
323 (system* tar "xvf"
324 (string-append builddir "/binaries.tar")))
325
326 (with-directory-excursion bindir
327 (chmod "." #o755)
328 (rename-file "gcc" ".gcc-wrapped")
329 (call-with-output-file "gcc"
330 (lambda (p)
331 (format p "#!~a
332exec ~a/bin/.gcc-wrapped -B~a/lib \
333 -Wl,-rpath -Wl,~a/lib \
334 -Wl,-dynamic-linker -Wl,~a/~a \"$@\"~%"
335 bash
336 out libc libc libc
337 ,(glibc-dynamic-linker system))))
338
339 (chmod "gcc" #o555)))))))
340 (inputs
341 `(("tar" ,(lambda (system)
342 (search-bootstrap-binary "tar" system)))
343 ("xz" ,(lambda (system)
344 (search-bootstrap-binary "xz" system)))
345 ("bash" ,(lambda (system)
346 (search-bootstrap-binary "bash" system)))
347 ("libc" ,%bootstrap-glibc)
348 ("tarball" ,(lambda (system)
349 (bootstrap-origin
350 (origin
351 (method http-fetch)
352 (uri (string-append %bootstrap-base-url "/"
353 system "/gcc-4.7.2.tar.xz"))
354 (sha256
355 (match system
356 ("x86_64-linux"
357 (base32
358 "07piqzcdaksjbcj037y5gdbh9dfqwzjivg6fkhgg8kif82ibwxxr"))
359 ("i686-linux"
360 (base32
361 "0caiihphp23rrqn382cabykz9ps3ixd5p63dgdnkhz1f01jiarl2"))))))))))
362 (synopsis "Bootstrap binaries of the GNU Compiler Collection")
363 (description #f)
364 (home-page #f)))
365
366(define %bootstrap-inputs
367 ;; The initial, pre-built inputs. From now on, we can start building our
368 ;; own packages.
369 `(("libc" ,%bootstrap-glibc)
370 ("gcc" ,%bootstrap-gcc)
371 ("binutils" ,%bootstrap-binutils)
372 ("coreutils&co" ,%bootstrap-coreutils&co)))
373
374;;; bootstrap.scm ends here