Skip to content

Commit

Permalink
refactor: use node util to handle bigint.
Browse files Browse the repository at this point in the history
  • Loading branch information
7086cmd committed Oct 2, 2024
1 parent 34f3e74 commit bfe1858
Showing 1 changed file with 23 additions and 38 deletions.
61 changes: 23 additions & 38 deletions crates/oxc_minifier/src/ast_passes/peephole_fold_constants.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use std::cmp::Ordering;
use std::ops::Neg;
use std::str::FromStr;

use num_bigint::BigInt;
use oxc_ast::ast::*;
Expand Down Expand Up @@ -188,22 +187,17 @@ impl<'a> PeepholeFoldConstants {
_ => None,
},
UnaryOperator::BitwiseNot => match &mut expr.argument {
Expression::BigIntLiteral(n) => n
.base
.is_base_10()
.then(|| {
// Use `unwrap`, because we know it's a valid BigInt literal, which ends with 'n'.
let value = BigInt::from_str(n.raw.as_str().strip_suffix('n').unwrap());
value.ok().map(|value| {
let value = !value;
ctx.ast.expression_big_int_literal(
SPAN,
value.to_string() + "n",
BigintBase::Decimal,
)
})
Expression::BigIntLiteral(n) => {
let value = ctx.get_string_bigint_value(n.raw.as_str().trim_end_matches('n'));
value.map(|value| {
let value = !value;
ctx.ast.expression_big_int_literal(
SPAN,
value.to_string() + "n",
BigintBase::Decimal,
)
})
.unwrap_or(None),
}
Expression::NumericLiteral(n) => is_within_i32_range(n.value).then(|| {
let value = !n.value.to_js_int_32();
ctx.ast.expression_numeric_literal(
Expand All @@ -222,25 +216,17 @@ impl<'a> PeepholeFoldConstants {
UnaryOperator::UnaryNegation if un.argument.is_big_int_literal() => {
// `~-1n` -> `0n`
if let Expression::BigIntLiteral(n) = &mut un.argument {
n.base
.is_base_10()
.then(|| {
// The value is a valid BigInt literal, which ends with 'n'.
let value = BigInt::from_str(
n.raw.as_str().strip_suffix('n').unwrap(),
);
value
.ok()
.and_then(|value| value.checked_sub(&BigInt::from(1)))
.map(|value| {
ctx.ast.expression_big_int_literal(
SPAN,
value.neg().to_string() + "n",
BigintBase::Decimal,
)
})
})
.unwrap_or(None)
let value = ctx
.get_string_bigint_value(n.raw.as_str().trim_end_matches('n'));
value.and_then(|value| value.checked_sub(&BigInt::from(1))).map(
|value| {
ctx.ast.expression_big_int_literal(
SPAN,
value.neg().to_string() + "n",
BigintBase::Decimal,
)
},
)
} else {
None
}
Expand Down Expand Up @@ -1400,9 +1386,8 @@ mod test {
test("~-1n", "0n");
test("~~1n", "1n");

// The num_bigint does not natively parse non-decimal numbers, or its format is not JS-like.
// test("~0x3n", "-4n");
// test("~0b11n", "-4n");
test("~0x3n", "-4n");
test("~0b11n", "-4n");
}

#[test]
Expand Down

0 comments on commit bfe1858

Please sign in to comment.