Compare v0.1.0

Source
Finds the offset at which two blocks of memory first differ.

Package: Memory

Signature

func Compare(
    lhs: *opaque,
    rhs: *opaque,
    length: uint
) -> uint;

Parameters

NameTypeDescription
lhs*opaqueThe first block.
rhs*opaqueThe second block.
lengthuintThe number of bytes to compare.

Returns

The offset of the first byte that differs, or length if the first length bytes are equal. This is not C's memcmp: there is no sign, and equality is reported as length rather than as 0.

The two comparisons that trip people up:

  • Equal blocks return length, so the equality test is Compare(a, b, n) == n, and never == 0.
  • 0 means the blocks differ at the very first byte — except when length is 0, where nothing is compared and 0 means trivially equal.

The comparison stops at length, so bytes that differ beyond it are invisible. Both blocks must be at least length bytes long.

Example

import Memory::{ Alloc, Compare, Free, Set };

func Main() -> int {
    let lhs = Alloc(16);
    let rhs = Alloc(16);
    Set(lhs, 16, 0x5A);
    Set(rhs, 16, 0x5A);

    Compare(lhs, rhs, 16); // 16 -- equal, so the full length

    let bytes = rhs as *var uint8;
    *(bytes + 5) = 0x00;

    Compare(lhs, rhs, 16); // 5 -- the first difference
    Compare(lhs, rhs, 5);  // 5 -- equal, the difference is out of range

    Free(rhs);
    Free(lhs);
    return 0;
}

See also

  • Memory — the package overview
  • Copy — make one block equal to another
  • Set — fill a block with a known byte before comparing