Test a complete failure of the JVM

Say you want to test that your application behaves correctly on restart even after the application crashes. One approach is to trigger a crash in test code and check that data is in a correctable state on restart.
Unsafe unsafe = getUnsafe(); // use reflection
unsafe.setMemory(0, 1, (byte) 0);
This triggers a SIGSEGV
#
# A fatal error has been detected by the Java Runtime Environment:
#
#  SIGSEGV (0xb) at pc=0x00000032b967ae09, pid=17870, tid=1082034496
#
# JRE version: 7.0_01-b08
# Java VM: Java HotSpot(TM) 64-Bit Server VM (21.1-b02 mixed mode linux-amd64 compressed oops)
# Problematic frame:
# C  [libc.so.6+0x7ae09]  memset+0x9
#
If your tests still pass, you can be reasonably confident it is recoverable even on a complete failure of the JVM.

For the code for getUnsafe().

Warning: This class is appropriately named and misuse can result in a crash of the JVM. It can also change in future versions (It is more likely new methods will be added rather than removed)

public static Unsafe getUnsafe() {
    try {
        Field field = Unsafe.class.getDeclaredField("theUnsafe");
        field.setAccessible(true);
        return (Unsafe) field.get(null);
    } catch (Exception e) {
        throw new AssertionError(e);
    }
} 

Comments

  1. I don't think everyone knows about/has access to a getUnsafe() method, so for reference here is such a method that should work

    Unsafe getUnsafe() {
    Unsafe unsafe = null;
    try {
    Field field = sun.misc.Unsafe.class.getDeclaredField("theUnsafe");
    field.setAccessible(true);
    unsafe = (sun.misc.Unsafe) field.get(null);
    } catch (Exception e) {
    throw new AssertionError(e);
    }
    return unsafe;
    }

    ReplyDelete
  2. hi,

    what's the usefulness of such test? if the JVM crashes your app needs to reloaded, re-initialized, re-warmed-up, etc.

    "test that your application behaves correctly" - what application? when the JVM is down there is no application - it's like a machine reboot for Apache server, right?

    cheers

    ReplyDelete
  3. @Premyslav, The application stores its data in memory mapped files. On restart, all the data is already in memory. ;) In this case, it is to ensure that data written to memory is not lost even if the program immediately crashes.

    ReplyDelete
  4. @jackson, I tend not to give the source on the assumption that anyone who can't figure it out probably shouldn't be using it. ;)

    ReplyDelete
  5. OK I get it but "behaves correctly" is not enough. you should make a full scan to see if memory state is not corrupted.

    anyway, thanks for sharing this. sometimes it's quite useful to simulate unplugged power or network cable ;)

    ReplyDelete
  6. Thanks Jackson for the code listing.

    ReplyDelete

Post a Comment

Popular posts from this blog

Low Latency Microservices, A Retrospective

Unusual Java: StackTrace Extends Throwable

System wide unique nanosecond timestamps