Skip to content

Commit

Permalink
feat(ast, ast_macros): apply stable_repr to all #[ast] items.
Browse files Browse the repository at this point in the history
  • Loading branch information
rzvxa committed Jul 30, 2024
1 parent c9c38a1 commit c28e09d
Show file tree
Hide file tree
Showing 7 changed files with 50 additions and 39 deletions.
5 changes: 5 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

16 changes: 0 additions & 16 deletions crates/oxc_ast/src/ast/js.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -269,7 +268,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize))]
#[serde(untagged)]
Expand Down Expand Up @@ -359,7 +357,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -436,7 +433,6 @@ pub struct TemplateElementValue<'a> {

/// <https://tc39.es/ecma262/#prod-MemberExpression>
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -597,7 +593,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -706,7 +701,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand All @@ -725,7 +719,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -780,7 +773,6 @@ macro_rules! match_simple_assignment_target {
pub use match_simple_assignment_target;

#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -846,7 +838,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -949,7 +940,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -979,7 +969,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -1050,7 +1039,6 @@ pub struct BlockStatement<'a> {

/// Declarations and the Variable Statement
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -1217,7 +1205,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -1251,7 +1238,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -2000,7 +1986,6 @@ pub struct StaticBlock<'a> {
/// export as namespace d; // TSNamespaceExportDeclaration
/// ```
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -2303,7 +2288,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down
1 change: 0 additions & 1 deletion crates/oxc_ast/src/ast/jsx.rs
Original file line number Diff line number Diff line change
Expand Up @@ -240,7 +240,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down
4 changes: 2 additions & 2 deletions crates/oxc_ast/src/ast/macros.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
///
/// ```
/// inherit_variants! {
/// #[repr(C, u8)]
/// #[ast]
/// enum Statement<'a> {
/// pub enum Statement<'a> {
/// BlockStatement(Box<'a, BlockStatement<'a>>) = 0,
Expand All @@ -35,7 +35,7 @@
/// expands to:
///
/// ```
/// #[repr(C, u8)]
/// #[ast]
/// enum Statement<'a> {
/// pub enum Statement<'a> {
/// BlockStatement(Box<'a, BlockStatement<'a>>) = 0,
Expand Down
6 changes: 0 additions & 6 deletions crates/oxc_ast/src/ast/ts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -191,7 +190,6 @@ pub enum TSLiteral<'a> {
/// This is the root-level type for TypeScript types, kind of like [`Expression`] is for
/// expressions.
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged, rename_all = "camelCase")]
Expand Down Expand Up @@ -483,7 +481,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged, rename_all = "camelCase")]
Expand Down Expand Up @@ -642,7 +639,6 @@ pub struct TSTypeReference<'a> {
/// IdentifierReference
/// NamespaceName . IdentifierReference
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -1035,7 +1031,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged)]
Expand Down Expand Up @@ -1208,7 +1203,6 @@ inherit_variants! {
///
/// [`ast` module docs]: `super`
#[ast(visit)]
#[repr(C, u8)]
#[derive(Debug, Hash)]
#[cfg_attr(feature = "serialize", derive(Serialize, Tsify))]
#[serde(untagged, rename_all = "camelCase")]
Expand Down
5 changes: 5 additions & 0 deletions crates/oxc_ast_macros/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -19,3 +19,8 @@ workspace = true
[lib]
proc-macro = true
doctest = false

[dependencies]
quote = { workspace = true }
syn = { workspace = true, features = ["full"] }
proc-macro2 = { workspace = true }
52 changes: 38 additions & 14 deletions crates/oxc_ast_macros/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,30 +1,54 @@
use proc_macro::TokenStream;
use std::str::FromStr;
use proc_macro2::TokenStream as TokenStream2;
use quote::quote;

/// Attach to AST node type (struct or enum), to signal to codegen to create visitor for this type.
///
/// Macro's role is not to generate code - it's purely a means to communicate information to the codegen.
///
/// Only thing macro does is add `#[derive(Ast)]` to the item.
/// Deriving `Ast` does nothing, but supports `#[scope]`, `#[visit]`, and other attrs on struct fields.
/// These "helper" attributes are also signals to the codegen, and do nothing in themselves.
/// returns `#[repr(C, u8)]` if `enum_` has any non-unit variant,
/// Otherwise it would return `#[repr(C)]`.
fn enum_repr(enum_: &syn::ItemEnum) -> TokenStream2 {
if enum_.variants.iter().any(|var| !matches!(var.fields, syn::Fields::Unit)) {
quote!(#[repr(C, u8)])
} else {
quote!(#[repr(C)])
}
}

/// This attribute serves two purposes,
/// First, it is a marker for our codegen to detect AST types. Furthermore.
/// It is also a lightweight macro; All of its computation is cached and
/// it only applies the following changes without any complex operation:
///
/// This is a workaround for Rust not supporting helper attributes for `proc_macro_attribute` macros,
/// so we need to use a derive macro to get that support.
/// * Prepend `#[repr(C)]` to structs
/// * Prepend `#[repr(C, u8)]` to enums
/// * Prepend `#[repr(C)]` to unit enums
/// * Prepend `#[derive(oxc_ast_macros::Ast)]`
///
/// Use native Rust `TokenStream`, to avoid dependency on slow-compiling crates like `syn` and `quote`.
#[proc_macro_attribute]
#[allow(clippy::missing_panics_doc)]
pub fn ast(_args: TokenStream, input: TokenStream) -> TokenStream {
let mut stream = TokenStream::from_str("#[derive(::oxc_ast_macros::Ast)]").unwrap();
stream.extend(input);
stream
let input = syn::parse_macro_input!(input as syn::Item);

let repr = match input {
syn::Item::Enum(ref enum_) => enum_repr(enum_),
syn::Item::Struct(_) => TokenStream2::default(),

_ => {
unreachable!()
}
};

let expanded = quote! {
#[derive(::oxc_ast_macros::Ast)]
#repr
#input
};
TokenStream::from(expanded)
}

/// Dummy derive macro for a non-existent trait `Ast`.
///
/// Does not generate any code.
/// Only purpose is to allow using `#[scope]`, `#[visit]`, and other attrs in the AST node type defs.
/// These "marker" attributes are used in codegen.
#[proc_macro_derive(Ast, attributes(span, scope, visit, visit_as, visit_args, serde, tsify))]
pub fn ast_derive(_item: TokenStream) -> TokenStream {
TokenStream::new()
Expand Down

0 comments on commit c28e09d

Please sign in to comment.