Assessment reports>Astria Shared Sequencer>Low findings>Log parsing issue in ,extract_required_fee_from_log
Category: Coding Mistakes

Log parsing issue in extract_required_fee_from_log

Low Severity
Low Impact
Low Likelihood

Description

The extract_required_fee_from_log function currently makes a best-effort attempt to parse the log returned as part of Celestia's response to a Cosmos transaction when a transaction fails due to insufficient fees. However, it does not handle parsing failures, which can result in a fallback to the original fee-calculation logic without any adjustment. This can lead to repeated failures in fee-submission attempts, creating a potential DOS issue.

Impact

If parsing the log fails, the function falls back to the default logic in calculate_fee. This can cause an infinite retry loop where the transaction is repeatedly submitted with an insufficient fee, leading to a system hang or a DOS scenario.

/// `log`'s value for this case currently looks like:
/// "insufficient fees; got: 1234utia required: 7980utia: insufficient fee"
/// We'll make a best-effort attempt to parse, but this is just a failsafe to check the
/// new calculated fee using updated Celestia costs is sufficient, so if parsing fails
/// we'll just log the error and otherwise ignore.
fn extract_required_fee_from_log(celestia_broadcast_tx_error_log: &str) -> Option<u64> {
    const SUFFIX: &str = "utia: insufficient fee";
    // Should be left with e.g. "insufficient fees; got: 1234utia required: 7980".
    let Some(log_without_suffix) = celestia_broadcast_tx_error_log.strip_suffix(SUFFIX) else {
        warn!(
            celestia_broadcast_tx_error_log,
            "insufficient gas error doesn't end with '{SUFFIX}'"
        );
        return None;
    };
    // Should be left with e.g. "7980".
    let Some(required) = log_without_suffix.rsplit(' ').next() else {
        warn!(
            celestia_broadcast_tx_error_log,
            "insufficient gas error doesn't have a space before the required amount"
        );
        return None;
    };
    match required.parse::<u64>() {
        Ok(required_fee) => {
            info!(
                required_fee,
                "extracted required fee from broadcast transaction response raw log"
            );
            Some(required_fee)
        }
        Err(error) => {
            warn!(
                celestia_broadcast_tx_error_log, %error,
                "insufficient gas error required amount cannot be parsed as u64"
            );
            None
        }
    }
}

Recommendations

We recommend the following:

  • Improve the robustness of the log parsing in the extract_required_fee_from_log function, such as logging detailed errors and possibly adjusting the fee by a reasonable percentage to avoid repeated failures.

  • Implement more comprehensive tests for fee calculation, including nightly tests to ensure the log-parsing and fee-submission mechanisms are functioning as expected.

Remediation

Zellic © 2025Back to top ↑