diff --git a/.vscode/tasks.json b/.vscode/tasks.json index cc7543bd1285545d68ee100b9d7f207b74e6d3c0..51e1bacbaae588938d0589c503cf8fadb74945a6 100644 --- a/.vscode/tasks.json +++ b/.vscode/tasks.json @@ -50,6 +50,18 @@ "kind": "build", "isDefault": true } - } + }, + { + "type": "shell", + "label": "cargo run --example app", + "command": "cargo run --example app", + "problemMatcher": [ + "$rustc" + ], + "group": { + "kind": "build", + "isDefault": true + } + }, ] } \ No newline at end of file diff --git a/examples/app.rs b/examples/app.rs new file mode 100644 index 0000000000000000000000000000000000000000..a5690dd36e35597a57a57eef48859908c4d5e310 --- /dev/null +++ b/examples/app.rs @@ -0,0 +1,12 @@ +#![feature(proc_macro)] + +extern crate parsetest; +use parsetest::app; + +app!{ + id1, id2 +} + +fn main() { + println!("here"); +} diff --git a/src/lib.rs b/src/lib.rs index e59aaf4ccc80cceb5ff6a7e9a5d8efe69b877326..b8d51aa7afede22323ad11a2f250264dc3d5f355 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -9,7 +9,7 @@ extern crate syn; use proc_macro::TokenStream; use syn::spanned::Spanned; use syn::synom::Synom; -use syn::LitInt; +use syn::{Ident, LitInt}; use quote::ToTokens; use std::convert::From; @@ -24,7 +24,10 @@ pub fn lit(input: TokenStream) -> TokenStream { if !(10 <= value && value < 100) { v.span() .unstable() - .error(format!("expected literal 10 <= x < 100, got {}", value,)) + .error(format!( + "expected literal 10 <= x < 100, got {}", + value, + )) .emit(); } From::from(v.into_tokens()) @@ -40,7 +43,10 @@ pub fn lite(input: TokenStream) -> TokenStream { if !(10 <= value && value < 100) { v.span() .unstable() - .error(format!("expected literal 10 <= x < 100, got {}", value,)) + .error(format!( + "expected literal 10 <= x < 100, got {}", + value, + )) .emit(); } From::from(v.into_tokens()) @@ -55,6 +61,89 @@ pub fn lite(input: TokenStream) -> TokenStream { } } +use syn::Path; + +enum AppKeys { + Device, + Resources, + Interrupts, + Tasks, + Idle, + Init, +} + +fn to_app_keys(id: Ident) -> Option<AppKeys> { + match id.as_ref() { + "device" => Some(AppKeys::Device), + _ => None, + } +} + +// struct KeyVal { + +// } + +// impl Synom for KeyVal { +// named!(parse -> Self, do_parse!( +// val: syn!(Punctuadet) >> (KeyVal { }) + +// field: syn!(Ident) >> +// _colon: punct!(:) >> +// + switch!(value!(field.as_ref()), +// "path" => map!(syn!(Path), |path| { +// + parsed_init.path = Some(path); +// + }) | +// + "resources" => map!(parse_resource_ident, |res| { +// + parsed_init.resources = Some(res); +// + }) | +// + _ => call!(|_| { +// + field.span.unstable().error(format!("Unknown field `{}`", field)).emit(); +// + panic!("Unknown field `{}`", field); +// + }) +// + ) >> +// + _comma: syn!(Token![,]) >> +// + (()) +// )); +// } + +use syn::punctuated::Punctuated; +struct AppK {} + +struct KeyVal { + kv: Punctuated<Ident, Token![,]>, +} + +impl Synom for KeyVal { + named!(parse -> Self, do_parse!( + kv: call!(Punctuated::parse_terminated_nonempty) >> + (KeyVal { kv }) + )); +} + +#[proc_macro] +pub fn app(input: TokenStream) -> TokenStream { + println!("-- app --"); + let k: KeyVal = syn::parse(input).unwrap(); + for k in k.kv.into_iter() { + println!("{:?}", k.as_ref()); + } + // { + // Ok(app) => { + // let tokens = quote!(); + // tokens.into() + // } + // Err(err) => { + // let desc = err.description(); + // let tokens = quote! { + // compile_error!(#desc) + // }; + // tokens.into() + // } + // } + let tokens = quote!(); + tokens.into() +} + // named!(parse -> LitInt, do_parse!( // val: syn!(LitInt) >> (val) // )); @@ -85,30 +174,33 @@ pub fn lite(input: TokenStream) -> TokenStream { // } // } -/// MyLit -struct MyLit { - val: LitInt, -} +// /// MyLit +// struct MyLit { +// val: LitInt, +// } -impl Synom for MyLit { - named!(parse -> Self, do_parse!( - val: syn!(LitInt) >> (MyLit { val }) - )); -} +// impl Synom for MyLit { +// named!(parse -> Self, do_parse!( +// val: syn!(LitInt) >> (MyLit { val }) +// )); +// } -#[proc_macro] -pub fn mylit(input: TokenStream) -> TokenStream { - let v: MyLit = syn::parse(input).unwrap(); - let value = v.val.value(); - if !(10 <= value && value < 100) { - v.val - .span() - .unstable() - .error(format!("expected literal 10 <= x < 100, got {}", value,)) - .emit(); - } - From::from(v.val.into_tokens()) -} +// #[proc_macro] +// pub fn mylit(input: TokenStream) -> TokenStream { +// let v: MyLit = syn::parse(input).unwrap(); +// let value = v.val.value(); +// if !(10 <= value && value < 100) { +// v.val +// .span() +// .unstable() +// .error(format!( +// "expected literal 10 <= x < 100, got {}", +// value, +// )) +// .emit(); +// } +// From::from(v.val.into_tokens()) +// } // /// MyLitP // struct MyLitP {