FAILURE MAP
← Case archive

FA-72736 / Check-digit algorithms / Open access

CPF first check digit can become ten · case 01

Numbers whose first check digit should be 0 are rejected.

Verified by executionVariant 1 · 8 checks per implementationDownload source bundle ↓JSON ↗

ROOT CAUSE

k1 is reduced mod 11 only; the remainder 10 must become 0.

VERIFIED REPAIR

Reduce the mod-11 result once more mod 10.

Unsuccessful approach: Using 11 minus the remainder without clamping yields 10 or 11 for remainders 1 and 0.

Case contract

Brazilian CPF taxpayer number: dots and hyphens removed, then 11 ASCII digits that are not all the same digit (else "malformed"). k1 = (sum of digits 1-9 weighted 10..2) * 10 mod 11 mod 10; k2 = (digits 1-9 and the computed k1 weighted 11..2) * 10 mod 11 mod 10. Return [k1, k2, whether digits 10-11 equal them].

Why this case matters

Onboarding and invoicing flows validate CPF numbers before tax reporting.

1 / The failure

Exit 1
"""Failure Map reference implementation. Python standard library only."""
import json

N = 1
observations = []
def solve(s):
    t = s.replace('.', '').replace('-', '')
    if len(t) != 11 or not t.isascii() or not t.isdigit():
        return 'malformed'
    if len(set(t)) == 1:
        return 'malformed'
    d = [int(ch) for ch in t]
    k1 = sum(w * x for w, x in zip(range(10, 1, -1), d[:9])) * 10 % 11
    k2 = sum(w * x for w, x in zip(range(11, 1, -1), d[:9] + [k1])) * 10 % 11 % 10
    return [k1, k2, d[9] == k1 and d[10] == k2]
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[['regression ["29622049718"]', ['29622049718'], [0, 2, False]], ['regression ["47444770261"]', ['47444770261'], [0, 4, False]], ['partial-repair ["80112861152"]', ['80112861152'], [0, 5, False]], ['control ["42765277574"]', ['42765277574'], [9, 1, False]], ['control ["04160821863"]', ['04160821863'], [1, 2, False]], ['control ["11181886176"]', ['11181886176'], [6, 3, False]], ['control ["54166960081"]', ['54166960081'], [1, 6, False]], ['control ["61682621036"]', ['61682621036'], [5, 7, False]]], [['regression ["123.456.789-00"]', ['123.456.789-00'], [0, 9, False]], ['regression ["58537963305"]', ['58537963305'], [0, 5, True]], ['partial-repair ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['control ["91615291602"]', ['91615291602'], [8, 7, False]], ['control ["38203173222"]', ['38203173222'], [5, 0, False]], ['control ["71865383378"]', ['71865383378'], [9, 2, False]], ['control ["11888021888"]', ['11888021888'], [6, 1, False]], ['control ["02970275879"]', ['02970275879'], [1, 3, False]]], [['regression ["83495775501"]', ['83495775501'], [0, 1, True]], ['regression ["76913448309"]', ['76913448309'], [0, 9, True]], ['partial-repair ["92730181903"]', ['92730181903'], [0, 3, True]], ['control ["33143111705"]', ['33143111705'], [6, 3, False]], ['control ["22747397622"]', ['22747397622'], [5, 3, False]], ['control ["25998738965"]', ['25998738965'], [4, 2, False]], ['control ["52682522850"]', ['52682522850'], [3, 1, False]], ['control ["78829380673"]', ['78829380673'], [8, 7, False]]], [['regression ["47444770261"]', ['47444770261'], [0, 4, False]], ['regression ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['partial-repair ["63302001304"]', ['63302001304'], [0, 4, True]], ['partial-repair ["80112861152"]', ['80112861152'], [0, 5, False]], ['control ["72986172530"]', ['72986172530'], [7, 1, False]], ['control ["37134793981"]', ['37134793981'], [9, 0, False]], ['control ["529.982.247-25"]', ['529.982.247-25'], [2, 5, True]], ['control ["52998224725"]', ['52998224725'], [2, 5, True]]], [['regression ["58537963305"]', ['58537963305'], [0, 5, True]], ['regression ["92730181903"]', ['92730181903'], [0, 3, True]], ['partial-repair ["47444770261"]', ['47444770261'], [0, 4, False]], ['partial-repair ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['control ["111.111.111-11"]', ['111.111.111-11'], 'malformed'], ['control ["00000000000"]', ['00000000000'], 'malformed'], ['control ["22222222222"]', ['22222222222'], 'malformed'], ['control ["1234567890"]', ['1234567890'], 'malformed']]]
for label, args, expected in fixtures[N - 1]:
    check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
Boundary fixtureActualExpectedOutcome
regression ["29622049718"][10, 4, False][0, 2, False]Failed
regression ["47444770261"][10, 6, False][0, 4, False]Failed
partial-repair ["80112861152"][0, 5, False][0, 5, False]Passed
control ["42765277574"][9, 1, False][9, 1, False]Passed
control ["04160821863"][1, 2, False][1, 2, False]Passed
control ["11181886176"][6, 3, False][6, 3, False]Passed
control ["54166960081"][1, 6, False][1, 6, False]Passed
control ["61682621036"][5, 7, False][5, 7, False]Passed

SHA-256 / 471502440650dded74491be2f1234fa0a9f3a68a859e0707d4db70df83dda2c8

2 / The unsuccessful fix

Exit 1
"""Failure Map reference implementation. Python standard library only."""
import json

N = 1
observations = []
def solve(s):
    t = s.replace('.', '').replace('-', '')
    if len(t) != 11 or not t.isascii() or not t.isdigit():
        return 'malformed'
    if len(set(t)) == 1:
        return 'malformed'
    d = [int(ch) for ch in t]
    k1 = 11 - sum(w * x for w, x in zip(range(10, 1, -1), d[:9])) % 11
    k2 = sum(w * x for w, x in zip(range(11, 1, -1), d[:9] + [k1])) * 10 % 11 % 10
    return [k1, k2, d[9] == k1 and d[10] == k2]
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[['regression ["29622049718"]', ['29622049718'], [0, 2, False]], ['regression ["47444770261"]', ['47444770261'], [0, 4, False]], ['partial-repair ["80112861152"]', ['80112861152'], [0, 5, False]], ['control ["42765277574"]', ['42765277574'], [9, 1, False]], ['control ["04160821863"]', ['04160821863'], [1, 2, False]], ['control ["11181886176"]', ['11181886176'], [6, 3, False]], ['control ["54166960081"]', ['54166960081'], [1, 6, False]], ['control ["61682621036"]', ['61682621036'], [5, 7, False]]], [['regression ["123.456.789-00"]', ['123.456.789-00'], [0, 9, False]], ['regression ["58537963305"]', ['58537963305'], [0, 5, True]], ['partial-repair ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['control ["91615291602"]', ['91615291602'], [8, 7, False]], ['control ["38203173222"]', ['38203173222'], [5, 0, False]], ['control ["71865383378"]', ['71865383378'], [9, 2, False]], ['control ["11888021888"]', ['11888021888'], [6, 1, False]], ['control ["02970275879"]', ['02970275879'], [1, 3, False]]], [['regression ["83495775501"]', ['83495775501'], [0, 1, True]], ['regression ["76913448309"]', ['76913448309'], [0, 9, True]], ['partial-repair ["92730181903"]', ['92730181903'], [0, 3, True]], ['control ["33143111705"]', ['33143111705'], [6, 3, False]], ['control ["22747397622"]', ['22747397622'], [5, 3, False]], ['control ["25998738965"]', ['25998738965'], [4, 2, False]], ['control ["52682522850"]', ['52682522850'], [3, 1, False]], ['control ["78829380673"]', ['78829380673'], [8, 7, False]]], [['regression ["47444770261"]', ['47444770261'], [0, 4, False]], ['regression ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['partial-repair ["63302001304"]', ['63302001304'], [0, 4, True]], ['partial-repair ["80112861152"]', ['80112861152'], [0, 5, False]], ['control ["72986172530"]', ['72986172530'], [7, 1, False]], ['control ["37134793981"]', ['37134793981'], [9, 0, False]], ['control ["529.982.247-25"]', ['529.982.247-25'], [2, 5, True]], ['control ["52998224725"]', ['52998224725'], [2, 5, True]]], [['regression ["58537963305"]', ['58537963305'], [0, 5, True]], ['regression ["92730181903"]', ['92730181903'], [0, 3, True]], ['partial-repair ["47444770261"]', ['47444770261'], [0, 4, False]], ['partial-repair ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['control ["111.111.111-11"]', ['111.111.111-11'], 'malformed'], ['control ["00000000000"]', ['00000000000'], 'malformed'], ['control ["22222222222"]', ['22222222222'], 'malformed'], ['control ["1234567890"]', ['1234567890'], 'malformed']]]
for label, args, expected in fixtures[N - 1]:
    check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
Boundary fixtureActualExpectedOutcome
regression ["29622049718"][10, 4, False][0, 2, False]Failed
regression ["47444770261"][10, 6, False][0, 4, False]Failed
partial-repair ["80112861152"][11, 5, False][0, 5, False]Failed
control ["42765277574"][9, 1, False][9, 1, False]Passed
control ["04160821863"][1, 2, False][1, 2, False]Passed
control ["11181886176"][6, 3, False][6, 3, False]Passed
control ["54166960081"][1, 6, False][1, 6, False]Passed
control ["61682621036"][5, 7, False][5, 7, False]Passed

SHA-256 / e7a0f9773e66253a49ae95291987db67f5790f0c3358dd4c270fc7f73ea612fb

3 / The verified repair

Exit 0
"""Failure Map reference implementation. Python standard library only."""
import json

N = 1
observations = []
def solve(s):
    t = s.replace('.', '').replace('-', '')
    if len(t) != 11 or not t.isascii() or not t.isdigit():
        return 'malformed'
    if len(set(t)) == 1:
        return 'malformed'
    d = [int(ch) for ch in t]
    k1 = sum(w * x for w, x in zip(range(10, 1, -1), d[:9])) * 10 % 11 % 10
    k2 = sum(w * x for w, x in zip(range(11, 1, -1), d[:9] + [k1])) * 10 % 11 % 10
    return [k1, k2, d[9] == k1 and d[10] == k2]
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[['regression ["29622049718"]', ['29622049718'], [0, 2, False]], ['regression ["47444770261"]', ['47444770261'], [0, 4, False]], ['partial-repair ["80112861152"]', ['80112861152'], [0, 5, False]], ['control ["42765277574"]', ['42765277574'], [9, 1, False]], ['control ["04160821863"]', ['04160821863'], [1, 2, False]], ['control ["11181886176"]', ['11181886176'], [6, 3, False]], ['control ["54166960081"]', ['54166960081'], [1, 6, False]], ['control ["61682621036"]', ['61682621036'], [5, 7, False]]], [['regression ["123.456.789-00"]', ['123.456.789-00'], [0, 9, False]], ['regression ["58537963305"]', ['58537963305'], [0, 5, True]], ['partial-repair ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['control ["91615291602"]', ['91615291602'], [8, 7, False]], ['control ["38203173222"]', ['38203173222'], [5, 0, False]], ['control ["71865383378"]', ['71865383378'], [9, 2, False]], ['control ["11888021888"]', ['11888021888'], [6, 1, False]], ['control ["02970275879"]', ['02970275879'], [1, 3, False]]], [['regression ["83495775501"]', ['83495775501'], [0, 1, True]], ['regression ["76913448309"]', ['76913448309'], [0, 9, True]], ['partial-repair ["92730181903"]', ['92730181903'], [0, 3, True]], ['control ["33143111705"]', ['33143111705'], [6, 3, False]], ['control ["22747397622"]', ['22747397622'], [5, 3, False]], ['control ["25998738965"]', ['25998738965'], [4, 2, False]], ['control ["52682522850"]', ['52682522850'], [3, 1, False]], ['control ["78829380673"]', ['78829380673'], [8, 7, False]]], [['regression ["47444770261"]', ['47444770261'], [0, 4, False]], ['regression ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['partial-repair ["63302001304"]', ['63302001304'], [0, 4, True]], ['partial-repair ["80112861152"]', ['80112861152'], [0, 5, False]], ['control ["72986172530"]', ['72986172530'], [7, 1, False]], ['control ["37134793981"]', ['37134793981'], [9, 0, False]], ['control ["529.982.247-25"]', ['529.982.247-25'], [2, 5, True]], ['control ["52998224725"]', ['52998224725'], [2, 5, True]]], [['regression ["58537963305"]', ['58537963305'], [0, 5, True]], ['regression ["92730181903"]', ['92730181903'], [0, 3, True]], ['partial-repair ["47444770261"]', ['47444770261'], [0, 4, False]], ['partial-repair ["123.456.789-09"]', ['123.456.789-09'], [0, 9, True]], ['control ["111.111.111-11"]', ['111.111.111-11'], 'malformed'], ['control ["00000000000"]', ['00000000000'], 'malformed'], ['control ["22222222222"]', ['22222222222'], 'malformed'], ['control ["1234567890"]', ['1234567890'], 'malformed']]]
for label, args, expected in fixtures[N - 1]:
    check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
Boundary fixtureActualExpectedOutcome
regression ["29622049718"][0, 2, False][0, 2, False]Passed
regression ["47444770261"][0, 4, False][0, 4, False]Passed
partial-repair ["80112861152"][0, 5, False][0, 5, False]Passed
control ["42765277574"][9, 1, False][9, 1, False]Passed
control ["04160821863"][1, 2, False][1, 2, False]Passed
control ["11181886176"][6, 3, False][6, 3, False]Passed
control ["54166960081"][1, 6, False][1, 6, False]Passed
control ["61682621036"][5, 7, False][5, 7, False]Passed

SHA-256 / 35f23eec677b98295c4ace7eda578daffc04e8f4d2a0824fab403e2f0ac06851

Verification & scope

A deterministic, bounded teaching model of the named scheme under the stated contract; not a certified validator. This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.

Observations recorded using Python 3.12.14 at 2026-09-29T14:48:41.094857+00:00.

Case digest / 4cf42bc9b896fadf638535b2f36e7dacc358d90e53f97ee5281391780bb21d63