Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bug Report: Assertion Failure in ODE dSolveLCP #1899

Open
2 tasks done
DUT-ShiLongYu opened this issue Jan 10, 2025 · 5 comments
Open
2 tasks done

Bug Report: Assertion Failure in ODE dSolveLCP #1899

DUT-ShiLongYu opened this issue Jan 10, 2025 · 5 comments
Labels
type: bug Indicates an unexpected problem or unintended behavior

Comments

@DUT-ShiLongYu
Copy link

If you're not reporting a bug, please use the forum to ask questions.

Bug Report

Please answer the following questions for yourself before reporting a bug.

  • I checked the documentation and the forum but found no answer.
  • I checked to make sure that this issue has not already been filed.

Environment

Select the following information.

  • DART version: main
  • OS name and version name(or number): Ubuntu 22.04
  • Compiler name and version number: Clang 10.0.1

Expected Behavior

The test code can successfully execute the test

Current Behavior

During fuzz testing, when running Collision_CollisionOfPrescribedJoints_Test, the program triggered an internal error, specifically an assertion failure in the ODE (Open Dynamics Engine) solver dSolveLCP(). The core of the issue is that a non-zero command (-1.5708) was attempted to be set for a joint marked as "PASSIVE" (joint 1), which violates the internal assertion condition in ODE.
Below is the call stack that triggered the bug.

INFO: Seed: 1427290015
INFO: Loaded 1 modules   (139538 inline 8-bit counters): 139538 [0x192bce8, 0x194ddfa), 
INFO: Loaded 1 PC tables (139538 PCs): 139538 [0x194de00,0x1b6ef20), 
/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test: Running 1 inputs 1 time(s) each.
Running: /root/UTopia/exp/dart/output/fuzzers/information_Collision_CollisionOfPrescribedJoints_Test/crash-42a961c4906c4ab7c43441ac9414b829e316d0ff
�[1;33mWarning [GenericJoint.hpp:328]�[0m [GenericJoint::setCommand] Attempting to set a non-zero (-1.5708) command for a PASSIVE joint [joint 1].

ODE INTERNAL ERROR 1: assertion "lo[k] <= 0 && hi[k] >= 0" failed in dSolveLCP() [/root/UTopia/exp/dart/dart/external/odelcpsolver/lcp.cpp:791]
==2526485== ERROR: libFuzzer: deadly signal
    #0 0x54d361 in __sanitizer_print_stack_trace (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x54d361)
    #1 0x4984c8 in fuzzer::PrintStackTrace() (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x4984c8)
    #2 0x47d613 in fuzzer::Fuzzer::CrashCallback() (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x47d613)
    #3 0x77478f3b451f  (/lib/x86_64-linux-gnu/libc.so.6+0x4251f)
    #4 0x77478f4089fb in pthread_kill (/lib/x86_64-linux-gnu/libc.so.6+0x969fb)
    #5 0x77478f3b4475 in raise ../sysdeps/posix/raise.c:26:13
    #6 0x77478f39a7f2 in abort (/lib/x86_64-linux-gnu/libc.so.6+0x287f2)
    #7 0x141ec50 in dart::external::ode::dDebug(int, char const*, ...) /root/UTopia/exp/dart/dart/external/odelcpsolver/error.cpp:105:3
    #8 0x1408508 in dart::external::ode::dSolveLCP(int, double*, double*, double*, double*, int, double*, double*, int*, bool) /root/UTopia/exp/dart/dart/external/odelcpsolver/lcp.cpp:791:29
    #9 0x104818e in dart::constraint::BoxedLcpConstraintSolver::solveConstrainedGroup(dart::constraint::ConstrainedGroup&) /root/UTopia/exp/dart/dart/constraint/BoxedLcpConstraintSolver.cpp:261:35
    #10 0xf01729 in dart::constraint::ConstraintSolver::solveConstrainedGroups() /root/UTopia/exp/dart/dart/constraint/ConstraintSolver.cpp:700:5
    #11 0xf01729 in dart::constraint::ConstraintSolver::solve() /root/UTopia/exp/dart/dart/constraint/ConstraintSolver.cpp:381:3
    #12 0xf741d5 in dart::simulation::World::step(bool) /root/UTopia/exp/dart/dart/simulation/World.cpp:181:24
    #13 0x5f7b3b in Collision_CollisionOfPrescribedJoints_Test::TestBody() /root/UTopia/exp/dart/tests/integration/test_Collision.cpp:1620:12
    #14 0x5fead9 in enterAutofuzz::AutofuzzTest::runTest() /root/UTopia/exp/dart/tests/integration/test_Collision.cpp:1709:9
    #15 0x5fe6e5 in enterAutofuzz /root/UTopia/exp/dart/tests/integration/test_Collision.cpp:1720:10
    #16 0x142d664 in TestOneProtoInput(AutoFuzz::FuzzArgsProfile const&) /root/UTopia/exp/dart/tests/integration/fuzz_entry.cc:60:3
    #17 0x142d44b in LLVMFuzzerTestOneInput /root/UTopia/exp/dart/tests/integration/fuzz_entry.cc:44:1
    #18 0x47ecd1 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x47ecd1)
    #19 0x46a442 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x46a442)
    #20 0x46fef6 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x46fef6)
    #21 0x498bb2 in main (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x498bb2)
    #22 0x77478f39bd8f in __libc_start_call_main ../sysdeps/nptl/libc_start_call_main.h:58:16
    #23 0x77478f39be3f in __libc_start_main ../csu/libc-start.c:392:3
    #24 0x444ae4 in _start (/root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test+0x444ae4)

NOTE: libFuzzer has rudimentary signal handlers.
      Combine libFuzzer with AddressSanitizer or similar for better crash reports.
SUMMARY: libFuzzer: deadly signal

Steps to Reproduce

Please provide detailed steps for reproducing the issue.

1.Compile test_Collision.cpp

clang++ -DDART_ACTIVE_LOG_LEVEL=2 -DDART_HAVE_spdlog=1 -DFMT_HEADER_ONLY=1 -DFMT_LOCALE -DFMT_SHARED -DSPDLOG_FMT_EXTERNAL -I/root/UTopia/exp/dart/tests -I/root/UTopia/exp/dart -I/root/UTopia/exp/dart/build -isystem /usr/include/eigen3 -isystem /root/UTopia/exp/dart/build/_deps/googletest-src/googletest/include -isystem /root/UTopia/exp/dart/build/_deps/googletest-src/googletest -isystem /usr/include/bullet -g -Wall -Wextra -fPIC -std=gnu++17 -MD -MT tests/integration/CMakeFiles/test_Collision.dir/test_Collision.cpp.o -MF CMakeFiles/test_Collision.dir/test_Collision.cpp.o.d -o /root/UTopia/exp/dart/build/tests/integration/CMakeFiles/test_Collision.dir/test_Collision.cpp.o -c /root/UTopia/exp/dart/tests/integration/test_Collision.cpp -DBOOST_TEST_NO_MAIN -DAUTOFUZZ -fsanitize=address,fuzzer-no-link -fprofile-instr-generate -fcoverage-mapping

2.Compile FuzzArgsProfile.pb.cc

clang++ -DDART_ACTIVE_LOG_LEVEL=2 -DDART_HAVE_spdlog=1 -DFMT_HEADER_ONLY=1 -DFMT_LOCALE -DFMT_SHARED -DSPDLOG_FMT_EXTERNAL -I/root/UTopia/exp/dart/tests -I/root/UTopia/exp/dart -I/root/UTopia/exp/dart/build -isystem /usr/include/eigen3 -isystem /root/UTopia/exp/dart/build/_deps/googletest-src/googletest/include -isystem /root/UTopia/exp/dart/build/_deps/googletest-src/googletest -isystem /usr/include/bullet -g -Wall -Wextra -fPIC -std=gnu++17 -MD -MT tests/integration/CMakeFiles/test_Collision.dir/test_Collision.cpp.o -MF CMakeFiles/test_Collision.dir/test_Collision.cpp.o.d -o /root/UTopia/exp/dart/build/avas_out/FuzzArgsProfile.pb.cc.o -c /root/UTopia/exp/dart/tests/integration/FuzzArgsProfile.pb.cc -I/usr/local/include/libprotobuf-mutator -DBOOST_TEST_NO_MAIN -DAUTOFUZZ -fsanitize=address,fuzzer-no-link -fprofile-instr-generate -fcoverage-mapping

3.Compile fuzz_entry.cc

clang++ -DDART_ACTIVE_LOG_LEVEL=2 -DDART_HAVE_spdlog=1 -DFMT_HEADER_ONLY=1 -DFMT_LOCALE -DFMT_SHARED -DSPDLOG_FMT_EXTERNAL -I/root/UTopia/exp/dart/tests -I/root/UTopia/exp/dart -I/root/UTopia/exp/dart/build -isystem /usr/include/eigen3 -isystem /root/UTopia/exp/dart/build/_deps/googletest-src/googletest/include -isystem /root/UTopia/exp/dart/build/_deps/googletest-src/googletest -isystem /usr/include/bullet -g -Wall -Wextra -fPIC -std=gnu++17 -MD -MT tests/integration/CMakeFiles/test_Collision.dir/test_Collision.cpp.o -MF CMakeFiles/test_Collision.dir/test_Collision.cpp.o.d -o /root/UTopia/exp/dart/build/avas_out/fuzz_entry.cc.o -c /root/UTopia/exp/dart/tests/integration/fuzz_entry.cc -I/usr/local/include/libprotobuf-mutator -DBOOST_TEST_NO_MAIN -DAUTOFUZZ -fsanitize=address,fuzzer-no-link -fprofile-instr-generate -fcoverage-mapping

4.Link

clang++ -g -g CMakeFiles/test_Collision.dir/test_Collision.cpp.o -o /root/UTopia/exp/dart/output/fuzzers/Collision_CollisionOfPrescribedJoints_Test \
-L/root/UTopia/exp/dart/output -l:libdart_fuzzer.a -l:libgtest_fuzzer.a -l:libgtest_main_fuzzer.a -l:libdart-utils_fuzzer.a \
-l:libdart-collision-bullet_fuzzer.a -l:libdart-collision-ode_fuzzer.a \
/usr/lib/x86_64-linux-gnu/libtinyxml2.so /usr/lib/x86_64-linux-gnu/libBulletDynamics.so \
/usr/lib/x86_64-linux-gnu/libBulletCollision.so /usr/lib/x86_64-linux-gnu/libLinearMath.so \
/usr/lib/x86_64-linux-gnu/libBulletSoftBody.so \
-L/root/UTopia/exp/dart/output -l:libdart_fuzzer.a -ldl ../../dart/external/odelcpsolver/libdart-external-odelcpsolver.a \
/usr/lib/x86_64-linux-gnu/libfcl.so.0.7.0 /usr/lib/x86_64-linux-gnu/libccd.so -lm \
/usr/lib/x86_64-linux-gnu/libassimp.so /usr/lib/x86_64-linux-gnu/libfmt.so.8.1.1 \
-Wl,--as-needed /usr/lib/x86_64-linux-gnu/liboctomap.so.1.9.7 /usr/lib/x86_64-linux-gnu/liboctomath.so.1.9.7 \
/usr/lib/x86_64-linux-gnu/libode.so /root/UTopia/exp/dart/build/avas_out/FuzzArgsProfile.pb.cc.o \
/root/UTopia/exp/dart/build/avas_out/fuzz_entry.cc.o

5.Reproduce the bug

Collision_CollisionOfPrescribedJoints_Test ./crash-42a961c4906c4ab7c43441ac9414b829e316d0ff 

Code to Reproduce

Test_code_and_Reproduction_File.tar.gz

@DUT-ShiLongYu DUT-ShiLongYu added the type: bug Indicates an unexpected problem or unintended behavior label Jan 10, 2025
@jslee02
Copy link
Member

jslee02 commented Jan 11, 2025

Sorry, I don't have the capacity to debug the entire test, but the error message indicates that the linear constraints for x in the LCP formulation do not satisfy the restrictions (lo[k] <= 0 && hi[k] >= 0).

You might want to investigate how the value ended up being set this way. The issue could stem from an invalid constraint setup (e.g., a negative friction coefficient can make lo and hi invalid) or a potential implementation error in DART.

@DUT-ShiLongYu
Copy link
Author

Thank you for your reply, I will continue to explore this issue

@DUT-ShiLongYu
Copy link
Author

hey, I narrowed down the error to the timeStep value of CollisionOfPrescribedJoints in test_Collision.cpp. It is set to 0.0/0.0 and it triggers the error. I also tried other cases, if it is defined as 1e308 * 1e308 or 1.0 / 0.0, it will be forced to 0. It is surprising that 0.0/0.0 does not trigger this protection.

@DUT-ShiLongYu
Copy link
Author

This is the protection prompt mentioned above, but 0.0/0.0 does not appear

Error [BoxedLcpConstraintSolver.cpp:293] [BoxedLcpConstraintSolver] The solution of LCP includes NAN values: -nan. We're setting it zero for safety. Consider using more robust solver such as PGS as a secondary solver. If this happens even with PGS solver, please report this as a bug.

@jslee02
Copy link
Member

jslee02 commented Jan 20, 2025

hey, I narrowed down the error to the timeStep value of CollisionOfPrescribedJoints in test_Collision.cpp. It is set to 0.0/0.0 and it triggers the error.

Apologies, I’m a bit confused. The line you mentioned sets the time step to 1e-3, which is a valid value—it’s neither 0.0/0.0 nor 0. Are you saying that a NaN occurs when using 0.0/0.0 (which is already undefined behavior due to division by zero)?

Or are you concerned that World::setTimeStep() doesn’t perform validity checks on the time step? If so, you’re right—it currently only checks for negativity, but not for infinity, NaN, or similar cases:

if (_timeStep <= 0.0) {
dtwarn << "[World] Attempting to set negative timestep. Ignoring this "
<< "request because it can lead to undefined behavior.\n";
return;
}

Adding such checks would be a good improvement.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type: bug Indicates an unexpected problem or unintended behavior
Projects
None yet
Development

No branches or pull requests

2 participants