On Mon, Nov 3, 2025 at 7:14 PM Tom Lane <[email protected]> wrote: > "Tristan Partin" <[email protected]> writes: > > What is the benefit of -Dextra_include_dirs when you could use -Dc_flags > > or CFLAGS to specify extra include directories? If you tried either of > > those as an alternative, would they fix the issue? The existence of the > > option goes all the way back to the initial commit of the meson port, so > > I presume it exists to mirror --with-includes, but why does that exist?
Good questions. Sounds plausible and probably more conventional. It doesn't work right now but probably only for superficial reasons. But I also worry about hiding current or future problems and generally being too blunt. But that's also true of -Dextra_XXX. > --with-includes, and likewise --with-libs, exist because there are > platforms that require it. For example, on pretty much any > BSD-derived system, the core /usr/include and /usr/lib files are very > limited and you'll need to point at places like /usr/pkg/include or > /opt/local/include or whatever to pull in non-core packages. Yeah. I for one cargo-culted that configure habit across to the new world, but you can actually build without -Dextra_XXX on FreeBSD and maybe macOS + MacPorts too with -Dnls=disabled, as long as your $PATH contains pkg-config (FreeBSD: yes by default, macOS: probably yes if you can type "meson"). NetBSD handles even -Dnls=enabled thanks to its built-in libintl, as CI already demonstrates. So I wonder if we have this only because out-of-libc libintl and pkg-config have some unresolved beef[1][2]...? Know of any other complications in our universe or libraries that I might be overlooking? If that really is the last reason we need this on typical package-managed non-Linux environments (not sure!)... here's an experimental patch that probes the conventional paths relative to msgfmt to hunt for them. They were all compiled from the same source package by the same packaging pipeline so I think it has pretty good odds. It's not quite $PATH -> pkg-config -> .pc -> exact results, but it's ... well, something vaguely similar, instead of nothing. Too crazy an overreaching assumption, or friendly out-of-the-box support for lots of common systems including Macs? It passes on all CI OSes. No loss if it guesses wrong on your DeathStation 9000: you can still supply -Dextra_XXX as before. On the flip side, if you stop using a "catch-all" include path, you have to declare dependencies accurately or some combinations might break, for example that gssapi I had to add, because the CI macOS task found Apple's base system OpenSSL and then didn't think it needed any extra includes, because we forgot to say that libpq_oauth_st also depends on gssapi. That's an example of a "broad" -Dextra_include_dirs hiding something that is technically incorrect, or being forgiving depending on your perspective... First two patches as before, except for a couple of unnecessary hunks I deleted based on an off-list review from Bilal. [1] https://lists.gnu.org/archive/html/bug-gettext/2012-03/msg00022.html [2] https://lists.nongnu.org/archive/html/bug-gettext/2019-10/msg00003.html
From 172ebde3ea93a9c9bd3db8a134cd873ca3daedda Mon Sep 17 00:00:00 2001 From: Thomas Munro <[email protected]> Date: Mon, 14 Jul 2025 11:54:00 +1200 Subject: [PATCH v4 1/4] meson: Fix libpq header include order. Don't allow external copies of libpq-fe.h to hide the in-tree libpq's headers. libpq is now always declared as the first dependency, so that it can arrange for libpq_inc to be searched before extra_include_dirs, c_flags or system/ports include directory discovered by Meson. This is mostly a mechanical change to multiple dependency lists. A separate commit will add a CI check to prevent future mistakes. This clearly didn't affect many people, maybe just me (Thomas), but it could have broken on basically any non-Linux system that happened to install a libpq-with-headers package. Back-patch to 16, where meson arrived. Reviewed-by: Heikki Linnakangas <[email protected]> Reviewed-by: Bilal Yavuz <[email protected]> Reviewed-by: Tristan Partin <[email protected]> Discussion: https://postgr.es/m/CA+hUKGKispvxLyrBn3=3mp0BB1N+RBYR5eE2guCOksnwEoOcPQ@mail.gmail.com --- contrib/dblink/meson.build | 2 +- contrib/oid2name/meson.build | 2 +- contrib/postgres_fdw/meson.build | 2 +- contrib/vacuumlo/meson.build | 2 +- src/backend/replication/libpqwalreceiver/meson.build | 2 +- src/bin/initdb/meson.build | 2 +- src/bin/pg_amcheck/meson.build | 2 +- src/bin/pg_basebackup/meson.build | 4 ++-- src/bin/pg_ctl/meson.build | 2 +- src/bin/pg_dump/meson.build | 8 ++++---- src/bin/pg_rewind/meson.build | 2 +- src/bin/pg_upgrade/meson.build | 2 +- src/bin/pg_verifybackup/meson.build | 2 +- src/bin/pgbench/meson.build | 2 +- src/bin/psql/meson.build | 2 +- src/bin/scripts/meson.build | 8 ++++---- src/fe_utils/meson.build | 2 +- src/interfaces/ecpg/ecpglib/meson.build | 6 +++--- src/interfaces/ecpg/include/meson.build | 2 +- src/interfaces/ecpg/test/meson.build | 4 ++-- src/interfaces/ecpg/test/thread/meson.build | 2 +- src/interfaces/libpq/test/meson.build | 4 ++-- src/test/isolation/meson.build | 4 ++-- src/test/modules/libpq_pipeline/meson.build | 2 +- src/test/modules/oauth_validator/meson.build | 2 +- src/test/modules/test_escape/meson.build | 2 +- src/test/modules/test_int128/meson.build | 2 +- src/test/modules/test_json_parser/meson.build | 2 +- src/test/regress/meson.build | 2 +- 29 files changed, 41 insertions(+), 41 deletions(-) diff --git a/contrib/dblink/meson.build b/contrib/dblink/meson.build index a19ce6cf4b9..28da26d3d45 100644 --- a/contrib/dblink/meson.build +++ b/contrib/dblink/meson.build @@ -13,7 +13,7 @@ endif dblink = shared_module('dblink', dblink_sources, kwargs: contrib_mod_args + { - 'dependencies': contrib_mod_args['dependencies'] + [libpq], + 'dependencies': [libpq] + contrib_mod_args['dependencies'], }, ) contrib_targets += dblink diff --git a/contrib/oid2name/meson.build b/contrib/oid2name/meson.build index 074f16acd72..dd958f00bdf 100644 --- a/contrib/oid2name/meson.build +++ b/contrib/oid2name/meson.build @@ -12,7 +12,7 @@ endif oid2name = executable('oid2name', oid2name_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) contrib_targets += oid2name diff --git a/contrib/postgres_fdw/meson.build b/contrib/postgres_fdw/meson.build index aac89ffdde8..a2890251d69 100644 --- a/contrib/postgres_fdw/meson.build +++ b/contrib/postgres_fdw/meson.build @@ -17,7 +17,7 @@ endif postgres_fdw = shared_module('postgres_fdw', postgres_fdw_sources, kwargs: contrib_mod_args + { - 'dependencies': contrib_mod_args['dependencies'] + [libpq], + 'dependencies': [libpq] + contrib_mod_args['dependencies'], }, ) contrib_targets += postgres_fdw diff --git a/contrib/vacuumlo/meson.build b/contrib/vacuumlo/meson.build index deee1d2832d..51e8fe9a325 100644 --- a/contrib/vacuumlo/meson.build +++ b/contrib/vacuumlo/meson.build @@ -12,7 +12,7 @@ endif vacuumlo = executable('vacuumlo', vacuumlo_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) contrib_targets += vacuumlo diff --git a/src/backend/replication/libpqwalreceiver/meson.build b/src/backend/replication/libpqwalreceiver/meson.build index 2150f31cfa3..5318a76e29d 100644 --- a/src/backend/replication/libpqwalreceiver/meson.build +++ b/src/backend/replication/libpqwalreceiver/meson.build @@ -14,7 +14,7 @@ libpqwalreceiver = shared_module('pqwalreceiver', libpqwalreceiver_sources, kwargs: pg_mod_args + { 'name_prefix': 'lib', - 'dependencies': pg_mod_args['dependencies'] + [libpq], + 'dependencies': [libpq] + pg_mod_args['dependencies'], } ) diff --git a/src/bin/initdb/meson.build b/src/bin/initdb/meson.build index 06958e370f3..b8584fe56de 100644 --- a/src/bin/initdb/meson.build +++ b/src/bin/initdb/meson.build @@ -21,7 +21,7 @@ initdb = executable('initdb', # shared library from a different PG version. Define # USE_PRIVATE_ENCODING_FUNCS to ensure that that happens. c_args: ['-DUSE_PRIVATE_ENCODING_FUNCS'], - dependencies: [frontend_code, libpq, icu, icu_i18n], + dependencies: [libpq, frontend_code, icu, icu_i18n], kwargs: default_bin_args, ) bin_targets += initdb diff --git a/src/bin/pg_amcheck/meson.build b/src/bin/pg_amcheck/meson.build index 316ea0d40b8..c8f792ff971 100644 --- a/src/bin/pg_amcheck/meson.build +++ b/src/bin/pg_amcheck/meson.build @@ -12,7 +12,7 @@ endif pg_amcheck = executable('pg_amcheck', pg_amcheck_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += pg_amcheck diff --git a/src/bin/pg_basebackup/meson.build b/src/bin/pg_basebackup/meson.build index 3a7fc10eab0..b85ba465d47 100644 --- a/src/bin/pg_basebackup/meson.build +++ b/src/bin/pg_basebackup/meson.build @@ -7,7 +7,7 @@ common_sources = files( 'walmethods.c', ) -pg_basebackup_deps = [frontend_code, libpq, lz4, zlib, zstd] +pg_basebackup_deps = [libpq, frontend_code, lz4, zlib, zstd] pg_basebackup_common = static_library('libpg_basebackup_common', common_sources, dependencies: pg_basebackup_deps, @@ -45,7 +45,7 @@ endif pg_createsubscriber = executable('pg_createsubscriber', pg_createsubscriber_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += pg_createsubscriber diff --git a/src/bin/pg_ctl/meson.build b/src/bin/pg_ctl/meson.build index e92ba50f8a3..4f4a977dc0f 100644 --- a/src/bin/pg_ctl/meson.build +++ b/src/bin/pg_ctl/meson.build @@ -12,7 +12,7 @@ endif pg_ctl = executable('pg_ctl', pg_ctl_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += pg_ctl diff --git a/src/bin/pg_dump/meson.build b/src/bin/pg_dump/meson.build index f3c669f484e..2264ed9faa9 100644 --- a/src/bin/pg_dump/meson.build +++ b/src/bin/pg_dump/meson.build @@ -22,7 +22,7 @@ pg_dump_common_sources = files( pg_dump_common = static_library('libpgdump_common', pg_dump_common_sources, c_pch: pch_postgres_fe_h, - dependencies: [frontend_code, libpq, lz4, zlib, zstd], + dependencies: [libpq, frontend_code, lz4, zlib, zstd], kwargs: internal_lib_args, ) @@ -42,7 +42,7 @@ endif pg_dump = executable('pg_dump', pg_dump_sources, link_with: [pg_dump_common], - dependencies: [frontend_code, libpq, zlib], + dependencies: [libpq, frontend_code, zlib], kwargs: default_bin_args, ) bin_targets += pg_dump @@ -61,7 +61,7 @@ endif pg_dumpall = executable('pg_dumpall', pg_dumpall_sources, link_with: [pg_dump_common], - dependencies: [frontend_code, libpq, zlib], + dependencies: [libpq, frontend_code, zlib], kwargs: default_bin_args, ) bin_targets += pg_dumpall @@ -80,7 +80,7 @@ endif pg_restore = executable('pg_restore', pg_restore_sources, link_with: [pg_dump_common], - dependencies: [frontend_code, libpq, zlib], + dependencies: [libpq, frontend_code, zlib], kwargs: default_bin_args, ) bin_targets += pg_restore diff --git a/src/bin/pg_rewind/meson.build b/src/bin/pg_rewind/meson.build index 97f001d94a5..f241f37673c 100644 --- a/src/bin/pg_rewind/meson.build +++ b/src/bin/pg_rewind/meson.build @@ -21,7 +21,7 @@ endif pg_rewind = executable('pg_rewind', pg_rewind_sources, - dependencies: [frontend_code, libpq, lz4, zstd], + dependencies: [libpq, frontend_code, lz4, zstd], c_args: ['-DFRONTEND'], # needed for xlogreader et al kwargs: default_bin_args, ) diff --git a/src/bin/pg_upgrade/meson.build b/src/bin/pg_upgrade/meson.build index ac992f0d14b..8aefaeea91f 100644 --- a/src/bin/pg_upgrade/meson.build +++ b/src/bin/pg_upgrade/meson.build @@ -28,7 +28,7 @@ endif pg_upgrade = executable('pg_upgrade', pg_upgrade_sources, c_pch: pch_postgres_fe_h, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += pg_upgrade diff --git a/src/bin/pg_verifybackup/meson.build b/src/bin/pg_verifybackup/meson.build index f45ea790d8e..7aaee24bd79 100644 --- a/src/bin/pg_verifybackup/meson.build +++ b/src/bin/pg_verifybackup/meson.build @@ -13,7 +13,7 @@ endif pg_verifybackup = executable('pg_verifybackup', pg_verifybackup_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += pg_verifybackup diff --git a/src/bin/pgbench/meson.build b/src/bin/pgbench/meson.build index a2a909a8442..de013cc9827 100644 --- a/src/bin/pgbench/meson.build +++ b/src/bin/pgbench/meson.build @@ -27,7 +27,7 @@ endif pgbench = executable('pgbench', pgbench_sources, - dependencies: [frontend_code, libpq, thread_dep], + dependencies: [libpq, frontend_code, thread_dep], include_directories: include_directories('.'), c_pch: pch_postgres_fe_h, c_args: host_system == 'windows' ? ['-DFD_SETSIZE=1024'] : [], diff --git a/src/bin/psql/meson.build b/src/bin/psql/meson.build index d344053c23b..4749d751aa8 100644 --- a/src/bin/psql/meson.build +++ b/src/bin/psql/meson.build @@ -58,7 +58,7 @@ psql = executable('psql', psql_sources, c_pch: pch_postgres_fe_h, include_directories: include_directories('.'), - dependencies: [frontend_code, libpq, readline], + dependencies: [libpq, frontend_code, readline], kwargs: default_bin_args, ) bin_targets += psql diff --git a/src/bin/scripts/meson.build b/src/bin/scripts/meson.build index a4fed59d1c9..d422ca542f9 100644 --- a/src/bin/scripts/meson.build +++ b/src/bin/scripts/meson.build @@ -2,7 +2,7 @@ scripts_common = static_library('libscripts_common', files('common.c'), - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: internal_lib_args, ) @@ -28,7 +28,7 @@ foreach binary : binaries binary = executable(binary, binary_sources, link_with: [scripts_common], - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += binary @@ -36,7 +36,7 @@ endforeach vacuuming_common = static_library('libvacuuming_common', files('common.c', 'vacuuming.c'), - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: internal_lib_args, ) @@ -55,7 +55,7 @@ foreach binary : binaries binary = executable(binary, binary_sources, link_with: [vacuuming_common], - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args, ) bin_targets += binary diff --git a/src/fe_utils/meson.build b/src/fe_utils/meson.build index ddac3c3a658..0a65b973779 100644 --- a/src/fe_utils/meson.build +++ b/src/fe_utils/meson.build @@ -32,7 +32,7 @@ fe_utils_sources += psqlscan fe_utils = static_library('libpgfeutils', fe_utils_sources, c_pch: pch_postgres_fe_h, - include_directories: [postgres_inc, libpq_inc], + include_directories: [libpq_inc, postgres_inc], c_args: host_system == 'windows' ? ['-DFD_SETSIZE=1024'] : [], dependencies: frontend_common_code, kwargs: default_lib_args, diff --git a/src/interfaces/ecpg/ecpglib/meson.build b/src/interfaces/ecpg/ecpglib/meson.build index 8f478c6a73e..fb7d33d2a0e 100644 --- a/src/interfaces/ecpg/ecpglib/meson.build +++ b/src/interfaces/ecpg/ecpglib/meson.build @@ -30,7 +30,7 @@ ecpglib_st = static_library('libecpg', include_directories: ecpglib_inc, c_args: ecpglib_c_args, c_pch: pch_postgres_fe_h, - dependencies: [frontend_stlib_code, thread_dep, libpq], + dependencies: [libpq, frontend_stlib_code, thread_dep], link_with: [ecpg_pgtypes_st], kwargs: default_lib_args, ) @@ -41,7 +41,7 @@ ecpglib_so = shared_library('libecpg', include_directories: ecpglib_inc, c_args: ecpglib_c_args, c_pch: pch_postgres_fe_h, - dependencies: [frontend_shlib_code, libpq, thread_dep], + dependencies: [libpq, frontend_shlib_code, thread_dep], link_with: ecpg_pgtypes_so, soversion: host_system != 'windows' ? '6' : '', darwin_versions: ['6', '6.' + pg_version_major.to_string()], @@ -58,7 +58,7 @@ pkgconfig.generate( url: pg_url, libraries: ecpglib_so, libraries_private: [frontend_stlib_code, thread_dep], - requires_private: ['libpgtypes', 'libpq'], + requires_private: ['libpq', 'libpgtypes'], ) subdir('po', if_found: libintl) diff --git a/src/interfaces/ecpg/include/meson.build b/src/interfaces/ecpg/include/meson.build index a6541e1a686..133ebe2f11f 100644 --- a/src/interfaces/ecpg/include/meson.build +++ b/src/interfaces/ecpg/include/meson.build @@ -1,6 +1,6 @@ # Copyright (c) 2022-2025, PostgreSQL Global Development Group -ecpg_inc = include_directories('.') +ecpg_inc = [libpq_inc, include_directories('.')] ecpg_conf_keys = [ 'SIZEOF_LONG', diff --git a/src/interfaces/ecpg/test/meson.build b/src/interfaces/ecpg/test/meson.build index 4ccdf9d295a..0d48e035e5a 100644 --- a/src/interfaces/ecpg/test/meson.build +++ b/src/interfaces/ecpg/test/meson.build @@ -20,7 +20,7 @@ pg_regress_ecpg = executable('pg_regress_ecpg', pg_regress_ecpg_sources, c_args: pg_regress_cflags, include_directories: [pg_regress_inc, include_directories('.')], - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install': false }, @@ -30,7 +30,7 @@ ecpg_test_dependencies += pg_regress_ecpg # create .c files and executables from .pgc files ecpg_test_exec_kw = { 'c_args': cflags_no_missing_var_decls, - 'dependencies': [frontend_code, libpq], + 'dependencies': [libpq, frontend_code], 'include_directories': [ecpg_inc], 'link_with': [ecpglib_so, ecpg_compat_so, ecpg_pgtypes_so], 'build_by_default': false, diff --git a/src/interfaces/ecpg/test/thread/meson.build b/src/interfaces/ecpg/test/thread/meson.build index 6a6745ce0fc..2c34a611898 100644 --- a/src/interfaces/ecpg/test/thread/meson.build +++ b/src/interfaces/ecpg/test/thread/meson.build @@ -18,6 +18,6 @@ foreach pgc_file : pgc_files ecpg_test_dependencies += executable(pgc_file, exe_input, - kwargs: ecpg_test_exec_kw + {'dependencies': [frontend_code, libpq, thread_dep,]}, + kwargs: ecpg_test_exec_kw + {'dependencies': [libpq, frontend_code, thread_dep,]}, ) endforeach diff --git a/src/interfaces/libpq/test/meson.build b/src/interfaces/libpq/test/meson.build index 07a5facc321..75d2012ba17 100644 --- a/src/interfaces/libpq/test/meson.build +++ b/src/interfaces/libpq/test/meson.build @@ -14,7 +14,7 @@ endif libpq_test_deps += executable('libpq_uri_regress', libpq_uri_regress_sources, - dependencies: [frontend_no_fe_utils_code, libpq], + dependencies: [libpq, frontend_no_fe_utils_code], kwargs: default_bin_args + { 'install': false, } @@ -33,7 +33,7 @@ endif libpq_test_deps += executable('libpq_testclient', libpq_testclient_sources, - dependencies: [frontend_no_fe_utils_code, libpq], + dependencies: [libpq, frontend_no_fe_utils_code], kwargs: default_bin_args + { 'install': false, } diff --git a/src/test/isolation/meson.build b/src/test/isolation/meson.build index a180e4e2741..660b11eff8b 100644 --- a/src/test/isolation/meson.build +++ b/src/test/isolation/meson.build @@ -35,7 +35,7 @@ pg_isolation_regress = executable('pg_isolation_regress', isolation_sources, c_args: pg_regress_cflags, include_directories: pg_regress_inc, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install_dir': dir_pgxs / 'src/test/isolation', }, @@ -52,7 +52,7 @@ endif isolationtester = executable('isolationtester', isolationtester_sources, include_directories: include_directories('.'), - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install_dir': dir_pgxs / 'src/test/isolation', }, diff --git a/src/test/modules/libpq_pipeline/meson.build b/src/test/modules/libpq_pipeline/meson.build index 3fd70a04a38..83201111ca3 100644 --- a/src/test/modules/libpq_pipeline/meson.build +++ b/src/test/modules/libpq_pipeline/meson.build @@ -12,7 +12,7 @@ endif libpq_pipeline = executable('libpq_pipeline', libpq_pipeline_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install': false, }, diff --git a/src/test/modules/oauth_validator/meson.build b/src/test/modules/oauth_validator/meson.build index a6f937fd7d7..2cd5c4cd537 100644 --- a/src/test/modules/oauth_validator/meson.build +++ b/src/test/modules/oauth_validator/meson.build @@ -60,7 +60,7 @@ endif oauth_hook_client = executable('oauth_hook_client', oauth_hook_client_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install': false, }, diff --git a/src/test/modules/test_escape/meson.build b/src/test/modules/test_escape/meson.build index a21341d5067..04fd0be0889 100644 --- a/src/test/modules/test_escape/meson.build +++ b/src/test/modules/test_escape/meson.build @@ -10,7 +10,7 @@ endif test_escape = executable('test_escape', test_escape_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install': false, } diff --git a/src/test/modules/test_int128/meson.build b/src/test/modules/test_int128/meson.build index 4c2be7a0326..94bca2edc5c 100644 --- a/src/test/modules/test_int128/meson.build +++ b/src/test/modules/test_int128/meson.build @@ -12,7 +12,7 @@ endif test_int128 = executable('test_int128', test_int128_sources, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install': false, }, diff --git a/src/test/modules/test_json_parser/meson.build b/src/test/modules/test_json_parser/meson.build index 5672045f496..2c6031a14df 100644 --- a/src/test/modules/test_json_parser/meson.build +++ b/src/test/modules/test_json_parser/meson.build @@ -23,7 +23,7 @@ test_json_parser_incremental = executable('test_json_parser_incremental', # the shared-library flavor of jsonapi. test_json_parser_incremental_shlib = executable('test_json_parser_incremental_shlib', test_json_parser_incremental_sources, - dependencies: [frontend_shlib_code, libpq], + dependencies: [libpq, frontend_shlib_code], c_args: ['-DJSONAPI_SHLIB_ALLOC'], link_with: [common_excluded_shlib], kwargs: default_bin_args + { diff --git a/src/test/regress/meson.build b/src/test/regress/meson.build index 1da9e9462a9..3fe900d5847 100644 --- a/src/test/regress/meson.build +++ b/src/test/regress/meson.build @@ -30,7 +30,7 @@ endif pg_regress = executable('pg_regress', regress_sources, c_args: pg_regress_cflags, - dependencies: [frontend_code, libpq], + dependencies: [libpq, frontend_code], kwargs: default_bin_args + { 'install_dir': dir_pgxs / 'src/test/regress', }, -- 2.51.1
From 3ed517c7904666e1f9dcf45171ffa2684126eb2f Mon Sep 17 00:00:00 2001 From: Thomas Munro <[email protected]> Date: Mon, 3 Nov 2025 11:32:57 +1300 Subject: [PATCH v4 2/4] ci: Test include path order with canary libpq-fe.h. If the build script would allow libpq-fe.h installed under --with-includes (configure) or -Dextra_include_dirs (meson) to hide the in-tree header, it will now reach an #error in contrived error on CI. This tests that libpq is ordered correctly for all code that includes the header. The list of canary headers could be extended in future. Also add missing set -e to the shell scripts run under su, since otherwise the build step would confusingly succeed despite not completing. Reviewed-by: Bilal Yavuz <[email protected]> Discussion: https://postgr.es/m/CA%2BhUKG%2Bx-cys30%3D7L2B8%3DcZ%2B-z6QDOj-oQy9O3CnkeXnrnm3OQ%40mail.gmail.com --- .cirrus.tasks.yml | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/.cirrus.tasks.yml b/.cirrus.tasks.yml index f2581cfb2e5..3df6de6acd9 100644 --- a/.cirrus.tasks.yml +++ b/.cirrus.tasks.yml @@ -424,6 +424,8 @@ task: CCACHE_DIR: /tmp/ccache_dir DEBUGINFOD_URLS: "https://debuginfod.debian.net" + POISONED_HEADERS: /tmp/poisoned_headers + # Enable a reasonable set of sanitizers. Use the linux task for that, as # it's one of the fastest tasks (without sanitizers). Also several of the # sanitizers work best on linux. @@ -492,11 +494,24 @@ task: #apt-get update #DEBIAN_FRONTEND=noninteractive apt-get -y install ... + # Detect mistakes that would allow unwanted headers from outside our tree be + # found with --with-includes or -Dextra_include_dirs. That is primarily a + # risk on non-Linux systems that install packages under eg /usr/local that + # must be explicitly added to the header search path, but this is a + # convenient place to test both build systems. + setup_poisoned_headers_script: | + for header in "libpq-fe.h" "libpq/libpq-fe.h" ; do + mkdir -p "${POISONED_HEADERS}/$(dirname $header)" + echo '#error "external header hides in-tree header"' \ + > "${POISONED_HEADERS}/$header" + done + matrix: # SPECIAL: # - Uses address sanitizer, sanitizer failures are typically printed in # the server log # - Configures postgres with a small segment size + # - Poisoned headers in search path - name: Linux - Debian Bookworm - Autoconf env: @@ -517,6 +532,7 @@ task: --with-segsize-blocks=6 \ --with-libnuma \ --with-liburing \ + --with-includes="${POISONED_HEADERS}" \ \ ${LINUX_CONFIGURE_FEATURES} \ \ @@ -540,6 +556,7 @@ task: # - Test both 64bit and 32 bit builds # - uses io_method=io_uring # - Uses meson feature autodetection + # - Poisoned headers in search path - name: Linux - Debian Bookworm - Meson env: @@ -552,6 +569,7 @@ task: su postgres <<-EOF meson setup \ ${MESON_COMMON_PG_CONFIG_ARGS} \ + -Dextra_include_dirs="${POISONED_HEADERS}" \ --buildtype=debug \ ${LINUX_MESON_FEATURES} -Dllvm=enabled \ build @@ -564,6 +582,7 @@ task: export CC='ccache gcc -m32' meson setup \ ${MESON_COMMON_PG_CONFIG_ARGS} \ + -Dextra_include_dirs="${POISONED_HEADERS}" \ --buildtype=debug \ --pkg-config-path /usr/lib/i386-linux-gnu/pkgconfig/ \ -DPERL=perl5.36-i386-linux-gnu \ @@ -573,12 +592,14 @@ task: build_script: | su postgres <<-EOF + set -e ninja -C build -j${BUILD_JOBS} ${MBUILD_TARGET} ninja -C build -t missingdeps EOF build_32_script: | su postgres <<-EOF + set -e ninja -C build-32 -j${BUILD_JOBS} ${MBUILD_TARGET} ninja -C build -t missingdeps EOF -- 2.51.1
From 290bf24a89a075f3380c7e9af03d357475718887 Mon Sep 17 00:00:00 2001 From: Thomas Munro <[email protected]> Date: Tue, 4 Nov 2025 03:09:22 +1300 Subject: [PATCH v4 3/4] meson: Try to find libintl without -Dextra_XXX. Since libintl is the only dependency that Meson can't usually find via pkg-config on typical non-Linux Unix systems, let's try a bit harder to find it with existing clues. We typically find msgfmt in $PATH, so we can plausibly guess that the library and headers are installed in the same prefix, and then try that before giving up and requiring a manual path configuration. This revealed some missing dependency declarations previously covered by the catch-all extra_includes_dir, added here. XXX Is this a terrible idea for some reason? --- meson.build | 34 +++++++++++++++++++++----- src/backend/jit/llvm/meson.build | 5 +++- src/interfaces/libpq-oauth/meson.build | 1 + src/port/meson.build | 6 ++--- 4 files changed, 36 insertions(+), 10 deletions(-) diff --git a/meson.build b/meson.build index 0f61ff6a700..2690d7a7b2b 100644 --- a/meson.build +++ b/meson.build @@ -2973,6 +2973,7 @@ cdata.set_quoted('PG_VERSION_STR', nlsopt = get_option('nls') libintl = not_found_dep +libintl_include_dirs = [] if not nlsopt.disabled() # otherwise there'd be lots of @@ -2982,7 +2983,7 @@ if not nlsopt.disabled() # meson 0.59 has this wrapped in dependency('intl') if (msgfmt.found() and - cc.check_header('libintl.h', required: nlsopt, + cc.check_header('libintl.h', args: test_c_args, include_directories: postgres_inc)) # in libc @@ -2990,13 +2991,34 @@ if not nlsopt.disabled() libintl = declare_dependency() else libintl = cc.find_library('intl', - has_headers: ['libintl.h'], required: nlsopt, + has_headers: ['libintl.h'], header_include_directories: postgres_inc, dirs: test_lib_d) endif endif + if (msgfmt.found() and not libintl.found()) + # libintl doesn't provide libintl.pc, but since we found its companion + # binary msgfmt we have a solid clue where to look, assuming standard + # layout within the install prefix. + guess_libintl_prefix = fs.parent(fs.parent(msgfmt.full_path())) + guess_libintl_lib_d = guess_libintl_prefix / 'lib' + guess_libintl_include = guess_libintl_prefix / 'include' + guess_libintl_include_dirs = include_directories(guess_libintl_include) + libintl_lib = cc.find_library('intl', + has_headers: ['libintl.h'], + header_include_directories: guess_libintl_include_dirs, + dirs: guess_libintl_lib_d) + if libintl_lib.found() + libintl = declare_dependency(dependencies: libintl_lib, + include_directories: guess_libintl_include_dirs) + libintl_include_dirs += guess_libintl_include # needed for llvmjit_types.bc + endif + endif + if libintl.found() + cc.check_header('libintl.h', required: nlsopt, + args: test_c_args, include_directories: postgres_inc, dependencies: libintl) i18n = import('i18n') cdata.set('ENABLE_NLS', 1) endif @@ -3220,14 +3242,14 @@ subdir('config') frontend_port_code = declare_dependency( compile_args: ['-DFRONTEND'], include_directories: [postgres_inc], - dependencies: os_deps, + dependencies: [os_deps, libintl] ) backend_port_code = declare_dependency( compile_args: ['-DBUILDING_DLL'], include_directories: [postgres_inc], sources: [errcodes], # errcodes.h is needed due to use of ereport - dependencies: os_deps, + dependencies: [os_deps, libintl] ) subdir('src/port') @@ -3236,14 +3258,14 @@ frontend_common_code = declare_dependency( compile_args: ['-DFRONTEND'], include_directories: [postgres_inc], sources: generated_headers_stamp, - dependencies: [os_deps, zlib, zstd, lz4], + dependencies: [os_deps, libintl, zlib, zstd, lz4], ) backend_common_code = declare_dependency( compile_args: ['-DBUILDING_DLL'], include_directories: [postgres_inc], sources: generated_headers_stamp, - dependencies: [os_deps, zlib, zstd], + dependencies: [os_deps, libintl, zlib, zstd], ) subdir('src/common') diff --git a/src/backend/jit/llvm/meson.build b/src/backend/jit/llvm/meson.build index 805fbd69006..bcc5efed8a2 100644 --- a/src/backend/jit/llvm/meson.build +++ b/src/backend/jit/llvm/meson.build @@ -32,7 +32,7 @@ endif llvmjit = shared_module('llvmjit', llvmjit_sources, kwargs: pg_mod_args + { - 'dependencies': pg_mod_args['dependencies'] + [llvm], + 'dependencies': pg_mod_args['dependencies'] + [llvm, libintl], 'cpp_args': pg_mod_args['cpp_args'] + llvm.get_variable(configtool: 'cxxflags').split(), } ) @@ -69,6 +69,9 @@ bitcode_cflags += '-I@BUILD_ROOT@/src/include' bitcode_cflags += '-I@BUILD_ROOT@/src/backend/utils/misc' bitcode_cflags += '-I@SOURCE_ROOT@/src/include' +foreach d : libintl_include_dirs + bitcode_cflags += ['-I' + d] +endforeach # Note this is intentionally not installed to bitcodedir, as it's not for # inlining diff --git a/src/interfaces/libpq-oauth/meson.build b/src/interfaces/libpq-oauth/meson.build index 505e1671b86..9d7fa1bc67c 100644 --- a/src/interfaces/libpq-oauth/meson.build +++ b/src/interfaces/libpq-oauth/meson.build @@ -29,6 +29,7 @@ libpq_oauth_st = static_library('libpq-oauth', frontend_stlib_code, libpq_oauth_deps, ssl, # libpq-int.h includes OpenSSL headers + gssapi, # and gssapi ], kwargs: default_lib_args, ) diff --git a/src/port/meson.build b/src/port/meson.build index fc7b059fee5..9c4f5459e0a 100644 --- a/src/port/meson.build +++ b/src/port/meson.build @@ -154,14 +154,14 @@ endif pgport = {} pgport_variants = { '_srv': internal_lib_args + { - 'dependencies': [backend_port_code], + 'dependencies': [backend_port_code, libintl], }, '': default_lib_args + { - 'dependencies': [frontend_port_code], + 'dependencies': [frontend_port_code, libintl], }, '_shlib': default_lib_args + { 'pic': true, - 'dependencies': [frontend_port_code], + 'dependencies': [frontend_port_code, libintl], }, } -- 2.51.1
From e553e694574113cd0ddf9b07af7ebc8bbaa8e246 Mon Sep 17 00:00:00 2001 From: Thomas Munro <[email protected]> Date: Tue, 4 Nov 2025 12:47:41 +1300 Subject: [PATCH v4 4/4] ci: Remove -Dextra_XXX on FreeBSD and macOS. Since FreeBSD and MacPorts install .pc files for the libraries want, Meson can find them. The only exception is libintl, which the previous commit handled specially. NetBSD has its own libintl in libc, and OpenBSD doesn't have nls enabled, explaining why they didn't need -Dextra_include_dirs and -Dextra_lib_dirs in the first place. The Windows task still needs them to find OpenSSL. --- .cirrus.tasks.yml | 3 --- 1 file changed, 3 deletions(-) diff --git a/.cirrus.tasks.yml b/.cirrus.tasks.yml index 3df6de6acd9..31e498dc9b9 100644 --- a/.cirrus.tasks.yml +++ b/.cirrus.tasks.yml @@ -232,7 +232,6 @@ task: meson setup \ ${MESON_COMMON_PG_CONFIG_ARGS} \ --buildtype=debug \ - -Dextra_lib_dirs=/usr/local/lib -Dextra_include_dirs=/usr/local/include/ \ ${MESON_COMMON_FEATURES} ${MESON_FEATURES} \ build EOF @@ -731,8 +730,6 @@ task: meson setup \ ${MESON_COMMON_PG_CONFIG_ARGS} \ --buildtype=debug \ - -Dextra_include_dirs=/opt/local/include \ - -Dextra_lib_dirs=/opt/local/lib \ ${MESON_COMMON_FEATURES} ${MESON_FEATURES} \ build -- 2.51.1
