Being able to run jvm without a wrapper is pretty significant (I guest it was 
possible as of over 4 years ago when support for running pies in OSv was 
added). We do not need all this related baggage anymore. Even now wrapper has 
some limiting preventing certain java 9 and up apps from running due to 
inadequate support of new options. 

In my other email I also mentioned I was able to run Python 2 as is without 
having to compile the main executable like in python2x app. 

On Sunday, April 14, 2019 at 6:03:37 PM UTC-4, Nadav Har'El wrote:
> On Sun, Apr 14, 2019 at 11:21 PM Waldek Kozaczuk <[email protected]> wrote:
> 
> As I was researching OSv ability to run unmodified Linux pie as is from host 
> I did quick experiment with Java 8.
> 
> 
> I created an app that took all java 8 artifacts as is from host (so no 
> wrapper):
> 
> 
> 
> cat usr.manifest 
> /usr/lib/jvm/java-8-openjdk-amd64/jre/**: 
> /usr/lib/jvm/java-8-openjdk-amd64/jre/**
> /usr/lib/libjli.so: -> 
> /usr/lib/jvm/java-8-openjdk-amd64/jre/lib/amd64/jli/libjli.so
> /Hello.class: ${MODULE_DIR}/Hello.classand I was able to run it with two 
> caveats
> 
> 
> 1. After executing java apps OSv did not terminate and after I connected with 
> gdb and some Java threads were stuck like this:
> 
> 
> 
> (gdb) bt
> #0  sched::thread::switch_to (this=0xffff800000aa7040, 
> this@entry=0xffff800001e73040) at arch/x64/arch-switch.hh:108
> #1  0x00000000003fd104 in sched::cpu::reschedule_from_interrupt 
> (this=0xffff80000096b040, 
>     called_from_yield=called_from_yield@entry=false, preempt_after=..., 
> preempt_after@entry=...) at core/sched.cc:339
> #2  0x00000000003fd5fc in sched::cpu::schedule () at include/osv/sched.hh:1309
> #3  0x00000000003fdd22 in sched::thread::wait 
> (this=this@entry=0xffff800002f87040) at core/sched.cc:1214
> #4  0x00000000003e096f in 
> sched::thread::do_wait_until<sched::noninterruptible, 
> sched::thread::dummy_lock, waiter::wait(sched::timer*) 
> const::{lambda()#1}>(sched::thread::dummy_lock&, waiter::wait(sched::timer*) 
> const::{lambda()#1}) (pred=..., 
>     mtx=<synthetic pointer>...) at include/osv/sched.hh:938
> #5  sched::thread::wait_until<waiter::wait(sched::timer*) 
> const::{lambda()#1}>(waiter::wait(sched::timer*) const::{lambda()#1}) 
> (pred=...) at include/osv/sched.hh:1076
> #6  waiter::wait (tmr=0x0, this=0x2000105ce670) at 
> include/osv/wait_record.hh:46
> #7  condvar::wait (this=0xffffa00002c61280, user_mutex=0xffffa00002c5b140, 
> tmr=<optimized out>) at core/condvar.cc:43
> #8  0x0000100000c9842b in 
> SharedRuntime::generate_native_wrapper(MacroAssembler*, methodHandle, int, 
> BasicType*, VMRegPair*, BasicType) ()
> #9  0x0000100000c8036d in 
> SharedRuntime::throw_StackOverflowError(JavaThread*) ()
> #10 0x0000000000000000 in ?? ()
> I wonder if that is similar to why we have special logic to terminate all 
> java threads in wrapper (java.cc). Ctrl-C does not work.
> 
> 
> Yes. The code at the end of java.cc explains why it's needed:
> 
> 
>     // Unfortunately, Java's jvm->DestroyJavaVM() doesn't fully clean up, and
>     // leaves behind some detached threads such as GC threads and compilation
>     // threads. If we return with those still existing, loader.cc will wait
>     // (using application::join()) in vain for these threads to finish.
>     // So let's stop these threads. This call is unsafe, in the sense we
>     // assume that those renegade threads are not holding any critical
>     // resources (e.g., not in the middle of I/O or memory allocation).
>     while(!osv::application::unsafe_stop_and_abandon_other_threads()) {
>         usleep(100000);
>     }
> 
> 
> 
> The thing is that when loader.cc runs an application it, deliberately, 
> doesn't just wait for the main() function to return - it also waits for any 
> other threads that the application started to finish as well. But in Java, 
> there is simply no way to close these extra threads (such as Java GC 
> threads). This is really a bug in Java, but it does make one wonder why OSv 
> needs to be that pedantic about it. We could have a run option to just run 
> main() and shut down once main() returns, without caring about any other 
> threads (and of course without being able to run another application after 
> this one 


Sounds like a great idea. I will try to come up with a patch at some point. 
> 
> 
> 
>  
> 
> 
> 
> 
> 2. I believe there is a bug in elf.cc::program::load_object() where I had to 
> hack it to force finding and loading one of the shared object java pie 
> executable depended on (all other so loaded fine). There may be actually 2 
> bugs:
> there is a bug that prevents loading libjli.so by java pie; adding this nasty 
> hack worked: 
> 
> 
> 
> @@ -1149,6 +1150,9 @@ std::shared_ptr<elf::object>
>  program::load_object(std::string name, std::vector<std::string> extra_path,
>          std::vector<std::shared_ptr<object>> &loaded_objects)
>  {
> +    if( name == "libjli.so" ) {
> +        name = 
> "/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/amd64/jli/libjli.so";
> +    }
>      fileref f;
> 
> 
> Let's see how this is supposed to work:
> 
> 
> 
> libjli.so is needed by jre/lib/amd64/libinstrument.so. On my host (Fedora 29),
> 
> 
> $ ldd /usr/lib/jvm/java-1.8.0-openjdk/jre/lib/amd64/libinstrument.so
>         linux-vdso.so.1 (0x00007ffec512e000)
>         libz.so.1 => /lib64/libz.so.1 (0x00007fcd91ac0000)
>         libjli.so => 
> /usr/lib/jvm/java-1.8.0-openjdk/jre/lib/amd64/jli/libjli.so 
> (0x00007fcd91aae000)
>         libdl.so.2 => /lib64/libdl.so.2 (0x00007fcd91aa8000)
>         libc.so.6 => /lib64/libc.so.6 (0x00007fcd918e2000)
>         libpthread.so.0 => /lib64/libpthread.so.0 (0x00007fcd918c0000)
>         /lib64/ld-linux-x86-64.so.2 (0x00007fcd91b28000)
> 
> 
> 
> How did it find the pathname of libjli.so? Well, 
> 
> 
> 
> $ readelf -a /usr/lib/jvm/java-1.8.0-openjdk/jre/lib/amd64/libinstrument.so
> ...
>  0x0000000000000001 (NEEDED)             Shared library: [libz.so.1]
>  0x0000000000000001 (NEEDED)             Shared library: [libjli.so]
>  0x0000000000000001 (NEEDED)             Shared library: [libdl.so.2]
>  0x0000000000000001 (NEEDED)             Shared library: [libc.so.6]
>  0x000000000000000e (SONAME)             Library soname: [libinstrument.so]
>  0x000000000000000f (RPATH)              Library rpath: [$ORIGIN:$ORIGIN/jli]
> 
> 
> 
> This RPATH asks when loading 
> /usr/lib/jvm/java-1.8.0-openjdk/jre/lib/amd64/libinstrument.so and searching 
> for "libjli.so" to also search for it in $ORIGIN/jli, i.e., 
> /usr/lib/jvm/java-1.8.0-openjdk/jre/lib/amd64/jli. Where it indeed is.
> 
> 
> And we do have proper handling of DT_RPATH in core/elf.cc.
> 
> 
> So either we have a bug in that RPATH handling that wasn't apparent to me now 
> when I reviewed the code (and to Avi Kivity when he wrote it), or there's a 
> different problem. Maybe me installed libjli.so at the wrong tree? Maybe if 
> you add printouts to core/elf.cc's handling of DT_RPATH you can see more 
> clearly what's the bug.
I will try to figure it out. Hopefully something simple.  
> 
> 
> 
> 
> there is a bug that silently ignores the fact that shared file has not been 
> loaded and ends up OSv report this:
> For historic reasons, OSv prints missing DT_NEEDED messages with debug():
> 
> 
>             debug("could not load %s\n", lib);
> 
> 
>  This means that unless you run with --verbose, you'll never see these 
> messages... 
> 
> Hiding these messages was convenient in the past, and sometimes still is (see 
> https://github.com/cloudius-systems/osv/issues/601) but maybe it makes sense 
> to convert this message to a debug_always(), so it is always shown?
> 
> 
> 
>  
> 
> 
> 
> 
> 
> 
> /usr/lib/jvm/java-8-openjdk-amd64/jre/bin/java: failed looking up symbol 
> JLI_Launch
> 
> 
> [backtrace]
> 0x000000000035cb8d <elf::object::symbol(unsigned int, bool)+1325>
> 0x000000000035cc4f <elf::object::resolve_pltgot(unsigned int)+127>
> 0x000000000035ce29 <elf_resolve_pltgot+57>
> 0x00000000003a2d1f <???+3812639>
> 0x00002000001ffe9f <???+2096799>
> 0x000000000042e97c <osv::application::run_main()+60>
> 0x000000000042eaae <__libc_start_main+46>
> 0x00001000000060c9 <???+24777>
> 
> 
> I also ran more complicated examples like vertx REST service one and it 
> worked perfectly.
> 
> 
> Waldek 
> 
> 
> 
> 
> -- 
> 
> You received this message because you are subscribed to the Google Groups 
> "OSv Development" group.
> 
> To unsubscribe from this group and stop receiving emails from it, send an 
> email to [email protected].
> 
> For more options, visit https://groups.google.com/d/optout.

-- 
You received this message because you are subscribed to the Google Groups "OSv 
Development" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.

Reply via email to