FastDDS ソースコード分析: DataWriter 分析

目次

データライター分析

DataWriter クラスの分析

DataWriterImpl クラスの分析

主要機能分析


データライター分析
DataWriter クラスの分析

DataWriter クラスは Fast DDS ライブラリの重要なクラスであり、DDS (Data Distribution Service) パブリッシュ/サブスクライブ通信モデルにおけるデータ書き込み機能を実装するために使用されます。

目的:
DataWriter クラスは、特定のトピック (トピック) にデータを公開するために使用されます。これは、トピックにデータを書き込み、トピックにサブスクライブされたデータ リーダー (DataReader) にデータを送信する役割を果たします。 DataWriter を通じて、ユーザーはデータの公開、データ インスタンスの登録と登録解除、ステータス情報の取得、データ書き込みの QoS (サービス品質) の設定を行うことができます。

メンバー変数:

  • impl_: DataWriter の実際の実装である DataWriterImpl クラスのインスタンスへのポインタ。

メンバー関数:
DataWriter クラスには複数のメンバー関数が用意されています。いくつかの重要な関数とその関数を次に示します。

  • Enable(): データライターを有効にします。
  • write(data): トピックにデータを書き込みます。
  • register_instance(instance): データインスタンスを登録します。
  • unregister_instance(instance): データ インスタンスの登録を解除します。
  • get_key_value(key_holder, handle): データ インスタンスのキー値を取得します。
  • set_qos(qos): データ書き込みの QoS を設定します。
  • get_qos(): 現在のデータ書き込みの QoS を取得します。
  • set_listener(listener): データ書き込み用のリスナーを設定します。
  • get_topic(): 関連するトピックを取得します。
  • get_publisher(): データ ライターを作成したパブリッシャーを取得します。

大まかな実装方法:
DataWriter クラスの実装方法は、主に基礎となる DataWriterImpl クラスに依存します。 DataWriterImpl クラスは DataWriter の実際の実装であり、データ書き込みに関連する基礎となるロジックと操作をカプセル化します。 DataWriter のメンバ関数では、DataWriterImpl の対応するメンバ関数を呼び出すことで対応する操作が完了します。たとえば、write(data) 関数では、DataWriterImpl の write(data) 関数を呼び出して、実際にデータの書き込み操作を実行します。

同時にDataWriterクラスは、loan_sample関数やdiscard_loan関数を通じて内部プール内のデータサンプルを直接借用・返却する機能や、データ書き込みのステータス情報を取得する機能なども提供します。

以下は詳細な方法の説明です

このクラスは本質的に単なるラッパー クラスであるため、主要な関数は基本的に DataWriterImpl クラスによって実装されます。

DataWriterImpl クラスの分析

クラス図

DataWriterImpl クラスは Fast DDS ライブラリの主要なクラスであり、データ書き込み関数の実装に使用されます。これには、データ書き込みに関連する操作とステータス、および基礎となる通信層 (RTPS) との対話が含まれます。以下は、このクラスとその機能の役割と一般的な実装の概要です。

  • DataWriterImpl(PublisherImpl*, TypeSupport, Topic*, const DataWriterQos&, DataWriterListener*): DataWriterImpl オブジェクトを作成し、そのメンバー変数を初期化するために使用されるクラスのコンストラクター。
  • ~DataWriterImpl(): クラスのデストラクターは、リソースをクリーンアップしてメモリを解放するために使用されます。
  • Enable(): DataWriterImpl オブジェクトを有効にし、基礎となるエンティティ (RTPSWriter) を作成します。
  • loan_sample(void*, LoanInitializationKind): データを書き込むために内部プールからサンプルを借用します。
  • Discard_loan(void*&): 以前に借用したサンプルを破棄します。
  • write(void*): トピックにデータを書き込みます。
  • write(void*, fastrtps::rtps::WriteParams&): 書き込みパラメーターを使用して、トピックにデータを書き込みます。
  • write(void*, const InstanceHandle_t&): 指定されたインスタンスにデータを書き込みます。
  • write_w_timestamp(void*, const InstanceHandle_t&, const fastrtps::Time_t&): タイムスタンプを使用して、指定されたインスタンスにデータを書き込みます。
  • register_instance(void*): 新しいインスタンスを登録し、インスタンスのハンドルを返します。
  • register_instance_w_timestamp(void*, const fastrtps::Time_t&): タイムスタンプを使用して、新しいインスタンスを登録し、インスタンスのハンドルを返します。
  • unregister_instance(void*, const InstanceHandle_t&, bool = false): 指定されたインスタンスの登録を解除します。
  • unregister_instance_w_timestamp(void*, const InstanceHandle_t&, const fastrtps::Time_t&, bool = false): タイムスタンプを使用して、指定されたインスタンスをログアウトします。
  • guid(): DataWriter の GUID を取得します。
  • get_instance_handle(): DataWriter のインスタンス ハンドルを取得します。
  • get_type(): データ型サポート オブジェクトを取得します。
  • get_qos(): DataWriter の QoS 設定を取得します。
  • get_topic(): DataWriter に関連付けられたトピックを取得します。
  • get_listener(): DataWriterのリスナーを取得します。
  • set_listener(DataWriterListener*): DataWriterのリスナーを設定します。
  • get_publication_matched_status(PublicationMatchedStatus&): パブリケーションの一致ステータスを取得します。
  • get_offered_deadline_missed_status(OfferedDeadlineMissedStatus&): 未達成の期限ステータスを取得します。
  • get_offered_incompatibility_qos_status(OfferedIncompatibilityQosStatus&): 非互換の QoS ステータスを取得します。
  • set_qos(const DataWriterQos&): DataWriter の QoS 構成を設定します。
  • get_liveiness_lost_status(LiveinessLostStatus&): 失われた活力のステータスを取得します。
  • get_publisher(): 関連付けられたパブリッシャーを取得します。
  • assert_liveiness(): 活性をアサートします。
  • disable(): DataWriterImpl オブジェクトを無効にし、すべてのリスナーを削除します。
  • clear_history(size_t*): 履歴内のすべてのデータをクリアします。
  • get_sending_locators(rtps::LocatorList&): DataWriter がデータを送信できるロケーターのリストを取得します。
  • filter_is_being_removed(const char*): フィルターが削除されたときに呼び出されるメソッド。
主要機能分析

書く

ReturnCode_t DataWriterImpl::write(void* データ)
{
    // DataWriter が既に使用されているかどうか
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    // 检查データが空かどうか
    if (data == nullptr)
    {
        return ReturnCode_t::RETCODE_BAD_PARAMETER;
    }

    // 检查データ共有共有可否
    if (is_data_sharing_compatibility_)
    {
        // 负ダウンロード池を使用してペイロードを割り当てます
        SerializedPayload_t ペイロード;
        if (!get_payload_pool()->get_payload(ペイロード))
        {
            return ReturnCode_t::RETCODE_OUT_OF_RESOURCES;
        }

        // 配列化データを负ダウンロード中
        if (!type_->serialize(data, &payload))
        {
            get_payload_pool()->release_payload(ペイロード);
            return ReturnCode_t::RETCODE_ERROR;
        }

        // 新しい変更を作成し、史记录に追加しました
        WriteParams wparams;
        ReturnCode_t ret = create_new_change_with_params(ALIVE, data, wparams);
        if (ret != ReturnCode_t::RETCODE_OK)
        {
            get_payload_pool()->release_payload(ペイロード);
            return ret;
        }

        // 設置负ダウンロード并配信変更
        CacheChange_t* 変更 =history_.get_last_added_change();
        Change->serializedPayload = ペイロード;
        Writer_->add_change(変更);
    }
    それ以外
    {
        // 内部ロード分配器を使用してペイロードを分配します
        std::unique_ptr<SerializedPayload_t> payload(new SerializedPayload_t());
        if (!payload || !get_payload_pool()->get_payload(*payload))
        {
            return ReturnCode_t::RETCODE_OUT_OF_RESOURCES;
        }

        // 配列化データを负ダウンロード中
        if (!type_->serialize(data, payload.get()))
        {
            get_payload_pool()->release_payload(*ペイロード);
            return ReturnCode_t::RETCODE_ERROR;
        }

        // 新しい変更を作成し、史记录に追加しました
        WriteParams wparams;
        ReturnCode_t ret = create_new_change_with_params(ALIVE, data, wparams);
        if (ret != ReturnCode_t::RETCODE_OK)
        {
            get_payload_pool()->release_payload(*ペイロード);
            return ret;
        }

        // 設置负ダウンロード并配信変更
        CacheChange_t* 変更 =history_.get_last_added_change();
        Change->serializedPayload = *payload;
        Writer_->add_change(変更);
    }

    return ReturnCode_t::RETCODE_OK;
}

書き込み関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. 次に、データが空かどうかを確認し、空の場合は RETCODE_BAD_PARAMETER を返します。
  3. 次に、データ共有の互換性に基づいて、異なる負荷ディストリビューターを使用することを選択します。
  4. データ共有に互換性がある場合は、ロード プールを使用して SerializedPayload_t オブジェクトを割り当て、データをペイロードにシリアル化します。
  5. 新しい変更を作成し、履歴に追加します。
  6. ペイロードを設定し、DataWriter に変更を追加します。
  7. データ共有に互換性がない場合、内部ロード アロケータを使用して SerializedPayload_t オブジェクトが割り当てられ、データがペイロードにシリアル化されます。
  8. 新しい変更を作成し、履歴に追加します。
  9. ペイロードを設定し、DataWriter に変更を追加します。
  10. RETCODE_OK が返された場合は、書き込み操作が成功したことを示します。

write_w_timestamp

ReturnCode_t DataWriterImpl::write_w_timestamp(void* データ, const fastrtps::Time_t& タイムスタンプ)
{
    // DataWriter が有効かどうかを確認します
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    // データが空かどうかを確認します
    if (data == nullptr)
    {
        return ReturnCode_t::RETCODE_BAD_PARAMETER;
    }

    // データ共有に互換性があるかどうかを確認する
    if (is_data_sharing_compatibility_)
    {
        // ロード プールを使用してペイロードを分散します
        SerializedPayload_t ペイロード;
        if (!get_payload_pool()->get_payload(ペイロード))
        {
            return ReturnCode_t::RETCODE_OUT_OF_RESOURCES;
        }

        // データをペイロードにシリアル化します
        if (!type_->serialize(data, &payload))
        {
            get_payload_pool()->release_payload(ペイロード);
            return ReturnCode_t::RETCODE_ERROR;
        }

        // 新しい変更を作成し、履歴に追加します
        WriteParams wparams;
        ReturnCode_t ret = create_new_change_with_params(ALIVE, data, wparams);
        if (ret != ReturnCode_t::RETCODE_OK)
        {
            get_payload_pool()->release_payload(ペイロード);
            return ret;
        }

        // タイムスタンプを設定し、変更を公開する
        CacheChange_t* 変更 =history_.get_last_added_change();
        Change->serializedPayload = ペイロード;
        Change->sourceTimestamp = タイムスタンプ;
        Writer_->add_change(変更);
    }
    それ以外
    {
        // 内部負荷分散装置を使用してペイロードを分散します
        std::unique_ptr<SerializedPayload_t> ペイロード(new SerializedPayload_t());
        if (!payload || !get_payload_pool()->get_payload(*payload))
        {
            return ReturnCode_t::RETCODE_OUT_OF_RESOURCES;
        }

        // データをペイロードにシリアル化します
        if (!type_->serialize(data, payload.get()))
        {
            get_payload_pool()->release_payload(*ペイロード);
            return ReturnCode_t::RETCODE_ERROR;
        }

        // 新しい変更を作成し、履歴に追加します
        WriteParams wparams;
        ReturnCode_t ret = create_new_change_with_params(ALIVE, data, wparams);
        if (ret != ReturnCode_t::RETCODE_OK)
        {
            get_payload_pool()->release_payload(*ペイロード);
            return ret;
        }

        // タイムスタンプを設定し、変更を公開する
        CacheChange_t* 変更 =history_.get_last_added_change();
        Change->serializedPayload = *payload;
        変更->sourceTimestamp = タイムスタンプ;
        Writer_->add_change(変更);
    }

    return ReturnCode_t::RETCODE_OK;
}

write_w_timestamp 関数の実装は、write 関数と非常によく似ています。違いは、データのタイムスタンプを指定するために使用される追加のパラメーター タイムスタンプを受け入れることです。

write_w_timestamp 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. 次に、データが空かどうかを確認し、空の場合は RETCODE_BAD_PARAMETER を返します。
  3. 次に、データ共有の互換性に基づいて、異なる負荷ディストリビューターを使用することを選択します。
  4. データ共有に互換性がある場合、ロード プールを使用して SerializedPayload_t オブジェクトが割り当てられ、データがペイロードにシリアル化されます。
  5. 新しい変更を作成し、履歴に追加します。
  6. タイムスタンプを設定し、DataWriter に変更を追加します。
  7. データ共有に互換性がない場合は、内部ロード アロケータを使用して SerializedPayload_t オブジェクトが割り当てられ、データがペイロードにシリアル化されます。
  8. 新しい変更を作成し、履歴に追加します。
  9. タイムスタンプを設定し、DataWriter に変更を追加します。
  10. RETCODE_OK が返された場合は、書き込み操作が成功したことを示します。


 

インスタンスの登録

ReturnCode_t DataWriterImpl::register_instance(void* キー)
{
    // DataWriter が有効かどうかを確認します
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    // キー値が空かどうかを確認します
    if (key == nullptr)
    {
        return ReturnCode_t::RETCODE_BAD_PARAMETER;
    }

    // キーが登録されているかどうかを確認します
    if (history_.key_exists(key))
    {
        return ReturnCode_t::RETCODE_PRECONDITION_NOT_MET;
    }

    // 新しい変更を作成し、履歴に追加します
    WriteParams wparams;
    ReturnCode_t ret = create_new_change_with_params(NOT_ALIVE_UNREGISTERED, key, wparams);
    if (ret != ReturnCode_t::RETCODE_OK)
    {
        return ret;
    }

    // インスタンスを履歴レコードに登録します
    CacheChange_t* 変更 =history_.get_last_added_change();
    History_.register_instance(変更, キー);

    return ReturnCode_t::RETCODE_OK;
}

register_instance 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. 次に、キー値が空かどうかを確認し、空の場合は RETCODE_BAD_PARAMETER を返します。
  3. 次に、キーが登録されているかどうかを確認し、すでに登録されている場合は RETCODE_PRECONDITION_NOT_MET を返します。
  4. 新しい変更を作成し、履歴に追加します。ここでは、create_new_change_with_params 関数を使用して新しい変更を作成します。変更タイプは NOT_ALIVE_UNREGISTERED で、データはキー値です。
  5. インスタンスを履歴に登録します。 register_instance 関数を呼び出して変更をキー値に関連付けると、履歴でインスタンスの状態を追跡できるようになります。
  6. RETCODE_OK が返された場合は、登録インスタンス操作が成功したことを示します。

History_ は、DataWriterImpl クラスのメンバー変数であり、DataWriter の変更履歴レコードを管理するために使用されるオブジェクトです。

History_ の目的は、DataWriter によって送信されたすべての変更を保存することです。 DataWriter が新しいデータを送信する必要がある場合は常に、新しい変更 (CacheChange_t オブジェクト) を作成し、それをhistory_ に追加します。履歴の変更をシーケンス番号で並べ替えることができるため、データは正しい順序で送信および送信されます。

履歴レコードを管理することにより、DataWriter は信頼性のサポート、履歴アクセス、データのバックトラッキングと再送信など、いくつかの重要な機能を実現できます。履歴レコードは、オンデマンド読み取り、履歴データ クエリ、データ フィルタリングなどの加入者のニーズに対応するためにも使用できます。

DataWriterImpl において、history_ は WriterHistory 型のオブジェクトであり、履歴変更記録を管理および維持する機能を実装します。 WriterHistory は、履歴変更を管理するために Fast DDS ライブラリによって提供される実装です。

History_ を使用することで、DataWriter は送信されたデータを追跡および管理し、データの信頼性と一貫性を確保し、柔軟な履歴アクセスおよびデータ処理機能を提供できます。

get_publication_matched_status

ReturnCode_t DataWriterImpl::get_publication_matched_status(PublicationMatchedStatus& ステータス)
{
    // DataWriter が既に使用されているかどうか
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    {
        std::unique_lock<RecursiveTimedMutex> lock(writer_->getMutex());

        // 取得PublicationMatchedStatus并复制给statusパラメータ
        status = Publication_matched_status_;

        // current_count_change と total_count_change を重ねます
        Publication_matched_status_.current_count_change = 0;
        Publication_matched_status_.total_count_change = 0;
    }

    // 対応する状態条件を設定します
    user_datawriter_->get_statuscondition().get_impl()->set_status(StatusMask::publication_matched(), false);

    return ReturnCode_t::RETCODE_OK;
}

get_publication_matched_status 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. std::unique_lock を使用して DataWriter のミューテックスをロックし、スレッドの安全性を確保します。
  3. Publication_matched_status_ を status パラメーターにコピーします。
  4. public_matched_status_ の current_count_change と total_count_change を 0 にリセットして、これらの変更が処理されたことを示します。
  5. user_datawriter_->get_statuscondition().get_impl()->set_status() を呼び出して、対応するステータス条件を設定し、publication_matched_status_ の変更をユーザーに通知します。
  6. RETCODE_OK が返された場合は、PublicationMatchedStatus が正常に取得されたことを示します。

DataWriter の現在の PublicationMatchedStatus は、この DataWriter に関連付けられたサブスクライバ (DataReader) の一致ステータスを表します。 PublicationMatchedStatus は、DataWriter に関連するサブスクライバー数の変化を記録します。

PublicationMatchedStatus 構造体には次のフィールドが含まれます。

  • total_count: DataWriter に関連付けられたサブスクライバーの合計数を示します。
  • total_count_change: 最後に PublicationMatchedStatus が取得されてからの購読者の合計数の変化を示します。
  • current_count: DataWriter に一致する現在のサブスクライバーの数を示します。
  • current_count_change: 最後に PublicationMatchedStatus が取得されてからの現在の購読者数の変化を示します。

PublicationMatchedStatus の変化を監視することで、DataWriter とサブスクライバー間のマッチング状況の変化を知ることができます。たとえば、新しいサブスクライバが DataWriter に一致すると、current_count と total_count が増加し、current_count_change フィールドと total_count_change フィールドをチェックすることで一致ステータスの変化を知ることができます。

次のような一部の機能は、PublicationMatchedStatus を使用して実現できます。

  • DataWriter とサブスクライバの接続ステータスを監視して、通信接続が正常に確立されているかどうかを判断します。
  • DataWriter に一致するサブスクライバーの数に基づいてデータ公開戦略を調整します。
  • PublicationMatchedStatus の変更に基づいて特定の操作またはコールバック関数をトリガーする

get_offered_deadline_missed_status

ReturnCode_t DataWriterImpl::get_offered_deadline_missed_status(OfferedDeadlineMissedStatus& ステータス)
{
    // DataWriter が既に使用されているかどうか
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    {
        std::unique_lock<RecursiveTimedMutex> lock(writer_->getMutex());

        // 取得OfferedDeadlineMissedStatus并复制给statusパラメータ
        status = Offered_deadline_missed_status_;

        // total_count と total_count_change を重ねます
        Offered_deadline_missed_status_.total_count_change = 0;
    }

    // 対応する状態条件を設定します
    user_datawriter_->get_statuscondition().get_impl()->set_status(StatusMask::offered_deadline_missed(), false);

    return ReturnCode_t::RETCODE_OK;
}

get_offered_deadline_missed_status 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. std::unique_lock を使用して DataWriter のミューテックスをロックし、スレッドの安全性を確保します。
  3. Offered_deadline_missed_status_ を status パラメーターにコピーします。
  4. Offered_deadline_missed_status_ の total_count_change を 0 にリセットして、変更が処理されたことを示します。
  5. user_datawriter_->get_statuscondition().get_impl()->set_status() を呼び出して、対応するステータス条件を設定し、OfferedDeadlineMissedStatus の変更をユーザーに通知します。
  6. RETCODE_OK が返された場合は、OfferedDeadlineMissedStatus が正常に取得されたことを示します。

OfferedDeadlineMissedStatus は、DataWriter の期限に達していないことを示します。このステータスは、定義された期限要件に従って時間内にデータを送信できなかった DataWriter の統計を記録します。

OfferedDeadlineMissedStatus 構造体には次のフィールドが含まれます。

  • total_count: DataWriter が開始されてから、期限に達したか、期限を超えた合計回数を示します。
  • total_count_change: 最後に OfferedDeadlineMissedStatus を取得してから、期限に達した、または期限を超えた回数の変化値を示します。

OfferedDeadlineMissedStatus の変化を監視することで、DataWriter が期限までに要求どおりにデータを送信しない状況を把握できます。 DataWriter が期限内にデータを送信できなかった場合、total_count および total_count_change フィールドが増加します。これらのフィールドの値を確認することで、期限に達していない回数と変更を知ることができます。

次のような一部の機能は、OfferedDeadlineMissedStatus を使用して実現できます。

  • DataWriter が期限どおりにデータを送信するかどうかを監視します。
  • 期限を過ぎた場合には、データの再送や補償操作など、適切なフォールトトレランス措置を講じてください。
  • OfferedDeadlineMissedStatus の変更に基づいて、特定の操作またはコールバック関数をトリガーします。


get_offered_incompatibility_qos_status

ReturnCode_t DataWriterImpl::get_offered_incompatibility_qos_status(OfferedIncompatibilityQosStatus& ステータス)
{
    // DataWriter が既に使用されているかどうか
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    {
        std::unique_lock<RecursiveTimedMutex> lock(writer_->getMutex());

        // 取得OfferedIncompatibilityQosStatus并复制给statusパラメータ
        status = Offered_incompatibility_qos_status_;

        // total_count と total_count_change を重ねます
        Offered_incompatibility_qos_status_.total_count_change = 0;
    }

    // 対応する状態条件を設定します
    user_datawriter_->get_statuscondition().get_impl()->set_status(StatusMask::offered_incompatibility_qos(), false);

    return ReturnCode_t::RETCODE_OK;
}

get_offered_incompatibility_qos_status 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. std::unique_lock を使用して DataWriter のミューテックスをロックし、スレッドの安全性を確保します。
  3. Offered_incompatibility_qos_status_ を status パラメーターにコピーします。
  4. Offered_incompatibility_qos_status_ の total_count_change を 0 にリセットして、変更が処理されたことを示します。
  5. user_datawriter_->get_statuscondition().get_impl()->set_status() を呼び出して、対応するステータス条件を設定し、OfferedIncompatibilityQosStatus の変更をユーザーに通知します。
  6. RETCODE_OK が返された場合は、OfferedIncompatibilityQosStatus が正常に取得されたことを示します。

OfferedIncompatibilityQosStatus は、DataWriter によって提供される QoS (Quality of Service) が加入者 (DataReader) の QoS と互換性がないことを示します。このステータスは、DataWriter とサブスクライバ間の QoS 非互換性統計を記録します。

OfferedIncompatibilityQosStatus 構造体には次のフィールドが含まれます。

  • total_count: DataWriter の開始以降に検出された、互換性のない QoS の合計数を示します。
  • total_count_change:最後に OfferedIncompatibilityQosStatus を取得してから検出された非互換 QoS の数の変化値を示します。

OfferedIncompatibilityQosStatus の変化を監視することにより、DataWriter とサブスクライバ間の QoS の非互換性を理解できます。 DataWriter と加入者が互換性のない QoS を発見すると、total_count および total_count_change フィールドが増加し、これらのフィールドの値を確認することで、互換性のない QoS の数と変化を知ることができます。

次のような一部の機能は、OfferedIncompatibilityQosStatus を使用して実現できます。

  • DataWriter とサブスクライバ間の QoS 互換性を監視します。
  • QoS の再設定を試みたり、加入者と交渉したりするなど、互換性のない QoS の状況に基づいて適切なアクションを実行します。
  • OfferedIncompatibilityQosStatus の変更に基づいて、特定の操作またはコールバック関数をトリガーします。

get_liveiness_lost_status

ReturnCode_t DataWriterImpl::get_liveiness_lost_status(LiveinessLostStatus& ステータス)
{
    // DataWriter が既に使用されているかどうか
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    {
        std::unique_lock<RecursiveTimedMutex> lock(writer_->getMutex());

        // 获取LiveinessLostStatus并复制给statusパラメータ
        status = liveiness_lost_status_;

        // total_count と total_count_change を重ねます
        liveiness_lost_status_.total_count_change = 0;
    }

    // 対応する状態条件を設定します
    user_datawriter_->get_statuscondition().get_impl()->set_status(StatusMask::liveiness_lost(), false);

    return ReturnCode_t::RETCODE_OK;
}

get_liveiness_lost_status 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. std::unique_lock を使用して DataWriter のミューテックスをロックし、スレッドの安全性を確保します。
  3. liveiness_lost_status_ を status パラメータにコピーします。
  4. liveiness_lost_status_ の total_count_change を 0 にリセットして、変更が処理されたことを示します。
  5. user_datawriter_->get_statuscondition().get_impl()->set_status() を呼び出して、対応するステータス条件を設定し、LiveinessLostStatus の変更をユーザーに通知します。
  6. RETCODE_OK が返された場合は、LiveinessLostStatus が正常に取得されたことを示します。

データ通信において、活性とは、エンティティ (DataWriter など) が存在し続け、アクティブである状態を指します。パブリッシュ/サブスクライブ モデルでは、DataWriter は活性メッセージを送信するか、ハートビート メッセージを定期的に送信することによって、そのアクティブ ステータスを証明します。このようにして、加入者 (DataReader) は、通信リンクを維持するために DataWriter がまだアクティブであるかどうかを確認できます。

ライブネスの目的は、通信リンクの有効性と一貫性を維持するために、データ通信内のエンティティがアクティブなままであることを保証することです。ライブネス メカニズムを通じて、DataWriter がアクティブでなくなったかどうか、つまりライブネス メッセージやハートビート メッセージの送信を停止したか、何らかの理由でライブネス要件を満たすことができなかったかを検出できます。 DataWriter がアクティビティを失った場合、サブスクライバは、サブスクライバのステータスを更新したり、リソースを再割り当てしたり、その他のフォールト トレラント措置を講じたりするなど、それに応じて処理できます。

get_sending_locators

ReturnCode_t DataWriterImpl::get_sending_locators(rtps::LocatorList& locators) const
{
    // DataWriter が有効かどうかを確認します
    if (writer_ == nullptr)
    {
        return ReturnCode_t::RETCODE_NOT_ENABLED;
    }

    // DataWriter によって使用されている送信ロケーターのリストを取得します
    rtps::LocatorList Sending_locators =writer_->getRTPSParticipant()->getSendingLocators();

    // 送信ロケーター リストを出力パラメーター ロケーターにコピーします
    ロケーター = Sending_locators;

    return ReturnCode_t::RETCODE_OK;
}

get_sending_locators 関数の主な手順は次のとおりです。

  1. まず、DataWriter が有効かどうかを確認し、有効でない場合は RETCODE_NOT_ENABLED を返します。
  2. Writer_->getRTPSParticipant()->getSendingLocators() を呼び出して、DataWriter によって使用されている送信ロケーターのリストを取得します。
  3. 送信ロケーターのリストを出力パラメーター ロケーターにコピーします。
  4. RETCODE_OK が返された場合は、送信ロケータ リストの取得が成功したことを示します。

get_sending_locators 関数を呼び出すと、DataWriter で使用されている送信ロケーターのリストを取得できます。送信ロケータリストには、DataWriter がデータを送信するために使用するネットワークロケータ情報が含まれており、DataWriter の現在の通信構成や接続情報を把握するために使用できます。これは、データ転送とネットワーク構成の監視とデバッグに役立ちます。

おすすめ

転載: blog.csdn.net/qq_32378713/article/details/131699450