Skip to content

[YottaDB/Lang/YDBGo#34] Add test for Go wrapper changes that added yottadb.[Un]RegisterSignalHandler() functions

Steven Estes requested to merge estess/YDBTest:usrsighndlr into master

These additions test the following functions that were added to the the YDBGo Wrapper with [YottaDB/Lang/YDBGo#34 (closed)]:

  • yottadb.RegisterSignalHandler(sig syscall.Signal, usrHandlr func (syscall.Signal, int), beforOrAfterYDB int) error
  • yottadb.UnRegisterSignalHandler(sig syscall.Signal)

This test does not (cannot) test all of the possible signals that are supported but does try most of them. The signals not tested are:

  1. syscall.SIGALRM - since this signal occurs as part of normal operation, we cannot tell the difference between a SIGALRM that we sent to ourselves and a SIGALRM that is sent from the interval timer popping so these signals periodically cause false failures.
  2. syscall.SIGURG - this is the same signal as SIGPOLL and SIGIO. In a test like this which is writing things to output, this signal was occurring several times per second for the entire duration of the test. In another scenario not doing frequent IO, it might be usable but it was not usable in this test.
  3. The SIGSTOP, SIGTSTP, SIGTTIO and SIGTTOU signals are not tested as they caused a lot of problems with testing (everything just froze as we tried to output anything).

This test is being added but one piece of it is disabled since it periodically fails. When the YDBGo wrapper gets notified by Go that a particular signal has occurred, it sends that notification to YottaDB itself which runs its own handler. For fatal signals, the current code drives the YDBGo wrapper routine YDBWrapperPanic() to drive a Go panic to unwind the Go stack driving handlers. But this test is trying to CATCH that panic with a 'defer/recover' block. Each goroutine has to have its own defer/recover block. This test has one in the main and in each of the 4 goroutines that are doing busy-work but sometimes, none of these panic catchers get control and Go completes the panic (with only YDBWrapperPanic() in the stack) and kills the process with no cleanup. This causes the test to fail. Most recently, in 20 runs, 12 of them failed with this issue. Each run does 20 random signals.

It is not currently understood why sometimes the panic is thrown in a context that cannot be caught but the current thinking is moving away from throwing panics to unwind things and doing the unwind ourselves might be more beneficial and lead to better consistency in signal handling. This proposal is captured in YDB#790 where [YottaDB/Lang/YDBGo#34 (closed)] was the first step, and two further steps are discussed there.

In order to not have the test periodically failing, we've disabled a random choice that was being made in the user signal handler. A workaround in place overrides a randomly chosen choice between just shutting the process down by first running yottadb.Exit() to closeout the DB engine and then running os.Exit() to kill the process without engaging the YottaDB signal handler or letting the YottaDB signal handler run by avoiding the latter choice entirely. Once YDB#790 is complete, the override for this choice can be removed so both paths are tested.

Edited by Steven Estes

Merge request reports