desugars operator overloading
saturating
bendn 12 months ago
parent 3e4e0c9 · commit 47ddf5f
-rw-r--r--Cargo.toml2
-rw-r--r--src/lib.rs38
2 files changed, 37 insertions, 3 deletions
diff --git a/Cargo.toml b/Cargo.toml
index f372dc9..833de4f 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -1,6 +1,6 @@
[package]
name = "lower-macros"
-version = "0.2.4"
+version = "0.2.6"
authors = ["bend-n <[email protected]>"]
description = "desugar math where the compiler wont"
edition = "2021"
diff --git a/src/lib.rs b/src/lib.rs
index 9b184e2..68676bf 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -85,6 +85,31 @@ impl Sub for Wrapping {
}
}
+struct Saturating;
+impl Sub for Saturating {
+ fn sub_bin(&self, op: BinOp, left: TokenStream, right: TokenStream) -> TokenStream {
+ use syn::BinOp::*;
+ match op {
+ Add(_) => quote!((#left).saturating_add(#right)),
+ Sub(_) => quote!((#left).saturating_sub(#right)),
+ Mul(_) => quote!((#left).saturating_mul(#right)),
+ Div(_) => quote!((#left).saturating_div(#right)),
+ Rem(_) => quote!((#left).saturating_rem(#right)),
+ Shl(_) => quote!((#left).saturating_shl(#right)),
+ Shr(_) => quote!((#left).saturating_shr(#right)),
+
+ _ => quote!((#left) #op (#right)),
+ }
+ }
+
+ fn sub_unop(&self, op: UnOp, x: TokenStream) -> TokenStream {
+ match op {
+ UnOp::Neg(_) => quote!((#x).saturating_neg()),
+ _ => quote!(#op #x),
+ }
+ }
+}
+
struct Algebraic;
impl Sub for Algebraic {
fn sub_bin(&self, op: BinOp, left: TokenStream, right: TokenStream) -> TokenStream {
@@ -163,7 +188,7 @@ fn walk(sub: &impl Sub, e: Expr) -> TokenStream {
..
}) => {
let body = walk(*body);
- quote!(#lifetimes #constness #movability #asyncness #capture |#inputs| #output #body)
+ quote!(#lifetimes #constness #movability #asyncness #capture |#inputs| #output { #body })
}
Expr::ForLoop(ExprForLoop {
label,
@@ -455,6 +480,11 @@ pub fn wrapping(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
walk!(input, Wrapping {})
}
+#[proc_macro]
+pub fn saturating(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
+ walk!(input, Saturating {})
+}
+
#[proc_macro_attribute]
pub fn apply(
args: proc_macro::TokenStream,
@@ -465,6 +495,10 @@ pub fn apply(
"fast" => fast(input),
"algebraic" => algebraic(input),
"wrapping" => wrapping(input),
- _ => quote! { compile_error!("type must be {fast, basic, algebraic, wrapping}") }.into(),
+ "saturating" => saturating(input),
+ _ => {
+ quote! { compile_error!("type must be {fast, basic, algebraic, wrapping, saturating}") }
+ .into()
+ }
}
}