diff options
| author | Morgan Arnold <morgan.arnold@proton.me> | 2025-03-06 10:16:29 +0000 |
|---|---|---|
| committer | Ludovic Courtès <ludo@gnu.org> | 2025-06-06 18:41:19 +0200 |
| commit | b5745a327e8dae21caaf10b59256dc7b16d54588 (patch) | |
| tree | 209ab88d1fa10cce5be4d04943a71f25b4a0d0bc | |
| parent | a54f3f3e2ab2e518cbb868fcc909fc7ba6b16f3f (diff) | |
publish: Prevent publication of non-substitutable derivation outputs.
This commit prevents Guix substitute servers from distributing binaries
which are marked non-substitutable. This prevents substitute servers
from accidentally committing copyright violations by distributing
binaries that are non-substitutable for copyright reasons.
* guix/scripts/publish.scm (render-nar): Query the derivers of
‘store-path’ and do nothing if one of them does not match
‘substitutable-derivation?’.
* tests/publish.scm ("non-substitutable derivation"): New test.
Change-Id: Iaca81f5bdb430a12a3ad41e9b83e0bcc535af607
Signed-off-by: Ludovic Courtès <ludo@gnu.org>
Modified-by: Ludovic Courtès <ludo@gnu.org>
| -rw-r--r-- | guix/scripts/publish.scm | 8 | ||||
| -rw-r--r-- | tests/publish.scm | 17 |
2 files changed, 23 insertions, 2 deletions
diff --git a/guix/scripts/publish.scm b/guix/scripts/publish.scm index 6f993ef0d64..e9c69336392 100644 --- a/guix/scripts/publish.scm +++ b/guix/scripts/publish.scm | |||
| @@ -61,6 +61,7 @@ | |||
| 61 | #:use-module (guix cache) | 61 | #:use-module (guix cache) |
| 62 | #:use-module (guix ui) | 62 | #:use-module (guix ui) |
| 63 | #:use-module (guix scripts) | 63 | #:use-module (guix scripts) |
| 64 | #:use-module (guix derivations) | ||
| 64 | #:use-module ((guix utils) | 65 | #:use-module ((guix utils) |
| 65 | #:select (with-atomic-file-output compressed-file?)) | 66 | #:select (with-atomic-file-output compressed-file?)) |
| 66 | #:use-module ((guix build utils) | 67 | #:use-module ((guix build utils) |
| @@ -693,11 +694,14 @@ requested using POOL." | |||
| 693 | (define* (render-nar store request store-item | 694 | (define* (render-nar store request store-item |
| 694 | #:key (compression %no-compression)) | 695 | #:key (compression %no-compression)) |
| 695 | "Render archive of the store path corresponding to STORE-ITEM." | 696 | "Render archive of the store path corresponding to STORE-ITEM." |
| 696 | (let ((store-path (string-append %store-directory "/" store-item))) | 697 | (let* ((store-path (string-append %store-directory "/" store-item)) |
| 698 | (derivations (map read-derivation-from-file | ||
| 699 | (valid-derivers store store-path))) | ||
| 700 | (substitutable? (every substitutable-derivation? derivations))) | ||
| 697 | ;; The ISO-8859-1 charset *must* be used otherwise HTTP clients will | 701 | ;; The ISO-8859-1 charset *must* be used otherwise HTTP clients will |
| 698 | ;; interpret the byte stream as UTF-8 and arbitrarily change invalid byte | 702 | ;; interpret the byte stream as UTF-8 and arbitrarily change invalid byte |
| 699 | ;; sequences. | 703 | ;; sequences. |
| 700 | (if (valid-path? store store-path) | 704 | (if (and substitutable? (valid-path? store store-path)) |
| 701 | (values `((content-type . (application/x-nix-archive | 705 | (values `((content-type . (application/x-nix-archive |
| 702 | (charset . "ISO-8859-1"))) | 706 | (charset . "ISO-8859-1"))) |
| 703 | (x-nar-compression . ,compression)) | 707 | (x-nar-compression . ,compression)) |
diff --git a/tests/publish.scm b/tests/publish.scm index 3c80c50d515..c8f66b69cd1 100644 --- a/tests/publish.scm +++ b/tests/publish.scm | |||
| @@ -425,6 +425,23 @@ FileSize: ~a~%" | |||
| 425 | (display "This file is not a valid store item." port))) | 425 | (display "This file is not a valid store item." port))) |
| 426 | (response-code (http-get (publish-uri (string-append "/nar/invalid")))))) | 426 | (response-code (http-get (publish-uri (string-append "/nar/invalid")))))) |
| 427 | 427 | ||
| 428 | (test-equal "non-substitutable derivation" | ||
| 429 | 404 | ||
| 430 | (let* ((non-substitutable | ||
| 431 | (run-with-store %store | ||
| 432 | (gexp->derivation "non-substitutable" | ||
| 433 | #~(begin | ||
| 434 | (mkdir #$output) | ||
| 435 | (chdir #$output) | ||
| 436 | (call-with-output-file "foo.txt" | ||
| 437 | (lambda (port) | ||
| 438 | (display "bar" port)))) | ||
| 439 | #:substitutable? #f))) | ||
| 440 | (item (derivation->output-path non-substitutable))) | ||
| 441 | (build-derivations %store (list non-substitutable)) | ||
| 442 | (response-code (http-get (publish-uri | ||
| 443 | (string-append "/nar/" (basename item))))))) | ||
| 444 | |||
| 428 | (test-equal "/file/NAME/sha256/HASH" | 445 | (test-equal "/file/NAME/sha256/HASH" |
| 429 | "Hello, Guix world!" | 446 | "Hello, Guix world!" |
| 430 | (let* ((data "Hello, Guix world!") | 447 | (let* ((data "Hello, Guix world!") |
