Skip to content

Commit

Permalink
feat: Make Address.toString() checksum
Browse files Browse the repository at this point in the history
  • Loading branch information
William Cory authored and William Cory committed May 8, 2024
1 parent 0ed0a07 commit b0cde17
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 12 deletions.
17 changes: 16 additions & 1 deletion packages/util/src/address.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import { keccak256 } from 'ethereum-cryptography/keccak.js'

import {
generateAddress,
generateAddress2,
Expand Down Expand Up @@ -129,7 +131,20 @@ export class Address {
* Returns hex encoding of address.
*/
toString(): PrefixedHexString {
return bytesToHex(this.bytes)
const unprefixedString = bytesToHex(this.bytes).substring(2).split('')

const hash = keccak256(this.bytes)

for (let i = 0; i < 40; i += 2) {
if (hash[i >> 1] >> 4 >= 8 && unprefixedString[i]) {
unprefixedString[i] = unprefixedString[i].toUpperCase()
}
if ((hash[i >> 1] & 0x0f) >= 8 && unprefixedString[i + 1]) {
unprefixedString[i + 1] = unprefixedString[i + 1].toUpperCase()
}
}

return `0x${unprefixedString.join('')}`
}

/**
Expand Down
11 changes: 6 additions & 5 deletions packages/util/test/address.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ describe('Address', () => {
const pubKey = hexToBytes(
'0x3a443d8381a6798a70c6ff9304bdc8cb0163c23211d11628fae52ef9e0dca11a001cf066d56a8156fc201cd5df8a36ef694eecd258903fca7086c1fae7441e1d'
)
const str = '0x2f015c60e0be116b1f0cd534704db9c92118fb6a'
const str = '0x2f015c60E0BE116b1f0cd534704Db9c92118FB6a'
const addr = Address.fromPublicKey(pubKey)
assert.equal(addr.toString(), str)
})
Expand All @@ -55,18 +55,18 @@ describe('Address', () => {
it('should instantiate from private key', () => {
// prettier-ignore
const privateKey = Uint8Array.from([234, 84, 189, 197, 45, 22, 63, 136, 201, 58, 176, 97, 87, 130, 207, 113, 138, 46, 251, 158, 81, 167, 152, 154, 171, 27, 8, 6, 126, 156, 28, 95])
const str = '0x2f015c60e0be116b1f0cd534704db9c92118fb6a'
const str = '0x2f015c60E0BE116b1f0cd534704Db9c92118FB6a'
const addr = Address.fromPrivateKey(privateKey)
assert.equal(addr.toString(), str)
})

it('should generate address for created contract', () => {
const from = Address.fromString('0x990ccf8a0de58091c028d6ff76bb235ee67c1c39')
const addr = Address.generate(from, BigInt(14))
assert.equal(addr.toString(), '0xd658a4b8247c14868f3c512fa5cbb6e458e4a989')
assert.equal(addr.toString(), '0xd658a4b8247C14868F3c512fa5cBB6e458e4A989')

const addr2 = Address.generate(from, BigInt(0))
assert.equal(addr2.toString(), '0xbfa69ba91385206bfdd2d8b9c1a5d6c10097a85b')
assert.equal(addr2.toString(), '0xbFA69bA91385206BFdD2D8B9c1a5d6C10097a85b')
})

it('should provide correct precompile check', () => {
Expand Down Expand Up @@ -94,10 +94,11 @@ describe('Address', () => {

it('should provide a Uint8Array that does not mutate the original address', () => {
const str = '0x2f015c60e0be116b1f0cd534704db9c92118fb6a'
const checksumStr = '0x2f015c60E0BE116b1f0cd534704Db9c92118FB6a'
const address = Address.fromString(str)
const addressBytes = address.toBytes()
addressBytes.fill(0)
assert.equal(address.toString(), str)
assert.equal(address.toString(), checksumStr)
})

it('should compare equality properly', () => {
Expand Down
12 changes: 6 additions & 6 deletions packages/util/test/testdata/eip1014Examples.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,46 +13,46 @@
"salt": "0x0000000000000000000000000000000000000000000000000000000000000000",
"initCode": "0x00",
"gas": "32006",
"result": "0xb928f69bb1d91cd65274e3c79d8986362984fda3"
"result": "0xB928F69Bb1D91cD65274e3C79D8986362984FdA3"
},
{
"comment": "Example 2",
"address": "0xdeadbeef00000000000000000000000000000000",
"salt": "0x000000000000000000000000feed000000000000000000000000000000000000",
"initCode": "0x00",
"gas": "32006",
"result": "0xd04116cdd17bebe565eb2422f2497e06cc1c9833"
"result": "0xD04116CdD17BEBE565EB2422F2497E06cc1c9833"
},
{
"comment": "Example 3",
"address": "0x0000000000000000000000000000000000000000",
"salt": "0x0000000000000000000000000000000000000000000000000000000000000000",
"initCode": "0xdeadbeef",
"gas": "32006",
"result": "0x70f2b2914a2a4b783faefb75f459a580616fcb5e"
"result": "0x70f2B2914A2a4b783FAEfb75f459a580616fCb5e"
},
{
"comment": "Example 4",
"address": "0x00000000000000000000000000000000deadbeef",
"salt": "0x00000000000000000000000000000000000000000000000000000000cafebabe",
"initCode": "0xdeadbeef",
"gas": "32006",
"result": "0x60f3f640a8508fc6a86d45df051962668e1e8ac7"
"result": "0x60f3F640a8508Fc6a86D45dF051962668e1e8ac7"
},
{
"comment": "Example 5",
"address": "0x00000000000000000000000000000000deadbeef",
"salt": "0x00000000000000000000000000000000000000000000000000000000cafebabe",
"initCode": "0xdeadbeefdeadbeefdeadbeefdeadbeefdeadbeefdeadbeefdeadbeefdeadbeefdeadbeefdeadbeefdeadbeef",
"gas": "32012",
"result": "0x1d8bfdc5d46dc4f61d6b6115972536ebe6a8854c"
"result": "0x1D8BfDC5d46Dc4f61d6b6115972536ebe6A8854c"
},
{
"comment": "Example 6",
"address": "0x0000000000000000000000000000000000000000",
"salt": "0x0000000000000000000000000000000000000000000000000000000000000000",
"initCode": "0x",
"gas": "32000",
"result": "0xe33c0c7f7df4809055c3eba6c09cfe4baf1bd9e0"
"result": "0xE33c0c7F7Df4809055C3Eba6c09cfe4baF1BD9E0"
}
]

0 comments on commit b0cde17

Please sign in to comment.