スマートコントラクト自動検出ツール「チェーン必須テスト」、Web3.0の世界への扉を開く方法

[Chain Bitest] の新バージョンをリリースして以来、多くの開発者が試しに来ていますので、今日はこのツールについて詳しく紹介したいと思います。

【Chain Bitest】ブロックチェーンスマートコントラクトの脆弱性を検出するために使用できるスマートコントラクト自動検出ツール。このプラットフォームは、ユーザーごとに個別のテスト チェーンをシミュレートし、ユーザーはテスト チェーン上でスマート コントラクトを個別に展開、テスト、検証することができ、スマート コントラクトの開発、テスト、検証を統合した包括的なプラットフォームです。

検証のプロセスでは、プラットフォームは形式検証やその他のテクノロジーを採用して実行環境をモデル化し、数学的推論やその他の方法でセキュリティ属性を検証し、コントラクトの実行中に発生する可能性のあるセキュリティ問題を発見し、コントラクト開発者が次のことを行うのを支援します。潜在的なセキュリティ リスクを見つけ、脆弱性の場所を特定し、契約のセキュリティを強化します。これには主に、コード仕様の検出、標準仕様の検出、関数呼び出しの検出、ビジネス ロジックのセキュリティの検出の 4 つの検出側面が含まれます。

Web3.0の世界で最も欠かせないのがスマートコントラクトです。今すぐ私たちに従って、このスマート コントラクト自動検出ツールを学び、Web3.0 の世界を一緒に解き放ちましょう。

ONEコード仕様検出

1. メモリ ABIEncoderV2 配列

レベル:エラー

説明:バージョン 0.4.7 ~ 0.5.9 の solc コンパイラにはバグがあり、このバグにより、多次元配列の処理時に abi.encode インターフェイスが誤った結果を生成します。

サンプル

コンパイラのバージョンが 0.5.9 の場合、入れ子配列 badArr の戻り値が [[1, 2], [2, 3], [3, 4]] となります。コンパイラのバージョンが 0.6.7 の場合、入れ子配列 badArr の戻り値は [[1, 2], [3, 4], [5, 6]] となります。

修正提案: 0.4.7 ~ 0.5.9 コンパイラの使用を避けるか、0.4.7 ~ 0.5.9 コンパイラの abi.encode インターフェイスを無効にします。

2. 複数のコンストラクター

レベル:エラー

説明:コンパイラのバージョン 0.4.22 では、コントラクトは 2 つの形式 (constructor キーワードを使用したコンストラクターの宣言、またはコントラクト名を使用した関数の宣言) でコンストラクターを同時に持つことができます。したがって、コンストラクター内の変数は相互に上書きされる危険があります。

サンプル

constructor() では x は 1 に初期化されますが、Test() では x は 2 に初期化され、後で定義されたコンストラクターは無効になるため、x は最終的に 1 に初期化されます。

推奨される修正:コンストラクターを 1 つだけ使用します。

3. パブリックマッピングの入れ子構造変数

レベル:エラー

説明:パブリック変数にはデフォルトの読み取り専用ゲッター関数がありますが、パブリック マッピングのネストされた参照構造では不正なゲッター関数が生成されます。

サンプル

パブリック マッピング m は参照型構造体をネストするため、パブリック変数のデフォルトの読み取りメソッド m[1].a が失敗します。

修正提案:パブリック マッピングのネストされた参照型の使用を避けるか、実験的なプラグマ ABIEncoderV2 を使用してください。

4. 制御文字を右から左に読み書きします。

レベル:エラー

説明: Unicode [U+202E] は、コンパイラに通常とは対照的に右から左への読み取りを強制するため、ユーザーに誤解を与える可能性があります。

サンプル

_f 関数は、入力値 i、j、m が a、b、c に順番に渡されることを期待していますが、U+202E の存在により、入力関数は j の順序で与える必要があります。私とMさん。

修正提案: U+202E 文字の使用を避けてください。

5. 状態変数のカバレッジ

レベル:エラー

説明:コントラクトの継承には、状態変数の継承が含まれます。サブコントラクト内の基本クラス コントラクトの状態変数をオーバーロードすると、変数の使用時にロジック エラーが発生する可能性があります。

サンプル

コントラクト Test は Base のサブコントラクトであり、Test の a の定義は Base の状態変数 a をオーバーロードします。f1() を呼び出すと Base に が返され、f2() を呼び出すと Test に が返されます。

修正提案:基本クラスのコントラクト状態変数のオーバーロードを避けてください。

6. 初期化されていないストレージ変数

レベル:エラー

説明:初期化されていないストレージ状態変数のアドレスは最初の状態変数のアドレスを指すため、これを使用するとデータの上書きやデータ損失が発生する可能性があります。

サンプル

初期化されていない変数 st の記憶ポインタは状態変数 a を指し、st.b の代入により変数 a が上書きされ、a の値は 2 になります。

修復の提案:使用する前にストレージ ローカル変数を初期化するか、代わりにメモリ ローカル変数を使用します。

7. 定数関数の状態変更

レベル:警告

説明: Solidity 0.5.0 より前では、その可変性は constant/prue/view 関数として定義されていましたが、関数本体のステートメントが変更されました。このような関数はコンパイルできますが、警告のみが報告され、それ以降の関数の呼び出しは失敗します。この問題は 0.5.0 以降のバージョンで修正されており、定数関数で実装された状態変更はコンパイルできません。

サンプル

変数 a は f() 関数で値を変更しますが、a() 関数はビューとしてマークされます。したがって、 f() を呼び出しても a は変更されません。

提案される修正: Solidity 0.5.0 より前のコントラクトに対して可変性が正しいことを確認します。

8. マッピングを含む構造を削除します。

レベル:警告

説明: delete を使用してマッピングを含む構造体をリセットすると、構造体のマッピングはリセットされず、後続のロジック エラーが発生する可能性があります。

サンプル

コントラクトは初期化後に構造体 a をインスタンス化し、ai を 10 に、aj[10] を 100 に初期化します。f1 で delete a を使用すると、構造体 a がリセットされます。f2() でデータを読み取ることができ、その結果、変数 ai は 0 にリセットされていますが、aj[10] のデータは 100 のままです。

修復の提案:マッピングを含む構造体をリセットするために delete を使用することは避けてください。

9. 戻り値の不一致

レベル:警告

説明:戻り値の名前と型が returns ステートメントで宣言されていますが、実際の戻り値は宣言内の変数と一致しません。

サンプル

関数 f() は戻り値の型と名前を uint a として定義しており、return ステートメントは直接 100 を返しますが、これは return ステートメントと一致しません。

推奨される修正: return ステートメントの値が returns ステートメントの return ステートメントと一致していることを確認してください。

10. 基本クラスのコンストラクターを再利用する

レベル:警告

説明:コントラクト間では継承が許可されており、子コントラクトは親コントラクトの状態変数、関数、およびコンストラクターを継承します。サブコントラクトが複数のコンストラクターを継承する場合、コンストラクターは複数回再利用される場合があります。

サンプル

Test1 と Test2 はどちらもコントラクト test を継承するサブコントラクトであり、コンストラクターを再利用してそれぞれの状態変数 a を 1 と 2 に初期化します。コントラクト Test3 はコントラクト Test1 と Test2 を継承するため、2 つの異なるコンストラクターがあり、結果として Test3 になります。状態変数 a は複数回割り当てられ、最終的に値 2 が割り当てられます。

提案される修正:サブコントラクトに一意に継承されたコンストラクターがあることを確認してください。

2つの標準仕様テスト

1. 未チェックの転送動作

レベル:エラー

説明: ERC20規格のtransfer/transferFromインターフェースをコントラクトで定義している場合、transfer/transferFromインターフェースの戻り値を確認する必要があり、これを確認しないと転送状態の判定を誤ることになります。

サンプル

token.transferFrom(msg.sender, address(this), amount); の戻り値を確認する必要があります。

修復提案:すべての伝達関数の結果を確認します。

2. 間違った ERC20 インターフェイス

レベル:警告

説明:標準 ERC20 インターフェイスを定義する場合、標準 ERC20 インターフェイスと完全には一致しません。

サンプル

ERC20 標準の転送イベントは、event Transfer(address indexed from, address indexed to, uint256 value); です。

修復提案: ERC20 イベントとインターフェイスを ERC20 標準に従って完全に設定します。

3. 間違った ERC721 インターフェイス

レベル:警告

説明:定義された標準 ERC721 インターフェイスは、標準 ERC721 インターフェイスとまったく同じではありません。

サンプル

関数 ownerOf(uint256 tokenId) は ERC721 のインターフェイスですが、パラメータや戻り値がありません。

修理提案: ERC721と比較してください

THREE 関数呼び出しの検出

1 制御されたプロキシ呼び出し

レベル:エラー

説明:デリゲート呼び出しは、コントラクトを呼び出す方法です。デリゲート コールの操作スペースはコールが開始される側にあるため、権限制御のないコールや不明なコール アドレスはハッキングされる可能性があります。

サンプル

addr は呼び出し側が任意に操作できます。

修復提案: delegatecall が実行される関数のアクセス許可制御を設定し、呼び出し元を指定します。

2. 未チェックの基礎となる呼び出し

レベル:エラー

説明:スマート コントラクトの基礎となる呼び出しには戻りデータがあります。呼び出しコントラクトの実行に失敗しても、通話開始コントラクトの実行は失敗しません。呼び出し操作が失敗し、戻り値がチェックされない場合、次のような違いが生じる可能性があります。期待されるロジックと実際の状態。

サンプル

address(f).call(abi.encodePacked(function_selector)); は、コントラクト Base 内の関数 f() への呼び出しを実現します。ただし、call を使用すると呼び出しの戻り値が検証されないため、呼び出しの状態を判断できなくなります。

修復提案:基礎となるすべての呼び出しメソッドの戻り値を確認してください。

3. 送信方法のチェックを外した場合

レベル:エラー

説明:スマート コントラクトの転送関数 send には戻り値があり、転送が失敗してもコードは実行を継続し、呼び出しによって状態はロールバックされません。したがって、send を使用して送金する場合は戻り値を確認し、送金が成功したかどうかを判断するために使用する必要があります。

サンプル

関数 f は send を使用して ether を転送しますが、send の戻り値が検証されていないため、本当に転送が成功したかどうかはわかりません。

修復提案: Send を使用して送金する場合は、戻り値を確認してください。

4. ボトムコール

レベル:情報

説明:低レベルの呼び出しを使用するのは危険です。低レベルの呼び出しでは、コードの存在や呼び出しの成功はチェックされません。

修復提案:低レベルの呼び出しを避ける

4つのビジネスロジックのセキュリティ検出

1. 転送先アドレスが不明

レベル:エラー

説明:譲渡機能には権限制限はなく、譲渡先を設定することができ、誰でも契約資金を取得することができます。

サンプル

関数 f() には権限制御がなく、転送の受信者は msg.sender です。f() を呼び出して、コントラクトのすべての資金を取得します。

修正提案:コントラクトに外部転送機能がある場合、含まれている転送機能に正しい権限制御を追加します。

2. 動的配列長の変更

レベル:エラー

説明: solc バージョン 0.6.0 より下では、動的配列型の長さ情報を直接変更でき、長さ情報の変更は格納されている配列データに直接影響します。

サンプル

コントラクトがデプロイされた後、動的配列 a のデータ a[20] の 20 番目のビットは 1 になります。 f(10) を呼び出して a の長さを 10 に変更すると、a[20] が指す値は次のようになります。失った。

修復の提案:動的配列の長さの直接的または間接的な変更は避けてください。

3. 列挙型は控えめに使用する

レベル:エラー

説明:バージョン 0.4.5 より前では、列挙型の呼び出しではオーバーフロー判定が行われません。

サンプル

E は長さ 3 の enum 型なので、E の 10 番目を読み取ろうとしても、bug() 関数は回復しません。

修復提案:バージョン 0.4.0 ~ 0.4.4 の solc コンパイラの使用を避けるか、列挙値の間隔判定を実行します。

4. ETHをロックする契約

レベル:エラー

説明:スマートコントラクトにはイーサ通貨を受け取る機能はありますが、通貨を発行する機能がないため、イーサ通貨はコントラクト内にロックされてしまいます。

サンプル

関数 f() には支払い可能なシンボルがありますが、コントラクトにはイーサを使用/転送する機能がありません。

修正提案:入金機能のpayable属性を削除するか、Etherを消費/外部へ送金できる機能を追加してください。

5. 間違ったデコレータ

レベル:エラー

説明:デコレータは状態/権限コントロールとして機能します。デコレータ内の _; コード セグメントに到達できない場合、関数は実行できず、論理エラーが発生します。

サンプル

修飾子 bug1() には if 文があり、 bool_test が false の場合、 _; に到達しない場合、関数 use() は使用されません。

修復の提案:デコレータが _; コード セグメントに到達できることを確認し、デコレータ関数を正しく実行してください。

6. 戻り値がありません

レベル:エラー

説明:関数の return ステートメントに戻り値がありますが、対応する return 実装がありません。

サンプル

関数 f() は uint 型の値を返すように宣言されており、コントラクトには関数本体に return キーワードがありません。そのため、0 (uint 型の最小値) が返されます。

修正の提案:対応する戻り値を追加するか、return ステートメントを削除します。

7. 再入リスク

レベル:エラー

説明:外部コントラクトを呼び出す主な危険の 1 つは、外部コントラクトが制御フローを乗っ取る可能性があることです。リエントランシー攻撃 (別名、再帰呼び出し攻撃) では、関数への最初の呼び出しが完了する前に、悪意のあるコントラクトが呼び出し側コントラクトにコールバックします。これにより、関数のさまざまな呼び出しが望ましくない形で相互作用する可能性があります。呼び出し後に主要な状態変数を変更すると、再入の危険が生じやすくなります。

サンプル

関数 f() がアドレスの所有量を判断した後、呼び出しを使用して ether を送信し、最終的に転送操作の後にストレージ変数 book が変更されます。したがって、攻撃者はループ内で f() を呼び出してイーサを引き出すことができます。

修復提案:再突入攻撃を回避するには、check-validate-interactive モードを使用してください。

8. 契約自爆機能

レベル:エラー

説明:コントラクトには自己破壊機能が含まれており、認証を使用しないため、コントラクトは不安定な状態になります。

サンプル

f() を呼び出すことで、誰でもコントラクトを破棄し、コントラクト内の資金を引き出すことができます。

修復の提案:自己破壊機能の使用を避けるか、正しい権限制御を追加してください。

9. コンストラクター内に初期化されていない関数ポインターがあります

レベル:エラー

説明:コントラクトのコンストラクターに初期化されていない関数ポインターがあり、これらのポインターを直接呼び出すとエラーが発生します。

サンプル

f はコンストラクター内の関数ポインターであり、関数ポインターが完全に実現される前に呼び出されます。この動作により、展開が失敗します。

修正提案:関数ポインターが完全に実体化されるまで、関数ポインターを呼び出さないでください。

10. 初期化されていない状態変数

レベル:エラー

説明:初期化されていない状態変数を使用すると、論理エラーが発生する可能性があります。

サンプル

状態変数 a は初期化されていないため、デフォルトでアドレス 0 に設定されます。転送操作が実行されると、イーサは失われます (転送は 0x0 アドレスに行われます)。

修正提案:状態変数を宣言するときに、可能な限り状態変数を初期化します。

11. ハッキング可能なアップグレード契約

レベル:エラー

説明:コントラクトには自己破壊関数が含まれており、初期化関数は誰でも呼び出すことができます。

サンプル

関数Initialize()はコントラクトを初期化しますが、誰でも呼び出すことができます。攻撃者が所有者よりも先にinitialize()を呼び出した場合、攻撃者はいつでもkill()を呼び出してプロキシコントラクトの機能を無効にすることができます。

修復提案:コントラクト内のコンストラクターで初期化関数 function を実行して、所有者が任意に変更されないようにします。

12. アサーションエラー

レベル:エラー

説明: assert の制約を満たす必要があります。

修復の提案:コード ロジックを確認して問題を見つけて修正してください。

13. 整数オーバーフロー

レベル:エラー

説明:オーバーフローとは、演算の結果が結果の型で表現できる上限を超えることを意味します。

修正提案:オーバーフロー判定を追加するか、計算に SafeMath ライブラリを使用してください。

14. 整数のアンダーフロー

レベル:エラー

説明:アンダーフローは、計算操作の結果が結果の型で表現できる下限を超えていることを示します。

修復提案:アンダーフロー判定を追加するか、SafeMath を使用してください。

上記では少数のケースのみを選択しました

セキュリティ検出項目をさらに表示する

次の Web サイトをコピーして読むことができます

https://beosinofficial.gitbook.io/vaas-zhong-wen/

成都蓮安の最も強力な「単一製品」の 1 つ

Lianbitest v3.1 強力な高度な

申請の最初のバッチが開始されました

wx を追加: qiuqiupapa520

試用版のリンクを送ってもらうよう依頼する

おすすめ

転載: blog.csdn.net/CDLianan/article/details/124450479
おすすめ