sync

Backup service to store encrypted wallet databases (experimental)
Log | Files | Refs | Submodules | README | LICENSE

commit 2b93b4ad289ecc237cdcfbd853577320197611f3
parent 32c597ca33d3dfaa7e240b179ed21177e4a8bf16
Author: Martin Schanzenbach <schanzen@gnunet.org>
Date:   Sun, 12 Apr 2026 14:03:59 +0200

build: move from autotools to meson build

Diffstat:
M.gitignore | 2--
AMakefile.in | 49+++++++++++++++++++++++++++++++++++++++++++++++++
Mbootstrap | 4----
Aconfigure | 255+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Acontrib/meson.build | 9+++++++++
Mdebian/libsync-dev.install | 1+
Mdebian/rules | 5+----
Adoc/meson.build | 11+++++++++++
Aflake.lock | 94+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Aflake.nix | 108+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ameson.build | 358+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ameson.options | 5+++++
Ascripts/doxygen.meson.sh | 18++++++++++++++++++
Asrc/include/meson.build | 1+
Asrc/include/sync/meson.build | 9+++++++++
Asrc/include/sync/sync-database/meson.build | 15+++++++++++++++
Asrc/lib/meson.build | 39+++++++++++++++++++++++++++++++++++++++
Asrc/meson.build | 6++++++
Asrc/sync/meson.build | 56++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Asrc/syncdb/Makefile.sql | 10++++++++++
Asrc/syncdb/meson.build | 102+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Asrc/testing/meson.build | 73+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Asrc/util/meson.build | 38++++++++++++++++++++++++++++++++++++++
23 files changed, 1258 insertions(+), 10 deletions(-)

diff --git a/.gitignore b/.gitignore @@ -8,7 +8,6 @@ .deps/ .libs/ Makefile -Makefile.in aclocal.m4 autom4te.cache/ compile @@ -17,7 +16,6 @@ config.guess config.log config.status config.sub -configure contrib/uncrustify.sh depcomp doc/Makefile diff --git a/Makefile.in b/Makefile.in @@ -0,0 +1,49 @@ +# Build the program in the local tree +.PHONY: all +all: + $(NINJA) -C $(mesonbuilddir) + +# Install the program +.PHONY: install +install: all + $(MESON) install -C $(mesonbuilddir) + +# Remove files created during 'all' +.PHONY: clean +clean: + $(NINJA) -C $(mesonbuilddir) -t clean + +# Remove files created during 'install' +.PHONY: uninstall +uninstall: + $(NINJA) uninstall -C $(mesonbuilddir) + +# Make tarball +.PHONY: dist +dist: + $(MESON) dist -C $(mesonbuilddir) --no-tests --formats gztar + +# Make doxygen +.PHONY: doxygen +doxygen: + $(NINJA) -C $(mesonbuilddir) doxygen + +# Run tests +.PHONY: check +check: + $(MESON) test -C $(mesonbuilddir) + +.PHONY: installcheck +installcheck: + $(MESON) test -C $(mesonbuilddir) --suite=installcheck + +.PHONY: integrationtests +integrationtests: + $(MESON) test -C $(mesonbuilddir) --suite=integrationtests + +format: + $(MESON) fmt -i -r . + #find ./src -name "*.[h,c]" | uncrustify -l c -c contrib/conf/uncrustify.cfg -F - --replace --no-backup + +Makefile: Makefile.in + ./config.status diff --git a/bootstrap b/bootstrap @@ -25,7 +25,3 @@ if existence uncrustify; then else echo "Uncrustify not detected, hook not installed. Please install uncrustify if you plan on doing development" fi - - -echo "$0: Running autoreconf" -autoreconf -if diff --git a/configure b/configure @@ -0,0 +1,255 @@ +#!/bin/sh + +pkg_name="sync" +pkg_default_features="" +pkg_optional_features="coverage logging only-doc install-rpath" +pkg_optional_dependencies="" + +# DO NOT EDIT BELOW THIS LINE +standard_dirs="prefix exec_prefix bindir sbindir libexecdir sysconfdir sharedstatedir localstatedir runstatedir libdir includedir oldincludedir datarootdir datadir infodir localedir mandir docdir htmldir dvidir pdfdir psdir srcdir mesonbuilddir" +standard_utils="AR AS BISON CC CXX CPP FLEX INSTALL LD LDCONFIG LEX MAKE MAKEINFO RANLIB TEXI2DVI YACC CHGRP CHMOD CHOWN MKNOD RM NINJA MESON" +standard_flags="ARFLAGS BISONFLAGS CFLAGS CXXFLAGS CPPFLAGS FLEXFLAGS INSTALLFLAGS LDFLAGS LDCONFIGFLAGS LFLAGS MAKEFLAGS MAKEINFOFLAGS RANLIBFLAGS TEXI2DVIFLAGS YACCFLAGS CHGRPFLAGS CHMODFLAGS CHOWNFLAGS MKNODFLAGS" +standard_vars="INSTALL_DATA INSTALL_PROGRAM INSTALL_SCRIPT" +generated_comment="# This file was generated by configure. DO NOT edit it directly." + +# Save arguments +cat > config.status <<EOF +#!/bin/sh +$generated_comment +$0 $* +EOF +chmod 755 config.status + +# Parse arguments +oldifs="$IFS" +while [ "$#" -gt "0" ]; do + arg="$1" + shift + argsave="$@" + + IFS="=" + set -- $arg + IFS="$oldifs" + arg="$1" + shift + argparam="$@" + + case "$arg" in + --help|-h) + cat <<-EOF + Usage: $0 [options...] + General options: + + <variable>=<value> Overrides default utils and flags, e.g. CC=gcc + EOF + echo "" + echo "Directory variables:" + for sdir in $standard_dirs; do + echo "--$sdir=<directory>" + done + echo "" + echo "Options specific to $pkg_name:" + for feat in $pkg_optional_features; do + echo "--enable-$feat[=arg]" + done + for feat in $pkg_default_features; do + echo "--disable-$feat" + done + for dep in $pkg_optional_dependencies; do + echo "--with-$dep" + done + + echo + echo Other options will be ignored. Please see the README for additional information. + exit 0 + ;; + --enable-*) + for feat in $pkg_optional_features $pkg_default_features; do + ft=$(echo $feat | tr - _) + if [ "--enable-$feat" = "$arg" ] && [ -z "$argparam" ]; then + eval "enable_$ft=true" + elif [ "--enable-$feat" = "$arg" ]; then + if [ "$argparam" = "yes" ]; then + eval "enable_$ft=\"true\"" + else + eval "enable_$ft=\"$argparam\"" + fi + fi + done + ;; + --disable-*) + argsave="--enable-${arg#--disable-}=false $argsave" + ;; + --with-*) + for dep in $pkg_optional_dependencies; do + if [ "--with-$dep" = "$arg" ] && [ -z "$argparam" ]; then + eval "with_$dep=yes" + elif [ "--with-$dep" = "$arg" ]; then + eval "with_$dep=\"$argparam\"" + fi + done + ;; + --without-*) + argsave="--with-${arg#--without-}=no $argsave" + ;; + --*) + for dir in $standard_dirs; do + [ "--$dir" = "$arg" ] && eval "var_$dir=\"$argparam\"" + done + ;; + *) + for flag in $standard_utils $standard_flags standard_vars; do + [ "$flag" = "$arg" ] && eval "$flag=\"$argparam\"" + done + ;; + esac + + set -- $argsave +done + +# Set default values +for util in $standard_utils; do + case "$util" in + CPP) eval "$util=\"\${${util}:-\\\$(CC) -E}\"" ;; + CXX) eval "$util=\"\${${util}:-g++}\"" ;; + RM) eval "$util=\"\${${util}:-rm -f}\"" ;; + MESON) eval "$util=\"\${${util}:-meson}\"" ;; + NINJA) eval "$util=\"\${${util}:-ninja}\"" ;; + *) eval "$util=\"\${${util}:-${util}}\"" ;; + esac +done +for feat in $pkg_optional_features; do + ft=$(echo $feat | tr - _) + eval "enable_$ft=\${enable_$ft:-false}" +done +for feat in $pkg_default_features; do + eval "enable_$feat=\${enable_$feat:-true}" +done +for feat in $pkg_optional_dependencies; do + eval "with_$feat=\${with_$feat:-no}" +done + +# Find source files +if [ -z "$var_srcdir" ]; then + [ -f ../Makefile.in ] && var_srcdir=.. + [ -f ./Makefile.in ] && var_srcdir=. +fi +if [ -z "$var_srcdir" ]; then + echo "Source files not found. Please specify a directory using --srcdir=..." >&2 + exit 1 +fi + +# Write Makefile +cat > Makefile <<EOF +$generated_comment +SHELL = /bin/sh +VPATH = ${var_srcdir} + +mesonbuilddir = ${var_mesonbuilddir:-build} +srcdir = ${var_srcdir} +prefix = ${var_prefix:-/usr/local} +exec_prefix = ${var_exec_prefix:-\$(prefix)} +bindir = ${var_bindir:-\$(exec_prefix)/bin} +sbindir = ${var_sbindir:-\$(exec_prefix)/sbin} +libexecdir = ${var_libexecdir:-\$(exec_prefix)/libexec} +datarootdir = ${var_datarootdir:-\$(prefix)/share} +datadir = ${var_datadir:-\$(datarootdir)} +sysconfdir = ${var_sysconfdir:-\$(prefix)/etc} +sharedstatedir = ${var_sharedstatedir:-\$(prefix)/com} +localstatedir = ${var_localstatedir:-\$(prefix)/var} +runstatedir = ${var_runstatedir:-\$(localstatedir)/run} +includedir = ${var_includedir:-\$(prefix)/include} +oldincludedir = ${var_oldincludedir:-/usr/include} +docdir = ${var_docdir:-\$(datarootdir)/doc/"$pkg_name"} +infodir = ${var_infodir:-\$(datarootdir)/info} +htmldir = ${var_htmldir:-\$(docdir)} +dvidir = ${var_dvidir:-\$(docdir)} +pdfdir = ${var_pdfdir:-\$(docdir)} +psdir = ${var_psdir:-\$(docdir)} +libdir = ${var_libdir:-\$(exec_prefix)/lib} +lispdir = ${var_lispdir:-\$(datarootdir)/emacs/site-lisp} +localedir = ${var_localedir:-\$(datarootdir)/locale} +mandir = ${var_mandir:-\$(datarootdir)/man} +manext = .1 +EOF + +if [ -d ${var_mesonbuilddir:-build} ]; then + echo "${var_mesonbuilddir:-build} already exists, deleting with" + $RM -r ${var_mesonbuilddir:-build} || exit 1 +fi + +for var in $standard_utils $standard_flags $standard_vars; do + eval "echo \"${var} = \$${var}\" >> Makefile" +done +echo >> Makefile + +mesonfeatopts="" +for feat in $pkg_optional_features $pkg_default_features; do + ft=$(echo $feat | tr - _) + eval "echo \"enable_$ft=\${enable_$ft}\" >> Makefile" + if [ "coverage" = $feat ]; then + mfeat="b_$feat" + else + mfeat=$feat + fi + eval "mesonfeatopts=\"$mesonfeatopts -D$mfeat=\${enable_$ft}\"" +done +for dep in $pkg_optional_dependencies; do + eval "echo \"with_$dep=\${with_$dep}\" >> Makefile" +done +echo >> Makefile + +cat "${var_srcdir}/Makefile.in" >> Makefile + +# Create default targets, if not already present +default_target() { + grep "^$1:" Makefile >/dev/null && return + echo ".PHONY: $1" >> Makefile + echo "$1: $2" >> Makefile + cat >> Makefile + echo >> Makefile +} + +#default_target Makefile <<EOF +# ./config.status +#EOF +for format in html dvi pdf ps; do + default_target "$format" </dev/null + default_target "install-$format" "$format" </dev/null +done +default_target check </dev/null +default_target mostlyclean clean </dev/null +default_target distclean clean <<EOF + \$(RM) Makefile config.status +EOF +default_target maintainer-clean distclean </dev/null +default_target install-strip <<EOF + \$(MAKE) INSTALL_PROGRAM='\$(INSTALL_PROGRAM) -s' \\ + INSTALL_SCRIPT='\$(INSTALL_SCRIPT)' install +EOF + +mesondiropts="" +for dr in $standard_dirs; do + if [ $dr = "srcdir" ]; then + continue + fi + if [ $dr = "mesonbuilddir" ]; then + continue + fi + eval "vn=\${var_$dr}" + if [ ! -z $vn ]; then + eval "mesondiropts=\"$mesondiropts -D$dr=\${var_$dr}\"" + fi +done + +${MESON} setup \ + -Ddefault_library=shared \ + $mesondiropts \ + $mesonfeatopts \ + ${var_mesonbuilddir:-build} \ + ${var_srcdir} || exit 1 + +# Done +echo "Package $pkg_name configured successfully." +echo "Run 'make' to build and 'make install' to install the package" + diff --git a/contrib/meson.build b/contrib/meson.build @@ -0,0 +1,9 @@ +# This build file is in the public domain. + +configure_file( + input: 'sync-dbconfig', + output: 'sync-dbconfig', + configuration: cdata, + install: true, + install_dir: get_option('bindir'), +) diff --git a/debian/libsync-dev.install b/debian/libsync-dev.install @@ -1,2 +1,3 @@ usr/include/sync/* usr/lib/*/libsync* +usr/lib/*/pkgconfig/*.pc diff --git a/debian/rules b/debian/rules @@ -5,14 +5,11 @@ SHELL := sh -e include /usr/share/dpkg/architecture.mk %: - dh ${@} + dh ${@} --buildsystem=meson override_dh_builddeb: dh_builddeb -- -Zgzip -override_dh_auto_configure-arch: - dh_auto_configure -- --disable-rpath --with-microhttpd=yes $(shell dpkg-buildflags --export=configure) - override_dh_auto_configure-indep: override_dh_auto_build-indep: diff --git a/doc/meson.build b/doc/meson.build @@ -0,0 +1,11 @@ +# This build file is in the public domain + +install_man( + [ + 'prebuilt' / 'man' / 'sync-config.1', + 'prebuilt' / 'man' / 'sync-dbconfig.1', + 'prebuilt' / 'man' / 'sync-dbinit.1', + 'prebuilt' / 'man' / 'sync-httpd.1', + 'prebuilt' / 'man' / 'sync.conf.5', + ], +) diff --git a/flake.lock b/flake.lock @@ -0,0 +1,94 @@ +{ + "nodes": { + "gnunet": { + "inputs": { + "nixpkgs": "nixpkgs", + "systems": "systems" + }, + "locked": { + "lastModified": 1774899416, + "narHash": "sha256-YcGma1gX/t76xDv9DW71nKkWFhzXYz3NkN/WEceHbZM=", + "ref": "refs/heads/master", + "rev": "7c6b613e37e301b0e81fb94af5878d00c98e5b75", + "revCount": 33194, + "submodules": true, + "type": "git", + "url": "https://git.gnunet.org/gnunet" + }, + "original": { + "rev": "7c6b613e37e301b0e81fb94af5878d00c98e5b75", + "type": "git", + "url": "https://git.gnunet.org/gnunet" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1774799055, + "narHash": "sha256-Tsq9BCz0q47ej1uFF39m4tuhcwru/ls6vCCJzutEpaw=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "107cba9eb4a8d8c9f8e9e61266d78d340867913a", + "type": "github" + }, + "original": { + "id": "nixpkgs", + "ref": "release-25.11", + "type": "indirect" + } + }, + "nixpkgs_2": { + "locked": { + "lastModified": 1775988051, + "narHash": "sha256-QMoWRyJFUTEVVaidgVsVk6RfNj2MFSKVUvZhO+oYkNU=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "9cd23560868d3d1c5721858b2b7fe72ce251ca6d", + "type": "github" + }, + "original": { + "id": "nixpkgs", + "ref": "release-25.11", + "type": "indirect" + } + }, + "root": { + "inputs": { + "gnunet": "gnunet", + "nixpkgs": "nixpkgs_2", + "systems": "systems_2" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + }, + "systems_2": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix @@ -0,0 +1,108 @@ +{ + inputs = { + nixpkgs.url = "nixpkgs/release-25.11"; + systems.url = "github:nix-systems/default"; + gnunet.url = "git+https://git.gnunet.org/gnunet?rev=7c6b613e37e301b0e81fb94af5878d00c98e5b75"; + self.submodules = true; + }; + + outputs = { self, nixpkgs, gnunet, systems, ... } @ inputs: + let + supportedSystems = [ "x86_64-linux" "x86_64-darwin" "aarch64-linux" "aarch64-darwin" ]; + forEachSystem = nixpkgs.lib.genAttrs supportedSystems; + nixpkgsFor = forEachSystem (system: import nixpkgs { inherit system; }); + in + { + # This defines (installable) package derivations + # For use in flakes that use this flake as input in order + # to specify/use this package from git as a dependency + packages = forEachSystem (system: + let + pkgs = nixpkgsFor.${system}; + gnunetpkgs = gnunet.packages.${system}; + in { + gnunet = pkgs.stdenv.mkDerivation { + name = "sync"; + src = ./.; + nativeBuildInputs = [ + pkgs.gnumake + pkgs.automake + pkgs.autoconf + pkgs.pkg-config + pkgs.python3 + pkgs.texinfo + ]; + buildInputs = [ + pkgs.libtool + pkgs.jansson + pkgs.git + pkgs.gettext + pkgs.postgresql + (pkgs.python3.withPackages (python-pkgs: [ + python-pkgs.jinja2 + ])) + pkgs.libmicrohttpd + pkgs.libsodium + pkgs.libgcrypt + pkgs.libunistring + pkgs.curlWithGnuTls + pkgs.jq + gnunetpkgs.gnunet + ]; + preConfigure = '' + patchShebangs --build contrib/check-prebuilt + ./bootstrap + ''; + }; + } + ); + defaultPackage = forEachSystem (system: self.packages.${system}.gnunet); + # This defines a development shell in which you can compile + # (and use) exchange + devShells = forEachSystem + (system: + let + pkgs = nixpkgsFor.${system}; + gnunetpkgs = gnunet.packages.${system}; + in + { + default = pkgs.mkShell { + packages = [ + pkgs.gcc + pkgs.meson + pkgs.ninja + pkgs.gnumake + pkgs.pkg-config + pkgs.libtool + pkgs.jansson + pkgs.git + pkgs.postgresql + pkgs.curlWithGnuTls + gnunetpkgs.gnunet + pkgs.codespell + pkgs.clang-tools + pkgs.uncrustify + pkgs.jq #probably not needed + ]; + + shellHook = '' + echo "taler-sync environment loaded." + export CC=gcc + export CFLAGS="-O" + mkdir -p default + export PGHOST=localhost + export PGPORT=5432 + export PGUSER=$USER + export PGDATABASE=talercheck + export PGDATA="$PWD/default/.pg" + echo $PWD + [ ! -d $PGDATA ] && PGHOST="$PGDATA" pg_ctl initdb -o "-U $PGUSER" + + pg_ctl -o "-p $PGPORT -k $PGDATA" start && createdb talercheck && { + trap 'pg_ctl stop && rm -r $PGDATA' EXIT + } + ''; + }; + }); + }; +} diff --git a/meson.build b/meson.build @@ -0,0 +1,358 @@ +project( + 'sync', + 'c', + license: 'AGPLv3', + meson_version: '>=1.1.0', + version: '1.5.12', +) + +cc = meson.get_compiler('c') +incdir = include_directories('src/include') + +# Used to populate gnunet_private_config.h +private_config = configuration_data() + +pkgcfgdir = get_option('datadir') / 'taler-sync' / 'config.d' +docdir = get_option('datadir') / 'doc' / 'taler-sync' + +if get_option('install-rpath') + rpath_option = get_option('prefix') / get_option('libdir') +else + rpath_option = '' +endif + +install_emptydir(docdir) +install_data('README', 'COPYING', install_dir: docdir) + +gnunet_user = false +dpkg_architecture_bin = find_program( + 'dpkg-architecture', + '/usr/bin/getent', + required: false, +) +if dpkg_architecture_bin.found() + private_config.set( + 'MULTIARCH', + dpkg_architecture_bin.full_path() + ' -qDEB_HOST_MULTIARCH', + ) +endif + +TALER_PLUGIN_LDFLAGS = [ + '-export-dynamic', + '-avoid-version', + '-module', + '--no-undefined', +] + +cdata = configuration_data() +if not get_option('only-doc') + add_project_arguments( + '-Wall', + '-Wno-address-of-packed-member', + language: 'c', + ) + taler_lib_ldflags = '-export-dynamic -no-undefined' + + check_headers = ['stdint.h', 'stdlib.h', 'string.h', 'unistd.h'] + + foreach h : check_headers + if cc.check_header(h) + define = 'HAVE_' + h.underscorify().to_upper() + message(define) + private_config.set(define, 1) + endif + endforeach + + + mhd_dep = dependency('libmicrohttpd', required: false) + if not mhd_dep.found() + mhd_dep = cc.find_library('microhttpd', required: true) + endif + + mhd2_dep = dependency('libmicrohttpd2', required: false) + if not mhd2_dep.found() + mhd_dep2 = cc.find_library('microhttpd2', required: false) + endif + + json_dep = dependency('jansson', required: false) + if not json_dep.found() + json_dep = cc.find_library('jansson', required: true) + endif + + gcrypt_dep = dependency('libgcrypt', required: false) + if not gcrypt_dep.found() + gcrypt_dep = cc.find_library('gcrypt', required: true) + endif + + private_config.set_quoted('NEED_LIBGCRYPT_VERSION', '1.6.1') + + gnunetutil_dep = dependency('gnunetutil', required: false) + if not gnunetutil_dep.found() + gnunetutil_dep = cc.find_library('gnunetutil', required: true) + endif + + cc.has_header_symbol( + 'gnunet/gnunet_util_lib.h', + 'GNUNET_TIME_round_up', + dependencies: [gnunetutil_dep], + required: true, + ) + + gnunetjson_dep = dependency('gnunetjson', required: false) + if not gnunetjson_dep.found() + gnunetjson_dep = cc.find_library('gnunetjson', required: true) + endif + + gnunetmhd_dep = dependency('gnunetmhd', required: false) + if not gnunetmhd_dep.found() + gnunetmhd_dep = cc.find_library('gnunetmhd', required: true) + endif + cc.has_header_symbol( + 'gnunet/gnunet_mhd_lib.h', + 'GNUNET_MHD_post_parser', + dependencies: [gnunetmhd_dep], + required: true, + ) + + curl_dep = dependency('libcurl', version: '>=7.34.0', required: false) + if not curl_dep.found() + curl_dep = cc.find_library('curl', required: true) + curl_version_check = '''#include <curl/curl.h> + int main(int argc, char **argv) { + #if LIBCURL_VERSION_NUM < 0x073400 + #error "cURL version >= 7.34.0 required" + #endif + return 0; + } + ''' + if not cc.compiles( + curl_version_check, + name: 'cURL version check', + dependencies: curl_dep, + ) + error('cURL version >=7.34.0 required') + endif + endif + + gnunetcurl_dep = dependency('gnunetcurl', required: false) + if not gnunetcurl_dep.found() + gnunetcurl_dep = cc.find_library('gnunetcurl', required: true) + endif + cc.has_header_symbol( + 'gnunet/gnunet_curl_lib.h', + 'GNUNET_CURL_get_select_info', + dependencies: [gnunetcurl_dep], + required: true, + ) + + pq_dep = dependency('libpq', required: false) + if not pq_dep.found() + pq_dep = cc.find_library('pq', required: true) + endif + + gnunetpq_dep = dependency('gnunetpq', required: false) + if not gnunetpq_dep.found() + gnunetpq_dep = cc.find_library('gnunetpq', required: true) + endif + cc.has_header_symbol( + 'gnunet/gnunet_pq_lib.h', + 'GNUNET_PQ_query_param_blind_sign_priv', + required: true, + dependencies: [pq_dep, gnunetpq_dep], + ) + private_config.set10('HAVE_GNUNETPQ', gnunetpq_dep.found()) + + talerutil_dep = dependency('talerutil', required: false) + if not talerutil_dep.found() + talerutil_dep = cc.find_library('talerutil', required: true) + endif + cc.has_header_symbol( + 'taler/taler_util.h', + 'TALER_merchant_instance_auth_hash_with_salt', + required: true, + dependencies: [talerutil_dep], + ) + private_config.set10('HAVE_TALERUTIL', talerutil_dep.found()) + + talercurl_dep = dependency('talercurl', required: false) + if not talercurl_dep.found() + talercurl_dep = cc.find_library('talercurl', required: true) + endif + talerkyclogic_dep = dependency('talerkyclogic', required: false) + if not talerkyclogic_dep.found() + talerkyclogic_dep = cc.find_library('talerkyclogic', required: true) + endif + talerbank_dep = dependency('talerbank', required: false) + if not talerbank_dep.found() + talerbank_dep = cc.find_library('talerbank', required: true) + endif + talerfakebank_dep = dependency('talerfakebank', required: false) + if not talerfakebank_dep.found() + talerfakebank_dep = cc.find_library('talerfakebank', required: false) + endif + talertemplating_dep = dependency('talertemplating', required: false) + if not talertemplating_dep.found() + talertemplating_dep = cc.find_library('talertemplating', required: true) + endif + talertesting_dep = dependency('talertesting', required: false) + if not talertesting_dep.found() + talertesting_dep = cc.find_library('talertesting', required: true) + endif + + talerexchange_dep = dependency('talerexchange', required: false) + if not talerexchange_dep.found() + talerexchange_dep = cc.find_library('talerexchange', required: true) + endif + cc.has_header_symbol( + 'taler/taler_exchange_service.h', + 'TALER_EXCHANGE_keys_test_account_allowed', + required: true, + dependencies: [talerexchange_dep], + ) + private_config.set10('HAVE_TALEREXCHANGE', talerexchange_dep.found()) + + talermhd_dep = dependency('talermhd', required: false) + if not talermhd_dep.found() + talermhd_dep = cc.find_library('talermhd', required: true) + endif + cc.has_header_symbol( + 'taler/taler_mhd_lib.h', + 'TALER_MHD_parse_request_arg_rel_time', + required: true, + dependencies: [talermhd_dep], + ) + private_config.set10('HAVE_TALERMHD', talermhd_dep.found()) + + + talerjson_dep = dependency('talerjson', required: false) + if not talerjson_dep.found() + talerjson_dep = cc.find_library('talerjson', required: true) + endif + cc.has_header_symbol( + 'taler/taler_json_lib.h', + 'TALER_JSON_currency_specs_to_json', + required: true, + dependencies: [talerjson_dep], + ) + private_config.set10('HAVE_TALERJSON', talerjson_dep.found()) + + + talerpq_dep = dependency('talerpq', required: false) + if not talerpq_dep.found() + talerpq_dep = cc.find_library('talerpq', required: true) + endif + cc.has_header_symbol( + 'taler/taler_pq_lib.h', + 'TALER_PQ_query_param_array_blinded_denom_sig', + required: true, + dependencies: [talerpq_dep], + ) + private_config.set10('HAVE_TALERPQ', talerpq_dep.found()) + + talermerchant_dep = dependency('talermerchant', required: false) + if not talermerchant_dep.found() + talermerchant_dep = cc.find_library('talermerchant', required: true) + endif + cc.has_header_symbol( + 'taler/taler_merchant_service.h', + 'TALER_MERCHANT_get_private_order_create', + required: true, + dependencies: [talermerchant_dep], + ) + talermerchanttesting_dep = dependency( + 'talermerchanttesting', + required: false, + ) + if not talermerchanttesting_dep.found() + talermerchanttesting_dep = cc.find_library( + 'talermerchanttesting', + required: true, + ) + endif + m_dep = cc.find_library('m', required: false) + if m_dep.found() + private_config.set('HAVE_LIBM', 1) + endif + + + logging_opt = get_option('logging') + logging_verbosity = 0 + + if logging_opt == 'yes' + logging_verbosity = 1 + endif + if logging_opt == 'no' + add_project_arguments('-DGNUNET_CULL_LOGGING=1', language: 'c') + endif + if logging_opt == 'verbose' + logging_verbosity = 2 + endif + if logging_opt == 'veryverbose' + logging_verbosity = 3 + endif + + libltversions = [ + ['libsync', '0:1:0'], + ['libsyncutil', '0:1:0'], + ['libsynctesting', '0:1:0'], + ['libsyncdb', '1:0:0'], + ] + + solibversions = {} + + foreach libversion : libltversions + ltversion = libversion[1].split(':') + current = ltversion[0].to_int() + revision = ltversion[1].to_int() + age = ltversion[2].to_int() + soversion_str = '@0@'.format(current - age) + ltversion_str = '@0@.@1@.@2@'.format(current - age, age, revision) + solibversions = solibversions + { + libversion[0]: { + 'soversion': soversion_str, + 'version': ltversion_str, + }, + } + endforeach + + private_config.set_quoted('PACKAGE_VERSION', meson.project_version()) + # Compatibility. Used in source. + private_config.set_quoted('VERSION', meson.project_version()) + private_config.set_quoted('VCS_VERSION', 'mesonbuild') + private_config.set_quoted('PACKAGE_BUGREPORT', 'taler@gnu.org') + configure_file(output: 'taler_sync_config.h', configuration: private_config) + configuration_inc = include_directories('.') + + cdata.merge_from(private_config) + add_project_arguments('-DHAVE_CONFIG_H', language: 'c') + + pkg = import('pkgconfig') + subdir('contrib') + subdir('src') + if not get_option('disable-doc') + subdir('doc') + endif + + taler_prefix = get_option('prefix') / get_option('libdir') + + add_test_setup( + 'default', + env: ['TALER_SYNC_PREFIX=' + taler_prefix], + exclude_suites: ['perf', 'installcheck', 'integrationtests'], + is_default: true, + ) +else + subdir('contrib') + if not get_option('disable-doc') + subdir('doc') + endif +endif + +run_target( + 'doxygen', + command: 'scripts/doxygen.meson.sh', + env: {'PACKAGE_VERSION': meson.project_version()}, +) + +#meson.add_dist_script('meson-dist-script') + diff --git a/meson.options b/meson.options @@ -0,0 +1,5 @@ +# Build options +option('only-doc', type : 'boolean', value : false, description: 'whether to compile documentation ONLY') +option('disable-doc', type : 'boolean', value : false, description: 'whether to disable documentation') +option('install-rpath', type : 'boolean', value : false, description: 'Add rpath to installed binaries if set') +option('logging', type : 'string', value: 'yes', description: 'Log setting. Can be set to "yes" (logging, default), "no" (no logging), "verbose" (extra logging"), "veryverbose" (even more logging)') diff --git a/scripts/doxygen.meson.sh b/scripts/doxygen.meson.sh @@ -0,0 +1,18 @@ +#!/bin/sh + +# This is more portable than `which' but comes with +# the caveat of not(?) properly working on busybox's ash: +existence() +{ + type "$1" >/dev/null 2>&1 +} + +if ! existence doxygen; then + echo "Doxygen not found" + exit 1 +fi +cd "${MESON_SOURCE_ROOT}/doc/doxygen" +echo "PROJECT_NUMBER = ${PACKAGE_VERSION}" > version.doxy +make all + +echo "Doxygen files generated into ${MESON_SOURCE_ROOT}/doc/doxygen!" diff --git a/src/include/meson.build b/src/include/meson.build @@ -0,0 +1 @@ +subdir('sync') diff --git a/src/include/sync/meson.build b/src/include/sync/meson.build @@ -0,0 +1,9 @@ +subdir('sync-database') + +install_data( + 'sync_database_lib.h', + 'sync_service.h', + 'sync_testing_lib.h', + 'sync_util.h', + install_dir: get_option('includedir') / 'sync', +) diff --git a/src/include/sync/sync-database/meson.build b/src/include/sync/sync-database/meson.build @@ -0,0 +1,15 @@ +install_data( + 'create_tables.h', + 'common.h', + 'drop_tables.h', + 'gc.h', + 'increment_lifetime_TR.h', + 'lookup_account_TR.h', + 'lookup_backup_TR.h', + 'lookup_pending_payments_by_account_TR.h', + 'preflight.h', + 'store_backup_TR.h', + 'store_payment_TR.h', + 'update_backup_TR.h', + install_dir: get_option('includedir') / 'sync' / 'sync-database', +) diff --git a/src/lib/meson.build b/src/lib/meson.build @@ -0,0 +1,39 @@ +# This build file is in the public domain + +libsync_la_SOURCES = [ + 'sync_api_curl_defaults.c', + 'sync_api_download.c', + 'sync_api_upload.c', +] + +libsync = library( + 'sync', + libsync_la_SOURCES, + soversion: solibversions['libsync']['soversion'], + version: solibversions['libsync']['soversion'], + install_rpath: rpath_option, + dependencies: [ + talerutil_dep, + talercurl_dep, + talerjson_dep, + gnunetutil_dep, + gnunetjson_dep, + gnunetcurl_dep, + talerutil_dep, + talerjson_dep, + json_dep, + curl_dep, + ], + include_directories: [incdir, configuration_inc], + install: true, + install_dir: get_option('libdir'), +) + +libsync_dep = declare_dependency(link_with: libsync) +pkg.generate( + libsync, + url: 'https://taler.net', + description: 'GNU Taler sync library', +) + + diff --git a/src/meson.build b/src/meson.build @@ -0,0 +1,6 @@ +subdir('include') +subdir('util') +subdir('syncdb') +subdir('sync') +subdir('lib') +subdir('testing') diff --git a/src/sync/meson.build b/src/sync/meson.build @@ -0,0 +1,56 @@ +# This build file is in the public domain +install_data('sync.conf', install_dir: pkgcfgdir) + +executable( + 'sync-httpd', + [ + 'sync-httpd.c', + 'sync-httpd_backup.c', + 'sync-httpd_backup_post.c', + 'sync-httpd_config.c', + 'sync-httpd_mhd.c', + ], + dependencies: [ + libsyncutil_dep, + libsyncdb_dep, + talerutil_dep, + talerjson_dep, + talermerchant_dep, + talermhd_dep, + gnunetutil_dep, + gnunetjson_dep, + gnunetcurl_dep, + mhd_dep, + json_dep, + ], + include_directories: [incdir, configuration_inc], + install: true, +) + +if mhd2_dep.found() + executable( + 'sync-httpd2', + [ + 'sync-httpd2.c', + 'sync-httpd2_backup.c', + 'sync-httpd2_backup_post.c', + 'sync-httpd2_config.c', + 'sync-httpd2_mhd.c', + ], + dependencies: [ + libsyncutil_dep, + libsyncdb_dep, + talerutil_dep, + talerjson_dep, + talermerchant_dep, + talermhd_dep, + gnunetutil_dep, + gnunetjson_dep, + gnunetcurl_dep, + mhd2_dep, + json_dep, + ], + include_directories: [incdir, configuration_inc], + install: true, + ) +endif diff --git a/src/syncdb/Makefile.sql b/src/syncdb/Makefile.sql @@ -0,0 +1,10 @@ +procedures.sql: procedures.sql.in syncdb_*_TR.sql + gcc -E -P -undef - < procedures.sql.in 2>/dev/null | sed -e "s/--.*//" | awk 'NF' - >$@ + +CLEANFILES = \ + procedures.sql + +all: ${CLEANFILES} + +clean: + rm ${CLEANFILES} diff --git a/src/syncdb/meson.build b/src/syncdb/meson.build @@ -0,0 +1,102 @@ +# This build file is in the public domain +install_data('sync_db_postgres.conf', install_dir: pkgcfgdir) + +sqldir = get_option('datadir') / 'sync' / 'sql' + +# FIXME possibly provide this output in the tgz through dist script +run_command('make', '-f', 'Makefile.sql', 'all', check: true) + +sqlfiles = ['versioning.sql', 'procedures.sql', 'sync-0001.sql', 'drop.sql'] + +install_data(sources: sqlfiles, install_dir: sqldir) + +# This makes meson copy the files into the build directory for testing +foreach f : sqlfiles + configure_file(input: f, output: f, copy: true) +endforeach + + +libsyncdb_SOURCES = [ + 'syncdb_pg.c', + 'syncdb_drop_tables.c', + 'syncdb_create_tables.c', + 'syncdb_preflight.c', + 'syncdb_gc.c', + 'syncdb_store_payment_TR.c', + 'syncdb_lookup_pending_payments_by_account_TR.c', + 'syncdb_store_backup_TR.c', + 'syncdb_update_backup_TR.c', + 'syncdb_lookup_account_TR.c', + 'syncdb_lookup_backup_TR.c', + 'syncdb_increment_lifetime_TR.c', +] +libsyncdb = library( + 'syncdb', + libsyncdb_SOURCES, + soversion: solibversions['libsyncdb']['soversion'], + version: solibversions['libsyncdb']['soversion'], + install_rpath: rpath_option, + dependencies: [ + libsyncutil_dep, + talerpq_dep, + talerutil_dep, + gnunetutil_dep, + gnunetpq_dep, + pq_dep, + ], + include_directories: [incdir, configuration_inc], + install: true, + install_dir: get_option('libdir'), +) + +libsyncdb_dep = declare_dependency(link_with: libsyncdb) +pkg.generate( + libsyncdb, + url: 'https://taler.net', + description: 'GNU Taler sync DB library', +) + +executable( + 'sync-dbinit', + ['sync-dbinit.c'], + dependencies: [ + libsyncutil_dep, + talerutil_dep, + libsyncdb_dep, + talerpq_dep, + gnunetutil_dep, + gnunetpq_dep, + pq_dep, + gcrypt_dep, + ], + include_directories: [incdir, configuration_inc], + install: true, +) + + +test_syncdb_postgres = executable( + 'test-syncdb-postgres', + ['test_sync_db.c'], + install_rpath: rpath_option, + dependencies: [ + libsyncdb_dep, + libsyncutil_dep, + talerutil_dep, + gnunetutil_dep, + gnunetpq_dep, + ], + include_directories: [incdir, configuration_inc], + install: false, +) +test( + 'test-syncdb-postgres', + test_syncdb_postgres, + workdir: meson.current_build_dir(), + suite: ['syncdb', 'installcheck'], + is_parallel: false, +) +configure_file( + input: 'test_sync_db_postgres.conf', + output: 'test_sync_db_postgres.conf', + copy: true, +) diff --git a/src/testing/meson.build b/src/testing/meson.build @@ -0,0 +1,73 @@ +# This build file is in the public domain +libsynctesting = library( + 'synctesting', + [ + 'testing_api_cmd_backup_download.c', + 'testing_api_cmd_backup_upload.c', + 'testing_api_traits.c', + ], + soversion: solibversions['libsynctesting']['soversion'], + version: solibversions['libsynctesting']['soversion'], + install_rpath: rpath_option, + dependencies: [ + libsync_dep, + talermerchant_dep, + talerutil_dep, + talerexchange_dep, + talerjson_dep, + talertesting_dep, + gnunetjson_dep, + gnunetutil_dep, + gnunetcurl_dep, + json_dep, + ], + include_directories: [incdir, configuration_inc], + install: true, + install_dir: get_option('libdir'), +) + +libsynctesting_dep = declare_dependency(link_with: libsynctesting) +pkg.generate( + libsynctesting, + url: 'https://taler.net', + description: 'GNU Taler sync testing library', +) + + +test_sync_api = executable( + 'test_sync_api', + ['test_sync_api.c'], + install_rpath: rpath_option, + dependencies: [ + libsync_dep, + libsynctesting_dep, + talerutil_dep, + talerjson_dep, + talermerchant_dep, + talerexchange_dep, + talerbank_dep, + talerfakebank_dep, + talermerchanttesting_dep, + talertesting_dep, + gnunetutil_dep, + gnunetjson_dep, + gnunetcurl_dep, + json_dep, + ], + include_directories: [incdir, configuration_inc], + install: false, +) +test( + 'test_sync_api', + test_sync_api, + workdir: meson.current_build_dir(), + suite: ['testing', 'installcheck'], + is_parallel: false, +) +configure_file( + input: 'test_sync_api.conf', + output: 'test_sync_api.conf', + copy: true, +) + +subdir('test_sync_api_home' / '.local' / 'share' / 'taler' / 'exchange-offline') diff --git a/src/util/meson.build b/src/util/meson.build @@ -0,0 +1,38 @@ +# This build file is in the public domain +configure_file( + input: 'paths.conf', + output: 'paths.conf', + configuration: cdata, + install: true, + install_dir: pkgcfgdir, +) + + +libsyncutil = library( + 'syncutil', + ['os_installation.c'], + soversion: solibversions['libsyncutil']['soversion'], + version: solibversions['libsyncutil']['soversion'], + install_rpath: rpath_option, + dependencies: [gnunetutil_dep], + include_directories: [incdir, configuration_inc], + install: true, + install_dir: get_option('libdir'), +) + +libsyncutil_dep = declare_dependency(link_with: libsyncutil) +pkg.generate( + libsyncutil, + url: 'https://taler.net', + description: 'GNU Taler sync utilities library', +) + +executable( + 'sync-config', + ['sync-config.c'], + dependencies: [libsyncutil_dep, gnunetutil_dep], + include_directories: [incdir, configuration_inc], + install: true, +) + +