Skip to content

Commit

Permalink
Merge pull request #2015 from fzyzcjy/feat/12125
Browse files Browse the repository at this point in the history
Detect and skip functions with generics
  • Loading branch information
fzyzcjy committed Jun 3, 2024
2 parents cabecba + 807bf29 commit 7154d2b
Show file tree
Hide file tree
Showing 9 changed files with 49 additions and 45 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ pub(crate) trait SynItemStructOrEnum: Clone {
fn attrs(&self) -> &[Attribute];

fn attrs_mut(&mut self) -> &mut Vec<Attribute>;

fn generics(&self) -> &Generics;
}

macro_rules! impl_trait {
Expand All @@ -16,6 +18,10 @@ macro_rules! impl_trait {
fn attrs_mut(&mut self) -> &mut Vec<syn::Attribute> {
&mut self.attrs
}

fn generics(&self) -> &syn::Generics {
&self.generics
}
}
};
}
Expand Down
4 changes: 4 additions & 0 deletions frb_codegen/src/library/codegen/ir/mir/skip.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ pub struct MirSkip {
#[derive(Copy, PartialOrd, Ord)]
pub(crate) enum MirSkipReason {
IgnoredFunctionNotPub,
IgnoredFunctionGeneric,
IgnoredTypeNotUsedByPub,
IgnoredMisc,
Err,
Expand All @@ -21,6 +22,9 @@ impl MirSkipReason {
Self::IgnoredFunctionNotPub => {
"These functions are ignored because they are not marked as `pub`"
}
Self::IgnoredFunctionGeneric => {
"These functions are ignored because they have generic arguments"
}
Self::IgnoredTypeNotUsedByPub => {
"These types are ignored because they are not used by any `pub` functions"
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ use crate::codegen::parser::mir::sanity_checker::auto_accessor_checker;
use crate::codegen::parser::mir::type_parser::{
TypeParser, TypeParserParsingContext, TypeParserWithContext,
};
use crate::library::codegen::ir::mir::ty::MirTypeTrait;
use crate::utils::namespace::NamespacedName;
use field::parse_auto_accessor_of_field;
use itertools::Itertools;
Expand Down Expand Up @@ -63,6 +64,9 @@ fn parse_auto_accessors_of_struct(
if !matches!(ty_direct_parse, MirType::RustAutoOpaqueImplicit(_)) {
return Ok(vec![]);
}
if ty_direct_parse.should_ignore(type_parser) {
return Ok(vec![]);
}

let ty_struct_ref = TypeParserWithContext::new(type_parser, &context)
.parse_type_path_data_struct(&(&struct_name.name, &[]), Some(false));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ use crate::codegen::ir::mir::func::{
MirFunc, MirFuncArgMode, MirFuncInput, MirFuncMode, MirFuncOutput, MirFuncOwnerInfo,
MirFuncOwnerInfoMethod, MirFuncOwnerInfoMethodMode,
};
use crate::codegen::ir::mir::skip::MirSkipReason::IgnoredFunctionGeneric;
use crate::codegen::ir::mir::skip::{MirSkip, MirSkipReason};
use crate::codegen::ir::mir::ty::primitive::MirTypePrimitive;
use crate::codegen::ir::mir::ty::rust_opaque::RustOpaqueCodecMode;
Expand Down Expand Up @@ -80,6 +81,13 @@ impl<'a, 'b> FunctionParser<'a, 'b> {
IgnoredFunctionNotPub,
));
}
if !func.sig().generics.params.is_empty() {
return Ok(create_output_skip(
func,
namespace_naive,
IgnoredFunctionGeneric,
));
}

let src_lineno = func.span().start().line;
let attributes = FrbAttributes::parse(func.attrs())?;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@ use crate::codegen::ir::hir::hierarchical::struct_or_enum::HirStructOrEnum;
use crate::codegen::ir::hir::hierarchical::syn_item_struct_or_enum::SynItemStructOrEnum;
use crate::codegen::ir::mir::ty::MirType;
use crate::codegen::parser::mir::attribute_parser::FrbAttributes;
use crate::codegen::parser::mir::type_parser::misc::parse_type_should_ignore_simple;
use crate::codegen::parser::mir::type_parser::unencodable::SplayedSegment;
use crate::library::codegen::ir::mir::ty::MirTypeTrait;
use crate::utils::crate_name::CrateName;
use crate::utils::namespace::{Namespace, NamespacedName};
use log::debug;
use std::collections::{HashMap, HashSet};
Expand Down Expand Up @@ -37,7 +37,6 @@ where

if let Some(src_object) = self.src_objects().get(*name) {
let src_object = (*src_object).clone();
let vis = src_object.visibility;

let namespace = &src_object.namespaced_name.namespace;
let namespaced_name = NamespacedName::new(namespace.clone(), name.to_string());
Expand All @@ -47,7 +46,7 @@ where
if attrs_opaque == Some(true) {
debug!("Treat {name} as opaque since attribute says so");
return Ok(Some((
self.parse_opaque(&namespaced_name, &attrs, vis)?,
self.parse_opaque(&namespaced_name, &src_object)?,
attrs,
)));
}
Expand All @@ -70,7 +69,7 @@ where
{
debug!("Treat {name} as opaque by compute_default_opaque");
return Ok(Some((
self.parse_opaque(&namespaced_name, &attrs, vis)?,
self.parse_opaque(&namespaced_name, &src_object)?,
attrs,
)));
}
Expand Down Expand Up @@ -102,15 +101,13 @@ where
fn parse_opaque(
&mut self,
namespaced_name: &NamespacedName,
attrs: &FrbAttributes,
vis: HirVisibility,
src_object: &HirStructOrEnum<Item>,
) -> anyhow::Result<MirType> {
self.parse_type_rust_auto_opaque_implicit(
Some(namespaced_name.namespace.clone()),
&syn::parse_str(&namespaced_name.name)?,
Some(parse_type_should_ignore_simple(
attrs,
vis,
Some(parse_struct_or_enum_should_ignore(
src_object,
&namespaced_name.namespace.crate_name(),
)),
)
Expand Down Expand Up @@ -170,3 +167,16 @@ fn compute_name_and_wrapper_name(
};
(namespaced_name, wrapper_name)
}

pub(crate) fn parse_struct_or_enum_should_ignore<Item: SynItemStructOrEnum>(
src_object: &HirStructOrEnum<Item>,
crate_name: &CrateName,
) -> bool {
let attrs = FrbAttributes::parse(src_object.src.attrs()).unwrap();

attrs.ignore()
// For third party crates, if a struct is not public, then it is impossible to utilize it,
// thus we ignore it.
|| (crate_name != &CrateName::self_crate() && src_object.visibility != HirVisibility::Public)
|| !src_object.src.generics().params.is_empty()
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,9 @@ use crate::codegen::ir::mir::ty::MirType;
use crate::codegen::ir::mir::ty::MirType::{Delegate, EnumRef};
use crate::codegen::parser::mir::attribute_parser::FrbAttributes;
use crate::codegen::parser::mir::type_parser::enum_or_struct::{
EnumOrStructParser, EnumOrStructParserInfo,
};
use crate::codegen::parser::mir::type_parser::misc::{
parse_comments, parse_type_should_ignore_simple,
parse_struct_or_enum_should_ignore, EnumOrStructParser, EnumOrStructParserInfo,
};
use crate::codegen::parser::mir::type_parser::misc::parse_comments;
use crate::codegen::parser::mir::type_parser::structure::structure_compute_default_opaque;
use crate::codegen::parser::mir::type_parser::unencodable::SplayedSegment;
use crate::codegen::parser::mir::type_parser::TypeParserWithContext;
Expand All @@ -39,8 +37,6 @@ impl<'a, 'b, 'c> TypeParserWithContext<'a, 'b, 'c> {
name: NamespacedName,
wrapper_name: Option<String>,
) -> anyhow::Result<MirEnum> {
let attributes = FrbAttributes::parse(&src_enum.src.attrs)?;

let comments = parse_comments(&src_enum.src.attrs);
let raw_variants = src_enum
.src
Expand All @@ -51,11 +47,7 @@ impl<'a, 'b, 'c> TypeParserWithContext<'a, 'b, 'c> {

let mode = compute_enum_mode(&raw_variants);
let variants = maybe_field_wrap_box(raw_variants, mode);
let ignore = parse_type_should_ignore_simple(
&attributes,
src_enum.visibility,
&name.namespace.crate_name(),
);
let ignore = parse_struct_or_enum_should_ignore(src_enum, &name.namespace.crate_name());

Ok(MirEnum {
name,
Expand Down
14 changes: 0 additions & 14 deletions frb_codegen/src/library/codegen/parser/mir/type_parser/misc.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,4 @@
use crate::codegen::ir::hir::hierarchical::module::HirVisibility;
use crate::codegen::ir::mir::comment::MirComment;
use crate::codegen::parser::mir::attribute_parser::FrbAttributes;
use crate::utils::crate_name::CrateName;
use itertools::Itertools;
use syn::*;

Expand Down Expand Up @@ -48,14 +45,3 @@ fn parse_comment(input: &str) -> MirComment {
format!("///{input}")
})
}

pub(crate) fn parse_type_should_ignore_simple(
attrs: &FrbAttributes,
vis: HirVisibility,
crate_name: &CrateName,
) -> bool {
attrs.ignore()
// For third party crates, if a struct is not public, then it is impossible to utilize it,
// thus we ignore it.
|| (crate_name != &CrateName::self_crate() && vis != HirVisibility::Public)
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,9 @@ use crate::codegen::ir::mir::ty::MirType;
use crate::codegen::ir::mir::ty::MirType::StructRef;
use crate::codegen::parser::mir::attribute_parser::FrbAttributes;
use crate::codegen::parser::mir::type_parser::enum_or_struct::{
EnumOrStructParser, EnumOrStructParserInfo,
};
use crate::codegen::parser::mir::type_parser::misc::{
parse_comments, parse_type_should_ignore_simple,
parse_struct_or_enum_should_ignore, EnumOrStructParser, EnumOrStructParserInfo,
};
use crate::codegen::parser::mir::type_parser::misc::parse_comments;
use crate::codegen::parser::mir::type_parser::unencodable::SplayedSegment;
use crate::codegen::parser::mir::type_parser::TypeParserWithContext;
use crate::utils::namespace::{Namespace, NamespacedName};
Expand Down Expand Up @@ -53,11 +51,7 @@ impl<'a, 'b, 'c> TypeParserWithContext<'a, 'b, 'c> {
let attributes = FrbAttributes::parse(&src_struct.src.attrs)?;
let dart_metadata = attributes.dart_metadata();

let ignore = parse_type_should_ignore_simple(
&attributes,
src_struct.visibility,
&name.namespace.crate_name(),
);
let ignore = parse_struct_or_enum_should_ignore(src_struct, &name.namespace.crate_name());

Ok(MirStruct {
name,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"enum_pool": {
"crate::api/MyGenericEnum": {
"comments": [],
"ignore": false,
"ignore": true,
"mode": "Complex",
"name": "crate::api/MyGenericEnum",
"variants": [
Expand Down Expand Up @@ -528,7 +528,7 @@
],
"generate_eq": true,
"generate_hash": true,
"ignore": false,
"ignore": true,
"is_fields_named": true,
"name": "crate::api/MyGenericStruct",
"wrapper_name": null
Expand Down

0 comments on commit 7154d2b

Please sign in to comment.