在 DFv2 驅動程式庫中設定 devf

本指南將說明如何在 DFv2 驅動程式庫中設定 devfs,讓系統中的其他 Fuchsia 元件能夠偵測到驅動程式庫的服務。本指南會使用DFv2 驅動程式範例逐步說明 devfs 的設定程序。

步驟如下:

  1. 找出目標 FIDL 通訊協定
  2. 新增 ServerBindingGroup 物件
  3. 建立回呼函式
  4. 初始化 devfs 連接器
  5. 將 devfs 連接器繫結至調度器
  6. 將 devfs 連接器新增至子節點

1. 找出目標 FIDL 通訊協定

在 DFv2 驅動程式的原始碼中,為此 devfs 設定識別目標 FIDL 通訊協定 (可繼承自 fidl::Server<>fidl::WireServer<>),例如:

class RetrieverDriver final : public fdf::DriverBase,
                              public fidl::Server<fuchsia_examples_metadata::Retriever> {

  ...

  // fuchsia.hardware.test/Child implementation.
  void GetMetadata(GetMetadataCompleter::Sync& completer) override {
    ...
  }
};

(來源:retriever-driver.cc)

本指南的範例使用 fuchsia.examples.metadata.fidl 中定義的 Retriever 通訊協定。

2. 新增 ServerBindingGroup 物件

ServerBindingGroup 物件新增至驅動程式庫類別,以繫結 FIDL 通訊協定,例如:

class RetrieverDriver final : public fdf::DriverBase,
                              public fidl::Server<fuchsia_examples_metadata::Retriever> {

...

fidl::ServerBindingGroup<fuchsia_examples_metadata::Retriever> bindings_;

(來源:retriever-driver.cc)

3. 建立回呼函式

建立回呼函式,當用戶端嘗試連線至驅動程式庫時,系統會叫用此函式。在這個回呼函式中,新增從 ServerBindingGroup<> 物件到 ServerEnd 物件的繫結,例如:

class RetrieverDriver final : public fdf::DriverBase,
                              public fidl::Server<fuchsia_examples_metadata::Retriever> {
  ...

  void Serve(fidl::ServerEnd<fuchsia_examples_metadata::Retriever> request) {
    bindings_.AddBinding(dispatcher(), std::move(request), this, fidl::kIgnoreBindingClosure);
  }

(來源:retriever-driver.cc)

4. 初始化 devfs 連接器

步驟 1 中傳遞目標 FIDL 通訊協定,並在 步驟 3 中建立回呼函式,藉此初始化 devfs 連接器物件,例如:

  driver_devfs::Connector<fuchsia_examples_metadata::Retriever> devfs_connector_{
      fit::bind_member<&RetrieverDriver::Serve>(this)};

(來源:retriever-driver.cc)

5. 將 devfs 連接器繫結至調度器

devfs 連接器繫結至驅動程式庫調度器,例如:

zx::result connector = devfs_connector_.Bind(dispatcher());
    if (connector.is_error()) {
      FDF_SLOG(ERROR, "Failed to bind devfs connector.", KV("status", connector.status_string()));
      return connector.status_value();
    }

(來源:retriever-driver.cc)

6. 將 devfs 連接器新增至子節點

新增子節點時,請從步驟 5將繫結的 devfs 連接器傳遞至節點的 NodeAddArgs 物件。如要這麼做,請建立 DevfsAddArgs 物件,該物件已在 fuchsia.driver.framework/topology.fidl 中定義,並將 connector 欄位設為 devfs 連接器,例如:

fuchsia_driver_framework::DevfsAddArgs devfs_args{
  {.connector = std::move(connector.value())}
};

zx::result owned_child = AddOwnedChild("retriever", devfs_args);
if (owned_child.is_error()) {
  FDF_SLOG(ERROR, "Failed to add owned child.", KV("status", owned_child.status_string()));
  return owned_child.error_value();
}

(來源:retriever-driver.cc)