1use proc_macro2::{Span, TokenStream};
2use quote::{format_ident, quote};
3use syn::{Ident, Visibility};
4
5use crate::codegen::{AnonRegexArgs, RegexArgs, capture, parse};
6
7pub fn make_regex(
8 RegexArgs {
9 vis,
10 name,
11 pat,
12 flags,
13 }: RegexArgs,
14 impl_anon: bool,
15) -> TokenStream {
16 #![allow(nonstandard_style)]
17 let fmt = {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "std");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "fmt");
_s
}quote!(::std::fmt);
18 let HaystackSlice = {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "ct_regex");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "internal");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "haystack");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "HaystackSlice");
_s
}quote!(::ct_regex::internal::haystack::HaystackSlice);
19 let Regex = {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "ct_regex");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "internal");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "expr");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "Regex");
_s
}quote!(::ct_regex::internal::expr::Regex);
20 let AnonRegex = {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "ct_regex");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "internal");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "expr");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "AnonRegex");
_s
}quote!(::ct_regex::internal::expr::AnonRegex);
21
22 let mod_name = match ::quote::__private::IdentFragmentAdapter(&&name) {
arg =>
::quote::__private::mk_ident(&::alloc::__export::must_use({
::alloc::fmt::format(format_args!("__regex_{0}", arg))
}), ::quote::__private::Option::None.or(arg.span())),
}format_ident!("__regex_{}", &name);
23
24 let pat_str = pat.value();
25
26 let doc = ::alloc::__export::must_use({
::alloc::fmt::format(format_args!("A macro-generated regular expression matching the pattern: `{0}` with flags: {1}. See the [`Regex`](::ct_regex::internal::expr::Regex) trait for associated matching and capturing functions.",
pat_str, flags))
})format!(
27 "A macro-generated regular expression matching the pattern: `{pat_str}` with flags: \
28 {flags}. See the [`Regex`](::ct_regex::internal::expr::Regex) trait for associated \
29 matching and capturing functions." );
31
32 let mut config = flags.create_config();
33 config.unicode(false).utf8(false);
34
35 let (type_expr_byte, groups) = parse::parse_regex::<u8>(&pat_str, &config);
36
37 config.unicode(true).utf8(true);
38
39 let (type_expr_scalar, _) = parse::parse_regex::<char>(&pat_str, &config);
40
41 let (captures_name, captures_len, captures_impl) = capture::impl_captures(&name, groups);
42
43 let anon_impl = if impl_anon {
44 {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "impl");
::quote::ToTokens::to_tokens(&AnonRegex, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_ident(&mut _s, "u8");
::quote::__private::push_comma(&mut _s);
::quote::ToTokens::to_tokens(&captures_len, &mut _s);
::quote::__private::push_gt(&mut _s);
::quote::__private::push_ident(&mut _s, "for");
::quote::ToTokens::to_tokens(&name, &mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
::quote::__private::TokenStream::new());
::quote::__private::push_ident(&mut _s, "impl");
::quote::ToTokens::to_tokens(&AnonRegex, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_ident(&mut _s, "char");
::quote::__private::push_comma(&mut _s);
::quote::ToTokens::to_tokens(&captures_len, &mut _s);
::quote::__private::push_gt(&mut _s);
::quote::__private::push_ident(&mut _s, "for");
::quote::ToTokens::to_tokens(&name, &mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
::quote::__private::TokenStream::new());
_s
}quote! {
45 impl #AnonRegex<u8, #captures_len> for #name {}
46
47 impl #AnonRegex<char, #captures_len> for #name {}
48 }
49 } else {
50 ::quote::__private::TokenStream::new()quote!()
51 };
52
53 {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_pound(&mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Bracket,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "doc");
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Parenthesis,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "hidden");
_s
});
_s
});
::quote::__private::push_pound(&mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Bracket,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "allow");
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Parenthesis,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "non_snake_case");
_s
});
_s
});
::quote::__private::push_ident(&mut _s, "mod");
::quote::ToTokens::to_tokens(&mod_name, &mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_pound(&mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Bracket,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "doc");
::quote::__private::push_eq(&mut _s);
::quote::ToTokens::to_tokens(&doc, &mut _s);
_s
});
::quote::__private::push_ident(&mut _s, "pub");
::quote::__private::push_ident(&mut _s, "struct");
::quote::ToTokens::to_tokens(&name, &mut _s);
::quote::__private::push_semi(&mut _s);
::quote::__private::push_ident(&mut _s, "impl");
::quote::ToTokens::to_tokens(&Regex, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_ident(&mut _s, "u8");
::quote::__private::push_comma(&mut _s);
::quote::ToTokens::to_tokens(&captures_len, &mut _s);
::quote::__private::push_gt(&mut _s);
::quote::__private::push_ident(&mut _s, "for");
::quote::ToTokens::to_tokens(&name, &mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "type");
::quote::__private::push_ident(&mut _s, "Pattern");
::quote::__private::push_eq(&mut _s);
::quote::ToTokens::to_tokens(&type_expr_byte, &mut _s);
::quote::__private::push_semi(&mut _s);
::quote::__private::push_ident(&mut _s, "type");
::quote::__private::push_ident(&mut _s, "Capture");
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'a");
::quote::__private::push_comma(&mut _s);
::quote::__private::push_ident(&mut _s, "S");
::quote::__private::push_colon(&mut _s);
::quote::ToTokens::to_tokens(&HaystackSlice, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'a");
::quote::__private::push_shr(&mut _s);
::quote::__private::push_eq(&mut _s);
::quote::ToTokens::to_tokens(&captures_name, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'a");
::quote::__private::push_comma(&mut _s);
::quote::__private::push_ident(&mut _s, "S");
::quote::__private::push_gt(&mut _s);
::quote::__private::push_semi(&mut _s);
_s
});
::quote::__private::push_ident(&mut _s, "impl");
::quote::ToTokens::to_tokens(&Regex, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_ident(&mut _s, "char");
::quote::__private::push_comma(&mut _s);
::quote::ToTokens::to_tokens(&captures_len, &mut _s);
::quote::__private::push_gt(&mut _s);
::quote::__private::push_ident(&mut _s, "for");
::quote::ToTokens::to_tokens(&name, &mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "type");
::quote::__private::push_ident(&mut _s, "Pattern");
::quote::__private::push_eq(&mut _s);
::quote::ToTokens::to_tokens(&type_expr_scalar, &mut _s);
::quote::__private::push_semi(&mut _s);
::quote::__private::push_ident(&mut _s, "type");
::quote::__private::push_ident(&mut _s, "Capture");
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'a");
::quote::__private::push_comma(&mut _s);
::quote::__private::push_ident(&mut _s, "S");
::quote::__private::push_colon(&mut _s);
::quote::ToTokens::to_tokens(&HaystackSlice, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'a");
::quote::__private::push_shr(&mut _s);
::quote::__private::push_eq(&mut _s);
::quote::ToTokens::to_tokens(&captures_name, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'a");
::quote::__private::push_comma(&mut _s);
::quote::__private::push_ident(&mut _s, "S");
::quote::__private::push_gt(&mut _s);
::quote::__private::push_semi(&mut _s);
_s
});
::quote::ToTokens::to_tokens(&anon_impl, &mut _s);
::quote::__private::push_ident(&mut _s, "impl");
::quote::ToTokens::to_tokens(&fmt, &mut _s);
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "Debug");
::quote::__private::push_ident(&mut _s, "for");
::quote::ToTokens::to_tokens(&name, &mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "fn");
::quote::__private::push_ident(&mut _s, "fmt");
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Parenthesis,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_and(&mut _s);
::quote::__private::push_ident(&mut _s, "self");
::quote::__private::push_comma(&mut _s);
::quote::__private::push_ident(&mut _s, "f");
::quote::__private::push_colon(&mut _s);
::quote::__private::push_and(&mut _s);
::quote::__private::push_ident(&mut _s, "mut");
::quote::ToTokens::to_tokens(&fmt, &mut _s);
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "Formatter");
::quote::__private::push_lt(&mut _s);
::quote::__private::push_lifetime(&mut _s, "\'_");
::quote::__private::push_gt(&mut _s);
_s
});
::quote::__private::push_rarrow(&mut _s);
::quote::ToTokens::to_tokens(&fmt, &mut _s);
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "Result");
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "write");
::quote::__private::push_bang(&mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Parenthesis,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "f");
::quote::__private::push_comma(&mut _s);
::quote::__private::parse(&mut _s, "\"/{:?}/\"");
::quote::__private::push_comma(&mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_ident(&mut _s, "Self");
::quote::__private::push_ident(&mut _s, "as");
::quote::ToTokens::to_tokens(&Regex, &mut _s);
::quote::__private::push_lt(&mut _s);
::quote::__private::push_ident(&mut _s, "char");
::quote::__private::push_comma(&mut _s);
::quote::ToTokens::to_tokens(&captures_len, &mut _s);
::quote::__private::push_shr(&mut _s);
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "Pattern");
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_ident(&mut _s, "default");
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Parenthesis,
::quote::__private::TokenStream::new());
_s
});
_s
});
_s
});
::quote::ToTokens::to_tokens(&captures_impl, &mut _s);
_s
});
::quote::__private::push_pound(&mut _s);
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Bracket,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "doc");
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Parenthesis,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_ident(&mut _s, "inline");
_s
});
_s
});
::quote::ToTokens::to_tokens(&vis, &mut _s);
::quote::__private::push_ident(&mut _s, "use");
::quote::ToTokens::to_tokens(&mod_name, &mut _s);
::quote::__private::push_colon2(&mut _s);
::quote::__private::push_star(&mut _s);
::quote::__private::push_semi(&mut _s);
_s
}quote! {
54 #[doc(hidden)]
55 #[allow(non_snake_case)]
56 mod #mod_name {
57 #[doc = #doc]
58 pub struct #name;
59
60 impl #Regex<u8, #captures_len> for #name {
61 type Pattern = #type_expr_byte;
62
63 type Capture<'a, S: #HaystackSlice<'a>> = #captures_name<'a, S>;
64 }
65
66 impl #Regex<char, #captures_len> for #name {
67 type Pattern = #type_expr_scalar;
68 type Capture<'a, S: #HaystackSlice<'a>> = #captures_name<'a, S>;
69 }
70
71 #anon_impl
72
73 impl #fmt::Debug for #name {
74 fn fmt(&self, f: &mut #fmt::Formatter<'_>) -> #fmt::Result {
75 write!(f, "/{:?}/", <Self as #Regex<char, #captures_len>>::Pattern::default())
76 }
77 }
78
79 #captures_impl
80 }
81
82 #[doc(inline)]
83 #vis use #mod_name::*;
84 }
85}
86
87pub fn make_anon_regex(AnonRegexArgs { pat, flags }: AnonRegexArgs) -> TokenStream {
88 let impl_tokens = make_regex(
89 RegexArgs {
90 vis: Visibility::Inherited,
91 name: Ident::new("__AnonRegex", Span::call_site()),
92 pat,
93 flags,
94 },
95 true,
96 );
97 {
let mut _s = ::quote::__private::TokenStream::new();
::quote::__private::push_group(&mut _s,
::quote::__private::Delimiter::Brace,
{
let mut _s = ::quote::__private::TokenStream::new();
::quote::ToTokens::to_tokens(&impl_tokens, &mut _s);
::quote::__private::push_ident(&mut _s, "__AnonRegex");
_s
});
_s
}quote! {
98 {
99 #impl_tokens
100
101 __AnonRegex
102 }
103 }
104}