From 46a5b9bb0e290e64f81cea5f5a2f8e5fa3ba8cb8 Mon Sep 17 00:00:00 2001 From: Janis Date: Sat, 17 Jun 2023 16:49:46 +0200 Subject: [PATCH] parse ufunction into ClassMethod --- src/sdk/process.rs | 71 +++++++++++++++++++++++++++++++++++----------- 1 file changed, 55 insertions(+), 16 deletions(-) diff --git a/src/sdk/process.rs b/src/sdk/process.rs index e6285d9..c971e09 100644 --- a/src/sdk/process.rs +++ b/src/sdk/process.rs @@ -93,40 +93,79 @@ impl ClassField { } impl ClassMethod { - pub fn from_ufunction(value: UFunction) -> anyhow::Result { - todo!() + pub fn from_ufunction(func: UFunction) -> anyhow::Result { + let name = func.get_name().context("could not get function name")?; + let full_name = func + .get_full_name() + .context("could not get full function name")?; + + let params = func + .iter_children() + .filter_map(|field| match AnyField::from_field(field) { + AnyField::Property(prop) => Some(prop), + _ => None, + }) + .map(|prop| -> anyhow::Result> { + let param = ClassField { + offset: *prop.offset() as u32, + size: *prop.element_size() as u32, + name: prop.get_name().context("failed to get property name")?, + flags: *prop.property_flags(), + ty: if let Ok(ty) = resolve_type(prop) { + ty + } else { + log::warn!("skipping field {} with offset 0x{:x}", prop, prop.offset()); + return Ok(None); + }, + }; + + Ok(Some(param)) + }) + .fold_ok(Vec::new(), |mut acc, field| { + acc.extend(field); + acc + })?; + + Ok(ClassMethod { + name, + full_name, + flags: *func.function_flags(), + parameters: params, + }) } } impl Package { pub fn process(self) -> anyhow::Result { - self.children.par_iter().filter_map(|&object| { - match AnyObject::from_object(object) { - AnyObject::Field(field) => match AnyField::from_field(field) { - AnyField::Enum(my_enum) => {} - AnyField::Struct(my_struct) => match AnyStruct::from_struct(my_struct) { - my_struct @ AnyStruct::Class(_) - | my_struct @ AnyStruct::ScriptStruct(_) => {} + self.children + .par_iter() + .filter_map(|&object| -> Option { + match AnyObject::from_object(object) { + AnyObject::Field(field) => match AnyField::from_field(field) { + AnyField::Enum(my_enum) => {} + AnyField::Struct(my_struct) => match AnyStruct::from_struct(my_struct) { + my_struct @ AnyStruct::Class(_) + | my_struct @ AnyStruct::ScriptStruct(_) => {} + _ => {} + }, _ => {} }, _ => {} - }, - _ => {} - } + } - todo!() - }); + todo!() + }); todo!() } } fn resolve_type(prop: UProperty) -> anyhow::Result { - let ty = match AnyField::from(prop.clone()) { + let ty = match AnyProperty::from_prop(prop.clone()) { numeric @ AnyProperty::Numeric(_) => match numeric.as_any_numeric_property().unwrap() { any_type::AnyNumericProperty::U8(prop) => match prop.uenum() { Some(enm) => Type::Enum { underlying: Box::new(Type::Primitive(PrimitiveType::U8)), - enum_type: *enm, + enum_type: enm.as_uobject().object_ref(), }, None => Type::Primitive(PrimitiveType::U8), },