Secret Vault on Aptos

First Flight #46
Beginner FriendlyWallet
100 EXP
View results
Submission Details
Severity: high
Valid

Secrets stored as plain strings in `Vault` global storage

Summary

The Vault global storage stores user secrets as plain String values, which poses a significant security risk. These values can be easily exposed on the public blockchain, therefore undermines the contract's fundamental purpose of securely protecting user secrets.

Description

Vault's secret was found storing as String which poses high risk of exposing user's secret that can easily be viewed in public blockchain, deviating the core security of the contract to keep user's secret safe.

struct Vault has key {
<@@>! secret: String
}

Risk

Likelihood:

  • Occurs everytime user calls set_secret

Impact:

  • The user's secret is exposed on the public blockchain, severely compromising the security of their vault. This vulnerability could lead to unauthorized access and potential financial loss.

Proof of Concept

Add the following test in secret_vault.move:

#[test(user = @0x123)]
fun test_vault_secret_in_plain_text(user: &signer) acquires Vault{
use aptos_framework::account;
// Set up user test environment
account::create_account_for_test(signer::address_of(user));
// User sets vault secret
let secret = b"chocolate";
set_secret(user, secret);
let user_add = signer::address_of(user);
let user_vault = borrow_global<Vault>(user_add);
// user's secret can be read as plain text
debug::print(&user_vault.secret);
assert!(user_vault.secret == string::utf8(secret), 1);

In terminal run aptos move test -f test_vault_secret_in_plain_text :

$ aptos move test -f test_vault_secret_in_plain_text [16:28:14]
INCLUDING DEPENDENCY AptosFramework
INCLUDING DEPENDENCY AptosStdlib
INCLUDING DEPENDENCY MoveStdlib
BUILDING aptos-secret-vault
Running Move unit tests
[debug] "chocolate"
[ PASS ] 0x234::vault::test_vault_secret_in_plain_text
Test result: OK. Total tests: 1; passed: 1; failed: 0
{
"Result": "Success"
}

The test passed with user secret chocolate was retrieved and printed from its text form.

Recommended Mitigation

The data for secret shall be encrypted off-chain. Its data type in global storage Vault should be changed to type vector<u8>, aligning to the secret input parameter in set_secret function.

struct Vault has key {
- secret: String
+ secret: vector<u8>
}
...
#[view]
- public fun get_secret (caller: address):String acquires Vault{
+ public fun get_secret (caller: address):vector<u8> acquires Vault{
...
}
Updates

Lead Judging Commences

bube Lead Judge 16 days ago
Submission Judgement Published
Validated
Assigned finding tags:

Anyone can see the `secret` on chain

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.