diff mbox series

[bug#45101] scripts: discover: Remove file locks.

Message ID 20201207131706.96073-1-othacehe@gnu.org
State Accepted
Headers show
Series [bug#45101] scripts: discover: Remove file locks. | expand

Checks

Context Check Description
cbaines/comparison success View comparision
cbaines/git branch success View Git branch
cbaines/applying patch success View Laminar job
cbaines/issue success View issue

Commit Message

Mathieu Othacehe Dec. 7, 2020, 1:17 p.m. UTC
* guix/scripts/discover.scm (call-once, call-with-output-file/atomic): New
procedures copied from (system base compile).
(call-with-read-file-lock, with-read-file-lock): Remove them.
(write-publish-file): Use "call-with-output-file/atomic" instead of
"with-file-lock".
(read-substitute-urls): Remve file lock.
---
 guix/scripts/discover.scm | 86 +++++++++++++++++++++------------------
 1 file changed, 46 insertions(+), 40 deletions(-)

Comments

Ludovic Courtès Dec. 12, 2020, 7:52 p.m. UTC | #1
Hi!

Mathieu Othacehe <othacehe@gnu.org> skribis:

> * guix/scripts/discover.scm (call-once, call-with-output-file/atomic): New
> procedures copied from (system base compile).
> (call-with-read-file-lock, with-read-file-lock): Remove them.
> (write-publish-file): Use "call-with-output-file/atomic" instead of
> "with-file-lock".
> (read-substitute-urls): Remve file lock.

I think you could use ‘with-atomic-file-output’ from (guix utils).
(Apologies if I gave you the wrong name before!)

Apart from that LGTM, thanks!  :-)

Ludo’.
Mathieu Othacehe Dec. 13, 2020, 12:25 p.m. UTC | #2
Hey,

> I think you could use ‘with-atomic-file-output’ from (guix utils).
> (Apologies if I gave you the wrong name before!)
>
> Apart from that LGTM, thanks!  :-)

Fixed and pushed!

Thanks,

Mathieu
diff mbox series

Patch

diff --git a/guix/scripts/discover.scm b/guix/scripts/discover.scm
index 007db0d49d..86834a7afb 100644
--- a/guix/scripts/discover.scm
+++ b/guix/scripts/discover.scm
@@ -75,50 +75,60 @@  CACHE-DIRECTORY."
 (define %publish-file
   (make-parameter (publish-file %state-directory)))
 
+;; XXX: Copied from (system base compile).
+(define (call-once thunk)
+  (let ((entered #f))
+    (dynamic-wind
+        (lambda ()
+          (when entered
+            (error "thunk may only be entered once: ~a" thunk))
+          (set! entered #t))
+        thunk
+        (lambda () #t))))
+
+(define* (call-with-output-file/atomic filename proc #:optional reference)
+  (let* ((template (string-append filename ".XXXXXX"))
+         (tmp (mkstemp! template "wb")))
+    (call-once
+     (lambda ()
+       (with-throw-handler #t
+         (lambda ()
+           (proc tmp)
+           ;; Chmodding by name instead of by port allows this chmod to
+           ;; work on systems without fchmod, like MinGW.
+           (let ((perms (or (false-if-exception (stat:perms (stat reference)))
+                            (lognot (umask)))))
+             (chmod template (logand #o0666 perms)))
+           (close-port tmp)
+           (rename-file template filename))
+         (lambda args
+           (close-port tmp)
+           (delete-file template)))))))
+
 (define* (write-publish-file #:key (file (%publish-file)))
   "Dump the content of %PUBLISH-SERVICES hash table into FILE.  Use a write
 lock on FILE to synchronize with any potential readers."
-  (with-file-lock file
-    (call-with-output-file file
-      (lambda (port)
-        (hash-for-each
-         (lambda (name service)
-           (format port "http://~a:~a~%"
-                   (avahi-service-address service)
-                   (avahi-service-port service)))
-         %publish-services)))
-        (chmod file #o644)))
-
-(define (call-with-read-file-lock file thunk)
-  "Call THUNK with a read lock on FILE."
-  (let ((port #f))
-    (dynamic-wind
-      (lambda ()
-        (set! port
-              (let ((port (open-file file "r0")))
-                (fcntl-flock port 'read-lock)
-                port)))
-      thunk
-      (lambda ()
-        (when port
-          (unlock-file port))))))
-
-(define-syntax-rule (with-read-file-lock file exp ...)
-  "Wait to acquire a read lock on FILE and evaluate EXP in that context."
-  (call-with-read-file-lock file (lambda () exp ...)))
+  (call-with-output-file/atomic file
+    (lambda (port)
+      (hash-for-each
+       (lambda (name service)
+         (format port "http://~a:~a~%"
+                 (avahi-service-address service)
+                 (avahi-service-port service)))
+       %publish-services)))
+  (chmod file #o644))
 
 (define* (read-substitute-urls #:key (file (%publish-file)))
   "Read substitute urls list from FILE and return it.  Use a read lock on FILE
 to synchronize with the writer."
   (if (file-exists? file)
-      (with-read-file-lock file
-        (call-with-input-file file
-          (lambda (port)
-            (let loop ((url (read-line port))
-                       (urls '()))
-              (if (eof-object? url)
-                  urls
-                  (loop (read-line port) (cons url urls)))))))
+      (call-with-input-file file
+        (lambda (port)
+          (let loop ((url (read-line port))
+                     (urls '()))
+            (if (eof-object? url)
+                urls
+                (loop (read-line port) (cons url urls))))))
       '()))
 
 
@@ -158,7 +168,3 @@  to synchronize with the writer."
         (mkdir-p (dirname publish-file))
         (avahi-browse-service-thread service-proc
                                      #:types %services)))))
-
-;;; Local Variables:
-;;; eval: (put 'with-read-file-lock 'scheme-indent-function 1)
-;;; End: