Page MenuHome GnuPG

No OneTemporary

diff --git a/tests/gpgscm/tests.scm b/tests/gpgscm/tests.scm
index ebe1be5c6..272881757 100644
--- a/tests/gpgscm/tests.scm
+++ b/tests/gpgscm/tests.scm
@@ -1,428 +1,440 @@
;; Common definitions for writing tests.
;;
;; Copyright (C) 2016 g10 Code GmbH
;;
;; This file is part of GnuPG.
;;
;; GnuPG is free software; you can redistribute it and/or modify
;; it under the terms of the GNU General Public License as published by
;; the Free Software Foundation; either version 3 of the License, or
;; (at your option) any later version.
;;
;; GnuPG is distributed in the hope that it will be useful,
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
;; GNU General Public License for more details.
;;
;; You should have received a copy of the GNU General Public License
;; along with this program; if not, see <http://www.gnu.org/licenses/>.
;; Trace displays and returns the given value. A debugging aid.
(define (trace x)
(display x)
(newline)
x)
;; Stringification.
(define (stringify expression)
(let ((p (open-output-string)))
(write expression p)
(get-output-string p)))
;; Reporting.
(define (echo . msg)
(for-each (lambda (x) (display x) (display " ")) msg)
(newline))
(define (info . msg)
(apply echo msg)
(flush-stdio))
(define (error . msg)
(apply info msg)
(exit 1))
(define (skip . msg)
(apply info msg)
(exit 77))
(define (make-counter)
(let ((c 0))
(lambda ()
(let ((r c))
(set! c (+ 1 c))
r))))
(define *progress-nesting* 0)
(define (call-with-progress msg what)
(set! *progress-nesting* (+ 1 *progress-nesting*))
(if (= 1 *progress-nesting*)
(begin
(info msg)
(display " > ")
(flush-stdio)
(what (lambda (item)
(display item)
(display " ")
(flush-stdio)))
(info "< "))
(begin
(what (lambda (item) (display ".") (flush-stdio)))
(display " ")
(flush-stdio)))
(set! *progress-nesting* (- *progress-nesting* 1)))
(define (for-each-p msg proc lst)
(for-each-p' msg proc (lambda (x) x) lst))
(define (for-each-p' msg proc fmt lst)
(call-with-progress
msg
(lambda (progress)
(for-each (lambda (a)
(progress (fmt a))
(proc a))
lst))))
;; Process management.
(define CLOSED_FD -1)
(define (call-with-fds what infd outfd errfd)
(wait-process (stringify what) (spawn-process-fd what infd outfd errfd) #t))
(define (call what)
(call-with-fds what
CLOSED_FD
(if (< *verbose* 0) STDOUT_FILENO CLOSED_FD)
(if (< *verbose* 0) STDERR_FILENO CLOSED_FD)))
(define (call-check what)
(if (not (= 0 (call what)))
(throw (list what "failed"))))
;; Accessor functions for the results of 'spawn-process'.
(define :stdin car)
(define :stdout cadr)
(define :stderr caddr)
(define :pid cadddr)
(define (call-with-io what in)
(let ((h (spawn-process what 0)))
(es-write (:stdin h) in)
(es-fclose (:stdin h))
(let* ((out (es-read-all (:stdout h)))
(err (es-read-all (:stderr h)))
(result (wait-process (car what) (:pid h) #t)))
(es-fclose (:stdout h))
(es-fclose (:stderr h))
(list result out err))))
;; Accessor function for the results of 'call-with-io'. ':stdout' and
;; ':stderr' can also be used.
(define :retcode car)
(define (call-popen command input-string)
(let ((result (call-with-io command input-string)))
(if (= 0 (:retcode result))
(:stdout result)
(throw (:stderr result)))))
;;
;; estream helpers.
;;
(define (es-read-all stream)
(let loop
((acc ""))
(if (es-feof stream)
acc
(loop (string-append acc (es-read stream 4096))))))
;;
;; File management.
;;
(define (file-exists? name)
(call-with-input-file name (lambda (port) #t)))
(define (file=? a b)
(file-equal a b #t))
(define (text-file=? a b)
(file-equal a b #f))
(define (file-copy from to)
(catch '() (unlink to))
(letfd ((source (open from (logior O_RDONLY O_BINARY)))
(sink (open to (logior O_WRONLY O_CREAT O_BINARY) #o600)))
(splice source sink)))
(define (text-file-copy from to)
(catch '() (unlink to))
(letfd ((source (open from O_RDONLY))
(sink (open to (logior O_WRONLY O_CREAT) #o600)))
(splice source sink)))
+(define (path-join . components)
+ (let loop ((acc #f) (rest (filter (lambda (s)
+ (not (string=? "" s))) components)))
+ (if (null? rest)
+ acc
+ (loop (if (string? acc)
+ (string-append acc "/" (car rest))
+ (car rest))
+ (cdr rest)))))
+(assert (string=? (path-join "foo" "bar" "baz") "foo/bar/baz"))
+(assert (string=? (path-join "" "bar" "baz") "bar/baz"))
+
(define (canonical-path path)
(if (char=? #\/ (string-ref path 0))
path
(string-append (getcwd) "/" path)))
(define (in-srcdir what)
(canonical-path (string-append (getenv "srcdir") "/" what)))
(define (with-path name)
(let loop ((path (string-split (getenv "GPGSCM_PATH") #\:)))
(if (null? path)
name
(let* ((qualified-name (string-append (car path) "/" name))
(file-exists (call-with-input-file qualified-name
(lambda (x) #t))))
(if file-exists
qualified-name
(loop (cdr path)))))))
(define (basename path)
(let ((i (string-index path #\/)))
(if (equal? i #f)
path
(basename (substring path (+ 1 i) (string-length path))))))
(define (basename-suffix path suffix)
(basename
(if (string-suffix? path suffix)
(substring path 0 (- (string-length path) (string-length suffix)))
path)))
;; Helper for (pipe).
(define :read-end car)
(define :write-end cadr)
;; let-like macro that manages file descriptors.
;;
;; (letfd <bindings> <body>)
;;
;; Bind all variables given in <bindings> and initialize each of them
;; to the given initial value, and close them after evaluting <body>.
(macro (letfd form)
(let ((result-sym (gensym)))
`((lambda (,(caaadr form))
(let ((,result-sym
,(if (= 1 (length (cadr form)))
`(begin ,@(cddr form))
`(letfd ,(cdadr form) ,@(cddr form)))))
(close ,(caaadr form))
,result-sym)) ,@(cdaadr form))))
(macro (with-working-directory form)
(let ((result-sym (gensym)) (cwd-sym (gensym)))
`(let* ((,cwd-sym (getcwd))
(_ (if ,(cadr form) (chdir ,(cadr form))))
(,result-sym (begin ,@(cddr form))))
(chdir ,cwd-sym)
,result-sym)))
(macro (with-temporary-working-directory form)
(let ((result-sym (gensym)) (cwd-sym (gensym)) (tmp-sym (gensym)))
`(let* ((,cwd-sym (getcwd))
- (,tmp-sym (mkdtemp "gpgscm-XXXXXX"))
+ (,tmp-sym (mkdtemp (path-join (getenv "TMP") "gpgscm-XXXXXX")))
(_ (chdir ,tmp-sym))
(,result-sym (begin ,@(cdr form))))
(chdir ,cwd-sym)
(unlink-recursively ,tmp-sym)
,result-sym)))
(define (make-temporary-file . args)
- (canonical-path (string-append (mkdtemp "gpgscm-XXXXXX")
- "/"
- (if (null? args) "a" (car args)))))
+ (canonical-path (path-join
+ (mkdtemp (path-join (getenv "TMP") "gpgscm-XXXXXX"))
+ (if (null? args) "a" (car args)))))
(define (remove-temporary-file filename)
(catch '()
(unlink filename))
(let ((dirname (substring filename 0 (string-rindex filename #\/))))
(catch (echo "removing temporary directory" dirname "failed")
(rmdir dirname))))
;; let-like macro that manages temporary files.
;;
;; (lettmp <bindings> <body>)
;;
;; Bind all variables given in <bindings>, initialize each of them to
;; a string representing an unique path in the filesystem, and delete
;; them after evaluting <body>.
(macro (lettmp form)
(let ((result-sym (gensym)))
`((lambda (,(caadr form))
(let ((,result-sym
,(if (= 1 (length (cadr form)))
`(begin ,@(cddr form))
`(lettmp ,(cdadr form) ,@(cddr form)))))
(remove-temporary-file ,(caadr form))
,result-sym)) (make-temporary-file ,(symbol->string (caadr form))))))
(define (check-execution source transformer)
(lettmp (sink)
(transformer source sink)))
(define (check-identity source transformer)
(lettmp (sink)
(transformer source sink)
(if (not (file=? source sink))
(error "mismatch"))))
;;
;; Monadic pipe support.
;;
(define pipeM
(package
(define (new procs source sink producer)
(package
(define (dump)
(write (list procs source sink producer))
(newline))
(define (add-proc command pid)
(new (cons (list command pid) procs) source sink producer))
(define (commands)
(map car procs))
(define (pids)
(map cadr procs))
(define (set-source source')
(new procs source' sink producer))
(define (set-sink sink')
(new procs source sink' producer))
(define (set-producer producer')
(if producer
(throw "producer already set"))
(new procs source sink producer'))))))
(define (pipe:do . commands)
(let loop ((M (pipeM::new '() CLOSED_FD CLOSED_FD #f)) (cmds commands))
(if (null? cmds)
(begin
(if M::producer (M::producer))
(if (not (null? M::procs))
(let* ((retcodes (wait-processes (map stringify (M::commands))
(M::pids) #t))
(results (map (lambda (p r) (append p (list r)))
M::procs retcodes))
(failed (filter (lambda (x) (not (= 0 (caddr x))))
results)))
(if (not (null? failed))
(throw failed))))) ; xxx nicer reporting
(if (and (= 2 (length cmds)) (number? (cadr cmds)))
;; hack: if it's an fd, use it as sink
(let ((M' ((car cmds) (M::set-sink (cadr cmds)))))
(if (> M::source 2) (close M::source))
(if (> (cadr cmds) 2) (close (cadr cmds)))
(loop M' '()))
(let ((M' ((car cmds) M)))
(if (> M::source 2) (close M::source))
(loop M' (cdr cmds)))))))
(define (pipe:open pathname flags)
(lambda (M)
(M::set-source (open pathname flags))))
(define (pipe:defer producer)
(lambda (M)
(let* ((p (outbound-pipe))
(M' (M::set-source (:read-end p))))
(M'::set-producer (lambda ()
(producer (:write-end p))
(close (:write-end p)))))))
(define (pipe:echo data)
(pipe:defer (lambda (sink) (display data (fdopen sink "wb")))))
(define (pipe:spawn command)
(lambda (M)
(define (do-spawn M new-source)
(let ((pid (spawn-process-fd command M::source M::sink
(if (> *verbose* 0)
STDERR_FILENO CLOSED_FD)))
(M' (M::set-source new-source)))
(M'::add-proc command pid)))
(if (= CLOSED_FD M::sink)
(let* ((p (pipe))
(M' (do-spawn (M::set-sink (:write-end p)) (:read-end p))))
(close (:write-end p))
(M'::set-sink CLOSED_FD))
(do-spawn M CLOSED_FD))))
(define (pipe:splice sink)
(lambda (M)
(splice M::source sink)
(M::set-source CLOSED_FD)))
(define (pipe:write-to pathname flags mode)
(open pathname flags mode))
;;
;; Monadic transformer support.
;;
(define (tr:do . commands)
(let loop ((tmpfiles '()) (source #f) (cmds commands))
(if (null? cmds)
(for-each remove-temporary-file tmpfiles)
(let* ((v ((car cmds) tmpfiles source))
(tmpfiles' (car v))
(sink (cadr v))
(error (caddr v)))
(if error
(begin
(for-each remove-temporary-file tmpfiles')
(throw error)))
(loop tmpfiles' sink (cdr cmds))))))
(define (tr:open pathname)
(lambda (tmpfiles source)
(list tmpfiles pathname #f)))
(define (tr:spawn input command)
(lambda (tmpfiles source)
(if (and (member '**in** command) (not source))
(error (string-append (stringify cmd) " needs an input")))
(let* ((t (make-temporary-file))
(cmd (map (lambda (x)
(cond
((equal? '**in** x) source)
((equal? '**out** x) t)
(else x))) command)))
(catch (list (cons t tmpfiles) t *error*)
(call-popen cmd input)
(if (and (member '**out** command) (not (file-exists? t)))
(error (string-append (stringify cmd)
" did not produce '" t "'.")))
(list (cons t tmpfiles) t #f)))))
(define (tr:write-to pathname)
(lambda (tmpfiles source)
(rename source pathname)
(list tmpfiles pathname #f)))
(define (tr:pipe-do . commands)
(lambda (tmpfiles source)
(let ((t (make-temporary-file)))
(apply pipe:do
`(,@(if source `(,(pipe:open source (logior O_RDONLY O_BINARY))) '())
,@commands
,(pipe:write-to t (logior O_WRONLY O_BINARY O_CREAT) #o600)))
(list (cons t tmpfiles) t #f))))
(define (tr:assert-identity reference)
(lambda (tmpfiles source)
(if (not (file=? source reference))
(error "mismatch"))
(list tmpfiles source #f)))
(define (tr:assert-weak-identity reference)
(lambda (tmpfiles source)
(if (not (text-file=? source reference))
(error "mismatch"))
(list tmpfiles source #f)))
(define (tr:call-with-content function . args)
(lambda (tmpfiles source)
(catch (list tmpfiles source *error*)
(apply function `(,(call-with-input-file source read-all) ,@args)))
(list tmpfiles source #f)))
diff --git a/tests/migrations/Makefile.am b/tests/migrations/Makefile.am
index 0377b23d6..9c82d66ee 100644
--- a/tests/migrations/Makefile.am
+++ b/tests/migrations/Makefile.am
@@ -1,53 +1,56 @@
# Makefile.am - For tests/openpgp
# Copyright (C) 2016 g10 Code GmbH
#
# This file is part of GnuPG.
#
# GnuPG is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# GnuPG is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, see <http://www.gnu.org/licenses/>.
# Process this file with automake to create Makefile.in
# Programs required before we can run these tests.
required_pgms = ../../g10/gpg$(EXEEXT) ../../agent/gpg-agent$(EXEEXT)
AM_CPPFLAGS = -I$(top_srcdir)/common
include $(top_srcdir)/am/cmacros.am
AM_CFLAGS =
+TMP ?= /tmp
+
TESTS_ENVIRONMENT = GPG_AGENT_INFO= LC_ALL=C \
PATH=../gpgscm:$(PATH) \
+ TMP=$(TMP) \
GPGSCM_PATH=$(top_srcdir)/tests/gpgscm:$(top_srcdir)/tests/migrations
TESTS = from-classic.scm \
extended-pkf.scm
TEST_FILES = from-classic.tar.asc \
extended-pkf.tar.asc
EXTRA_DIST = common.scm $(TESTS) $(TEST_FILES)
CLEANFILES = prepared.stamp x y yy z out err $(data_files) \
plain-1 plain-2 plain-3 trustdb.gpg *.lock .\#lk* \
*.test.log gpg_dearmor gpg.conf gpg-agent.conf S.gpg-agent \
pubring.gpg pubring.gpg~ pubring.kbx pubring.kbx~ \
secring.gpg pubring.pkr secring.skr \
gnupg-test.stop random_seed gpg-agent.log tofu.db
clean-local:
-rm -rf from-classic.gpghome/*.gpg
# We need to depend on a couple of programs so that the tests don't
# start before all programs are built.
all-local: $(required_pgms)
diff --git a/tests/openpgp/Makefile.am b/tests/openpgp/Makefile.am
index 4137018d1..012a3f20c 100644
--- a/tests/openpgp/Makefile.am
+++ b/tests/openpgp/Makefile.am
@@ -1,164 +1,167 @@
# Makefile.am - For tests/openpgp
# Copyright (C) 1998, 1999, 2000, 2001, 2003,
# 2010 Free Software Foundation, Inc.
#
# This file is part of GnuPG.
#
# GnuPG is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# GnuPG is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, see <http://www.gnu.org/licenses/>.
# Process this file with automake to create Makefile.in
# Programs required before we can run these tests.
required_pgms = ../../g10/gpg$(EXEEXT) ../../agent/gpg-agent$(EXEEXT) \
../../tools/gpg-connect-agent$(EXEEXT) \
../../tools/mk-tdata$(EXEEXT) \
../gpgscm/gpgscm$(EXEEXT)
AM_CPPFLAGS = -I$(top_srcdir)/common
include $(top_srcdir)/am/cmacros.am
AM_CFLAGS =
noinst_PROGRAMS = fake-pinentry
fake_pinentry_SOURCES = fake-pinentry.c
+TMP ?= /tmp
+
TESTS_ENVIRONMENT = GNUPGHOME=$(abs_builddir) GPG_AGENT_INFO= LC_ALL=C \
EXEEXT=$(EXEEXT) \
PATH=../gpgscm:$(PATH) \
+ TMP=$(TMP) \
objdir=$(abs_top_builddir) \
GPGSCM_PATH=$(top_srcdir)/tests/gpgscm:$(top_srcdir)/tests/openpgp
# Note: setup.scm needs to be the first test to run and finish.scm
# the last one
TESTS = setup.scm \
version.scm \
mds.scm \
decrypt.scm \
decrypt-dsa.scm \
sigs.scm \
sigs-dsa.scm \
encrypt.scm \
encrypt-dsa.scm \
seat.scm \
clearsig.scm \
encryptp.scm \
detach.scm \
detachm.scm \
armsigs.scm \
armencrypt.scm \
armencryptp.scm \
signencrypt.scm \
signencrypt-dsa.scm \
armsignencrypt.scm \
armdetach.scm \
armdetachm.scm \
genkey1024.scm \
conventional.scm \
conventional-mdc.scm \
multisig.scm \
verify.scm \
armor.scm \
import.scm \
ecc.scm \
4gb-packet.scm \
tofu.scm \
gpgtar.scm \
use-exact-key.scm \
default-key.scm \
export.scm \
finish.scm
TEST_FILES = pubring.asc secring.asc plain-1o.asc plain-2o.asc plain-3o.asc \
plain-1.asc plain-2.asc plain-3.asc plain-1-pgp.asc \
plain-largeo.asc \
pubring.pkr.asc secring.skr.asc secdemo.asc pubdemo.asc \
gpg.conf.tmpl gpg-agent.conf.tmpl \
bug537-test.data.asc bug894-test.asc \
bug1223-good.asc bug1223-bogus.asc 4gb-packet.asc \
tofu-keys.asc tofu-keys-secret.asc \
tofu-2183839A-1.txt tofu-BC15C85A-1.txt tofu-EE37CF96-1.txt
data_files = data-500 data-9000 data-32000 data-80000 plain-large
priv_keys = privkeys/50B2D4FA4122C212611048BC5FC31BD44393626E.asc \
privkeys/7E201E28B6FEB2927B321F443205F4724EBE637E.asc \
privkeys/13FDB8809B17C5547779F9D205C45F47CE0217CE.asc \
privkeys/343D8AF79796EE107D645A2787A9D9252F924E6F.asc \
privkeys/8B5ABF3EF9EB8D96B91A0B8C2C4401C91C834C34.asc \
privkeys/0D6F6AD4C4C803B25470F9104E9F4E6A4CA64255.asc \
privkeys/FD692BD59D6640A84C8422573D469F84F3B98E53.asc \
privkeys/76F7E2B35832976B50A27A282D9B87E44577EB66.asc \
privkeys/A0747D5F9425E6664F4FFBEED20FBCA79FDED2BD.asc \
privkeys/0DD40284FF992CD24DC4AAC367037E066FCEE26A.asc \
privkeys/2BC997C0B8691D41D29A4EC81CCBCF08454E4961.asc \
privkeys/3C9D5ECA70130C2DBB1FC6AC0076BEEEC197716F.asc \
privkeys/449E644892C951A37525654730DD32C202079926.asc \
privkeys/58FFE844087634E62440224908BDE44BEA7EB730.asc \
privkeys/4DF9172D6FF428C97A0E9AA96F03E8BCE3B2F188.asc \
privkeys/9D7CD8F53F2F14C3E2177D1E9D1D11F39513A4A4.asc \
privkeys/6E6B7ED0BD4425018FFC54F3921D5467A3AE00EB.asc \
privkeys/C905D0AB6AE9655C5A35975939997BBF3325D6DD.asc \
privkeys/B2BAA7144303DF19BB6FDE23781DD3FDD97918D4.asc \
privkeys/CF60965BF51F67CF80DECE853E0D2D343468571D.asc \
privkeys/DF00E361D34F80868D06879AC21D7A7D4E4FAD76.asc \
privkeys/00FE67F28A52A8AA08FFAED20AF832DA916D1985.asc \
privkeys/1DF48228FEFF3EC2481B106E0ACA8C465C662CC5.asc \
privkeys/A2832820DC9F40751BDCD375BB0945BA33EC6B4C.asc \
privkeys/ADE710D74409777B7729A7653373D820F67892E0.asc \
privkeys/CEFC51AF91F68A2904FBFF62C4F075A4785B803F.asc \
privkeys/1E28F20E41B54C2D1234D896096495FF57E08D18.asc \
privkeys/EB33B687EB8581AB64D04852A54453E85F3DF62D.asc \
privkeys/C6A6390E9388CDBAD71EAEA698233FE5E04F001E.asc \
privkeys/D69102E0F5AC6B6DB8E4D16DA8E18CF46D88CAE3.asc
sample_keys = samplekeys/README \
samplekeys/ecc-sample-1-pub.asc \
samplekeys/ecc-sample-2-pub.asc \
samplekeys/ecc-sample-3-pub.asc \
samplekeys/ecc-sample-1-sec.asc \
samplekeys/ecc-sample-2-sec.asc \
samplekeys/ecc-sample-3-sec.asc \
samplekeys/eddsa-sample-1-pub.asc \
samplekeys/eddsa-sample-1-sec.asc \
samplekeys/dda252ebb8ebe1af-1.asc \
samplekeys/dda252ebb8ebe1af-2.asc \
samplekeys/whats-new-in-2.1.asc \
samplekeys/e2e-p256-1-clr.asc \
samplekeys/e2e-p256-1-prt.asc \
samplekeys/E657FB607BB4F21C90BB6651BC067AF28BC90111.asc \
samplekeys/rsa-rsa-sample-1.asc \
samplekeys/ed25519-cv25519-sample-1.asc \
samplekeys/silent-running.asc
EXTRA_DIST = defs.inc defs.scm pinentry.sh $(TESTS) $(TEST_FILES) \
mkdemodirs signdemokey $(priv_keys) $(sample_keys) \
ChangeLog-2011
CLEANFILES = prepared.stamp x y yy z out err $(data_files) \
plain-1 plain-2 plain-3 trustdb.gpg *.lock .\#lk* \
*.test.log gpg_dearmor gpg.conf gpg-agent.conf S.gpg-agent \
pubring.gpg pubring.gpg~ pubring.kbx pubring.kbx~ \
secring.gpg pubring.pkr secring.skr \
gnupg-test.stop random_seed gpg-agent.log tofu.db \
passphrases
clean-local:
-rm -rf private-keys-v1.d openpgp-revocs.d tofu.d gpgtar.d
# We need to depend on a couple of programs so that the tests don't
# start before all programs are built.
all-local: $(required_pgms)

File Metadata

Mime Type
text/x-diff
Expires
Sun, Feb 23, 7:17 PM (1 h, 1 m)
Storage Engine
local-disk
Storage Format
Raw Data
Storage Handle
28/b6/f0f17304c879064c0e5069fad3a3

Event Timeline