ublk - Man Page

Utility to manage ublk devices

Synopsis

ublk <command> [<command options>] [<type specific options>]

Description

ublk is a utility that allows you to create, recover, view or delete user-space block devices.

ublk by default comes with several different types of devices, such as iscsi, nbd, nfs, null and loop.

The following commands are supported:

Add Command

Command to add a ublk device.

add {-t, --type} TYPE [{-n, --number} DEV_ID] [{-q, --queues} NR_HW_QUEUES] [{-d, --depth} QUEUE_DEPTH] [{-u, --uring_comp} URING_COMP] [{-g, --need-get-data} NEED_GET_DATA] [{-r, --user_recovery} {0|1}] [{-i, --user_recovery_reissue} {0|1}] [{-e, --user_recovery_fail_io} {0|1}] [--debug_mask=0x{DBG_MASK}] [--unprivileged] [--usercopy] [--max_io_buf_bytes={BYTES}] [{-z, --zerocopy}] [<type specific options>]

-t,  --type

Specifies the type of device to create. The five types of supported devices are iscsi, nbd, nfs, null and loop.

-n,  --number

Create a device with this id. The device node will be /dev/ublkb_n_.

-q,  --queue

Number of queues to create. Each queue is services by a dedicated child process. Default is 1.

-d,  --depth

Maximum queue-depthfor each queue. Default is 4096.

-u,  --uring_comp

Force to complete io cmd via io_uring_cmd_complete_in_task so that performance comparison is done easily with using task_work_add.

-g,  --need_get_data

User should issue io cmd again for write requests to set io buffer address and copy data from bio vectors to the userspace io buffer.

-r,  --user_recovey

Block devices are recoverable if ublk server exits and restarts. Outstanding I/O when ublk server exits is met with errors. I/O issued while there is no ublk server queues.

-i,  --user_recovey_reissue

Block devices are recoverable if ublk server exits and restarts Outstanding I/O when ublk server exits is reissued I/O issued while there is no ublk server queues

-e,  --user_recovey_fail_io

Block devices are recoverable if ublk server exits and restarts Outstanding I/O when ublk server exits is met with errors I/O issued while there is no ublk server is met with errors

--debug_mask

Bitmask specifying which debug features to enable.

--max_io_buf_bytes

Maximum I/O size. Default is 512kb.

NOTE: Memory buffers are pre-allocated with one buffer for each entry in queue_depth.

--unprivileged

Unprivileged user can create /dev/ublkcN and /dev/ublkbN.

/dev/ublk-control needs to be available for unprivileged user, and it can be done via udev rule to make all control commands available to unprivileged user. Except for the command of UBLK_CMD_ADD_DEV, all other commands are only allowed for the owner of the specified device.

When userspace sends UBLK_CMD_ADD_DEV, the device pair's owner_uid and owner_gid are stored to ublksrv_ctrl_dev_info by kernel, so far only the current user's uid/gid is stored, that said owner of the created device is always the current user.

We still need udev rule to apply OWNER/GROUP with the stored owner_uid and owner_gid.

Then ublk server can be run as unprivileged user, and /dev/ublkbN can be accessed and managed by its owner represented by owner_uid/owner_gid.

--user_copy

Copy between request and user buffer by pread()/pwrite()

-z,  --zerocopy

Zero-copy is based on io-uring uring_cmd of REGISTER_IO_BUF & UNREGISTER_IO_BUF, which avoids data copy between ublk frontend request buffer and ublk server buffer, so memory bandwidth is saved, and throughput & latency improvement can be often observed on large I/O size

This requires Linux kernel 6.15 or later.

Null

The null device type does not take any extra options.

Loop

Extra options for the loop device type:

add -t loop ... {-f, --file} FILE [--buffered_io] [-o, --offset OFFSET]

-f,  --file

File to use as backing storage for the loop device.

--buffered_io

Use buffered i/o for accessing the backing file. Default is direct i/o.

--offset

Offset skips first NUM sectors on backing file.

Example: Create a loop block device

    # ublk add -t loop -n 0 -f 10M.raw

NBD

Extra options for the nbd (Network Block Device) device type:

add -t nbd ... {--host HOST | --unix UNIX_PATH} --export_name EXP_NAME [--send_zc] [--read_only]

--host

Hostname of NBD server.

--host

Hostname of NBD server to use.

--unix

Path to unix domain socket to use to talk to NBD.

--export_name

Name of NBD export.

--send_zc

Use Zero-Copy.

--read_only

Read-only device.

NFS

Extra options for the nfs device type:

add -t nfs ... --nfs NFS-URL

--nfs NFS-URL

URL to the NFS file to use as the block device.

The NFS-URL format is describe in the libnfs README: https://github.com/sahlberg/libnfs/blob/9fa155bfa9d34347a669fbecf4a64259cc573724/README#L55

Example: Create a nfs block device

    # ublk add -t nfs -n 0 --nfs nfs://10.0.0.1/export/10M.raw

iSCSI

Extra options for the iSCSI device type. iSCSI support requires libiscsi 1.20.3 or later.

add -t iscsi ... --iscsi ISCSI-URL --initiator-name NAME

--iscsi ISCSI-URL

URL to the iSCSI device to use as the block device.

The ISCSI-URL format is describe in the libiscsi README: https://github.com/sahlberg/libiscsi/blob/eb19863f77e2bad4799ceb90e47fa3bc6205233e/README.md?plain=1#L37

--initiator-name NAME

The initiator name to use when logging in to the target.

Example: Create an iSCSI block device

    # ublk add -t iscsi -n 0 --iscsi iscsi://iscsi-stgt/iqn.2001-04.com.ronnie.sr0/1 --initiator-name iqn.ronnie.test

Del Command

Command to delete a ublk device.

del {-n, --number} DEV_ID [-a, --all] [--async]

-n, --number

Delete the device with this id.

-a, --all

Delete all devices.

Example: Deleting a loop block device

    # ublk del -n 0

Set_affinity Command

Command to change queue affinity.

set_affinity {-n, --number} DEV_ID [-q, --queue] QID --cpuset="[SET]"

-n, --number

Change the affinity on this device.

-q, --queue

Which queue to change the affinity for.

--cpuset="[SET]"

The new cpuset for this device/queue. Format is a comma-separated list of CPUs within squre brackets.

Example: Set affinity to core 7 for device 0, queue 1

    # ublk set_affinity -n 0 -q 1 --cpuset="[7]"

List Command

List one or all devices and show their configutaion.

list {-n, --number} DEV_ID [-v, --verbose]

-n, --number

List the device with this id. If omitted all devices will be listed

-v, --verbose

Verbose listing. Include the JSON device arguments in the output.

Recover Command

Recover a failed ublk device.

recover {-n, --number} DEV_ID

-n, --number

Device to recover.

Features Command

Show supported features for the ublk driver.

features

Help Command

Show generic ot type specific help.

help [{-t, --type} TYPE]

-t, --type

Show help page. It -t is specified, show help page for the specific device type.

Version

Show help page..

{-v, --version}

Recovery

There are three arguments that control how ublk will behave in case of a failure, such as crashing. The default behavior is no recovery and the device will fail and be removed once the target exists.

To enable recovery mode set "--recovery 1" on the command line. Then instead of removing the device upon failure it will instead become inactive in a quiesced state.

dev id 0: nr_hw_queues 1 queue_depth 128 block size 4096 dev_capacity 20480
    max rq size 524288 daemon pid 1239110 state QUIESCED
    flags 0x4a [ URING_CMD_COMP_IN_TASK RECOVERY CMD_IOCTL_ENCODE ]
    ublkc: 511:0 ublkb: 259:4 owner: 0:0
    queue 0: tid 1239112 affinity(0 1 2 3 4 5 6 7 )
    target {"backing_file":"10M","dev_size":10485760,"direct_io":1,"name":"loop","offset":0,"type":0}

In this state the block device still exists but no I/O can be performed.

To recover a QUIESCED device you can use the recover command: ublk recover -n DEV_ID

There are two additional flags that control how ublk will handle I/O that were in flight when a device is recovered.

--user_recovery_reissue 1

When the device is recovered ublk will reissue any I/O that were in flight.

--user_recovery_fail_io 1

When the device is recovered ublk will fail all I/O and return an error back to the application.

See Also

http://github.com/ublk-org/ublksrv

Info

07/16/2025 ublk: manage ublk devices