Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Binance] Fix timelock unlock signature error #1143

Merged
merged 3 commits into from Oct 18, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
11 changes: 8 additions & 3 deletions src/Binance/Serialization.cpp
Expand Up @@ -125,14 +125,19 @@ json Binance::orderJSON(const Proto::SigningInput& input) {
j["amount"] = tokensJSON(input.time_lock_order().amount());
j["lock_time"] = input.time_lock_order().lock_time();
} else if (input.has_time_relock_order()) {
const auto amount = input.time_relock_order().amount();
j["from"] = addressString(input.time_relock_order().from_address());
j["id"] = input.time_relock_order().id();
j["time_lock_id"] = input.time_relock_order().id();
j["description"] = input.time_relock_order().description();
j["amount"] = tokensJSON(input.time_relock_order().amount());
// if amount is empty or omitted, set null to avoid signature verification error
j["amount"] = nullptr;
if (amount.size() > 0) {
j["amount"] = tokensJSON(amount);
}
j["lock_time"] = input.time_relock_order().lock_time();
} else if (input.has_time_unlock_order()) {
j["from"] = addressString(input.time_unlock_order().from_address());
j["id"] = input.time_unlock_order().id();
j["time_lock_id"] = input.time_unlock_order().id();
}
return j;
}
Expand Down
71 changes: 69 additions & 2 deletions swift/Tests/Blockchains/BinanceChainTests.swift
Expand Up @@ -9,6 +9,8 @@ import WalletCore

class BinanceChainTests: XCTestCase {

let testKey = PrivateKey(data: Data(hexString: "eeba3f6f2db26ced519a3d4c43afff101db957a21d54d25dc7fd235c404d7a5d")!)!

func testAddress() {
let publicKey = PublicKey(data: Data(hexString: "0x026a35920088d98c3888ca68c53dfc93f4564602606cbb87f0fe5ee533db38e502")!, type: .secp256k1)!
let address = AnyAddress(publicKey: publicKey, coin: .binance)
Expand Down Expand Up @@ -64,7 +66,7 @@ class BinanceChainTests: XCTestCase {
}

func testSignTransferOutOrder() throws {
let key = PrivateKey(data: Data(hexString: "eeba3f6f2db26ced519a3d4c43afff101db957a21d54d25dc7fd235c404d7a5d")!)!
let key = testKey
let pubkey = key.getPublicKeySecp256k1(compressed: true)
let input = BinanceSigningInput.with {
$0.chainID = "test-chain"
Expand All @@ -89,7 +91,7 @@ class BinanceChainTests: XCTestCase {
}

func testSignStakeOrder() throws {
let key = PrivateKey(data: Data(hexString: "eeba3f6f2db26ced519a3d4c43afff101db957a21d54d25dc7fd235c404d7a5d")!)!
let key = testKey
let pubkey = key.getPublicKeySecp256k1(compressed: true)
let input = BinanceSigningInput.with {
$0.chainID = "test-chain"
Expand All @@ -113,6 +115,71 @@ class BinanceChainTests: XCTestCase {
XCTAssertEqual(output.encoded.hexString, "ba01f0625dee0a44e3a07fd20a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e112147cc24a1de5245f14a95e457f903bcc8461ac869c1a0a0a03424e42108084af5f220663686170656c126e0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc7124039302c9975fb2a09ac2b6b6fb1d3b9fb5b4c03630d3d7a7da42b1c6736d6127142a3fcdca0b70a3d065da8d4f4df8b5d9d8f46aeb3627a7d7aa901fe186af34c180f2001")
}

func testSignTimeLock() throws {
// https://explorer.binance.org/tx/802824DCB6811339EA90118D33A57916D4698C9F982A78506BAC3AB7F1B6977B
// real key 1p
let key = testKey
let from = AnyAddress(publicKey: key.getPublicKeySecp256k1(compressed: true), coin: .binance)

let input = BinanceSigningInput.with {
$0.chainID = "Binance-Chain-Tigris"
$0.accountNumber = 29
$0.sequence = 1313
$0.privateKey = key.data
$0.timeLockOrder = BinanceTimeLockOrder.with {
$0.fromAddress = from.data
$0.description_p = "test"
$0.amount = [
BinanceSendOrder.Token.with {
$0.amount = 10000000
$0.denom = "BUSD-BD1"
}
]
$0.lockTime = 1603002246
}
}
let output: BinanceSigningOutput = AnySigner.sign(input: input, coin: .binance)
XCTAssertEqual(output.encoded.hexString, "ae01f0625dee0a37079215310a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e11204746573741a0f0a08425553442d4244311080ade2042086bfaffc05126f0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc71240ef7ef0f792c2ec0b06181a176a842d6f475c21e784eb0cbc93fc27795cf5573a58b2364e57b9889dbf1da6175de2ba7c6dc8e7c9b596e8bf4abe2b1fd32165a9181d20a10a")
}

func testSignUnlock() throws {
// https://explorer.binance.org/tx/97074A501A69DE20391C22CA8F79F991FC7D174727D235C2EA345DA485ECEAA0
let key = testKey
let from = AnyAddress(publicKey: key.getPublicKeySecp256k1(compressed: true), coin: .binance)
let input = BinanceSigningInput.with {
$0.chainID = "Binance-Chain-Tigris"
$0.accountNumber = 29
$0.sequence = 1314
$0.privateKey = key.data
$0.timeUnlockOrder = BinanceTimeUnlockOrder.with {
$0.fromAddress = from.data
$0.id = 1312
}
}
let output: BinanceSigningOutput = AnySigner.sign(input: input, coin: .binance)
XCTAssertEqual(output.encoded.hexString, "9401f0625dee0a1dc4050c6c0a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e110a00a126f0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc7124036ae67e8301f7b229ead7f299429308e70c5b44a28d173ecf951c5fe94507a767dcbda27c11610845210d0b9a8fec82e111a6c18c933a32d702d001900b02601181d20a20a")
}

func testSignRelock() throws {
// https://explorer.binance.org/tx/1DAE8A0871A15D06907FF8DAD29D657309DA8A9004CAF5B94FF9B61F8B52B5E5
let key = testKey
let from = AnyAddress(publicKey: key.getPublicKeySecp256k1(compressed: true), coin: .binance)
let input = BinanceSigningInput.with {
$0.chainID = "Binance-Chain-Tigris"
$0.accountNumber = 29
$0.sequence = 1315
$0.privateKey = key.data
$0.timeRelockOrder = BinanceTimeRelockOrder.with {
$0.fromAddress = from.data
$0.id = 1314
$0.description_p = "test_relock"
$0.lockTime = 1603022621
}
}
let output: BinanceSigningOutput = AnySigner.sign(input: input, coin: .binance)
XCTAssertEqual(output.encoded.hexString, "a701f0625dee0a30504711da0a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e110a20a1a0b746573745f72656c6f636b289ddeb0fc05126f0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc71240b8df4f80b8f7714d13280134ee16dc04c826cbc50a0fb20532e91879320b24f812698f736b3fccb3060b3bdc0ffcdbd2ddf2026aeda32c6d159205f183c712cf181d20a30a")
}

func testSignJSON() {
let json = """
{
Expand Down
17 changes: 9 additions & 8 deletions tests/Binance/SignerTests.cpp
Expand Up @@ -671,10 +671,11 @@ TEST(BinanceSigner, BuildTimeRelockOrder) {

const auto data = Binance::Signer(std::move(signingInput)).build();
EXPECT_EQ(hex(data.begin(), data.end()),
"c201f0625dee0a4c"
"504711da"
"0a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e110cd021a1c4465736372697074696f6e206c6f636b656420666f72206f6666657222090a03424e4210c0843d28dbaaf8fa05126e0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc712401a217ece28c8a5e3d9dd44a8228a308e0c7d74d3f4ad8c539f785fd007fb90c714d971b84dbe2eadc65672d880410aab93681211fd44a1f9ee643b0565d1664a180f2001"
);
"c201f0625dee0a4c504711da0a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e110cd021a1c446573"
"6372697074696f6e206c6f636b656420666f72206f6666657222090a03424e4210c0843d28dbaaf8fa05"
"126e0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc7"
"124086ddaa077c8ae551d402fa409cf7e91663982b0542200967c03c0b5876b181353250f689d342f221"
"7624a077b671ce7d09649187e29879f40abbbee9de7ab27c180f2001");
}

TEST(BinanceSigner, BuildTimeUnlockOrder) {
Expand All @@ -695,10 +696,10 @@ TEST(BinanceSigner, BuildTimeUnlockOrder) {

const auto data = Binance::Signer(std::move(signingInput)).build();
EXPECT_EQ(hex(data.begin(), data.end()),
"9301f0625dee0a1d"
"c4050c6c"
"0a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e110cd02126e0a26eb5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc71240006ed2f3f655ad2f3dc570d5409105a6acf28f5ea96162f40db7f5762b7feefc2bd5c8907beaae606cb4092680f69d784edc914d26907d52d35e64468ce5fc91180f2001"
);
"9301f0625dee0a1dc4050c6c0a1408c7c918f6b72c3c0c21b7d08eb6fc66509998e110cd02126e0a26eb"
"5ae9872103a9a55c040c8eb8120f3d1b32193250841c08af44ea561aac993dbe0f6b6a8fc71240da777b"
"fd2032834f59ec9fe69fd6eaa4aca24242dfbc5ec4ef8c435cb9da7eb05ab78e1b8ca9f109657cb77996"
"898f1b59137b3d8f1e00f842e409e18033b347180f2001");
}

} // namespace TW::Binance