From 90e244c9647e88f6137f0ab67a6945436209fadd Mon Sep 17 00:00:00 2001 From: VegOwOtenks Date: Mon, 18 Nov 2024 17:08:54 +0100 Subject: [PATCH] Now calls the main method with an uncountable amount of hacks --- src/jvm.rs | 118 ++++++++++++++---- src/main.rs | 1 + src/native_methods.rs | 272 ++++++++++++++++++++++++++++++++---------- src/virtual_thread.rs | 22 ++++ 4 files changed, 325 insertions(+), 88 deletions(-) create mode 100644 src/virtual_thread.rs diff --git a/src/jvm.rs b/src/jvm.rs index 2774ae5..0ead479 100644 --- a/src/jvm.rs +++ b/src/jvm.rs @@ -1,3 +1,4 @@ +use crate::virtual_thread::VirtualThread; use crate::classfile::ExceptionTableEntry; use core::fmt::{Display, Formatter}; @@ -55,18 +56,20 @@ impl Display for Error { #[derive(Debug)] pub struct JVM { pub class_store: ClassStore, - pub stack_frames: Vec, pub heap_area: HeapArea, pub native_registry: NativeRegistry, + pub threads: Vec, + pub active_thread: usize } impl JVM { pub fn new() -> Self { return JVM { class_store: ClassStore::new(), - stack_frames: Vec::new(), heap_area: HeapArea::new(usize::MAX), native_registry: NativeRegistry::default(), + threads: Vec::new(), + active_thread: 0, } } @@ -462,37 +465,97 @@ impl JVM { .collect(); let argument_array_ref = self.heap_area.make_array(&self.class_store, string_refs); - + self.setup_main_thread()?; + // push the entry frame which will call main let entry_frame = StackFrame::new(self.class_store.get_class(&String::from("::EntryPoint")).unwrap().0, 0, 0, &[StackValue::Reference(argument_array_ref)]); - self.stack_frames.push(entry_frame); + self.active_thread_mut().add_frame(entry_frame); + + Ok(()) + } + + pub fn setup_main_thread(&mut self) -> Result<(), Error> { + let thread_group_class_index = self.load_class_hierarchy(&"java/lang/ThreadGroup".to_string())?; + let main_thread_group_reference = self.heap_area.make_object(&self.class_store, thread_group_class_index); + + let holder_class_index = self.load_class_hierarchy(&"java/lang/Thread$FieldHolder".to_string())?; + let main_thread_holder_reference = self.heap_area.make_object(&self.class_store, holder_class_index); + self.heap_area.object_area.set_object_field( + main_thread_holder_reference, + "threadStatus", + FieldValue::Int(1), // alive + holder_class_index, + &self.class_store + )?; + self.heap_area.object_area.set_object_field( + main_thread_holder_reference, + "group", + main_thread_group_reference.into(), + holder_class_index, + &self.class_store + )?; + + let thread_class_index = self.load_class_hierarchy(&"java/lang/Thread".to_string())?; + let main_thread_reference = { + self.heap_area.make_object(&self.class_store, thread_class_index) + }; + self.heap_area.object_area.set_object_field( + main_thread_reference, + "eetop", + FieldValue::Long(0), // thread array index + thread_class_index, + &self.class_store + )?; + let main_thread_name = self.heap_area.make_handmade_string(&"main".to_string(), &self.class_store); + self.heap_area.object_area.set_object_field( + main_thread_reference, + "name", + FieldValue::Reference(main_thread_name), + thread_class_index, + &self.class_store + )?; + self.heap_area.object_area.set_object_field( + main_thread_reference, + "holder", + FieldValue::Reference(main_thread_holder_reference), + thread_class_index, + &self.class_store + )?; + + + self.threads.push( + VirtualThread::new(main_thread_reference) + ); Ok(()) } pub fn run(&mut self) -> Result<(), Error> { - while self.stack_frames.len() != 0 { + while self.active_thread_mut().stack_frames.len() != 0 { let jvm_op = self.bytecode_loop()?; match jvm_op { JVMCallbackOperation::PopFrame() => { - self.stack_frames.truncate(self.stack_frames.len() - 1) + let frame_count = self.active_thread_mut().stack_frames.len() - 1; + self.active_thread_mut().stack_frames.truncate(frame_count); }, JVMCallbackOperation::ReturnFrame(value) => { // Pop returning frame - self.stack_frames.truncate(self.stack_frames.len() - 1); + let frame_count = self.active_thread_mut().stack_frames.len() - 1; + self.active_thread_mut().stack_frames.truncate(frame_count); let frame = { - let frame_index = self.stack_frames.len() - 1; - &mut self.stack_frames[frame_index] + let thread = &mut self.threads[self.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = self.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = & class.methods[frame.method_index as usize]; - wrap_stackframe_error(class, method, self.stack_frames.last_mut().unwrap().operand_stack.push_field_value(value))?; + wrap_stackframe_error(class, method, frame.operand_stack.push_field_value(value))?; } - JVMCallbackOperation::PushFrame(frame) => self.stack_frames.push(frame), + JVMCallbackOperation::PushFrame(frame) => self.active_thread_mut().stack_frames.push(frame), JVMCallbackOperation::LoadClass(name) => { // TODO: throw exception @@ -514,8 +577,9 @@ impl JVM { while ! is_handler_found { is_handler_found = { let frame = { - let frame_index = self.stack_frames.len() - 1; - &mut self.stack_frames[frame_index] + let thread = &mut self.threads[self.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = self.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = &class.methods[frame.method_index as usize]; @@ -527,14 +591,15 @@ impl JVM { }; if ! is_handler_found { - self.stack_frames.pop(); + self.active_thread_mut().stack_frames.pop(); } } if is_handler_found { - let frame = { - let frame_index = self.stack_frames.len() - 1; - &mut self.stack_frames[frame_index] + let frame = { + let thread = &mut self.threads[self.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = self.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = &class.methods[frame.method_index as usize]; @@ -703,7 +768,7 @@ impl JVM { &[], ); - self.stack_frames.push(clinit_frame); + self.active_thread_mut().add_frame(clinit_frame); } // finish @@ -714,8 +779,9 @@ impl JVM { fn native_call(&mut self) -> Result { let frame = { - let frame_index = self.stack_frames.len() - 1; - &mut self.stack_frames[frame_index] + let thread = &mut self.threads[self.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = self.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = & class.methods[frame.method_index as usize]; @@ -734,8 +800,12 @@ impl JVM { fn bytecode_loop(&mut self) -> Result { //println!("Enter bytecode loop:"); - let frame_index = self.stack_frames.len() - 1; - let frame = &mut self.stack_frames[frame_index]; + let frame_index = self.active_thread_mut().stack_frames.len() - 1; + let frame = { + let thread = &mut self.threads[self.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] + }; let class = self.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = & class.methods[frame.method_index as usize]; @@ -2541,6 +2611,10 @@ impl JVM { Ok(JVMCallbackOperation::PopFrame()) } + pub fn active_thread_mut(&mut self) -> &mut VirtualThread { + return &mut self.threads[self.active_thread]; + } + } pub enum JVMCallbackOperation { diff --git a/src/main.rs b/src/main.rs index e8d5b95..ce02395 100644 --- a/src/main.rs +++ b/src/main.rs @@ -9,6 +9,7 @@ mod heap_area; mod iterators; mod native_registry; mod native_methods; +mod virtual_thread; //use std::fs::File; // diff --git a/src/native_methods.rs b/src/native_methods.rs index c22fbd0..099665b 100644 --- a/src/native_methods.rs +++ b/src/native_methods.rs @@ -11,6 +11,7 @@ use crate::native_registry::NativeMethodCallable; use crate::jvm::JVM; use crate::jvm::Error; use crate::jvm::JVMCallbackOperation; +use crate::virtual_thread::VirtualThread; pub fn ignore_call(_: &mut JVM) -> Result { Ok(JVMCallbackOperation::PopFrame()) @@ -59,9 +60,10 @@ struct JavaLangClass {} impl JavaLangClass { fn is_array(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let this = frame.load_local_reference(0).unwrap(); let class_class_index = jvm.heap_area.object_area.get_object_class_index(this); @@ -76,9 +78,10 @@ impl JavaLangClass { } pub fn get_primitive_class(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; // max_locals: 1 // max_stack: 1 @@ -327,9 +330,10 @@ struct JavaLangFloat {} impl JavaLangFloat { pub fn float_to_raw_int_bits(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = jvm.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = & class.methods[frame.method_index as usize]; @@ -346,9 +350,10 @@ struct JavaLangDouble {} impl JavaLangDouble { pub fn double_to_raw_long_bits(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = jvm.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = & class.methods[frame.method_index as usize]; @@ -365,9 +370,10 @@ struct JavaLangObject {} impl JavaLangObject { fn clone(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let this = frame.load_local_reference(0).unwrap(); @@ -377,9 +383,10 @@ impl JavaLangObject { } fn get_class(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let this = frame.load_local_reference(0).unwrap(); @@ -389,9 +396,10 @@ impl JavaLangObject { } fn hashcode(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; if frame.operand_stack.capacity() == 1 { frame.operand_stack.grow(2); @@ -447,6 +455,15 @@ impl JavaLangObject { } } +struct JavaLangRefFinalizer {} + +impl JavaLangRefFinalizer { + pub fn is_finalization_enabled(jvm: &mut JVM) -> Result { + // TODO: enable + Ok(JVMCallbackOperation::ReturnFrame(FieldValue::Boolean(false))) + } +} + struct JavaLangRuntime {} impl JavaLangRuntime { @@ -459,9 +476,10 @@ struct JavaLangSignal {} impl JavaLangSignal { fn find_signal_0(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let string_ref = frame.load_local_reference(0).unwrap(); let rust_string = jvm.heap_area.decode_java_string(string_ref, &jvm.class_store); @@ -485,8 +503,9 @@ impl JavaLangSystem { fn register_natives(jvm: &mut JVM) -> Result { // Load class because it won't be loaded otherwise let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let r#return = match frame.instruction_pointer { @@ -508,8 +527,9 @@ impl JavaLangSystem { fn set_err_0(jvm: &mut JVM) -> Result { let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let input_stream = frame.load_local_reference(0).unwrap(); @@ -525,8 +545,9 @@ impl JavaLangSystem { fn set_out_0(jvm: &mut JVM) -> Result { let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let input_stream = frame.load_local_reference(0).unwrap(); @@ -542,8 +563,9 @@ impl JavaLangSystem { fn set_in_0(jvm: &mut JVM) -> Result { let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let input_stream = frame.load_local_reference(0).unwrap(); @@ -559,8 +581,9 @@ impl JavaLangSystem { pub fn arraycopy(jvm: &mut JVM) -> Result { let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let src = frame.load_local_reference(0).unwrap(); let src_pos = frame.load_local_int(1).unwrap(); @@ -577,6 +600,60 @@ impl JavaLangSystem { } } +struct JavaLangThread {} + +impl JavaLangThread { + pub fn start_0(jvm: &mut JVM) -> Result { + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] + }; + let this = frame.load_local_reference(0).unwrap(); + + jvm.threads.push(VirtualThread::new(this)); + // TODO: Push frames + + Ok(JVMCallbackOperation::PopFrame()) + } + pub fn set_priority_0(jvm: &mut JVM) -> Result { + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] + }; + let this = frame.load_local_reference(0).unwrap(); + let priority = frame.load_local_int(1).unwrap(); + let thread_class_index = frame.class_index; + + let holder = jvm.heap_area.object_area.get_object_field( + this, + "holder", + thread_class_index, + &jvm.class_store, + )?.expect_reference(); + + let holder_class_index = jvm.heap_area.object_area.get_reference_class_index(holder, &jvm.class_store); + jvm.heap_area.object_area.set_object_field( + holder, + "priority", + FieldValue::Int(priority), + holder_class_index, + &jvm.class_store, + )?; + + Ok(JVMCallbackOperation::PopFrame()) + } + + pub fn get_next_thread_id_offset(jvm: &mut JVM) -> Result { + Ok(JVMCallbackOperation::ReturnFrame(FieldValue::Long(0xDEADBEEF))) // this offset will be passed to getAndAddLong + } + + pub fn current_thread(jvm: &mut JVM) -> Result { + Ok(JVMCallbackOperation::ReturnFrame(jvm.active_thread_mut().thread_object.into())) + } +} + struct JavaLangThrowable {} impl JavaLangThrowable { @@ -598,13 +675,15 @@ impl JavaLangThrowable { let this = { let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &jvm.stack_frames[frame_index] + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; frame.load_local_reference(0).unwrap() }; - let stackelement_array = jvm.heap_area.make_empty_array(&jvm.class_store, AbstractTypeDescription::class_type("java/lang/StackTraceElement"), jvm.stack_frames.len()); + let frame_count = jvm.active_thread_mut().stack_frames.len(); + let stackelement_array = jvm.heap_area.make_empty_array(&jvm.class_store, AbstractTypeDescription::class_type("java/lang/StackTraceElement"), frame_count); jvm.heap_area.object_area.set_object_field( this, @@ -614,7 +693,12 @@ impl JavaLangThrowable { &jvm.class_store )?; - for (index, frame) in (&jvm.stack_frames).into_iter().enumerate() { + let active_thread_frames = { + let thread = &mut jvm.threads[jvm.active_thread]; + &mut thread.stack_frames + }; + + for (index, frame) in (active_thread_frames).into_iter().enumerate() { let class_file = jvm.class_store.class_file_from_idx(frame.class_index).unwrap(); let method_info = &class_file.methods[frame.method_index as usize]; @@ -738,9 +822,10 @@ impl JdkInternalMiscUnsafe { } pub fn compare_and_set_reference(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let object = frame.load_local_reference(1).unwrap(); @@ -769,9 +854,10 @@ impl JdkInternalMiscUnsafe { } pub fn put_reference_volatile(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let object = frame.load_local_reference(1).unwrap(); @@ -791,10 +877,28 @@ impl JdkInternalMiscUnsafe { } } + pub fn get_long_volatile(jvm: &mut JVM) -> Result { + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] + }; + + let object = frame.load_local_reference(1).unwrap(); + let offset = frame.load_local_long(2).unwrap(); + + if object == ObjectReference::NULL && offset == 0xDEADBEEF { + Ok(JVMCallbackOperation::ReturnFrame(FieldValue::Long(jvm.threads.len() as i64 - 1))) + } else { + todo!() + } + } + pub fn get_reference_volatile(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let object = frame.load_local_reference(1).unwrap(); @@ -827,9 +931,10 @@ impl JdkInternalMiscUnsafe { } pub fn compare_and_set_long(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let object = frame.load_local_reference(1).unwrap(); @@ -837,6 +942,11 @@ impl JdkInternalMiscUnsafe { let expected = frame.load_local_long(4).unwrap(); let replacement = frame.load_local_long(6).unwrap(); + if object == ObjectReference::NULL && offset == 0xDEADBEEF { + let success = jvm.threads.len() as i64 - 1 == expected; + return Ok(JVMCallbackOperation::ReturnFrame(FieldValue::Boolean(success))) + } + let object_class_descriptor = jvm.heap_area.object_area.get_reference_native_class_name(object, &jvm.class_store); let object_class_index = jvm.class_store.class_index_for_type(AbstractTypeDescription::parse_full(object_class_descriptor).unwrap()).unwrap(); @@ -860,9 +970,10 @@ impl JdkInternalMiscUnsafe { } pub fn compare_and_set_int(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let object = frame.load_local_reference(1).unwrap(); @@ -894,9 +1005,10 @@ impl JdkInternalMiscUnsafe { pub fn object_field_offset_1(jvm: &mut JVM) -> Result { // args: Class class, String fieldName - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class_object_reference = frame.load_local_reference(1).unwrap(); @@ -915,9 +1027,10 @@ impl JdkInternalMiscUnsafe { } pub fn array_index_scale_0(jvm: &mut JVM) -> Result { - let frame = { - let frame_index = jvm.stack_frames.len() - 1; - &mut jvm.stack_frames[frame_index] + let frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 1; + &mut thread.stack_frames[frame_index] }; let class = jvm.class_store.class_file_from_idx(frame.class_index).unwrap(); let method = & class.methods[frame.method_index as usize]; @@ -939,7 +1052,11 @@ struct JdkInternalReflectReflection {} impl JdkInternalReflectReflection { pub fn get_caller_class(jvm: &mut JVM) -> Result { - let caller_frame = &jvm.stack_frames[jvm.stack_frames.len() - 2]; + let caller_frame = { + let thread = &mut jvm.threads[jvm.active_thread]; + let frame_index = thread.stack_frames.len() - 2; + &mut thread.stack_frames[frame_index] + }; let caller_class_index = caller_frame.class_index; let caller_class_reference = jvm.class_store.get_class_objectref_from_index(caller_class_index); @@ -1533,7 +1650,7 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul argument_types: Box::new([]), return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Void()}, }, - todo_call + ignore_call // TODO: Unpark threads or something ), ( @@ -2246,7 +2363,7 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul ]), return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Long()}, }, - todo_call + JdkInternalMiscUnsafe::get_long_volatile ), ( @@ -2962,7 +3079,7 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul argument_types: Box::new([]), return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Classname("java/lang/Thread".to_string())}, }, - todo_call + JavaLangThread::current_thread, ), ( @@ -3053,7 +3170,7 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul ]), return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Void()}, }, - todo_call + JavaLangThread::start_0 ), ( @@ -3111,7 +3228,7 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul ]), return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Void()}, }, - todo_call + JavaLangThread::set_priority_0 ), ( @@ -3155,7 +3272,7 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul ]), return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Long()}, }, - todo_call + JavaLangThread::get_next_thread_id_offset ), ( @@ -3992,6 +4109,29 @@ pub fn function_for(class_name: &str, m: &crate::classfile::MethodInfo) -> Resul }, todo_call ), + + ( + "java/lang/ref/Finalizer", + "isFinalizationEnabled", + MethodDescriptor { + argument_types: Box::new([ + ]), + return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Boolean() }, + }, + JavaLangRefFinalizer::is_finalization_enabled + ), + + ( + "java/lang/ref/Finalizer", + "reportComplete", + MethodDescriptor { + argument_types: Box::new([ + AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Classname("java/lang/Object".to_string()) }, + ]), + return_type: AbstractTypeDescription { array_level: 0, kind: AbstractTypeKind::Void() }, + }, + todo_call + ), ]; for (classname, methodname, methoddescriptor, binding) in native_mappings { diff --git a/src/virtual_thread.rs b/src/virtual_thread.rs new file mode 100644 index 0000000..8618453 --- /dev/null +++ b/src/virtual_thread.rs @@ -0,0 +1,22 @@ + +use crate::heap_area::ObjectReference; +use crate::stackframe::StackFrame; + +#[derive(Debug)] +pub struct VirtualThread { + pub stack_frames: Vec, + pub thread_object: ObjectReference, +} + +impl VirtualThread { + pub fn new(thread_reference: ObjectReference) -> Self { + VirtualThread { + stack_frames: Vec::new(), + thread_object: thread_reference, + } + } + + pub fn add_frame(&mut self, frame: StackFrame) -> () { + self.stack_frames.push(frame) + } +}