~ruther/guix-kria

guix-kria/modules/zynqmp/packages/images.scm -rw-r--r-- 7.0 KiB
79fd3786 — Rutherther chore: Add script to build the final image 2 months ago
                                                                                
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
(define-module (zynqmp packages images)
  #:use-module (zynqmp packages bootloader)
  #:use-module (zynqmp packages linux)
  #:use-module (guix packages)
  #:use-module (guix modules)
  #:use-module (guix gexp)
  #:use-module (guix build-system trivial)
  #:use-module (gnu services base)
  #:use-module (gnu packages base)
  #:use-module (gnu system)
  #:use-module (gnu system shadow)
  #:use-module (gnu system nss)
  #:use-module (gnu system image)
  #:use-module (gnu image)
  #:use-module (gnu bootloader extlinux)
  #:use-module (gnu bootloader))

(define root-offset (+ 512 (* 256 1024 1024)))

;; TODO: FDT
(define* (install-xilinx-bootloader fdt)
  (with-imported-modules '((zynqmp build bootloader))
    #~(begin
        (use-modules (zynqmp build bootloader))

        (lambda (bootloader device mount-point)
          (let* ((bootcfg-file (string-append (getcwd) "/" mount-point "/bootcfg"))
                 (bootcfg (load bootcfg-file)))

            ;; Configuration
            (mkdir-p (string-append mount-point "/extlinux"))
            (call-with-output-file
                (string-append mount-point "/extlinux/extlinux.conf")
              (lambda (port)
                (display (apply string-append (map bootcfg-entry->config-menu-entry bootcfg)) port)))

            ;; GNU store needed files
            (for-each
             (lambda (source-file)
               (let* ((dest-file (string-append mount-point source-file)))
                 (mkdir-p (dirname dest-file))
                 (copy-recursively source-file dest-file)))
             (get-required-files bootcfg))


            (copy-file (string-append bootloader "/libexec/boot.bin")
                       (string-append mount-point "/boot.bin"))
            (copy-file (string-append bootloader "/libexec/u-boot.itb")
                       (string-append mount-point "/u-boot.itb"))

            ;; From the first element extract linux.
            ;; There can be just one fdt file... the first element should be the newest...
            (let* ((entry (list-ref bootcfg 0))
                   (linux (list-ref entry 1))
                   (linux-dir (dirname linux)))
              (copy-file (string-append linux-dir "/lib/dtbs/" #$fdt ".dtb")
                         (string-append mount-point "/system.dtb"))))))))

;; This is just a configuration stub. Actually it will write the bootcfg to a file.
;; This file is then consumed by the install bootloader script. And this script
;; will generate the proper configuration
(define* (xilinx-external-bootloader-configuration config entries #:key #:allow-other-keys)
  (define all-entries
    (append entries (bootloader-configuration-menu-entries config)))

  (define (menu-entry->gexp entry)
    (let ((label (menu-entry-label entry))
          (kernel (menu-entry-linux entry))
          (kernel-arguments (menu-entry-linux-arguments entry))
          (initrd (menu-entry-initrd entry)))
      #~(list #$label #$kernel (list #$@kernel-arguments) #$initrd)))

  (define builder
    #~(call-with-output-file #$output
        (lambda (port)
          (write '(list #$@(map menu-entry->gexp all-entries)) port))))

  (computed-file "bootcfg" builder))

(define xilinx-bootloader
  (bootloader
   (inherit extlinux-bootloader)
   (name 'xilinx-uboot)
   (package u-boot-for-kr260)
   (configuration-file-generator xilinx-external-bootloader-configuration)
   (installer (install-xilinx-bootloader "xilinx/zynqmp-smk-k26-revA-sck-kr-g-revB"))
   (configuration-file "/bootcfg")))

(define root-partition
  (partition
   (size 'guess)
   (label "root")
   (file-system "ext4")
   (offset root-offset)
   ;; Disable the metadata_csum and 64bit features of ext4, for compatibility
   ;; with U-Boot.
   (file-system-options (list "-O" "^metadata_csum,^64bit"))
   (flags '(boot))
   (initializer
    #~(lambda* (root #:key
                 (copy-closures? #t)
                 (deduplicate? #t)
                 references-graphs
                 (register-closures? #t)
                 system-directory
                 make-device-nodes
                 (wal-mode? #t)
                 #:allow-other-keys)
        (initialize-root-partition root
                                   #:bootcfg #f
                                   #:bootcfg-location #f
                                   #:bootloader-package #f
                                   #:bootloader-installer #f
                                   #:copy-closures? copy-closures?
                                   #:deduplicate? deduplicate?
                                   #:references-graphs references-graphs
                                   #:system-directory system-directory
                                   #:make-device-nodes make-device-nodes
                                   #:wal-mode? wal-mode?)))))

(define boot-partition
  (partition
   (size (* 256 1024 1024))
   (label "BOOT")
   (file-system "vfat")
   (offset 512)
   (flags '(boot))
   (initializer
    (with-imported-modules (source-module-closure
                            '((guix build utils)
                              (gnu build install)))
      #~(lambda* (root #:key
                   bootcfg
                   bootcfg-location
                   bootloader-package
                   bootloader-installer
                   (copy-closures? #t)
                   (deduplicate? #t)
                   references-graphs
                   (register-closures? #t)
                   system-directory
                   make-device-nodes
                   (wal-mode? #t)
                   #:allow-other-keys)
          (use-modules (gnu build install))
          (mkdir-p root)
          (when bootcfg
            (install-boot-config bootcfg bootcfg-location root))
          (when bootloader-installer
            (display "installing bootloader...\n")
            (bootloader-installer bootloader-package #f root)
            (display "bootloader installed...\n")))))))

(define os
  (operating-system
    (host-name "guix")
    (timezone "Europe/Prague")
    (bootloader
     (bootloader-configuration
      (bootloader xilinx-bootloader)))
    (kernel-arguments '("console=ttyPS1,115200"))
    (kernel xilinx-linux-for-zynqmp)
    (initrd-modules '())
    (file-systems (list)) ; Doesn't matter as replaced by image
    (users %base-user-accounts)
    (packages %base-packages)
    (services %base-services)
    (name-service-switch %mdns-host-lookup-nss)))

(define-public zynqmp-base-image
  (image
   (operating-system os)
   (format 'disk-image)
   (partition-table-type 'mbr) ;; TODO
   (volatile-root? #f)
   (partitions
    (list root-partition
          boot-partition))))

(define-public zynqmp-base-system-image
  (package
    (name "zynqmp-base-system-image.img")
    (version "0")
    (source #f)
    (build-system trivial-build-system)
    (arguments
     (list
      #:modules '((guix build utils))
      #:builder
      #~(begin
          (use-modules (guix build utils))
          (symlink
           #$(system-image zynqmp-base-image)
           #$output))))
    (synopsis #f)
    (home-page #f)
    (license #f)
    (description #f)))