summaryrefslogtreecommitdiffabout
Unidiff
Diffstat (more/less context) (ignore whitespace changes)
-rw-r--r--Makefile.am4
-rwxr-xr-xbootstrap618
-rw-r--r--bootstrap.conf68
-rw-r--r--configure.ac5
-rw-r--r--gnulib.modules4
m---------grecs0
-rw-r--r--src/Makefile.am5
-rw-r--r--src/backup.c165
-rw-r--r--src/builtin.c10
-rw-r--r--src/config.c26
-rw-r--r--src/dictionary.c11
-rw-r--r--src/directive.c8
-rw-r--r--src/diskio.c6
-rw-r--r--src/exec.c2
-rw-r--r--src/gpg.c7
-rw-r--r--src/job.c2
-rw-r--r--src/lock.c12
-rw-r--r--src/mail.c14
-rw-r--r--src/net.c4
-rw-r--r--src/process.c4
-rw-r--r--src/sql.c4
-rw-r--r--src/timer.c5
-rw-r--r--src/triplet.c17
-rw-r--r--src/txtacc.c16
-rw-r--r--src/verify.c4
-rw-r--r--src/wydawca.c8
-rw-r--r--src/wydawca.h20
-rw-r--r--tests/.gitignore1
-rw-r--r--tests/Makefile.am14
-rw-r--r--tests/backup01.at33
-rw-r--r--tests/backup02.at43
-rw-r--r--tests/backup03.at41
-rw-r--r--tests/bkupname.c79
-rw-r--r--tests/testsuite.at4
34 files changed, 485 insertions, 779 deletions
diff --git a/Makefile.am b/Makefile.am
index a182931..29641e2 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -5,27 +5,27 @@
5# it under the terms of the GNU General Public License as published by 5# it under the terms of the GNU General Public License as published by
6# the Free Software Foundation; either version 3, or (at your option) 6# the Free Software Foundation; either version 3, or (at your option)
7# any later version. 7# any later version.
8# 8#
9# Wydawca is distributed in the hope that it will be useful, 9# Wydawca is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of 10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details. 12# GNU General Public License for more details.
13# 13#
14# You should have received a copy of the GNU General Public License 14# You should have received a copy of the GNU General Public License
15# along with wydawca. If not, see <http://www.gnu.org/licenses/>. 15# along with wydawca. If not, see <http://www.gnu.org/licenses/>.
16 16
17ACLOCAL_AMFLAGS = -I m4 -I grecs/am 17ACLOCAL_AMFLAGS = -I grecs/am
18 18
19SUBDIRS=gnu grecs src doc etc tests 19SUBDIRS=grecs src doc etc tests
20 20
21# We never remove files from the configuration directory 21# We never remove files from the configuration directory
22distuninstallcheck_listfiles = \ 22distuninstallcheck_listfiles = \
23 find $(prefix) -type f -not -path '$(sysconfdir)/*' 23 find $(prefix) -type f -not -path '$(sysconfdir)/*'
24 24
25gen_start_date = 2009-01-25 25gen_start_date = 2009-01-25
26 26
27.PHONY: ChangeLog 27.PHONY: ChangeLog
28ChangeLog: 28ChangeLog:
29 $(AM_V_GEN)if test -d .git; then \ 29 $(AM_V_GEN)if test -d .git; then \
30 git log --pretty='format:%ct %an <%ae>%n%n%s%n%n%b%n' | \ 30 git log --pretty='format:%ct %an <%ae>%n%n%s%n%n%b%n' | \
31 awk -f $(top_srcdir)/@GRECS_SUBDIR@/build-aux/git2chg.awk > ChangeLog; \ 31 awk -f $(top_srcdir)/@GRECS_SUBDIR@/build-aux/git2chg.awk > ChangeLog; \
diff --git a/bootstrap b/bootstrap
index 760a095..ae677ac 100755
--- a/bootstrap
+++ b/bootstrap
@@ -1,615 +1,5 @@
1#! /bin/sh 1#! /bin/sh
2 2set -e
3# Bootstrap this package from checked-out sources. 3git submodule init
4 4git submodule update
5# Copyright (C) 2003-2008, 2009 Free Software Foundation, Inc. 5autoreconf -f -i -s
6
7# Dico is free software: you can redistribute it and/or modify
8# it under the terms of the GNU General Public License as published by
9# the Free Software Foundation, either version 3 of the License, or
10# (at your option) any later version.
11
12# Dico is distributed in the hope that it will be useful,
13# but WITHOUT ANY WARRANTY; without even the implied warranty of
14# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15# GNU General Public License for more details.
16
17# You should have received a copy of the GNU General Public License
18# along with Dico. If not, see <http://www.gnu.org/licenses/>.
19
20# Written by Paul Eggert.
21
22nl='
23'
24
25# Ensure file names are sorted consistently across platforms.
26LC_ALL=C
27export LC_ALL
28
29local_gl_dir=gl
30
31# Temporary directory names.
32bt='._bootmp'
33bt_regex=`echo "$bt"| sed 's/\./[.]/g'`
34bt2=${bt}2
35
36usage() {
37 echo >&2 "\
38Usage: $0 [OPTION]...
39Bootstrap this package from the checked-out sources.
40
41Options:
42 --gnulib-srcdir=DIRNAME Specify the local directory where gnulib
43 sources reside. Use this if you already
44 have gnulib sources on your machine, and
45 do not want to waste your bandwidth downloading
46 them again.
47 --copy Copy files instead of creating symbolic links.
48 --force Attempt to bootstrap even if the sources seem
49 not to have been checked out.
50 --skip-po Do not download po files.
51
52If the file bootstrap.conf exists in the current working directory, its
53contents are read as shell variables to configure the bootstrap.
54
55Running without arguments will suffice in most cases.
56"
57}
58
59# Configuration.
60
61# Name of the Makefile.am
62gnulib_mk=gnulib.mk
63
64# List of gnulib modules needed.
65gnulib_modules=
66
67# Any gnulib files needed that are not in modules.
68gnulib_files=
69
70# The command to download all .po files for a specified domain into
71# a specified directory. Fill in the first %s is the domain name, and
72# the second with the destination directory. Use rsync's -L and -r
73# options because the latest/%s directory and the .po files within are
74# all symlinks.
75po_download_command_format=\
76"rsync -Lrtvz 'translationproject.org::tp/latest/%s/' '%s'"
77
78extract_package_name='
79 /^AC_INIT(/{
80 /.*,.*,.*, */{
81 s///
82 s/[][]//g
83 s/)$//
84 p
85 q
86 }
87 s/AC_INIT(\[*//
88 s/]*,.*//
89 s/^GNU //
90 y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/
91 s/[^A-Za-z0-9_]/-/g
92 p
93 }
94'
95package=`sed -n "$extract_package_name" configure.ac` || exit
96gnulib_name=lib$package
97
98build_aux=build-aux
99source_base=lib
100m4_base=m4
101doc_base=doc
102tests_base=tests
103
104# Extra files from gnulib, which override files from other sources.
105gnulib_extra_files="
106 $build_aux/install-sh
107 $build_aux/missing
108 $build_aux/mdate-sh
109 $build_aux/texinfo.tex
110 $build_aux/depcomp
111 $build_aux/config.guess
112 $build_aux/config.sub
113 doc/INSTALL
114"
115
116# Additional gnulib-tool options to use. Use "\newline" to break lines.
117gnulib_tool_option_extras=
118
119# Other locale categories that need message catalogs.
120EXTRA_LOCALE_CATEGORIES=
121
122# Additional xgettext options to use. Use "\\\newline" to break lines.
123XGETTEXT_OPTIONS='\\\
124 --flag=_:1:pass-c-format\\\
125 --flag=N_:1:pass-c-format\\\
126 --flag=error:3:c-format --flag=error_at_line:5:c-format\\\
127'
128
129# Package bug report address for gettext files
130MSGID_BUGS_ADDRESS=bug-$package@gnu.org
131
132# Files we don't want to import.
133excluded_files=
134
135# File that should exist in the top directory of a checked out hierarchy,
136# but not in a distribution tarball.
137checkout_only_file=README-hacking
138
139# Whether to use copies instead of symlinks.
140copy=false
141
142# Set this to '.cvsignore .gitignore' in bootstrap.conf if you want
143# those files to be generated in directories like lib/, m4/, and po/.
144# Or set it to 'auto' to make this script select which to use based
145# on which version control system (if any) is used in the source directory.
146vc_ignore=auto
147
148# Override the default configuration, if necessary.
149test -r bootstrap.conf && . ./bootstrap.conf
150
151if test "$vc_ignore" = auto; then
152 vc_ignore=
153 test -d .git && vc_ignore=.gitignore
154 test -d CVS && vc_ignore="$vc_ignore .cvsignore"
155fi
156
157# Translate configuration into internal form.
158
159# Parse options.
160
161for option
162do
163 case $option in
164 --help)
165 usage
166 exit;;
167 --gnulib-srcdir=*)
168 GNULIB_SRCDIR=`expr "$option" : '--gnulib-srcdir=\(.*\)'`;;
169 --skip-po)
170 SKIP_PO=t;;
171 --force)
172 checkout_only_file=;;
173 --copy)
174 copy=true;;
175 *)
176 echo >&2 "$0: $option: unknown option"
177 exit 1;;
178 esac
179done
180
181if test -n "$checkout_only_file" && test ! -r "$checkout_only_file"; then
182 echo "$0: Bootstrapping from a non-checked-out distribution is risky." >&2
183 exit 1
184fi
185
186# If $STR is not already on a line by itself in $FILE, insert it,
187# sorting the new contents of the file and replacing $FILE with the result.
188insert_sorted_if_absent() {
189 file=$1
190 str=$2
191 test -f $file || touch $file
192 echo "$str" | sort -u - $file | cmp -s - $file \
193 || echo "$str" | sort -u - $file -o $file \
194 || exit 1
195}
196
197# Die if there is no AC_CONFIG_AUX_DIR($build_aux) line in configure.ac.
198found_aux_dir=no
199 grep '^[ ]*AC_CONFIG_AUX_DIR(\['"$build_aux"'\])' configure.ac \
200 >/dev/null && found_aux_dir=yes
201 grep '^[ ]*AC_CONFIG_AUX_DIR('"$build_aux"')' configure.ac \
202 >/dev/null && found_aux_dir=yes
203if test $found_aux_dir = no; then
204 echo "$0: expected line not found in configure.ac. Add the following:" >&2
205 echo " AC_CONFIG_AUX_DIR([$build_aux])" >&2
206 exit 1
207fi
208
209# If $build_aux doesn't exist, create it now, otherwise some bits
210# below will malfunction. If creating it, also mark it as ignored.
211if test ! -d $build_aux; then
212 mkdir $build_aux
213 for dot_ig in x $vc_ignore; do
214 test $dot_ig = x && continue
215 insert_sorted_if_absent $dot_ig $build_aux
216 done
217fi
218
219echo "$0: Bootstrapping from checked-out $package sources..."
220
221cleanup_gnulib() {
222 status=$?
223 rm -fr gnulib
224 exit $status
225}
226
227# Get gnulib files.
228
229case ${GNULIB_SRCDIR--} in
230-)
231 if [ ! -d gnulib ]; then
232 echo "$0: getting gnulib files..."
233
234 trap cleanup_gnulib 1 2 13 15
235
236 git clone --depth 2 git://git.sv.gnu.org/gnulib ||
237 cleanup_gnulib
238
239 trap - 1 2 13 15
240 fi
241 GNULIB_SRCDIR=gnulib
242esac
243
244gnulib_tool=$GNULIB_SRCDIR/gnulib-tool
245<$gnulib_tool || exit
246
247# Get translations.
248
249download_po_files() {
250 subdir=$1
251 domain=$2
252 echo "$0: getting translations into $subdir for $domain..."
253 cmd=`printf "$po_download_command_format" "$domain" "$subdir"`
254 eval "$cmd"
255}
256
257# Download .po files to $po_dir/.reference and copy only the new
258# or modified ones into $po_dir. Also update $po_dir/LINGUAS.
259update_po_files() {
260 # Directory containing primary .po files.
261 # Overwrite them only when we're sure a .po file is new.
262 po_dir=$1
263 domain=$2
264
265 # Download *.po files into this dir.
266 # Usually contains *.s1 checksum files.
267 ref_po_dir="$po_dir/.reference"
268
269 test -d $ref_po_dir || mkdir $ref_po_dir || return
270 download_po_files $ref_po_dir $domain \
271 && ls "$ref_po_dir"/*.po 2>/dev/null |
272 sed 's|.*/||; s|\.po$||' > "$po_dir/LINGUAS"
273
274 langs=`cd $ref_po_dir && echo *.po|sed 's/\.po//g'`
275 test "$langs" = '*' && langs=x
276 for po in `cd $ref_po_dir && echo *.po|sed 's/\.po//g'`; do
277 case $po in x) continue;; esac
278 new_po="$ref_po_dir/$po.po"
279 cksum_file="$ref_po_dir/$po.s1"
280 if ! test -f "$cksum_file" ||
281 ! test -f "$po_dir/$po.po" ||
282 ! sha1sum -c --status "$cksum_file" < "$new_po" > /dev/null; then
283 echo "updated $po_dir/$po.po..."
284 cp "$new_po" "$po_dir/$po.po" && sha1sum < "$new_po" > "$cksum_file"
285 fi
286 done
287}
288
289case $SKIP_PO in
290'')
291 if test -d po; then
292 update_po_files po $package || exit
293 fi
294
295 if test -d runtime-po; then
296 update_po_files runtime-po $package-runtime || exit
297 fi;;
298esac
299
300symlink_to_dir()
301{
302 src=$1/$2
303 dst=${3-$2}
304
305 test -f "$src" && {
306
307 # If the destination directory doesn't exist, create it.
308 # This is required at least for "lib/uniwidth/cjk.h".
309 dst_dir=`dirname "$dst"`
310 if ! test -d "$dst_dir"; then
311 mkdir -p "$dst_dir"
312
313 # If we've just created a directory like lib/uniwidth,
314 # tell version control system(s) it's ignorable.
315 # FIXME: for now, this does only one level
316 parent=`dirname "$dst_dir"`
317 for dot_ig in x $vc_ignore; do
318 test $dot_ig = x && continue
319 ig=$parent/$dot_ig
320 insert_sorted_if_absent $ig `echo "$dst_dir"|sed 's,.*/,,'`
321 done
322 fi
323
324 if $copy; then
325 {
326 test ! -h "$dst" || {
327 echo "$0: rm -f $dst" &&
328 rm -f "$dst"
329 }
330 } &&
331 test -f "$dst" &&
332 cmp -s "$src" "$dst" || {
333 echo "$0: cp -fp $src $dst" &&
334 cp -fp "$src" "$dst"
335 }
336 else
337 test -h "$dst" &&
338 src_ls=`ls -diL "$src" 2>/dev/null` && set $src_ls && src_i=$1 &&
339 dst_ls=`ls -diL "$dst" 2>/dev/null` && set $dst_ls && dst_i=$1 &&
340 test "$src_i" = "$dst_i" || {
341 dot_dots=
342 case $src in
343 /*) ;;
344 *)
345 case /$dst/ in
346 *//* | */../* | */./* | /*/*/*/*/*/)
347 echo >&2 "$0: invalid symlink calculation: $src -> $dst"
348 exit 1;;
349 /*/*/*/*/)dot_dots=../../../;;
350 /*/*/*/)dot_dots=../../;;
351 /*/*/)dot_dots=../;;
352 esac;;
353 esac
354
355 echo "$0: ln -fs $dot_dots$src $dst" &&
356 ln -fs "$dot_dots$src" "$dst"
357 }
358 fi
359 }
360}
361
362cp_mark_as_generated()
363{
364 cp_src=$1
365 cp_dst=$2
366
367 if cmp -s "$cp_src" "$GNULIB_SRCDIR/$cp_dst"; then
368 symlink_to_dir "$GNULIB_SRCDIR" "$cp_dst"
369 elif cmp -s "$cp_src" "$local_gl_dir/$cp_dst"; then
370 symlink_to_dir $local_gl_dir "$cp_dst"
371 else
372 case $cp_dst in
373 *.[ch]) c1='/* '; c2=' */';;
374 *.texi) c1='@c '; c2= ;;
375 *.m4|*/Make*|Make*) c1='# ' ; c2= ;;
376 *) c1= ; c2= ;;
377 esac
378
379 # If the destination directory doesn't exist, create it.
380 # This is required at least for "lib/uniwidth/cjk.h".
381 dst_dir=`dirname "$cp_dst"`
382 test -d "$dst_dir" || mkdir -p "$dst_dir"
383
384 if test -z "$c1"; then
385 cmp -s "$cp_src" "$cp_dst" || {
386 echo "$0: cp -f $cp_src $cp_dst" &&
387 rm -f "$cp_dst" &&
388 sed "s!$bt_regex/!!g" "$cp_src" > "$cp_dst"
389 }
390 else
391 # Copy the file first to get proper permissions if it
392 # doesn't already exist. Then overwrite the copy.
393 cp "$cp_src" "$cp_dst-t" &&
394 (
395 echo "$c1-*- buffer-read-only: t -*- vi: set ro:$c2" &&
396 echo "${c1}DO NOT EDIT! GENERATED AUTOMATICALLY!$c2" &&
397 sed "s!$bt_regex/!!g" "$cp_src"
398 ) > $cp_dst-t &&
399 if cmp -s "$cp_dst-t" "$cp_dst"; then
400 rm -f "$cp_dst-t"
401 else
402 echo "$0: cp $cp_src $cp_dst # with edits" &&
403 mv -f "$cp_dst-t" "$cp_dst"
404 fi
405 fi
406 fi
407}
408
409version_controlled_file() {
410 dir=$1
411 file=$2
412 found=no
413 if test -d CVS; then
414 grep -F "/$file/" $dir/CVS/Entries 2>/dev/null |
415 grep '^/[^/]*/[0-9]' > /dev/null && found=yes
416 elif test -d .git; then
417 git rm -n "$dir/$file" > /dev/null 2>&1 && found=yes
418 elif test -d .svn; then
419 svn log -r HEAD "$dir/$file" > /dev/null 2>&1 && found=yes
420 else
421 echo "$0: no version control for $dir/$file?" >&2
422 fi
423 test $found = yes
424}
425
426slurp() {
427 for dir in . `(cd $1 && find * -type d -print)`; do
428 copied=
429 sep=
430 for file in `ls -a $1/$dir`; do
431 case $file in
432 .|..) continue;;
433 .*) continue;; # FIXME: should all file names starting with "." be ignored?
434 esac
435 test -d $1/$dir/$file && continue
436 for excluded_file in $excluded_files; do
437 test "$dir/$file" = "$excluded_file" && continue 2
438 done
439 if test $file = Makefile.am; then
440 copied=$copied${sep}$gnulib_mk; sep=$nl
441 remove_intl='/^[^#].*\/intl/s/^/#/;'"s!$bt_regex/!!g"
442 sed "$remove_intl" $1/$dir/$file | cmp -s - $dir/$gnulib_mk || {
443 echo "$0: Copying $1/$dir/$file to $dir/$gnulib_mk ..." &&
444 rm -f $dir/$gnulib_mk &&
445 sed "$remove_intl" $1/$dir/$file >$dir/$gnulib_mk
446 }
447 elif { test "${2+set}" = set && test -r $2/$dir/$file; } ||
448 version_controlled_file $dir $file; then
449 echo "$0: $dir/$file overrides $1/$dir/$file"
450 else
451 copied=$copied$sep$file; sep=$nl
452 if test $file = gettext.m4; then
453 echo "$0: patching m4/gettext.m4 to remove need for intl/* ..."
454 rm -f $dir/$file
455 sed '
456 /^AC_DEFUN(\[AM_INTL_SUBDIR],/,/^]/c\
457 AC_DEFUN([AM_INTL_SUBDIR], [
458 /^AC_DEFUN(\[gt_INTL_SUBDIR_CORE],/,/^]/c\
459 AC_DEFUN([gt_INTL_SUBDIR_CORE], [])
460 $a\
461 AC_DEFUN([gl_LOCK_EARLY], [])
462 ' $1/$dir/$file >$dir/$file
463 else
464 cp_mark_as_generated $1/$dir/$file $dir/$file
465 fi
466 fi || exit
467 done
468
469 for dot_ig in x $vc_ignore; do
470 test $dot_ig = x && continue
471 ig=$dir/$dot_ig
472 if test -n "$copied"; then
473 insert_sorted_if_absent $ig "$copied"
474 # If an ignored file name ends with .in.h, then also add
475 # the name with just ".h". Many gnulib headers are generated,
476 # e.g., stdint.in.h -> stdint.h, dirent.in.h ->..., etc.
477 # Likewise for .gperf -> .h, .y -> .c, and .sin -> .sed
478 f=`echo "$copied"|sed 's/\.in\.h$/.h/;s/\.sin$/.sed/;s/\.y$/.c/;s/\.gperf$/.h/'`
479 insert_sorted_if_absent $ig "$f"
480
481 # For files like sys_stat.in.h and sys_time.in.h, record as
482 # ignorable the directory we might eventually create: sys/.
483 f=`echo "$copied"|sed 's/sys_.*\.in\.h$/sys/'`
484 insert_sorted_if_absent $ig "$f"
485 fi
486 done
487 done
488}
489
490
491# Create boot temporary directories to import from gnulib and gettext.
492rm -fr $bt $bt2 &&
493mkdir $bt $bt2 || exit
494
495# Import from gnulib.
496
497gnulib_tool_options="\
498 --import\
499 --no-changelog\
500 --aux-dir $bt/$build_aux\
501 --doc-base $bt/$doc_base\
502 --lib $gnulib_name\
503 --m4-base $bt/$m4_base/\
504 --source-base $bt/$source_base/\
505 --tests-base $bt/$tests_base\
506 --local-dir $local_gl_dir\
507 $gnulib_tool_option_extras\
508"
509echo "$0: $gnulib_tool $gnulib_tool_options --import ..."
510$gnulib_tool $gnulib_tool_options --import $gnulib_modules &&
511slurp $bt || exit
512
513for file in $gnulib_files; do
514 symlink_to_dir "$GNULIB_SRCDIR" $file || exit
515done
516
517
518# Import from gettext.
519with_gettext=yes
520 grep '^[ ]*AM_GNU_GETTEXT_VERSION(' configure.ac >/dev/null || \
521 with_gettext=no
522
523if test $with_gettext = yes; then
524 echo "$0: (cd $bt2; autopoint) ..."
525 cp configure.ac $bt2 &&
526 (cd $bt2 && autopoint && rm configure.ac) &&
527 slurp $bt2 $bt || exit
528
529 rm -fr $bt $bt2 || exit
530fi
531
532# Coreutils is unusual in that it generates some of its test-related
533# Makefile.am files. That must be done before invoking automake.
534mam_template=tests/Makefile.am.in
535if test -f $mam_template; then
536 PERL=perl
537 for tool in cut head join pr sort tac tail test tr uniq wc; do
538 m=tests/$tool/Makefile.am
539 t=${m}t
540 rm -f $m $t
541 sed -n '1,/^##test-files-begin/p' $mam_template > $t
542 echo "x = $tool" >> $t
543 srcdir=tests/$tool
544 $PERL -I$srcdir -w -- tests/mk-script $srcdir --list >> $t
545 sed -n '/^##test-files-end/,$p' $mam_template >> $t
546 chmod -w $t
547 mv $t $m
548 done
549fi
550
551# Remove any dangling symlink matching "*.m4" or "*.[ch]" in some
552# gnulib-populated directories. Such .m4 files would cause aclocal to fail.
553# The following requires GNU find 4.2.3 or newer. Considering the usual
554# portability constraints of this script, that may seem a very demanding
555# requirement, but it should be ok. Ignore any failure, which is fine,
556# since this is only a convenience to help developers avoid the relatively
557# unusual case in which a symlinked-to .m4 file is git-removed from gnulib
558# between successive runs of this script.
559find "$m4_base" "$source_base" \
560 -depth \( -name '*.m4' -o -name '*.[ch]' \) \
561 -type l -xtype l -delete > /dev/null 2>&1
562
563# Reconfigure, getting other files.
564
565echo "$0: autoreconf --force --install --symlink ..."
566autoreconf --force --install --symlink
567
568# FIXME: A kludge to avoid unnecessary data in the distribution.
569test -d libltdl/config && rm -rf libltdl/config
570test -d libltdl/m4 && rm -rf libltdl/m4
571
572# Get some extra files from gnulib, overriding existing files.
573for file in $gnulib_extra_files; do
574 case $file in
575 */INSTALL) dst=INSTALL;;
576 build-aux/*) dst=$build_aux/`expr "$file" : 'build-aux/\(.*\)'`;;
577 *) dst=$file;;
578 esac
579 symlink_to_dir "$GNULIB_SRCDIR" $file $dst || exit
580done
581
582if test $with_gettext = yes; then
583 # Create gettext configuration.
584 echo "$0: Creating po/Makevars from po/Makevars.template ..."
585 rm -f po/Makevars
586 sed '
587 /^EXTRA_LOCALE_CATEGORIES *=/s/=.*/= '"$EXTRA_LOCALE_CATEGORIES"'/
588 /^MSGID_BUGS_ADDRESS *=/s/=.*/= '"$MSGID_BUGS_ADDRESS"'/
589 /^XGETTEXT_OPTIONS *=/{
590 s/$/ \\/
591 a\
592 '"$XGETTEXT_OPTIONS"' $${end_of_xgettext_options+}
593 }
594 ' po/Makevars.template >po/Makevars
595
596 if test -d runtime-po; then
597 # Similarly for runtime-po/Makevars, but not quite the same.
598 rm -f runtime-po/Makevars
599 sed '
600 /^DOMAIN *=.*/s/=.*/= '"$package"'-runtime/
601 /^subdir *=.*/s/=.*/= runtime-po/
602 /^MSGID_BUGS_ADDRESS *=/s/=.*/= bug-'"$package"'@gnu.org/
603 /^XGETTEXT_OPTIONS *=/{
604 s/$/ \\/
605 a\
606 '"$XGETTEXT_OPTIONS_RUNTIME"' $${end_of_xgettext_options+}
607 }
608 ' <po/Makevars.template >runtime-po/Makevars
609
610 # Copy identical files from po to runtime-po.
611 (cd po && cp -p Makefile.in.in *-quot *.header *.sed *.sin ../runtime-po)
612 fi
613fi
614
615echo "$0: done. Now you can run './configure'."
diff --git a/bootstrap.conf b/bootstrap.conf
deleted file mode 100644
index 8464d0d..0000000
--- a/bootstrap.conf
+++ b/dev/null
@@ -1,68 +0,0 @@
1# Bootstrap configuration.
2
3# Copyright (C) 2007, 2009, 2010 Sergey Poznyakoff
4#
5# Wydawca is free software; you can redistribute it and/or modify
6# it under the terms of the GNU General Public License as published by
7# the Free Software Foundation; either version 3, or (at your option)
8# any later version.
9#
10# Wydawca is distributed in the hope that it will be useful,
11# but WITHOUT ANY WARRANTY; without even the implied warranty of
12# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13# GNU General Public License for more details.
14#
15# You should have received a copy of the GNU General Public License
16# along with wydawca. If not, see <http://www.gnu.org/licenses/>.
17
18source_base=gnu
19gnulib_name=libgnu
20gnulib_mk=Makefile.am
21
22test -d $source_base || mkdir -p $source_base
23
24git submodule init || exit $?
25git submodule update || exit $?
26
27# We don't need these modules, even though gnulib-tool mistakenly
28# includes them because of gettext dependencies.
29avoided_gnulib_modules='
30 --avoid=lock
31 --avoid=size_max
32'
33
34# gnulib modules used by this package.
35gnulib_modules="`grep -h '^[^#]' gnulib.modules | sort | uniq`"
36
37# Additional xgettext options to use. Use "\\\newline" to break lines.
38XGETTEXT_OPTIONS=$XGETTEXT_OPTIONS'\\\
39 --flag=_:1:pass-c-format\\\
40 --flag=N_:1:pass-c-format\\\
41 --flag=error:3:c-format --flag=error_at_line:5:c-format\\\
42 --flag=asnprintf:3:c-format --flag=vasnprintf:3:c-format\\\
43 --flag=gconf_warning:3:c-format\\\
44 --flag=gconf_error:3:c-format\\\
45'
46
47# Gettext supplies these files, but we don't need them since
48# we don't have an intl subdirectory.
49excluded_files='
50 m4/glibc2.m4
51 m4/intdiv0.m4
52 m4/lcmessage.m4
53 m4/lock.m4
54 m4/uintmax_t.m4
55 m4/ulonglong.m4
56 m4/visibility.m4
57'
58
59# Read local configuration file
60if [ -r .bootstrap ]; then
61 echo "$0: Reading configuration file .bootstrap"
62 eval set -- "`sed 's/#.*$//;/^$/d' .bootstrap | tr '\n' ' '` $*"
63fi
64
65test -f Changelog || cat > ChangeLog <<EOT
66This file is a placeholder. It will be replaced with the actual ChangeLog
67by make dist. Run make ChangeLog if you wish to create it earlier.
68EOT
diff --git a/configure.ac b/configure.ac
index 7002fb9..344c3b8 100644
--- a/configure.ac
+++ b/configure.ac
@@ -17,46 +17,42 @@
17AC_PREREQ(2.63) 17AC_PREREQ(2.63)
18AC_INIT([wydawca], 2.1.90, [bug-wydawca@gnu.org.ua]) 18AC_INIT([wydawca], 2.1.90, [bug-wydawca@gnu.org.ua])
19AC_CONFIG_SRCDIR([src/wydawca.c]) 19AC_CONFIG_SRCDIR([src/wydawca.c])
20AC_CONFIG_AUX_DIR([build-aux]) 20AC_CONFIG_AUX_DIR([build-aux])
21AC_CONFIG_HEADER([config.h]) 21AC_CONFIG_HEADER([config.h])
22AM_INIT_AUTOMAKE([1.11 gnits tar-ustar dist-bzip2 dist-xz std-options silent-rules]) 22AM_INIT_AUTOMAKE([1.11 gnits tar-ustar dist-bzip2 dist-xz std-options silent-rules])
23 23
24# Enable silent rules by default: 24# Enable silent rules by default:
25AM_SILENT_RULES([yes]) 25AM_SILENT_RULES([yes])
26 26
27# Checks for programs. 27# Checks for programs.
28AC_PROG_CC 28AC_PROG_CC
29 gl_EARLY
30AC_PROG_LEX
31AC_PROG_YACC
32AC_PROG_RANLIB 29AC_PROG_RANLIB
33 30
34# Checks for libraries. 31# Checks for libraries.
35 32
36# Checks for header files. 33# Checks for header files.
37AC_HEADER_STDC 34AC_HEADER_STDC
38AC_HEADER_SYS_WAIT 35AC_HEADER_SYS_WAIT
39AC_CHECK_HEADERS([stdlib.h string.h sys/file.h unistd.h]) 36AC_CHECK_HEADERS([stdlib.h string.h sys/file.h unistd.h])
40 37
41# Checks for typedefs, structures, and compiler characteristics. 38# Checks for typedefs, structures, and compiler characteristics.
42AC_C_CONST 39AC_C_CONST
43 AC_TYPE_SIGNAL 40 AC_TYPE_SIGNAL
44AC_TYPE_UID_T 41AC_TYPE_UID_T
45AC_TYPE_PID_T 42AC_TYPE_PID_T
46AC_TYPE_SIZE_T 43AC_TYPE_SIZE_T
47AC_HEADER_STDBOOL 44AC_HEADER_STDBOOL
48 45
49# Checks for library functions. 46# Checks for library functions.
50gl_INIT
51AC_FUNC_FORK 47AC_FUNC_FORK
52AC_FUNC_MALLOC 48AC_FUNC_MALLOC
53AC_FUNC_MEMCMP 49AC_FUNC_MEMCMP
54AC_FUNC_STAT 50AC_FUNC_STAT
55AC_FUNC_VPRINTF 51AC_FUNC_VPRINTF
56AC_CHECK_FUNCS([fchdir memset strchr strdup strerror strrchr setegid setregid setresgid setresuid seteuid setreuid vsyslog sysconf getdtablesize]) 52AC_CHECK_FUNCS([fchdir memset strchr strdup strerror strrchr setegid setregid setresgid setresuid seteuid setreuid vsyslog sysconf getdtablesize])
57 53
58 # ********************** 54 # **********************
59# Mailutils 55# Mailutils
60 # ********************** 56 # **********************
61 57
62AM_GNU_MAILUTILS(2.0, [mailer], [:]) 58AM_GNU_MAILUTILS(2.0, [mailer], [:])
@@ -126,17 +122,16 @@ AH_BOTTOM([
126# Initialize the test suite. 122# Initialize the test suite.
127AC_CONFIG_TESTDIR(tests) 123AC_CONFIG_TESTDIR(tests)
128AC_CONFIG_FILES([tests/Makefile tests/atlocal tests/etc/Makefile]) 124AC_CONFIG_FILES([tests/Makefile tests/atlocal tests/etc/Makefile])
129AM_MISSING_PROG([AUTOM4TE], [autom4te]) 125AM_MISSING_PROG([AUTOM4TE], [autom4te])
130 126
131AC_PATH_PROG(GPG, gpg, '') 127AC_PATH_PROG(GPG, gpg, '')
132if test -n "$GPG"; then 128if test -n "$GPG"; then
133 AC_SUBST(WYDAWCA_GPGFILES, '$(GPGFILES)') 129 AC_SUBST(WYDAWCA_GPGFILES, '$(GPGFILES)')
134fi 130fi
135 131
136AC_CONFIG_FILES([Makefile 132AC_CONFIG_FILES([Makefile
137 doc/Makefile 133 doc/Makefile
138 gnu/Makefile
139 src/Makefile 134 src/Makefile
140 etc/Makefile]) 135 etc/Makefile])
141 136
142AC_OUTPUT 137AC_OUTPUT
diff --git a/gnulib.modules b/gnulib.modules
deleted file mode 100644
index dd5124a..0000000
--- a/gnulib.modules
+++ b/dev/null
@@ -1,4 +0,0 @@
1xalloc
2getline
3mkdtemp
4backupfile
diff --git a/grecs b/grecs
Subproject f8ca129aaf4876dfa9778c34ed5bd8a669ca22e Subproject 4c1056b45580fcb687cac656834f42dd9fba4ae
diff --git a/src/Makefile.am b/src/Makefile.am
index 8139849..3b524ba 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -7,24 +7,25 @@
7# any later version. 7# any later version.
8# 8#
9# Wydawca is distributed in the hope that it will be useful, 9# Wydawca is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of 10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details. 12# GNU General Public License for more details.
13# 13#
14# You should have received a copy of the GNU General Public License 14# You should have received a copy of the GNU General Public License
15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>. 15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>.
16 16
17sbin_PROGRAMS=wydawca 17sbin_PROGRAMS=wydawca
18wydawca_SOURCES=\ 18wydawca_SOURCES=\
19 backup.c\
19 builtin.c\ 20 builtin.c\
20 builtin.h\ 21 builtin.h\
21 cmdline.h\ 22 cmdline.h\
22 config.c\ 23 config.c\
23 dictionary.c\ 24 dictionary.c\
24 directive.c\ 25 directive.c\
25 diskio.c\ 26 diskio.c\
26 exec.c\ 27 exec.c\
27 gpg.c\ 28 gpg.c\
28 interval.c\ 29 interval.c\
29 job.c\ 30 job.c\
30 lock.c\ 31 lock.c\
@@ -51,21 +52,21 @@ wydawca_SOURCES=\
51 52
52BUILT_SOURCES=cmdline.h 53BUILT_SOURCES=cmdline.h
53EXTRA_DIST=cmdline.opt pp-setup update-2.0.awk 54EXTRA_DIST=cmdline.opt pp-setup update-2.0.awk
54 55
55SUFFIXES=.opt .c .h 56SUFFIXES=.opt .c .h
56 57
57.opt.h: 58.opt.h:
58 $(AM_V_GEN)m4 -s $(top_srcdir)/@GRECS_SUBDIR@/build-aux/getopt.m4 $< > $@ 59 $(AM_V_GEN)m4 -s $(top_srcdir)/@GRECS_SUBDIR@/build-aux/getopt.m4 $< > $@
59 60
60incdir=$(pkgdatadir)/$(VERSION)/include 61incdir=$(pkgdatadir)/$(VERSION)/include
61inc_DATA = $(PP_SETUP_FILE) 62inc_DATA = $(PP_SETUP_FILE)
62 63
63LDADD=../grecs/src/libgrecs.a ../gnu/libgnu.a @SQLLIB@ @GPGMELIB@ @MAILUTILS_LIBS@ 64LDADD=../grecs/src/libgrecs.a @SQLLIB@ @GPGMELIB@ @MAILUTILS_LIBS@
64INCLUDES = -I$(top_srcdir)/grecs/src/ -I$(top_srcdir)/gnu -I../gnu @MAILUTILS_INCLUDES@ 65INCLUDES = -I$(top_srcdir)/grecs/src/ @MAILUTILS_INCLUDES@
65AM_CPPFLAGS= \ 66AM_CPPFLAGS= \
66 -DSYSCONFDIR=\"$(sysconfdir)\"\ 67 -DSYSCONFDIR=\"$(sysconfdir)\"\
67 -DLOCALSTATEDIR=\"$(localstatedir)\"\ 68 -DLOCALSTATEDIR=\"$(localstatedir)\"\
68 -DDEFAULT_VERSION_INCLUDE_DIR=\"$(incdir)\"\ 69 -DDEFAULT_VERSION_INCLUDE_DIR=\"$(incdir)\"\
69 -DDEFAULT_INCLUDE_DIR=\"$(pkgdatadir)/include\"\ 70 -DDEFAULT_INCLUDE_DIR=\"$(pkgdatadir)/include\"\
70 -DDEFAULT_PREPROCESSOR="$(DEFAULT_PREPROCESSOR)" 71 -DDEFAULT_PREPROCESSOR="$(DEFAULT_PREPROCESSOR)"
71 72
diff --git a/src/backup.c b/src/backup.c
new file mode 100644
index 0000000..312375d
--- a/dev/null
+++ b/src/backup.c
@@ -0,0 +1,165 @@
1/* wydawca - automatic release submission daemon
2 Copyright (C) 2011 Sergey Poznyakoff
3
4 Wydawca is free software; you can redistribute it and/or modify it
5 under the terms of the GNU General Public License as published by the
6 Free Software Foundation; either version 3 of the License, or (at your
7 option) any later version.
8
9 Wydawca is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License along
15 with wydawca. If not, see <http://www.gnu.org/licenses/>. */
16
17#include "wydawca.h"
18
19char const *simple_backup_suffix = "~";
20
21static const char *
22split_filename (char const *file, char **pdir)
23{
24 const char *p = strrchr (file, '/');
25
26 if (!p)
27 {
28 *pdir = grecs_strdup (".");
29 p = file;
30 }
31 else
32 {
33 size_t len = p - file;
34 char *dir = grecs_malloc (len + 1);
35 memcpy (dir, file, len);
36 dir[len] = 0;
37 *pdir = dir;
38 p++;
39 }
40 return p;
41}
42
43#define MINSUFSIZE 8
44#define ISDIGIT(c) ('0' <= (c) && (c) <= '9')
45
46static char *
47get_backup_suffix (char const *file, enum backup_type type)
48{
49 char *dirname;
50 const char *basename;
51 size_t baselen;
52 DIR *dir;
53 struct dirent *ent;
54 char *lastsuf = NULL;
55 size_t lastsuflen = 0;
56 size_t lastsufsize = 0;
57 int carry;
58 char *newsuf;
59 char *q;
60
61 if (type == simple_backups)
62 return grecs_strdup (simple_backup_suffix);
63
64 basename = split_filename (file, &dirname);
65 baselen = strlen (basename);
66 dir = opendir (dirname);
67 if (!dir)
68 {
69 int ec = errno;
70 free (dirname);
71 errno = ec;
72 return NULL;
73 }
74
75 while ((ent = readdir (dir)))
76 {
77 size_t len = strlen (ent->d_name);
78 const char *p;
79 size_t suflen;
80
81 if (len < baselen + 4 || memcmp (ent->d_name, basename, baselen))
82 continue;
83 p = ent->d_name + baselen;
84 suflen = len - baselen;
85 if (p[0] == '.' && p[1] == '~' && p[suflen-1] == '~' &&
86 (suflen > lastsuflen
87 || (suflen == lastsuflen &&
88 memcmp (p, lastsuf, lastsuflen) > 0)))
89 {
90 carry = 1;
91 for (q = (char*) p + suflen - 2; q > p + 1 && ISDIGIT (*q); q--)
92 if (*q != '9')
93 carry = 0;
94 q++;
95 if (!ISDIGIT (*q))
96 continue;
97
98 if (suflen > lastsufsize)
99 {
100 lastsufsize = suflen;
101 if (!lastsuf)
102 {
103 if (lastsufsize < MINSUFSIZE)
104 lastsufsize = MINSUFSIZE;
105 lastsuf = grecs_malloc (lastsufsize);
106 }
107 else
108 lastsuf = grecs_realloc (lastsuf, lastsufsize);
109 }
110 memcpy (lastsuf, p, suflen);
111 lastsuflen = suflen;
112 }
113 }
114 closedir (dir);
115 free (dirname);
116
117 if (lastsuf)
118 {
119 size_t newsuflen;
120
121 newsuflen = lastsuflen + carry;
122 newsuf = grecs_malloc (newsuflen + 1);
123 newsuf[0] = '.';
124 newsuf[1] = '~';
125 newsuf[2] = '0';
126 memcpy (newsuf + 2 + carry, lastsuf + 2, lastsuflen - 3);
127 newsuf[newsuflen-1] = '~';
128 newsuf[newsuflen] = 0;
129
130 for (q = newsuf + newsuflen - 2; *q == '9'; q--)
131 *q = '0';
132 ++*q;
133 free (lastsuf);
134 }
135 else if (type == numbered_existing_backups)
136 newsuf = grecs_strdup (simple_backup_suffix);
137 else
138 newsuf = grecs_strdup (".~1~");
139 return newsuf;
140}
141
142char *
143find_backup_file_name (char const *file, enum backup_type type)
144{
145 size_t flen;
146 char *suffix;
147 char *newname;
148
149 if (type == no_backups)
150 {
151 errno = 0;
152 return NULL;
153 }
154
155 suffix = get_backup_suffix (file, type);
156 if (!suffix)
157 return NULL;
158 flen = strlen (file);
159 newname = grecs_malloc (flen + strlen (suffix) + 1);
160 memcpy (newname, file, flen);
161 strcpy (newname + flen, suffix);
162 free (suffix);
163 /* FIXME: Check newname length */
164 return newname;
165}
diff --git a/src/builtin.c b/src/builtin.c
index 9d1063c..8a07eab 100644
--- a/src/builtin.c
+++ b/src/builtin.c
@@ -7,26 +7,28 @@
7 option) any later version. 7 option) any later version.
8 8
9 Wydawca is distributed in the hope that it will be useful, 9 Wydawca is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of 10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details. 12 GNU General Public License for more details.
13 13
14 You should have received a copy of the GNU General Public License along 14 You should have received a copy of the GNU General Public License along
15 with wydawca. If not, see <http://www.gnu.org/licenses/>. */ 15 with wydawca. If not, see <http://www.gnu.org/licenses/>. */
16 16
17#include "wydawca.h" 17#include "wydawca.h"
18#include "builtin.h" 18#include "builtin.h"
19#include "fnmatch.h" 19
20#include "regex.h" 20#ifndef FNM_CASEFOLD
21# define FNM_CASEFOLD 0
22#endif
21 23
22int 24int
23builtin_init (struct dictionary *dict) 25builtin_init (struct dictionary *dict)
24{ 26{
25 return 0; 27 return 0;
26} 28}
27 29
28int 30int
29builtin_done (struct dictionary *dict) 31builtin_done (struct dictionary *dict)
30{ 32{
31 return 0; 33 return 0;
32} 34}
@@ -211,27 +213,27 @@ builtin_lookup (struct dictionary *dict, void *handle, const char *req)
211 213
212 if (count == 0) 214 if (count == 0)
213 { 215 {
214 txtacc_free (acc); 216 txtacc_free (acc);
215 bds = NULL; 217 bds = NULL;
216 rc = 1; 218 rc = 1;
217 } 219 }
218 else 220 else
219 { 221 {
220 size_t i; 222 size_t i;
221 char *p; 223 char *p;
222 224
223 bds = xmalloc (sizeof (*bds)); 225 bds = grecs_malloc (sizeof (*bds));
224 count *= ncol; 226 count *= ncol;
225 bds->wp = xcalloc (count, sizeof (bds->wp[0])); 227 bds->wp = grecs_calloc (count, sizeof (bds->wp[0]));
226 bds->acc = acc; 228 bds->acc = acc;
227 p = txtacc_finish (acc, 0); 229 p = txtacc_finish (acc, 0);
228 230
229 for (i = 0; i < count; i++) 231 for (i = 0; i < count; i++)
230 { 232 {
231 bds->wp[i] = p; 233 bds->wp[i] = p;
232 p += strlen (p) + 1; 234 p += strlen (p) + 1;
233 } 235 }
234 rc = 0; 236 rc = 0;
235 } 237 }
236 238
237 dict->storage = bds; 239 dict->storage = bds;
diff --git a/src/config.c b/src/config.c
index df9816e..8250749 100644
--- a/src/config.c
+++ b/src/config.c
@@ -137,25 +137,25 @@ safe_file_name (char *file_name)
137 { 137 {
138 file_name[0] = '/'; 138 file_name[0] = '/';
139 file_name[1] = 0; 139 file_name[1] = 0;
140 } 140 }
141 141
142 return file_name; 142 return file_name;
143} 143}
144 144
145/* Same as safe_file_name, but returns an allocated copy. */ 145/* Same as safe_file_name, but returns an allocated copy. */
146char * 146char *
147safe_file_name_alloc (const char *file_name) 147safe_file_name_alloc (const char *file_name)
148{ 148{
149 char *s = xstrdup (file_name); 149 char *s = grecs_strdup (file_name);
150 char *ns = safe_file_name (s); 150 char *ns = safe_file_name (s);
151 if (!ns) 151 if (!ns)
152 free (s); 152 free (s);
153 return ns; 153 return ns;
154} 154}
155 155
156 156
157static struct keyword event_tab[] = { 157static struct keyword event_tab[] = {
158 { "success", ev_success }, 158 { "success", ev_success },
159 { "bad-ownership", ev_bad_ownership }, 159 { "bad-ownership", ev_bad_ownership },
160 { "bad-directive-signature", ev_bad_directive_signature }, 160 { "bad-directive-signature", ev_bad_directive_signature },
161 { "bad-detached-signature", ev_bad_detached_signature }, 161 { "bad-detached-signature", ev_bad_detached_signature },
@@ -540,70 +540,70 @@ cb_sql_host (enum grecs_callback_command cmd,
540 char *p; 540 char *p;
541 541
542 if (assert_string_arg (locus, cmd, value)) 542 if (assert_string_arg (locus, cmd, value))
543 return 1; 543 return 1;
544 544
545 p = strchr (value->v.string, ':'); 545 p = strchr (value->v.string, ':');
546 if (p) 546 if (p)
547 { 547 {
548 /* FIXME: Modifies constant string */ 548 /* FIXME: Modifies constant string */
549 *p++ = 0; 549 *p++ = 0;
550 if (p[0] == '/') 550 if (p[0] == '/')
551 { 551 {
552 pconn->socket = xstrdup (p); 552 pconn->socket = grecs_strdup (p);
553 pconn->host = xstrdup ("localhost"); 553 pconn->host = grecs_strdup ("localhost");
554 } 554 }
555 else 555 else
556 { 556 {
557 char *end; 557 char *end;
558 unsigned long n = strtoul (p, &end, 10); 558 unsigned long n = strtoul (p, &end, 10);
559 if (*end) 559 if (*end)
560 { 560 {
561 grecs_error (locus, 0, _("invalid port number (near %s)"), end); 561 grecs_error (locus, 0, _("invalid port number (near %s)"), end);
562 return 0; 562 return 0;
563 } 563 }
564 if (n == 0 || n > USHRT_MAX) 564 if (n == 0 || n > USHRT_MAX)
565 { 565 {
566 grecs_error (locus, 0, _("port number out of range 1..%d"), 566 grecs_error (locus, 0, _("port number out of range 1..%d"),
567 USHRT_MAX); 567 USHRT_MAX);
568 return 0; 568 return 0;
569 } 569 }
570 pconn->port = n; 570 pconn->port = n;
571 /* Save host name */ 571 /* Save host name */
572 pconn->host = xstrdup (value->v.string); 572 pconn->host = grecs_strdup (value->v.string);
573 } 573 }
574 } 574 }
575 else 575 else
576 pconn->host = xstrdup (value->v.string); 576 pconn->host = grecs_strdup (value->v.string);
577 return 0; 577 return 0;
578} 578}
579 579
580static int 580static int
581cb_sql (enum grecs_callback_command cmd, 581cb_sql (enum grecs_callback_command cmd,
582 grecs_locus_t *locus, 582 grecs_locus_t *locus,
583 void *varptr, 583 void *varptr,
584 grecs_value_t *value, 584 grecs_value_t *value,
585 void *cb_data) 585 void *cb_data)
586{ 586{
587 struct sqlconn *pconn; 587 struct sqlconn *pconn;
588 void **pdata = cb_data; 588 void **pdata = cb_data;
589 589
590 switch (cmd) { 590 switch (cmd) {
591 case grecs_callback_section_begin: 591 case grecs_callback_section_begin:
592 if (!value || value->type != GRECS_TYPE_STRING) 592 if (!value || value->type != GRECS_TYPE_STRING)
593 { 593 {
594 grecs_error(locus, 0, _("tag must be a string")); 594 grecs_error(locus, 0, _("tag must be a string"));
595 return 0; 595 return 0;
596 } 596 }
597 pconn = xzalloc (sizeof (*pconn)); 597 pconn = grecs_zalloc (sizeof (*pconn));
598 pconn->ident = strdup (value->v.string); 598 pconn->ident = strdup (value->v.string);
599 *pdata = pconn; 599 *pdata = pconn;
600 break; 600 break;
601 601
602 case grecs_callback_section_end: 602 case grecs_callback_section_end:
603 pconn = *pdata; 603 pconn = *pdata;
604 sql_register_conn (pconn); 604 sql_register_conn (pconn);
605 free (pconn); 605 free (pconn);
606 *pdata = NULL; 606 *pdata = NULL;
607 break; 607 break;
608 608
609 case grecs_callback_set_value: 609 case grecs_callback_set_value:
@@ -887,25 +887,25 @@ static struct grecs_keyword notify_event_kw[] = {
887static int 887static int
888cb_notify_event (enum grecs_callback_command cmd, 888cb_notify_event (enum grecs_callback_command cmd,
889 grecs_locus_t *locus, 889 grecs_locus_t *locus,
890 void *varptr, 890 void *varptr,
891 grecs_value_t *value, 891 grecs_value_t *value,
892 void *cb_data) 892 void *cb_data)
893{ 893{
894 struct notification *ntf; 894 struct notification *ntf;
895 void **pdata = cb_data; 895 void **pdata = cb_data;
896 896
897 switch (cmd) { 897 switch (cmd) {
898 case grecs_callback_section_begin: 898 case grecs_callback_section_begin:
899 ntf = xzalloc (sizeof (*ntf)); 899 ntf = grecs_zalloc (sizeof (*ntf));
900 *pdata = ntf; 900 *pdata = ntf;
901 break; 901 break;
902 902
903 case grecs_callback_section_end: 903 case grecs_callback_section_end:
904 ntf = *pdata; 904 ntf = *pdata;
905 if (!ntf->msg) 905 if (!ntf->msg)
906 grecs_error (locus, 0, _("missing message definition")); 906 grecs_error (locus, 0, _("missing message definition"));
907 else 907 else
908 { 908 {
909 struct notification **p = (struct notification **) varptr; 909 struct notification **p = (struct notification **) varptr;
910 ntf->next = *p; 910 ntf->next = *p;
911 *p = ntf; 911 *p = ntf;
@@ -975,34 +975,34 @@ cb_dictionary_params (enum grecs_callback_command cmd,
975 size = grecs_list_size (value->v.list); 975 size = grecs_list_size (value->v.list);
976 if (size == 0) 976 if (size == 0)
977 { 977 {
978 meth->parmc = 0; 978 meth->parmc = 0;
979 meth->parmv = NULL; 979 meth->parmv = NULL;
980 } 980 }
981 else 981 else
982 { 982 {
983 int i; 983 int i;
984 struct grecs_list_entry *ep; 984 struct grecs_list_entry *ep;
985 985
986 meth->parmc = size; 986 meth->parmc = size;
987 meth->parmv = xcalloc (size + 1, sizeof (meth->parmv[0])); 987 meth->parmv = grecs_calloc (size + 1, sizeof (meth->parmv[0]));
988 988
989 for (i = 0, ep = value->v.list->head; ep; ep = ep->next, i++) 989 for (i = 0, ep = value->v.list->head; ep; ep = ep->next, i++)
990 { 990 {
991 const grecs_value_t *vp = ep->data; 991 const grecs_value_t *vp = ep->data;
992 992
993 if (assert_string_arg (locus, cmd, vp)) 993 if (assert_string_arg (locus, cmd, vp))
994 break; 994 break;
995 995
996 meth->parmv[i] = xstrdup (vp->v.string); 996 meth->parmv[i] = grecs_strdup (vp->v.string);
997 } 997 }
998 meth->parmv[i] = NULL; 998 meth->parmv[i] = NULL;
999 } 999 }
1000 return 0; 1000 return 0;
1001} 1001}
1002 1002
1003static struct grecs_keyword dictionary_kw[] = { 1003static struct grecs_keyword dictionary_kw[] = {
1004 { "type", N_("type"), N_("Dictionary type"), 1004 { "type", N_("type"), N_("Dictionary type"),
1005 grecs_type_string, NULL, offsetof(struct dictionary, type), 1005 grecs_type_string, NULL, offsetof(struct dictionary, type),
1006 cb_dictionary_type }, 1006 cb_dictionary_type },
1007 { "query", N_("string"), N_("Query template"), 1007 { "query", N_("string"), N_("Query template"),
1008 grecs_type_string, NULL, offsetof(struct dictionary, query) }, 1008 grecs_type_string, NULL, offsetof(struct dictionary, query) },
@@ -1150,26 +1150,26 @@ cb_spool (enum grecs_callback_command cmd,
1150 struct spool *spool; 1150 struct spool *spool;
1151 void **pdata = cb_data; 1151 void **pdata = cb_data;
1152 int rc, ec, i; 1152 int rc, ec, i;
1153 1153
1154 switch (cmd) 1154 switch (cmd)
1155 { 1155 {
1156 case grecs_callback_section_begin: 1156 case grecs_callback_section_begin:
1157 if (!value || value->type != GRECS_TYPE_STRING) 1157 if (!value || value->type != GRECS_TYPE_STRING)
1158 { 1158 {
1159 grecs_error (locus, 0, _("tag must be a string")); 1159 grecs_error (locus, 0, _("tag must be a string"));
1160 return 1; 1160 return 1;
1161 } 1161 }
1162 spool = xzalloc (sizeof (*spool)); 1162 spool = grecs_zalloc (sizeof (*spool));
1163 spool->tag = xstrdup (value->v.string); 1163 spool->tag = grecs_strdup (value->v.string);
1164 spool->file_sweep_time = file_sweep_time; 1164 spool->file_sweep_time = file_sweep_time;
1165 for (i = 0; i < NITEMS (spool->dictionary); i++) 1165 for (i = 0; i < NITEMS (spool->dictionary); i++)
1166 spool->dictionary[i] = default_dictionary[i]; 1166 spool->dictionary[i] = default_dictionary[i];
1167 spool->archive = default_archive_descr; 1167 spool->archive = default_archive_descr;
1168 *pdata = spool; 1168 *pdata = spool;
1169 break; 1169 break;
1170 1170
1171 case grecs_callback_section_end: 1171 case grecs_callback_section_end:
1172 rc = 0; 1172 rc = 0;
1173 spool = *pdata; 1173 spool = *pdata;
1174 if (!spool->source_dir) 1174 if (!spool->source_dir)
1175 { 1175 {
@@ -1268,26 +1268,26 @@ cb_supp_groups (enum grecs_callback_command cmd,
1268 grecs_error (locus, 0, _("expected list value")); 1268 grecs_error (locus, 0, _("expected list value"));
1269 return 1; 1269 return 1;
1270 } 1270 }
1271 1271
1272 wydawca_supp_groupc = grecs_list_size (value->v.list); 1272 wydawca_supp_groupc = grecs_list_size (value->v.list);
1273 if (wydawca_supp_groupc == 0) 1273 if (wydawca_supp_groupc == 0)
1274 wydawca_supp_groups = NULL; 1274 wydawca_supp_groups = NULL;
1275 else 1275 else
1276 { 1276 {
1277 int i; 1277 int i;
1278 struct grecs_list_entry *ep; 1278 struct grecs_list_entry *ep;
1279 1279
1280 wydawca_supp_groups = xcalloc (wydawca_supp_groupc, 1280 wydawca_supp_groups = grecs_calloc (wydawca_supp_groupc,
1281 sizeof (wydawca_supp_groups[0])); 1281 sizeof (wydawca_supp_groups[0]));
1282 1282
1283 for (i = 0, ep = value->v.list->head; ep; ep = ep->next, i++) 1283 for (i = 0, ep = value->v.list->head; ep; ep = ep->next, i++)
1284 { 1284 {
1285 const grecs_value_t *vp = ep->data; 1285 const grecs_value_t *vp = ep->data;
1286 struct group *grp; 1286 struct group *grp;
1287 1287
1288 if (assert_string_arg (locus, cmd, vp)) 1288 if (assert_string_arg (locus, cmd, vp))
1289 break; 1289 break;
1290 grp = getgrnam (vp->v.string); 1290 grp = getgrnam (vp->v.string);
1291 if (!grp) 1291 if (!grp)
1292 { 1292 {
1293 grecs_error (locus, 0, _("no such group: %s"), value->v.string); 1293 grecs_error (locus, 0, _("no such group: %s"), value->v.string);
diff --git a/src/dictionary.c b/src/dictionary.c
index b7baf05..2b995d4 100644
--- a/src/dictionary.c
+++ b/src/dictionary.c
@@ -39,26 +39,25 @@ static struct dictionary_descr dictionary_tab[] = {
39 { "sql", sql_init_dictionary, sql_done_dictionary, sql_free_result, 39 { "sql", sql_init_dictionary, sql_done_dictionary, sql_free_result,
40 sql_open, NULL, sql_get_dictionary, sql_lookup_dictionary, sql_quote }, 40 sql_open, NULL, sql_get_dictionary, sql_lookup_dictionary, sql_quote },
41 { "builtin", builtin_init, builtin_done, builtin_free_result, 41 { "builtin", builtin_init, builtin_done, builtin_free_result,
42 builtin_open, NULL, 42 builtin_open, NULL,
43 builtin_get, 43 builtin_get,
44 builtin_lookup }, 44 builtin_lookup },
45 { "external", NULL, NULL, NULL, NULL, NULL, NULL, NULL } 45 { "external", NULL, NULL, NULL, NULL, NULL, NULL, NULL }
46}; 46};
47 47
48struct dictionary * 48struct dictionary *
49dictionary_new (enum dictionary_id id, enum dictionary_type type) 49dictionary_new (enum dictionary_id id, enum dictionary_type type)
50{ 50{
51 struct dictionary *mp = xmalloc (sizeof mp[0]); 51 struct dictionary *mp = grecs_zalloc (sizeof mp[0]);
52 memset (mp, 0, sizeof mp[0]);
53 mp->id = id; 52 mp->id = id;
54 mp->type = type; 53 mp->type = type;
55 return mp; 54 return mp;
56} 55}
57 56
58int 57int
59dictionary_init (struct dictionary *dict) 58dictionary_init (struct dictionary *dict)
60{ 59{
61 struct dictionary_descr *mp = dictionary_tab + dict->type; 60 struct dictionary_descr *mp = dictionary_tab + dict->type;
62 int rc = 0; 61 int rc = 0;
63 62
64 if (dict->init_passed++) 63 if (dict->init_passed++)
@@ -83,24 +82,26 @@ dictionary_open (struct dictionary *dict)
83{ 82{
84 struct dictionary_descr *mp = dictionary_tab + dict->type; 83 struct dictionary_descr *mp = dictionary_tab + dict->type;
85 84
86 if (!mp->open) 85 if (!mp->open)
87 return NULL; 86 return NULL;
88 return mp->open (dict); 87 return mp->open (dict);
89} 88}
90 89
91int 90int
92dictionary_close (struct dictionary *dict, void *handle) 91dictionary_close (struct dictionary *dict, void *handle)
93{ 92{
94 struct dictionary_descr *mp = dictionary_tab + dict->type; 93 struct dictionary_descr *mp = dictionary_tab + dict->type;
94 if (mp->free)
95 mp->free (dict, handle);
95 if (!mp->close) 96 if (!mp->close)
96 return 0; 97 return 0;
97 return mp->close (dict, handle); 98 return mp->close (dict, handle);
98} 99}
99 100
100int 101int
101dictionary_done (struct dictionary *dict) 102dictionary_done (struct dictionary *dict)
102{ 103{
103 struct dictionary_descr *mp = dictionary_tab + dict->type; 104 struct dictionary_descr *mp = dictionary_tab + dict->type;
104 int rc = 0; 105 int rc = 0;
105 106
106 if (dict->init_passed == 0) 107 if (dict->init_passed == 0)
@@ -177,52 +178,52 @@ dictionary_result (struct dictionary *dict, void *handle,
177 if (nrow >= dict->nrow || ncol >= dict->ncol 178 if (nrow >= dict->nrow || ncol >= dict->ncol
178 || mp->get (dict, handle, nrow, ncol)) 179 || mp->get (dict, handle, nrow, ncol))
179 return NULL; 180 return NULL;
180 return dict->result; 181 return dict->result;
181} 182}
182 183
183void 184void
184dictionary_copy_result (struct dictionary *dict, const char *res, size_t size) 185dictionary_copy_result (struct dictionary *dict, const char *res, size_t size)
185{ 186{
186 if (dict->result_size < size + 1) 187 if (dict->result_size < size + 1)
187 { 188 {
188 dict->result_size = size + 1; 189 dict->result_size = size + 1;
189 dict->result = x2realloc (dict->result, &dict->result_size); 190 dict->result = grecs_realloc (dict->result, dict->result_size);
190 } 191 }
191 memcpy (dict->result, res, size); 192 memcpy (dict->result, res, size);
192 dict->result[size] = 0; 193 dict->result[size] = 0;
193} 194}
194 195
195/* Quote non-printable characters in INPUT. Point *OUTPUT to the malloc'ed 196/* Quote non-printable characters in INPUT. Point *OUTPUT to the malloc'ed
196 quoted string. Return its length. */ 197 quoted string. Return its length. */
197int 198int
198dictionary_quote_string (struct dictionary *dict, void *handle, 199dictionary_quote_string (struct dictionary *dict, void *handle,
199 const char *input, 200 const char *input,
200 char **poutput, size_t *psize) 201 char **poutput, size_t *psize)
201{ 202{
202 struct dictionary_descr *mp = dictionary_tab + dict->type; 203 struct dictionary_descr *mp = dictionary_tab + dict->type;
203 size_t size; 204 size_t size;
204 int quote; 205 int quote;
205 char *output; 206 char *output;
206 207
207 if (!input) 208 if (!input)
208 { 209 {
209 *poutput = xmalloc (1); 210 *poutput = grecs_malloc (1);
210 (*poutput)[0] = 0; 211 (*poutput)[0] = 0;
211 *psize = 1; 212 *psize = 1;
212 return 0; 213 return 0;
213 } 214 }
214 215
215 if (mp->quote) 216 if (mp->quote)
216 return mp->quote (dict, handle, input, poutput, psize); 217 return mp->quote (dict, handle, input, poutput, psize);
217 218
218 size = wordsplit_c_quoted_length (input, 0, &quote); 219 size = wordsplit_c_quoted_length (input, 0, &quote);
219 output = xmalloc (size + 1); 220 output = grecs_malloc (size + 1);
220 wordsplit_c_quote_copy (output, input, 0); 221 wordsplit_c_quote_copy (output, input, 0);
221 output[size] = 0; 222 output[size] = 0;
222 223
223 *poutput = output; 224 *poutput = output;
224 if (psize) 225 if (psize)
225 *psize = size; 226 *psize = size;
226 return 0; 227 return 0;
227} 228}
228 229
diff --git a/src/directive.c b/src/directive.c
index 08a14df..fadaedf 100644
--- a/src/directive.c
+++ b/src/directive.c
@@ -25,25 +25,25 @@ directive_parse (struct file_triplet *trp)
25 size_t dcount, i, j; 25 size_t dcount, i, j;
26 char *p; 26 char *p;
27 27
28 if (debug_level > 2) 28 if (debug_level > 2)
29 logmsg (LOG_DEBUG, _("%s: parsing directive blurb: %s"), 29 logmsg (LOG_DEBUG, _("%s: parsing directive blurb: %s"),
30 trp->file[file_directive].name, trp->blurb); 30 trp->file[file_directive].name, trp->blurb);
31 31
32 dcount = 0; 32 dcount = 0;
33 for (p = trp->blurb; *p; p++) 33 for (p = trp->blurb; *p; p++)
34 if (*p == '\n') 34 if (*p == '\n')
35 dcount++; 35 dcount++;
36 36
37 trp->directive = xcalloc (dcount + 1, sizeof trp->directive[0]); 37 trp->directive = grecs_calloc (dcount + 1, sizeof trp->directive[0]);
38 p = trp->blurb; 38 p = trp->blurb;
39 for (i = j = 0; i < dcount; i++) 39 for (i = j = 0; i < dcount; i++)
40 { 40 {
41 trp->directive[j] = p; 41 trp->directive[j] = p;
42 p = strchr (p, '\n'); 42 p = strchr (p, '\n');
43 if (p) 43 if (p)
44 *p++ = 0; 44 *p++ = 0;
45 if (trim (trp->directive[j]) == 0) /* ignore empty lines */ 45 if (trim (trp->directive[j]) == 0) /* ignore empty lines */
46 continue; 46 continue;
47 if (strchr (trp->directive[j], ':') == NULL) 47 if (strchr (trp->directive[j], ':') == NULL)
48 { 48 {
49 logmsg (LOG_ERR, _("%s: invalid line: %s"), 49 logmsg (LOG_ERR, _("%s: invalid line: %s"),
@@ -102,25 +102,25 @@ _directive_seq_get (int n, struct file_triplet *trp,
102{ 102{
103 char *p; 103 char *p;
104 size_t len; 104 size_t len;
105 105
106 if (trp->directive[n] == NULL) 106 if (trp->directive[n] == NULL)
107 return 0; 107 return 0;
108 108
109 p = strchr (trp->directive[n], ':'); 109 p = strchr (trp->directive[n], ':');
110 len = p - trp->directive[n]; 110 len = p - trp->directive[n];
111 if (len + 1 > trp->tmpsize) 111 if (len + 1 > trp->tmpsize)
112 { 112 {
113 trp->tmpsize = len + 1; 113 trp->tmpsize = len + 1;
114 trp->tmp = x2realloc (trp->tmp, &trp->tmpsize); 114 trp->tmp = grecs_realloc (trp->tmp, trp->tmpsize);
115 } 115 }
116 memcpy (trp->tmp, trp->directive[n], len); 116 memcpy (trp->tmp, trp->directive[n], len);
117 trp->tmp[len] = 0; 117 trp->tmp[len] = 0;
118 *pkey = trp->tmp; 118 *pkey = trp->tmp;
119 for (p++; *p && isspace (*p); p++) 119 for (p++; *p && isspace (*p); p++)
120 ; 120 ;
121 if (pval) 121 if (pval)
122 *pval = p; 122 *pval = p;
123 return ++n; 123 return ++n;
124} 124}
125 125
126/* Get the first directive from TRP. Point *PKEY to its keyword and 126/* Get the first directive from TRP. Point *PKEY to its keyword and
@@ -371,25 +371,25 @@ stderr_redirector (const char *tag)
371 } 371 }
372 372
373 if (pid == 0) 373 if (pid == 0)
374 { 374 {
375 FILE *fp; 375 FILE *fp;
376 size_t size = 0; 376 size_t size = 0;
377 char *buf = NULL; 377 char *buf = NULL;
378 378
379 close (p[1]); 379 close (p[1]);
380 fp = fdopen (p[0], "r"); 380 fp = fdopen (p[0], "r");
381 if (!fp) 381 if (!fp)
382 _exit (127); 382 _exit (127);
383 while (getline (&buf, &size, fp) >= 0) 383 while (grecs_getline (&buf, &size, fp) >= 0)
384 { 384 {
385 trim_crlf (buf); 385 trim_crlf (buf);
386 logmsg (LOG_NOTICE, "%s: %s", tag, buf); 386 logmsg (LOG_NOTICE, "%s: %s", tag, buf);
387 } 387 }
388 _exit (0); 388 _exit (0);
389 } 389 }
390 390
391 close (p[0]); 391 close (p[0]);
392 return p[1]; 392 return p[1];
393} 393}
394 394
395static int 395static int
@@ -484,25 +484,25 @@ run_check_script (const char *script, struct file_triplet *trp,
484 execv ("/bin/sh", argv); 484 execv ("/bin/sh", argv);
485 _exit (127); 485 _exit (127);
486 } 486 }
487 487
488 /* Master */ 488 /* Master */
489 free (script_file); 489 free (script_file);
490 close (p[1]); 490 close (p[1]);
491 fp = fdopen (p[0], "r"); 491 fp = fdopen (p[0], "r");
492 buf = NULL; 492 buf = NULL;
493 size = total = 0; 493 size = total = 0;
494 if (debug_level > 2) 494 if (debug_level > 2)
495 logmsg (LOG_DEBUG, _("reading script output...")); 495 logmsg (LOG_DEBUG, _("reading script output..."));
496 while (getline (&buf, &size, fp) > 0) 496 while (grecs_getline (&buf, &size, fp) > 0)
497 { 497 {
498 size_t len = strlen (buf); 498 size_t len = strlen (buf);
499 if (debug_level > 2) 499 if (debug_level > 2)
500 logmsg (LOG_DEBUG, _("read: %s"), buf); 500 logmsg (LOG_DEBUG, _("read: %s"), buf);
501 txtacc_grow (trp->acc, buf, len); 501 txtacc_grow (trp->acc, buf, len);
502 total += size; 502 total += size;
503 } 503 }
504 txtacc_1grow (trp->acc, 0); 504 txtacc_1grow (trp->acc, 0);
505 if (debug_level > 2) 505 if (debug_level > 2)
506 logmsg (LOG_DEBUG, _("bytes read: %lu"), (unsigned long)total); 506 logmsg (LOG_DEBUG, _("bytes read: %lu"), (unsigned long)total);
507 507
508 fclose (fp); 508 fclose (fp);
diff --git a/src/diskio.c b/src/diskio.c
index 9addd9b..b175a45 100644
--- a/src/diskio.c
+++ b/src/diskio.c
@@ -37,25 +37,25 @@ sub_dir_p (const char *arg, const char *dir)
37 slash. */ 37 slash. */
38char * 38char *
39concat_dir (const char *base, const char *name, size_t *pbaselen) 39concat_dir (const char *base, const char *name, size_t *pbaselen)
40{ 40{
41 size_t len = strlen (base); 41 size_t len = strlen (base);
42 size_t size; 42 size_t size;
43 char *dir; 43 char *dir;
44 44
45 while (len > 0 && base[len-1] == '/') 45 while (len > 0 && base[len-1] == '/')
46 len--; 46 len--;
47 47
48 size = len + 1 + strlen (name); 48 size = len + 1 + strlen (name);
49 dir = xmalloc (size + 1); 49 dir = grecs_malloc (size + 1);
50 memcpy (dir, base, len); 50 memcpy (dir, base, len);
51 dir[len++] = '/'; 51 dir[len++] = '/';
52 strcpy (dir + len, name); 52 strcpy (dir + len, name);
53 53
54 if (pbaselen) 54 if (pbaselen)
55 *pbaselen = len; 55 *pbaselen = len;
56 return dir; 56 return dir;
57} 57}
58 58
59/* Create the directory DIR, eventually creating all intermediate directories 59/* Create the directory DIR, eventually creating all intermediate directories
60 starting from DIR + BASELEN. */ 60 starting from DIR + BASELEN. */
61int 61int
@@ -162,25 +162,25 @@ copy_file (const char *file, const char *dst_file)
162 file, strerror (errno)); 162 file, strerror (errno));
163 close (in_fd); 163 close (in_fd);
164 return 1; 164 return 1;
165 } 165 }
166 166
167 buf = NULL; 167 buf = NULL;
168 fsize = st.st_size; 168 fsize = st.st_size;
169 169
170 for (bufsize = fsize; bufsize > 0 && (buf = malloc (bufsize)) == NULL; 170 for (bufsize = fsize; bufsize > 0 && (buf = malloc (bufsize)) == NULL;
171 bufsize /= 2) 171 bufsize /= 2)
172 ; 172 ;
173 if (bufsize == 0) 173 if (bufsize == 0)
174 xalloc_die (); 174 grecs_alloc_die ();
175 175
176 rc = 0; 176 rc = 0;
177 while (fsize > 0) 177 while (fsize > 0)
178 { 178 {
179 size_t rest; 179 size_t rest;
180 size_t rdbytes; 180 size_t rdbytes;
181 181
182 rest = fsize > bufsize ? bufsize : fsize; 182 rest = fsize > bufsize ? bufsize : fsize;
183 rdbytes = read (in_fd, buf, rest); 183 rdbytes = read (in_fd, buf, rest);
184 if (rdbytes == -1) 184 if (rdbytes == -1)
185 { 185 {
186 logmsg (LOG_ERR, _("unexpected error reading %s: %s"), 186 logmsg (LOG_ERR, _("unexpected error reading %s: %s"),
@@ -483,25 +483,25 @@ archive_single_file (struct file_triplet *trp, const char *file_name,
483 free (dst_dir); 483 free (dst_dir);
484 return rc; 484 return rc;
485} 485}
486 486
487static char * 487static char *
488make_signame (const char *file_name) 488make_signame (const char *file_name)
489{ 489{
490 size_t len; 490 size_t len;
491 491
492 if (((len = strlen (file_name)) > SUF_SIG_LEN 492 if (((len = strlen (file_name)) > SUF_SIG_LEN
493 && memcmp (file_name + len - SUF_SIG_LEN, SUF_SIG, SUF_SIG_LEN))) 493 && memcmp (file_name + len - SUF_SIG_LEN, SUF_SIG, SUF_SIG_LEN)))
494 { 494 {
495 char *signame = xmalloc (len + SUF_SIG_LEN + 1); 495 char *signame = grecs_malloc (len + SUF_SIG_LEN + 1);
496 strcpy (signame, file_name); 496 strcpy (signame, file_name);
497 return strcat (signame, SUF_SIG); 497 return strcat (signame, SUF_SIG);
498 } 498 }
499 return NULL; 499 return NULL;
500} 500}
501 501
502/* Archive the file FILE_NAME, located in DPAIR->dest_dir, and remove the 502/* Archive the file FILE_NAME, located in DPAIR->dest_dir, and remove the
503 file. Get user IDs from the triplet TRP. Unless FILE_NAME ends in 503 file. Get user IDs from the triplet TRP. Unless FILE_NAME ends in
504 ".sig", do the same with FILE_NAME.sig, if such a file exists. 504 ".sig", do the same with FILE_NAME.sig, if such a file exists.
505 Do nothing if dry_run_mode is set. 505 Do nothing if dry_run_mode is set.
506*/ 506*/
507int 507int
diff --git a/src/exec.c b/src/exec.c
index ed7ee1e..7ebf152 100644
--- a/src/exec.c
+++ b/src/exec.c
@@ -66,25 +66,25 @@ start_prog (int argc, const char **argv, pid_t *ppid)
66 return fp; 66 return fp;
67} 67}
68 68
69/* Log everything read from FP as the output from the program PROG, using 69/* Log everything read from FP as the output from the program PROG, using
70 syslog priority PRIO. */ 70 syslog priority PRIO. */
71void 71void
72log_output (int prio, const char *prog, FILE *fp) 72log_output (int prio, const char *prog, FILE *fp)
73{ 73{
74 size_t size = 0; 74 size_t size = 0;
75 char *buf = NULL; 75 char *buf = NULL;
76 76
77 logmsg (prio, _("%s output follows:"), prog); 77 logmsg (prio, _("%s output follows:"), prog);
78 while (getline (&buf, &size, fp) > 0) 78 while (grecs_getline (&buf, &size, fp) > 0)
79 logmsg (prio, "%s", buf); 79 logmsg (prio, "%s", buf);
80 logmsg (prio, _("end of %s output"), prog); 80 logmsg (prio, _("end of %s output"), prog);
81 free (buf); 81 free (buf);
82} 82}
83 83
84/* Execute ARGC/ARGV. Return the exit code in RETCODE. */ 84/* Execute ARGC/ARGV. Return the exit code in RETCODE. */
85enum exec_result 85enum exec_result
86wydawca_exec (int argc, const char **argv, int *retcode) 86wydawca_exec (int argc, const char **argv, int *retcode)
87{ 87{
88 FILE *fp; 88 FILE *fp;
89 pid_t pid, npid; 89 pid_t pid, npid;
90 int status; 90 int status;
diff --git a/src/gpg.c b/src/gpg.c
index 474d94b..d4f9b71 100644
--- a/src/gpg.c
+++ b/src/gpg.c
@@ -123,25 +123,25 @@ remove_homedir ()
123 logmsg (LOG_DEBUG, _("removing GNUPG home directory: %s"), temp_homedir); 123 logmsg (LOG_DEBUG, _("removing GNUPG home directory: %s"), temp_homedir);
124 if (rmdir_r (temp_homedir)) 124 if (rmdir_r (temp_homedir))
125 logmsg (LOG_CRIT, _("failed to remove GPG directory %s"), temp_homedir); 125 logmsg (LOG_CRIT, _("failed to remove GPG directory %s"), temp_homedir);
126} 126}
127 127
128/* Create a temporary GPG home directory */ 128/* Create a temporary GPG home directory */
129static int 129static int
130create_gpg_homedir () 130create_gpg_homedir ()
131{ 131{
132 if (temp_homedir) 132 if (temp_homedir)
133 return 0; 133 return 0;
134 134
135 temp_homedir = xstrdup ("/tmp/wydawca-XXXXXX"); 135 temp_homedir = grecs_strdup ("/tmp/wydawca-XXXXXX");
136 if (!mkdtemp (temp_homedir)) 136 if (!mkdtemp (temp_homedir))
137 { 137 {
138 logmsg (LOG_CRIT, _("cannot create GPG home directory (%s): %s"), 138 logmsg (LOG_CRIT, _("cannot create GPG home directory (%s): %s"),
139 temp_homedir, strerror (errno)); 139 temp_homedir, strerror (errno));
140 return 1; 140 return 1;
141 } 141 }
142 atexit (remove_homedir); 142 atexit (remove_homedir);
143 if (debug_level > 1) 143 if (debug_level > 1)
144 logmsg (LOG_DEBUG, _("GNUPG home directory: %s"), temp_homedir); 144 logmsg (LOG_DEBUG, _("GNUPG home directory: %s"), temp_homedir);
145 setenv ("GNUPGHOME", temp_homedir, 1); 145 setenv ("GNUPGHOME", temp_homedir, 1);
146 return 0; 146 return 0;
147} 147}
@@ -228,25 +228,25 @@ verify_directive_signature (struct file_triplet *trp)
228 for (uptr = trp->uploader_list; uptr; uptr = uptr->next) 228 for (uptr = trp->uploader_list; uptr; uptr = uptr->next)
229 { 229 {
230 gpgme_import_result_t res; 230 gpgme_import_result_t res;
231 gpgme_import_status_t pstat; 231 gpgme_import_status_t pstat;
232 232
233 fail_if_err (gpgme_data_new_from_mem (&key_data, 233 fail_if_err (gpgme_data_new_from_mem (&key_data,
234 uptr->gpg_key, 234 uptr->gpg_key,
235 strlen (uptr->gpg_key), 235 strlen (uptr->gpg_key),
236 0)); 236 0));
237 fail_if_err (gpgme_op_import (ctx, key_data)); 237 fail_if_err (gpgme_op_import (ctx, key_data));
238 res = gpgme_op_import_result (ctx); 238 res = gpgme_op_import_result (ctx);
239 pstat = res->imports; 239 pstat = res->imports;
240 uptr->fpr = xstrdup (pstat->fpr); 240 uptr->fpr = grecs_strdup (pstat->fpr);
241 if (debug_level > 2) 241 if (debug_level > 2)
242 logmsg (LOG_DEBUG, _("imported key: user = %s, fingerprint = %s"), 242 logmsg (LOG_DEBUG, _("imported key: user = %s, fingerprint = %s"),
243 uptr->name, uptr->fpr); 243 uptr->name, uptr->fpr);
244 } 244 }
245 245
246 fail_if_err (gpgme_data_new_from_file (&directive_data, 246 fail_if_err (gpgme_data_new_from_file (&directive_data,
247 trp->file[file_directive].name, 1)); 247 trp->file[file_directive].name, 1));
248 gpgme_data_new (&plain); 248 gpgme_data_new (&plain);
249 ec = gpgme_op_verify (ctx, directive_data, NULL, plain); 249 ec = gpgme_op_verify (ctx, directive_data, NULL, plain);
250 if (ec == GPG_ERR_NO_ERROR) 250 if (ec == GPG_ERR_NO_ERROR)
251 { 251 {
252 gpgme_verify_result_t result; 252 gpgme_verify_result_t result;
@@ -262,25 +262,26 @@ verify_directive_signature (struct file_triplet *trp)
262 rc = 0; 262 rc = 0;
263 } 263 }
264 else 264 else
265 { 265 {
266 rc = 1; 266 rc = 1;
267 UPDATE_STATS (STAT_BAD_SIGNATURE); 267 UPDATE_STATS (STAT_BAD_SIGNATURE);
268 logmsg (LOG_ERR, _("%s: directive verification failed: %s"), 268 logmsg (LOG_ERR, _("%s: directive verification failed: %s"),
269 trp->name, gpgme_strerror (ec)); 269 trp->name, gpgme_strerror (ec));
270 } 270 }
271 271
272 gpgme_data_release (directive_data); 272 gpgme_data_release (directive_data);
273 gpgme_data_release (key_data); 273 gpgme_data_release (key_data);
274 274 gpgme_release (ctx);
275
275 return rc; 276 return rc;
276} 277}
277 278
278/* Verify the detached signature of TRP. 279/* Verify the detached signature of TRP.
279 NOTE: It is assumed that the public key is already registered (by 280 NOTE: It is assumed that the public key is already registered (by
280 a previous call to verify_directive_signature). */ 281 a previous call to verify_directive_signature). */
281int 282int
282verify_detached_signature (struct file_triplet *trp) 283verify_detached_signature (struct file_triplet *trp)
283{ 284{
284 gpgme_engine_info_t info; 285 gpgme_engine_info_t info;
285 const char *argv[5]; 286 const char *argv[5];
286 const struct spool *spool; 287 const struct spool *spool;
diff --git a/src/job.c b/src/job.c
index 7e3fdf5..764e463 100644
--- a/src/job.c
+++ b/src/job.c
@@ -196,25 +196,25 @@ schedule_job (const struct spool *spool, uid_t uid)
196 struct job *job; 196 struct job *job;
197 197
198 if (!spool) 198 if (!spool)
199 spool = &fake_spool; 199 spool = &fake_spool;
200 200
201 if (debug_level) 201 if (debug_level)
202 logmsg (LOG_DEBUG, _("scheduling job: %s, %lu"), 202 logmsg (LOG_DEBUG, _("scheduling job: %s, %lu"),
203 spool->tag, (unsigned long)uid); 203 spool->tag, (unsigned long)uid);
204 204
205 job = job_locate (spool, uid); 205 job = job_locate (spool, uid);
206 if (!job) 206 if (!job)
207 { 207 {
208 job = xzalloc (sizeof (*job)); 208 job = grecs_zalloc (sizeof (*job));
209 job->spool = spool; 209 job->spool = spool;
210 job->uid = uid; 210 job->uid = uid;
211 job->pid = -1; 211 job->pid = -1;
212 time (&job->timestamp); 212 time (&job->timestamp);
213 job_insert (job, NULL); 213 job_insert (job, NULL);
214 } 214 }
215 215
216 job->state |= STATE_QUEUED; 216 job->state |= STATE_QUEUED;
217 job_start (job); 217 job_start (job);
218} 218}
219 219
220static void 220static void
diff --git a/src/lock.c b/src/lock.c
index 32367de..dece75d 100644
--- a/src/lock.c
+++ b/src/lock.c
@@ -178,33 +178,33 @@ host_name ()
178 static char *hostbuf = NULL; 178 static char *hostbuf = NULL;
179 size_t size = 0; 179 size_t size = 0;
180 int rc; 180 int rc;
181 181
182 if (hostbuf) 182 if (hostbuf)
183 return hostbuf; 183 return hostbuf;
184 184
185 do 185 do
186 { 186 {
187 if (!hostbuf) 187 if (!hostbuf)
188 { 188 {
189 size = 256; 189 size = 256;
190 hostbuf = xmalloc (size); 190 hostbuf = grecs_malloc (size);
191 } 191 }
192 else 192 else
193 { 193 {
194 size_t ns = size * 2; 194 size_t ns = size * 2;
195 if (size < ns) 195 if (size < ns)
196 xalloc_die (); 196 grecs_alloc_die ();
197 size = ns; 197 size = ns;
198 hostbuf = xrealloc (hostbuf, size); 198 hostbuf = grecs_realloc (hostbuf, size);
199 } 199 }
200 } 200 }
201 while ((rc = gethostname (hostbuf, size )) == -1 && 201 while ((rc = gethostname (hostbuf, size )) == -1 &&
202 (errno == EINVAL 202 (errno == EINVAL
203#ifdef ENAMETOOLONG 203#ifdef ENAMETOOLONG
204 || errno == ENAMETOOLONG 204 || errno == ENAMETOOLONG
205#endif 205#endif
206 )); 206 ));
207 if (rc) 207 if (rc)
208 { 208 {
209 logmsg (LOG_ERR, _("cannot get hostname: %s"), strerror (rc)); 209 logmsg (LOG_ERR, _("cannot get hostname: %s"), strerror (rc));
210 exit (EX_SOFTWARE); 210 exit (EX_SOFTWARE);
@@ -252,45 +252,45 @@ wydawca_lock (const char *lockname)
252} 252}
253 253
254void 254void
255wydawca_unlock (const char *lockfile) 255wydawca_unlock (const char *lockfile)
256{ 256{
257 if (enable_locking) 257 if (enable_locking)
258 unlink (lockfile); 258 unlink (lockfile);
259} 259}
260 260
261static char * 261static char *
262fix_tagname (const char *tag) 262fix_tagname (const char *tag)
263{ 263{
264 char *tagname = xstrdup (tag); 264 char *tagname = grecs_strdup (tag);
265 char *p; 265 char *p;
266 266
267 for (p = tagname; *p; p++) 267 for (p = tagname; *p; p++)
268 if (!isalnum (*p) && *p != '_' && *p != '-') 268 if (!isalnum (*p) && *p != '_' && *p != '-')
269 *p = '_'; 269 *p = '_';
270 return tagname; 270 return tagname;
271} 271}
272 272
273char * 273char *
274wydawca_lockname (const char *tag) 274wydawca_lockname (const char *tag)
275{ 275{
276 char *lockname = NULL; 276 char *lockname = NULL;
277 size_t size = 0; 277 size_t size = 0;
278 char *tagname = fix_tagname (tag); 278 char *tagname = fix_tagname (tag);
279 grecs_asprintf (&lockname, &size, "%s/LCK.%s", lockdir, tagname); 279 grecs_asprintf (&lockname, &size, "%s/LCK.%s", lockdir, tagname);
280 if (!lockname) 280 if (!lockname)
281 xalloc_die (); 281 grecs_alloc_die ();
282 free (tagname); 282 free (tagname);
283 return lockname; 283 return lockname;
284} 284}
285 285
286void 286void
287wydawca_lock_init () 287wydawca_lock_init ()
288{ 288{
289 if (enable_locking) 289 if (enable_locking)
290 { 290 {
291 if (!lockdir) 291 if (!lockdir)
292 lockdir = xstrdup (LOCALSTATEDIR "/lock/" PACKAGE); 292 lockdir = grecs_strdup (LOCALSTATEDIR "/lock/" PACKAGE);
293 if (create_hierarchy (lockdir, 0)) 293 if (create_hierarchy (lockdir, 0))
294 exit (EX_OSFILE); 294 exit (EX_OSFILE);
295 } 295 }
296} 296}
diff --git a/src/mail.c b/src/mail.c
index bac0381..6855ed7 100644
--- a/src/mail.c
+++ b/src/mail.c
@@ -282,34 +282,34 @@ mail_send_message (mu_address_t rcpt, const char *text,
282 mu_stream_unref (stream); 282 mu_stream_unref (stream);
283 if (rc) 283 if (rc)
284 { 284 {
285 logmsg (LOG_CRIT, _("cannot create message: %s"), mu_strerror (rc)); 285 logmsg (LOG_CRIT, _("cannot create message: %s"), mu_strerror (rc));
286 return; 286 return;
287 } 287 }
288 mu_message_get_header (msg, &hdr); 288 mu_message_get_header (msg, &hdr);
289 mu_header_append (hdr, "X-Mailer", x_mailer); 289 mu_header_append (hdr, "X-Mailer", x_mailer);
290 290
291 if (rcpt) 291 if (rcpt)
292 { 292 {
293 mu_address_to_string (rcpt, NULL, 0, &size); 293 mu_address_to_string (rcpt, NULL, 0, &size);
294 buf = xmalloc (size + 1); 294 buf = grecs_malloc (size + 1);
295 mu_address_to_string (rcpt, buf, size + 1, NULL); 295 mu_address_to_string (rcpt, buf, size + 1, NULL);
296 296
297 mu_header_set_value (hdr, "To", buf, 1); 297 mu_header_set_value (hdr, "To", buf, 1);
298 free (buf); 298 free (buf);
299 299
300 if (from_address && mu_header_sget_value (hdr, "From", &sval)) 300 if (from_address && mu_header_sget_value (hdr, "From", &sval))
301 { 301 {
302 mu_address_to_string (from_address, NULL, 0, &size); 302 mu_address_to_string (from_address, NULL, 0, &size);
303 buf = xmalloc (size + 1); 303 buf = grecs_malloc (size + 1);
304 mu_address_to_string (from_address, buf, size + 1, NULL); 304 mu_address_to_string (from_address, buf, size + 1, NULL);
305 mu_header_set_value (hdr, "From", buf, 1); 305 mu_header_set_value (hdr, "From", buf, 1);
306 free (buf); 306 free (buf);
307 } 307 }
308 } 308 }
309 309
310 if (debug_level > 1) 310 if (debug_level > 1)
311 { 311 {
312 mu_debug_level_t level; 312 mu_debug_level_t level;
313 313
314 mu_debug_get_category_level (MU_DEBCAT_MAILER, &level); 314 mu_debug_get_category_level (MU_DEBCAT_MAILER, &level);
315 level |= MU_DEBUG_LEVEL_MASK (MU_DEBUG_TRACE0) | 315 level |= MU_DEBUG_LEVEL_MASK (MU_DEBUG_TRACE0) |
@@ -425,35 +425,35 @@ mail_stats ()
425 425
426 if (!admin_address) 426 if (!admin_address)
427 { 427 {
428 logmsg (LOG_ERR, _("cannot mail statistics: admin-address not defined")); 428 logmsg (LOG_ERR, _("cannot mail statistics: admin-address not defined"));
429 return; 429 return;
430 } 430 }
431 431
432 if (debug_level) 432 if (debug_level)
433 { 433 {
434 size_t size; 434 size_t size;
435 char *buf; 435 char *buf;
436 mu_address_to_string (admin_address, NULL, 0, &size); 436 mu_address_to_string (admin_address, NULL, 0, &size);
437 buf = xmalloc (size + 1); 437 buf = grecs_malloc (size + 1);
438 mu_address_to_string (admin_address, buf, size + 1, NULL); 438 mu_address_to_string (admin_address, buf, size + 1, NULL);
439 logmsg (LOG_DEBUG, _("sending stats to %s"), buf); 439 logmsg (LOG_DEBUG, _("sending stats to %s"), buf);
440 free (buf); 440 free (buf);
441 } 441 }
442 442
443 tc = timer_get_count () * 3; 443 tc = timer_get_count () * 3;
444 exp = make_stat_expansion (tc + 1); 444 exp = make_stat_expansion (tc + 1);
445 time (&t); 445 time (&t);
446 exp[0].kw = "date"; 446 exp[0].kw = "date";
447 exp[0].value = exp[0].storage = xstrdup (ctime (&t)); 447 exp[0].value = exp[0].storage = grecs_strdup (ctime (&t));
448 exp[0].value [strlen (exp[0].value) - 1] = 0; 448 exp[0].value [strlen (exp[0].value) - 1] = 0;
449 timer_fill_meta (exp + 1, tc); 449 timer_fill_meta (exp + 1, tc);
450 450
451 tmpl = resolve_message_template (admin_stat_message); 451 tmpl = resolve_message_template (admin_stat_message);
452 if (!tmpl) 452 if (!tmpl)
453 { 453 {
454 logmsg (LOG_ERR, _("undefined message reference: %s"), 454 logmsg (LOG_ERR, _("undefined message reference: %s"),
455 admin_stat_message); 455 admin_stat_message);
456 return; 456 return;
457 } 457 }
458 text = meta_expand_string (tmpl, exp, NULL, NULL, NULL); 458 text = meta_expand_string (tmpl, exp, NULL, NULL, NULL);
459 459
@@ -589,25 +589,25 @@ do_notify (struct file_triplet *trp, enum notification_event ev,
589 trp->project, 589 trp->project,
590 notification_event_str (ev), gettext (errp)); 590 notification_event_str (ev), gettext (errp));
591 return; 591 return;
592 } 592 }
593 593
594 if (debug_level) 594 if (debug_level)
595 { 595 {
596 if (rcpt) 596 if (rcpt)
597 { 597 {
598 size_t size; 598 size_t size;
599 char *buf; 599 char *buf;
600 mu_address_to_string (rcpt, NULL, 0, &size); 600 mu_address_to_string (rcpt, NULL, 0, &size);
601 buf = xmalloc (size + 1); 601 buf = grecs_malloc (size + 1);
602 mu_address_to_string (rcpt, buf, size + 1, NULL); 602 mu_address_to_string (rcpt, buf, size + 1, NULL);
603 logmsg (LOG_DEBUG, _("notifying %s (project %s) about %s"), 603 logmsg (LOG_DEBUG, _("notifying %s (project %s) about %s"),
604 buf, trp->project, notification_event_str (ev)); 604 buf, trp->project, notification_event_str (ev));
605 free (buf); 605 free (buf);
606 } 606 }
607 else 607 else
608 logmsg (LOG_DEBUG, 608 logmsg (LOG_DEBUG,
609 _("notifying message recipients (project %s) about %s"), 609 _("notifying message recipients (project %s) about %s"),
610 trp->project, notification_event_str (ev)); 610 trp->project, notification_event_str (ev));
611 } 611 }
612 612
613 msg = resolve_message_template (ntf->msg); 613 msg = resolve_message_template (ntf->msg);
@@ -633,25 +633,25 @@ notify (struct notification *notification_list,
633 if (p->ev == ev) 633 if (p->ev == ev)
634 do_notify (trp, ev, p); 634 do_notify (trp, ev, p);
635 /* FIXME */ 635 /* FIXME */
636} 636}
637 637
638const char * 638const char *
639expand_email_admin (struct metadef *def, void *data) 639expand_email_admin (struct metadef *def, void *data)
640{ 640{
641 size_t size; 641 size_t size;
642 if (mu_address_to_string (admin_address, NULL, 0, &size) == 0) 642 if (mu_address_to_string (admin_address, NULL, 0, &size) == 0)
643 { 643 {
644 size++; 644 size++;
645 def->storage = xmalloc (size); 645 def->storage = grecs_malloc (size);
646 mu_address_to_string (admin_address, def->storage, size, NULL); 646 mu_address_to_string (admin_address, def->storage, size, NULL);
647 def->value = def->storage; 647 def->value = def->storage;
648 } 648 }
649 else 649 else
650 def->value = ""; 650 def->value = "";
651 return def->value; 651 return def->value;
652} 652}
653 653
654const char * 654const char *
655expand_email_owner (struct metadef *def, void *data) 655expand_email_owner (struct metadef *def, void *data)
656{ 656{
657 struct file_triplet *trp = data; 657 struct file_triplet *trp = data;
@@ -661,22 +661,22 @@ expand_email_owner (struct metadef *def, void *data)
661 661
662 addr = get_recipient (trp->spool->dictionary[project_owner_dict], 662 addr = get_recipient (trp->spool->dictionary[project_owner_dict],
663 trp, &errp); 663 trp, &errp);
664 if (!addr) 664 if (!addr)
665 { 665 {
666 logmsg (LOG_ERR, _("cannot get email of the %s's owner: %s"), 666 logmsg (LOG_ERR, _("cannot get email of the %s's owner: %s"),
667 trp->project, gettext (errp)); 667 trp->project, gettext (errp));
668 def->value = ""; 668 def->value = "";
669 } 669 }
670 else if (mu_address_to_string (addr, NULL, 0, &size) == 0) 670 else if (mu_address_to_string (addr, NULL, 0, &size) == 0)
671 { 671 {
672 size++; 672 size++;
673 def->storage = xmalloc (size); 673 def->storage = grecs_malloc (size);
674 mu_address_to_string (addr, def->storage, size, NULL); 674 mu_address_to_string (addr, def->storage, size, NULL);
675 def->value = def->storage; 675 def->value = def->storage;
676 mu_address_destroy (&addr); 676 mu_address_destroy (&addr);
677 } 677 }
678 else 678 else
679 def->value = ""; 679 def->value = "";
680 return def->value; 680 return def->value;
681} 681}
682 682
diff --git a/src/net.c b/src/net.c
index 3e9fe30..d08a6ba 100644
--- a/src/net.c
+++ b/src/net.c
@@ -94,47 +94,47 @@ trim_crlf (char *s)
94 } 94 }
95} 95}
96 96
97void 97void
98handle_connection (FILE *in, FILE *out) 98handle_connection (FILE *in, FILE *out)
99{ 99{
100 char *buf = NULL; 100 char *buf = NULL;
101 size_t buflen = 0; 101 size_t buflen = 0;
102 const struct spool *spool; 102 const struct spool *spool;
103 char *p; 103 char *p;
104 struct passwd *pw; 104 struct passwd *pw;
105 105
106 if (getline (&buf, &buflen, in) <= 0) 106 if (grecs_getline (&buf, &buflen, in) <= 0)
107 return; 107 return;
108 trim_crlf (buf); 108 trim_crlf (buf);
109 if (debug_level) 109 if (debug_level)
110 logmsg (LOG_DEBUG, "recv: %s", buf); 110 logmsg (LOG_DEBUG, "recv: %s", buf);
111 spool = wydawca_find_spool (buf); 111 spool = wydawca_find_spool (buf);
112 if (!spool) 112 if (!spool)
113 { 113 {
114 if (all_spool_aliases && grecs_list_locate (all_spool_aliases, buf)) 114 if (all_spool_aliases && grecs_list_locate (all_spool_aliases, buf))
115 fprintf (out, "+ OK, all spools\r\n"); 115 fprintf (out, "+ OK, all spools\r\n");
116 else 116 else
117 { 117 {
118 fprintf (out, "- Unknown service name\r\n"); 118 fprintf (out, "- Unknown service name\r\n");
119 free (buf); 119 free (buf);
120 return; 120 return;
121 } 121 }
122 } 122 }
123 else if (spool->url) 123 else if (spool->url)
124 fprintf (out, "+ OK, URL %s\r\n", spool->url); 124 fprintf (out, "+ OK, URL %s\r\n", spool->url);
125 else 125 else
126 fprintf (out, "+ OK, spool %s\r\n", spool->tag); 126 fprintf (out, "+ OK, spool %s\r\n", spool->tag);
127 127
128 if (getline (&buf, &buflen, in) < 0) 128 if (grecs_getline (&buf, &buflen, in) < 0)
129 { 129 {
130 logmsg (LOG_ERR, "protocol error"); 130 logmsg (LOG_ERR, "protocol error");
131 free (buf); 131 free (buf);
132 return; 132 return;
133 } 133 }
134 134
135 trim_crlf (buf); 135 trim_crlf (buf);
136 if (debug_level) 136 if (debug_level)
137 logmsg (LOG_DEBUG, "recv: %s", buf); 137 logmsg (LOG_DEBUG, "recv: %s", buf);
138 138
139 p = strchr (buf, ' '); 139 p = strchr (buf, ' ');
140 if (p) 140 if (p)
diff --git a/src/process.c b/src/process.c
index e41709d..200d987 100644
--- a/src/process.c
+++ b/src/process.c
@@ -18,25 +18,25 @@
18 18
19struct spool_list 19struct spool_list
20{ 20{
21 struct spool_list *next; 21 struct spool_list *next;
22 struct spool spool; 22 struct spool spool;
23}; 23};
24 24
25static struct spool_list *spool_list; 25static struct spool_list *spool_list;
26 26
27void 27void
28register_spool (struct spool *spool) 28register_spool (struct spool *spool)
29{ 29{
30 struct spool_list *sp = xmalloc (sizeof *sp); 30 struct spool_list *sp = grecs_malloc (sizeof *sp);
31 sp->spool = *spool; 31 sp->spool = *spool;
32 sp->next = spool_list; 32 sp->next = spool_list;
33 spool_list = sp; 33 spool_list = sp;
34} 34}
35 35
36static int 36static int
37spool_check_alias (struct spool *spool, const char *name) 37spool_check_alias (struct spool *spool, const char *name)
38{ 38{
39 if (spool->aliases && grecs_list_locate (spool->aliases, (char*) name)) 39 if (spool->aliases && grecs_list_locate (spool->aliases, (char*) name))
40 return 1; 40 return 1;
41 return 0; 41 return 0;
42} 42}
@@ -104,25 +104,25 @@ parse_file_name (const char *name, struct file_info *finfo)
104 { SUF_DIR, SUF_DIR_LEN, file_directive }, 104 { SUF_DIR, SUF_DIR_LEN, file_directive },
105 { "", 0, file_dist } 105 { "", 0, file_dist }
106 }; 106 };
107 int i; 107 int i;
108 unsigned len = strlen (name); 108 unsigned len = strlen (name);
109 109
110 for (i = 0; i < sizeof suftab / sizeof suftab[0]; i++) 110 for (i = 0; i < sizeof suftab / sizeof suftab[0]; i++)
111 { 111 {
112 if (len >= suftab[i].len 112 if (len >= suftab[i].len
113 && memcmp (name + len - suftab[i].len, 113 && memcmp (name + len - suftab[i].len,
114 suftab[i].suf, suftab[i].len) == 0) 114 suftab[i].suf, suftab[i].len) == 0)
115 { 115 {
116 finfo->name = xstrdup (name); 116 finfo->name = grecs_strdup (name);
117 finfo->type = suftab[i].type; 117 finfo->type = suftab[i].type;
118 finfo->root_len = len - suftab[i].len; 118 finfo->root_len = len - suftab[i].len;
119 return; 119 return;
120 } 120 }
121 } 121 }
122 abort (); /* should not happen */ 122 abort (); /* should not happen */
123} 123}
124 124
125int 125int
126match_uid_p (uid_t uid, int uc, uid_t *uv) 126match_uid_p (uid_t uid, int uc, uid_t *uv)
127{ 127{
128 int i; 128 int i;
diff --git a/src/sql.c b/src/sql.c
index a4b311e..80eb344 100644
--- a/src/sql.c
+++ b/src/sql.c
@@ -21,25 +21,25 @@
21struct sql_list 21struct sql_list
22{ 22{
23 struct sql_list *next; 23 struct sql_list *next;
24 struct sqlconn conn; 24 struct sqlconn conn;
25}; 25};
26 26
27static struct sql_list *sql_list; 27static struct sql_list *sql_list;
28 28
29/* Append CONN to the end of sql_list */ 29/* Append CONN to the end of sql_list */
30void 30void
31sql_register_conn (struct sqlconn *conn) 31sql_register_conn (struct sqlconn *conn)
32{ 32{
33 struct sql_list *ent = xmalloc (sizeof *ent); 33 struct sql_list *ent = grecs_malloc (sizeof *ent);
34 ent->conn = *conn; 34 ent->conn = *conn;
35 ent->next = sql_list; 35 ent->next = sql_list;
36 sql_list = ent; 36 sql_list = ent;
37} 37}
38 38
39/* Find a configured connection that has the given IDENT */ 39/* Find a configured connection that has the given IDENT */
40struct sqlconn * 40struct sqlconn *
41sql_find_connection (const char *ident) 41sql_find_connection (const char *ident)
42{ 42{
43 struct sql_list *p; 43 struct sql_list *p;
44 for (p = sql_list; p; p = p->next) 44 for (p = sql_list; p; p = p->next)
45 if (strcmp (p->conn.ident, ident) == 0) 45 if (strcmp (p->conn.ident, ident) == 0)
@@ -189,19 +189,19 @@ sql_get_dictionary (struct dictionary *dict, void *handle,
189} 189}
190 190
191int 191int
192sql_quote (struct dictionary *dict, void *handle, const char *input, 192sql_quote (struct dictionary *dict, void *handle, const char *input,
193 char **poutput, size_t *psize) 193 char **poutput, size_t *psize)
194{ 194{
195 struct sqlconn *conn = handle; 195 struct sqlconn *conn = handle;
196 size_t len, size; 196 size_t len, size;
197 char *output; 197 char *output;
198 198
199 len = strlen (input); 199 len = strlen (input);
200 size = 2 * len + 1; 200 size = 2 * len + 1;
201 output = xmalloc (size); 201 output = grecs_malloc (size);
202 mysql_real_escape_string (&conn->mysql, output, input, len); 202 mysql_real_escape_string (&conn->mysql, output, input, len);
203 *poutput = output; 203 *poutput = output;
204 if (psize) 204 if (psize)
205 *psize = strlen (output); 205 *psize = strlen (output);
206 return 0; 206 return 0;
207} 207}
diff --git a/src/timer.c b/src/timer.c
index 1634462..cece63a 100644
--- a/src/timer.c
+++ b/src/timer.c
@@ -11,25 +11,24 @@
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details. 12 GNU General Public License for more details.
13 13
14 You should have received a copy of the GNU General Public License along 14 You should have received a copy of the GNU General Public License along
15 with wydawca. If not, see <http://www.gnu.org/licenses/>. */ 15 with wydawca. If not, see <http://www.gnu.org/licenses/>. */
16 16
17#include <wydawca.h> 17#include <wydawca.h>
18#include <sys/time.h> 18#include <sys/time.h>
19#include <sys/resource.h> 19#include <sys/resource.h>
20#include <unistd.h> 20#include <unistd.h>
21#include <string.h> 21#include <string.h>
22#include <ctype.h> 22#include <ctype.h>
23#include <xalloc.h>
24 23
25struct timer_slot 24struct timer_slot
26{ 25{
27 char *name; 26 char *name;
28 double real; 27 double real;
29 double self_user; /* user time in sec */ 28 double self_user; /* user time in sec */
30 double self_system; /* system time in sec */ 29 double self_system; /* system time in sec */
31 double children_user; /* user time in sec */ 30 double children_user; /* user time in sec */
32 double children_system;/* system time in sec */ 31 double children_system;/* system time in sec */
33 struct timeval real_mark; 32 struct timeval real_mark;
34 struct rusage self_mark; 33 struct rusage self_mark;
35 struct rusage children_mark; 34 struct rusage children_mark;
@@ -173,25 +172,25 @@ timer_format_time (double t)
173 s -= h * 3600; 172 s -= h * 3600;
174 m = s / 60; 173 m = s / 60;
175 s -= m * 60; 174 s -= m * 60;
176 175
177 if (d) 176 if (d)
178 grecs_asprintf (&str, &size, "%ld+%02ld:%02ld:%02ld", d, h, m, s); 177 grecs_asprintf (&str, &size, "%ld+%02ld:%02ld:%02ld", d, h, m, s);
179 else if (h) 178 else if (h)
180 grecs_asprintf (&str, &size, "%02ld:%02ld:%02ld", h, m, s); 179 grecs_asprintf (&str, &size, "%02ld:%02ld:%02ld", h, m, s);
181 else 180 else
182 grecs_asprintf (&str, &size, "%02ld:%02ld", m, s); 181 grecs_asprintf (&str, &size, "%02ld:%02ld", m, s);
183 } 182 }
184 if (!str) 183 if (!str)
185 xalloc_die (); 184 grecs_alloc_die ();
186 return str; 185 return str;
187} 186}
188 187
189size_t 188size_t
190timer_get_count () 189timer_get_count ()
191{ 190{
192 return _timer_count; 191 return _timer_count;
193} 192}
194 193
195struct timer_data 194struct timer_data
196{ 195{
197 struct metadef *def; 196 struct metadef *def;
@@ -201,25 +200,25 @@ struct timer_data
201int 200int
202_fill_meta (void *sym, void *data) 201_fill_meta (void *sym, void *data)
203{ 202{
204 struct timer_slot *slot = sym; 203 struct timer_slot *slot = sym;
205 struct timer_data *tp = data; 204 struct timer_data *tp = data;
206 #define CREATE_DEF(arg) \ 205 #define CREATE_DEF(arg) \
207 if (tp->num) \ 206 if (tp->num) \
208 { \ 207 { \
209 char *buf = NULL; \ 208 char *buf = NULL; \
210 size_t size = 0; \ 209 size_t size = 0; \
211 grecs_asprintf (&buf, &size, "timer:%s:%s", slot->name, #arg); \ 210 grecs_asprintf (&buf, &size, "timer:%s:%s", slot->name, #arg); \
212 if (!buf) \ 211 if (!buf) \
213 xalloc_die (); \ 212 grecs_alloc_die (); \
214 tp->def->kw = buf; \ 213 tp->def->kw = buf; \
215 tp->def->storage = timer_format_time (__cat2__(timer_get_,arg) (slot)); \ 214 tp->def->storage = timer_format_time (__cat2__(timer_get_,arg) (slot)); \
216 tp->def->value = tp->def->storage; \ 215 tp->def->value = tp->def->storage; \
217 tp->def->expand = NULL; \ 216 tp->def->expand = NULL; \
218 tp->def++; \ 217 tp->def++; \
219 tp->num--; \ 218 tp->num--; \
220 } 219 }
221 220
222 CREATE_DEF(system); 221 CREATE_DEF(system);
223 CREATE_DEF(real); 222 CREATE_DEF(real);
224 CREATE_DEF(user); 223 CREATE_DEF(user);
225 224
diff --git a/src/triplet.c b/src/triplet.c
index 3083c64..9dfdf2c 100644
--- a/src/triplet.c
+++ b/src/triplet.c
@@ -51,24 +51,25 @@ hash_triplet_free (void *data)
51 free (tp->file[i].name); 51 free (tp->file[i].name);
52 } 52 }
53 53
54 free (tp->directive); 54 free (tp->directive);
55 free (tp->blurb); 55 free (tp->blurb);
56 free (tp->tmp); 56 free (tp->tmp);
57 txtacc_free (tp->acc); 57 txtacc_free (tp->acc);
58 58
59 /* Free uploader list */ 59 /* Free uploader list */
60 for (up = tp->uploader_list; up; ) 60 for (up = tp->uploader_list; up; )
61 { 61 {
62 struct uploader_info *next = up->next; 62 struct uploader_info *next = up->next;
63 free (up->fpr);
63 free (up); 64 free (up);
64 up = next; 65 up = next;
65 } 66 }
66 67
67 free (tp); 68 free (tp);
68} 69}
69 70
70char * 71char *
71triplet_strdup (struct file_triplet *tp, const char *str) 72triplet_strdup (struct file_triplet *tp, const char *str)
72{ 73{
73 size_t len = strlen (str); 74 size_t len = strlen (str);
74 txtacc_grow (tp->acc, str, len + 1); 75 txtacc_grow (tp->acc, str, len + 1);
@@ -85,25 +86,25 @@ register_file (struct file_info *finfo, const struct spool *spool)
85 if (!triplet_table) 86 if (!triplet_table)
86 { 87 {
87 triplet_table = grecs_symtab_create (sizeof (struct file_triplet), 88 triplet_table = grecs_symtab_create (sizeof (struct file_triplet),
88 hash_triplet_hasher, 89 hash_triplet_hasher,
89 hash_triplet_compare, 90 hash_triplet_compare,
90 NULL, 91 NULL,
91 NULL, 92 NULL,
92 hash_triplet_free); 93 hash_triplet_free);
93 if (!triplet_table) 94 if (!triplet_table)
94 grecs_alloc_die (); 95 grecs_alloc_die ();
95 } 96 }
96 97
97 key.name = xmalloc (finfo->root_len + 1); 98 key.name = grecs_malloc (finfo->root_len + 1);
98 memcpy (key.name, finfo->name, finfo->root_len); 99 memcpy (key.name, finfo->name, finfo->root_len);
99 key.name[finfo->root_len] = 0; 100 key.name[finfo->root_len] = 0;
100 101
101 ret = grecs_symtab_lookup_or_install (triplet_table, &key, &install); 102 ret = grecs_symtab_lookup_or_install (triplet_table, &key, &install);
102 if (!ret) 103 if (!ret)
103 grecs_alloc_die (); 104 grecs_alloc_die ();
104 free (key.name); 105 free (key.name);
105 if (install) 106 if (install)
106 { 107 {
107 ret->spool = spool; 108 ret->spool = spool;
108 ret->acc = txtacc_create (); 109 ret->acc = txtacc_create ();
109 } 110 }
@@ -369,58 +370,58 @@ format_file_data (struct file_triplet *trp, enum file_type type, char **pret)
369 user_name = "unknown"; 370 user_name = "unknown";
370 else 371 else
371 user_name = pw->pw_name; 372 user_name = pw->pw_name;
372 373
373 grp = getgrgid (TRIPLET_GID (trp)); 374 grp = getgrgid (TRIPLET_GID (trp));
374 if (!grp) 375 if (!grp)
375 group_name = "unknown"; /* should not happen */ 376 group_name = "unknown"; /* should not happen */
376 else 377 else
377 group_name = grp->gr_name; 378 group_name = grp->gr_name;
378 379
379 /* Size */ 380 /* Size */
380 if (grecs_asprintf (&sptr, &slen, "%lu", (unsigned long) info->sb.st_size)) 381 if (grecs_asprintf (&sptr, &slen, "%lu", (unsigned long) info->sb.st_size))
381 xalloc_die (); 382 grecs_alloc_die ();
382 383
383 /* Figure out padding and format the buffer */ 384 /* Figure out padding and format the buffer */
384 slen = strlen (sptr); 385 slen = strlen (sptr);
385 pad = strlen (user_name) + 1 + strlen (group_name) + 1 + slen; 386 pad = strlen (user_name) + 1 + strlen (group_name) + 1 + slen;
386 if (pad > ugswidth) 387 if (pad > ugswidth)
387 ugswidth = pad; 388 ugswidth = pad;
388 389
389 if (grecs_asprintf (&buf, &size, 390 if (grecs_asprintf (&buf, &size,
390 "%s %s %s %*s %s %s", 391 "%s %s %s %*s %s %s",
391 modes, user_name, group_name, ugswidth - pad + slen, 392 modes, user_name, group_name, ugswidth - pad + slen,
392 sptr, 393 sptr,
393 timebuf, info->name)) 394 timebuf, info->name))
394 xalloc_die (); 395 grecs_alloc_die ();
395 free (sptr); 396 free (sptr);
396 *pret = buf; 397 *pret = buf;
397 return 0; 398 return 0;
398} 399}
399 400
400static const char * 401static const char *
401expand_triplet_ls_full (struct metadef *def, void *data) 402expand_triplet_ls_full (struct metadef *def, void *data)
402{ 403{
403 struct file_triplet *trp = data; 404 struct file_triplet *trp = data;
404 char *buf[FILE_TYPE_COUNT] = { NULL, NULL, NULL }; 405 char *buf[FILE_TYPE_COUNT] = { NULL, NULL, NULL };
405 size_t size = 0; 406 size_t size = 0;
406 407
407 if (format_file_data (trp, file_dist, &buf[file_dist]) == 0) 408 if (format_file_data (trp, file_dist, &buf[file_dist]) == 0)
408 size += strlen (buf[file_dist]) + 1; 409 size += strlen (buf[file_dist]) + 1;
409 if (format_file_data (trp, file_signature, &buf[file_signature]) == 0) 410 if (format_file_data (trp, file_signature, &buf[file_signature]) == 0)
410 size += strlen (buf[file_signature]) + 1; 411 size += strlen (buf[file_signature]) + 1;
411 if (format_file_data (trp, file_directive, &buf[file_directive]) == 0) 412 if (format_file_data (trp, file_directive, &buf[file_directive]) == 0)
412 size += strlen (buf[file_directive]) + 1; 413 size += strlen (buf[file_directive]) + 1;
413 414
414 def->value = def->storage = xmalloc (size + 1); 415 def->value = def->storage = grecs_malloc (size + 1);
415 def->value[0] = 0; 416 def->value[0] = 0;
416 if (buf[file_dist]) 417 if (buf[file_dist])
417 { 418 {
418 strcat (def->value, buf[file_dist]); 419 strcat (def->value, buf[file_dist]);
419 strcat (def->value, "\n"); 420 strcat (def->value, "\n");
420 } 421 }
421 if (buf[file_signature]) 422 if (buf[file_signature])
422 { 423 {
423 strcat (def->value, buf[file_signature]); 424 strcat (def->value, buf[file_signature]);
424 strcat (def->value, "\n"); 425 strcat (def->value, "\n");
425 } 426 }
426 if (buf[file_directive]) 427 if (buf[file_directive])
@@ -437,25 +438,25 @@ expand_triplet_ls_full (struct metadef *def, void *data)
437static const char * 438static const char *
438expand_triplet_ls_upload (struct metadef *def, void *data) 439expand_triplet_ls_upload (struct metadef *def, void *data)
439{ 440{
440 struct file_triplet *trp = data; 441 struct file_triplet *trp = data;
441 char *buf[2] = { NULL, NULL }; 442 char *buf[2] = { NULL, NULL };
442 size_t size = 0; 443 size_t size = 0;
443 444
444 if (format_file_data (trp, file_dist, &buf[file_dist]) == 0) 445 if (format_file_data (trp, file_dist, &buf[file_dist]) == 0)
445 size += strlen (buf[file_dist]) + 1; 446 size += strlen (buf[file_dist]) + 1;
446 if (format_file_data (trp, file_signature, &buf[file_signature]) == 0) 447 if (format_file_data (trp, file_signature, &buf[file_signature]) == 0)
447 size += strlen (buf[file_signature]) + 1; 448 size += strlen (buf[file_signature]) + 1;
448 449
449 def->value = def->storage = xmalloc (size + 1); 450 def->value = def->storage = grecs_malloc (size + 1);
450 def->value[0] = 0; 451 def->value[0] = 0;
451 if (buf[file_dist]) 452 if (buf[file_dist])
452 { 453 {
453 strcat (def->value, buf[file_dist]); 454 strcat (def->value, buf[file_dist]);
454 strcat (def->value, "\n"); 455 strcat (def->value, "\n");
455 } 456 }
456 if (buf[file_signature]) 457 if (buf[file_signature])
457 { 458 {
458 strcat (def->value, buf[file_signature]); 459 strcat (def->value, buf[file_signature]);
459 strcat (def->value, "\n"); 460 strcat (def->value, "\n");
460 } 461 }
461 462
@@ -543,25 +544,25 @@ expand_user_email (struct metadef *def, void *data)
543 return def->value; 544 return def->value;
544} 545}
545 546
546static const char * 547static const char *
547expand_email_user (struct metadef *def, void *data) 548expand_email_user (struct metadef *def, void *data)
548{ 549{
549 struct file_triplet *trp = data; 550 struct file_triplet *trp = data;
550 if (trp->uploader) 551 if (trp->uploader)
551 { 552 {
552 size_t size = 0; 553 size_t size = 0;
553 if (grecs_asprintf (&def->storage, &size, "\"%s\" <%s>", 554 if (grecs_asprintf (&def->storage, &size, "\"%s\" <%s>",
554 trp->uploader->realname, trp->uploader->email)) 555 trp->uploader->realname, trp->uploader->email))
555 xalloc_die (); 556 grecs_alloc_die ();
556 def->value = def->storage; 557 def->value = def->storage;
557 } 558 }
558 return def->value; 559 return def->value;
559} 560}
560 561
561static const char * 562static const char *
562expand_report (struct metadef *def, void *data) 563expand_report (struct metadef *def, void *data)
563{ 564{
564 return report_string; 565 return report_string;
565} 566}
566 567
567static const char * 568static const char *
@@ -585,33 +586,33 @@ expand_check_result (struct metadef *def, void *data)
585{ 586{
586 struct file_triplet *trp = data; 587 struct file_triplet *trp = data;
587 int status = trp->check_result; 588 int status = trp->check_result;
588 589
589 if (status == 0) 590 if (status == 0)
590 return def->value = "0"; 591 return def->value = "0";
591 else if (WIFEXITED (status)) 592 else if (WIFEXITED (status))
592 { 593 {
593 size_t size = 0; 594 size_t size = 0;
594 def->storage = NULL; 595 def->storage = NULL;
595 if (grecs_asprintf (&def->storage, &size, 596 if (grecs_asprintf (&def->storage, &size,
596 "%d", WEXITSTATUS (status))) 597 "%d", WEXITSTATUS (status)))
597 xalloc_die (); 598 grecs_alloc_die ();
598 } 599 }
599 else if (WIFSIGNALED (status)) 600 else if (WIFSIGNALED (status))
600 { 601 {
601 size_t size = 0; 602 size_t size = 0;
602 def->storage = NULL; 603 def->storage = NULL;
603 if (grecs_asprintf (&def->storage, &size, "SIG+%d", 604 if (grecs_asprintf (&def->storage, &size, "SIG+%d",
604 WTERMSIG (status))) 605 WTERMSIG (status)))
605 xalloc_die (); 606 grecs_alloc_die ();
606 } 607 }
607 else 608 else
608 return def->value = "[unrecognized return code]"; 609 return def->value = "[unrecognized return code]";
609 return def->value = def->storage; 610 return def->value = def->storage;
610} 611}
611 612
612 #define DECL_EXPAND_TIMER(what) \ 613 #define DECL_EXPAND_TIMER(what) \
613 static const char * \ 614 static const char * \
614__cat2__(expand_timer_,what) (struct metadef *def, void *data) \ 615__cat2__(expand_timer_,what) (struct metadef *def, void *data) \
615{ \ 616{ \
616 wydawca_timer_t t = timer_stop ((char*)def->data); \ 617 wydawca_timer_t t = timer_stop ((char*)def->data); \
617 def->storage = timer_format_time (__cat2__(timer_get_,what) (t));\ 618 def->storage = timer_format_time (__cat2__(timer_get_,what) (t));\
diff --git a/src/txtacc.c b/src/txtacc.c
index 91659f6..442e27e 100644
--- a/src/txtacc.c
+++ b/src/txtacc.c
@@ -25,26 +25,26 @@ struct txtacc_entry
25#define TXTACC_BUFSIZE 1024 25#define TXTACC_BUFSIZE 1024
26#define txtacc_entry_freesize(e) ((e)->size - (e)->len) 26#define txtacc_entry_freesize(e) ((e)->size - (e)->len)
27 27
28struct txtacc 28struct txtacc
29{ 29{
30 struct grecs_list *cur; /* Current build list */ 30 struct grecs_list *cur; /* Current build list */
31 struct grecs_list *mem; /* List of already allocated elements */ 31 struct grecs_list *mem; /* List of already allocated elements */
32}; 32};
33 33
34static struct txtacc_entry * 34static struct txtacc_entry *
35txtacc_alloc_entry (struct grecs_list *list, size_t size) 35txtacc_alloc_entry (struct grecs_list *list, size_t size)
36{ 36{
37 struct txtacc_entry *p = xmalloc (sizeof (*p)); 37 struct txtacc_entry *p = grecs_malloc (sizeof (*p));
38 p->buf = xmalloc (size); 38 p->buf = grecs_malloc (size);
39 p->size = size; 39 p->size = size;
40 p->len = 0; 40 p->len = 0;
41 grecs_list_append (list, p); 41 grecs_list_append (list, p);
42 return p; 42 return p;
43} 43}
44 44
45static struct txtacc_entry * 45static struct txtacc_entry *
46txtacc_cur_entry (struct txtacc *acc) 46txtacc_cur_entry (struct txtacc *acc)
47{ 47{
48 struct txtacc_entry *ent; 48 struct txtacc_entry *ent;
49 49
50 if (grecs_list_size (acc->cur) == 0) 50 if (grecs_list_size (acc->cur) == 0)
@@ -80,25 +80,25 @@ txtacc_entry_free (void *p)
80{ 80{
81 if (p) 81 if (p)
82 { 82 {
83 struct txtacc_entry *ent = p; 83 struct txtacc_entry *ent = p;
84 free (ent->buf); 84 free (ent->buf);
85 free (ent); 85 free (ent);
86 } 86 }
87} 87}
88 88
89struct txtacc * 89struct txtacc *
90txtacc_create () 90txtacc_create ()
91{ 91{
92 struct txtacc *acc = xmalloc (sizeof (*acc)); 92 struct txtacc *acc = grecs_malloc (sizeof (*acc));
93 acc->cur = grecs_list_create (); 93 acc->cur = grecs_list_create ();
94 acc->cur->free_entry = txtacc_entry_free; 94 acc->cur->free_entry = txtacc_entry_free;
95 acc->mem = grecs_list_create (); 95 acc->mem = grecs_list_create ();
96 acc->mem->free_entry = txtacc_entry_free; 96 acc->mem->free_entry = txtacc_entry_free;
97 return acc; 97 return acc;
98} 98}
99 99
100void 100void
101txtacc_free (struct txtacc *acc) 101txtacc_free (struct txtacc *acc)
102{ 102{
103 grecs_list_free (acc->cur); 103 grecs_list_free (acc->cur);
104 grecs_list_free (acc->mem); 104 grecs_list_free (acc->mem);
@@ -128,55 +128,57 @@ txtacc_finish (struct txtacc *acc, int steal)
128 size_t size; 128 size_t size;
129 char *p; 129 char *p;
130 130
131 switch (grecs_list_size (acc->cur)) 131 switch (grecs_list_size (acc->cur))
132 { 132 {
133 case 0: 133 case 0:
134 return NULL; 134 return NULL;
135 135
136 case 1: 136 case 1:
137 txtent = acc->cur->head->data; 137 txtent = acc->cur->head->data;
138 acc->cur->head->data = NULL; 138 acc->cur->head->data = NULL;
139 txtacc_entry_tailor (txtent); 139 txtacc_entry_tailor (txtent);
140 grecs_list_append (acc->mem, txtent);
140 break; 141 break;
141 142
142 default: 143 default:
143 size = 0; 144 size = 0;
144 for (ep = acc->cur->head; ep; ep = ep->next) 145 for (ep = acc->cur->head; ep; ep = ep->next)
145 { 146 {
146 txtent = ep->data; 147 txtent = ep->data;
147 size += txtent->len; 148 size += txtent->len;
148 } 149 }
149 150
150 txtent = txtacc_alloc_entry (acc->mem, size); 151 txtent = txtacc_alloc_entry (acc->mem, size);
151 for (ep = acc->cur->head; ep; ep = ep->next) 152 for (ep = acc->cur->head; ep; ep = ep->next)
152 { 153 {
153 struct txtacc_entry *tp = ep->data; 154 struct txtacc_entry *tp = ep->data;
154 txtacc_entry_append (txtent, tp->buf, tp->len); 155 txtacc_entry_append (txtent, tp->buf, tp->len);
155 } 156 }
156 } 157 }
157 158
158 grecs_list_clear (acc->cur); 159 grecs_list_clear (acc->cur);
159 p = txtent->buf; 160 p = txtent->buf;
160 if (steal) 161 if (steal)
161 free (txtent); 162 {
162 else 163 grecs_list_remove_tail (acc->mem);
163 grecs_list_append (acc->mem, txtent); 164 free (txtent);
165 }
164 return p; 166 return p;
165} 167}
166 168
167void 169void
168txtacc_free_string (struct txtacc *acc, char *str) 170txtacc_free_string (struct txtacc *acc, char *str)
169{ 171{
170 struct grecs_list_entry *ep; 172 struct grecs_list_entry *ep;
171 for (ep = acc->mem->head; ep; ep = ep->next) 173 for (ep = acc->mem->head; ep; ep = ep->next)
172 { 174 {
173 struct txtacc_entry *tp = ep->data; 175 struct txtacc_entry *tp = ep->data;
174 if (tp->buf == str) 176 if (tp->buf == str)
175 { 177 {
176 grecs_list_remove_entry(acc->mem, ep); 178 grecs_list_remove_entry (acc->mem, ep);
177 free (tp->buf); 179 free (tp->buf);
178 return; 180 return;
179 } 181 }
180 } 182 }
181} 183}
182 184
diff --git a/src/verify.c b/src/verify.c
index a49983c..c8fef11 100644
--- a/src/verify.c
+++ b/src/verify.c
@@ -104,25 +104,25 @@ fill_project_name (struct file_triplet *trp)
104 trp->file[file_directive].name); 104 trp->file[file_directive].name);
105 return 1; 105 return 1;
106 } 106 }
107 107
108 fp = fopen (trp->file[file_directive].name, "r"); 108 fp = fopen (trp->file[file_directive].name, "r");
109 if (!fp) 109 if (!fp)
110 { 110 {
111 logmsg (LOG_ERR, _("cannot open file %s: %s"), 111 logmsg (LOG_ERR, _("cannot open file %s: %s"),
112 trp->file[file_directive].name, strerror (errno)); 112 trp->file[file_directive].name, strerror (errno));
113 return 1; 113 return 1;
114 } 114 }
115 115
116 blurb = xmalloc (size + 1); 116 blurb = grecs_malloc (size + 1);
117 117
118 rc = fread (blurb, size, 1, fp); 118 rc = fread (blurb, size, 1, fp);
119 fclose (fp); 119 fclose (fp);
120 120
121 if (rc != 1) 121 if (rc != 1)
122 { 122 {
123 logmsg (LOG_ERR, _("error reading file %s: %s"), 123 logmsg (LOG_ERR, _("error reading file %s: %s"),
124 trp->file[file_directive].name, strerror (errno)); 124 trp->file[file_directive].name, strerror (errno));
125 free (blurb); 125 free (blurb);
126 return 1; 126 return 1;
127 } 127 }
128 128
@@ -173,25 +173,25 @@ fill_project_name (struct file_triplet *trp)
173 txtacc_1grow (trp->acc, 0); 173 txtacc_1grow (trp->acc, 0);
174 trp->project = txtacc_finish (trp->acc, 0); 174 trp->project = txtacc_finish (trp->acc, 0);
175 } 175 }
176 else 176 else
177 trp->project = trp->relative_dir; 177 trp->project = trp->relative_dir;
178 178
179 return 0; 179 return 0;
180} 180}
181 181
182struct uploader_info * 182struct uploader_info *
183new_uploader_info (struct uploader_info *src) 183new_uploader_info (struct uploader_info *src)
184{ 184{
185 struct uploader_info *p = xmalloc (sizeof (*p)); 185 struct uploader_info *p = grecs_malloc (sizeof (*p));
186 p->next = NULL; 186 p->next = NULL;
187 p->name = src->name; 187 p->name = src->name;
188 p->realname = src->realname; 188 p->realname = src->realname;
189 p->gpg_key = src->gpg_key; 189 p->gpg_key = src->gpg_key;
190 p->email = src->email; 190 p->email = src->email;
191 p->fpr = NULL; 191 p->fpr = NULL;
192 return p; 192 return p;
193} 193}
194 194
195struct uploader_info * 195struct uploader_info *
196uploader_find_frp (struct uploader_info *list, const char *fpr) 196uploader_find_frp (struct uploader_info *list, const char *fpr)
197{ 197{
diff --git a/src/wydawca.c b/src/wydawca.c
index cc1815b..36aa8b7 100644
--- a/src/wydawca.c
+++ b/src/wydawca.c
@@ -62,25 +62,25 @@ void
62syslog_printer (int prio, const char *fmt, va_list ap) 62syslog_printer (int prio, const char *fmt, va_list ap)
63{ 63{
64 if (syslog_include_prio) 64 if (syslog_include_prio)
65 { 65 {
66 static char *fmtbuf; 66 static char *fmtbuf;
67 static size_t fmtsize; 67 static size_t fmtsize;
68 const char *p = mu_syslog_priority_to_string (prio); 68 const char *p = mu_syslog_priority_to_string (prio);
69 size_t size = strlen (p) + 3 + strlen (fmt) + 1; 69 size_t size = strlen (p) + 3 + strlen (fmt) + 1;
70 70
71 if (size > fmtsize) 71 if (size > fmtsize)
72 { 72 {
73 fmtsize = size; 73 fmtsize = size;
74 fmtbuf = x2realloc (fmtbuf, &fmtsize); 74 fmtbuf = grecs_realloc (fmtbuf, fmtsize);
75 } 75 }
76 sprintf (fmtbuf, "[%s] %s", p, fmt); 76 sprintf (fmtbuf, "[%s] %s", p, fmt);
77 fmt = fmtbuf; 77 fmt = fmtbuf;
78 } 78 }
79 79
80#if HAVE_VSYSLOG 80#if HAVE_VSYSLOG
81 vsyslog (prio, fmt, ap); 81 vsyslog (prio, fmt, ap);
82#else 82#else
83 char buf[128]; 83 char buf[128];
84 vsnprintf (buf, sizeof buf, fmt, ap); 84 vsnprintf (buf, sizeof buf, fmt, ap);
85 syslog (prio, "%s", buf); 85 syslog (prio, "%s", buf);
86#endif 86#endif
@@ -170,35 +170,35 @@ stat_mask_p (unsigned long mask)
170 if (wydawca_stat[i] != 0 && (mask && STAT_MASK (i))) 170 if (wydawca_stat[i] != 0 && (mask && STAT_MASK (i)))
171 return 1; 171 return 1;
172 return 0; 172 return 0;
173} 173}
174 174
175static const char * 175static const char *
176stat_expand (struct metadef *def, void *data) 176stat_expand (struct metadef *def, void *data)
177{ 177{
178 size_t size = 0; 178 size_t size = 0;
179 def->storage = NULL; 179 def->storage = NULL;
180 if (grecs_asprintf (&def->storage, &size, "%u", 180 if (grecs_asprintf (&def->storage, &size, "%u",
181 wydawca_stat[(int) def->data])) 181 wydawca_stat[(int) def->data]))
182 xalloc_die (); 182 grecs_alloc_die ();
183 def->value = def->storage; 183 def->value = def->storage;
184 return def->value; 184 return def->value;
185} 185}
186 186
187struct metadef * 187struct metadef *
188make_stat_expansion (size_t count) 188make_stat_expansion (size_t count)
189{ 189{
190 int i; 190 int i;
191 struct metadef *def, *p; 191 struct metadef *def, *p;
192 def = xcalloc (MAX_STAT + count + 1, sizeof (def[0])); 192 def = grecs_calloc (MAX_STAT + count + 1, sizeof (def[0]));
193 p = def + count; 193 p = def + count;
194 for (i = 0; i < MAX_STAT; i++, p++) 194 for (i = 0; i < MAX_STAT; i++, p++)
195 { 195 {
196 p->kw = stat_kwname[i]; 196 p->kw = stat_kwname[i];
197 p->value = NULL; 197 p->value = NULL;
198 p->storage = NULL; 198 p->storage = NULL;
199 p->expand = stat_expand; 199 p->expand = stat_expand;
200 p->data = (void*) i; 200 p->data = (void*) i;
201 } 201 }
202 p->kw = NULL; 202 p->kw = NULL;
203 return def; 203 return def;
204} 204}
@@ -243,25 +243,25 @@ grecs_print_diag (grecs_locus_t *locus, int err, int errcode, const char *msg)
243} 243}
244 244
245 245
246static int uidc; 246static int uidc;
247static uid_t *uidv; 247static uid_t *uidv;
248 248
249static void 249static void
250collect_uids (int argc, char **argv) 250collect_uids (int argc, char **argv)
251{ 251{
252 int i; 252 int i;
253 253
254 uidc = argc; 254 uidc = argc;
255 uidv = xcalloc (uidc, sizeof (uidv[0])); 255 uidv = grecs_calloc (uidc, sizeof (uidv[0]));
256 for (i = 0; i < argc; i++) 256 for (i = 0; i < argc; i++)
257 { 257 {
258 struct passwd *pw = getpwnam (argv[i]); 258 struct passwd *pw = getpwnam (argv[i]);
259 if (!pw) 259 if (!pw)
260 { 260 {
261 char *p; 261 char *p;
262 unsigned n = strtoul (argv[i], &p, 10); 262 unsigned n = strtoul (argv[i], &p, 10);
263 if (*p) 263 if (*p)
264 { 264 {
265 logmsg (LOG_ERR, _("no such user: %s"), argv[i]); 265 logmsg (LOG_ERR, _("no such user: %s"), argv[i]);
266 exit (EX_NOUSER); 266 exit (EX_NOUSER);
267 } 267 }
diff --git a/src/wydawca.h b/src/wydawca.h
index 2307bad..94b7ee3 100644
--- a/src/wydawca.h
+++ b/src/wydawca.h
@@ -32,32 +32,31 @@
32#include <limits.h> 32#include <limits.h>
33#include <dirent.h> 33#include <dirent.h>
34#include <sys/stat.h> 34#include <sys/stat.h>
35#include <sys/socket.h> 35#include <sys/socket.h>
36#include <netinet/in.h> 36#include <netinet/in.h>
37#include <sys/un.h> 37#include <sys/un.h>
38#include <sys/wait.h> 38#include <sys/wait.h>
39#include <netdb.h> 39#include <netdb.h>
40#include <arpa/inet.h> 40#include <arpa/inet.h>
41#include <fcntl.h> 41#include <fcntl.h>
42#include <time.h> 42#include <time.h>
43#include <sysexits.h> 43#include <sysexits.h>
44#include <fnmatch.h>
45#include <regex.h>
44 46
45#include <mailutils/types.h> 47#include <mailutils/types.h>
46#include <mailutils/url.h> 48#include <mailutils/url.h>
47#include <mailutils/errno.h> 49#include <mailutils/errno.h>
48 50
49#include "error.h"
50#include "xalloc.h"
51#include "backupfile.h"
52#include "grecs.h" 51#include "grecs.h"
53#include "wordsplit.h" 52#include "wordsplit.h"
54 53
55#define SP(s) ((s) ? (s) : "NONE") 54#define SP(s) ((s) ? (s) : "NONE")
56 55
57#define WYDAWCA_EX_AGAIN 1 56#define WYDAWCA_EX_AGAIN 1
58 57
59/* The range of directive versions we accept (major * 100 + minor) */ 58/* The range of directive versions we accept (major * 100 + minor) */
60#define MIN_DIRECTIVE_VERSION 101 59#define MIN_DIRECTIVE_VERSION 101
61#define MAX_DIRECTIVE_VERSION 101 60#define MAX_DIRECTIVE_VERSION 101
62 61
63/* Default modes for mkdir and creat commands: rely on the umask value */ 62/* Default modes for mkdir and creat commands: rely on the umask value */
@@ -101,24 +100,39 @@ struct dictionary
101 to use; */ 100 to use; */
102 101
103 int init_passed; /* Initialization count */ 102 int init_passed; /* Initialization count */
104 char *result; /* Result storage */ 103 char *result; /* Result storage */
105 size_t result_size; /* Size of result */ 104 size_t result_size; /* Size of result */
106 unsigned ncol; /* Number of columns per row */ 105 unsigned ncol; /* Number of columns per row */
107 unsigned nrow; /* Number of rows */ 106 unsigned nrow; /* Number of rows */
108 107
109 void *storage; 108 void *storage;
110}; 109};
111 110
112 111
112enum backup_type
113 {
114 no_backups, /* Don't make backups */
115 simple_backups, /* Make only simple backups */
116 numbered_existing_backups,/* Make numbered backups for files that already
117 have such backups and simple backups for the
118 rest */
119 numbered_backups, /* Make only numbered backups */
120 };
121
122extern char const *simple_backup_suffix;
123
124char *find_backup_file_name (char const *, enum backup_type);
125
126
113/* Archive types */ 127/* Archive types */
114 128
115enum archive_type 129enum archive_type
116 { 130 {
117 archive_none, /* No archivation requested */ 131 archive_none, /* No archivation requested */
118 archive_directory, /* Archive by moving files to a separate directory 132 archive_directory, /* Archive by moving files to a separate directory
119 hierarchy */ 133 hierarchy */
120 archive_tar /* Archive by appending to a tar file (tar -r) */ 134 archive_tar /* Archive by appending to a tar file (tar -r) */
121 }; 135 };
122 136
123struct archive_descr 137struct archive_descr
124{ 138{
diff --git a/tests/.gitignore b/tests/.gitignore
index 7c8bd6b..1df6b71 100644
--- a/tests/.gitignore
+++ b/tests/.gitignore
@@ -1,11 +1,12 @@
1atconfig 1atconfig
2atlocal 2atlocal
3package.m4 3package.m4
4testsuite 4testsuite
5testsuite.dir 5testsuite.dir
6testsuite.log 6testsuite.log
7source 7source
8dest 8dest
9wstest 9wstest
10wsbatch 10wsbatch
11pushck 11pushck
12bkupname
diff --git a/tests/Makefile.am b/tests/Makefile.am
index b174fcd..cc52dbf 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -15,40 +15,44 @@
15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>. 15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>.
16 16
17EXTRA_DIST = $(TESTSUITE_AT) testsuite package.m4 dist 17EXTRA_DIST = $(TESTSUITE_AT) testsuite package.m4 dist
18DISTCLEANFILES = atconfig $(check_SCRIPTS) 18DISTCLEANFILES = atconfig $(check_SCRIPTS)
19MAINTAINERCLEANFILES = Makefile.in $(TESTSUITE) 19MAINTAINERCLEANFILES = Makefile.in $(TESTSUITE)
20SUBDIRS = etc 20SUBDIRS = etc
21 21
22## ------------ ## 22## ------------ ##
23## package.m4. ## 23## package.m4. ##
24## ------------ ## 24## ------------ ##
25 25
26$(srcdir)/package.m4: $(top_srcdir)/configure.ac 26$(srcdir)/package.m4: $(top_srcdir)/configure.ac
27 { \ 27 $(AM_V_GEN){ \
28 echo '# Signature of the current package.'; \ 28 echo '# Signature of the current package.'; \
29 echo 'm4_define([AT_PACKAGE_NAME], [@PACKAGE_NAME@])'; \ 29 echo 'm4_define([AT_PACKAGE_NAME], [@PACKAGE_NAME@])'; \
30 echo 'm4_define([AT_PACKAGE_TARNAME], [@PACKAGE_TARNAME@])'; \ 30 echo 'm4_define([AT_PACKAGE_TARNAME], [@PACKAGE_TARNAME@])'; \
31 echo 'm4_define([AT_PACKAGE_VERSION], [@PACKAGE_VERSION@])'; \ 31 echo 'm4_define([AT_PACKAGE_VERSION], [@PACKAGE_VERSION@])'; \
32 echo 'm4_define([AT_PACKAGE_STRING], [@PACKAGE_STRING@])'; \ 32 echo 'm4_define([AT_PACKAGE_STRING], [@PACKAGE_STRING@])'; \
33 echo 'm4_define([AT_PACKAGE_BUGREPORT], [@PACKAGE_BUGREPORT@])'; \ 33 echo 'm4_define([AT_PACKAGE_BUGREPORT], [@PACKAGE_BUGREPORT@])'; \
34 } >$(srcdir)/package.m4 34 } >$(srcdir)/package.m4
35 35
36# 36#
37 37
38## ------------ ## 38## ------------ ##
39## Test suite. ## 39## Test suite. ##
40## ------------ ## 40## ------------ ##
41 41
42TESTSUITE_AT = \ 42TESTSUITE_AT = \
43 backup00.at\
44 backup01.at\
45 backup02.at\
46 backup03.at\
43 check-fail.at\ 47 check-fail.at\
44 check-notify.at\ 48 check-notify.at\
45 check-ok.at\ 49 check-ok.at\
46 notify-upl.at\ 50 notify-upl.at\
47 mailstats.at\ 51 mailstats.at\
48 pushdir.at\ 52 pushdir.at\
49 testsuite.at\ 53 testsuite.at\
50 upload.at\ 54 upload.at\
51 upload-dry.at\ 55 upload-dry.at\
52 version.at\ 56 version.at\
53 wordsplit.at 57 wordsplit.at
54 58
@@ -64,18 +68,20 @@ atconfig: $(top_builddir)/config.status
64 cd $(top_builddir) && ./config.status tests/$@ 68 cd $(top_builddir) && ./config.status tests/$@
65 69
66clean-local: 70clean-local:
67 test ! -f $(TESTSUITE) || $(SHELL) $(TESTSUITE) --clean 71 test ! -f $(TESTSUITE) || $(SHELL) $(TESTSUITE) --clean
68 72
69check-local: atconfig atlocal $(TESTSUITE) 73check-local: atconfig atlocal $(TESTSUITE)
70 $(SHELL) $(TESTSUITE) 74 $(SHELL) $(TESTSUITE)
71 75
72# Run the test suite on the *installed* tree. 76# Run the test suite on the *installed* tree.
73#installcheck-local: 77#installcheck-local:
74 #$(SHELL) $(TESTSUITE) AUTOTEST_PATH=$(exec_prefix)/bin 78 #$(SHELL) $(TESTSUITE) AUTOTEST_PATH=$(exec_prefix)/bin
75 79
76check_PROGRAMS = wstest wsbatch pushck 80check_PROGRAMS = wstest wsbatch pushck bkupname
77INCLUDES = -I$(top_srcdir)/grecs/src -I$(top_srcdir)/gnu -I../gnu -I$(top_srcdir)/src 81INCLUDES = -I$(top_srcdir)/grecs/src -I$(top_srcdir)/src
78LDADD=../grecs/src/libgrecs.a ../gnu/libgnu.a 82LDADD=../grecs/src/libgrecs.a
79 83
80pushck_LDADD=../src/pushd.o 84pushck_LDADD=../src/pushd.o
85bkupname_LDADD=../src/backup.o ../grecs/src/libgrecs.a
86
81 87
diff --git a/tests/backup01.at b/tests/backup01.at
new file mode 100644
index 0000000..7cf4f93
--- a/dev/null
+++ b/tests/backup01.at
@@ -0,0 +1,33 @@
1# This file is part of wydawca testsuite -*- Autotest -*-
2# Copyright (C) 2009, 2010 Sergey Poznyakoff
3#
4# Wydawca is free software; you can redistribute it and/or modify
5# it under the terms of the GNU General Public License as published by
6# the Free Software Foundation; either version 3, or (at your option)
7# any later version.
8#
9# Wydawca is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details.
13#
14# You should have received a copy of the GNU General Public License
15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>.
16
17AT_SETUP(simple backups)
18AT_KEYWORDS([backup backup01 simple_backups])
19
20AT_CHECK([bkupname -simple a],
21[0],
22[a~
23])
24
25AT_CHECK([
26touch a
27bkupname -simple a
28],
29[0],
30[a~
31])
32
33AT_CLEANUP
diff --git a/tests/backup02.at b/tests/backup02.at
new file mode 100644
index 0000000..b5bcc54
--- a/dev/null
+++ b/tests/backup02.at
@@ -0,0 +1,43 @@
1# This file is part of wydawca testsuite -*- Autotest -*-
2# Copyright (C) 2009, 2010 Sergey Poznyakoff
3#
4# Wydawca is free software; you can redistribute it and/or modify
5# it under the terms of the GNU General Public License as published by
6# the Free Software Foundation; either version 3, or (at your option)
7# any later version.
8#
9# Wydawca is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details.
13#
14# You should have received a copy of the GNU General Public License
15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>.
16
17AT_SETUP(numbered backups)
18AT_KEYWORDS([backup backup02 numbered_backups])
19
20AT_CHECK([bkupname -numbered a],
21[0],
22[a.~1~
23])
24
25AT_CHECK([
26touch a.~1~
27bkupname -numbered a
28],
29[0],
30[a.~2~
31])
32
33AT_CHECK([
34touch a.~99~
35bkupname -numbered a
36],
37[0],
38[a.~100~
39])
40
41
42
43AT_CLEANUP
diff --git a/tests/backup03.at b/tests/backup03.at
new file mode 100644
index 0000000..947c145
--- a/dev/null
+++ b/tests/backup03.at
@@ -0,0 +1,41 @@
1# This file is part of wydawca testsuite -*- Autotest -*-
2# Copyright (C) 2009, 2010 Sergey Poznyakoff
3#
4# Wydawca is free software; you can redistribute it and/or modify
5# it under the terms of the GNU General Public License as published by
6# the Free Software Foundation; either version 3, or (at your option)
7# any later version.
8#
9# Wydawca is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details.
13#
14# You should have received a copy of the GNU General Public License
15# along with Wydawca. If not, see <http://www.gnu.org/licenses/>.
16
17AT_SETUP(numbered existing backups)
18AT_KEYWORDS([backup backup03 numbered_existing_backups])
19
20AT_CHECK([bkupname -existing a],
21[0],
22[a~
23])
24
25AT_CHECK([
26touch a.~1~
27bkupname -existing a
28],
29[0],
30[a.~2~
31])
32
33AT_CHECK([
34touch a.~99~
35bkupname -existing a
36],
37[0],
38[a.~100~
39])
40
41AT_CLEANUP
diff --git a/tests/bkupname.c b/tests/bkupname.c
new file mode 100644
index 0000000..6187146
--- a/dev/null
+++ b/tests/bkupname.c
@@ -0,0 +1,79 @@