Skip to content

Recognize DragonFly BSD, and fix what keeps the tests from running on the BSDs - #2160

Open
zakinko wants to merge 7 commits into
abseil:masterfrom
zakinko:bsd-honest
Open

Recognize DragonFly BSD, and fix what keeps the tests from running on the BSDs#2160
zakinko wants to merge 7 commits into
abseil:masterfrom
zakinko:bsd-honest

Conversation

@zakinko

@zakinko zakinko commented Sep 10, 2026

Copy link
Copy Markdown

Abseil does not build on DragonFly BSD, and on the other BSDs its test
suite fails in places that have nothing to do with the code under test.
This fixes those, and reports what is left.

  • DragonFly is a FreeBSD descendant but is spelled DragonFly, so
    it missed every FreeBSD branch: GetTID, the auxv type names in
    vdso_support, two config macros, and cctz's _XOPEN_SOURCE, which
    hides the C99 wide functions from libstdc++'s there.
  • raw_logging.cc did not list NetBSD and DragonFly among the systems
    with write(), so a FATAL there aborted without its message and every
    death test failed with "died but not with expected error".
  • stripping_test could not open its own executable on the BSDs. It
    now uses KERN_PROC_PATHNAME on FreeBSD, DragonFly and NetBSD. OpenBSD
    has no such call, and the tests are skipped there.
  • convert_test skipped NaN on Apple by name because "%+f" prints "nan"
    with no sign there; the BSDs do the same, so that is now a probe.
    The hex-float rounding probe gains the case where rounding carries
    into the exponent, which FreeBSD prints as "0x1p+1" for 1.5.
  • OpenBSD links with --execute-only, which refuses the data that
    symbolize_test places in .text on purpose; that one test links with
    --no-execute-only there.
  • GrowExtremelyLargeTable reserves close to 8 GB of address space and
    now skips itself where RLIMIT_DATA is below that, which is OpenBSD's
    default.

Measured with CMake (ABSL_BUILD_TESTING, googletest at head, Release,
C++17):

NetBSD 11.0     gcc 12.5    241 of 242
FreeBSD 15.1    clang 19    240 of 242
OpenBSD 7.9     clang 19    240 of 242 (a third, clock_interface_test,
                            failed once under load and passes alone)
DragonFly 6.4   gcc 14      240 of 242 (gcc 14 from dports; Abseil
                            requires gcc 10 or later, base has 8.3)

The tests still failing are str_format_convert_test and charconv_test,
and in every case the failure is in the platform's libc, which those
tests use as the reference: FreeBSD, NetBSD and DragonFly do not type
the argument of a positional %F ("%1$*2$F"), and on FreeBSD the
vsnprintf return value then makes the test's helper allocate hundreds
of megabytes at a time, so I ran that test alone under a 4 GB address
space limit; OpenBSD prints nothing for "%#.0o" of zero; DragonFly's
"%lc" encodes a negative wchar_t instead of failing; and nan(3) and
strtod disagree on NaN payloads on FreeBSD, OpenBSD and DragonFly. Each
was confirmed with a small C program, and StrFormat and from_chars give
the C answer in every case. I have left those comparisons in place
rather than skip them; the bugs are for the BSDs to fix, and I will
report them there.

DragonFly is a FreeBSD descendant and shares its interfaces where Abseil
looks at them, but it is spelled __DragonFly__, so it fell through every
FreeBSD branch. Building there stopped in three places: GetTID had no
arm (pthread_getthreadid_np exists, in pthread_np.h), vdso_support did
not know the auxv type names (Elf64_Auxinfo, as on FreeBSD), and cctz's
time_zone_format.cc defined _XOPEN_SOURCE, under which DragonFly's
wchar.h hides the C99 wide functions that libstdc++'s <cwchar> then
fails to find. Two config macros follow FreeBSD as well: mmap and
pthread_getschedparam are both there.

Add DragonFly next to FreeBSD in each of those, and in the cctz lookup
test's list of systems whose gmtime_r fails on extreme positive values,
which DragonFly's does (MakeTime.SysSecondsLimits fails without the
line and passes with it).
raw_logging.cc only writes its messages where it knows the platform has
POSIX write(); elsewhere it stays silent and a FATAL still aborts.
NetBSD and DragonFly were not in the list, so a CHECK failure there
killed the process without saying why, and every death test that
matches the message failed with "died but not with expected error".
Both have write() in unistd.h like the other BSDs already listed.
stripping_test opens its own executable to look for strings in it, and
knows how to on Linux (/proc/self/exe), Fuchsia, macOS and Windows. On
the BSDs it printed "unimplemented" and failed. FreeBSD and DragonFly
answer KERN_PROC_PATHNAME under KERN_PROC, NetBSD the same name under
KERN_PROC_ARGS; open what that returns. OpenBSD has no such call and
stays as it was.
Two places where the BSD printfs and glibc's disagree, both within what
C allows, and the test compared them anyway. When rounding a hex float
carries out of the mantissa, glibc prints "0x2p+0" for "%.0a" of 1.5
and FreeBSD renormalizes to "0x1p+1"; the probe that decides whether
the platform rounds like glibc did not cover that case, so add it. And
under "%+f" glibc prints "+nan" where Apple, FreeBSD and NetBSD print
"nan"; the test skipped NaN on Apple by name, so make that a probe as
well rather than a growing list of platforms.
They search the running executable for strings, and OpenBSD gives a
process no way to find its own file: no /proc/self/exe, and no
KERN_PROC_PATHNAME. Skip them there in SetUp, next to the skip for
unoptimized builds, rather than fail on "unimplemented".
symbolize_test places two read-only arrays in .text on purpose, to check
that data there can be symbolized. OpenBSD's compiler driver links with
--execute-only, and lld then refuses the object:

    ld: error: cannot place symbolize_test.cc.o:(.text) into .text:
    --execute-only does not support intermingling data and code

Pass --no-execute-only for this one test there.
The test grows a table until its capacity is in the hundreds of
millions, and on the way reserves close to 8 GB of address space (peak
VSZ 7.7 GB, RSS 1.5 GB, measured on OpenBSD 7.9 with the limit raised).
OpenBSD's default login class caps RLIMIT_DATA at 4 GB, so there the
allocation throws bad_alloc and the test fails without proving
anything. Check the limit first and skip, saying what it is.
zakinko added a commit to zakinko/NetBSD-i386 that referenced this pull request Sep 10, 2026
abseil の cctz は time_zone_format.cc の中で HAS_STRPTIME のために
_XOPEN_SOURCE を自分で立てる。上流 abseil はそこから OpenBSD を外していて、
abseil/abseil-cpp#2160 が Apple と DragonFly も外そうとしている。

DragonFly では _XOPEN_SOURCE=500 で __ISO_C_VISIBLE が 2011 から 1990 に
落ち、libstdc++ の <cwchar> が要る C99 の wide 関数 (vfwscanf) が消える。
FreeBSD は 2023 から 2011 へ、OpenBSD は 2011 のまま、NetBSD は
__ISO_C_VISIBLE を持たない。

mozc は cctz を実際に組む (NetBSD の build log に time_zone_format.cc が
出る) ので、同じ所を通る。当て物を足す前に、四つで値と組めるかを測る。
zakinko added a commit to zakinko/NetBSD-i386 that referenced this pull request Sep 11, 2026
abseil の sysinfo.cc は <sys/sysctl.h> を __APPLE__ と __FreeBSD__ でしか
読まない。GetNominalCPUFrequency の枝は

  #elif defined(CTL_HW) && defined(HW_CPU_FREQ)

で選ばれるので、header を読まない OS では枝に入らず、組めたまま別経路に
落ちる。link は通り、CPU 周波数だけが違う値になる。

abseil/abseil-cpp#2160 は DragonFly をこの include に足しているが、足す意味が
在るかはその OS が macro を持つかで決まる。NetBSD は持っていない。三つでも
測る。
zakinko added a commit to zakinko/NetBSD-i386 that referenced this pull request Sep 11, 2026
user が abseil/abseil-cpp#2160 を含む一連の PR を上流へ出した。mozc が
同梱する abseil にも同じ変更が要るので、こちらは当て物として抱える。
merge されたら消せばよいものと、こちらでしか要らないものを、名前で
区別できるようにした。pkgsrc には patch-CVE-2017-17969 のような出所を
名前にする前例が在る。

  patch-abseil-2160-*                    #2160 に出してあるもの
  patch-third__party_abseil-cpp_...      こちらだけのもの

改名しても当てる順序は変わらない。35 本のどれも触る file が重なっていない
ことを先に数えた。

三本は #2160 と同じ変更を独立に書いていた (config.h の二つの macro、
raw_logging.cc、vdso_support.cc)。突き合わせて、こちらに無いものが二つ出た。

cctz の time_zone_format.cc を足した。cctz は strptime のために自分で
_XOPEN_SOURCE を立てる。DragonFly ではそれで __ISO_C_VISIBLE が 2011 から
1990 に落ち、libstdc++ の <cwchar> が vfwscanf で落ちる。四つで測って、
落ちるのは DragonFly だけだった。mozc は cctz を実際に組む。

sysinfo.cc は足さなかった。#2160 は <sys/sysctl.h> の include に DragonFly を
足しているが、それを使う枝は #elif defined(CTL_HW) && defined(HW_CPU_FREQ)
で選ばれる。四つとも HW_CPU_FREQ を持たない - FreeBSD すら - ので、どの BSD
でもこの枝に入らない。足しても何も変わらないので、抱えない。
@brad0

brad0 commented Sep 13, 2026

Copy link
Copy Markdown
Contributor

OpenBSD has no such call, and the tests are skipped there.

That is no longer true. OpenBSD now has getexecpath().

zakinko added a commit to zakinko/pkgsrc-zakinko that referenced this pull request Sep 14, 2026
同梱の abseil は ABSL_HAVE_MMAP や ABSL_HAVE_POSIX_WRITE を platform の
名前を並べて決めていて、DragonFly はどの一覧にも居ない。raw_logging.cc の
一覧には NetBSD も居らず、ABSL_RAW_LOG が NetBSD では何も書いていなかった。
build は通り program も動くので気づかない。

上流には abseil/abseil-cpp#2160 として出してあるが、その diff は master
向けで、mozc が pin する 987c57f3 には三 hunk が折り返しの違いで当たらない。
意味を変えずに pin 版の姿で書き直した五本。名前に PR 番号を入れてあるのは、
当てる先が直った瞬間に当たらなくなって気づけるようにするため。

同じ command で raw_logging.cc を組むと、素の source は write を参照せず、
当てた方は U write を持つ。gyp で 690/690 通し、package まで作れた。

bazel の道は abseil を BCR (20250814.0) から取るので、この patches/ では
届かない。そちらは別に当てる。
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants