SG_VERIFY(8)

πŸ“¦
version 1.49 Β· 4 versions
, in alpine 3.24, arch rolling, centos-stream 10, debian trixie, fedora 43, fedora 44, nixos 26.05, nixpkgs unstable, ubuntu questing, ubuntu resolute, ubuntu stonking

✨ NAME ✨

Okay bestie, the manual name is sg_verify and it's giving: invoke SCSI VERIFY command(s) on a block device πŸ’…πŸ¦‹


πŸ’– SYNOPSIS πŸ’–

sg_verify [--0] [--16] [--bpc=BPC] [--count=COUNT] [--dpo] [--ff]
[--ebytchk=BCH] [--group=GN] [--help] [--in=IF] [--lba=LBA] [--ndo=NDO]
[--quiet] [--readonly] [--verbose] [--version] [--vrprotect=VRP] DEVICE

🌸 DESCRIPTION 🌸

Okay so sg_verify sends one or more SCSI VERIFY (10 or 16) commands to DEVICE. These commands are defined in the SBC-2 and SBC-3 standards at https://www.t10.org and in SBC-4 drafts, so it's very official and very serious ✨

When --ndo=NDO is not given, the verify starts at the logical block address from --lba=LBA and keeps going for --count=COUNT blocks. No more than --bpc=BPC blocks get verified by each VERIFY command, so if needed, multiple VERIFY commands get sent. The medium verification is done by the DEVICE itself (for example, assuming each block has extra EEC data, it checks that against the logical block contents) 🧚 And honestly? No news is good news. If no verify errors are detected, nothing gets sent to stderr and the Unix exit status is 0 🫢

When --ndo=NDO is given, the --bpc=BPC option gets ignored. A single VERIFY command is issued and a comparison starts at the logical block address from --lba=LBA and continues for --count=COUNT blocks. The VERIFY command has a data-out buffer that is NDO bytes long. That buffer gets its contents from the FN file (if --in=FN is given) or from stdin. Then a comparison happens between the data-out buffer and the logical blocks on the DEVICE. If the comparison is good, no messages go to stderr and the exit status is 0 ✨ If it fails, a sense buffer with a sense key of MISCOMPARE comes back, and in that case the exit status will be 14 😭 Messages get sent to stderr for that MISCOMPARE sense buffer unless --quiet is given.

⚠️ Heads up: In SBC-3 revision 34, the BYTCHK field in all SCSI VERIFY commands got expanded from one bit to two bits. That meant some options in this utility had to change, so check the section below on OPTION CHANGES πŸ™ˆ

πŸ‘‘ OPTIONS πŸ‘‘

Arguments to long options are mandatory for short options as well. The options are arranged in alphabetical order based on the long option name πŸŽ€

  • -0, --0 β€” This sends a buffer NDO bytes long, completely full of zeros, as the data-out part of a VERIFY command. Stdin doesn't get read, and if --in=IF is given, you'll get an error. It's super handy when BCH is 3, for checking whether some or all of DEVICE (like a disk) is zero-filled blocks πŸ“
  • -S, --16 β€” Uses a VERIFY(16) command instead of the default VERIFY(10). Even without this option, if you pass an --lba=LBA that's too large, the utility will issue a VERIFY(16) command on its own πŸ’œ
  • -b, --bpc=BPC β€” This gets ignored if --ndo=NDO is given. Otherwise, BPC is the max number of blocks a single SCSI VERIFY command will verify. The default is 128 blocks, which works out to 64 KB for a disk with 512 byte blocks. If BPC is less than COUNT, multiple SCSI VERIFY commands get sent to the DEVICE. For the default VERIFY(10), BPC can't go past 0xffff (65,535), while for VERIFY(16) it can't go past 0x7fffffff (2,147,483,647). For recent block devices (disks), this might be limited by the maximum transfer length field in the block limits VPD page πŸ”₯
  • -c, --count=COUNT β€” COUNT is how many blocks to verify. The default is 1 . If COUNT is bigger than BPC (or its default of 128) and NDO isn't given, then 0 or less than multiple SCSI VERIFY commands get sent to the device. Otherwise, COUNT becomes the contents of the verification length field in the SCSI VERIFY command that gets issued. If you need to find out the maximum number of blocks a block device (like a disk) has, the sg_readcap utility can help you with that 🌈
  • -d, --dpo β€” Disable page out. This changes the cache retention priority of blocks read on the device's cache down to the lowest priority. Translation: blocks read by other commands are more likely to stick around in the device's cache 🧚
  • -E, --ebytchk=BCH β€” This sets the BYTCHK field to BCH, overriding the value of 1 that --ndo=NDO sets. Values of 1, 2 or 3 are accepted for BCH, but sbc3r34 reserves the value 2, so no 2 for you πŸ™…β€β™€οΈ If this option is given, then --ndo=NDO must also be given. If BCH is 3, then NDO should be the size of one logical block (plus the size of some or all of the protection information if VRP is greater than 0) πŸ¦‹
  • -f, --ff β€” This sends a buffer NDO bytes long, full of 0xff bytes, as the data-out part of a VERIFY command. Stdin doesn't get read, and if --in=IF is given, you'll get an error. Super useful when BCH is 3 for checking whether some or all of DEVICE (like a disk) is 0xff byte-filled blocks ✨
  • -g, --group=GN β€” GN becomes the contents of the group number field in the SCSI VERIFY(16) command. It can be anywhere from 0 to 63 inclusive, and the default is 0. Just a heads up, this option is ignored for the SCSI VERIFY(10) command πŸ’…
  • -h, --help β€” Outputs the usage message, then exits 🫢
  • -i, --in=IF β€” IF is the name of a file to read NDO bytes from, which then get placed in the data-out buffer. This only happens when --ndo=NDO is given. If this option isn't given, stdin gets read instead. If IF is "-", stdin gets used too πŸ“₯
  • -l, --lba=LBA β€” LBA is the logical block address of the first block to start the verify operation. LBA is assumed to be decimal unless you prefix it with '0x' or give it a trailing 'h' (more on that below). The default is 0, which is the start of the device 🌸
  • -n, --ndo=NDO β€” NDO is the number of bytes to grab from the FN file (if --in=FN is given) or from stdin. Those bytes go into the data-out buffer tied to the SCSI VERIFY command, and NDO gets placed in the verification length field in the CDB. The default for NDO is 0, and the max value depends on the OS πŸ‘‘ If --ebytchk=BCH isn't given, the BYTCHK field in the CDB gets set to 1.
  • -q, --quiet β€” Suppresses the sense buffer messages for a MISCOMPARE sense key that would otherwise be sent to stderr. The exit status still gets set to 14, which is the sense key value for a MISCOMPARE πŸ™ˆ
  • -r, --readonly β€” Opens the DEVICE read-only instead of read-write, which is the default. The Linux sg driver needs read-write access for the SCSI VERIFY command, but other access methods might need read-only access πŸŽ€
  • -v, --verbose β€” Increases the level of verbosity, which means more debug output πŸ”
  • -V, --version β€” Prints the version string, then exits 🌈
  • -P, --vrprotect=VRP β€” VRP is the value in the vrprotect field of the VERIFY command CDB. It has to be between 0 and 7 inclusive. The default is zero 🧚

πŸ¦‹ BYTCHK πŸ¦‹

BYTCHK is the name of a field (two bits wide) in the VERIFY(10) and VERIFY(16) commands. When it's set to 1 or 3 (sbc3r34 reserves the value 2), it means a data-out buffer will be sent to the device (disk) to check along with the SCSI VERIFY command. Using --ndo=NDO sets the BYTCHK field to 1, and NDO is the number of bytes placed in the data-out buffer. Those bytes come from stdin or from IF (via the --in=FN option). You can use --ebytchk=BCH to override the BYTCHK value of 1 with BCH πŸ’–

The calculation of NDO is up to you, bestie πŸ’… Its value depends on the logical block size (which you can find with the sg_readcap utility), the COUNT and the VRP values. If VRP is greater than 0, then each logical block will contain an extra 8 bytes (at least) of protection information.

When the BYTCHK field is 0, the verification process done by the device (disk) is vendor specific. It usually involves checking each block on the disk against its error correction codes (ECC), which is extra data also stored on the disk 🌸

Many operating systems put limits on the maximum size of the data-out (and data-in) buffer. For Linux, the limit used to be less than 1 MB, but it has gotten a bit bigger since then ✨


πŸŽ€ OPTION CHANGES πŸŽ€

Earlier versions of this utility had a --bytchk=NDO option that set the BYTCHK bit and set the cdb verification length field to NDO. The shorter form of that option was -B NDO. For backward compatibility, that option is still around, but it's not documented anymore. In its place is --ndo=NDO, whose shorter form is -n NDO. --ndo=NDO sets the BYTCHK field to 1, unless that gets overridden by --ebytchk=BCH πŸ¦‹


🧚 NOTES 🧚

Various numeric arguments (like LBA) can include multiplicative suffixes or be given in hexadecimal. Check out the "NUMERIC ARGUMENTS" section in the sg3_utils(8) man page for the deets πŸ”₯

The amount of error correction and the number of retries attempted before a block is considered defective are controlled partly by the Verify Error Recovery mode page. A note in the SBC-3 draft (rev 29, section 6.4.9 on the Verify Error Recovery mode page) says that if you want to minimize the number of checks (and therefore have the most "sensitive" verify check), do the following in that mode page: set the EER bit to 0, the PER bit to 1, the DTE bit to 1, the DCR bit to 1, the verify retry count to 0 and the verify recovery time limit to 0. You can change mode pages with the sdparm utility πŸ’œ

The SCSI VERIFY(6) command defined in the SSC-2 standard and later (which is for tape drive systems) is not supported by this utility. Sorry, tape fans πŸ™ˆ


πŸ’… EXIT STATUS πŸ’…

The exit status of sg_verify is 0 when it succeeds. When BCH is anything other than 0, a comparison happens, and if it fails, the exit status is 14, which just so happens to be the sense key value of MISCOMPARE 😭 Otherwise, check the EXIT STATUS section in the sg3_utils(8) man page.

Earlier versions of this utility set an exit status of 98 when there was a MISCOMPARE. Old news, bestie 🌈


🫢 AUTHORS 🫢

Written by Douglas Gilbert. Iconic ✨


🐞 REPORTING BUGS 🐞

Report bugs to <dgilbert at interlog dot com>. Be nice about it πŸ₯Ί


Copyright Β© 2004-2019 Douglas Gilbert This software is distributed under a BSD-2-Clause license. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE πŸ’€


πŸ“ SEE ALSO πŸ“

sdparm(sdparm), sg_modes(sg3_utils), sg_readcap(sg3_utils), sg_inq(sg3_utils)


Okay that's the tea! ✨ This was sg3_utils-1.45, last updated December 2019. Stay iconic, bestie πŸ’–πŸ¦‹πŸ‘‘

πŸ“¦ where this page comes from