Skip to content

fix: Adapt to rapidyaml 0.11’s callback changes#1313

Draft
musicinmybrain wants to merge 2 commits intogoogle:masterfrom
musicinmybrain:rapidyaml-0.11
Draft

fix: Adapt to rapidyaml 0.11’s callback changes#1313
musicinmybrain wants to merge 2 commits intogoogle:masterfrom
musicinmybrain:rapidyaml-0.11

Conversation

@musicinmybrain
Copy link
Copy Markdown

Fixes #1312.

FYI, @jcpunk.

@musicinmybrain
Copy link
Copy Markdown
Author

musicinmybrain commented Mar 28, 2026

Testing this downstream in Fedora, combined with @jcpunk’s other recent updates and with a proposed rapidyaml 0.11.1 update, it does compile but I do still see one test failure:

59/59 Test #59: regression_test ..............................***Failed   13.12 sec
FAIL (exit code):  /builddir/build/BUILD/jsonnet-0.22.0-build/jsonnet-0.22.0/redhat-linux-build/jsonnet  --ext-str var1=test --ext-code var2='{x:1,y:2}'  error.std_parseYaml1.jsonnet
This run's output:
line=1 col=6 (5B): ERROR: [parse] two colons on same line
/builddir/build/BUILD/rapidyaml-0.11.1-build/rapidyaml-0.11.1/src/c4/yml/parse_engine.def.hpp:4140: (detected here)
Actual exit code 134, expected 1

-----------------------------

/builddir/build/BUILD/jsonnet-0.22.0-build/jsonnet-0.22.0/test_suite/run_tests.sh: FAILED: 1 / 173

I don’t really know what to make of that output.

@jcpunk
Copy link
Copy Markdown
Contributor

jcpunk commented Mar 29, 2026

I believe the newer rapidyaml doesn't output detailed pointers to the failure where 0.10.0 did. With git installed in the buildroot I get:

-1:6: a: b:  (size=5)
-          ^  (cols 6-6)

In jsonnet b3f1e52 might be related

@musicinmybrain
Copy link
Copy Markdown
Author

I’ve pushed a follow-up commit to upgrade the vendored rapidyaml from 0.10.0 to 0.11.1, since the changes in this PR aren’t backwards compatible.

We could deal with the change in error output described in #1313 (comment) like this:

diff --git a/test_suite/error.std_parseYaml1.jsonnet.golden b/test_suite/error.std_parseYaml1.jsonnet.golden
index 6d8b54b..460f2b5 100644
--- a/test_suite/error.std_parseYaml1.jsonnet.golden
+++ b/test_suite/error.std_parseYaml1.jsonnet.golden
@@ -1,5 +1,3 @@
 RUNTIME ERROR: YAML error: 1:6: ERROR: two colons on same line
-1:6: a: b:  (size=5)
-          ^  (cols 6-6)
 
        error.std_parseYaml1.jsonnet:1:1-23     

However, we still have this to contend with:

FAIL (exit code):  /builddir/build/BUILD/jsonnet-0.22.0-build/jsonnet-0.22.0/redhat-linux-build/jsonnet  --ext-str var1=test --ext-code var2='{x:1,y:2}'  error.std_parseYaml1.jsonnet
This run's output:
line=1 col=6 (5B): ERROR: [parse] two colons on same line
/builddir/build/BUILD/rapidyaml-0.11.1-build/rapidyaml-0.11.1/src/c4/yml/parse_engine.def.hpp:4140: (detected here)
Actual exit code 134, expected 1

-----------------------------

/builddir/build/BUILD/jsonnet-0.22.0-build/jsonnet-0.22.0/test_suite/run_tests.sh: FAILED: 1 / 173

The expectation that failures will exit with code 1 is hard-coded in test_suite/run_tests.sh:

EXPECTED_EXIT_CODE=0
if [ $(echo "$TEST" | cut -b 1-6) == "error." ] ; then
EXPECTED_EXIT_CODE=1
fi

Following the 128+n convention, this suggests that the test is exiting with signal 6, SIGABRT. I don’t have time to investigate that right now. Obtaining and inspecting a core dump would probably help.

@musicinmybrain
Copy link
Copy Markdown
Author

Ok, I did manage to reproduce this in a git checkout and capture a backtrace:

$ cmake -S. -Bbuild -DCMAKE_BUILD_TYPE=Debug
$ cmake --build build -j16
$ ctest --test-dir build
$ coredumpctl debug
(gdb) set pagination off
(gdb) set logging file jsonnet_backtrace.txt
(gdb) set logging on
(gdb) thread apply all bt full

Now, this results in the gdb process running at 100% CPU for a long time. I haven’t determined yet whether it ever finishes. If I stop it with Ctrl+c, though, I still get useful output.

jsonnet_backtrace.txt

Excerpting the most relevant stack frames:

#4  0x00000000004c7f36 in c4::yml::(anonymous namespace)::error_parse_impl (msg=..., errdata=...) at /home/ben/src/forks/jsonnet/third_party/rapidyaml/rapidyaml-0.11.1.hpp:34858
No locals. 
#5  0x00000000004c8477 in c4::yml::err_parse (callbacks=..., errdata=..., msg_=0x59e5f4 "two colons on same line") at /home/ben/src/forks/jsonnet/third_party/rapidyaml/rapidyaml-0.11.1.hpp:35021

So this is coming from the explicit abort() in error_parse_impl:

[[noreturn]] C4_NO_INLINE void error_parse_impl(csubstr msg, ErrorDataParse const& errdata, void * /*user_data*/)
{
    err_parse_format(dump2stderr, msg, errdata);
    endmsg();
    #ifdef _RYML_WITH_EXCEPTIONS
    throw ExceptionParse(msg, errdata);
    #else
    abort(); // LCOV_EXCL_LINE
    #endif
}

… and looking at the definitions of the callbacks,

/** the type of the function used to report basic errors.
 *
 * @warning Must not return. When implemented by the user, this
 * function MUST interrupt execution (and ideally be marked with
 * `[[noreturn]]`). If the function returned, the caller could enter
 * into an infinite loop, or the program may crash. It is up to the
 * user to choose the interruption mechanism; typically by either
 * throwing an exception, or using `std::longjmp()` ([see
 * documentation](https://en.cppreference.com/w/cpp/utility/program/setjmp))
 * or ultimately by calling `std::abort()`. */
using pfn_error_basic = void (*) (csubstr msg, ErrorDataBasic const& errdata, void *user_data);
/** the type of the function used to report parse errors.
 *
 * @warning Must not return. When implemented by the user, this
 * function MUST interrupt execution (and ideally be marked with
 * `[[noreturn]]`). If the function returned, the caller could enter
 * into an infinite loop, or the program may crash. It is up to the
 * user to choose the interruption mechanism; typically by either
 * throwing an exception, or using `std::longjmp()` ([see
 * documentation](https://en.cppreference.com/w/cpp/utility/program/setjmp))
 * or ultimately by calling `std::abort()`. */
using pfn_error_parse = void (*) (csubstr msg, ErrorDataParse const& errdata, void *user_data);
/** the type of the function used to report visit errors.
 *
 * @warning Must not return. When implemented by the user, this
 * function MUST interrupt execution (and ideally be marked with
 * `[[noreturn]]`). If the function returned, the caller could enter
 * into an infinite loop, or the program may crash. It is up to the
 * user to choose the interruption mechanism; typically by either
 * throwing an exception, or using `std::longjmp()` ([see
 * documentation](https://en.cppreference.com/w/cpp/utility/program/setjmp))
 * or ultimately by calling `std::abort()`. */
using pfn_error_visit = void (*) (csubstr msg, ErrorDataVisit const& errdata, void *user_data);

I see that they are required to either abort or raise an exception.

I conclude that this PR should just be treated as a starting point, and further design work by someone actively involved in jsonnet development is going to be required to decide what should really happen here.

@musicinmybrain musicinmybrain marked this pull request as draft March 29, 2026 07:48
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.

Incompatible with rapidyaml 0.11.0+

2 participants