LoginSignup
0
0

More than 5 years have passed since last update.

account 情報の保存場所を調べてみました

Posted at

EOSAccount は結局どこで保存しているかを知りたいので、調べてみました。

結論

さきに結論を言いますと

  • EOS ネイティブの実装で、shared_multi_index_container に下記のマルチインデックステーブルに保持しています
    • account_object 情報
    • account_sequence_object 情報
    • permission 情報

アカウント作成処理

アカウント作成するとき newaccount を実行していますが、
contracts/eosio.system/eosio.system.cpp#native::newaccount には、リソースの処理しかありません。
libraries/chain/eosio_contract.cpp#apply_eosio_newaccount に実際のアカウント作成を処理しています。
処理の流れとしては、

  • 入力データの検証処理
  • account_object データを作成する
  • account_sequence_object データを作成する
  • permission_object データを作成する(owneractive2つのレコード)
    • permission_object のshared_authority は構造体であり、認証用の情報を保持している

データ構成は下記になっています。

account_object

class account_object : public chainbase::object<account_object_type, account_object> {
  ...
  id_type              id;
  account_name         name;
  uint8_t              vm_type      = 0;
  uint8_t              vm_version   = 0;
  bool                 privileged   = false;

  time_point           last_code_update;
  digest_type          code_version;
  block_timestamp_type creation_date;

  shared_blob    code;
  shared_blob    abi;
  ...

  using account_index = chainbase::shared_multi_index_container<
    account_object,
    indexed_by<
        ordered_unique<tag<by_id>, member<account_object, account_object::id_type, &account_object::id>>,
        ordered_unique<tag<by_name>, member<account_object, account_name, &account_object::name>>
    >
  >;
  ...
}

class account_sequence_object : public chainbase::object<account_sequence_object_type, account_sequence_object>
{
  OBJECT_CTOR(account_sequence_object);

  id_type      id;
  account_name name;
  uint64_t     recv_sequence = 0;
  uint64_t     auth_sequence = 0;
  uint64_t     code_sequence = 0;
  uint64_t     abi_sequence  = 0;
};

struct by_name;
using account_sequence_index = chainbase::shared_multi_index_container<
  account_sequence_object,
  indexed_by<
      ordered_unique<tag<by_id>, member<account_sequence_object, account_sequence_object::id_type, &account_sequence_object::id>>,
      ordered_unique<tag<by_name>, member<account_sequence_object, account_name, &account_sequence_object::name>>
  >
>;

permission_object

class permission_object : public chainbase::object<permission_object_type, permission_object> {
  ...
  id_type                           id;
  permission_usage_object::id_type  usage_id;
  id_type                           parent; ///< parent permission
  account_name                      owner; ///< the account this permission belongs to
  permission_name                   name; ///< human-readable name for the permission
  time_point                        last_updated; ///< the last time this authority was updated
  shared_authority  
  ...
}

using permission_index = chainbase::shared_multi_index_container<
  permission_object,
  indexed_by<
      ordered_unique<tag<by_id>, member<permission_object, permission_object::id_type, &permission_object::id>>,
      ordered_unique<tag<by_parent>,
        composite_key<permission_object,
            member<permission_object, permission_object::id_type, &permission_object::parent>,
            member<permission_object, permission_object::id_type, &permission_object::id>
        >
      >,
      ordered_unique<tag<by_owner>,
        composite_key<permission_object,
            member<permission_object, account_name, &permission_object::owner>,
            member<permission_object, permission_name, &permission_object::name>
        >
      >,
      ordered_unique<tag<by_name>,
        composite_key<permission_object,
            member<permission_object, permission_name, &permission_object::name>,
            member<permission_object, permission_object::id_type, &permission_object::id>
        >
      >
  >
>;

shared_authority

struct shared_authority {
  ...

   uint32_t                                   threshold = 0;
   shared_vector<key_weight>                  keys;
   shared_vector<permission_level_weight>     accounts;
   shared_vector<wait_weight>                 waits;
   ...

まとめ

EOS アカウント周りは、仕組み的には普通のスマートコントラクトと同じくマルチインデックスを使ってますが、実際の処理とアクセス制限いろいろあるので、ネイティブ実装になっていることを分かりました。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0