diff --git a/serde_derive/src/de.rs b/serde_derive/src/de.rs index e6ff6c95..dc7410f3 100644 --- a/serde_derive/src/de.rs +++ b/serde_derive/src/de.rs @@ -357,7 +357,10 @@ fn deserialize_transparent(cont: &Container, params: &Parameters) -> Fragment { let path = match transparent_field.attrs.deserialize_with() { Some(path) => quote!(#path), - None => quote!(_serde::Deserialize::deserialize), + None => { + let span = transparent_field.original.span(); + quote_spanned!(span=> _serde::Deserialize::deserialize) + }, }; let assign = fields.iter().map(|field| { @@ -797,8 +800,10 @@ fn deserialize_newtype_struct( let value = match field.attrs.deserialize_with() { None => { + let span = field.original.span(); + let func = quote_spanned!(span=> <#field_ty as _serde::Deserialize>::deserialize); quote! { - try!(<#field_ty as _serde::Deserialize>::deserialize(__e)) + try!(#func(__e)) } } Some(path) => { @@ -1803,10 +1808,10 @@ fn deserialize_externally_tagged_newtype_variant( match field.attrs.deserialize_with() { None => { let field_ty = field.ty; + let span = field.original.span(); + let func = quote_spanned!(span=> _serde::de::VariantAccess::newtype_variant::<#field_ty>); quote_expr! { - _serde::export::Result::map( - _serde::de::VariantAccess::newtype_variant::<#field_ty>(__variant), - #this::#variant_ident) + _serde::export::Result::map(#func(__variant), #this::#variant_ident) } } Some(path) => { @@ -1831,10 +1836,10 @@ fn deserialize_untagged_newtype_variant( let field_ty = field.ty; match field.attrs.deserialize_with() { None => { + let span = field.original.span(); + let func = quote_spanned!(span=> <#field_ty as _serde::Deserialize>::deserialize); quote_expr! { - _serde::export::Result::map( - <#field_ty as _serde::Deserialize>::deserialize(#deserializer), - #this::#variant_ident) + _serde::export::Result::map(#func(#deserializer), #this::#variant_ident) } } Some(path) => { @@ -2441,7 +2446,10 @@ fn deserialize_map( .map(|&(field, ref name)| { let field_ty = field.ty; let func = match field.attrs.deserialize_with() { - None => quote!(_serde::de::Deserialize::deserialize), + None => { + let span = field.original.span(); + quote_spanned!(span=> _serde::de::Deserialize::deserialize) + }, Some(path) => quote!(#path), }; quote! { @@ -2793,7 +2801,9 @@ fn wrap_deserialize_variant_with( fn expr_is_missing(field: &Field, cattrs: &attr::Container) -> Fragment { match *field.attrs.default() { attr::Default::Default => { - return quote_expr!(_serde::export::Default::default()); + let span = field.original.span(); + let func = quote_spanned!(span=> _serde::export::Default::default); + return quote_expr!(#func()); } attr::Default::Path(ref path) => { return quote_expr!(#path()); diff --git a/serde_derive/src/lib.rs b/serde_derive/src/lib.rs index 40f99201..c05a0497 100644 --- a/serde_derive/src/lib.rs +++ b/serde_derive/src/lib.rs @@ -62,6 +62,7 @@ mod internals; use proc_macro::TokenStream; use syn::DeriveInput; +use syn::spanned::Spanned; #[macro_use] mod bound; @@ -77,7 +78,7 @@ mod try; pub fn derive_serialize(input: TokenStream) -> TokenStream { let input = parse_macro_input!(input as DeriveInput); ser::expand_derive_serialize(&input) - .unwrap_or_else(compile_error) + .unwrap_or_else(|message| compile_error(input.span(), message)) .into() } @@ -85,12 +86,12 @@ pub fn derive_serialize(input: TokenStream) -> TokenStream { pub fn derive_deserialize(input: TokenStream) -> TokenStream { let input = parse_macro_input!(input as DeriveInput); de::expand_derive_deserialize(&input) - .unwrap_or_else(compile_error) + .unwrap_or_else(|message| compile_error(input.span(), message)) .into() } -fn compile_error(message: String) -> proc_macro2::TokenStream { - quote! { +fn compile_error(span: proc_macro2::Span, message: String) -> proc_macro2::TokenStream { + quote_spanned! {span=> compile_error!(#message); } } diff --git a/serde_derive/src/ser.rs b/serde_derive/src/ser.rs index 5afba924..94d5555f 100644 --- a/serde_derive/src/ser.rs +++ b/serde_derive/src/ser.rs @@ -200,7 +200,10 @@ fn serialize_transparent(cont: &Container, params: &Parameters) -> Fragment { let path = match transparent_field.attrs.serialize_with() { Some(path) => quote!(#path), - None => quote!(_serde::Serialize::serialize), + None => { + let span = transparent_field.original.span(); + quote_spanned!(span=> _serde::Serialize::serialize) + }, }; quote_block! { @@ -505,8 +508,10 @@ fn serialize_externally_tagged_variant( field_expr = wrap_serialize_field_with(params, field.ty, path, &field_expr); } + let span = field.original.span(); + let func = quote_spanned!(span=> _serde::Serializer::serialize_newtype_variant); quote_expr! { - _serde::Serializer::serialize_newtype_variant( + #func( __serializer, #type_name, #variant_index, @@ -579,8 +584,10 @@ fn serialize_internally_tagged_variant( field_expr = wrap_serialize_field_with(params, field.ty, path, &field_expr); } + let span = field.original.span(); + let func = quote_spanned!(span=> _serde::private::ser::serialize_tagged_newtype); quote_expr! { - _serde::private::ser::serialize_tagged_newtype( + #func( __serializer, #enum_ident_str, #variant_ident_str, @@ -637,12 +644,14 @@ fn serialize_adjacently_tagged_variant( field_expr = wrap_serialize_field_with(params, field.ty, path, &field_expr); } + let span = field.original.span(); + let func = quote_spanned!(span=> _serde::ser::SerializeStruct::serialize_field); return quote_block! { let mut __struct = try!(_serde::Serializer::serialize_struct( __serializer, #type_name, 2)); try!(_serde::ser::SerializeStruct::serialize_field( &mut __struct, #tag, #variant_name)); - try!(_serde::ser::SerializeStruct::serialize_field( + try!(#func( &mut __struct, #content, #field_expr)); _serde::ser::SerializeStruct::end(__struct) }; @@ -738,8 +747,10 @@ fn serialize_untagged_variant( field_expr = wrap_serialize_field_with(params, field.ty, path, &field_expr); } + let span = field.original.span(); + let func = quote_spanned!(span=> _serde::Serialize::serialize); quote_expr! { - _serde::Serialize::serialize(#field_expr, __serializer) + #func(#field_expr, __serializer) } } Style::Tuple => serialize_tuple_variant(TupleVariant::Untagged, params, &variant.fields), @@ -1079,8 +1090,9 @@ fn serialize_struct_visitor( let span = field.original.span(); let ser = if field.attrs.flatten() { + let func = quote_spanned!(span=> _serde::Serialize::serialize); quote! { - try!(_serde::Serialize::serialize(&#field_expr, _serde::private::ser::FlatMapSerializer(&mut __serde_state))); + try!(#func(&#field_expr, _serde::private::ser::FlatMapSerializer(&mut __serde_state))); } } else { let func = struct_trait.serialize_field(span);