[block] Add FIDL protocol for block devices
These bindings have parity with the remaining ioctl declarations.
For direct comparison, refer to: system/public/zircon/device/block.h
Test: Declarations only; bindings utilized in subsequent patches.
Change-Id: I6cfba4834b3d4688e1be92c04da20bd945df4afc
diff --git a/system/fidl/fuchsia-hardware-block-partition/partition.fidl b/system/fidl/fuchsia-hardware-block-partition/partition.fidl
new file mode 100644
index 0000000..f8442cd
--- /dev/null
+++ b/system/fidl/fuchsia-hardware-block-partition/partition.fidl
@@ -0,0 +1,33 @@
+// Copyright 2019 The Fuchsia Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+library fuchsia.hardware.block.partition;
+using zx;
+using fuchsia.hardware.block as block;
+
+const uint32 GUID_LENGTH = 16;
+const uint32 NAME_LENGTH = 24;
+
+// A Globally Unique IDentifier, which may be utilized to identify
+// a partition.
+struct GUID {
+ array<uint8>:GUID_LENGTH value;
+};
+
+// Partition describes a region of one or more block devices, labelled
+// with distinguishing identifiers.
+[Layout = "Simple", FragileBase]
+interface Partition : block.Block {
+ // Gets the type GUID of the partition (if one exists).
+ // If the partition has no type GUID, ZX_ERR_NOT_SUPPORTED is returned.
+ GetTypeGuid() -> (zx.status status, GUID? guid);
+
+ // Gets the instance GUID of the partition (if one exists).
+ // If the partition has no instance GUID, ZX_ERR_NOT_SUPPORTED is returned.
+ GetInstanceGuid() -> (zx.status status, GUID? guid);
+
+ // Gets the name of the partition (if one exists).
+ // If the partition has no name, ZX_ERR_NOT_SUPPORTED is returned.
+ GetName() -> (zx.status status, string:NAME_LENGTH? name);
+};
diff --git a/system/fidl/fuchsia-hardware-block-partition/rules.mk b/system/fidl/fuchsia-hardware-block-partition/rules.mk
new file mode 100644
index 0000000..065672b
--- /dev/null
+++ b/system/fidl/fuchsia-hardware-block-partition/rules.mk
@@ -0,0 +1,21 @@
+# Copyright 2019 The Fuchsia Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+LOCAL_DIR := $(GET_LOCAL_DIR)
+
+MODULE := $(LOCAL_DIR)
+
+MODULE_TYPE := fidl
+
+MODULE_PACKAGE := fidl
+
+MODULE_FIDL_LIBRARY := fuchsia.hardware.block.partition
+
+MODULE_SRCS += \
+ $(LOCAL_DIR)/partition.fidl \
+
+MODULE_FIDL_DEPS := \
+ system/fidl/fuchsia-hardware-block \
+
+include make/module.mk
diff --git a/system/fidl/fuchsia-hardware-block-volume/rules.mk b/system/fidl/fuchsia-hardware-block-volume/rules.mk
new file mode 100644
index 0000000..308fc9e
--- /dev/null
+++ b/system/fidl/fuchsia-hardware-block-volume/rules.mk
@@ -0,0 +1,22 @@
+# Copyright 2019 The Fuchsia Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+LOCAL_DIR := $(GET_LOCAL_DIR)
+
+MODULE := $(LOCAL_DIR)
+
+MODULE_TYPE := fidl
+
+MODULE_PACKAGE := fidl
+
+MODULE_FIDL_LIBRARY := fuchsia.hardware.block.volume
+
+MODULE_SRCS += \
+ $(LOCAL_DIR)/volume.fidl \
+
+MODULE_FIDL_DEPS := \
+ system/fidl/fuchsia-hardware-block \
+ system/fidl/fuchsia-hardware-block-partition \
+
+include make/module.mk
diff --git a/system/fidl/fuchsia-hardware-block-volume/volume.fidl b/system/fidl/fuchsia-hardware-block-volume/volume.fidl
new file mode 100644
index 0000000..a33dddf
--- /dev/null
+++ b/system/fidl/fuchsia-hardware-block-volume/volume.fidl
@@ -0,0 +1,102 @@
+// Copyright 2019 The Fuchsia Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+library fuchsia.hardware.block.volume;
+using zx;
+using fuchsia.hardware.block.partition as partition;
+
+// VolumeInfo describes characteristics of either a single Volume, or all
+// Volumes combined.
+struct VolumeInfo {
+ // Size of a single slice, in bytes.
+ uint64 slice_size;
+
+ // Number of addressable slices.
+ uint64 vslice_count;
+
+ // Total number of allocatable slices.
+ uint64 pslice_total_count;
+
+ // Total number of currently allocated slices.
+ uint64 pslice_allocated_count;
+};
+
+// Indicates that the partition should be created as inactive, implying that it
+// will be destroyed on reboot (unless activated by a call to "Activate").
+const uint32 AllocatePartitionFlagInactive = 0x00000001;
+
+// VolumeManager controls a collection of Volumes.
+[Layout = "Simple"]
+interface VolumeManager {
+ // Allocates a virtual partition with the requested features.
+ //
+ // |slice_count| is the number of slices initially allocated to the partition, at
+ // offset zero. The number of slices allocated to a new partition must be at least one.
+ // |type| and |value| indicate type and instance GUIDs for the partition, respectively.
+ // |name| indicates the name of the new partition.
+ AllocatePartition(uint64 slice_count, partition.GUID type,
+ partition.GUID instance, string:partition.NAME_LENGTH name,
+ uint32 flags) -> (zx.status status);
+
+ // Gets slice size information about all volumes.
+ Query() -> (zx.status status, VolumeInfo? info);
+
+ // Atomically marks a vpartition (by instance GUID) as inactive, while finding
+ // another partition (by instance GUID) and marking it as active.
+ //
+ // If the "old" partition does not exist, the GUID is ignored.
+ // If the "old" partition is the same as the "new" partition, the "old"
+ // GUID is ignored.
+ // If the "new" partition does not exist, |ZX_ERR_NOT_FOUND| is returned.
+ //
+ // This function does not destroy the "old" partition, it just marks it as
+ // inactive -- to reclaim that space, the "old" partition must be explicitly
+ // destroyed. This destruction can also occur automatically when the FVM driver
+ // is rebound (i.e., on reboot).
+ //
+ // This function may be useful for A/B updates within the FVM,
+ // since it will allow activating updated partitions.
+ Activate(partition.GUID old_guid, partition.GUID new_guid) -> (zx.status status);
+};
+
+// An arbitrary cap on the number of slices which may be requested when querying
+// for allocation information from a volume.
+const uint32 MAX_SLICE_REQUESTS = 16;
+
+// VsliceRange describes a range of virtual slices: start, length, and allocated status.
+//
+// These ranges are returned in an ordered container, which implicitly describes the
+// starting offset, starting from the "index zero" slice.
+struct VsliceRange {
+ // True if the virtual slices are allocated, false otherwise.
+ bool allocated;
+
+ // The number of contiguous virtual slices.
+ uint64 count;
+};
+
+// Volume is a partition which may access virtually-mapped blocks within a device.
+[Layout = "Simple"]
+interface Volume : partition.Partition {
+ // Gets slice size information about the parent volume.
+ Query() -> (zx.status status, VolumeInfo? info);
+
+ // Returns the number of contiguous allocated (or unallocated) vslices
+ // starting from each vslice.
+ //
+ // TODO(smklein): Replace array with vector; doing so would be non-simple.
+ QuerySlices(vector<uint64>:MAX_SLICE_REQUESTS start_slices)
+ -> (zx.status status, array<VsliceRange>:MAX_SLICE_REQUESTS response, uint64 response_count);
+
+ // Extends the mapping of this partition.
+ Extend(uint64 start_slice, uint64 slice_count) -> (zx.status status);
+
+ // Shrinks a virtual partition. Returns |ZX_OK| if ANY slices are
+ // freed, even if part of the requested range contains unallocated slices.
+ Shrink(uint64 start_slice, uint64 slice_count) -> (zx.status status);
+
+ // Destroys the current partition, removing it from the VolumeManager, and
+ // freeing all underlying storage.
+ Destroy() -> (zx.status status);
+};
diff --git a/system/fidl/fuchsia-hardware-block/block.fidl b/system/fidl/fuchsia-hardware-block/block.fidl
new file mode 100644
index 0000000..c1a5b66
--- /dev/null
+++ b/system/fidl/fuchsia-hardware-block/block.fidl
@@ -0,0 +1,105 @@
+// Copyright 2019 The Fuchsia Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+library fuchsia.hardware.block;
+using zx;
+
+// All writes to the block device will fail.
+const uint32 FLAG_READONLY = 0x00000001;
+
+// The block device may be removed from the device during operation.
+const uint32 FLAG_REMOVABLE = 0x00000002;
+
+// The device has a bootdata partition map.
+const uint32 FLAG_BOOTPART = 0x00000004;
+
+// The maximum value for a transfer size, identifying that there
+// effectively exists no maximum for a single operation.
+const uint32 MAX_TRANSFER_UNBOUNDED = 0xFFFFFFFF;
+
+// Describes metatadata about a block device.
+struct BlockInfo {
+ // The number of blocks in this block device.
+ uint64 block_count;
+
+ // The size of a single block.
+ uint32 block_size;
+
+ // The maximum size, in bytes, of a transfer.
+ // Set to MAX_TRANSFER_UNBOUNDED if no such maximum exists.
+ uint32 max_transfer_size;
+
+ // Identifiers about the device; refer to the "FLAG_*" documentation above.
+ uint32 flags;
+
+ uint32 reserved;
+};
+
+// Describes statistics about the operations on the block device since boot.
+struct BlockStats {
+ // The total number of operations which have been processed.
+ int64 ops;
+
+ // The total number of blocks which have been acted upon.
+ int64 blocks;
+
+ // The total number of requests to read from the device.
+ int64 reads;
+
+ // The total number of blocks which have been read from the device.
+ int64 blocks_read;
+
+ // The total number of requests to write to the device.
+ int64 writes;
+
+ // The total number of blocks which have been written to the device.
+ int64 blocks_written;
+};
+
+// A client-identifier to a VMO.
+// This value may be utilized by clients to refer to a VMO which is being held
+// by a block device server.
+struct VmoID {
+ uint16 id;
+};
+
+// Dummy value reserved for "invalid" VmoID. Will never be allocated by the server,
+// and may be utilized as a local value for an unallocated ID.
+const uint16 VMOID_INVALID = 0;
+
+// Defines access to a device which is accessible in block-granularity chunks
+// for reading and writing.
+[Layout = "Simple", FragileBase]
+interface Block {
+ // Get information about the underlying block device.
+ GetInfo() -> (zx.status status, BlockInfo? info);
+
+ // Returns stats about the block device on the provided buffer and optionally
+ // clears the counters.
+ GetStats(bool clear) -> (zx.status status, BlockStats? stats);
+
+ // Sets up a FIFO-based server on the block device; acquire the handle to it.
+ GetFifo() -> (zx.status status, handle<fifo> fifo);
+
+ // Attaches a VMO to the currently running FIFO server.
+ AttachVmo(handle<vmo> vmo) -> (zx.status status, VmoID? vmoid);
+
+ // Shuts down the fifo server, waiting for it to be ready to be started again.
+ //
+ // When this method returns, a client may safely invoke GetFifo to acquire
+ // a new connection to the block server, without being told that a server
+ // is already serving requests on a different fifo.
+ //
+ // If, instead of invoking "CloseFifo", a client merely closes their fifo,
+ // the server automatically cleans up all resources anyway. In this case,
+ // however, the client will have no guarantee that the next invocation of
+ // "GetFifo" will return a connection successfully.
+ CloseFifo() -> (zx.status status);
+
+ // Rebinds the block device (if supported).
+ //
+ // WARNING: This is only added for parity with block device ioctls;
+ // this is going to move into the device FIDL API.
+ RebindDevice() -> (zx.status status);
+};
diff --git a/system/fidl/fuchsia-hardware-block/rules.mk b/system/fidl/fuchsia-hardware-block/rules.mk
index 731eb3d..7c729be 100644
--- a/system/fidl/fuchsia-hardware-block/rules.mk
+++ b/system/fidl/fuchsia-hardware-block/rules.mk
@@ -13,6 +13,7 @@
MODULE_FIDL_LIBRARY := fuchsia.hardware.block
MODULE_SRCS += \
+ $(LOCAL_DIR)/block.fidl \
$(LOCAL_DIR)/ftl.fidl \
include make/module.mk