diff --git a/sdks/v3-sdk/package.json b/sdks/v3-sdk/package.json index 257900a26..cf85b0091 100644 --- a/sdks/v3-sdk/package.json +++ b/sdks/v3-sdk/package.json @@ -26,7 +26,7 @@ "dependencies": { "@ethersproject/abi": "^5.5.0", "@ethersproject/solidity": "^5.0.9", - "@uniswap/sdk-core": "^5.0.0", + "@uniswap/sdk-core": "^5.3.0", "@uniswap/swap-router-contracts": "^1.3.0", "@uniswap/v3-periphery": "^1.1.1", "@uniswap/v3-staker": "1.0.0", diff --git a/sdks/v3-sdk/src/constants.ts b/sdks/v3-sdk/src/constants.ts index 3dbe3ffa8..086ccd1a5 100644 --- a/sdks/v3-sdk/src/constants.ts +++ b/sdks/v3-sdk/src/constants.ts @@ -1,9 +1,21 @@ +import { ChainId } from '@uniswap/sdk-core' + export const FACTORY_ADDRESS = '0x1F98431c8aD98523631AE4a59f267346ea31F984' export const ADDRESS_ZERO = '0x0000000000000000000000000000000000000000' +// @deprecated please use poolInitCodeHash(chainId: ChainId) export const POOL_INIT_CODE_HASH = '0xe34f199b19b2b4f47f68442619d555527d244f78a3297ea89325f843f87b8b54' +export function poolInitCodeHash(chainId?: ChainId): string { + switch (chainId) { + case ChainId.ZKSYNC: + return '0x010013f177ea1fcbc4520f9a3ca7cd2d1d77959e05aa66484027cb38e712aeed' + default: + return POOL_INIT_CODE_HASH + } +} + /** * The default factory enabled fee amounts, denominated in hundredths of bips. */ diff --git a/sdks/v3-sdk/src/utils/computePoolAddress.test.ts b/sdks/v3-sdk/src/utils/computePoolAddress.test.ts index 806e57457..79e739dd0 100644 --- a/sdks/v3-sdk/src/utils/computePoolAddress.test.ts +++ b/sdks/v3-sdk/src/utils/computePoolAddress.test.ts @@ -1,6 +1,9 @@ +import { defaultAbiCoder } from '@ethersproject/abi' import { Token } from '@uniswap/sdk-core' +import { computeZksyncCreate2Address } from '@uniswap/sdk-core' import { FeeAmount } from '../constants' import { computePoolAddress } from './computePoolAddress' +import { keccak256 as solKeccak256 } from '@ethersproject/solidity' describe('#computePoolAddress', () => { const factoryAddress = '0x1111111111111111111111111111111111111111' @@ -41,4 +44,22 @@ describe('#computePoolAddress', () => { expect(resultA).toEqual(resultB) }) + + it('should correctly compute zkevm pool address', () => { + const USDCE = new Token(324, '0x3355df6D4c9C3035724Fd0e3914dE96A5a83aaf4', 6, 'USDC.e', 'Bridged USDC (zkSync)') + const WETH = new Token(324, '0x5AEa5775959fBC2557Cc8789bC1bf90A239D9a91', 18, 'WETH', 'Wrapped Ether') + let tokenA = USDCE + let tokenB = WETH + const salt = solKeccak256( + ['bytes'], + [defaultAbiCoder.encode(['address', 'address', 'uint24'], [tokenA.address, tokenB.address, FeeAmount.MEDIUM])] + ) + const zkaddress = computeZksyncCreate2Address( + '0x8FdA5a7a8dCA67BBcDd10F02Fa0649A937215422', + '0x010013f177ea1fcbc4520f9a3ca7cd2d1d77959e05aa66484027cb38e712aeed', + salt + ) + + expect(zkaddress).toEqual('0xff577f0E828a878743Ecc5E2632cbf65ceCf17cF') + }) }) diff --git a/sdks/v3-sdk/src/utils/computePoolAddress.ts b/sdks/v3-sdk/src/utils/computePoolAddress.ts index 5395eb55b..2a13a21ba 100644 --- a/sdks/v3-sdk/src/utils/computePoolAddress.ts +++ b/sdks/v3-sdk/src/utils/computePoolAddress.ts @@ -1,8 +1,8 @@ import { defaultAbiCoder } from '@ethersproject/abi' import { getCreate2Address } from '@ethersproject/address' import { keccak256 } from '@ethersproject/solidity' -import { Token } from '@uniswap/sdk-core' -import { FeeAmount, POOL_INIT_CODE_HASH } from '../constants' +import { ChainId, computeZksyncCreate2Address, Token } from '@uniswap/sdk-core' +import { FeeAmount, poolInitCodeHash } from '../constants' /** * Computes a pool address @@ -11,6 +11,7 @@ import { FeeAmount, POOL_INIT_CODE_HASH } from '../constants' * @param tokenB The second token of the pair, irrespective of sort order * @param fee The fee tier of the pool * @param initCodeHashManualOverride Override the init code hash used to compute the pool address if necessary + * @param chainId * @returns The pool address */ export function computePoolAddress({ @@ -19,20 +20,28 @@ export function computePoolAddress({ tokenB, fee, initCodeHashManualOverride, + chainId, }: { factoryAddress: string tokenA: Token tokenB: Token fee: FeeAmount initCodeHashManualOverride?: string + chainId?: ChainId }): string { const [token0, token1] = tokenA.sortsBefore(tokenB) ? [tokenA, tokenB] : [tokenB, tokenA] // does safety checks - return getCreate2Address( - factoryAddress, - keccak256( - ['bytes'], - [defaultAbiCoder.encode(['address', 'address', 'uint24'], [token0.address, token1.address, fee])] - ), - initCodeHashManualOverride ?? POOL_INIT_CODE_HASH + const salt = keccak256( + ['bytes'], + [defaultAbiCoder.encode(['address', 'address', 'uint24'], [token0.address, token1.address, fee])] ) + const initCodeHash = initCodeHashManualOverride ?? poolInitCodeHash(chainId) + + // ZKSync uses a different create2 address computation + // Most likely all ZKEVM chains will use the different computation from standard create2 + switch (chainId) { + case ChainId.ZKSYNC: + return computeZksyncCreate2Address(factoryAddress, initCodeHash, salt) + default: + return getCreate2Address(factoryAddress, salt, initCodeHash) + } } diff --git a/yarn.lock b/yarn.lock index c817a0b35..fb66533a6 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4630,17 +4630,20 @@ __metadata: languageName: unknown linkType: soft -"@uniswap/sdk-core@npm:^5.0.0": - version: 5.0.0 - resolution: "@uniswap/sdk-core@npm:5.0.0" +"@uniswap/sdk-core@npm:^5.0.0, @uniswap/sdk-core@npm:^5.3.0": + version: 5.3.0 + resolution: "@uniswap/sdk-core@npm:5.3.0" dependencies: "@ethersproject/address": ^5.0.2 + "@ethersproject/bytes": ^5.7.0 + "@ethersproject/keccak256": 5.7.0 + "@ethersproject/strings": 5.7.0 big.js: ^5.2.2 decimal.js-light: ^2.5.0 jsbi: ^3.1.4 tiny-invariant: ^1.1.0 toformat: ^2.0.0 - checksum: 06a4b9ccec3e19bdf695011999c4039a0477910ad5e4128efd8a06e44c23fb40d3685ef5ef2d520632562fe4d0fa486d01326b391266e8e08f43dfc522bd41d5 + checksum: 82570af027937c998208f8ea0bb8c44bd8a2e541023f3b6a5115d9298c95c5f37b20b892ccedf6cc6582ab01f5683f4a8c078cccac43565a5da3362b7363cee7 languageName: node linkType: hard @@ -4835,7 +4838,7 @@ __metadata: "@ethersproject/abi": ^5.5.0 "@ethersproject/solidity": ^5.0.9 "@types/jest": ^24.0.25 - "@uniswap/sdk-core": ^5.0.0 + "@uniswap/sdk-core": ^5.3.0 "@uniswap/swap-router-contracts": ^1.3.0 "@uniswap/v3-core": 1.0.0 "@uniswap/v3-periphery": ^1.1.1