forge_lint/sol/gas/
keccak.rs

1use super::AsmKeccak256;
2use crate::{
3    declare_forge_lint,
4    linter::EarlyLintPass,
5    sol::{Severity, SolLint},
6};
7use solar_ast::{CallArgsKind, Expr, ExprKind};
8use solar_interface::kw;
9
10declare_forge_lint!(
11    ASM_KECCAK256,
12    Severity::Gas,
13    "asm-keccak256",
14    "hash using inline assembly to save gas"
15);
16
17impl<'ast> EarlyLintPass<'ast> for AsmKeccak256 {
18    fn check_expr(&mut self, ctx: &crate::linter::LintContext<'_>, expr: &'ast Expr<'ast>) {
19        if let ExprKind::Call(expr, args) = &expr.kind {
20            if let ExprKind::Ident(ident) = &expr.kind {
21                if ident.name == kw::Keccak256 {
22                    // Do not flag when hashing a single literal, as the compiler should optimize it
23                    if let CallArgsKind::Unnamed(ref exprs) = args.kind {
24                        if exprs.len() == 1 {
25                            if let ExprKind::Lit(_, _) = exprs[0].kind {
26                                return;
27                            }
28                        }
29                    }
30                    ctx.emit(&ASM_KECCAK256, expr.span);
31                }
32            }
33        }
34    }
35}