SYNOPSIS

$GIT_DIR/index

DESCRIPTION

Git インデックス形式(index format)

The Git index file has the following format

すべての2進数はネットワークバイトオーダーです。 従来の SHA-1 を使用するリポジトリでは、以下で説明するチェックサムとオブジェクトID (オブジェクト名) はすべて SHA-1 を使用して計算されます。 同様に、SHA-256 リポジトリでは、これらの値は SHA-256 を使用して計算されます。 特に断りのない限り、ここではバージョン 2 について説明します。

  • 12バイトのヘッダー は以下から構成されます

    • 4バイト シグネチャ:

      シグネチャは { D, I, R, C } (「dircache」の略)

    • 4バイト バージョン番号:

      現在サポートしているバージョンは 2 と 3 と 4 です。

    • 32ビット インデクスエントリの数

  • ソートされたインデックスエントリの数(下記参照)。

  • 拡張機能(extensions)

    拡張機能(extensions)はシグネチャによって識別されます。 オプションの拡張機能(extensions)は、Git が理解できない場合は無視できます。

    • 4バイト 拡張機能シグネチャ。最初のバイトが AZ の場合は、その拡張機能はオプションで、無視する事ができます。

    • 32ビット 拡張機能(extension)のサイズ

    • 拡張機能データ

  • このチェックサムより前のインデックスファイルの内容に対するハッシュチェックサム。

Index entry

インデックスエントリは名前フィールドで昇順にソートされ、符号なしバイト(unsigned bytes)の文字列(string)として解釈されます(つまり、 memcmp() 順で、ローカライズなしで、ディレクトリセパレータ / という特別な場合は無し)。 同一名のエントリでは、それらのステージフィールド(stage field)によってソートされます。

通常、インデックスエントリはファイルを表します。 ただし、コーンモードでスパースチェックアウトが有効(core.sparseCheckoutCone が有効)で、 extensions.sparseIndex 拡張機能が有効な場合、インデックスにはスパースチェックアウト定義外のディレクトリのエントリが含まれる場合があります。 これらのエントリのモードは「040000」で、「SKIP_WORKTREE」ビットが含まれ、パスはディレクトリセパレータで終わります。

  • 32ビット ctime秒。ファイルのメタデータが最後に変更された時刻

    これは stat(2) のデータです

  • 32ビット ctime のナノ秒部分

    これは stat(2) のデータです

  • 32ビット mtime 秒。ファイルのデータが最後に変更された時刻

    これは stat(2) のデータです

  • 32ビット mtime のナノ秒部分

    これは stat(2) のデータです

  • 32ビット dev

    これは stat(2) のデータです

  • 32ビット ino

    これは stat(2) のデータです

  • 32ビット モード。以下の通り分割されています(高位からから低位ビットの順です)

    • 4ビット オブジェクトタイプ

      有効な値は、2進数で 1000 (通常のファイル)と、1010 (シンボリック リンク)と、1110 (gitlink) です。

    • 16ビット 未使用。0でなければならない

    • 4ビット オブジェクトタイプ

      有効な値は、2進数で 1000 (通常のファイル)と、1010 (シンボリック リンク)と、1110 (gitlink) です。

    • 3ビット 未使用。0でなければならない

  • 32ビット uid

    これは stat(2) のデータです

  • 32ビット gid

    これは stat(2) のデータです

  • 32ビット ファイルサイズ

    これは stat(2) からのディスク上のサイズで、32ビットに切り捨て(truncate)られます。

  • 表現されたオブジェクトのオブジェクト名

  • 16ビットの「flags」フィールドは以下のように分割されています(高位ビットから低位ビットへの順です)

    • 1ビット assume-valid フラグ

    • 1ビット extended フラグ(バージョン2ではゼロでなければなりません)

    • 2ビット ステージ(マージ作業中のステージ)

    • 12ビット 名前の長さ(長さが 0xFFF 未満の場合)、それ以外の場合、このフィールドには 0xFFF が格納されます。

      (バージョン3以降) 16ビットフィールド。上記の「extended flag」が 1 の場合にのみ適用され、以下のように分割されます(上位ビットから下位ビットの順)

    • 1ビット 将来の為に予約

    • 1ビット skip-worktree フラグ(スパースチェックアウトで使用)

    • 1ビット intent-to-add フラグ(「git add -N」で使用)

    • 13ビット 未使用。0でなければならない

  • 最上位ディレクトリに対するエントリ パス名 (可変長) (先頭のスラッシュなし)。 / はパス区切りとして使用されます。 特別なパスコンポーネント ....git (引用符なし) は許可されていません。 末尾のスラッシュも許可されていません。

    正確なエンコーディングは未定義ですが、 ./ 文字は 7ビットASCII でエンコードされ、エンコードに NUL バイトを含めることはできません (つまり、これは UNIX パス名です)。

    (バージョン 4) バージョン 4 では、 エントリのパス名は、 前のエントリのパス名に対してプレフィックス圧縮されます(最初のエントリは、 前のエントリのパス名が空の文字列であるかのようにエンコードされます)。 エントリの先頭に、 可変幅エンコーディング(オフセットと同じエンコーディングが OFS_DELTA パック・エントリにエンコードされます。 gitformat-pack(5) 参照)の整数 N が格納され、その後に NUL で終了する文字列 S が続きます。 前のエントリのパス名の末尾から N バイトを削除し、 文字列 S に置き換えると、このエントリのパス名が生成されます。

  • 1~8個の nul バイト。 名前を NUL で終了させたまま、必要に応じて 1~8個の nul バイト を使用して エントリを 8 バイトの倍数にパディングします。

    (バージョン 4)バージョン4では、パス名の後のパディングは存在しません。

分割インデックスモードでのインデックス エントリの解釈は、まったく異なります。 詳細については、下記を参照してください。

拡張機能(extensions)

Cache tree

インデックスはディレクトリのエントリを記録しないため、キャッシュエントリは、既存のコミットから変更されていないインデックスの領域のオブジェクトデータベースに既に存在するツリーオブジェクトを記述することはできません。 キャッシュツリー拡張機能は、既に存在し、キャッシュエントリのセクションと完全に一致するツリーを記述する再帰的なツリー構造を格納します。 これにより、そのコミットに対して「新しい」ツリーのみを計算することで、新しいコミットのインデックスからのツリー オブジェクトの生成が高速化されます。 また、ツリーの比較で同等性が示される場合にインデックスのセクションをスキップできるため、インデックスを HEAD^{tree} などの別のツリーと比較する場合にも役立ちます。

再帰的なツリー構造は、多数の キャッシュエントリや、サブノードのリストや、オブジェクトID(OID) を格納するノードを使用します。 OID は、そのノードの既存のツリーが存在することがわかっている場合、それを参照します。 サブノードは、それ自体がキャッシュツリーノードを持つサブディレクトリに対応します。 キャッシュエントリの数は、そのツリーのディレクトリ内のパスを記述するインデックス内のキャッシュエントリの数に対応します。

拡張機能は、キャッシュツリー拡張機能で全体のディレクトリ構造(full directory structure)を追跡しますが、これは通常、全体のキャッシュエントリリスト(full cache entry list)よりも小さくなります。

インデックスでパスが更新されると、Gitはそのパスの親ディレクトリに対応する再帰キャッシュツリーのすべてのノードを無効にします。 キャッシュエントリの数として「-1」を使用して、これらのツリーノードを「無効」として保存します。 無効なノードは引き続き一連のインデックスエントリを格納するため、Git は完全なキャッシュツリーを再構築する際にその作業に集中できます。

  • この拡張機能のシグネチャは { T, R, E, E } です。

  • 一連のエントリの連なりで拡張機能全体を満たします。これは以下のものから構成されています:

    • NUL終端のパスコンポーネント(その親ディレクトリからの相対指定);

    • ASCII文字による10進数の数値 このエントリが表すツリーによってカバーされるインデックス内のエントリの数 (entry_count);

    • 空白1つ(ASCII 32);

    • ASCII文字による10進数の数値。このツリーが持っているサブツリーの数をあらわします。

    • 改行(newline)(ASCII 10);

    • オブジェクト名。この範囲のインデックスをツリーとして書き込んだ結果となるオブジェクトのオブジェクト名。

エントリは無効化された状態にある可能性があり、entry_count フィールドに負の数があることで表されます。 この場合、オブジェクト名はなく、改行(newline)の直後に次のエントリが開始されます。 無効なエントリを書き込む場合、entry_count として常に「-1」を使用する必要があります。

エントリは、上から下へ、深さ優先の順序で書き出されます。 最初のエントリはリポジトリのルート レベルを表し、ルートレベルの最初のサブツリー(これをAとする)(これはルートレベルに相対的な名前です)が続き、さらに A の最初のサブツリー(これはAに相対的な名前です)が続きます。 サブツリーの指定された数は、再帰スタックの現在のレベルがいつ完了するかを示します。

Resolve undo

競合は、より高いステージのエントリのセットとしてインデックスで表されます。 (「git add path」などを使用して)競合が解決されると、これらの上位ステージのエントリが削除され、適切な解決策を持つ ステージ 0 エントリが追加されます。

これらのより高いステージのエントリが削除されると、解決前に戻す拡張機能(the resolve undo extension)に保存されるため、ユーザーが最初から競合解決をやり直したい場合に備えて、競合を再作成できます (たとえば、「git checkout -m」を使用)。

  • この拡張機能のシグネチャは { R, E, U, C } です。

  • 一連のエントリの連なりで拡張機能全体を満たします。これは以下のものから構成されています:

    • エントリを説明する、NULで終わるパス名(リポジトリのルートからの相対、つまりフルパス名)

    • 3つのNULで終わるASCII文字による8進数値。ステージ1〜3でのエントリのエントリモード(欠落しているステージは、このフィールドでは「0」で表されます)

    • ステージ1〜3でのエントリの最大3つのオブジェクト名(欠落しているステージには何も書き込まれません)。

Split index

分割インデックス モードでは、インデックスエントリの大部分を別のファイルに保存できます。 この拡張機能は、最終的なインデックスを生成するために加えられる変更を記録します。

  • この拡張機能のシグネチャは { l, i, n, k } です。

  • この拡張機能は以下から構成されます:

    • 共有インデックスファイルのハッシュ。 共有インデックスファイルのパスは $GIT_DIR/sharedindex.<hash> です。 すべてのビットが 0 の場合、インデックスは共有インデックスファイルを必要としません。

    • ewahでエンコードされた削除ビットマップで、各ビットは共有インデックス内のエントリを表します。ビットが設定されている場合、共有インデックス内の対応するエントリが最終インデックスから削除されます。 削除操作はインデックス エントリの位置を変更しますが、置換フェーズでは元の位置が必要になるため、エントリを削除するようにマークし、置換後に一括削除を実行することをお勧めします。

    • ewahでエンコードされた置換ビットマップで、各ビットは共有インデックス内のエントリを表します。 ビットが設定されている場合、共有インデックス内の対応するエントリは、このインデックス ファイル内のエントリに置き換えられます。 置換されたすべてのエントリは、このインデックスに並べ替えられた順序で格納されます。 置換ビットマップの最初の「1」ビットは最初のインデックス エントリに対応し、2 番目の「1」ビットは 2 番目のエントリに対応し、以下同様です。 スペースを節約するために、置換されたエントリのパス名が空の場合があります。

置き換えられた後の残りのインデックスエントリは、最終的なインデックスに追加されます。 これらの追加されたエントリも、エントリ名、ステージの順でソートされます。

Untracked cache

未追跡キャッシュ(untracked cache)は、未追跡ファイルのリストと、キャッシュを検証するために必要なデータを保存します。 この拡張機能(extension)のシグネチャは {U, N, T, R } です。

この拡張機能は以下から始まります

  • 可変長エンコーディング(variable width encoding)のシーケンスのサイズが前に付いた、NUL で終了する文字列のシーケンス。 各文字列には、キャッシュを使用できる環境が記述されています。

  • $GIT_DIR/info/exclude の統計(stat)データ。 ctime フィールドから「file size」までの「Index entry」セクションを参照してください。

  • core.excludesFileの統計(stat)データ

  • 32ビット dir_flags (struct dir_struct 参照)

  • $GIT_DIR/info/exclude の ハッシュ。 nullハッシュは、ファイルが存在しないことを意味します。

  • core.excludesFile のハッシュ。 null ハッシュは、ファイルが存在しないことを意味します。

  • ディレクトリごとの除外ファイル名の NUL で終わる文字列。 これは通常「.gitignore」です。

  • 次のディレクトリブロックの数、可変長エンコーディング(variable width encoding)。 この数がゼロの場合、拡張機能(the extension)は、ここに続く NUL で終わりです。

  • 深さ優先検索順(depth-first-search order)のディレクトリブロックの数。これは以下から構成されます

    • 未追跡エントリ(untracked entries)の数。可変長エンコーディング。

    • サブディレクトリブロックの数。可変長エンコーディング。

    • NUL終端されたディレクトリ名。

    • NUL終端された 未追跡ファイル名/未追跡ディレクトリ名 の数。

各ディレクトリブロックの残りのデータは、タイプ別にグループ化されます:

  • ewah ビットマップでは、n番目のビットは、n番目のディレクトリに未追跡の有効なキャッシュエントリがあるかどうかを表します。

  • ewah ビットマップでは、n番目のビットは、n番目のディレクトリの read_directory_recursive() の「check-only」ビットを記録します。

  • ewah ビットマップでは、n番目のビットは、ハッシュと統計(stat)データがn番目のディレクトリで有効であり、次のデータに存在するかどうかを表します。

  • 統計(stat)データの配列。 n番目のデータは、この前にあるewahビットマップのn番目の「1」ビットに対応します。

  • ハッシュの配列。 n番目のハッシュは、この前のewahビットマップのn番目の「1」ビットに対応します。

  • 1つのNUL。

File System Monitor cache

ファイルシステムモニター キャッシュは、 core.fsmonitor フックが変更を通知したファイルを追跡します。 この拡張機能のシグネチャは { F, S, M, N } です。

この拡張機能は以下から始まります

  • 32ビット version number: 現在サポートするバージョンは 1 と 2 です。

  • (バージョン 1)

    64ビット time: 拡張機能データは、1970年1月1日午前0時からの経過ナノ秒として格納されている指定の時間までのすべての変更を反映します。

  • (バージョン 2)

    NULL終端文字列: ファイルシステムモニター アプリケーションによって定義される不透明な(opaque)トークン。 拡張機能データには、そのトークンに関連するすべての変更が反映されます。

  • 32ビット bitmap size: CE_FSMONITOR_VALIDビットマップのサイズ。

  • ewah ビットマップでは、n 番目のビットは、n 番目のインデックス エントリが CE_FSMONITOR_VALID では無いかどうかを表します。

End of Index Entry

インデックスエントリの終わり(End of Index Entry;EOIE)は、可変長インデックスエントリの終わりと拡張機能の始まりを見つけるために使用されます。プログラムコードはこれを利用して、すべてのインデックスエントリを解析しなくてもインデックス拡張をすばやく見つけることができます。

可変長キャッシュエントリやその他のインデックス拡張の前にロードできる必要があるため、この拡張機能は最後に書き込む必要があります。この拡張機能のシグネチャは { E, O, I, E } です。

この拡張機能は以下から構成されます:

  • 32ビット インデックス エントリの末尾までのオフセット

  • 拡張機能のタイプとそのサイズをハッシュします(ただし、その内容はハッシュしません)。 例えば。 N バイト長の「TREE」拡張機能、M バイト長の「REUC」拡張機能の後に「EOIE」が続く場合、ハッシュは以下のようになります:

    Hash("TREE" + <Nの2進数表現>
    "REUC" + <Mの2進数表現>)

Index Entry Offset Table

インデックスエントリオフセットテーブル(Index Entry Offset Table;IEOT)は、キャッシュエントリをディスク上のフォーマットからメモリ上のフォーマットに変換する処理のマルチスレッド化を有効にすることで、インデックスをロードするための CPU コストに対処するために使用されます。 この拡張機能のシグネチャは { I, E, O, T } です。

この拡張機能は以下から構成されます:

  • 32ビット version (現在 1)

  • インデックスオフセットエントリの数。以下から構成されます:

    • 32ビット。ファイルの先頭から、このエントリブロック内の最初のキャッシュエントリまでのオフセット。

    • 32ビット。このブロック内のキャッシュエントリの数

Sparse Directory Entries

sparse-checkout をコーンモードで使用する場合、ツリー内の展開されたパスのリスト全体ではなく、ツリー オブジェクトをポイントすることで、インデックス内の一部のディレクトリ全体を要約できます。 このようなエントリを含むインデックスは「スパースインデックス」です。 インデックス フォーマット バージョン 4 以前は、このようなエントリを考慮して実装されていませんでした。 したがって、これらのバージョンでは、スパース ディレクトリ エントリを含むインデックスには、この拡張機能とシグネチャ { s, d, i, r } が含まれます。 分割インデックス拡張機能と同様に、ツールは、この拡張機能を理解していない限り、スパースインデックスとのやり取りを避ける必要があります。

GIT

Part of the git(1) suite