fix(multicall): resolve critical multicall parsing corruption issues

- Added comprehensive bounds checking to prevent buffer overruns in multicall parsing
- Implemented graduated validation system (Strict/Moderate/Permissive) to reduce false positives
- Added LRU caching system for address validation with 10-minute TTL
- Enhanced ABI decoder with missing Universal Router and Arbitrum-specific DEX signatures
- Fixed duplicate function declarations and import conflicts across multiple files
- Added error recovery mechanisms with multiple fallback strategies
- Updated tests to handle new validation behavior for suspicious addresses
- Fixed parser test expectations for improved validation system
- Applied gofmt formatting fixes to ensure code style compliance
- Fixed mutex copying issues in monitoring package by introducing MetricsSnapshot
- Resolved critical security vulnerabilities in heuristic address extraction
- Progress: Updated TODO audit from 10% to 35% complete

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Krypto Kajun
2025-10-17 00:12:55 -05:00
parent f358f49aa9
commit 850223a953
8621 changed files with 79808 additions and 7340 deletions

View File

@@ -2,12 +2,15 @@ package mev
import (
"context"
"math"
"math/big"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/ethclient"
"github.com/fraktal/mev-beta/internal/logger"
"github.com/fraktal/mev-beta/pkg/math"
mathpkg "github.com/fraktal/mev-beta/pkg/math"
"github.com/fraktal/mev-beta/pkg/security"
)
// MEVOpportunity represents a potential MEV opportunity
@@ -45,10 +48,10 @@ type CompetitionAnalysis struct {
type CompetitionAnalyzer struct {
client *ethclient.Client
logger *logger.Logger
decimalConverter *math.DecimalConverter
decimalConverter *mathpkg.DecimalConverter
competitorData map[common.Address]*CompetitorProfile
gasHistory []GasDataPoint
profitThresholds map[string]*math.UniversalDecimal
profitThresholds map[string]*mathpkg.UniversalDecimal
config CompetitionConfig
}
@@ -76,8 +79,8 @@ type CompetitionConfig struct {
BaseGasMultiplier float64
MaxGasMultiplier float64
GasHistorySize int
CompetitorThreshold *math.UniversalDecimal
MaxOpportunitySize *math.UniversalDecimal
CompetitorThreshold *mathpkg.UniversalDecimal
MaxOpportunitySize *mathpkg.UniversalDecimal
}
// NewCompetitionAnalyzer creates a new competition analyzer
@@ -85,10 +88,10 @@ func NewCompetitionAnalyzer(client *ethclient.Client, logger *logger.Logger) *Co
analyzer := &CompetitionAnalyzer{
client: client,
logger: logger,
decimalConverter: math.NewDecimalConverter(),
decimalConverter: mathpkg.NewDecimalConverter(),
competitorData: make(map[common.Address]*CompetitorProfile),
gasHistory: make([]GasDataPoint, 0),
profitThresholds: make(map[string]*math.UniversalDecimal),
profitThresholds: make(map[string]*mathpkg.UniversalDecimal),
}
analyzer.config = CompetitionConfig{
@@ -141,7 +144,14 @@ func (analyzer *CompetitionAnalyzer) AnalyzeCompetition(ctx context.Context, opp
successProbability := analyzer.estimateSuccessProbability(opportunity, competitionFactor)
// Calculate net profit after gas costs
gasCost := new(big.Int).Mul(big.NewInt(int64(opportunity.RequiredGas)), adjustedGasPrice)
// Calculate net profit after gas costs
requiredGasInt64, err := security.SafeUint64ToInt64(opportunity.RequiredGas)
if err != nil {
analyzer.logger.Error("Required gas exceeds int64 maximum", "requiredGas", opportunity.RequiredGas, "error", err)
// Use maximum safe value as fallback
requiredGasInt64 = math.MaxInt64
}
gasCost := new(big.Int).Mul(big.NewInt(requiredGasInt64), adjustedGasPrice)
netProfit := new(big.Int).Sub(opportunity.EstimatedProfit, gasCost)
// Create competition data
@@ -170,13 +180,21 @@ func (analyzer *CompetitionAnalyzer) CalculateOptimalBid(ctx context.Context, op
// Start with the suggested gas price from competition analysis
baseGasPrice := competition.SuggestedGasPrice
// Calculate base strategy
// Calculate base strategy with safe gas conversion
requiredGasInt64, err := security.SafeUint64ToInt64(opportunity.RequiredGas)
if err != nil {
analyzer.logger.Error("Required gas exceeds int64 maximum", "requiredGas", opportunity.RequiredGas, "error", err)
// Use maximum safe value as fallback
requiredGasInt64 = math.MaxInt64
}
gasCostForBaseStrategy := new(big.Int).Mul(baseGasPrice, big.NewInt(requiredGasInt64))
strategy := &BiddingStrategy{
PriorityFee: baseGasPrice,
BaseFee: competition.BaseFee,
GasLimit: opportunity.RequiredGas,
SuccessProbability: competition.SuccessProbability,
TotalCost: new(big.Int).Mul(baseGasPrice, big.NewInt(int64(opportunity.RequiredGas))),
TotalCost: gasCostForBaseStrategy,
NetProfit: competition.NetProfit,
}
@@ -203,8 +221,15 @@ func (analyzer *CompetitionAnalyzer) CalculateOptimalBid(ctx context.Context, op
increasedPriority = maxGasPrice
}
// Calculate new total cost with increased priority fee using safe conversion
requiredGasInt64_safe, err := security.SafeUint64ToInt64(opportunity.RequiredGas)
if err != nil {
analyzer.logger.Error("Required gas exceeds int64 maximum for TotalCost in strategy", "requiredGas", opportunity.RequiredGas, "error", err)
// Use maximum safe value as fallback
requiredGasInt64_safe = math.MaxInt64
}
strategy.TotalCost = new(big.Int).Mul(increasedPriority, big.NewInt(requiredGasInt64_safe))
strategy.PriorityFee = increasedPriority
strategy.TotalCost = new(big.Int).Mul(increasedPriority, big.NewInt(int64(opportunity.RequiredGas)))
}
// Update net profit
@@ -281,5 +306,5 @@ type CompetitionData struct {
CompetitionLevel float64
SuccessProbability float64
TotalCost *big.Int
Threshold *math.UniversalDecimal
Threshold *mathpkg.UniversalDecimal
}