Skip to content

The bytesToHex conformance property in LibHexString.bytesToHex.t.sol never reaches its accept arm #59

Description

@thedavidmeister

Audit scope: whole-repo, commit 7aa85a4

Dimension 2 (test coverage) / 5 (correctness/intent) · medium

Location: test/src/lib/LibHexString.bytesToHex.t.sol:368-393

Path note: PR #56 is open and unmerged as of filing. On main today this file is test/lib/LibHexString.bytesToHex.t.sol; it becomes test/src/lib/LibHexString.bytesToHex.t.sol after #56 merges.

Problem

The docstring states the property as "either reverts or returns exactly that
string with its first two characters removed". toStringReturn is fuzzed
independently of data, so conformance requires a random string to be exactly
data.length * 2 + 2 characters long and start 0x. Measured over 2048 runs:
seed 1 → 1 conforming, seed 2 → 1, seed 3 → 0, seed 4 → 0. On most seeds the
second half of the stated property is exercised zero times; the test is a
rejection test wearing a bi-conditional's name.

Proposed fix

Construct the conforming half. Verified: passes on seed 3 and moves the
branch split to 1036 conforming / 1012 non-conforming.

function testBytesToHexRejectsEveryNonConformingVmOutput(bytes memory data, string memory filler, bool conforming)
    external
{
    // A random string is essentially never `0x` plus two characters per input
    // byte, so the accepted half is CONSTRUCTED rather than waited for: measured
    // over 2048 runs an unconstructed return conformed 0 to 1 times.
    string memory toStringReturn = filler;
    if (conforming) {
        bytes memory payload = new bytes(data.length * 2);
        bytes memory fillerBytes = bytes(filler);
        for (uint256 i = 0; i < payload.length; i++) {
            payload[i] = fillerBytes.length == 0 ? bytes1("a") : fillerBytes[i % fillerBytes.length];
        }
        toStringReturn = string.concat("0x", string(payload));
    }
    // … body unchanged from line 374 on, with `toStringReturn` in place of the parameter.
}

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

auditAudit findingmediumAudit findingpass2Audit findingpass5Audit finding

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions