1 use super::*; 2 use crate::derive::{Data, DataEnum, DataStruct, DataUnion, DeriveInput}; 3 use crate::punctuated::Punctuated; 4 use proc_macro2::TokenStream; 5 6 #[cfg(feature = "parsing")] 7 use std::mem; 8 9 ast_enum_of_structs! { 10 /// Things that can appear directly inside of a module or scope. 11 /// 12 /// *This type is available only if Syn is built with the `"full"` feature.* 13 /// 14 /// # Syntax tree enum 15 /// 16 /// This type is a [syntax tree enum]. 17 /// 18 /// [syntax tree enum]: Expr#syntax-tree-enums 19 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 20 #[cfg_attr(not(syn_no_non_exhaustive), non_exhaustive)] 21 pub enum Item { 22 /// A constant item: `const MAX: u16 = 65535`. 23 Const(ItemConst), 24 25 /// An enum definition: `enum Foo<A, B> { A(A), B(B) }`. 26 Enum(ItemEnum), 27 28 /// An `extern crate` item: `extern crate serde`. 29 ExternCrate(ItemExternCrate), 30 31 /// A free-standing function: `fn process(n: usize) -> Result<()> { ... 32 /// }`. 33 Fn(ItemFn), 34 35 /// A block of foreign items: `extern "C" { ... }`. 36 ForeignMod(ItemForeignMod), 37 38 /// An impl block providing trait or associated items: `impl<A> Trait 39 /// for Data<A> { ... }`. 40 Impl(ItemImpl), 41 42 /// A macro invocation, which includes `macro_rules!` definitions. 43 Macro(ItemMacro), 44 45 /// A 2.0-style declarative macro introduced by the `macro` keyword. 46 Macro2(ItemMacro2), 47 48 /// A module or module declaration: `mod m` or `mod m { ... }`. 49 Mod(ItemMod), 50 51 /// A static item: `static BIKE: Shed = Shed(42)`. 52 Static(ItemStatic), 53 54 /// A struct definition: `struct Foo<A> { x: A }`. 55 Struct(ItemStruct), 56 57 /// A trait definition: `pub trait Iterator { ... }`. 58 Trait(ItemTrait), 59 60 /// A trait alias: `pub trait SharableIterator = Iterator + Sync`. 61 TraitAlias(ItemTraitAlias), 62 63 /// A type alias: `type Result<T> = std::result::Result<T, MyError>`. 64 Type(ItemType), 65 66 /// A union definition: `union Foo<A, B> { x: A, y: B }`. 67 Union(ItemUnion), 68 69 /// A use declaration: `use std::collections::HashMap`. 70 Use(ItemUse), 71 72 /// Tokens forming an item not interpreted by Syn. 73 Verbatim(TokenStream), 74 75 // Not public API. 76 // 77 // For testing exhaustiveness in downstream code, use the following idiom: 78 // 79 // match item { 80 // Item::Const(item) => {...} 81 // Item::Enum(item) => {...} 82 // ... 83 // Item::Verbatim(item) => {...} 84 // 85 // #[cfg_attr(test, deny(non_exhaustive_omitted_patterns))] 86 // _ => { /* some sane fallback */ } 87 // } 88 // 89 // This way we fail your tests but don't break your library when adding 90 // a variant. You will be notified by a test failure when a variant is 91 // added, so that you can add code to handle it, but your library will 92 // continue to compile and work for downstream users in the interim. 93 #[cfg(syn_no_non_exhaustive)] 94 #[doc(hidden)] 95 __NonExhaustive, 96 } 97 } 98 99 ast_struct! { 100 /// A constant item: `const MAX: u16 = 65535`. 101 /// 102 /// *This type is available only if Syn is built with the `"full"` feature.* 103 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 104 pub struct ItemConst { 105 pub attrs: Vec<Attribute>, 106 pub vis: Visibility, 107 pub const_token: Token![const], 108 pub ident: Ident, 109 pub colon_token: Token![:], 110 pub ty: Box<Type>, 111 pub eq_token: Token![=], 112 pub expr: Box<Expr>, 113 pub semi_token: Token![;], 114 } 115 } 116 117 ast_struct! { 118 /// An enum definition: `enum Foo<A, B> { A(A), B(B) }`. 119 /// 120 /// *This type is available only if Syn is built with the `"full"` feature.* 121 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 122 pub struct ItemEnum { 123 pub attrs: Vec<Attribute>, 124 pub vis: Visibility, 125 pub enum_token: Token![enum], 126 pub ident: Ident, 127 pub generics: Generics, 128 pub brace_token: token::Brace, 129 pub variants: Punctuated<Variant, Token![,]>, 130 } 131 } 132 133 ast_struct! { 134 /// An `extern crate` item: `extern crate serde`. 135 /// 136 /// *This type is available only if Syn is built with the `"full"` feature.* 137 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 138 pub struct ItemExternCrate { 139 pub attrs: Vec<Attribute>, 140 pub vis: Visibility, 141 pub extern_token: Token![extern], 142 pub crate_token: Token![crate], 143 pub ident: Ident, 144 pub rename: Option<(Token![as], Ident)>, 145 pub semi_token: Token![;], 146 } 147 } 148 149 ast_struct! { 150 /// A free-standing function: `fn process(n: usize) -> Result<()> { ... 151 /// }`. 152 /// 153 /// *This type is available only if Syn is built with the `"full"` feature.* 154 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 155 pub struct ItemFn { 156 pub attrs: Vec<Attribute>, 157 pub vis: Visibility, 158 pub sig: Signature, 159 pub block: Box<Block>, 160 } 161 } 162 163 ast_struct! { 164 /// A block of foreign items: `extern "C" { ... }`. 165 /// 166 /// *This type is available only if Syn is built with the `"full"` feature.* 167 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 168 pub struct ItemForeignMod { 169 pub attrs: Vec<Attribute>, 170 pub abi: Abi, 171 pub brace_token: token::Brace, 172 pub items: Vec<ForeignItem>, 173 } 174 } 175 176 ast_struct! { 177 /// An impl block providing trait or associated items: `impl<A> Trait 178 /// for Data<A> { ... }`. 179 /// 180 /// *This type is available only if Syn is built with the `"full"` feature.* 181 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 182 pub struct ItemImpl { 183 pub attrs: Vec<Attribute>, 184 pub defaultness: Option<Token![default]>, 185 pub unsafety: Option<Token![unsafe]>, 186 pub impl_token: Token![impl], 187 pub generics: Generics, 188 /// Trait this impl implements. 189 pub trait_: Option<(Option<Token![!]>, Path, Token![for])>, 190 /// The Self type of the impl. 191 pub self_ty: Box<Type>, 192 pub brace_token: token::Brace, 193 pub items: Vec<ImplItem>, 194 } 195 } 196 197 ast_struct! { 198 /// A macro invocation, which includes `macro_rules!` definitions. 199 /// 200 /// *This type is available only if Syn is built with the `"full"` feature.* 201 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 202 pub struct ItemMacro { 203 pub attrs: Vec<Attribute>, 204 /// The `example` in `macro_rules! example { ... }`. 205 pub ident: Option<Ident>, 206 pub mac: Macro, 207 pub semi_token: Option<Token![;]>, 208 } 209 } 210 211 ast_struct! { 212 /// A 2.0-style declarative macro introduced by the `macro` keyword. 213 /// 214 /// *This type is available only if Syn is built with the `"full"` feature.* 215 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 216 pub struct ItemMacro2 { 217 pub attrs: Vec<Attribute>, 218 pub vis: Visibility, 219 pub macro_token: Token![macro], 220 pub ident: Ident, 221 pub rules: TokenStream, 222 } 223 } 224 225 ast_struct! { 226 /// A module or module declaration: `mod m` or `mod m { ... }`. 227 /// 228 /// *This type is available only if Syn is built with the `"full"` feature.* 229 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 230 pub struct ItemMod { 231 pub attrs: Vec<Attribute>, 232 pub vis: Visibility, 233 pub mod_token: Token![mod], 234 pub ident: Ident, 235 pub content: Option<(token::Brace, Vec<Item>)>, 236 pub semi: Option<Token![;]>, 237 } 238 } 239 240 ast_struct! { 241 /// A static item: `static BIKE: Shed = Shed(42)`. 242 /// 243 /// *This type is available only if Syn is built with the `"full"` feature.* 244 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 245 pub struct ItemStatic { 246 pub attrs: Vec<Attribute>, 247 pub vis: Visibility, 248 pub static_token: Token![static], 249 pub mutability: Option<Token![mut]>, 250 pub ident: Ident, 251 pub colon_token: Token![:], 252 pub ty: Box<Type>, 253 pub eq_token: Token![=], 254 pub expr: Box<Expr>, 255 pub semi_token: Token![;], 256 } 257 } 258 259 ast_struct! { 260 /// A struct definition: `struct Foo<A> { x: A }`. 261 /// 262 /// *This type is available only if Syn is built with the `"full"` feature.* 263 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 264 pub struct ItemStruct { 265 pub attrs: Vec<Attribute>, 266 pub vis: Visibility, 267 pub struct_token: Token![struct], 268 pub ident: Ident, 269 pub generics: Generics, 270 pub fields: Fields, 271 pub semi_token: Option<Token![;]>, 272 } 273 } 274 275 ast_struct! { 276 /// A trait definition: `pub trait Iterator { ... }`. 277 /// 278 /// *This type is available only if Syn is built with the `"full"` feature.* 279 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 280 pub struct ItemTrait { 281 pub attrs: Vec<Attribute>, 282 pub vis: Visibility, 283 pub unsafety: Option<Token![unsafe]>, 284 pub auto_token: Option<Token![auto]>, 285 pub trait_token: Token![trait], 286 pub ident: Ident, 287 pub generics: Generics, 288 pub colon_token: Option<Token![:]>, 289 pub supertraits: Punctuated<TypeParamBound, Token![+]>, 290 pub brace_token: token::Brace, 291 pub items: Vec<TraitItem>, 292 } 293 } 294 295 ast_struct! { 296 /// A trait alias: `pub trait SharableIterator = Iterator + Sync`. 297 /// 298 /// *This type is available only if Syn is built with the `"full"` feature.* 299 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 300 pub struct ItemTraitAlias { 301 pub attrs: Vec<Attribute>, 302 pub vis: Visibility, 303 pub trait_token: Token![trait], 304 pub ident: Ident, 305 pub generics: Generics, 306 pub eq_token: Token![=], 307 pub bounds: Punctuated<TypeParamBound, Token![+]>, 308 pub semi_token: Token![;], 309 } 310 } 311 312 ast_struct! { 313 /// A type alias: `type Result<T> = std::result::Result<T, MyError>`. 314 /// 315 /// *This type is available only if Syn is built with the `"full"` feature.* 316 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 317 pub struct ItemType { 318 pub attrs: Vec<Attribute>, 319 pub vis: Visibility, 320 pub type_token: Token![type], 321 pub ident: Ident, 322 pub generics: Generics, 323 pub eq_token: Token![=], 324 pub ty: Box<Type>, 325 pub semi_token: Token![;], 326 } 327 } 328 329 ast_struct! { 330 /// A union definition: `union Foo<A, B> { x: A, y: B }`. 331 /// 332 /// *This type is available only if Syn is built with the `"full"` feature.* 333 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 334 pub struct ItemUnion { 335 pub attrs: Vec<Attribute>, 336 pub vis: Visibility, 337 pub union_token: Token![union], 338 pub ident: Ident, 339 pub generics: Generics, 340 pub fields: FieldsNamed, 341 } 342 } 343 344 ast_struct! { 345 /// A use declaration: `use std::collections::HashMap`. 346 /// 347 /// *This type is available only if Syn is built with the `"full"` feature.* 348 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 349 pub struct ItemUse { 350 pub attrs: Vec<Attribute>, 351 pub vis: Visibility, 352 pub use_token: Token![use], 353 pub leading_colon: Option<Token![::]>, 354 pub tree: UseTree, 355 pub semi_token: Token![;], 356 } 357 } 358 359 impl Item { 360 #[cfg(feature = "parsing")] replace_attrs(&mut self, new: Vec<Attribute>) -> Vec<Attribute>361 pub(crate) fn replace_attrs(&mut self, new: Vec<Attribute>) -> Vec<Attribute> { 362 match self { 363 Item::ExternCrate(ItemExternCrate { attrs, .. }) 364 | Item::Use(ItemUse { attrs, .. }) 365 | Item::Static(ItemStatic { attrs, .. }) 366 | Item::Const(ItemConst { attrs, .. }) 367 | Item::Fn(ItemFn { attrs, .. }) 368 | Item::Mod(ItemMod { attrs, .. }) 369 | Item::ForeignMod(ItemForeignMod { attrs, .. }) 370 | Item::Type(ItemType { attrs, .. }) 371 | Item::Struct(ItemStruct { attrs, .. }) 372 | Item::Enum(ItemEnum { attrs, .. }) 373 | Item::Union(ItemUnion { attrs, .. }) 374 | Item::Trait(ItemTrait { attrs, .. }) 375 | Item::TraitAlias(ItemTraitAlias { attrs, .. }) 376 | Item::Impl(ItemImpl { attrs, .. }) 377 | Item::Macro(ItemMacro { attrs, .. }) 378 | Item::Macro2(ItemMacro2 { attrs, .. }) => mem::replace(attrs, new), 379 Item::Verbatim(_) => Vec::new(), 380 381 #[cfg(syn_no_non_exhaustive)] 382 _ => unreachable!(), 383 } 384 } 385 } 386 387 impl From<DeriveInput> for Item { from(input: DeriveInput) -> Item388 fn from(input: DeriveInput) -> Item { 389 match input.data { 390 Data::Struct(data) => Item::Struct(ItemStruct { 391 attrs: input.attrs, 392 vis: input.vis, 393 struct_token: data.struct_token, 394 ident: input.ident, 395 generics: input.generics, 396 fields: data.fields, 397 semi_token: data.semi_token, 398 }), 399 Data::Enum(data) => Item::Enum(ItemEnum { 400 attrs: input.attrs, 401 vis: input.vis, 402 enum_token: data.enum_token, 403 ident: input.ident, 404 generics: input.generics, 405 brace_token: data.brace_token, 406 variants: data.variants, 407 }), 408 Data::Union(data) => Item::Union(ItemUnion { 409 attrs: input.attrs, 410 vis: input.vis, 411 union_token: data.union_token, 412 ident: input.ident, 413 generics: input.generics, 414 fields: data.fields, 415 }), 416 } 417 } 418 } 419 420 impl From<ItemStruct> for DeriveInput { from(input: ItemStruct) -> DeriveInput421 fn from(input: ItemStruct) -> DeriveInput { 422 DeriveInput { 423 attrs: input.attrs, 424 vis: input.vis, 425 ident: input.ident, 426 generics: input.generics, 427 data: Data::Struct(DataStruct { 428 struct_token: input.struct_token, 429 fields: input.fields, 430 semi_token: input.semi_token, 431 }), 432 } 433 } 434 } 435 436 impl From<ItemEnum> for DeriveInput { from(input: ItemEnum) -> DeriveInput437 fn from(input: ItemEnum) -> DeriveInput { 438 DeriveInput { 439 attrs: input.attrs, 440 vis: input.vis, 441 ident: input.ident, 442 generics: input.generics, 443 data: Data::Enum(DataEnum { 444 enum_token: input.enum_token, 445 brace_token: input.brace_token, 446 variants: input.variants, 447 }), 448 } 449 } 450 } 451 452 impl From<ItemUnion> for DeriveInput { from(input: ItemUnion) -> DeriveInput453 fn from(input: ItemUnion) -> DeriveInput { 454 DeriveInput { 455 attrs: input.attrs, 456 vis: input.vis, 457 ident: input.ident, 458 generics: input.generics, 459 data: Data::Union(DataUnion { 460 union_token: input.union_token, 461 fields: input.fields, 462 }), 463 } 464 } 465 } 466 467 ast_enum_of_structs! { 468 /// A suffix of an import tree in a `use` item: `Type as Renamed` or `*`. 469 /// 470 /// *This type is available only if Syn is built with the `"full"` feature.* 471 /// 472 /// # Syntax tree enum 473 /// 474 /// This type is a [syntax tree enum]. 475 /// 476 /// [syntax tree enum]: Expr#syntax-tree-enums 477 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 478 pub enum UseTree { 479 /// A path prefix of imports in a `use` item: `std::...`. 480 Path(UsePath), 481 482 /// An identifier imported by a `use` item: `HashMap`. 483 Name(UseName), 484 485 /// An renamed identifier imported by a `use` item: `HashMap as Map`. 486 Rename(UseRename), 487 488 /// A glob import in a `use` item: `*`. 489 Glob(UseGlob), 490 491 /// A braced group of imports in a `use` item: `{A, B, C}`. 492 Group(UseGroup), 493 } 494 } 495 496 ast_struct! { 497 /// A path prefix of imports in a `use` item: `std::...`. 498 /// 499 /// *This type is available only if Syn is built with the `"full"` feature.* 500 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 501 pub struct UsePath { 502 pub ident: Ident, 503 pub colon2_token: Token![::], 504 pub tree: Box<UseTree>, 505 } 506 } 507 508 ast_struct! { 509 /// An identifier imported by a `use` item: `HashMap`. 510 /// 511 /// *This type is available only if Syn is built with the `"full"` feature.* 512 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 513 pub struct UseName { 514 pub ident: Ident, 515 } 516 } 517 518 ast_struct! { 519 /// An renamed identifier imported by a `use` item: `HashMap as Map`. 520 /// 521 /// *This type is available only if Syn is built with the `"full"` feature.* 522 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 523 pub struct UseRename { 524 pub ident: Ident, 525 pub as_token: Token![as], 526 pub rename: Ident, 527 } 528 } 529 530 ast_struct! { 531 /// A glob import in a `use` item: `*`. 532 /// 533 /// *This type is available only if Syn is built with the `"full"` feature.* 534 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 535 pub struct UseGlob { 536 pub star_token: Token![*], 537 } 538 } 539 540 ast_struct! { 541 /// A braced group of imports in a `use` item: `{A, B, C}`. 542 /// 543 /// *This type is available only if Syn is built with the `"full"` feature.* 544 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 545 pub struct UseGroup { 546 pub brace_token: token::Brace, 547 pub items: Punctuated<UseTree, Token![,]>, 548 } 549 } 550 551 ast_enum_of_structs! { 552 /// An item within an `extern` block. 553 /// 554 /// *This type is available only if Syn is built with the `"full"` feature.* 555 /// 556 /// # Syntax tree enum 557 /// 558 /// This type is a [syntax tree enum]. 559 /// 560 /// [syntax tree enum]: Expr#syntax-tree-enums 561 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 562 #[cfg_attr(not(syn_no_non_exhaustive), non_exhaustive)] 563 pub enum ForeignItem { 564 /// A foreign function in an `extern` block. 565 Fn(ForeignItemFn), 566 567 /// A foreign static item in an `extern` block: `static ext: u8`. 568 Static(ForeignItemStatic), 569 570 /// A foreign type in an `extern` block: `type void`. 571 Type(ForeignItemType), 572 573 /// A macro invocation within an extern block. 574 Macro(ForeignItemMacro), 575 576 /// Tokens in an `extern` block not interpreted by Syn. 577 Verbatim(TokenStream), 578 579 // Not public API. 580 // 581 // For testing exhaustiveness in downstream code, use the following idiom: 582 // 583 // match item { 584 // ForeignItem::Fn(item) => {...} 585 // ForeignItem::Static(item) => {...} 586 // ... 587 // ForeignItem::Verbatim(item) => {...} 588 // 589 // #[cfg_attr(test, deny(non_exhaustive_omitted_patterns))] 590 // _ => { /* some sane fallback */ } 591 // } 592 // 593 // This way we fail your tests but don't break your library when adding 594 // a variant. You will be notified by a test failure when a variant is 595 // added, so that you can add code to handle it, but your library will 596 // continue to compile and work for downstream users in the interim. 597 #[cfg(syn_no_non_exhaustive)] 598 #[doc(hidden)] 599 __NonExhaustive, 600 } 601 } 602 603 ast_struct! { 604 /// A foreign function in an `extern` block. 605 /// 606 /// *This type is available only if Syn is built with the `"full"` feature.* 607 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 608 pub struct ForeignItemFn { 609 pub attrs: Vec<Attribute>, 610 pub vis: Visibility, 611 pub sig: Signature, 612 pub semi_token: Token![;], 613 } 614 } 615 616 ast_struct! { 617 /// A foreign static item in an `extern` block: `static ext: u8`. 618 /// 619 /// *This type is available only if Syn is built with the `"full"` feature.* 620 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 621 pub struct ForeignItemStatic { 622 pub attrs: Vec<Attribute>, 623 pub vis: Visibility, 624 pub static_token: Token![static], 625 pub mutability: Option<Token![mut]>, 626 pub ident: Ident, 627 pub colon_token: Token![:], 628 pub ty: Box<Type>, 629 pub semi_token: Token![;], 630 } 631 } 632 633 ast_struct! { 634 /// A foreign type in an `extern` block: `type void`. 635 /// 636 /// *This type is available only if Syn is built with the `"full"` feature.* 637 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 638 pub struct ForeignItemType { 639 pub attrs: Vec<Attribute>, 640 pub vis: Visibility, 641 pub type_token: Token![type], 642 pub ident: Ident, 643 pub semi_token: Token![;], 644 } 645 } 646 647 ast_struct! { 648 /// A macro invocation within an extern block. 649 /// 650 /// *This type is available only if Syn is built with the `"full"` feature.* 651 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 652 pub struct ForeignItemMacro { 653 pub attrs: Vec<Attribute>, 654 pub mac: Macro, 655 pub semi_token: Option<Token![;]>, 656 } 657 } 658 659 ast_enum_of_structs! { 660 /// An item declaration within the definition of a trait. 661 /// 662 /// *This type is available only if Syn is built with the `"full"` feature.* 663 /// 664 /// # Syntax tree enum 665 /// 666 /// This type is a [syntax tree enum]. 667 /// 668 /// [syntax tree enum]: Expr#syntax-tree-enums 669 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 670 #[cfg_attr(not(syn_no_non_exhaustive), non_exhaustive)] 671 pub enum TraitItem { 672 /// An associated constant within the definition of a trait. 673 Const(TraitItemConst), 674 675 /// A trait method within the definition of a trait. 676 Method(TraitItemMethod), 677 678 /// An associated type within the definition of a trait. 679 Type(TraitItemType), 680 681 /// A macro invocation within the definition of a trait. 682 Macro(TraitItemMacro), 683 684 /// Tokens within the definition of a trait not interpreted by Syn. 685 Verbatim(TokenStream), 686 687 // Not public API. 688 // 689 // For testing exhaustiveness in downstream code, use the following idiom: 690 // 691 // match item { 692 // TraitItem::Const(item) => {...} 693 // TraitItem::Method(item) => {...} 694 // ... 695 // TraitItem::Verbatim(item) => {...} 696 // 697 // #[cfg_attr(test, deny(non_exhaustive_omitted_patterns))] 698 // _ => { /* some sane fallback */ } 699 // } 700 // 701 // This way we fail your tests but don't break your library when adding 702 // a variant. You will be notified by a test failure when a variant is 703 // added, so that you can add code to handle it, but your library will 704 // continue to compile and work for downstream users in the interim. 705 #[cfg(syn_no_non_exhaustive)] 706 #[doc(hidden)] 707 __NonExhaustive, 708 } 709 } 710 711 ast_struct! { 712 /// An associated constant within the definition of a trait. 713 /// 714 /// *This type is available only if Syn is built with the `"full"` feature.* 715 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 716 pub struct TraitItemConst { 717 pub attrs: Vec<Attribute>, 718 pub const_token: Token![const], 719 pub ident: Ident, 720 pub colon_token: Token![:], 721 pub ty: Type, 722 pub default: Option<(Token![=], Expr)>, 723 pub semi_token: Token![;], 724 } 725 } 726 727 ast_struct! { 728 /// A trait method within the definition of a trait. 729 /// 730 /// *This type is available only if Syn is built with the `"full"` feature.* 731 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 732 pub struct TraitItemMethod { 733 pub attrs: Vec<Attribute>, 734 pub sig: Signature, 735 pub default: Option<Block>, 736 pub semi_token: Option<Token![;]>, 737 } 738 } 739 740 ast_struct! { 741 /// An associated type within the definition of a trait. 742 /// 743 /// *This type is available only if Syn is built with the `"full"` feature.* 744 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 745 pub struct TraitItemType { 746 pub attrs: Vec<Attribute>, 747 pub type_token: Token![type], 748 pub ident: Ident, 749 pub generics: Generics, 750 pub colon_token: Option<Token![:]>, 751 pub bounds: Punctuated<TypeParamBound, Token![+]>, 752 pub default: Option<(Token![=], Type)>, 753 pub semi_token: Token![;], 754 } 755 } 756 757 ast_struct! { 758 /// A macro invocation within the definition of a trait. 759 /// 760 /// *This type is available only if Syn is built with the `"full"` feature.* 761 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 762 pub struct TraitItemMacro { 763 pub attrs: Vec<Attribute>, 764 pub mac: Macro, 765 pub semi_token: Option<Token![;]>, 766 } 767 } 768 769 ast_enum_of_structs! { 770 /// An item within an impl block. 771 /// 772 /// *This type is available only if Syn is built with the `"full"` feature.* 773 /// 774 /// # Syntax tree enum 775 /// 776 /// This type is a [syntax tree enum]. 777 /// 778 /// [syntax tree enum]: Expr#syntax-tree-enums 779 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 780 #[cfg_attr(not(syn_no_non_exhaustive), non_exhaustive)] 781 pub enum ImplItem { 782 /// An associated constant within an impl block. 783 Const(ImplItemConst), 784 785 /// A method within an impl block. 786 Method(ImplItemMethod), 787 788 /// An associated type within an impl block. 789 Type(ImplItemType), 790 791 /// A macro invocation within an impl block. 792 Macro(ImplItemMacro), 793 794 /// Tokens within an impl block not interpreted by Syn. 795 Verbatim(TokenStream), 796 797 // Not public API. 798 // 799 // For testing exhaustiveness in downstream code, use the following idiom: 800 // 801 // match item { 802 // ImplItem::Const(item) => {...} 803 // ImplItem::Method(item) => {...} 804 // ... 805 // ImplItem::Verbatim(item) => {...} 806 // 807 // #[cfg_attr(test, deny(non_exhaustive_omitted_patterns))] 808 // _ => { /* some sane fallback */ } 809 // } 810 // 811 // This way we fail your tests but don't break your library when adding 812 // a variant. You will be notified by a test failure when a variant is 813 // added, so that you can add code to handle it, but your library will 814 // continue to compile and work for downstream users in the interim. 815 #[cfg(syn_no_non_exhaustive)] 816 #[doc(hidden)] 817 __NonExhaustive, 818 } 819 } 820 821 ast_struct! { 822 /// An associated constant within an impl block. 823 /// 824 /// *This type is available only if Syn is built with the `"full"` feature.* 825 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 826 pub struct ImplItemConst { 827 pub attrs: Vec<Attribute>, 828 pub vis: Visibility, 829 pub defaultness: Option<Token![default]>, 830 pub const_token: Token![const], 831 pub ident: Ident, 832 pub colon_token: Token![:], 833 pub ty: Type, 834 pub eq_token: Token![=], 835 pub expr: Expr, 836 pub semi_token: Token![;], 837 } 838 } 839 840 ast_struct! { 841 /// A method within an impl block. 842 /// 843 /// *This type is available only if Syn is built with the `"full"` feature.* 844 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 845 pub struct ImplItemMethod { 846 pub attrs: Vec<Attribute>, 847 pub vis: Visibility, 848 pub defaultness: Option<Token![default]>, 849 pub sig: Signature, 850 pub block: Block, 851 } 852 } 853 854 ast_struct! { 855 /// An associated type within an impl block. 856 /// 857 /// *This type is available only if Syn is built with the `"full"` feature.* 858 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 859 pub struct ImplItemType { 860 pub attrs: Vec<Attribute>, 861 pub vis: Visibility, 862 pub defaultness: Option<Token![default]>, 863 pub type_token: Token![type], 864 pub ident: Ident, 865 pub generics: Generics, 866 pub eq_token: Token![=], 867 pub ty: Type, 868 pub semi_token: Token![;], 869 } 870 } 871 872 ast_struct! { 873 /// A macro invocation within an impl block. 874 /// 875 /// *This type is available only if Syn is built with the `"full"` feature.* 876 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 877 pub struct ImplItemMacro { 878 pub attrs: Vec<Attribute>, 879 pub mac: Macro, 880 pub semi_token: Option<Token![;]>, 881 } 882 } 883 884 ast_struct! { 885 /// A function signature in a trait or implementation: `unsafe fn 886 /// initialize(&self)`. 887 /// 888 /// *This type is available only if Syn is built with the `"full"` feature.* 889 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 890 pub struct Signature { 891 pub constness: Option<Token![const]>, 892 pub asyncness: Option<Token![async]>, 893 pub unsafety: Option<Token![unsafe]>, 894 pub abi: Option<Abi>, 895 pub fn_token: Token![fn], 896 pub ident: Ident, 897 pub generics: Generics, 898 pub paren_token: token::Paren, 899 pub inputs: Punctuated<FnArg, Token![,]>, 900 pub variadic: Option<Variadic>, 901 pub output: ReturnType, 902 } 903 } 904 905 impl Signature { 906 /// A method's `self` receiver, such as `&self` or `self: Box<Self>`. receiver(&self) -> Option<&FnArg>907 pub fn receiver(&self) -> Option<&FnArg> { 908 let arg = self.inputs.first()?; 909 match arg { 910 FnArg::Receiver(_) => Some(arg), 911 FnArg::Typed(PatType { pat, .. }) => { 912 if let Pat::Ident(PatIdent { ident, .. }) = &**pat { 913 if ident == "self" { 914 return Some(arg); 915 } 916 } 917 None 918 } 919 } 920 } 921 } 922 923 ast_enum_of_structs! { 924 /// An argument in a function signature: the `n: usize` in `fn f(n: usize)`. 925 /// 926 /// *This type is available only if Syn is built with the `"full"` feature.* 927 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 928 pub enum FnArg { 929 /// The `self` argument of an associated method, whether taken by value 930 /// or by reference. 931 /// 932 /// Note that `self` receivers with a specified type, such as `self: 933 /// Box<Self>`, are parsed as a `FnArg::Typed`. 934 Receiver(Receiver), 935 936 /// A function argument accepted by pattern and type. 937 Typed(PatType), 938 } 939 } 940 941 ast_struct! { 942 /// The `self` argument of an associated method, whether taken by value 943 /// or by reference. 944 /// 945 /// Note that `self` receivers with a specified type, such as `self: 946 /// Box<Self>`, are parsed as a `FnArg::Typed`. 947 /// 948 /// *This type is available only if Syn is built with the `"full"` feature.* 949 #[cfg_attr(doc_cfg, doc(cfg(feature = "full")))] 950 pub struct Receiver { 951 pub attrs: Vec<Attribute>, 952 pub reference: Option<(Token![&], Option<Lifetime>)>, 953 pub mutability: Option<Token![mut]>, 954 pub self_token: Token![self], 955 } 956 } 957 958 impl Receiver { lifetime(&self) -> Option<&Lifetime>959 pub fn lifetime(&self) -> Option<&Lifetime> { 960 self.reference.as_ref()?.1.as_ref() 961 } 962 } 963 964 #[cfg(feature = "parsing")] 965 pub mod parsing { 966 use super::*; 967 use crate::ext::IdentExt; 968 use crate::parse::discouraged::Speculative; 969 use crate::parse::{Parse, ParseBuffer, ParseStream, Result}; 970 use crate::token::Brace; 971 use proc_macro2::{Delimiter, Group, Punct, Spacing, TokenTree}; 972 use std::iter::{self, FromIterator}; 973 974 crate::custom_keyword!(macro_rules); 975 976 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 977 impl Parse for Item { parse(input: ParseStream) -> Result<Self>978 fn parse(input: ParseStream) -> Result<Self> { 979 let begin = input.fork(); 980 let mut attrs = input.call(Attribute::parse_outer)?; 981 let ahead = input.fork(); 982 let vis: Visibility = ahead.parse()?; 983 984 let lookahead = ahead.lookahead1(); 985 let mut item = if lookahead.peek(Token![fn]) || peek_signature(&ahead) { 986 let vis: Visibility = input.parse()?; 987 let sig: Signature = input.parse()?; 988 if input.peek(Token![;]) { 989 input.parse::<Token![;]>()?; 990 Ok(Item::Verbatim(verbatim::between(begin, input))) 991 } else { 992 parse_rest_of_fn(input, Vec::new(), vis, sig).map(Item::Fn) 993 } 994 } else if lookahead.peek(Token![extern]) { 995 ahead.parse::<Token![extern]>()?; 996 let lookahead = ahead.lookahead1(); 997 if lookahead.peek(Token![crate]) { 998 input.parse().map(Item::ExternCrate) 999 } else if lookahead.peek(token::Brace) { 1000 input.parse().map(Item::ForeignMod) 1001 } else if lookahead.peek(LitStr) { 1002 ahead.parse::<LitStr>()?; 1003 let lookahead = ahead.lookahead1(); 1004 if lookahead.peek(token::Brace) { 1005 input.parse().map(Item::ForeignMod) 1006 } else { 1007 Err(lookahead.error()) 1008 } 1009 } else { 1010 Err(lookahead.error()) 1011 } 1012 } else if lookahead.peek(Token![use]) { 1013 input.parse().map(Item::Use) 1014 } else if lookahead.peek(Token![static]) { 1015 let vis = input.parse()?; 1016 let static_token = input.parse()?; 1017 let mutability = input.parse()?; 1018 let ident = input.parse()?; 1019 if input.peek(Token![=]) { 1020 input.parse::<Token![=]>()?; 1021 input.parse::<Expr>()?; 1022 input.parse::<Token![;]>()?; 1023 Ok(Item::Verbatim(verbatim::between(begin, input))) 1024 } else { 1025 let colon_token = input.parse()?; 1026 let ty = input.parse()?; 1027 if input.peek(Token![;]) { 1028 input.parse::<Token![;]>()?; 1029 Ok(Item::Verbatim(verbatim::between(begin, input))) 1030 } else { 1031 Ok(Item::Static(ItemStatic { 1032 attrs: Vec::new(), 1033 vis, 1034 static_token, 1035 mutability, 1036 ident, 1037 colon_token, 1038 ty, 1039 eq_token: input.parse()?, 1040 expr: input.parse()?, 1041 semi_token: input.parse()?, 1042 })) 1043 } 1044 } 1045 } else if lookahead.peek(Token![const]) { 1046 ahead.parse::<Token![const]>()?; 1047 let lookahead = ahead.lookahead1(); 1048 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 1049 let vis = input.parse()?; 1050 let const_token = input.parse()?; 1051 let ident = { 1052 let lookahead = input.lookahead1(); 1053 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 1054 input.call(Ident::parse_any)? 1055 } else { 1056 return Err(lookahead.error()); 1057 } 1058 }; 1059 let colon_token = input.parse()?; 1060 let ty = input.parse()?; 1061 if input.peek(Token![;]) { 1062 input.parse::<Token![;]>()?; 1063 Ok(Item::Verbatim(verbatim::between(begin, input))) 1064 } else { 1065 Ok(Item::Const(ItemConst { 1066 attrs: Vec::new(), 1067 vis, 1068 const_token, 1069 ident, 1070 colon_token, 1071 ty, 1072 eq_token: input.parse()?, 1073 expr: input.parse()?, 1074 semi_token: input.parse()?, 1075 })) 1076 } 1077 } else { 1078 Err(lookahead.error()) 1079 } 1080 } else if lookahead.peek(Token![unsafe]) { 1081 ahead.parse::<Token![unsafe]>()?; 1082 let lookahead = ahead.lookahead1(); 1083 if lookahead.peek(Token![trait]) 1084 || lookahead.peek(Token![auto]) && ahead.peek2(Token![trait]) 1085 { 1086 input.parse().map(Item::Trait) 1087 } else if lookahead.peek(Token![impl]) { 1088 let allow_verbatim_impl = true; 1089 if let Some(item) = parse_impl(input, allow_verbatim_impl)? { 1090 Ok(Item::Impl(item)) 1091 } else { 1092 Ok(Item::Verbatim(verbatim::between(begin, input))) 1093 } 1094 } else if lookahead.peek(Token![extern]) { 1095 input.parse::<Visibility>()?; 1096 input.parse::<Token![unsafe]>()?; 1097 input.parse::<ItemForeignMod>()?; 1098 Ok(Item::Verbatim(verbatim::between(begin, input))) 1099 } else if lookahead.peek(Token![mod]) { 1100 input.parse::<Visibility>()?; 1101 input.parse::<Token![unsafe]>()?; 1102 input.parse::<ItemMod>()?; 1103 Ok(Item::Verbatim(verbatim::between(begin, input))) 1104 } else { 1105 Err(lookahead.error()) 1106 } 1107 } else if lookahead.peek(Token![mod]) { 1108 input.parse().map(Item::Mod) 1109 } else if lookahead.peek(Token![type]) { 1110 parse_item_type(begin, input) 1111 } else if lookahead.peek(Token![struct]) { 1112 input.parse().map(Item::Struct) 1113 } else if lookahead.peek(Token![enum]) { 1114 input.parse().map(Item::Enum) 1115 } else if lookahead.peek(Token![union]) && ahead.peek2(Ident) { 1116 input.parse().map(Item::Union) 1117 } else if lookahead.peek(Token![trait]) { 1118 input.call(parse_trait_or_trait_alias) 1119 } else if lookahead.peek(Token![auto]) && ahead.peek2(Token![trait]) { 1120 input.parse().map(Item::Trait) 1121 } else if lookahead.peek(Token![impl]) 1122 || lookahead.peek(Token![default]) && !ahead.peek2(Token![!]) 1123 { 1124 let allow_verbatim_impl = true; 1125 if let Some(item) = parse_impl(input, allow_verbatim_impl)? { 1126 Ok(Item::Impl(item)) 1127 } else { 1128 Ok(Item::Verbatim(verbatim::between(begin, input))) 1129 } 1130 } else if lookahead.peek(Token![macro]) { 1131 input.parse().map(Item::Macro2) 1132 } else if vis.is_inherited() 1133 && (lookahead.peek(Ident) 1134 || lookahead.peek(Token![self]) 1135 || lookahead.peek(Token![super]) 1136 || lookahead.peek(Token![crate]) 1137 || lookahead.peek(Token![::])) 1138 { 1139 input.parse().map(Item::Macro) 1140 } else if ahead.peek(macro_rules) { 1141 input.advance_to(&ahead); 1142 input.parse::<ItemMacro>()?; 1143 Ok(Item::Verbatim(verbatim::between(begin, input))) 1144 } else { 1145 Err(lookahead.error()) 1146 }?; 1147 1148 attrs.extend(item.replace_attrs(Vec::new())); 1149 item.replace_attrs(attrs); 1150 Ok(item) 1151 } 1152 } 1153 1154 struct FlexibleItemType { 1155 vis: Visibility, 1156 defaultness: Option<Token![default]>, 1157 type_token: Token![type], 1158 ident: Ident, 1159 generics: Generics, 1160 colon_token: Option<Token![:]>, 1161 bounds: Punctuated<TypeParamBound, Token![+]>, 1162 ty: Option<(Token![=], Type)>, 1163 semi_token: Token![;], 1164 } 1165 1166 enum WhereClauseLocation { 1167 // type Ty<T> where T: 'static = T; 1168 BeforeEq, 1169 // type Ty<T> = T where T: 'static; 1170 #[allow(dead_code)] 1171 AfterEq, 1172 // TODO: goes away once the migration period on rust-lang/rust#89122 is over 1173 Both, 1174 } 1175 1176 impl FlexibleItemType { parse(input: ParseStream, where_clause_location: WhereClauseLocation) -> Result<Self>1177 fn parse(input: ParseStream, where_clause_location: WhereClauseLocation) -> Result<Self> { 1178 let vis: Visibility = input.parse()?; 1179 let defaultness: Option<Token![default]> = input.parse()?; 1180 let type_token: Token![type] = input.parse()?; 1181 let ident: Ident = input.parse()?; 1182 let mut generics: Generics = input.parse()?; 1183 let colon_token: Option<Token![:]> = input.parse()?; 1184 1185 let mut bounds = Punctuated::new(); 1186 if colon_token.is_some() { 1187 loop { 1188 if input.peek(Token![where]) || input.peek(Token![=]) || input.peek(Token![;]) { 1189 break; 1190 } 1191 bounds.push_value(input.parse::<TypeParamBound>()?); 1192 if input.peek(Token![where]) || input.peek(Token![=]) || input.peek(Token![;]) { 1193 break; 1194 } 1195 bounds.push_punct(input.parse::<Token![+]>()?); 1196 } 1197 } 1198 1199 match where_clause_location { 1200 WhereClauseLocation::BeforeEq | WhereClauseLocation::Both => { 1201 generics.where_clause = input.parse()?; 1202 } 1203 _ => {} 1204 } 1205 1206 let ty = if let Some(eq_token) = input.parse()? { 1207 Some((eq_token, input.parse::<Type>()?)) 1208 } else { 1209 None 1210 }; 1211 1212 match where_clause_location { 1213 WhereClauseLocation::AfterEq | WhereClauseLocation::Both 1214 if generics.where_clause.is_none() => 1215 { 1216 generics.where_clause = input.parse()?; 1217 } 1218 _ => {} 1219 } 1220 1221 let semi_token: Token![;] = input.parse()?; 1222 1223 Ok(FlexibleItemType { 1224 vis, 1225 defaultness, 1226 type_token, 1227 ident, 1228 generics, 1229 colon_token, 1230 bounds, 1231 ty, 1232 semi_token, 1233 }) 1234 } 1235 } 1236 1237 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1238 impl Parse for ItemMacro { parse(input: ParseStream) -> Result<Self>1239 fn parse(input: ParseStream) -> Result<Self> { 1240 let attrs = input.call(Attribute::parse_outer)?; 1241 let path = input.call(Path::parse_mod_style)?; 1242 let bang_token: Token![!] = input.parse()?; 1243 let ident: Option<Ident> = input.parse()?; 1244 let (delimiter, tokens) = input.call(mac::parse_delimiter)?; 1245 let semi_token: Option<Token![;]> = if !delimiter.is_brace() { 1246 Some(input.parse()?) 1247 } else { 1248 None 1249 }; 1250 Ok(ItemMacro { 1251 attrs, 1252 ident, 1253 mac: Macro { 1254 path, 1255 bang_token, 1256 delimiter, 1257 tokens, 1258 }, 1259 semi_token, 1260 }) 1261 } 1262 } 1263 1264 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1265 impl Parse for ItemMacro2 { parse(input: ParseStream) -> Result<Self>1266 fn parse(input: ParseStream) -> Result<Self> { 1267 let attrs = input.call(Attribute::parse_outer)?; 1268 let vis: Visibility = input.parse()?; 1269 let macro_token: Token![macro] = input.parse()?; 1270 let ident: Ident = input.parse()?; 1271 let mut rules = TokenStream::new(); 1272 1273 let mut lookahead = input.lookahead1(); 1274 if lookahead.peek(token::Paren) { 1275 let paren_content; 1276 let paren_token = parenthesized!(paren_content in input); 1277 let args: TokenStream = paren_content.parse()?; 1278 let mut args = Group::new(Delimiter::Parenthesis, args); 1279 args.set_span(paren_token.span); 1280 rules.extend(iter::once(TokenTree::Group(args))); 1281 lookahead = input.lookahead1(); 1282 } 1283 1284 if lookahead.peek(token::Brace) { 1285 let brace_content; 1286 let brace_token = braced!(brace_content in input); 1287 let body: TokenStream = brace_content.parse()?; 1288 let mut body = Group::new(Delimiter::Brace, body); 1289 body.set_span(brace_token.span); 1290 rules.extend(iter::once(TokenTree::Group(body))); 1291 } else { 1292 return Err(lookahead.error()); 1293 } 1294 1295 Ok(ItemMacro2 { 1296 attrs, 1297 vis, 1298 macro_token, 1299 ident, 1300 rules, 1301 }) 1302 } 1303 } 1304 1305 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1306 impl Parse for ItemExternCrate { parse(input: ParseStream) -> Result<Self>1307 fn parse(input: ParseStream) -> Result<Self> { 1308 Ok(ItemExternCrate { 1309 attrs: input.call(Attribute::parse_outer)?, 1310 vis: input.parse()?, 1311 extern_token: input.parse()?, 1312 crate_token: input.parse()?, 1313 ident: { 1314 if input.peek(Token![self]) { 1315 input.call(Ident::parse_any)? 1316 } else { 1317 input.parse()? 1318 } 1319 }, 1320 rename: { 1321 if input.peek(Token![as]) { 1322 let as_token: Token![as] = input.parse()?; 1323 let rename: Ident = if input.peek(Token![_]) { 1324 Ident::from(input.parse::<Token![_]>()?) 1325 } else { 1326 input.parse()? 1327 }; 1328 Some((as_token, rename)) 1329 } else { 1330 None 1331 } 1332 }, 1333 semi_token: input.parse()?, 1334 }) 1335 } 1336 } 1337 1338 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1339 impl Parse for ItemUse { parse(input: ParseStream) -> Result<Self>1340 fn parse(input: ParseStream) -> Result<Self> { 1341 Ok(ItemUse { 1342 attrs: input.call(Attribute::parse_outer)?, 1343 vis: input.parse()?, 1344 use_token: input.parse()?, 1345 leading_colon: input.parse()?, 1346 tree: input.parse()?, 1347 semi_token: input.parse()?, 1348 }) 1349 } 1350 } 1351 1352 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1353 impl Parse for UseTree { parse(input: ParseStream) -> Result<UseTree>1354 fn parse(input: ParseStream) -> Result<UseTree> { 1355 let lookahead = input.lookahead1(); 1356 if lookahead.peek(Ident) 1357 || lookahead.peek(Token![self]) 1358 || lookahead.peek(Token![super]) 1359 || lookahead.peek(Token![crate]) 1360 { 1361 let ident = input.call(Ident::parse_any)?; 1362 if input.peek(Token![::]) { 1363 Ok(UseTree::Path(UsePath { 1364 ident, 1365 colon2_token: input.parse()?, 1366 tree: Box::new(input.parse()?), 1367 })) 1368 } else if input.peek(Token![as]) { 1369 Ok(UseTree::Rename(UseRename { 1370 ident, 1371 as_token: input.parse()?, 1372 rename: { 1373 if input.peek(Ident) { 1374 input.parse()? 1375 } else if input.peek(Token![_]) { 1376 Ident::from(input.parse::<Token![_]>()?) 1377 } else { 1378 return Err(input.error("expected identifier or underscore")); 1379 } 1380 }, 1381 })) 1382 } else { 1383 Ok(UseTree::Name(UseName { ident })) 1384 } 1385 } else if lookahead.peek(Token![*]) { 1386 Ok(UseTree::Glob(UseGlob { 1387 star_token: input.parse()?, 1388 })) 1389 } else if lookahead.peek(token::Brace) { 1390 let content; 1391 Ok(UseTree::Group(UseGroup { 1392 brace_token: braced!(content in input), 1393 items: content.parse_terminated(UseTree::parse)?, 1394 })) 1395 } else { 1396 Err(lookahead.error()) 1397 } 1398 } 1399 } 1400 1401 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1402 impl Parse for ItemStatic { parse(input: ParseStream) -> Result<Self>1403 fn parse(input: ParseStream) -> Result<Self> { 1404 Ok(ItemStatic { 1405 attrs: input.call(Attribute::parse_outer)?, 1406 vis: input.parse()?, 1407 static_token: input.parse()?, 1408 mutability: input.parse()?, 1409 ident: input.parse()?, 1410 colon_token: input.parse()?, 1411 ty: input.parse()?, 1412 eq_token: input.parse()?, 1413 expr: input.parse()?, 1414 semi_token: input.parse()?, 1415 }) 1416 } 1417 } 1418 1419 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1420 impl Parse for ItemConst { parse(input: ParseStream) -> Result<Self>1421 fn parse(input: ParseStream) -> Result<Self> { 1422 Ok(ItemConst { 1423 attrs: input.call(Attribute::parse_outer)?, 1424 vis: input.parse()?, 1425 const_token: input.parse()?, 1426 ident: { 1427 let lookahead = input.lookahead1(); 1428 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 1429 input.call(Ident::parse_any)? 1430 } else { 1431 return Err(lookahead.error()); 1432 } 1433 }, 1434 colon_token: input.parse()?, 1435 ty: input.parse()?, 1436 eq_token: input.parse()?, 1437 expr: input.parse()?, 1438 semi_token: input.parse()?, 1439 }) 1440 } 1441 } 1442 pop_variadic(args: &mut Punctuated<FnArg, Token![,]>) -> Option<Variadic>1443 fn pop_variadic(args: &mut Punctuated<FnArg, Token![,]>) -> Option<Variadic> { 1444 let trailing_punct = args.trailing_punct(); 1445 1446 let last = match args.last_mut()? { 1447 FnArg::Typed(last) => last, 1448 _ => return None, 1449 }; 1450 1451 let ty = match last.ty.as_ref() { 1452 Type::Verbatim(ty) => ty, 1453 _ => return None, 1454 }; 1455 1456 let mut variadic = Variadic { 1457 attrs: Vec::new(), 1458 dots: parse2(ty.clone()).ok()?, 1459 }; 1460 1461 if let Pat::Verbatim(pat) = last.pat.as_ref() { 1462 if pat.to_string() == "..." && !trailing_punct { 1463 variadic.attrs = mem::replace(&mut last.attrs, Vec::new()); 1464 args.pop(); 1465 } 1466 } 1467 1468 Some(variadic) 1469 } 1470 variadic_to_tokens(dots: &Token![...]) -> TokenStream1471 fn variadic_to_tokens(dots: &Token![...]) -> TokenStream { 1472 TokenStream::from_iter(vec![ 1473 TokenTree::Punct({ 1474 let mut dot = Punct::new('.', Spacing::Joint); 1475 dot.set_span(dots.spans[0]); 1476 dot 1477 }), 1478 TokenTree::Punct({ 1479 let mut dot = Punct::new('.', Spacing::Joint); 1480 dot.set_span(dots.spans[1]); 1481 dot 1482 }), 1483 TokenTree::Punct({ 1484 let mut dot = Punct::new('.', Spacing::Alone); 1485 dot.set_span(dots.spans[2]); 1486 dot 1487 }), 1488 ]) 1489 } 1490 peek_signature(input: ParseStream) -> bool1491 fn peek_signature(input: ParseStream) -> bool { 1492 let fork = input.fork(); 1493 fork.parse::<Option<Token![const]>>().is_ok() 1494 && fork.parse::<Option<Token![async]>>().is_ok() 1495 && fork.parse::<Option<Token![unsafe]>>().is_ok() 1496 && fork.parse::<Option<Abi>>().is_ok() 1497 && fork.peek(Token![fn]) 1498 } 1499 1500 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1501 impl Parse for Signature { parse(input: ParseStream) -> Result<Self>1502 fn parse(input: ParseStream) -> Result<Self> { 1503 let constness: Option<Token![const]> = input.parse()?; 1504 let asyncness: Option<Token![async]> = input.parse()?; 1505 let unsafety: Option<Token![unsafe]> = input.parse()?; 1506 let abi: Option<Abi> = input.parse()?; 1507 let fn_token: Token![fn] = input.parse()?; 1508 let ident: Ident = input.parse()?; 1509 let mut generics: Generics = input.parse()?; 1510 1511 let content; 1512 let paren_token = parenthesized!(content in input); 1513 let mut inputs = parse_fn_args(&content)?; 1514 let variadic = pop_variadic(&mut inputs); 1515 1516 let output: ReturnType = input.parse()?; 1517 generics.where_clause = input.parse()?; 1518 1519 Ok(Signature { 1520 constness, 1521 asyncness, 1522 unsafety, 1523 abi, 1524 fn_token, 1525 ident, 1526 generics, 1527 paren_token, 1528 inputs, 1529 variadic, 1530 output, 1531 }) 1532 } 1533 } 1534 1535 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1536 impl Parse for ItemFn { parse(input: ParseStream) -> Result<Self>1537 fn parse(input: ParseStream) -> Result<Self> { 1538 let outer_attrs = input.call(Attribute::parse_outer)?; 1539 let vis: Visibility = input.parse()?; 1540 let sig: Signature = input.parse()?; 1541 parse_rest_of_fn(input, outer_attrs, vis, sig) 1542 } 1543 } 1544 parse_rest_of_fn( input: ParseStream, mut attrs: Vec<Attribute>, vis: Visibility, sig: Signature, ) -> Result<ItemFn>1545 fn parse_rest_of_fn( 1546 input: ParseStream, 1547 mut attrs: Vec<Attribute>, 1548 vis: Visibility, 1549 sig: Signature, 1550 ) -> Result<ItemFn> { 1551 let content; 1552 let brace_token = braced!(content in input); 1553 attr::parsing::parse_inner(&content, &mut attrs)?; 1554 let stmts = content.call(Block::parse_within)?; 1555 1556 Ok(ItemFn { 1557 attrs, 1558 vis, 1559 sig, 1560 block: Box::new(Block { brace_token, stmts }), 1561 }) 1562 } 1563 1564 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1565 impl Parse for FnArg { parse(input: ParseStream) -> Result<Self>1566 fn parse(input: ParseStream) -> Result<Self> { 1567 let attrs = input.call(Attribute::parse_outer)?; 1568 1569 let ahead = input.fork(); 1570 if let Ok(mut receiver) = ahead.parse::<Receiver>() { 1571 if !ahead.peek(Token![:]) { 1572 input.advance_to(&ahead); 1573 receiver.attrs = attrs; 1574 return Ok(FnArg::Receiver(receiver)); 1575 } 1576 } 1577 1578 let mut typed = input.call(fn_arg_typed)?; 1579 typed.attrs = attrs; 1580 Ok(FnArg::Typed(typed)) 1581 } 1582 } 1583 1584 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1585 impl Parse for Receiver { parse(input: ParseStream) -> Result<Self>1586 fn parse(input: ParseStream) -> Result<Self> { 1587 Ok(Receiver { 1588 attrs: Vec::new(), 1589 reference: { 1590 if input.peek(Token![&]) { 1591 Some((input.parse()?, input.parse()?)) 1592 } else { 1593 None 1594 } 1595 }, 1596 mutability: input.parse()?, 1597 self_token: input.parse()?, 1598 }) 1599 } 1600 } 1601 parse_fn_args(input: ParseStream) -> Result<Punctuated<FnArg, Token![,]>>1602 fn parse_fn_args(input: ParseStream) -> Result<Punctuated<FnArg, Token![,]>> { 1603 let mut args = Punctuated::new(); 1604 let mut has_receiver = false; 1605 1606 while !input.is_empty() { 1607 let attrs = input.call(Attribute::parse_outer)?; 1608 1609 let arg = if let Some(dots) = input.parse::<Option<Token![...]>>()? { 1610 FnArg::Typed(PatType { 1611 attrs, 1612 pat: Box::new(Pat::Verbatim(variadic_to_tokens(&dots))), 1613 colon_token: Token![:](dots.spans[0]), 1614 ty: Box::new(Type::Verbatim(variadic_to_tokens(&dots))), 1615 }) 1616 } else { 1617 let mut arg: FnArg = input.parse()?; 1618 match &mut arg { 1619 FnArg::Receiver(receiver) if has_receiver => { 1620 return Err(Error::new( 1621 receiver.self_token.span, 1622 "unexpected second method receiver", 1623 )); 1624 } 1625 FnArg::Receiver(receiver) if !args.is_empty() => { 1626 return Err(Error::new( 1627 receiver.self_token.span, 1628 "unexpected method receiver", 1629 )); 1630 } 1631 FnArg::Receiver(receiver) => { 1632 has_receiver = true; 1633 receiver.attrs = attrs; 1634 } 1635 FnArg::Typed(arg) => arg.attrs = attrs, 1636 } 1637 arg 1638 }; 1639 args.push_value(arg); 1640 1641 if input.is_empty() { 1642 break; 1643 } 1644 1645 let comma: Token![,] = input.parse()?; 1646 args.push_punct(comma); 1647 } 1648 1649 Ok(args) 1650 } 1651 fn_arg_typed(input: ParseStream) -> Result<PatType>1652 fn fn_arg_typed(input: ParseStream) -> Result<PatType> { 1653 // Hack to parse pre-2018 syntax in 1654 // test/ui/rfc-2565-param-attrs/param-attrs-pretty.rs 1655 // because the rest of the test case is valuable. 1656 if input.peek(Ident) && input.peek2(Token![<]) { 1657 let span = input.fork().parse::<Ident>()?.span(); 1658 return Ok(PatType { 1659 attrs: Vec::new(), 1660 pat: Box::new(Pat::Wild(PatWild { 1661 attrs: Vec::new(), 1662 underscore_token: Token![_](span), 1663 })), 1664 colon_token: Token![:](span), 1665 ty: input.parse()?, 1666 }); 1667 } 1668 1669 Ok(PatType { 1670 attrs: Vec::new(), 1671 pat: Box::new(pat::parsing::multi_pat(input)?), 1672 colon_token: input.parse()?, 1673 ty: Box::new(match input.parse::<Option<Token![...]>>()? { 1674 Some(dot3) => Type::Verbatim(variadic_to_tokens(&dot3)), 1675 None => input.parse()?, 1676 }), 1677 }) 1678 } 1679 1680 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1681 impl Parse for ItemMod { parse(input: ParseStream) -> Result<Self>1682 fn parse(input: ParseStream) -> Result<Self> { 1683 let mut attrs = input.call(Attribute::parse_outer)?; 1684 let vis: Visibility = input.parse()?; 1685 let mod_token: Token![mod] = input.parse()?; 1686 let ident: Ident = input.parse()?; 1687 1688 let lookahead = input.lookahead1(); 1689 if lookahead.peek(Token![;]) { 1690 Ok(ItemMod { 1691 attrs, 1692 vis, 1693 mod_token, 1694 ident, 1695 content: None, 1696 semi: Some(input.parse()?), 1697 }) 1698 } else if lookahead.peek(token::Brace) { 1699 let content; 1700 let brace_token = braced!(content in input); 1701 attr::parsing::parse_inner(&content, &mut attrs)?; 1702 1703 let mut items = Vec::new(); 1704 while !content.is_empty() { 1705 items.push(content.parse()?); 1706 } 1707 1708 Ok(ItemMod { 1709 attrs, 1710 vis, 1711 mod_token, 1712 ident, 1713 content: Some((brace_token, items)), 1714 semi: None, 1715 }) 1716 } else { 1717 Err(lookahead.error()) 1718 } 1719 } 1720 } 1721 1722 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1723 impl Parse for ItemForeignMod { parse(input: ParseStream) -> Result<Self>1724 fn parse(input: ParseStream) -> Result<Self> { 1725 let mut attrs = input.call(Attribute::parse_outer)?; 1726 let abi: Abi = input.parse()?; 1727 1728 let content; 1729 let brace_token = braced!(content in input); 1730 attr::parsing::parse_inner(&content, &mut attrs)?; 1731 let mut items = Vec::new(); 1732 while !content.is_empty() { 1733 items.push(content.parse()?); 1734 } 1735 1736 Ok(ItemForeignMod { 1737 attrs, 1738 abi, 1739 brace_token, 1740 items, 1741 }) 1742 } 1743 } 1744 1745 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1746 impl Parse for ForeignItem { parse(input: ParseStream) -> Result<Self>1747 fn parse(input: ParseStream) -> Result<Self> { 1748 let begin = input.fork(); 1749 let mut attrs = input.call(Attribute::parse_outer)?; 1750 let ahead = input.fork(); 1751 let vis: Visibility = ahead.parse()?; 1752 1753 let lookahead = ahead.lookahead1(); 1754 let mut item = if lookahead.peek(Token![fn]) || peek_signature(&ahead) { 1755 let vis: Visibility = input.parse()?; 1756 let sig: Signature = input.parse()?; 1757 if input.peek(token::Brace) { 1758 let content; 1759 braced!(content in input); 1760 content.call(Attribute::parse_inner)?; 1761 content.call(Block::parse_within)?; 1762 1763 Ok(ForeignItem::Verbatim(verbatim::between(begin, input))) 1764 } else { 1765 Ok(ForeignItem::Fn(ForeignItemFn { 1766 attrs: Vec::new(), 1767 vis, 1768 sig, 1769 semi_token: input.parse()?, 1770 })) 1771 } 1772 } else if lookahead.peek(Token![static]) { 1773 let vis = input.parse()?; 1774 let static_token = input.parse()?; 1775 let mutability = input.parse()?; 1776 let ident = input.parse()?; 1777 let colon_token = input.parse()?; 1778 let ty = input.parse()?; 1779 if input.peek(Token![=]) { 1780 input.parse::<Token![=]>()?; 1781 input.parse::<Expr>()?; 1782 input.parse::<Token![;]>()?; 1783 Ok(ForeignItem::Verbatim(verbatim::between(begin, input))) 1784 } else { 1785 Ok(ForeignItem::Static(ForeignItemStatic { 1786 attrs: Vec::new(), 1787 vis, 1788 static_token, 1789 mutability, 1790 ident, 1791 colon_token, 1792 ty, 1793 semi_token: input.parse()?, 1794 })) 1795 } 1796 } else if lookahead.peek(Token![type]) { 1797 parse_foreign_item_type(begin, input) 1798 } else if vis.is_inherited() 1799 && (lookahead.peek(Ident) 1800 || lookahead.peek(Token![self]) 1801 || lookahead.peek(Token![super]) 1802 || lookahead.peek(Token![crate]) 1803 || lookahead.peek(Token![::])) 1804 { 1805 input.parse().map(ForeignItem::Macro) 1806 } else { 1807 Err(lookahead.error()) 1808 }?; 1809 1810 let item_attrs = match &mut item { 1811 ForeignItem::Fn(item) => &mut item.attrs, 1812 ForeignItem::Static(item) => &mut item.attrs, 1813 ForeignItem::Type(item) => &mut item.attrs, 1814 ForeignItem::Macro(item) => &mut item.attrs, 1815 ForeignItem::Verbatim(_) => return Ok(item), 1816 1817 #[cfg(syn_no_non_exhaustive)] 1818 _ => unreachable!(), 1819 }; 1820 attrs.append(item_attrs); 1821 *item_attrs = attrs; 1822 1823 Ok(item) 1824 } 1825 } 1826 1827 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1828 impl Parse for ForeignItemFn { parse(input: ParseStream) -> Result<Self>1829 fn parse(input: ParseStream) -> Result<Self> { 1830 let attrs = input.call(Attribute::parse_outer)?; 1831 let vis: Visibility = input.parse()?; 1832 let sig: Signature = input.parse()?; 1833 let semi_token: Token![;] = input.parse()?; 1834 Ok(ForeignItemFn { 1835 attrs, 1836 vis, 1837 sig, 1838 semi_token, 1839 }) 1840 } 1841 } 1842 1843 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1844 impl Parse for ForeignItemStatic { parse(input: ParseStream) -> Result<Self>1845 fn parse(input: ParseStream) -> Result<Self> { 1846 Ok(ForeignItemStatic { 1847 attrs: input.call(Attribute::parse_outer)?, 1848 vis: input.parse()?, 1849 static_token: input.parse()?, 1850 mutability: input.parse()?, 1851 ident: input.parse()?, 1852 colon_token: input.parse()?, 1853 ty: input.parse()?, 1854 semi_token: input.parse()?, 1855 }) 1856 } 1857 } 1858 1859 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1860 impl Parse for ForeignItemType { parse(input: ParseStream) -> Result<Self>1861 fn parse(input: ParseStream) -> Result<Self> { 1862 Ok(ForeignItemType { 1863 attrs: input.call(Attribute::parse_outer)?, 1864 vis: input.parse()?, 1865 type_token: input.parse()?, 1866 ident: input.parse()?, 1867 semi_token: input.parse()?, 1868 }) 1869 } 1870 } 1871 parse_foreign_item_type(begin: ParseBuffer, input: ParseStream) -> Result<ForeignItem>1872 fn parse_foreign_item_type(begin: ParseBuffer, input: ParseStream) -> Result<ForeignItem> { 1873 let FlexibleItemType { 1874 vis, 1875 defaultness, 1876 type_token, 1877 ident, 1878 generics, 1879 colon_token, 1880 bounds: _, 1881 ty, 1882 semi_token, 1883 } = FlexibleItemType::parse(input, WhereClauseLocation::BeforeEq)?; 1884 1885 if defaultness.is_some() 1886 || generics.lt_token.is_some() 1887 || generics.where_clause.is_some() 1888 || colon_token.is_some() 1889 || ty.is_some() 1890 { 1891 Ok(ForeignItem::Verbatim(verbatim::between(begin, input))) 1892 } else { 1893 Ok(ForeignItem::Type(ForeignItemType { 1894 attrs: Vec::new(), 1895 vis, 1896 type_token, 1897 ident, 1898 semi_token, 1899 })) 1900 } 1901 } 1902 1903 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1904 impl Parse for ForeignItemMacro { parse(input: ParseStream) -> Result<Self>1905 fn parse(input: ParseStream) -> Result<Self> { 1906 let attrs = input.call(Attribute::parse_outer)?; 1907 let mac: Macro = input.parse()?; 1908 let semi_token: Option<Token![;]> = if mac.delimiter.is_brace() { 1909 None 1910 } else { 1911 Some(input.parse()?) 1912 }; 1913 Ok(ForeignItemMacro { 1914 attrs, 1915 mac, 1916 semi_token, 1917 }) 1918 } 1919 } 1920 1921 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1922 impl Parse for ItemType { parse(input: ParseStream) -> Result<Self>1923 fn parse(input: ParseStream) -> Result<Self> { 1924 Ok(ItemType { 1925 attrs: input.call(Attribute::parse_outer)?, 1926 vis: input.parse()?, 1927 type_token: input.parse()?, 1928 ident: input.parse()?, 1929 generics: { 1930 let mut generics: Generics = input.parse()?; 1931 generics.where_clause = input.parse()?; 1932 generics 1933 }, 1934 eq_token: input.parse()?, 1935 ty: input.parse()?, 1936 semi_token: input.parse()?, 1937 }) 1938 } 1939 } 1940 parse_item_type(begin: ParseBuffer, input: ParseStream) -> Result<Item>1941 fn parse_item_type(begin: ParseBuffer, input: ParseStream) -> Result<Item> { 1942 let FlexibleItemType { 1943 vis, 1944 defaultness, 1945 type_token, 1946 ident, 1947 generics, 1948 colon_token, 1949 bounds: _, 1950 ty, 1951 semi_token, 1952 } = FlexibleItemType::parse(input, WhereClauseLocation::BeforeEq)?; 1953 1954 if defaultness.is_some() || colon_token.is_some() || ty.is_none() { 1955 Ok(Item::Verbatim(verbatim::between(begin, input))) 1956 } else { 1957 let (eq_token, ty) = ty.unwrap(); 1958 Ok(Item::Type(ItemType { 1959 attrs: Vec::new(), 1960 vis, 1961 type_token, 1962 ident, 1963 generics, 1964 eq_token, 1965 ty: Box::new(ty), 1966 semi_token, 1967 })) 1968 } 1969 } 1970 1971 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1972 impl Parse for ItemStruct { parse(input: ParseStream) -> Result<Self>1973 fn parse(input: ParseStream) -> Result<Self> { 1974 let attrs = input.call(Attribute::parse_outer)?; 1975 let vis = input.parse::<Visibility>()?; 1976 let struct_token = input.parse::<Token![struct]>()?; 1977 let ident = input.parse::<Ident>()?; 1978 let generics = input.parse::<Generics>()?; 1979 let (where_clause, fields, semi_token) = derive::parsing::data_struct(input)?; 1980 Ok(ItemStruct { 1981 attrs, 1982 vis, 1983 struct_token, 1984 ident, 1985 generics: Generics { 1986 where_clause, 1987 ..generics 1988 }, 1989 fields, 1990 semi_token, 1991 }) 1992 } 1993 } 1994 1995 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 1996 impl Parse for ItemEnum { parse(input: ParseStream) -> Result<Self>1997 fn parse(input: ParseStream) -> Result<Self> { 1998 let attrs = input.call(Attribute::parse_outer)?; 1999 let vis = input.parse::<Visibility>()?; 2000 let enum_token = input.parse::<Token![enum]>()?; 2001 let ident = input.parse::<Ident>()?; 2002 let generics = input.parse::<Generics>()?; 2003 let (where_clause, brace_token, variants) = derive::parsing::data_enum(input)?; 2004 Ok(ItemEnum { 2005 attrs, 2006 vis, 2007 enum_token, 2008 ident, 2009 generics: Generics { 2010 where_clause, 2011 ..generics 2012 }, 2013 brace_token, 2014 variants, 2015 }) 2016 } 2017 } 2018 2019 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2020 impl Parse for ItemUnion { parse(input: ParseStream) -> Result<Self>2021 fn parse(input: ParseStream) -> Result<Self> { 2022 let attrs = input.call(Attribute::parse_outer)?; 2023 let vis = input.parse::<Visibility>()?; 2024 let union_token = input.parse::<Token![union]>()?; 2025 let ident = input.parse::<Ident>()?; 2026 let generics = input.parse::<Generics>()?; 2027 let (where_clause, fields) = derive::parsing::data_union(input)?; 2028 Ok(ItemUnion { 2029 attrs, 2030 vis, 2031 union_token, 2032 ident, 2033 generics: Generics { 2034 where_clause, 2035 ..generics 2036 }, 2037 fields, 2038 }) 2039 } 2040 } 2041 parse_trait_or_trait_alias(input: ParseStream) -> Result<Item>2042 fn parse_trait_or_trait_alias(input: ParseStream) -> Result<Item> { 2043 let (attrs, vis, trait_token, ident, generics) = parse_start_of_trait_alias(input)?; 2044 let lookahead = input.lookahead1(); 2045 if lookahead.peek(token::Brace) 2046 || lookahead.peek(Token![:]) 2047 || lookahead.peek(Token![where]) 2048 { 2049 let unsafety = None; 2050 let auto_token = None; 2051 parse_rest_of_trait( 2052 input, 2053 attrs, 2054 vis, 2055 unsafety, 2056 auto_token, 2057 trait_token, 2058 ident, 2059 generics, 2060 ) 2061 .map(Item::Trait) 2062 } else if lookahead.peek(Token![=]) { 2063 parse_rest_of_trait_alias(input, attrs, vis, trait_token, ident, generics) 2064 .map(Item::TraitAlias) 2065 } else { 2066 Err(lookahead.error()) 2067 } 2068 } 2069 2070 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2071 impl Parse for ItemTrait { parse(input: ParseStream) -> Result<Self>2072 fn parse(input: ParseStream) -> Result<Self> { 2073 let outer_attrs = input.call(Attribute::parse_outer)?; 2074 let vis: Visibility = input.parse()?; 2075 let unsafety: Option<Token![unsafe]> = input.parse()?; 2076 let auto_token: Option<Token![auto]> = input.parse()?; 2077 let trait_token: Token![trait] = input.parse()?; 2078 let ident: Ident = input.parse()?; 2079 let generics: Generics = input.parse()?; 2080 parse_rest_of_trait( 2081 input, 2082 outer_attrs, 2083 vis, 2084 unsafety, 2085 auto_token, 2086 trait_token, 2087 ident, 2088 generics, 2089 ) 2090 } 2091 } 2092 parse_rest_of_trait( input: ParseStream, mut attrs: Vec<Attribute>, vis: Visibility, unsafety: Option<Token![unsafe]>, auto_token: Option<Token![auto]>, trait_token: Token![trait], ident: Ident, mut generics: Generics, ) -> Result<ItemTrait>2093 fn parse_rest_of_trait( 2094 input: ParseStream, 2095 mut attrs: Vec<Attribute>, 2096 vis: Visibility, 2097 unsafety: Option<Token![unsafe]>, 2098 auto_token: Option<Token![auto]>, 2099 trait_token: Token![trait], 2100 ident: Ident, 2101 mut generics: Generics, 2102 ) -> Result<ItemTrait> { 2103 let colon_token: Option<Token![:]> = input.parse()?; 2104 2105 let mut supertraits = Punctuated::new(); 2106 if colon_token.is_some() { 2107 loop { 2108 if input.peek(Token![where]) || input.peek(token::Brace) { 2109 break; 2110 } 2111 supertraits.push_value(input.parse()?); 2112 if input.peek(Token![where]) || input.peek(token::Brace) { 2113 break; 2114 } 2115 supertraits.push_punct(input.parse()?); 2116 } 2117 } 2118 2119 generics.where_clause = input.parse()?; 2120 2121 let content; 2122 let brace_token = braced!(content in input); 2123 attr::parsing::parse_inner(&content, &mut attrs)?; 2124 let mut items = Vec::new(); 2125 while !content.is_empty() { 2126 items.push(content.parse()?); 2127 } 2128 2129 Ok(ItemTrait { 2130 attrs, 2131 vis, 2132 unsafety, 2133 auto_token, 2134 trait_token, 2135 ident, 2136 generics, 2137 colon_token, 2138 supertraits, 2139 brace_token, 2140 items, 2141 }) 2142 } 2143 2144 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2145 impl Parse for ItemTraitAlias { parse(input: ParseStream) -> Result<Self>2146 fn parse(input: ParseStream) -> Result<Self> { 2147 let (attrs, vis, trait_token, ident, generics) = parse_start_of_trait_alias(input)?; 2148 parse_rest_of_trait_alias(input, attrs, vis, trait_token, ident, generics) 2149 } 2150 } 2151 parse_start_of_trait_alias( input: ParseStream, ) -> Result<(Vec<Attribute>, Visibility, Token![trait], Ident, Generics)>2152 fn parse_start_of_trait_alias( 2153 input: ParseStream, 2154 ) -> Result<(Vec<Attribute>, Visibility, Token![trait], Ident, Generics)> { 2155 let attrs = input.call(Attribute::parse_outer)?; 2156 let vis: Visibility = input.parse()?; 2157 let trait_token: Token![trait] = input.parse()?; 2158 let ident: Ident = input.parse()?; 2159 let generics: Generics = input.parse()?; 2160 Ok((attrs, vis, trait_token, ident, generics)) 2161 } 2162 parse_rest_of_trait_alias( input: ParseStream, attrs: Vec<Attribute>, vis: Visibility, trait_token: Token![trait], ident: Ident, mut generics: Generics, ) -> Result<ItemTraitAlias>2163 fn parse_rest_of_trait_alias( 2164 input: ParseStream, 2165 attrs: Vec<Attribute>, 2166 vis: Visibility, 2167 trait_token: Token![trait], 2168 ident: Ident, 2169 mut generics: Generics, 2170 ) -> Result<ItemTraitAlias> { 2171 let eq_token: Token![=] = input.parse()?; 2172 2173 let mut bounds = Punctuated::new(); 2174 loop { 2175 if input.peek(Token![where]) || input.peek(Token![;]) { 2176 break; 2177 } 2178 bounds.push_value(input.parse()?); 2179 if input.peek(Token![where]) || input.peek(Token![;]) { 2180 break; 2181 } 2182 bounds.push_punct(input.parse()?); 2183 } 2184 2185 generics.where_clause = input.parse()?; 2186 let semi_token: Token![;] = input.parse()?; 2187 2188 Ok(ItemTraitAlias { 2189 attrs, 2190 vis, 2191 trait_token, 2192 ident, 2193 generics, 2194 eq_token, 2195 bounds, 2196 semi_token, 2197 }) 2198 } 2199 2200 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2201 impl Parse for TraitItem { parse(input: ParseStream) -> Result<Self>2202 fn parse(input: ParseStream) -> Result<Self> { 2203 let begin = input.fork(); 2204 let mut attrs = input.call(Attribute::parse_outer)?; 2205 let vis: Visibility = input.parse()?; 2206 let defaultness: Option<Token![default]> = input.parse()?; 2207 let ahead = input.fork(); 2208 2209 let lookahead = ahead.lookahead1(); 2210 let mut item = if lookahead.peek(Token![fn]) || peek_signature(&ahead) { 2211 input.parse().map(TraitItem::Method) 2212 } else if lookahead.peek(Token![const]) { 2213 ahead.parse::<Token![const]>()?; 2214 let lookahead = ahead.lookahead1(); 2215 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 2216 input.parse().map(TraitItem::Const) 2217 } else if lookahead.peek(Token![async]) 2218 || lookahead.peek(Token![unsafe]) 2219 || lookahead.peek(Token![extern]) 2220 || lookahead.peek(Token![fn]) 2221 { 2222 input.parse().map(TraitItem::Method) 2223 } else { 2224 Err(lookahead.error()) 2225 } 2226 } else if lookahead.peek(Token![type]) { 2227 parse_trait_item_type(begin.fork(), input) 2228 } else if lookahead.peek(Ident) 2229 || lookahead.peek(Token![self]) 2230 || lookahead.peek(Token![super]) 2231 || lookahead.peek(Token![crate]) 2232 || lookahead.peek(Token![::]) 2233 { 2234 input.parse().map(TraitItem::Macro) 2235 } else { 2236 Err(lookahead.error()) 2237 }?; 2238 2239 match (vis, defaultness) { 2240 (Visibility::Inherited, None) => {} 2241 _ => return Ok(TraitItem::Verbatim(verbatim::between(begin, input))), 2242 } 2243 2244 let item_attrs = match &mut item { 2245 TraitItem::Const(item) => &mut item.attrs, 2246 TraitItem::Method(item) => &mut item.attrs, 2247 TraitItem::Type(item) => &mut item.attrs, 2248 TraitItem::Macro(item) => &mut item.attrs, 2249 TraitItem::Verbatim(_) => unreachable!(), 2250 2251 #[cfg(syn_no_non_exhaustive)] 2252 _ => unreachable!(), 2253 }; 2254 attrs.append(item_attrs); 2255 *item_attrs = attrs; 2256 Ok(item) 2257 } 2258 } 2259 2260 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2261 impl Parse for TraitItemConst { parse(input: ParseStream) -> Result<Self>2262 fn parse(input: ParseStream) -> Result<Self> { 2263 Ok(TraitItemConst { 2264 attrs: input.call(Attribute::parse_outer)?, 2265 const_token: input.parse()?, 2266 ident: { 2267 let lookahead = input.lookahead1(); 2268 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 2269 input.call(Ident::parse_any)? 2270 } else { 2271 return Err(lookahead.error()); 2272 } 2273 }, 2274 colon_token: input.parse()?, 2275 ty: input.parse()?, 2276 default: { 2277 if input.peek(Token![=]) { 2278 let eq_token: Token![=] = input.parse()?; 2279 let default: Expr = input.parse()?; 2280 Some((eq_token, default)) 2281 } else { 2282 None 2283 } 2284 }, 2285 semi_token: input.parse()?, 2286 }) 2287 } 2288 } 2289 2290 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2291 impl Parse for TraitItemMethod { parse(input: ParseStream) -> Result<Self>2292 fn parse(input: ParseStream) -> Result<Self> { 2293 let mut attrs = input.call(Attribute::parse_outer)?; 2294 let sig: Signature = input.parse()?; 2295 2296 let lookahead = input.lookahead1(); 2297 let (brace_token, stmts, semi_token) = if lookahead.peek(token::Brace) { 2298 let content; 2299 let brace_token = braced!(content in input); 2300 attr::parsing::parse_inner(&content, &mut attrs)?; 2301 let stmts = content.call(Block::parse_within)?; 2302 (Some(brace_token), stmts, None) 2303 } else if lookahead.peek(Token![;]) { 2304 let semi_token: Token![;] = input.parse()?; 2305 (None, Vec::new(), Some(semi_token)) 2306 } else { 2307 return Err(lookahead.error()); 2308 }; 2309 2310 Ok(TraitItemMethod { 2311 attrs, 2312 sig, 2313 default: brace_token.map(|brace_token| Block { brace_token, stmts }), 2314 semi_token, 2315 }) 2316 } 2317 } 2318 2319 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2320 impl Parse for TraitItemType { parse(input: ParseStream) -> Result<Self>2321 fn parse(input: ParseStream) -> Result<Self> { 2322 let attrs = input.call(Attribute::parse_outer)?; 2323 let type_token: Token![type] = input.parse()?; 2324 let ident: Ident = input.parse()?; 2325 let mut generics: Generics = input.parse()?; 2326 let colon_token: Option<Token![:]> = input.parse()?; 2327 2328 let mut bounds = Punctuated::new(); 2329 if colon_token.is_some() { 2330 while !input.peek(Token![where]) && !input.peek(Token![=]) && !input.peek(Token![;]) 2331 { 2332 if !bounds.is_empty() { 2333 bounds.push_punct(input.parse()?); 2334 } 2335 bounds.push_value(input.parse()?); 2336 } 2337 } 2338 2339 let default = if input.peek(Token![=]) { 2340 let eq_token: Token![=] = input.parse()?; 2341 let default: Type = input.parse()?; 2342 Some((eq_token, default)) 2343 } else { 2344 None 2345 }; 2346 2347 generics.where_clause = input.parse()?; 2348 let semi_token: Token![;] = input.parse()?; 2349 2350 Ok(TraitItemType { 2351 attrs, 2352 type_token, 2353 ident, 2354 generics, 2355 colon_token, 2356 bounds, 2357 default, 2358 semi_token, 2359 }) 2360 } 2361 } 2362 parse_trait_item_type(begin: ParseBuffer, input: ParseStream) -> Result<TraitItem>2363 fn parse_trait_item_type(begin: ParseBuffer, input: ParseStream) -> Result<TraitItem> { 2364 let FlexibleItemType { 2365 vis, 2366 defaultness, 2367 type_token, 2368 ident, 2369 generics, 2370 colon_token, 2371 bounds, 2372 ty, 2373 semi_token, 2374 } = FlexibleItemType::parse(input, WhereClauseLocation::Both)?; 2375 2376 if defaultness.is_some() || vis.is_some() { 2377 Ok(TraitItem::Verbatim(verbatim::between(begin, input))) 2378 } else { 2379 Ok(TraitItem::Type(TraitItemType { 2380 attrs: Vec::new(), 2381 type_token, 2382 ident, 2383 generics, 2384 colon_token, 2385 bounds, 2386 default: ty, 2387 semi_token, 2388 })) 2389 } 2390 } 2391 2392 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2393 impl Parse for TraitItemMacro { parse(input: ParseStream) -> Result<Self>2394 fn parse(input: ParseStream) -> Result<Self> { 2395 let attrs = input.call(Attribute::parse_outer)?; 2396 let mac: Macro = input.parse()?; 2397 let semi_token: Option<Token![;]> = if mac.delimiter.is_brace() { 2398 None 2399 } else { 2400 Some(input.parse()?) 2401 }; 2402 Ok(TraitItemMacro { 2403 attrs, 2404 mac, 2405 semi_token, 2406 }) 2407 } 2408 } 2409 2410 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2411 impl Parse for ItemImpl { parse(input: ParseStream) -> Result<Self>2412 fn parse(input: ParseStream) -> Result<Self> { 2413 let allow_verbatim_impl = false; 2414 parse_impl(input, allow_verbatim_impl).map(Option::unwrap) 2415 } 2416 } 2417 parse_impl(input: ParseStream, allow_verbatim_impl: bool) -> Result<Option<ItemImpl>>2418 fn parse_impl(input: ParseStream, allow_verbatim_impl: bool) -> Result<Option<ItemImpl>> { 2419 let mut attrs = input.call(Attribute::parse_outer)?; 2420 let has_visibility = allow_verbatim_impl && input.parse::<Visibility>()?.is_some(); 2421 let defaultness: Option<Token![default]> = input.parse()?; 2422 let unsafety: Option<Token![unsafe]> = input.parse()?; 2423 let impl_token: Token![impl] = input.parse()?; 2424 2425 let has_generics = input.peek(Token![<]) 2426 && (input.peek2(Token![>]) 2427 || input.peek2(Token![#]) 2428 || (input.peek2(Ident) || input.peek2(Lifetime)) 2429 && (input.peek3(Token![:]) 2430 || input.peek3(Token![,]) 2431 || input.peek3(Token![>]) 2432 || input.peek3(Token![=])) 2433 || input.peek2(Token![const])); 2434 let mut generics: Generics = if has_generics { 2435 input.parse()? 2436 } else { 2437 Generics::default() 2438 }; 2439 2440 let is_const_impl = allow_verbatim_impl 2441 && (input.peek(Token![const]) || input.peek(Token![?]) && input.peek2(Token![const])); 2442 if is_const_impl { 2443 input.parse::<Option<Token![?]>>()?; 2444 input.parse::<Token![const]>()?; 2445 } 2446 2447 let begin = input.fork(); 2448 let polarity = if input.peek(Token![!]) && !input.peek2(token::Brace) { 2449 Some(input.parse::<Token![!]>()?) 2450 } else { 2451 None 2452 }; 2453 2454 #[cfg(not(feature = "printing"))] 2455 let first_ty_span = input.span(); 2456 let mut first_ty: Type = input.parse()?; 2457 let self_ty: Type; 2458 let trait_; 2459 2460 let is_impl_for = input.peek(Token![for]); 2461 if is_impl_for { 2462 let for_token: Token![for] = input.parse()?; 2463 let mut first_ty_ref = &first_ty; 2464 while let Type::Group(ty) = first_ty_ref { 2465 first_ty_ref = &ty.elem; 2466 } 2467 if let Type::Path(TypePath { qself: None, .. }) = first_ty_ref { 2468 while let Type::Group(ty) = first_ty { 2469 first_ty = *ty.elem; 2470 } 2471 if let Type::Path(TypePath { qself: None, path }) = first_ty { 2472 trait_ = Some((polarity, path, for_token)); 2473 } else { 2474 unreachable!(); 2475 } 2476 } else if !allow_verbatim_impl { 2477 #[cfg(feature = "printing")] 2478 return Err(Error::new_spanned(first_ty_ref, "expected trait path")); 2479 #[cfg(not(feature = "printing"))] 2480 return Err(Error::new(first_ty_span, "expected trait path")); 2481 } else { 2482 trait_ = None; 2483 } 2484 self_ty = input.parse()?; 2485 } else { 2486 trait_ = None; 2487 self_ty = if polarity.is_none() { 2488 first_ty 2489 } else { 2490 Type::Verbatim(verbatim::between(begin, input)) 2491 }; 2492 } 2493 2494 generics.where_clause = input.parse()?; 2495 2496 let content; 2497 let brace_token = braced!(content in input); 2498 attr::parsing::parse_inner(&content, &mut attrs)?; 2499 2500 let mut items = Vec::new(); 2501 while !content.is_empty() { 2502 items.push(content.parse()?); 2503 } 2504 2505 if has_visibility || is_const_impl || is_impl_for && trait_.is_none() { 2506 Ok(None) 2507 } else { 2508 Ok(Some(ItemImpl { 2509 attrs, 2510 defaultness, 2511 unsafety, 2512 impl_token, 2513 generics, 2514 trait_, 2515 self_ty: Box::new(self_ty), 2516 brace_token, 2517 items, 2518 })) 2519 } 2520 } 2521 2522 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2523 impl Parse for ImplItem { parse(input: ParseStream) -> Result<Self>2524 fn parse(input: ParseStream) -> Result<Self> { 2525 let begin = input.fork(); 2526 let mut attrs = input.call(Attribute::parse_outer)?; 2527 let ahead = input.fork(); 2528 let vis: Visibility = ahead.parse()?; 2529 2530 let mut lookahead = ahead.lookahead1(); 2531 let defaultness = if lookahead.peek(Token![default]) && !ahead.peek2(Token![!]) { 2532 let defaultness: Token![default] = ahead.parse()?; 2533 lookahead = ahead.lookahead1(); 2534 Some(defaultness) 2535 } else { 2536 None 2537 }; 2538 2539 let mut item = if lookahead.peek(Token![fn]) || peek_signature(&ahead) { 2540 input.parse().map(ImplItem::Method) 2541 } else if lookahead.peek(Token![const]) { 2542 let const_token: Token![const] = ahead.parse()?; 2543 let lookahead = ahead.lookahead1(); 2544 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 2545 input.advance_to(&ahead); 2546 let ident: Ident = input.call(Ident::parse_any)?; 2547 let colon_token: Token![:] = input.parse()?; 2548 let ty: Type = input.parse()?; 2549 if let Some(eq_token) = input.parse()? { 2550 return Ok(ImplItem::Const(ImplItemConst { 2551 attrs, 2552 vis, 2553 defaultness, 2554 const_token, 2555 ident, 2556 colon_token, 2557 ty, 2558 eq_token, 2559 expr: input.parse()?, 2560 semi_token: input.parse()?, 2561 })); 2562 } else { 2563 input.parse::<Token![;]>()?; 2564 return Ok(ImplItem::Verbatim(verbatim::between(begin, input))); 2565 } 2566 } else { 2567 Err(lookahead.error()) 2568 } 2569 } else if lookahead.peek(Token![type]) { 2570 parse_impl_item_type(begin, input) 2571 } else if vis.is_inherited() 2572 && defaultness.is_none() 2573 && (lookahead.peek(Ident) 2574 || lookahead.peek(Token![self]) 2575 || lookahead.peek(Token![super]) 2576 || lookahead.peek(Token![crate]) 2577 || lookahead.peek(Token![::])) 2578 { 2579 input.parse().map(ImplItem::Macro) 2580 } else { 2581 Err(lookahead.error()) 2582 }?; 2583 2584 { 2585 let item_attrs = match &mut item { 2586 ImplItem::Const(item) => &mut item.attrs, 2587 ImplItem::Method(item) => &mut item.attrs, 2588 ImplItem::Type(item) => &mut item.attrs, 2589 ImplItem::Macro(item) => &mut item.attrs, 2590 ImplItem::Verbatim(_) => return Ok(item), 2591 2592 #[cfg(syn_no_non_exhaustive)] 2593 _ => unreachable!(), 2594 }; 2595 attrs.append(item_attrs); 2596 *item_attrs = attrs; 2597 } 2598 2599 Ok(item) 2600 } 2601 } 2602 2603 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2604 impl Parse for ImplItemConst { parse(input: ParseStream) -> Result<Self>2605 fn parse(input: ParseStream) -> Result<Self> { 2606 Ok(ImplItemConst { 2607 attrs: input.call(Attribute::parse_outer)?, 2608 vis: input.parse()?, 2609 defaultness: input.parse()?, 2610 const_token: input.parse()?, 2611 ident: { 2612 let lookahead = input.lookahead1(); 2613 if lookahead.peek(Ident) || lookahead.peek(Token![_]) { 2614 input.call(Ident::parse_any)? 2615 } else { 2616 return Err(lookahead.error()); 2617 } 2618 }, 2619 colon_token: input.parse()?, 2620 ty: input.parse()?, 2621 eq_token: input.parse()?, 2622 expr: input.parse()?, 2623 semi_token: input.parse()?, 2624 }) 2625 } 2626 } 2627 2628 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2629 impl Parse for ImplItemMethod { parse(input: ParseStream) -> Result<Self>2630 fn parse(input: ParseStream) -> Result<Self> { 2631 let mut attrs = input.call(Attribute::parse_outer)?; 2632 let vis: Visibility = input.parse()?; 2633 let defaultness: Option<Token![default]> = input.parse()?; 2634 let sig: Signature = input.parse()?; 2635 2636 let block = if let Some(semi) = input.parse::<Option<Token![;]>>()? { 2637 // Accept methods without a body in an impl block because 2638 // rustc's *parser* does not reject them (the compilation error 2639 // is emitted later than parsing) and it can be useful for macro 2640 // DSLs. 2641 let mut punct = Punct::new(';', Spacing::Alone); 2642 punct.set_span(semi.span); 2643 let tokens = TokenStream::from_iter(vec![TokenTree::Punct(punct)]); 2644 Block { 2645 brace_token: Brace { span: semi.span }, 2646 stmts: vec![Stmt::Item(Item::Verbatim(tokens))], 2647 } 2648 } else { 2649 let content; 2650 let brace_token = braced!(content in input); 2651 attrs.extend(content.call(Attribute::parse_inner)?); 2652 Block { 2653 brace_token, 2654 stmts: content.call(Block::parse_within)?, 2655 } 2656 }; 2657 2658 Ok(ImplItemMethod { 2659 attrs, 2660 vis, 2661 defaultness, 2662 sig, 2663 block, 2664 }) 2665 } 2666 } 2667 2668 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2669 impl Parse for ImplItemType { parse(input: ParseStream) -> Result<Self>2670 fn parse(input: ParseStream) -> Result<Self> { 2671 let attrs = input.call(Attribute::parse_outer)?; 2672 let vis: Visibility = input.parse()?; 2673 let defaultness: Option<Token![default]> = input.parse()?; 2674 let type_token: Token![type] = input.parse()?; 2675 let ident: Ident = input.parse()?; 2676 let mut generics: Generics = input.parse()?; 2677 let eq_token: Token![=] = input.parse()?; 2678 let ty: Type = input.parse()?; 2679 generics.where_clause = input.parse()?; 2680 let semi_token: Token![;] = input.parse()?; 2681 Ok(ImplItemType { 2682 attrs, 2683 vis, 2684 defaultness, 2685 type_token, 2686 ident, 2687 generics, 2688 eq_token, 2689 ty, 2690 semi_token, 2691 }) 2692 } 2693 } 2694 parse_impl_item_type(begin: ParseBuffer, input: ParseStream) -> Result<ImplItem>2695 fn parse_impl_item_type(begin: ParseBuffer, input: ParseStream) -> Result<ImplItem> { 2696 let FlexibleItemType { 2697 vis, 2698 defaultness, 2699 type_token, 2700 ident, 2701 generics, 2702 colon_token, 2703 bounds: _, 2704 ty, 2705 semi_token, 2706 } = FlexibleItemType::parse(input, WhereClauseLocation::Both)?; 2707 2708 if colon_token.is_some() || ty.is_none() { 2709 Ok(ImplItem::Verbatim(verbatim::between(begin, input))) 2710 } else { 2711 let (eq_token, ty) = ty.unwrap(); 2712 Ok(ImplItem::Type(ImplItemType { 2713 attrs: Vec::new(), 2714 vis, 2715 defaultness, 2716 type_token, 2717 ident, 2718 generics, 2719 eq_token, 2720 ty, 2721 semi_token, 2722 })) 2723 } 2724 } 2725 2726 #[cfg_attr(doc_cfg, doc(cfg(feature = "parsing")))] 2727 impl Parse for ImplItemMacro { parse(input: ParseStream) -> Result<Self>2728 fn parse(input: ParseStream) -> Result<Self> { 2729 let attrs = input.call(Attribute::parse_outer)?; 2730 let mac: Macro = input.parse()?; 2731 let semi_token: Option<Token![;]> = if mac.delimiter.is_brace() { 2732 None 2733 } else { 2734 Some(input.parse()?) 2735 }; 2736 Ok(ImplItemMacro { 2737 attrs, 2738 mac, 2739 semi_token, 2740 }) 2741 } 2742 } 2743 2744 impl Visibility { is_inherited(&self) -> bool2745 fn is_inherited(&self) -> bool { 2746 match *self { 2747 Visibility::Inherited => true, 2748 _ => false, 2749 } 2750 } 2751 } 2752 2753 impl MacroDelimiter { is_brace(&self) -> bool2754 fn is_brace(&self) -> bool { 2755 match *self { 2756 MacroDelimiter::Brace(_) => true, 2757 MacroDelimiter::Paren(_) | MacroDelimiter::Bracket(_) => false, 2758 } 2759 } 2760 } 2761 } 2762 2763 #[cfg(feature = "printing")] 2764 mod printing { 2765 use super::*; 2766 use crate::attr::FilterAttrs; 2767 use crate::print::TokensOrDefault; 2768 use proc_macro2::TokenStream; 2769 use quote::{ToTokens, TokenStreamExt}; 2770 2771 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2772 impl ToTokens for ItemExternCrate { to_tokens(&self, tokens: &mut TokenStream)2773 fn to_tokens(&self, tokens: &mut TokenStream) { 2774 tokens.append_all(self.attrs.outer()); 2775 self.vis.to_tokens(tokens); 2776 self.extern_token.to_tokens(tokens); 2777 self.crate_token.to_tokens(tokens); 2778 self.ident.to_tokens(tokens); 2779 if let Some((as_token, rename)) = &self.rename { 2780 as_token.to_tokens(tokens); 2781 rename.to_tokens(tokens); 2782 } 2783 self.semi_token.to_tokens(tokens); 2784 } 2785 } 2786 2787 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2788 impl ToTokens for ItemUse { to_tokens(&self, tokens: &mut TokenStream)2789 fn to_tokens(&self, tokens: &mut TokenStream) { 2790 tokens.append_all(self.attrs.outer()); 2791 self.vis.to_tokens(tokens); 2792 self.use_token.to_tokens(tokens); 2793 self.leading_colon.to_tokens(tokens); 2794 self.tree.to_tokens(tokens); 2795 self.semi_token.to_tokens(tokens); 2796 } 2797 } 2798 2799 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2800 impl ToTokens for ItemStatic { to_tokens(&self, tokens: &mut TokenStream)2801 fn to_tokens(&self, tokens: &mut TokenStream) { 2802 tokens.append_all(self.attrs.outer()); 2803 self.vis.to_tokens(tokens); 2804 self.static_token.to_tokens(tokens); 2805 self.mutability.to_tokens(tokens); 2806 self.ident.to_tokens(tokens); 2807 self.colon_token.to_tokens(tokens); 2808 self.ty.to_tokens(tokens); 2809 self.eq_token.to_tokens(tokens); 2810 self.expr.to_tokens(tokens); 2811 self.semi_token.to_tokens(tokens); 2812 } 2813 } 2814 2815 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2816 impl ToTokens for ItemConst { to_tokens(&self, tokens: &mut TokenStream)2817 fn to_tokens(&self, tokens: &mut TokenStream) { 2818 tokens.append_all(self.attrs.outer()); 2819 self.vis.to_tokens(tokens); 2820 self.const_token.to_tokens(tokens); 2821 self.ident.to_tokens(tokens); 2822 self.colon_token.to_tokens(tokens); 2823 self.ty.to_tokens(tokens); 2824 self.eq_token.to_tokens(tokens); 2825 self.expr.to_tokens(tokens); 2826 self.semi_token.to_tokens(tokens); 2827 } 2828 } 2829 2830 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2831 impl ToTokens for ItemFn { to_tokens(&self, tokens: &mut TokenStream)2832 fn to_tokens(&self, tokens: &mut TokenStream) { 2833 tokens.append_all(self.attrs.outer()); 2834 self.vis.to_tokens(tokens); 2835 self.sig.to_tokens(tokens); 2836 self.block.brace_token.surround(tokens, |tokens| { 2837 tokens.append_all(self.attrs.inner()); 2838 tokens.append_all(&self.block.stmts); 2839 }); 2840 } 2841 } 2842 2843 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2844 impl ToTokens for ItemMod { to_tokens(&self, tokens: &mut TokenStream)2845 fn to_tokens(&self, tokens: &mut TokenStream) { 2846 tokens.append_all(self.attrs.outer()); 2847 self.vis.to_tokens(tokens); 2848 self.mod_token.to_tokens(tokens); 2849 self.ident.to_tokens(tokens); 2850 if let Some((brace, items)) = &self.content { 2851 brace.surround(tokens, |tokens| { 2852 tokens.append_all(self.attrs.inner()); 2853 tokens.append_all(items); 2854 }); 2855 } else { 2856 TokensOrDefault(&self.semi).to_tokens(tokens); 2857 } 2858 } 2859 } 2860 2861 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2862 impl ToTokens for ItemForeignMod { to_tokens(&self, tokens: &mut TokenStream)2863 fn to_tokens(&self, tokens: &mut TokenStream) { 2864 tokens.append_all(self.attrs.outer()); 2865 self.abi.to_tokens(tokens); 2866 self.brace_token.surround(tokens, |tokens| { 2867 tokens.append_all(self.attrs.inner()); 2868 tokens.append_all(&self.items); 2869 }); 2870 } 2871 } 2872 2873 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2874 impl ToTokens for ItemType { to_tokens(&self, tokens: &mut TokenStream)2875 fn to_tokens(&self, tokens: &mut TokenStream) { 2876 tokens.append_all(self.attrs.outer()); 2877 self.vis.to_tokens(tokens); 2878 self.type_token.to_tokens(tokens); 2879 self.ident.to_tokens(tokens); 2880 self.generics.to_tokens(tokens); 2881 self.generics.where_clause.to_tokens(tokens); 2882 self.eq_token.to_tokens(tokens); 2883 self.ty.to_tokens(tokens); 2884 self.semi_token.to_tokens(tokens); 2885 } 2886 } 2887 2888 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2889 impl ToTokens for ItemEnum { to_tokens(&self, tokens: &mut TokenStream)2890 fn to_tokens(&self, tokens: &mut TokenStream) { 2891 tokens.append_all(self.attrs.outer()); 2892 self.vis.to_tokens(tokens); 2893 self.enum_token.to_tokens(tokens); 2894 self.ident.to_tokens(tokens); 2895 self.generics.to_tokens(tokens); 2896 self.generics.where_clause.to_tokens(tokens); 2897 self.brace_token.surround(tokens, |tokens| { 2898 self.variants.to_tokens(tokens); 2899 }); 2900 } 2901 } 2902 2903 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2904 impl ToTokens for ItemStruct { to_tokens(&self, tokens: &mut TokenStream)2905 fn to_tokens(&self, tokens: &mut TokenStream) { 2906 tokens.append_all(self.attrs.outer()); 2907 self.vis.to_tokens(tokens); 2908 self.struct_token.to_tokens(tokens); 2909 self.ident.to_tokens(tokens); 2910 self.generics.to_tokens(tokens); 2911 match &self.fields { 2912 Fields::Named(fields) => { 2913 self.generics.where_clause.to_tokens(tokens); 2914 fields.to_tokens(tokens); 2915 } 2916 Fields::Unnamed(fields) => { 2917 fields.to_tokens(tokens); 2918 self.generics.where_clause.to_tokens(tokens); 2919 TokensOrDefault(&self.semi_token).to_tokens(tokens); 2920 } 2921 Fields::Unit => { 2922 self.generics.where_clause.to_tokens(tokens); 2923 TokensOrDefault(&self.semi_token).to_tokens(tokens); 2924 } 2925 } 2926 } 2927 } 2928 2929 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2930 impl ToTokens for ItemUnion { to_tokens(&self, tokens: &mut TokenStream)2931 fn to_tokens(&self, tokens: &mut TokenStream) { 2932 tokens.append_all(self.attrs.outer()); 2933 self.vis.to_tokens(tokens); 2934 self.union_token.to_tokens(tokens); 2935 self.ident.to_tokens(tokens); 2936 self.generics.to_tokens(tokens); 2937 self.generics.where_clause.to_tokens(tokens); 2938 self.fields.to_tokens(tokens); 2939 } 2940 } 2941 2942 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2943 impl ToTokens for ItemTrait { to_tokens(&self, tokens: &mut TokenStream)2944 fn to_tokens(&self, tokens: &mut TokenStream) { 2945 tokens.append_all(self.attrs.outer()); 2946 self.vis.to_tokens(tokens); 2947 self.unsafety.to_tokens(tokens); 2948 self.auto_token.to_tokens(tokens); 2949 self.trait_token.to_tokens(tokens); 2950 self.ident.to_tokens(tokens); 2951 self.generics.to_tokens(tokens); 2952 if !self.supertraits.is_empty() { 2953 TokensOrDefault(&self.colon_token).to_tokens(tokens); 2954 self.supertraits.to_tokens(tokens); 2955 } 2956 self.generics.where_clause.to_tokens(tokens); 2957 self.brace_token.surround(tokens, |tokens| { 2958 tokens.append_all(self.attrs.inner()); 2959 tokens.append_all(&self.items); 2960 }); 2961 } 2962 } 2963 2964 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2965 impl ToTokens for ItemTraitAlias { to_tokens(&self, tokens: &mut TokenStream)2966 fn to_tokens(&self, tokens: &mut TokenStream) { 2967 tokens.append_all(self.attrs.outer()); 2968 self.vis.to_tokens(tokens); 2969 self.trait_token.to_tokens(tokens); 2970 self.ident.to_tokens(tokens); 2971 self.generics.to_tokens(tokens); 2972 self.eq_token.to_tokens(tokens); 2973 self.bounds.to_tokens(tokens); 2974 self.generics.where_clause.to_tokens(tokens); 2975 self.semi_token.to_tokens(tokens); 2976 } 2977 } 2978 2979 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 2980 impl ToTokens for ItemImpl { to_tokens(&self, tokens: &mut TokenStream)2981 fn to_tokens(&self, tokens: &mut TokenStream) { 2982 tokens.append_all(self.attrs.outer()); 2983 self.defaultness.to_tokens(tokens); 2984 self.unsafety.to_tokens(tokens); 2985 self.impl_token.to_tokens(tokens); 2986 self.generics.to_tokens(tokens); 2987 if let Some((polarity, path, for_token)) = &self.trait_ { 2988 polarity.to_tokens(tokens); 2989 path.to_tokens(tokens); 2990 for_token.to_tokens(tokens); 2991 } 2992 self.self_ty.to_tokens(tokens); 2993 self.generics.where_clause.to_tokens(tokens); 2994 self.brace_token.surround(tokens, |tokens| { 2995 tokens.append_all(self.attrs.inner()); 2996 tokens.append_all(&self.items); 2997 }); 2998 } 2999 } 3000 3001 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3002 impl ToTokens for ItemMacro { to_tokens(&self, tokens: &mut TokenStream)3003 fn to_tokens(&self, tokens: &mut TokenStream) { 3004 tokens.append_all(self.attrs.outer()); 3005 self.mac.path.to_tokens(tokens); 3006 self.mac.bang_token.to_tokens(tokens); 3007 self.ident.to_tokens(tokens); 3008 match &self.mac.delimiter { 3009 MacroDelimiter::Paren(paren) => { 3010 paren.surround(tokens, |tokens| self.mac.tokens.to_tokens(tokens)); 3011 } 3012 MacroDelimiter::Brace(brace) => { 3013 brace.surround(tokens, |tokens| self.mac.tokens.to_tokens(tokens)); 3014 } 3015 MacroDelimiter::Bracket(bracket) => { 3016 bracket.surround(tokens, |tokens| self.mac.tokens.to_tokens(tokens)); 3017 } 3018 } 3019 self.semi_token.to_tokens(tokens); 3020 } 3021 } 3022 3023 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3024 impl ToTokens for ItemMacro2 { to_tokens(&self, tokens: &mut TokenStream)3025 fn to_tokens(&self, tokens: &mut TokenStream) { 3026 tokens.append_all(self.attrs.outer()); 3027 self.vis.to_tokens(tokens); 3028 self.macro_token.to_tokens(tokens); 3029 self.ident.to_tokens(tokens); 3030 self.rules.to_tokens(tokens); 3031 } 3032 } 3033 3034 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3035 impl ToTokens for UsePath { to_tokens(&self, tokens: &mut TokenStream)3036 fn to_tokens(&self, tokens: &mut TokenStream) { 3037 self.ident.to_tokens(tokens); 3038 self.colon2_token.to_tokens(tokens); 3039 self.tree.to_tokens(tokens); 3040 } 3041 } 3042 3043 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3044 impl ToTokens for UseName { to_tokens(&self, tokens: &mut TokenStream)3045 fn to_tokens(&self, tokens: &mut TokenStream) { 3046 self.ident.to_tokens(tokens); 3047 } 3048 } 3049 3050 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3051 impl ToTokens for UseRename { to_tokens(&self, tokens: &mut TokenStream)3052 fn to_tokens(&self, tokens: &mut TokenStream) { 3053 self.ident.to_tokens(tokens); 3054 self.as_token.to_tokens(tokens); 3055 self.rename.to_tokens(tokens); 3056 } 3057 } 3058 3059 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3060 impl ToTokens for UseGlob { to_tokens(&self, tokens: &mut TokenStream)3061 fn to_tokens(&self, tokens: &mut TokenStream) { 3062 self.star_token.to_tokens(tokens); 3063 } 3064 } 3065 3066 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3067 impl ToTokens for UseGroup { to_tokens(&self, tokens: &mut TokenStream)3068 fn to_tokens(&self, tokens: &mut TokenStream) { 3069 self.brace_token.surround(tokens, |tokens| { 3070 self.items.to_tokens(tokens); 3071 }); 3072 } 3073 } 3074 3075 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3076 impl ToTokens for TraitItemConst { to_tokens(&self, tokens: &mut TokenStream)3077 fn to_tokens(&self, tokens: &mut TokenStream) { 3078 tokens.append_all(self.attrs.outer()); 3079 self.const_token.to_tokens(tokens); 3080 self.ident.to_tokens(tokens); 3081 self.colon_token.to_tokens(tokens); 3082 self.ty.to_tokens(tokens); 3083 if let Some((eq_token, default)) = &self.default { 3084 eq_token.to_tokens(tokens); 3085 default.to_tokens(tokens); 3086 } 3087 self.semi_token.to_tokens(tokens); 3088 } 3089 } 3090 3091 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3092 impl ToTokens for TraitItemMethod { to_tokens(&self, tokens: &mut TokenStream)3093 fn to_tokens(&self, tokens: &mut TokenStream) { 3094 tokens.append_all(self.attrs.outer()); 3095 self.sig.to_tokens(tokens); 3096 match &self.default { 3097 Some(block) => { 3098 block.brace_token.surround(tokens, |tokens| { 3099 tokens.append_all(self.attrs.inner()); 3100 tokens.append_all(&block.stmts); 3101 }); 3102 } 3103 None => { 3104 TokensOrDefault(&self.semi_token).to_tokens(tokens); 3105 } 3106 } 3107 } 3108 } 3109 3110 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3111 impl ToTokens for TraitItemType { to_tokens(&self, tokens: &mut TokenStream)3112 fn to_tokens(&self, tokens: &mut TokenStream) { 3113 tokens.append_all(self.attrs.outer()); 3114 self.type_token.to_tokens(tokens); 3115 self.ident.to_tokens(tokens); 3116 self.generics.to_tokens(tokens); 3117 if !self.bounds.is_empty() { 3118 TokensOrDefault(&self.colon_token).to_tokens(tokens); 3119 self.bounds.to_tokens(tokens); 3120 } 3121 if let Some((eq_token, default)) = &self.default { 3122 eq_token.to_tokens(tokens); 3123 default.to_tokens(tokens); 3124 } 3125 self.generics.where_clause.to_tokens(tokens); 3126 self.semi_token.to_tokens(tokens); 3127 } 3128 } 3129 3130 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3131 impl ToTokens for TraitItemMacro { to_tokens(&self, tokens: &mut TokenStream)3132 fn to_tokens(&self, tokens: &mut TokenStream) { 3133 tokens.append_all(self.attrs.outer()); 3134 self.mac.to_tokens(tokens); 3135 self.semi_token.to_tokens(tokens); 3136 } 3137 } 3138 3139 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3140 impl ToTokens for ImplItemConst { to_tokens(&self, tokens: &mut TokenStream)3141 fn to_tokens(&self, tokens: &mut TokenStream) { 3142 tokens.append_all(self.attrs.outer()); 3143 self.vis.to_tokens(tokens); 3144 self.defaultness.to_tokens(tokens); 3145 self.const_token.to_tokens(tokens); 3146 self.ident.to_tokens(tokens); 3147 self.colon_token.to_tokens(tokens); 3148 self.ty.to_tokens(tokens); 3149 self.eq_token.to_tokens(tokens); 3150 self.expr.to_tokens(tokens); 3151 self.semi_token.to_tokens(tokens); 3152 } 3153 } 3154 3155 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3156 impl ToTokens for ImplItemMethod { to_tokens(&self, tokens: &mut TokenStream)3157 fn to_tokens(&self, tokens: &mut TokenStream) { 3158 tokens.append_all(self.attrs.outer()); 3159 self.vis.to_tokens(tokens); 3160 self.defaultness.to_tokens(tokens); 3161 self.sig.to_tokens(tokens); 3162 if self.block.stmts.len() == 1 { 3163 if let Stmt::Item(Item::Verbatim(verbatim)) = &self.block.stmts[0] { 3164 if verbatim.to_string() == ";" { 3165 verbatim.to_tokens(tokens); 3166 return; 3167 } 3168 } 3169 } 3170 self.block.brace_token.surround(tokens, |tokens| { 3171 tokens.append_all(self.attrs.inner()); 3172 tokens.append_all(&self.block.stmts); 3173 }); 3174 } 3175 } 3176 3177 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3178 impl ToTokens for ImplItemType { to_tokens(&self, tokens: &mut TokenStream)3179 fn to_tokens(&self, tokens: &mut TokenStream) { 3180 tokens.append_all(self.attrs.outer()); 3181 self.vis.to_tokens(tokens); 3182 self.defaultness.to_tokens(tokens); 3183 self.type_token.to_tokens(tokens); 3184 self.ident.to_tokens(tokens); 3185 self.generics.to_tokens(tokens); 3186 self.eq_token.to_tokens(tokens); 3187 self.ty.to_tokens(tokens); 3188 self.generics.where_clause.to_tokens(tokens); 3189 self.semi_token.to_tokens(tokens); 3190 } 3191 } 3192 3193 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3194 impl ToTokens for ImplItemMacro { to_tokens(&self, tokens: &mut TokenStream)3195 fn to_tokens(&self, tokens: &mut TokenStream) { 3196 tokens.append_all(self.attrs.outer()); 3197 self.mac.to_tokens(tokens); 3198 self.semi_token.to_tokens(tokens); 3199 } 3200 } 3201 3202 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3203 impl ToTokens for ForeignItemFn { to_tokens(&self, tokens: &mut TokenStream)3204 fn to_tokens(&self, tokens: &mut TokenStream) { 3205 tokens.append_all(self.attrs.outer()); 3206 self.vis.to_tokens(tokens); 3207 self.sig.to_tokens(tokens); 3208 self.semi_token.to_tokens(tokens); 3209 } 3210 } 3211 3212 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3213 impl ToTokens for ForeignItemStatic { to_tokens(&self, tokens: &mut TokenStream)3214 fn to_tokens(&self, tokens: &mut TokenStream) { 3215 tokens.append_all(self.attrs.outer()); 3216 self.vis.to_tokens(tokens); 3217 self.static_token.to_tokens(tokens); 3218 self.mutability.to_tokens(tokens); 3219 self.ident.to_tokens(tokens); 3220 self.colon_token.to_tokens(tokens); 3221 self.ty.to_tokens(tokens); 3222 self.semi_token.to_tokens(tokens); 3223 } 3224 } 3225 3226 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3227 impl ToTokens for ForeignItemType { to_tokens(&self, tokens: &mut TokenStream)3228 fn to_tokens(&self, tokens: &mut TokenStream) { 3229 tokens.append_all(self.attrs.outer()); 3230 self.vis.to_tokens(tokens); 3231 self.type_token.to_tokens(tokens); 3232 self.ident.to_tokens(tokens); 3233 self.semi_token.to_tokens(tokens); 3234 } 3235 } 3236 3237 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3238 impl ToTokens for ForeignItemMacro { to_tokens(&self, tokens: &mut TokenStream)3239 fn to_tokens(&self, tokens: &mut TokenStream) { 3240 tokens.append_all(self.attrs.outer()); 3241 self.mac.to_tokens(tokens); 3242 self.semi_token.to_tokens(tokens); 3243 } 3244 } 3245 maybe_variadic_to_tokens(arg: &FnArg, tokens: &mut TokenStream) -> bool3246 fn maybe_variadic_to_tokens(arg: &FnArg, tokens: &mut TokenStream) -> bool { 3247 let arg = match arg { 3248 FnArg::Typed(arg) => arg, 3249 FnArg::Receiver(receiver) => { 3250 receiver.to_tokens(tokens); 3251 return false; 3252 } 3253 }; 3254 3255 match arg.ty.as_ref() { 3256 Type::Verbatim(ty) if ty.to_string() == "..." => { 3257 match arg.pat.as_ref() { 3258 Pat::Verbatim(pat) if pat.to_string() == "..." => { 3259 tokens.append_all(arg.attrs.outer()); 3260 pat.to_tokens(tokens); 3261 } 3262 _ => arg.to_tokens(tokens), 3263 } 3264 true 3265 } 3266 _ => { 3267 arg.to_tokens(tokens); 3268 false 3269 } 3270 } 3271 } 3272 3273 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3274 impl ToTokens for Signature { to_tokens(&self, tokens: &mut TokenStream)3275 fn to_tokens(&self, tokens: &mut TokenStream) { 3276 self.constness.to_tokens(tokens); 3277 self.asyncness.to_tokens(tokens); 3278 self.unsafety.to_tokens(tokens); 3279 self.abi.to_tokens(tokens); 3280 self.fn_token.to_tokens(tokens); 3281 self.ident.to_tokens(tokens); 3282 self.generics.to_tokens(tokens); 3283 self.paren_token.surround(tokens, |tokens| { 3284 let mut last_is_variadic = false; 3285 for pair in self.inputs.pairs() { 3286 last_is_variadic = maybe_variadic_to_tokens(pair.value(), tokens); 3287 pair.punct().to_tokens(tokens); 3288 } 3289 if self.variadic.is_some() && !last_is_variadic { 3290 if !self.inputs.empty_or_trailing() { 3291 <Token![,]>::default().to_tokens(tokens); 3292 } 3293 self.variadic.to_tokens(tokens); 3294 } 3295 }); 3296 self.output.to_tokens(tokens); 3297 self.generics.where_clause.to_tokens(tokens); 3298 } 3299 } 3300 3301 #[cfg_attr(doc_cfg, doc(cfg(feature = "printing")))] 3302 impl ToTokens for Receiver { to_tokens(&self, tokens: &mut TokenStream)3303 fn to_tokens(&self, tokens: &mut TokenStream) { 3304 tokens.append_all(self.attrs.outer()); 3305 if let Some((ampersand, lifetime)) = &self.reference { 3306 ampersand.to_tokens(tokens); 3307 lifetime.to_tokens(tokens); 3308 } 3309 self.mutability.to_tokens(tokens); 3310 self.self_token.to_tokens(tokens); 3311 } 3312 } 3313 } 3314