Skip to content

Commit a390aff

Browse files
committed
Fix vector/hashtable collection
1 parent 0d0439d commit a390aff

File tree

2 files changed

+20
-21
lines changed

2 files changed

+20
-21
lines changed

jvm/src/garbage_collector.rs

Lines changed: 19 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -44,27 +44,26 @@ fn find_reachable_objects(jvm: &Jvm, object: &Box<dyn ClassInstance>, reachable_
4444
}
4545
entry.insert();
4646

47-
let fields = object.class_definition().fields();
47+
// XXX we have to deal with java value wrapped inside rust type e.g. java.util.Vector, java.util.Hashtable
48+
if jvm.is_instance(&**object, "java/util/Vector") {
49+
let members = vector_members(jvm, &**object);
50+
for member in members {
51+
find_reachable_objects(jvm, &member, reachable_objects);
52+
}
53+
} else if jvm.is_instance(&**object, "java/util/Hashtable") {
54+
let members = hashtable_members(jvm, &**object);
55+
for member in members {
56+
find_reachable_objects(jvm, &member, reachable_objects);
57+
}
58+
}
4859

60+
let fields = object.class_definition().fields();
4961
for field in fields {
5062
match field.r#type() {
5163
JavaType::Class(_) => {
5264
let value = object.get_field(&*field).unwrap();
5365
if let JavaValue::Object(Some(value)) = value {
5466
find_reachable_objects(jvm, &value, reachable_objects);
55-
56-
// XXX we have to deal with java value wrapped inside rust type e.g. java.util.Vector, java.util.Hashtable
57-
if jvm.is_instance(&*value, "java/util/Vector") {
58-
let members = vector_members(&*value);
59-
for member in members {
60-
find_reachable_objects(jvm, &member, reachable_objects);
61-
}
62-
} else if jvm.is_instance(&*value, "java/util/Hashtable") {
63-
let members = hashtable_members(&*value);
64-
for member in members {
65-
find_reachable_objects(jvm, &member, reachable_objects);
66-
}
67-
}
6867
}
6968
}
7069
JavaType::Array(_) => {
@@ -88,8 +87,8 @@ fn find_reachable_objects(jvm: &Jvm, object: &Box<dyn ClassInstance>, reachable_
8887
}
8988

9089
// Same as Jvm's one but without async
91-
fn get_rust_object_field<T: Clone>(object: &dyn ClassInstance, field_name: &str) -> T {
92-
let field = object.class_definition().field(field_name, "Ljava/lang/Object;", true).unwrap();
90+
fn get_rust_object_field<T: Clone>(jvm: &Jvm, object: &dyn ClassInstance, field_name: &str) -> T {
91+
let field = jvm.find_field(&*object.class_definition(), field_name, "[B").unwrap().unwrap();
9392
let value = object.get_field(&*field).unwrap();
9493
let buf: Vec<i8> = match value {
9594
JavaValue::Object(Some(value)) => {
@@ -110,15 +109,15 @@ fn get_rust_object_field<T: Clone>(object: &dyn ClassInstance, field_name: &str)
110109
result
111110
}
112111

113-
fn vector_members(vector: &dyn ClassInstance) -> Vec<Box<dyn ClassInstance>> {
114-
let rust_vector: RustVector = get_rust_object_field(vector, "raw");
112+
fn vector_members(jvm: &Jvm, vector: &dyn ClassInstance) -> Vec<Box<dyn ClassInstance>> {
113+
let rust_vector: RustVector = get_rust_object_field(jvm, vector, "raw");
115114

116115
let rust_vector = rust_vector.lock();
117116
rust_vector.iter().cloned().collect()
118117
}
119118

120-
fn hashtable_members(hashtable: &dyn ClassInstance) -> Vec<Box<dyn ClassInstance>> {
121-
let rust_hashmap: RustHashMap = get_rust_object_field(hashtable, "raw");
119+
fn hashtable_members(jvm: &Jvm, hashtable: &dyn ClassInstance) -> Vec<Box<dyn ClassInstance>> {
120+
let rust_hashmap: RustHashMap = get_rust_object_field(jvm, hashtable, "raw");
122121

123122
let rust_hashmap = rust_hashmap.lock();
124123
rust_hashmap.iter().flat_map(|(_, v)| v.iter().map(|x| x.1.clone())).collect()

jvm/src/jvm.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -716,7 +716,7 @@ impl Jvm {
716716
}
717717
}
718718

719-
fn find_field(&self, class: &dyn ClassDefinition, name: &str, descriptor: &str) -> Result<Option<Box<dyn Field>>> {
719+
pub(crate) fn find_field(&self, class: &dyn ClassDefinition, name: &str, descriptor: &str) -> Result<Option<Box<dyn Field>>> {
720720
let field = class.field(name, descriptor, false);
721721

722722
if let Some(x) = field {

0 commit comments

Comments
 (0)