効率的なロックフリー参照カウント構造: lockref

ロック参照

  lockref は、スピンロックと参照カウント変数を連続した整列された 8 バイトに結合する手法です。

lockref 構造体

struct lockref
{
    union
    {
#ifdef __LOCKREF_ENABLE_CMPXCHG__
        aligned_u64 lock_count; // 通过该变量的声明,使得整个lockref的地址按照8字节对齐
#endif
        struct
        {
            spinlock_t lock;
            int count;
        };
    };
};

特性説明

  負荷が高い状態では、システムは頻繁に「ロック - 参照変数の変更 - ロック解除」操作を実行するため、その間にスピンロックと参照カウント クロス キャッシュ ラインが発生する可能性が高く、パフォーマンスが大幅に低下します。Lockref は、アラインメントを強制することで占有されるキャッシュ ラインの数を可能な限り減らし、パフォーマンスを向上させます。

  さらに、x64 アーキテクチャーでは、ロックフリーの高速パスも cmpxchg() 命令によって実装されます。参照カウントの値は、スピン ロックをロックせずに変更できるため、パフォーマンスがさらに向上します。ファスト パスが存在しない場合 (サポートされていないアーキテクチャの場合)、または試行がタイムアウトになると、「ロック - 参照変数の変更 - ロック解除」操作に劣化します。このとき、lockref の強制アライメントにより、1 つのキャッシュ ラインのみが関与するため、パフォーマンスは元の spinlock+ref_count モードよりも高くなります。

cmpxchg_loop について

  参照カウントを変更する場合、cmpxchg は、最初に他のスレッドがロックを保持していないことを確認し、次に参照カウントを変更します。同時に、変更が命令によって発生したときに他のスレッドがロックを保持していないことを確認し、現在のlock cmpxchgターゲットの値を確認します。 lockref は古い変数に格納されるため、新しい値がターゲット lockref に格納されます。このロックフリー操作により、パフォーマンスが大幅に向上します。上記の条件が満たされない場合、複数回の試行の後、参照カウントを変更する従来のロック方法に退化します。

DragonOS での実装

DragonOS の実装はkernel/lib/lockref.cにあります。

参考文献

  lockref の紹介 – LWN.net、Jonathan Corbet

再版のソースを示してください:効率的なロックフリー参照カウント構造: lockref | | Longjin のブログ

私の公開アカウント「Denglong」に注目してください。一緒にもっと多くのことを知らせてください〜

おすすめ

転載: blog.csdn.net/qq_34026204/article/details/127192485