├── debian ├── compat ├── sg3-utils.examples ├── libsgutils2-2.install ├── sg3-utils.install ├── libsgutils2-dev.install ├── docs ├── README.debian4 ├── copyright ├── control └── rules ├── NEWS ├── bootstrap ├── inhex ├── vpd_zbdc.raw ├── inq_standard.raw ├── luns_lu_cong.hex ├── vpd_sfs.hex ├── readcap_zbc.hex ├── vpd_lbpro.hex ├── fixed_sense.hex ├── get_lba_status.hex ├── vpd_ref.hex ├── luns_wlun.hex ├── ref_sense.hex ├── vpd_dev_id.hex ├── vpd_lbpv.hex ├── forwarded_sense.hex ├── vpd_sbl.hex ├── vpd_cpr.hex ├── rep_density_media.hex ├── rep_density_media_typem.hex ├── vpd_tpc.hex ├── vpd_bdce.hex ├── logs_sdeb_aa.hex ├── vpd_zbdc.hex ├── descriptor_sense.hex ├── vpd_fp.hex ├── nvme_dev_self_test.hex ├── rep_density.hex ├── inq_standard.hex ├── rep_zdomains.hex ├── vpd_constituents.hex ├── nvme_identify_ctl.hex ├── z_act_query.hex ├── vpd_di_all.hex ├── logs_last_n.hex ├── opcodes.hex ├── rep_realms.hex ├── modes_sdeb.hex ├── rep_density_typem.hex ├── rep_zones.hex ├── nvme_write_ctl.hex ├── nvme_read_ctl.hex ├── nvme_read_oob_ctl.hex ├── get_elem_status.hex ├── tst_script.sh ├── modes_mm_sdeb.hex └── README ├── AUTHORS ├── scripts ├── Makefile.am ├── lunmask.service ├── scsi-enable-target-scan.sh ├── 40-usb-blacklist.rules ├── 59-fc-wwpn-id.rules ├── 59-scsi-cciss_id.rules ├── 00-scsi-sg3_config.rules ├── scsi_temperature ├── fc_wwpn_id ├── scsi_ready ├── scsi_start ├── scsi_readcap ├── scsi_stop ├── cciss_id ├── README ├── 54-before-scsi-sg3_id.rules └── scsi_mandat ├── examples ├── sdiag_sas_p1_stop.txt ├── sdiag_sas_p0_cjtpat.txt ├── sdiag_sas_p0_prbs9.txt ├── sdiag_sas_p1_prbs15.txt ├── reassign_addr.txt ├── sdiag_sas_p1_cjtpat.txt ├── sdiag_sas_p1_idle.txt ├── README ├── transport_ids.txt ├── sg_unmap_example.txt ├── Makefile.freebsd ├── sg_compare_and_write.txt ├── Makefile └── sg_simple16.c ├── utils ├── Makefile.cygwin ├── Makefile.mingw ├── README ├── Makefile.solaris ├── Makefile.freebsd └── Makefile ├── include ├── sg_lib_names.h ├── sg_cmds.h ├── Makefile.am ├── sg_json_sg_lib.h ├── sg_pt_linux_missing.h ├── sg_linux_inc.h ├── sg_cmds_mmc.h └── sg_pr2serr.h ├── doc ├── scsi_temperature.8 ├── scsi_start.8 ├── scsi_ready.8 ├── scsi_stop.8 ├── README ├── scsi_satl.8 ├── scsi_mandat.8 ├── sg_rdac.8 ├── Makefile.am ├── scsi_readcap.8 ├── sg_emc_trespass.8 ├── sg_read_block_limits.8 ├── sg_rep_pip.8 ├── sg_rtpg.8 ├── sg_rmsn.8 ├── sg_prevent.8 ├── sg_reset_wp.8 ├── sg_referrals.8 ├── sg_scan.8.linux ├── sg_bg_ctl.8 └── sg_test_rwbuf.8 ├── README.sg_start ├── README.iscsi ├── BSD_LICENSE ├── lib ├── BSD_LICENSE ├── Makefile.am └── sg_pr2serr.c ├── src └── BSD_LICENSE ├── COPYING ├── testing ├── sg_json_builder_test.c ├── README ├── Makefile.freebsd ├── Makefile.cyg └── random_write_cp_verify.sh ├── .gitignore ├── .github └── workflows │ └── ci.yml ├── README.tru64 └── getopt_long └── getopt.h /debian/compat: -------------------------------------------------------------------------------- 1 | 10 2 | -------------------------------------------------------------------------------- /NEWS: -------------------------------------------------------------------------------- 1 | See the ChangeLog file. 2 | -------------------------------------------------------------------------------- /debian/sg3-utils.examples: -------------------------------------------------------------------------------- 1 | examples/* 2 | -------------------------------------------------------------------------------- /debian/libsgutils2-2.install: -------------------------------------------------------------------------------- 1 | usr/lib/*.so.* 2 | -------------------------------------------------------------------------------- /bootstrap: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | ./autogen.sh "$@" 4 | -------------------------------------------------------------------------------- /debian/sg3-utils.install: -------------------------------------------------------------------------------- 1 | usr/bin/* 2 | usr/share/man/man8/* 3 | -------------------------------------------------------------------------------- /inhex/vpd_zbdc.raw: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hreinecke/sg3_utils/HEAD/inhex/vpd_zbdc.raw -------------------------------------------------------------------------------- /debian/libsgutils2-dev.install: -------------------------------------------------------------------------------- 1 | usr/include/scsi 2 | usr/lib/*.so 3 | usr/lib/*.la 4 | usr/lib/*.a 5 | -------------------------------------------------------------------------------- /inhex/inq_standard.raw: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hreinecke/sg3_utils/HEAD/inhex/inq_standard.raw -------------------------------------------------------------------------------- /debian/docs: -------------------------------------------------------------------------------- 1 | README 2 | README.sg_start 3 | AUTHORS 4 | COVERAGE 5 | CREDITS 6 | INSTALL 7 | ChangeLog 8 | -------------------------------------------------------------------------------- /AUTHORS: -------------------------------------------------------------------------------- 1 | Douglas Gilbert 2 | 3 | See the CREDITS file for the names of those who have contributed. 4 | -------------------------------------------------------------------------------- /inhex/luns_lu_cong.hex: -------------------------------------------------------------------------------- 1 | 2 | # report_luns_parameter_data 3 | 00 00 00 10 00 00 00 00 4 | 5 | 00 01 00 00 00 00 00 00 6 | 00 01 00 02 00 00 00 00 7 | 8 | -------------------------------------------------------------------------------- /inhex/vpd_sfs.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_sfs.hex 4 | 5 | 00 92 00 0e 00 00 00 00 6 | 00 01 01 01 01 02 02 01 7 | 09 09 8 | -------------------------------------------------------------------------------- /inhex/readcap_zbc.hex: -------------------------------------------------------------------------------- 1 | 2 | # read_capacity_16_parameter_data 3 | 00 00 00 09 18 5f ff ff 00 00 02 00 00 03 00 00 4 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 5 | -------------------------------------------------------------------------------- /inhex/vpd_lbpro.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_lbpro.hex 4 | 5 | 01 b5 00 10 00 00 00 00 6 | 03 01 20 e0 7 | 07 02 10 80 00 00 00 00 8 | -------------------------------------------------------------------------------- /scripts/Makefile.am: -------------------------------------------------------------------------------- 1 | dist_bin_SCRIPTS = scsi_logging_level scsi_mandat scsi_readcap scsi_ready \ 2 | scsi_satl scsi_start scsi_stop scsi_temperature \ 3 | rescan-scsi-bus.sh 4 | -------------------------------------------------------------------------------- /inhex/fixed_sense.hex: -------------------------------------------------------------------------------- 1 | # Test fixed format sense data. Values are in hex. 2 | # Invocation: 'sg_decode_sense -f fixed_sense.hex' [dpg 20220622] 3 | 4 | f0 00 03 00 00 12 34 0a 00 00 00 00 11 00 77 80 5 | 01 98 6 | -------------------------------------------------------------------------------- /inhex/get_lba_status.hex: -------------------------------------------------------------------------------- 1 | 2 | 3 | 0 0 0 34 4 | 0 0 0 6 5 | 6 | 0 0 0 0 0 0 0 0 7 | 11 22 33 0 8 | 9 | 0 0 0 0 10 | 11 | 0 0 0 0 11 22 33 0 12 | 0 0 0 44 13 | 14 | 1 1 0 0 15 | 16 | 0 0 0 0 11 22 33 44 17 | 0 0 0 33 18 | 19 | 11 1 0 0 20 | -------------------------------------------------------------------------------- /scripts/lunmask.service: -------------------------------------------------------------------------------- 1 | [Unit] 2 | Description=Disable LUN masking and scan SCSI Hosts 3 | After=systemd-udev-trigger.service 4 | 5 | [Service] 6 | Type=oneshot 7 | RemainAfterExit=yes 8 | ExecStart=/usr/lib/systemd/scripts/scsi-enable-target-scan.sh 9 | 10 | [Install] 11 | WantedBy=multi-user.target 12 | -------------------------------------------------------------------------------- /inhex/vpd_ref.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This is a manufactured response to an INQUIRY for the 3 | # Referrals VPD page (0xb3 ["ref"]). It may have been 4 | # generated by a call like this: 5 | # sg_vpd -p ref /dev/sg3 -HHHH 6 | 7 | # Referrals VPD page 8 | 00 b3 00 0c 00 00 00 00 9 | 11 22 33 44 00 00 10 00 10 | -------------------------------------------------------------------------------- /inhex/luns_wlun.hex: -------------------------------------------------------------------------------- 1 | 2 | # report_luns_parameter_data 3 | 00 00 00 40 00 00 00 00 4 | 5 | 00 01 00 00 00 00 00 00 6 | 03 08 02 04 01 02 00 01 7 | c1 01 00 00 00 00 00 00 8 | 52 34 00 00 00 00 00 00 9 | 81 44 00 00 00 00 00 00 10 | 11 | 03 09 d2 77 88 99 00 00 12 | e2 77 88 99 aa bb 00 00 13 | 14 | 15 | ff ff ff ff ff ff ff ff 16 | -------------------------------------------------------------------------------- /inhex/ref_sense.hex: -------------------------------------------------------------------------------- 1 | # Test User data segment referral sense data. Values are in hex. 2 | # Invocation: 'sg_decode_sense -f ref_sense.hex' [dpg 20210330] 3 | 4 | 72,0,0,0,0,0,0 38 5 | b,36,1,0 6 | 0,0,0,2,11,11,11,11,22,22,22,22,55,55,55,55,66,66,66,66 1,0,0,7, 2,0,0,8 7 | 0,0,0,1,77,77,77,77,77,77,77,77,88,88,88,88,88,88,88,88, 3,0,0,5 8 | -------------------------------------------------------------------------------- /inhex/vpd_dev_id.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_dev_id.hex 4 | 5 | 00 83 00 48 01 03 00 08 50 00 c5 00 30 11 cb 2b 6 | 61 93 00 08 50 00 c5 00 30 11 cb 29 61 94 00 04 7 | 00 00 00 01 61 a3 00 08 50 00 c5 00 30 11 cb 28 8 | 03 28 00 18 6e 61 61 2e 35 30 30 30 43 35 30 30 9 | 33 30 31 31 43 42 32 38 00 00 00 00 10 | -------------------------------------------------------------------------------- /inhex/vpd_lbpv.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This is a manufactured response to an INQUIRY for the 3 | # Logical Block Provisioning VPD page (0xb2 ["lbpv"]). It may 4 | # have been generated by a call like this: 5 | # sg_vpd -p lbpv /dev/sg3 -HHHH 6 | 7 | # Logical block provisioning VPD page 8 | 00 b2 00 10 00 01 00 00 9 | 01 03 00 08 51 22 33 44 55 66 77 88 10 | -------------------------------------------------------------------------------- /inhex/forwarded_sense.hex: -------------------------------------------------------------------------------- 1 | # Test forwarded sense data. Values are in hex. 2 | # Invocation: 'sg_decode_sense -f forwarded_sense.hex' [dpg 20210330] 3 | 4 | # descriptor header 5 | 72 6 18 7 0 0 0 1c 6 | 7 | # Forwarded sense [len=12] 8 | c a 1 2 9 | 72 6 18 7 0 0 0 0 10 | 11 | # Information [len=12] 12 | 0 a 80 0 11 22 33 44 55 66 77 88 13 | 14 | # FRU [len=4] 15 | 3 2 0 16 | 99 17 | -------------------------------------------------------------------------------- /inhex/vpd_sbl.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This is a manufactured response to an INQUIRY for the 3 | # Supported block lengths and protection types VPD page (0xb4 ["sbl"]). 4 | # It may have been generated by a call like this: 5 | # sg_vpd -p sbl /dev/sg3 -HHHH 6 | 7 | # Supported block lengths and protection types VPD page 8 | 00 b4 00 10 9 | 00 00 02 00 47 07 00 00 10 | 00 00 10 00 47 07 00 00 11 | -------------------------------------------------------------------------------- /examples/sdiag_sas_p1_stop.txt: -------------------------------------------------------------------------------- 1 | # This is the hex for a SAS protocol specific diagnostic 2 | # page. It will attempt to stop phy identifier 1 of the 3 | # given device producing a test pattern. 4 | # N.B. This should make phy id 1 usable for SAS protocols again. 5 | # 6 | # Usage example: 'sg_senddiag --pf --raw=- /dev/sg2 < {this_file}' 7 | # 8 | 3f,6,0,1c,1,0,2,9, 9 | 0,0,0,0,0,0,0,0, 10 | 0,0,0,0,0,0,0,0, 11 | 0,0,0,0,0,0,0,0 12 | -------------------------------------------------------------------------------- /examples/sdiag_sas_p0_cjtpat.txt: -------------------------------------------------------------------------------- 1 | # This is the hex for a SAS protocol specific diagnostic 2 | # page. It will attempt to put phy identifier 0 of the 3 | # given device into CJTPAT (jitter pattern) generation mode. 4 | # Physical transmission speed is 3 Gbps 5 | # N.B. This will turn the receiver off on phy id 0. 6 | # 7 | # Usage example: 'sg_senddiag --pf --raw=- /dev/sg2 < {this_file}' 8 | # 9 | 3f,6,0,1c,0,1,2,9, 10 | 0,0,0,0,0,0,0,0, 11 | 0,0,0,0,0,0,0,0, 12 | 0,0,0,0,0,0,0,0 13 | -------------------------------------------------------------------------------- /examples/sdiag_sas_p0_prbs9.txt: -------------------------------------------------------------------------------- 1 | # This is the hex for a SAS protocol specific diagnostic 2 | # page. It will attempt to put phy identifier 0 of the 3 | # given device into PRBS9 (jitter pattern) generation mode. 4 | # Physical transmission speed is 22.5 Gbps 5 | # N.B. This will turn the receiver off on phy id 0. 6 | # 7 | # Usage example: 'sg_senddiag --pf --raw=- /dev/sg2 < {this_file}' 8 | # 9 | 3f,6,0,1c,0,1,3,c, 10 | 0,0,0,0,0,0,0,0, 11 | 0,0,0,0,0,0,0,0, 12 | 0,0,0,0,0,0,0,0 13 | -------------------------------------------------------------------------------- /examples/sdiag_sas_p1_prbs15.txt: -------------------------------------------------------------------------------- 1 | # This is the hex for a SAS protocol specific diagnostic 2 | # page. It will attempt to put phy identifier 1 of the 3 | # given device into PRBS15 (jitter pattern) generation mode. 4 | # Physical transmission speed is 22.5 Gbps 5 | # N.B. This will turn the receiver off on phy id 1. 6 | # 7 | # Usage example: 'sg_senddiag --pf --raw=- /dev/sg2 < {this_file}' 8 | # 9 | 3f,6,0,1c,1,1,4,c, 10 | 0,0,0,0,0,0,0,0, 11 | 0,0,0,0,0,0,0,0, 12 | 0,0,0,0,0,0,0,0 13 | -------------------------------------------------------------------------------- /scripts/scsi-enable-target-scan.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | # -*- mode: shell-script; indent-tabs-mode: nil; sh-basic-offset: 4; -*- 3 | # ex: ts=8 sw=4 sts=4 et filetype=sh 4 | 5 | MODPARM=/sys/module/scsi_mod/parameters 6 | if [ -w "$MODPARM/scan" ] ; then 7 | scan_type=$(cat $MODPARM/scan) 8 | if [ "$scan_type" = "manual" ] ; then 9 | echo sync > $MODPARM/scan 10 | 11 | for shost in /sys/class/scsi_host/host* ; do 12 | echo '- - -' > ${shost}/scan 13 | done 14 | fi 15 | fi 16 | -------------------------------------------------------------------------------- /examples/reassign_addr.txt: -------------------------------------------------------------------------------- 1 | # This file is an example for the sg_reassign utility. 2 | # That utility can take one or more logical block addresses from stdin when 3 | # either the '--address=-" or "-a -" option is given on the command line. 4 | 5 | # To see logical block addresses placed in the command parameter block 6 | # without executing them command try something like: 7 | # 'sg_reassign --address=- --dummy -vv /dev/sda < reassign_addr.txt 8 | 9 | 1,34,0x33,0X444 0x89abcde 0xdeadbeef # 6 lba's 10 | 11 | # dpg 20070130 12 | -------------------------------------------------------------------------------- /examples/sdiag_sas_p1_cjtpat.txt: -------------------------------------------------------------------------------- 1 | # This is the hex for a SAS protocol specific diagnostic 2 | # page. It will attempt to put phy identifier 1 of the 3 | # given device into CJTPAT (jitter pattern) generation mode. 4 | # Physical transmission speed is 3 Gbps 5 | # See sdiag_sas_p1_stop.txt to turn off this test pattern. 6 | # N.B. This will turn the receiver off on phy id 1. 7 | # 8 | # Usage example: 'sg_senddiag --pf --raw=- /dev/sg2 < {this_file}' 9 | # 10 | 3f,6,0,1c,1,1,2,9, 11 | 0,0,0,0,0,0,0,0, 12 | 0,0,0,0,0,0,0,0, 13 | 0,0,0,0,0,0,0,0 14 | -------------------------------------------------------------------------------- /scripts/40-usb-blacklist.rules: -------------------------------------------------------------------------------- 1 | # 2 | # Blacklist specific USB devices 3 | # 4 | # don't inquire sn and di on broken devices (https://bugzilla.suse.com/show_bug.cgi?id=840054) 5 | 6 | ACTION!="add|change", GOTO="usb_blacklist_end" 7 | KERNEL!="sd*[!0-9]|sr*", GOTO="usb_blacklist_end" 8 | 9 | # unknown device 10 | ATTRS{idVendor}=="0aec", ATTRS{idProduct}=="3260", ENV{ID_SCSI_INQUIRY}="1" 11 | # Sony/JMicron port replicator 12 | ATTRS{idVendor}=="054c", ATTRS{idProduct}=="06a0", ENV{ID_SCSI_INQUIRY}="1" 13 | 14 | LABEL="usb_blacklist_end" 15 | -------------------------------------------------------------------------------- /examples/sdiag_sas_p1_idle.txt: -------------------------------------------------------------------------------- 1 | # This is the hex for a SAS protocol specific diagnostic 2 | # page. It will attempt to put phy identifier 1 of the 3 | # given device into IDLE (continuously transmit idle dwords) mode. 4 | # Physical transmission speed is 3 Gbps (last number on first 5 | # active line can be 8 for 1.5Gbps, 9 for 3Gbps and 10 for 6Gbps). 6 | # See sdiag_sas_p1_stop.txt to turn off this test pattern. 7 | # N.B. This will turn the receiver off on phy id 1. 8 | # 9 | # Usage example: 'sg_senddiag --pf --raw=- /dev/sg2 < {this_file}' 10 | # 11 | 3f,6,0,1c,1,1,12,9, 12 | 0,0,0,0,0,0,0,0, 13 | 0,0,0,0,0,0,0,0, 14 | 0,0,0,0,0,0,0,0 15 | -------------------------------------------------------------------------------- /inhex/vpd_cpr.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_cpr.hex 4 | 5 | # Dummy data for Concurrent positioning ranges VPD page 6 | 00 b9 00 7c 00 00 00 00 7 | 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 8 | 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 9 | # after 64 byte header there is the first LBA range descriptor (32 bytes) 10 | 01 02 00 00 00 00 00 00 11 | 00 00 00 00 00 00 00 00 12 | 00 00 00 00 10 00 00 00 13 | 00 00 00 00 00 00 00 00 14 | # second LBA range descriptor (32 bytes) 15 | 02 02 00 00 00 00 00 00 16 | 00 00 00 00 10 00 00 00 17 | 00 00 00 00 10 00 00 00 18 | 00 00 00 00 00 00 00 00 19 | -------------------------------------------------------------------------------- /inhex/rep_density_media.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This file contains the response to SCSI REPORT DENSITY SUPPORTED command 3 | # using the sg_rep_density utility. This file was generated with: 4 | # sg_rep_density --media -HHH /dev/sg4 > rep_density_media.hex 5 | # where /dev/sg4 was a LTO-4 tape drive. To decode that file containing 6 | # hexadecimal in ASCII use: 7 | # sg_rep_density --inhex=rep_density_media.hex 8 | # The --media option is not needed in the decode invocation. 9 | 10 | 00 36 00 00 58 58 a0 00 00 00 3b 26 00 7f 05 00 11 | 00 17 85 3e 4c 54 4f 2d 43 56 45 20 55 2d 35 31 12 | 36 20 20 20 55 6c 74 72 69 75 6d 20 35 2f 31 36 13 | 54 20 20 20 20 20 20 20 14 | -------------------------------------------------------------------------------- /inhex/rep_density_media_typem.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This file contains the response to SCSI REPORT DENSITY SUPPORTED command 3 | # using the sg_rep_density utility. This file was generated with: 4 | # sg_rep_density -M -t -HHH /dev/sg4 > rep_density_media_typem.hex 5 | # where /dev/sg4 was a LTO-4 tape drive. To decode that file containing 6 | # hexadecimal in ASCII use: 7 | # sg_rep_density --typem -i rep_density_media_typem.hex 8 | # The --typem option is required in the decode invocation. 9 | 10 | 00 3a 00 00 00 00 00 34 01 58 00 00 00 00 00 00 11 | 00 00 00 7f 03 4e 00 00 48 50 20 20 20 20 20 20 12 | 4c 54 4f 35 44 61 74 61 55 6c 74 72 69 75 6d 20 13 | 35 20 44 61 74 61 20 54 61 70 65 20 14 | -------------------------------------------------------------------------------- /scripts/59-fc-wwpn-id.rules: -------------------------------------------------------------------------------- 1 | # 2 | # FC WWPN-based by-path links 3 | # 4 | 5 | ACTION!="add|change", GOTO="fc_wwpn_end" 6 | KERNEL!="sd*", GOTO="fc_wwpn_end" 7 | 8 | ENV{DEVTYPE}=="disk", IMPORT{program}="fc_wwpn_id %p" 9 | ENV{DEVTYPE}=="partition", IMPORT{parent}="FC_*" 10 | ENV{FC_TARGET_WWPN}!="?*", GOTO="fc_wwpn_end" 11 | ENV{FC_INITIATOR_WWPN}!="?*", GOTO="fc_wwpn_end" 12 | ENV{FC_TARGET_LUN}!="?*", GOTO="fc_wwpn_end" 13 | 14 | ENV{DEVTYPE}=="disk", SYMLINK+="disk/by-path/fc-$env{FC_INITIATOR_WWPN}-$env{FC_TARGET_WWPN}-lun-$env{FC_TARGET_LUN}" 15 | ENV{DEVTYPE}=="partition", SYMLINK+="disk/by-path/fc-$env{FC_INITIATOR_WWPN}-$env{FC_TARGET_WWPN}-lun-$env{FC_TARGET_LUN}-part%n" 16 | 17 | LABEL="fc_wwpn_end" 18 | -------------------------------------------------------------------------------- /inhex/vpd_tpc.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_tpc.hex 4 | 5 | 00 8f 00 8c 6 | 7 | 00 00 00 20 8 | 00 00 00 00 00 00 01 23 00 00 00 3c 9 | 00 00 00 1e 00 00 00 99 88 77 66 55 00 00 00 44 10 | 55 66 77 88 11 | 12 | 00 01 00 10 13 | 0d 14 | 00 00 15 | 03 00 16 | 12 00 17 | 83 02 10 11 18 | 84 01 07 19 | 00 00 # pad 20 | 21 | 00 04 00 1c 22 | 00 00 00 00 00 1c 00 40 00 01 22 33 23 | 00 99 88 77 00 00 00 00 00 00 00 00 00 00 00 00 24 | 25 | 00 08 00 04 26 | 02 27 | 02 e9 28 | 00 # pad 29 | 30 | 00 0c 00 0c 31 | 00 08 32 | 00 00 33 | 00 01 34 | c0 00 35 | ff ff 36 | 00 00 # pad 37 | 38 | 00 0d 00 14 39 | 12 40 | # UUID 41 | 10 00 11 22 33 44 55 66 77 88 99 aa bb cc dd ee 42 | fe dc 43 | 00 # pad 44 | -------------------------------------------------------------------------------- /inhex/vpd_bdce.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This is a manufactured response to an INQUIRY for the 3 | # Block device characteristics extension VPD page (0xb5 ["bdce"]). 4 | # It may have been generated by a call like this: 5 | # sg_vpd -p bdce /dev/sg3 -HHHH 6 | 7 | # Block device characteristics extension VPD page 8 | 00 b5 00 7c 9 | 00 03 05 0e 00 00 00 06 00 00 00 03 10 | 11 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 12 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 13 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 14 | 15 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 16 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 17 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 18 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 19 | -------------------------------------------------------------------------------- /utils/Makefile.cygwin: -------------------------------------------------------------------------------- 1 | # Assumes Makefile is used in a cygwin shell 2 | 3 | SHELL = /bin/sh 4 | 5 | CC = gcc 6 | LD = gcc 7 | 8 | EXECS = hxascdmp 9 | 10 | EXE_S = hxascdmp.exe 11 | 12 | # OS_FLAGS = -DSG_LIB_WIN32 -DSPTD 13 | OS_FLAGS = -DSG_LIB_WIN32 14 | LARGE_FILE_FLAGS = -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 15 | EXTRA_FLAGS = $(OS_FLAGS) $(LARGE_FILE_FLAGS) 16 | 17 | # CFLAGS = -O2 -Wall -W $(EXTRA_FLAGS) 18 | CFLAGS = -g -O2 -Wall -W $(EXTRA_FLAGS) 19 | # CFLAGS = -g -O2 -Wall -W -pedantic -std=c99 $(EXTRA_FLAGS) 20 | 21 | LDFLAGS = 22 | 23 | all: $(EXECS) 24 | 25 | clean: 26 | rm *.o $(EXE_S) 27 | 28 | .c.o: 29 | $(CC) $(INCLUDES) $(CFLAGS) $(S_CFLAGS) -c -o $@ $< 30 | 31 | hxascdmp: hxascdmp.o 32 | $(LD) -o $@ $(LDFLAGS) $@.o 33 | 34 | -------------------------------------------------------------------------------- /inhex/logs_sdeb_aa.hex: -------------------------------------------------------------------------------- 1 | # This page was generated by: 2 | # sg_logs -A -HHHH /dev/sg0 3 | # where /dev/sg0 was a scsi_debug device on a Linux system 4 | # 5 | # This file can be decoded using: 6 | # sg_logs -A -i 7 | # 8 | 9 | # Supported log pages log page [0x0]: 10 | 00 00 00 03 00 0d 2f 11 | 12 | # Supported log pages and subpages log page [0x0, 0xff]: 13 | 40 ff 00 0e 00 00 00 ff 0d 00 0d 01 0d ff 2f 00 14 | 2f ff 15 | 16 | # Temperature log page [0xd] 17 | 0d 00 00 0c 00 00 03 02 00 26 00 01 03 02 00 41 18 | 19 | # Environmental reporting log page [0xd,0x1] 20 | 4d 01 00 18 00 00 23 08 00 28 48 ff 2d 12 00 00 21 | 01 00 23 08 00 37 48 23 37 2d 00 00 22 | 23 | # Informational exceptions log page [0x2f] 24 | 2f 00 00 07 00 00 03 03 00 00 26 25 | -------------------------------------------------------------------------------- /debian/README.debian4: -------------------------------------------------------------------------------- 1 | For whatever reason Debian build scripts (e.g. debhelper and dbclean) 2 | seem to have changed in such a way to be Debian 4.0 ("etch") unfriendly. 3 | 4 | So when the ./build_debian.sh script is called on a Debian 4.0 system, 5 | it fails saying the debhelper is too old. That can be fixed by editing 6 | the 'control' file, changing this line: 7 | Build-Depends: debhelper (>> 7), libtool, libcam-dev [kfreebsd-i386 kfreebsd-amd64] 8 | to: 9 | Build-Depends: debhelper, libtool, libcam-dev [kfreebsd-i386 kfreebsd-amd64] 10 | 11 | The script then dies in dbclean and the hack to get around that is to 12 | edit the 'compat' file. It contains "7" which needs to be changed to 13 | "4". Evidently "4" is deprecated and "5" is preferable and should work. 14 | 15 | -------------------------------------------------------------------------------- /include/sg_lib_names.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_LIB_NAMES_H 2 | #define SG_LIB_NAMES_H 3 | 4 | /* 5 | * Copyright (c) 2022-2023 Douglas Gilbert. 6 | * All rights reserved. 7 | * Use of this source code is governed by a BSD-style 8 | * license that can be found in the BSD_LICENSE file. 9 | * 10 | * SPDX-License-Identifier: BSD-2-Clause 11 | */ 12 | 13 | #include 14 | 15 | #include "sg_lib_data.h" 16 | 17 | #ifdef __cplusplus 18 | extern "C" { 19 | #endif 20 | 21 | extern const struct sg_lib_simple_value_name_t sg_lib_names_mode_arr[]; 22 | extern const struct sg_lib_simple_value_name_t sg_lib_names_vpd_arr[]; 23 | 24 | extern const size_t sg_lib_names_mode_len; 25 | extern const size_t sg_lib_names_vpd_len; 26 | 27 | #ifdef __cplusplus 28 | } 29 | #endif 30 | 31 | #endif /* end of SG_LIB_NAMES */ 32 | -------------------------------------------------------------------------------- /utils/Makefile.mingw: -------------------------------------------------------------------------------- 1 | # Assumes makefile is used in a MSYS shell with a MinGW compiler available. 2 | 3 | SHELL = /bin/sh 4 | 5 | CC = gcc 6 | LD = gcc 7 | 8 | EXECS = hxascdmp 9 | 10 | EXE_S = hxascdmp.exe 11 | 12 | # OS_FLAGS = -DSG_LIB_WIN32 -DSG_LIB_MINGW -DSPTD 13 | OS_FLAGS = -DSG_LIB_WIN32 -DSG_LIB_MINGW 14 | LARGE_FILE_FLAGS = -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 15 | EXTRA_FLAGS = $(OS_FLAGS) $(LARGE_FILE_FLAGS) 16 | 17 | # CFLAGS = -O2 -Wall -W $(EXTRA_FLAGS) 18 | CFLAGS = -g -O2 -Wall -W $(EXTRA_FLAGS) 19 | # CFLAGS = -g -O2 -Wall -W -pedantic -std=c99 $(EXTRA_FLAGS) 20 | 21 | LDFLAGS = 22 | 23 | all: $(EXECS) 24 | 25 | clean: 26 | rm *.o $(EXE_S) 27 | 28 | .c.o: 29 | $(CC) $(INCLUDES) $(CFLAGS) $(S_CFLAGS) -c -o $@ $< 30 | 31 | hxascdmp: hxascdmp.o 32 | $(LD) -o $@ $(LDFLAGS) $@.o 33 | 34 | -------------------------------------------------------------------------------- /inhex/vpd_zbdc.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_zbdc.hex 4 | 5 | # Zoned block device characteristics VPD page [0xb6] 6 | # Host managed zoned block device model; pdt=0x14 7 | 14 b6 00 3c 8 | # ZBD extension=0; AAORb=0; URSWRZ=0 9 | 00 00 00 00 10 | 11 | # Optimal # of open sequential write preferred 12 | 00 00 00 00 13 | 14 | # Optimal # of open non-sequentailly written sequential write preferred 15 | 00 00 00 00 16 | 17 | # maximum # of open sequential write required 18 | 00 00 00 08 19 | 20 | # Zone alignment mode=1 (constant zone lengths) 21 | 00 00 00 01 22 | 23 | # Zone starting LBA granularity 24 | 00 00 00 02 00 00 00 00 25 | 26 | 27 | # pad to total length of 64 bytes 28 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 29 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 30 | -------------------------------------------------------------------------------- /scripts/59-scsi-cciss_id.rules: -------------------------------------------------------------------------------- 1 | # cciss compat rules 2 | 3 | ACTION!="add|change", GOTO="cciss_compat_end" 4 | KERNEL!="sd*", GOTO="cciss_compat_end" 5 | ENV{ID_VENDOR}!="HP", ENV{ID_VENDOR}!="COMPAQ", GOTO="cciss_compat_end" 6 | ENV{ID_MODEL}!="LOGICAL_VOLUME", GOTO="cciss_compat_end" 7 | 8 | ENV{DEVTYPE}=="disk", DRIVERS=="hpsa", IMPORT{program}="cciss_id %p" 9 | ENV{DEVTYPE}=="partition", IMPORT{parent}="ID_*" 10 | ENV{ID_CCISS}!="?*", GOTO="cciss_compat_end" 11 | 12 | ENV{DEVTYPE}=="disk", SYMLINK+="cciss/$env{ID_CCISS}" 13 | ENV{DEVTYPE}=="disk", ENV{ID_SERIAL}=="?*", SYMLINK+="disk/by-id/cciss-$env{ID_SERIAL}" 14 | 15 | ENV{DEVTYPE}=="partition", SYMLINK+="cciss/$env{ID_CCISS}p%n" 16 | ENV{DEVTYPE}=="partition", ENV{ID_SERIAL}=="?*", SYMLINK+="disk/by-id/cciss-$env{ID_SERIAL}-part%n" 17 | 18 | LABEL="cciss_compat_end" 19 | -------------------------------------------------------------------------------- /examples/README: -------------------------------------------------------------------------------- 1 | Building files in this directory depends on several files being already 2 | built in the ../lib directory. So to build files here, the ./configure 3 | needs to be executed in the parent directory followed by changing 4 | directory to the lib directory and calling 'make' there. 5 | Another way is to do a top level 'make' after the ./configure which 6 | will make the libraries followed by all the utilities in the src/ 7 | directory. To make them in FreeBSD use 'make -f Makefile.freebsd' . 8 | 9 | There is an brief explanation of each example in the README file in 10 | the main (i.e. this directory's parent) directory. There are also 11 | some notes at the top of each source file. 12 | 13 | Some files that were previously in this directory have been moved to 14 | the 'testing' directory. 15 | 16 | Douglas Gilbert 17 | 19th January 2018 18 | -------------------------------------------------------------------------------- /inhex/descriptor_sense.hex: -------------------------------------------------------------------------------- 1 | # Test descriptor format sense data. Values are in hex. 2 | # Invocation: 'sg_decode_sense -f descriptor_sense.hex' [dpg 20220626] 3 | 4 | 5 | # unrec_err, excessive_writes, sdat_ovfl, additional_len=? 6 | 72 01 03 02 80 00 00 4c 7 | 8 | # Information: 0x11223344556677bb 9 | 00 0a 80 00 11 22 33 44 55 66 77 bb 10 | 11 | # command specific: 0x3344556677bbccff 12 | 01 0a 00 00 33 44 55 66 77 bb cc ff 13 | 14 | # sense key specific: SKSV=1, actual_count=257 (hex: 0x101) 15 | 02 06 00 00 80 01 01 00 16 | 17 | # field replaceable code=0x45 18 | 03 02 00 45 19 | 20 | # another progress report indicator 21 | 0a 06 02 01 02 00 32 01 22 | 23 | # incorrect length indicator (ILI) 24 | 05 02 00 20 25 | 26 | # user data segment referral 27 | 0b 1a 01 00 28 | 00 00 00 01 01 02 03 04 05 06 07 08 29 | 01 02 03 04 55 06 07 08 30 | 02 00 12 34 31 | -------------------------------------------------------------------------------- /inhex/vpd_fp.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_fp.hex 4 | 5 | # Dummy data for Format presets VPD page 6 | 00 b8 00 80 7 | 8 | # after 4 byte header here is the first Format preset descriptor (64 bytes) 9 | 00 00 01 00 10 | 01 0 0 00 11 | 01 00 00 00 12 | 0 0 0 0 13 | 00 00 00 00 00 ff ff ff # last LBA 14 | 0 0 0 0 0 0 0 0 0 0 0 0 0 0 15 | 00 00 # FMPTINFO, Protection field usage and protection interval exp 16 | 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 17 | 0 0 0 0 0 0 0 0 18 | 19 | # second Format preset descriptor (64 bytes) 20 | 00 00 01 01 21 | 02 0 0 00 22 | 01 00 00 00 23 | 0 0 0 0 24 | 00 00 00 00 01 ff ff ff # last LBA 25 | 0 0 0 0 0 0 0 0 0 0 0 0 0 0 26 | 00 00 # FMPTINFO, Protection field usage and protection interval exp 27 | # host-aware zones schema type specific information 28 | 5 ff 29 | 0 0 0 0 0 0 0 0 0 0 30 | 20 00 00 00 31 | 0 0 0 0 32 | -------------------------------------------------------------------------------- /inhex/nvme_dev_self_test.hex: -------------------------------------------------------------------------------- 1 | # 64 byte NVMe Device Self Test command (an Admin command) that is suitable 2 | # for: 3 | # sg_raw --cmdfile= 4 | # 5 | # There is no data-in or data-out associated with this command. This command 6 | # is optional so check the Identify controller command response to see if 7 | # it is supported. 8 | # 9 | # The following invocation will self test the controller and all its 10 | # namespaces (since nsid=0xffffffff) and does a "short" self test on each 11 | # one (since CDW10 is 0x1). 12 | 13 | 14 00 00 00 ff ff ff ff 00 00 00 00 00 00 00 00 14 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 15 | 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 16 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 17 | 18 | # A typical invocation in Linux and FreeBSD would look like this: 19 | # sg_raw --cmdfile=nvme_dev_self_test.hex /dev/nvme0 20 | # 21 | -------------------------------------------------------------------------------- /inhex/rep_density.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This file contains the response to SCSI REPORT DENSITY SUPPORTED command 3 | # using the sg_rep_density utility. This file was generated with: 4 | # sg_rep_density -HHH /dev/sg4 > rep_density.hex 5 | # where /dev/sg4 was a LTO-4 tape drive. To decode that file containing 6 | # hexadecimal in ASCII use: 7 | # sg_rep_density --inhex=rep_density.hex 8 | 9 | 00 9e 00 00 44 44 00 00 00 00 25 a6 00 7f 02 c0 10 | 00 06 1a 80 4c 54 4f 2d 43 56 45 20 55 2d 33 31 11 | 36 20 20 20 55 6c 74 72 69 75 6d 20 33 2f 31 36 12 | 54 20 20 20 20 20 20 20 46 46 80 00 00 00 31 b5 13 | 00 7f 03 80 00 0c 35 00 4c 54 4f 2d 43 56 45 20 14 | 55 2d 34 31 36 20 20 20 55 6c 74 72 69 75 6d 20 15 | 34 2f 31 36 54 20 20 20 20 20 20 20 58 58 a0 00 16 | 00 00 3b 26 00 7f 05 00 00 16 e3 60 4c 54 4f 2d 17 | 43 56 45 20 55 2d 35 31 36 20 20 20 55 6c 74 72 18 | 69 75 6d 20 35 2f 31 36 54 20 20 20 20 20 20 20 19 | -------------------------------------------------------------------------------- /include/sg_cmds.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_CMDS_H 2 | #define SG_CMDS_H 3 | 4 | /******************************************************************** 5 | * This header did contain wrapper declarations for many SCSI commands 6 | * up until sg3_utils version 1.22 . In that version, the command 7 | * wrappers were broken into two groups, the 'basic' ones found in the 8 | * "sg_cmds_basic.h" header and the 'extra' ones found in the 9 | * "sg_cmds_extra.h" header. This header now simply includes those two 10 | * headers. 11 | * In sg3_utils version 1.26 the sg_cmds_mmc.h header was added and 12 | * contains some MMC specific commands. 13 | * The corresponding function definitions are found in the sg_cmds_basic.c, 14 | * sg_cmds_extra.c and sg_cmds_mmc.c files. 15 | ********************************************************************/ 16 | 17 | #include "sg_cmds_basic.h" 18 | #include "sg_cmds_extra.h" 19 | #include "sg_cmds_mmc.h" 20 | 21 | #endif 22 | -------------------------------------------------------------------------------- /scripts/00-scsi-sg3_config.rules: -------------------------------------------------------------------------------- 1 | # Configuration for SCSI device identification 2 | 3 | # To apply changes, copy this file to /etc/udev/rules.d and edit to suit your needs. 4 | # DO NOT EDIT THIS FILE IN PLACE! 5 | 6 | ACTION!="add|change", GOTO="scsi_identify_end" 7 | SUBSYSTEMS=="scsi", GOTO="scsi_identify" 8 | GOTO="scsi_identify_end" 9 | LABEL="scsi_identify" 10 | 11 | # Set ID_SCSI_INQUIRY to 0 to force running "sg_inq" for obtaining device IDs 12 | # from SCSI VPDs, rather than looking them up in sysfs (not recommended). 13 | ENV{ID_SCSI_INQUIRY}="" 14 | 15 | # Set enabled unreliable sources for setting the ID_SERIAL property. 16 | # See 55-scsi-sg3_id.rules for detailed documentation. 17 | ENV{.SCSI_ID_SERIAL_SRC}="T" 18 | 19 | # Set enabled unreliable sources for creating additional /dev/disk/by-id/scsi* symlinks. 20 | # See 58-scsi-sg3_symlink.rules for detailed documentation. 21 | ENV{.SCSI_SYMLINK_SRC}="" 22 | 23 | LABEL="scsi_identify_end" 24 | -------------------------------------------------------------------------------- /utils/README: -------------------------------------------------------------------------------- 1 | This directory contains these utilities: 2 | - hxascdmp: takes a binary stream and converts it to hexadecimal ASCII 3 | which is sent to stdout. The incoming binary stream can either be 4 | from a file or, in the absence of a file name, from stdin. Similar to 5 | the Unix "od" command. By default, it decodes 16 bytes per line with 6 | an ASCII interpretation to the right of each line. See its 7 | hxascdmp(1) man page. 8 | - sg_chk_asc and tst_sg_lib: are no longer here, they have been moved 9 | to the 'testing' directory (a sibling of this directory). 10 | 11 | 12 | By default, the Makefile only builds the hxascdmp utility. The 'Makefile' 13 | file (i.e. with no suffix) builds for Linux; the 'Makefile.freebsd' file 14 | builds for FreeBSD (e.g. 'make -f Makefile.freebsd'); the 15 | 'Makefile.solaris' file builds for Solaris; the 'Makefile.mingw' builds 16 | in the Windows MinGW environment (e.g. msys shell); and 'Makefile.cygwin' 17 | builds in the Windows Cygwin environment. 18 | 19 | Douglas Gilbert 20 | 4th November 2017 21 | -------------------------------------------------------------------------------- /utils/Makefile.solaris: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/man 6 | 7 | CC = gcc 8 | LD = gcc 9 | 10 | EXECS = hxascdmp 11 | 12 | MAN_PGS = 13 | MAN_PREF = man8 14 | 15 | CFLAGS = -g -O2 -W 16 | # CFLAGS = -g -O2 -W -pedantic -std=c99 17 | 18 | LDFLAGS = 19 | 20 | all: $(EXECS) 21 | 22 | depend dep: 23 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 24 | done > .depend 25 | 26 | clean: 27 | /bin/rm -f *.o $(EXECS) core .depend 28 | 29 | hxascdmp: hxascdmp.o 30 | $(LD) -o $@ $(LDFLAGS) $@.o 31 | 32 | 33 | install: $(EXECS) 34 | install -d $(INSTDIR) 35 | for name in $(EXECS); \ 36 | do install -s -f $(INSTDIR) $$name; \ 37 | done 38 | install -d $(MANDIR)/$(MAN_PREF) 39 | for mp in $(MAN_PGS); \ 40 | do install -m 644 -f $(MANDIR)/$(MAN_PREF) $$mp; \ 41 | done 42 | 43 | uninstall: 44 | dists="$(EXECS)"; \ 45 | for name in $$dists; do \ 46 | rm -f $(INSTDIR)/$$name; \ 47 | done 48 | for mp in $(MAN_PGS); do \ 49 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 50 | done 51 | 52 | -------------------------------------------------------------------------------- /utils/Makefile.freebsd: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/man 6 | 7 | CC = clang 8 | LD = clang 9 | 10 | EXECS = hxascdmp 11 | 12 | MAN_PGS = 13 | MAN_PREF = man8 14 | 15 | CFLAGS = -g -O2 -W 16 | # CFLAGS = -g -O2 -W -pedantic -std=c99 17 | 18 | LDFLAGS = 19 | 20 | all: $(EXECS) 21 | 22 | depend dep: 23 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 24 | done > .depend 25 | 26 | clean: 27 | /bin/rm -f *.o $(EXECS) core .depend 28 | 29 | hxascdmp: hxascdmp.o 30 | $(LD) -o $@ $(LDFLAGS) $@.o 31 | 32 | 33 | install: $(EXECS) 34 | install -d $(INSTDIR) 35 | for name in $(EXECS); \ 36 | do install -s -m 755 $$name $(INSTDIR); \ 37 | done 38 | install -d $(MANDIR)/$(MAN_PREF) 39 | for mp in $(MAN_PGS); \ 40 | do install -m 644 $$mp $(MANDIR)/$(MAN_PREF); \ 41 | gzip -9f $(MANDIR)/$(MAN_PREF)/$$mp; \ 42 | done 43 | 44 | uninstall: 45 | dists="$(EXECS)"; \ 46 | for name in $$dists; do \ 47 | rm -f $(INSTDIR)/$$name; \ 48 | done 49 | for mp in $(MAN_PGS); do \ 50 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 51 | done 52 | 53 | -------------------------------------------------------------------------------- /inhex/inq_standard.hex: -------------------------------------------------------------------------------- 1 | # This file contains the ASCII hex of a SCSI INQUIRY command 2 | # 'standard' response. In this case non-standard responses refers 3 | # to responses contain VPD page that are also fetched with the 4 | # SCSI INQUIRY command. 5 | 6 | # The response in this file can be decoded with: 7 | # sg_inq --inhex=inq_standard.hex 8 | # or 9 | # sg_vpd --inhex=inq_standard.hex --page=sinq 10 | # 11 | # The sg_inq utility defaults to the 'standard' INQUIRY while the 12 | # sg_vpd utility defaults to the "Supported VPD pages" VPD page. 13 | # Hence sg_vpd needs the extra option '--page=sinq' which says the 14 | # VPD page is the standard inquiry. Strictly speaking the standard 15 | # INQUIRY is not a VPD page but probably would be if SCSI was not 16 | # 40 years old and highly values backward compatibility. 17 | 18 | 00 00 07 02 5b 00 10 0a 4c 69 6e 75 78 20 20 20 19 | 73 63 73 69 5f 64 65 62 75 67 20 20 20 20 20 20 20 | 30 31 39 31 32 30 32 31 30 35 32 30 00 00 00 00 21 | 00 00 00 00 00 00 00 00 00 00 00 c0 05 c0 06 00 22 | 21 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 23 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 24 | -------------------------------------------------------------------------------- /scripts/scsi_temperature: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | ################################################################### 4 | # 5 | # Check the temperature of the given SCSI device(s). 6 | # 7 | # This script assumes the sg3_utils package is installed. 8 | # 9 | ################################################################## 10 | 11 | verbose="" 12 | 13 | usage() 14 | { 15 | echo "Usage: scsi_temperature [-h] [-v] +" 16 | echo " where:" 17 | echo " -h, --help print usage message" 18 | echo " -v, --verbose more verbose output" 19 | echo "" 20 | echo "Use SCSI LOG SENSE command to fetch temperature of each " 21 | } 22 | 23 | opt="$1" 24 | while test ! -z "$opt" -a -z "${opt##-*}"; do 25 | opt=${opt#-} 26 | case "$opt" in 27 | h|-help) usage ; exit 0 ;; 28 | v|-verbose) verbose="-v" ;; 29 | vv) verbose="-vv" ;; 30 | *) echo "Unknown option: -$opt " ; exit 1 ;; 31 | esac 32 | shift 33 | opt="$1" 34 | done 35 | 36 | if [ $# -lt 1 ] 37 | then 38 | usage 39 | exit 1 40 | fi 41 | 42 | for i 43 | do 44 | echo "sg_logs -t $verbose $i" 45 | sg_logs -t $verbose $i 46 | done 47 | -------------------------------------------------------------------------------- /include/Makefile.am: -------------------------------------------------------------------------------- 1 | 2 | scsiincludedir = $(includedir)/scsi 3 | 4 | scsiinclude_HEADERS = \ 5 | sg_lib.h \ 6 | sg_lib_data.h \ 7 | sg_lib_names.h \ 8 | sg_cmds.h \ 9 | sg_cmds_basic.h \ 10 | sg_cmds_extra.h \ 11 | sg_cmds_mmc.h \ 12 | sg_json.h \ 13 | sg_json_sg_lib.h \ 14 | sg_pr2serr.h \ 15 | sg_unaligned.h \ 16 | sg_pt.h \ 17 | sg_pt_nvme.h 18 | 19 | if OS_LINUX 20 | scsiinclude_HEADERS += \ 21 | sg_linux_inc.h \ 22 | sg_io_linux.h \ 23 | sg_pt_linux.h 24 | 25 | noinst_HEADERS = \ 26 | sg_pt_win32.h 27 | endif 28 | 29 | if OS_WIN32_MINGW 30 | scsiinclude_HEADERS += sg_pt_win32.h 31 | 32 | noinst_HEADERS = \ 33 | sg_linux_inc.h \ 34 | sg_io_linux.h 35 | endif 36 | 37 | if OS_WIN32_CYGWIN 38 | scsiinclude_HEADERS += sg_pt_win32.h 39 | 40 | noinst_HEADERS = \ 41 | sg_linux_inc.h \ 42 | sg_io_linux.h 43 | endif 44 | 45 | if OS_FREEBSD 46 | noinst_HEADERS = \ 47 | sg_linux_inc.h \ 48 | sg_io_linux.h \ 49 | sg_pt_win32.h 50 | endif 51 | 52 | if OS_SOLARIS 53 | noinst_HEADERS = \ 54 | sg_linux_inc.h \ 55 | sg_io_linux.h \ 56 | sg_pt_win32.h 57 | endif 58 | 59 | if OS_OSF 60 | noinst_HEADERS = \ 61 | sg_linux_inc.h \ 62 | sg_io_linux.h \ 63 | sg_pt_win32.h 64 | endif 65 | 66 | -------------------------------------------------------------------------------- /inhex/rep_zdomains.hex: -------------------------------------------------------------------------------- 1 | # This is the output (in hex) of the SCSI REPORT ZONE DOMAINS command. 2 | # This page is constructed from the command description in zbc2r10 3 | # with two zone domains. 4 | 5 | # A typical example: 6 | # sg_rep_zones --domain --inhex=rep_zdomains.hex 7 | 8 | # parameter data header (64 bytes) 9 | 00 00 00 c0 00 00 00 c0 02 02 00 30 00 00 00 00 10 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 11 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 12 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 13 | 14 | # first zone domain 15 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 16 | 00 00 00 00 00 00 00 03 00 00 00 00 00 00 00 00 17 | 00 00 00 00 00 13 ff ff 00 00 00 00 00 00 00 00 18 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 19 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 20 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 21 | 22 | # second zone domain 23 | 01 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 24 | 00 00 00 00 00 00 00 03 00 00 00 00 00 04 00 00 25 | 00 00 00 00 00 17 ff ff 00 00 00 00 00 00 00 00 26 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 27 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 28 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 29 | 30 | -------------------------------------------------------------------------------- /inhex/vpd_constituents.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_constituents.hex 4 | 5 | 6 | # Device constituent VPD page header 7 | 00 8b 00 c2 8 | 9 | # First constituent descriptor, fixed part 10 | 00 03 00 00 11 | 41 42 43 44 20 20 00 00 12 | 41 42 43 44 45 46 47 48 41 42 43 44 44 44 44 44 13 | 30 31 32 33 14 | 00 00 15 | 00 2a 16 | 17 | # inner constituent specific descriptor (for VPD page) 18 | 01 00 00 10 19 | # ... the VPD page 20 | 00 b3 00 0c 00 00 00 00 21 | 00 20 00 00 22 | 00 00 00 04 23 | 24 | # another inner constituent specific descriptor (for VPD page) 25 | 01 00 00 12 26 | # ... the VPD page 27 | 00 92 00 0e 00 00 00 00 28 | 00 01 01 01 01 02 02 01 29 | 09 09 30 | 31 | 32 | # Second constituent descriptor, fixed part 33 | 00 03 00 00 34 | 53 45 41 47 41 54 45 20 35 | 53 54 32 30 30 46 4d 30 30 37 33 20 20 20 20 20 36 | 30 30 30 37 37 | 00 00 38 | 00 50 39 | 40 | # inner constituent specific descriptor ("di" VPD page) 41 | 01 00 00 4c 42 | # ... the VPD page 43 | 00 83 00 48 01 03 00 08 50 00 c5 00 30 11 cb 2b 44 | 61 93 00 08 50 00 c5 00 30 11 cb 29 61 94 00 04 45 | 00 00 00 01 61 a3 00 08 50 00 c5 00 30 11 cb 28 46 | 03 28 00 18 6e 61 61 2e 35 30 30 30 43 35 30 30 47 | 33 30 31 31 43 42 32 38 00 00 00 00 48 | -------------------------------------------------------------------------------- /examples/transport_ids.txt: -------------------------------------------------------------------------------- 1 | # This file is an example for the sg_persist utility. 2 | # It discusses using "TransportID"s which are defined (most recently) 3 | # in SPC-4 revision 20 section 7.5.4 titled: "TransportID identifiers". 4 | # 5 | # The sg_persist utility can take one or more "transportID"s from stdin when 6 | # either the '--transport-id=-" or "-X -" option is given on the command 7 | # line. 8 | 9 | # To see transport IDs decoded after they have been read in (e.g. to check 10 | # they are well formed) use the verbose flag 3 times (i.e. "... -vvv ..."). 11 | 12 | # Here is a simple example (for SPI) of a comma separated hex list: 13 | 1,0,0,7,0,0,0,1 # SPI, initiator address=7, relative_port_num=1 14 | 15 | # and here is the transport specific format for the same thing: 16 | # spi,1,7 17 | 18 | # An example for SAS follows, first as a hex string, then in transport 19 | # specific format (incremented by 1) 20 | 6,0,0,0,50,6,5,b0,0,6,f2,60 21 | sas,500605b00006f261 22 | 23 | # For iSCSI the hex list form is awkward, better to use the transport 24 | # specific format. [The leading spaces are ignored.] 25 | iqn.5886.com.acme.diskarrays-sn-a8675309 26 | 27 | 28 | # Leading spaces and tabs before a '#' are ok. 29 | 30 | 31 | # dpg 20090824 32 | -------------------------------------------------------------------------------- /utils/Makefile: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/share/man 6 | 7 | CC = gcc 8 | LD = gcc 9 | 10 | EXECS = hxascdmp 11 | EXTRA_EXECS = hxascdmp 12 | 13 | MAN_PGS = hxascdmp.1 14 | MAN_PREF = man1 15 | 16 | CFLAGS = -g -O2 -W -Wall -iquote ../include 17 | # CFLAGS = -g -O2 -W -iquote ../include -pedantic -std=c99 18 | 19 | LDFLAGS = 20 | 21 | all: $(EXECS) 22 | 23 | depend dep: 24 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 25 | done > .depend 26 | 27 | clean: 28 | /bin/rm -f *.o $(EXTRA_EXECS) core .depend 29 | 30 | hxascdmp: hxascdmp.o 31 | $(LD) -o $@ $(LDFLAGS) $^ 32 | 33 | 34 | install: $(EXECS) 35 | install -d $(INSTDIR) 36 | for name in $^; \ 37 | do install -s -o root -g root -m 755 $$name $(INSTDIR); \ 38 | done 39 | install -d $(MANDIR)/$(MAN_PREF) 40 | for mp in $(MAN_PGS); \ 41 | do install -o root -g root -m 644 $$mp $(MANDIR)/$(MAN_PREF); \ 42 | gzip -9f $(MANDIR)/$(MAN_PREF)/$$mp; \ 43 | done 44 | 45 | uninstall: 46 | dists="$(EXECS)"; \ 47 | for name in $$dists; do \ 48 | rm -f $(INSTDIR)/$$name; \ 49 | done 50 | for mp in $(MAN_PGS); do \ 51 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 52 | done 53 | 54 | ifeq (.depend,$(wildcard .depend)) 55 | include .depend 56 | endif 57 | -------------------------------------------------------------------------------- /inhex/nvme_identify_ctl.hex: -------------------------------------------------------------------------------- 1 | # 64 byte NVMe Identify controller command (an Admin command) that is 2 | # suitable for: 3 | # sg_raw --cmdfile= --request=4096 4 | # 5 | # The address field (at byte offset 24, 8 bytes and little endian) gives 6 | # special meaning to the highest address pointers: 7 | # ffffffff fffffffe use address of data-in buffer 8 | # ffffffff fffffffd use address of data-out buffer 9 | # 10 | # The data length field (at byte offset 36, 4 bytes and little endian) 11 | # gives special meaning to the highest block counts: 12 | # fffffffe use byte length of data-in buffer 13 | # fffffffd use byte length of data-out buffer 14 | # 15 | # Since The Identify command reads data "in" from the device, then the 16 | # data-in buffer is appropriate. 17 | 18 | 06 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 19 | 00 00 00 00 00 00 00 00 fe ff ff ff ff ff ff ff 20 | 00 00 00 00 fe ff ff ff 01 00 00 00 00 00 00 00 21 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 22 | 23 | # A typical invocation in Linux and FreeBSD would look like this: 24 | # sg_raw --cmdfile=nvme_identify_ctl.hex -r 4k /dev/nvme0 25 | # 26 | # NVMe likes "4k" (4096 bytes) buffer size, preferably aligned to 27 | # a 4096 byte (or "page") boundary. 28 | -------------------------------------------------------------------------------- /inhex/z_act_query.hex: -------------------------------------------------------------------------------- 1 | # This is the output (in hex) of a simulated SCSI ZONE QUERY command. 2 | # 3 | # The hex bytes in this file may be generated by: 4 | # sg_z_act_query /dev/sg1 -HHH > /tmp/z_act_query.hex 5 | # where /dev/sg1 was a SCSI device implementing ZBC-2. 6 | 7 | # An example invocation: 8 | # sg_z_act_query --inhex=z_act_query.hex 9 | 10 | 11 | # parameter data header (64 bytes) 12 | 00 00 00 80 00 00 00 80 80 00 03 00 00 00 00 00 13 | 00 00 00 04 00 00 00 00 00 00 00 00 00 00 00 00 14 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 15 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 16 | 17 | # first zone activation descriptor, zone type: conventional 18 | 01 00 01 00 00 00 00 00 00 00 00 00 00 00 00 04 19 | 00 00 00 20 00 00 00 00 00 00 00 00 00 00 00 00 20 | # second zone activation descriptor, zone type: sequential write required 21 | 02 10 02 00 00 00 00 00 00 00 00 00 00 00 00 05 22 | 00 00 00 40 00 00 00 00 00 00 00 00 00 00 00 00 23 | # third zone descriptor, zone type: sequential write required 24 | 02 10 03 00 00 00 00 00 00 00 00 00 00 00 00 06 25 | 00 00 00 60 00 00 00 00 00 00 00 00 00 00 00 00 26 | # fourth and last zone activation descriptor, zone type: sequential write required 27 | 02 10 04 00 00 00 00 00 00 00 00 00 00 00 00 07 28 | 00 00 00 80 00 00 00 00 00 00 00 00 00 00 00 00 29 | -------------------------------------------------------------------------------- /doc/scsi_temperature.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_TEMPERATURE "8" "May 2011" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_temperature \- fetch the temperature of a SCSI device 4 | .SH SYNOPSIS 5 | .B scsi_temperature 6 | [\fI\-\-help\fR] [\fI\-\-verbose\fR] 7 | \fIDEVICE\fR [\fIDEVICE\fR]* 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls the sg_logs utility on each given 11 | \fIDEVICE\fR in order to find the device's temperature. The Temperature 12 | log page is checked first and if it is not available then the Informational 13 | Exceptions log page is checked. 14 | .SH OPTIONS 15 | Arguments to long options are mandatory for short options as well. 16 | .TP 17 | \fB\-h\fR, \fB\-\-help\fR 18 | print out the usage message then exit. 19 | .TP 20 | \fB\-v\fR, \fB\-\-verbose\fR 21 | increase level or verbosity. 22 | .SH EXIT STATUS 23 | The exit status of this script is 0 when it is successful. Otherwise the 24 | exit status is that of the last sg_logs utility called. See 25 | the sg3_utils(8) man page. 26 | .SH AUTHORS 27 | Written by D. Gilbert 28 | .SH COPYRIGHT 29 | Copyright \(co 2011\-2013 Douglas Gilbert 30 | .br 31 | This software is distributed under a BSD\-2\-Clause license. There is NO 32 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 33 | .SH "SEE ALSO" 34 | .B sg_logs (sg3_utils) 35 | -------------------------------------------------------------------------------- /README.sg_start: -------------------------------------------------------------------------------- 1 | Hi, 2 | 3 | you can use sg_start to start (spin-up, 1) and stop (spin-down, 0) devices. 4 | I also offers a parameter (-s) to send a synchronize cache command to a 5 | device, so it should write back its internal buffers to the medium. 6 | 7 | Be aware that the Linux SCSI subsystem at this time does not automatically 8 | starts stopped devices, so stopping a device which is in use may have fatal 9 | results for you. 10 | 11 | So, you should apply with care. 12 | I use it in my shutdown script at the end (before the poweroff command): 13 | 14 | # SG_SHUG_NOS is set in my config file rc.config 15 | # SG_SHUT_NOS="0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15" 16 | if test -x /bin/sg_start; then 17 | if test "`basename $command`" = "reboot"; then 18 | for no in $SG_SHUT_NOS; 19 | do /bin/sg_start /dev/sg$no -s >/dev/null 2>&1; 20 | done 21 | else 22 | for no in $SG_SHUT_NOS; 23 | do /bin/sg_start /dev/sg$no -s 0 >/dev/null 2>&1; 24 | done 25 | fi 26 | fi 27 | 28 | Enjoy! 29 | Kurt Garloff 30 | 31 | 32 | Postscript 33 | ========== 34 | sg_start has been reworked to allow a block device (e.g. /dev/sda) in 35 | addition to the sg device name (e.g. /dev/sg0) in the lk 2.6 series. 36 | sg_start now has more command line options, see its man page. 37 | 38 | Douglas Gilbert 2004/5/8 39 | -------------------------------------------------------------------------------- /scripts/fc_wwpn_id: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # 3 | # fc_wwpn_id 4 | # 5 | # Generates device node names links based on FC WWPN 6 | # Copyright (c) 2016-2021 Hannes Reinecke, SUSE Linux GmbH 7 | # 8 | # This program is free software; you can redistribute it and/or modify it 9 | # under the terms of the GNU General Public License as published by the 10 | # Free Software Foundation version 2 of the License. 11 | # 12 | 13 | DEVPATH=$1 14 | SCSIPATH=$(cd -P "/sys$DEVPATH/device" || exit; echo "$PWD") 15 | 16 | d=$SCSIPATH 17 | [ -d "$d/scsi_disk" ] || exit 0 18 | target_lun=${d##*:} 19 | 20 | while [ -n "$d" ] ; do 21 | d=${d%/*} 22 | e=${d##*/} 23 | case "$e" in 24 | rport*) 25 | rport=$e 26 | rport_dir="/sys/class/fc_remote_ports/$rport" 27 | if [ -d "$rport_dir" ] ; then 28 | rport_wwpn=$(cat "$rport_dir/port_name") 29 | fi 30 | ;; 31 | host*) 32 | host=$e 33 | host_dir="/sys/class/fc_host/$host" 34 | if [ -d "$host_dir" ] ; then 35 | host_wwpn=$(cat "$host_dir/port_name") 36 | break; 37 | fi 38 | esac 39 | done 40 | 41 | if [ -n "$rport_wwpn" ] || [ -n "$host_wwpn" ] ; then 42 | echo "FC_TARGET_LUN=$target_lun" 43 | fi 44 | 45 | if [ -n "$rport_wwpn" ] ; then 46 | echo "FC_TARGET_WWPN=$rport_wwpn" 47 | fi 48 | 49 | if [ -n "$host_wwpn" ] ; then 50 | echo "FC_INITIATOR_WWPN=$host_wwpn" 51 | fi 52 | -------------------------------------------------------------------------------- /inhex/vpd_di_all.hex: -------------------------------------------------------------------------------- 1 | # 2 | # An example invocation: 3 | # sg_vpd --inhex=vpd_di_all.hex 4 | 5 | 00 83 01 04 6 | 7 | # Vendor specific designator 8 | 01 00 00 16 11 22 33 44 55 66 77 88 99 aa bb cc 9 | dd ee ff ed cb a9 87 65 43 21 10 | 11 | # T10 vendor ID 12 | 02 01 00 14 13 | 41 42 43 20 20 20 20 20 14 | 58 59 5a 31 32 33 34 35 36 37 38 39 15 | 16 | # EUI-64 17 | 01 02 00 08 11 22 33 44 55 66 77 88 18 | 01 02 00 0c 11 22 33 44 55 66 77 88 00 00 01 23 19 | 01 02 00 10 01 23 45 67 89 ab cd ef 11 22 33 44 55 66 77 88 20 | 21 | # NAA 22 | 01 03 00 08 51 22 33 44 55 66 77 88 23 | 01 03 00 10 61 22 33 44 55 66 77 88 aa bb cc dd ee ff ee dd 24 | 25 | # Relative target port 26 | 01 14 00 04 00 00 00 02 27 | 28 | # Target port group 29 | 01 15 00 04 00 00 00 03 30 | 31 | # Logical unit group 32 | 01 06 00 04 00 00 00 04 33 | 34 | # MD5 logical unitp 35 | 01 07 00 10 ff ee dd cc bb aa 99 88 77 66 55 44 33 22 11 00 36 | 37 | # SCSI name string: iqn.5886.com.acme.diskarrays-sn-a8675309 38 | 02 28 00 28 39 | 69 71 6e 2e 35 38 38 36 2e 63 6f 6d 2e 61 63 6d 40 | 65 2e 64 69 73 6b 61 72 72 61 79 73 2d 73 6e 2d 41 | 61 38 36 37 35 33 30 39 42 | 43 | # Protocol specific 44 | # USB 45 | 91 99 00 04 04 00 02 00 46 | # PCIe 47 | a1 99 00 08 01 23 00 00 00 00 00 00 48 | 49 | # UUID 50 | 01 0a 00 12 10 00 11 22 33 44 55 66 77 88 99 aa 51 | bb cc dd ee fe dc 52 | -------------------------------------------------------------------------------- /scripts/scsi_ready: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | ################################################ 4 | # 5 | # Send a TEST UNIT READY SCSI command to each given device. 6 | # 7 | # This script assumes the sg3_utils package is installed and uses 8 | # the sg_turs utility.. 9 | # 10 | ############################################### 11 | 12 | verbose="" 13 | brief="" 14 | 15 | usage() 16 | { 17 | echo "Usage: scsi_ready [-b] [-h] [-v] +" 18 | echo " where:" 19 | echo " -b, --brief print 'ready' or 'device not ready' only" 20 | echo " -h, --help print usage message" 21 | echo " -v, --verbose more verbose output" 22 | echo "" 23 | echo "Send SCSI TEST UNIT READY to each " 24 | } 25 | 26 | opt="$1" 27 | while test ! -z "$opt" -a -z "${opt##-*}"; do 28 | opt=${opt#-} 29 | case "$opt" in 30 | b|-brief) brief="1" ;; 31 | h|-help) usage ; exit 0 ;; 32 | v|-verbose) verbose="-v" ;; 33 | vv) verbose="-vv" ;; 34 | vvv) verbose="-vvv" ;; 35 | *) echo "Unknown option: -$opt " ; exit 1 ;; 36 | esac 37 | shift 38 | opt="$1" 39 | done 40 | 41 | if [ $# -lt 1 ] 42 | then 43 | usage 44 | exit 1 45 | fi 46 | 47 | for i 48 | do 49 | if [ ! $brief ] ; then 50 | echo "sg_turs $verbose $i" 51 | fi 52 | echo -n " " 53 | if sg_turs $verbose $i ; then 54 | echo "ready" 55 | fi 56 | done 57 | -------------------------------------------------------------------------------- /inhex/logs_last_n.hex: -------------------------------------------------------------------------------- 1 | # This file contains the ASCII hex of a SCSI LOG SENSE command responses 2 | # for the various "Last n" log (sub)pages concaternated together. 3 | 4 | # The response in this file can be decoded with: 5 | # sg_logs --inhex=logs_last_n.hex 6 | # or 7 | # sg_logs --inhex=logs_last_n.hex --brief 8 | # or 9 | # sg_logs --inhex=logs_last_n.hex --exclude 10 | 11 | # Last n mode page data changed log subpage 12 | 4b 02 00 28 13 | 00 00 03 0c 00 00 00 04 00 00 00 02 00 00 00 01 14 | 00 01 03 04 0a 00 00 00 15 | 00 02 03 04 5a 01 00 00 16 | 00 03 03 04 5c 02 00 00 17 | 18 | # Last n INQUIRY data changed log subpage 19 | 4b 01 00 28 20 | 00 00 03 0c 00 00 00 01 00 00 00 03 00 00 00 02 21 | 00 01 03 04 00 00 00 00 22 | 00 02 03 04 01 80 00 00 23 | 00 03 03 04 01 83 00 00 24 | 25 | # Last n deferred errors or asynchronous events log subpage 26 | 0b 00 00 5a 27 | 00 00 03 40 28 | 73,0,0,0,0,0,0 38 29 | b,36,1,0 30 | 0,0,0,2,11,11,11,11,22,22,22,22,55,55,55,55,66,66,66,66 1,0,0,7, 2,0,0,8 31 | 0,0,0,1,77,77,77,77,77,77,77,77,88,88,88,88,88,88,88,88, 3,0,0,5 32 | 00 01 03 12 33 | f1 00 03 00 00 12 34 0a 00 00 00 00 11 00 00 00 00 00 34 | 35 | # Last n error events log page 36 | 07 00 00 31 37 | 00 00 01 0c 38 | 6d 65 64 69 75 6d 20 65 72 72 6f 72 39 | 00 01 01 1d 40 | 55 41 3a 20 63 61 70 61 63 69 74 79 20 64 61 74 41 | 61 20 68 61 73 20 63 68 61 6e 67 65 64 42 | -------------------------------------------------------------------------------- /inhex/opcodes.hex: -------------------------------------------------------------------------------- 1 | 00 00 01 a0 12 00 00 00 00 00 00 06 a0 00 00 00 2 | 00 00 00 0c 03 00 00 00 00 00 00 06 00 00 00 00 3 | 00 00 00 06 5a 00 00 00 00 00 00 0a 1a 00 00 00 4 | 00 00 00 06 55 00 00 00 00 00 00 0a 15 00 00 00 5 | 00 00 00 06 4d 00 00 00 00 00 00 0a 25 00 00 00 6 | 00 00 00 0a 88 00 00 00 00 00 00 10 28 00 00 00 7 | 00 00 00 0a 08 00 00 00 00 00 00 06 a8 00 00 00 8 | 00 00 00 0c 8a 00 00 00 00 00 00 10 2a 00 00 00 9 | 00 00 00 0a 0a 00 00 00 00 00 00 06 aa 00 00 00 10 | 00 00 00 0c 1b 00 00 00 00 00 00 06 9e 00 00 10 11 | 00 01 00 10 9e 00 00 12 00 01 00 10 9f 00 00 12 12 | 00 01 00 10 a3 00 00 0a 00 01 00 0c a3 00 00 0c 13 | 00 01 00 0c a3 00 00 0d 00 01 00 0c 8f 00 00 00 14 | 00 00 00 10 2f 00 00 00 00 00 00 0a 7f 00 00 09 15 | 00 01 00 20 7f 00 00 0b 00 01 00 20 7f 00 00 11 16 | 00 01 00 20 56 00 00 00 00 00 00 0a 16 00 00 00 17 | 00 00 00 06 57 00 00 00 00 00 00 0a 17 00 00 00 18 | 00 00 00 06 1e 00 00 00 00 00 00 06 01 00 00 00 19 | 00 00 00 06 1d 00 00 02 00 00 00 06 42 00 00 00 20 | 00 00 00 0a 3b 00 00 00 00 00 00 0a 41 00 00 00 21 | 00 00 00 0a 93 00 00 00 00 00 00 10 35 00 00 00 22 | 00 00 00 0a 91 00 00 00 00 00 00 10 89 00 00 00 23 | 00 00 00 10 34 00 00 00 00 00 00 0a 90 00 00 00 24 | 00 00 00 10 94 00 00 03 00 01 00 10 94 00 00 01 25 | 00 01 00 10 94 00 00 02 00 01 00 10 94 00 00 04 26 | 00 01 00 10 95 00 00 00 00 01 00 10 95 00 00 06 27 | 00 01 00 10 28 | -------------------------------------------------------------------------------- /debian/copyright: -------------------------------------------------------------------------------- 1 | 2 | Copyright (c) 1999-2018, Douglas Gilbert 3 | All rights reserved. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions are met: 7 | 8 | 1. Redistributions of source code must retain the above copyright notice, this 9 | list of conditions and the following disclaimer. 10 | 2. Redistributions in binary form must reproduce the above copyright notice, 11 | this list of conditions and the following disclaimer in the documentation 12 | and/or other materials provided with the distribution. 13 | 14 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 15 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 16 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 17 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 18 | ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 19 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 20 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 21 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 23 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 | 25 | -------------------------------------------------------------------------------- /README.iscsi: -------------------------------------------------------------------------------- 1 | iSCSI support for sg3-utils is available from external patches. 2 | 3 | To build sg3-utils from sources and activate built-in iSCSI support 4 | you need both sg3-utils and the external user-space iSCSI library hosted at : 5 | 6 | https://github.com/sahlberg/libiscsi 7 | 8 | This library provides a client library for accessing remote iSCSI 9 | devices and also comes with patches to the sg3-utils source code 10 | distribution to compile a special version of sg3-utils with iSCSI 11 | support. 12 | 13 | No support for iSCSI is provided by the sg3-utils maintainer. 14 | 15 | 16 | 17 | Once sg3-utils is compiler and installed with libiscsi support, you 18 | can specify remote iSCSI devices through a special URL format instead 19 | of the normal /dev/* syntax. 20 | 21 | Example: 22 | 23 | sg_inq iscsi://ronnie%password@10.1.1.27/iqn.ronnie.test/1 24 | standard INQUIRY: 25 | PQual=0 Device_type=0 RMB=0 version=0x05 [SPC-3] 26 | [AERC=0] [TrmTsk=1] NormACA=0 HiSUP=0 Resp_data_format=2 27 | SCCS=0 ACC=0 TPGS=0 3PC=0 Protect=0 BQue=0 28 | EncServ=0 MultiP=0 [MChngr=0] [ACKREQQ=0] Addr16=0 29 | [RelAdr=0] WBus16=0 Sync=0 Linked=0 [TranDis=0] CmdQue=1 30 | [SPI: Clocking=0x0 QAS=0 IUS=0] 31 | length=66 (0x42) Peripheral device type: disk 32 | Vendor identification: IET 33 | Product identification: VIRTUAL-DISK 34 | Product revision level: 0001 35 | Unit serial number: beaf11 36 | 37 | 38 | -------------------------------------------------------------------------------- /BSD_LICENSE: -------------------------------------------------------------------------------- 1 | 2 | Copyright (c) 1999-2022, Douglas Gilbert 3 | All rights reserved. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions are met: 7 | 8 | 1. Redistributions of source code must retain the above copyright notice, this 9 | list of conditions and the following disclaimer. 10 | 2. Redistributions in binary form must reproduce the above copyright notice, 11 | this list of conditions and the following disclaimer in the documentation 12 | and/or other materials provided with the distribution. 13 | 14 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 15 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 16 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 17 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 18 | ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 19 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 20 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 21 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 23 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 | 25 | 26 | Above is the: 27 | SPDX-License-Identifier: BSD-2-Clause 28 | -------------------------------------------------------------------------------- /lib/BSD_LICENSE: -------------------------------------------------------------------------------- 1 | 2 | Copyright (c) 1999-2019, Douglas Gilbert 3 | All rights reserved. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions are met: 7 | 8 | 1. Redistributions of source code must retain the above copyright notice, this 9 | list of conditions and the following disclaimer. 10 | 2. Redistributions in binary form must reproduce the above copyright notice, 11 | this list of conditions and the following disclaimer in the documentation 12 | and/or other materials provided with the distribution. 13 | 14 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 15 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 16 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 17 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 18 | ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 19 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 20 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 21 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 23 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 | 25 | Above is the: 26 | SPDX-License-Identifier: BSD-2-Clause 27 | -------------------------------------------------------------------------------- /src/BSD_LICENSE: -------------------------------------------------------------------------------- 1 | 2 | Copyright (c) 1999-2022, Douglas Gilbert 3 | All rights reserved. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions are met: 7 | 8 | 1. Redistributions of source code must retain the above copyright notice, this 9 | list of conditions and the following disclaimer. 10 | 2. Redistributions in binary form must reproduce the above copyright notice, 11 | this list of conditions and the following disclaimer in the documentation 12 | and/or other materials provided with the distribution. 13 | 14 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 15 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 16 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 17 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 18 | ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 19 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 20 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 21 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 23 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 | 25 | Above is the: 26 | SPDX-License-Identifier: BSD-2-Clause 27 | -------------------------------------------------------------------------------- /inhex/rep_realms.hex: -------------------------------------------------------------------------------- 1 | # This is the output (in hex) of the SCSI REPORT REALMS command. 2 | # This page is constructed from the command description in zbc2r10 3 | # with three realms, and two zone domains 4 | 5 | # A typical example: 6 | # sg_rep_zones --realm --inhex=rep_realms.hex 7 | 8 | 9 | # parameter data header (64 bytes) 10 | 00 00 00 90 00 00 00 03 00 00 00 30 00 00 00 00 11 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 12 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 13 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 14 | 15 | # first zone domain descriptor 16 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 17 | # first realm descriptor, zone domain 0 start,last 18 | 00 00 00 00 00 00 00 00 00 00 00 00 00 03 ff ff 19 | # first realm descriptor, zone domain 1 start,last 20 | 00 00 00 00 00 04 00 00 00 00 00 00 00 07 ff ff 21 | 22 | # second zone domain descriptor 23 | 00 00 00 01 00 00 00 00 00 00 00 00 00 00 00 00 24 | # second realm descriptor, zone domain 0 start,last 25 | 00 00 00 00 00 08 00 00 00 00 00 00 00 0b ff ff 26 | # second realm descriptor, zone domain 1 start,last 27 | 00 00 00 00 00 0c 00 00 00 00 00 00 00 0f ff ff 28 | 29 | # third realm descriptor 30 | 00 00 00 02 00 00 00 00 00 00 00 00 00 00 00 00 31 | # second realm descriptor, zone domain 0 start,last 32 | 00 00 00 00 00 10 00 00 00 00 00 00 00 13 ff ff 33 | # second realm descriptor, zone domain 1 start,last 34 | 00 00 00 00 00 14 00 00 00 00 00 00 00 17 ff ff 35 | 36 | -------------------------------------------------------------------------------- /scripts/scsi_start: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | ################################################ 4 | # 5 | # Spin up the given SCSI disk(s). 6 | # 7 | # SCSI disks (or disks that understand SCSI commands) 8 | # are assumed. By default, the immediate bit is set so the 9 | # command should return immediately. The disk however will 10 | # take 10 seconds or more to spin up. The '-w' option 11 | # causes each start to wait until the disk reports that it 12 | # has started. 13 | # 14 | # This script assumes the sg3_utils package is installed. 15 | # 16 | ############################################### 17 | 18 | verbose="" 19 | immediate="-i" 20 | 21 | usage() 22 | { 23 | echo "Usage: scsi_start [-h] [-v] [-w] +" 24 | echo " where:" 25 | echo " -h, --help print usage message" 26 | echo " -v, --verbose more verbose output" 27 | echo " -w, --wait wait for each start to complete" 28 | echo "" 29 | echo "Send SCSI START STOP UNIT command to start each " 30 | } 31 | 32 | opt="$1" 33 | while test ! -z "$opt" -a -z "${opt##-*}"; do 34 | opt=${opt#-} 35 | case "$opt" in 36 | h|-help) usage ; exit 0 ;; 37 | v|-verbose) verbose="-v" ;; 38 | w|-wait) immediate="" ;; 39 | *) echo "Unknown option: -$opt " ; exit 1 ;; 40 | esac 41 | shift 42 | opt="$1" 43 | done 44 | 45 | if [ $# -lt 1 ] 46 | then 47 | usage 48 | exit 1 49 | fi 50 | 51 | for i 52 | do 53 | echo "sg_start $immediate 1 $verbose $i" 54 | sg_start $immediate 1 $verbose $i 55 | done 56 | -------------------------------------------------------------------------------- /doc/scsi_start.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_START "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_start \- start one or more SCSI disks 4 | .SH SYNOPSIS 5 | .B scsi_start 6 | [\fI\-\-help\fR] [\fI\-\-verbose\fR] [\fI\-\-wait\fR] 7 | \fIDEVICE\fR [\fIDEVICE\fR]* 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls the sg_start utility on each given 11 | \fIDEVICE\fR. The purpose is to spin up (start) each given \fIDEVICE\fR. 12 | .SH OPTIONS 13 | Arguments to long options are mandatory for short options as well. 14 | .TP 15 | \fB\-h\fR, \fB\-\-help\fR 16 | print out the usage message then exit. 17 | .TP 18 | \fB\-v\fR, \fB\-\-verbose\fR 19 | increase level or verbosity. 20 | .TP 21 | \fB\-w\fR, \fB\-\-wait\fR 22 | wait for the spin up (start) on each given \fIDEVICE\fR to complete. 23 | The default action is to do each start in immediate mode. 24 | .SH NOTES 25 | If a large number of disks are spun up at the same time (i.e. without 26 | the \fI\-\-wait\fR option) then the power supply may be overloaded. 27 | .SH EXIT STATUS 28 | The exit status of this script is 0 when it is successful. Otherwise the 29 | exit status is that of the last sg_start utility called. See 30 | the sg3_utils(8) man page. 31 | .SH AUTHORS 32 | Written by D. Gilbert 33 | .SH COPYRIGHT 34 | Copyright \(co 2009\-2013 Douglas Gilbert 35 | .br 36 | This software is distributed under a BSD\-2\-Clause license. There is NO 37 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 38 | .SH "SEE ALSO" 39 | .B sg_start (sg3_utils) 40 | -------------------------------------------------------------------------------- /doc/scsi_ready.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_READY "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_ready \- do SCSI TEST UNIT READY on devices 4 | .SH SYNOPSIS 5 | .B scsi_ready 6 | [\fI\-\-brief\fR] [\fI\-\-help\fR] [\fI\-\-verbose\fR] 7 | \fIDEVICE\fR [\fIDEVICE\fR]* 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls the sg_turs utility on each given 11 | \fIDEVICE\fR. This will send a SCSI TEST UNIT READY command to each 12 | \fIDEVICE\fR. Disks, tape drives and DVD/BD players amongst others 13 | may respond to this SCSI command. 14 | .SH OPTIONS 15 | Arguments to long options are mandatory for short options as well. 16 | .TP 17 | \fB\-b\fR, \fB\-\-brief\fR 18 | for each \fIDEVICE\fR given output a line containing either ' ready' 19 | or ' device not ready'. If \fIDEVICE\fR is not found or there is 20 | another serious error then an error message will appear instead. 21 | .TP 22 | \fB\-h\fR, \fB\-\-help\fR 23 | print out the usage message then exit. 24 | .TP 25 | \fB\-v\fR, \fB\-\-verbose\fR 26 | increase level or verbosity. 27 | .SH EXIT STATUS 28 | The exit status of this script is 0 when it is successful. Otherwise the 29 | exit status is that of the last sg_turs utility called. See 30 | the sg3_utils(8) man page. 31 | .SH AUTHORS 32 | Written by D. Gilbert 33 | .SH COPYRIGHT 34 | Copyright \(co 2009\-2013 Douglas Gilbert 35 | .br 36 | This software is distributed under a BSD\-2\-Clause license. There is NO 37 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 38 | .SH "SEE ALSO" 39 | .B sg_turs (sg3_utils) 40 | -------------------------------------------------------------------------------- /scripts/scsi_readcap: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | ################################################################### 4 | # 5 | # Fetch READ CAPACITY information for the given SCSI device(s). 6 | # 7 | # This script assumes the sg3_utils package is installed. 8 | # 9 | ################################################################## 10 | 11 | verbose="" 12 | brief="" 13 | long_opt="" 14 | 15 | usage() 16 | { 17 | echo "Usage: scsi_readcap [-b] [-h] [-l] [-v] +" 18 | echo " where:" 19 | echo " -b, --brief output brief capacity data" 20 | echo " -h, --help print usage message" 21 | echo " -l, --long send longer SCSI READ CAPACITY (16) cdb" 22 | echo " -v, --verbose more verbose output" 23 | echo "" 24 | echo "Use SCSI READ CAPACITY command to fetch the size of each " 25 | } 26 | 27 | opt="$1" 28 | while test ! -z "$opt" -a -z "${opt##-*}"; do 29 | opt=${opt#-} 30 | case "$opt" in 31 | b|-brief) brief="-b" ;; 32 | h|-help) usage ; exit 0 ;; 33 | l|-long) long_opt="--16" ;; 34 | v|-verbose) verbose="-v" ;; 35 | vv) verbose="-vv" ;; 36 | vvv) verbose="-vvv" ;; 37 | *) echo "Unknown option: -$opt " ; exit 1 ;; 38 | esac 39 | shift 40 | opt="$1" 41 | done 42 | 43 | if [ $# -lt 1 ] 44 | then 45 | usage 46 | exit 1 47 | fi 48 | 49 | for i 50 | do 51 | if [ $brief ] ; then 52 | sg_readcap $brief $long_opt $verbose $i 2> /dev/null 53 | else 54 | echo "sg_readcap $brief $long_opt $verbose $i" 55 | sg_readcap $brief $long_opt $verbose $i 56 | fi 57 | done 58 | -------------------------------------------------------------------------------- /COPYING: -------------------------------------------------------------------------------- 1 | 2 | Upstream Authors: Douglas Gilbert , 3 | Bruce Allen , 4 | Peter Allworth , 5 | James Bottomley , 6 | Lars Marowsky-Bree , 7 | Kurt Garloff, 8 | Grant Grundler , 9 | Christophe Varoqui , 10 | Michael Weller , 11 | Eric Youngdale 12 | 13 | Copyright: 14 | 15 | This software is copyright(c) 1994-2021 by the authors 16 | 17 | Most of the code in this package is covered by a BSD license. 18 | On Debian systems, the complete text of the BSD License 19 | can be found in `/usr/share/common-licenses/BSD'. All the code 20 | in the library (usually called libsgutils) is covered by a 21 | BSD license. 22 | 23 | Some of the older utilities are covered by the GPL. More precisely: 24 | You are free to distribute this software under the terms of the 25 | GNU General Public License either version 2, or (at your option) 26 | any later version. On Debian systems, the complete text of the GNU 27 | General Public License can be found in /usr/share/common-licenses/GPL-2 28 | file. The later GPL-3 is found in /usr/share/common-licenses/GPL-3 29 | file but no code in this package refers to that license. 30 | 31 | Douglas Gilbert 32 | 4th October 2021 33 | -------------------------------------------------------------------------------- /doc/scsi_stop.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_STOP "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_stop \- stop (spin down) one or more SCSI disks 4 | .SH SYNOPSIS 5 | .B scsi_stop 6 | [\fI\-\-help\fR] [\fI\-\-verbose\fR] [\fI\-\-wait\fR] 7 | \fIDEVICE\fR [\fIDEVICE\fR]* 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls the sg_start utility on each given 11 | \fIDEVICE\fR. The purpose is to spin down (stop) each given \fIDEVICE\fR. 12 | .SH OPTIONS 13 | Arguments to long options are mandatory for short options as well. 14 | .TP 15 | \fB\-h\fR, \fB\-\-help\fR 16 | print out the usage message then exit. 17 | .TP 18 | \fB\-v\fR, \fB\-\-verbose\fR 19 | increase level or verbosity. 20 | .TP 21 | \fB\-w\fR, \fB\-\-wait\fR 22 | wait for the spin down (stop) on each given \fIDEVICE\fR to complete. 23 | The default action is to do each stop in immediate mode. 24 | .SH NOTES 25 | The sg_start utility calls the SCSI START STOP UNIT command and can 26 | either start (spin up) or stop (spin down) a SCSI disk depending 27 | on the given command line options. 28 | .SH EXIT STATUS 29 | The exit status of this script is 0 when it is successful. Otherwise the 30 | exit status is that of the last sg_start utility called. See 31 | the sg3_utils(8) man page. 32 | .SH AUTHORS 33 | Written by D. Gilbert 34 | .SH COPYRIGHT 35 | Copyright \(co 2009\-2013 Douglas Gilbert 36 | .br 37 | This software is distributed under a BSD\-2\-Clause license. There is NO 38 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 39 | .SH "SEE ALSO" 40 | .B sg_start (sg3_utils) 41 | -------------------------------------------------------------------------------- /inhex/modes_sdeb.hex: -------------------------------------------------------------------------------- 1 | # See the EXAMPLES section in the sg_modes(8) manpage 2 | 3 | # Mode parameter header from MODE SENSE(10): 4 | 00 ee 00 10 00 00 00 08 5 | # Block descriptor length=8 6 | # > Direct access device block descriptors: 7 | # Density code=0x0 8 | 00 80 00 00 00 00 02 00 9 | 10 | # >> Read-Write error recovery [0x1], page_control: current 11 | 01 0a c0 0b f0 00 00 00 05 00 ff ff 12 | # >> Disconnect-Reconnect [0x2], page_control: current 13 | 02 0e 80 80 00 0a 00 00 00 00 00 00 00 00 00 00 14 | # >> Format (obsolete) [0x3], page_control: current 15 | 03 16 00 00 00 00 00 00 00 00 00 3f 02 00 00 00 16 | 00 00 00 00 40 00 00 00 17 | # >> Caching [0x8], page_control: current 18 | 08 12 14 00 ff ff 00 00 ff ff ff ff 80 14 00 00 19 | 00 00 00 00 20 | # >> Control [0xa], page_control: current 21 | 0a 0a 02 00 00 80 00 00 00 00 02 4b 22 | # >> Protocol specific port (SPL) [0x19], page_control: current 23 | 19 06 06 00 07 d0 00 00 24 | # >> Phy control and discover (SPL) [0x19,0x1], page_control: current 25 | 59 01 00 64 00 06 00 02 00 00 00 00 10 09 08 00 26 | 32 22 22 20 00 00 07 ce 31 11 11 10 00 00 00 01 27 | 02 00 00 00 00 00 00 00 88 99 00 00 00 00 00 00 28 | 00 00 00 00 00 00 00 00 00 01 00 00 10 09 08 00 29 | 32 22 22 20 00 00 07 cf 31 11 11 10 00 00 00 01 30 | 03 00 00 00 00 00 00 00 88 99 00 00 00 00 00 00 31 | 00 00 00 00 00 00 00 00 32 | # >> Shared port control (SPL) [0x19,0x2], page_control: current 33 | 59 02 00 0c 00 06 10 00 00 00 00 00 00 00 00 00 34 | # >> Informational exceptions control [0x1c], page_control: current 35 | 1c 0a 08 00 00 00 00 00 00 00 00 00 36 | -------------------------------------------------------------------------------- /doc/README: -------------------------------------------------------------------------------- 1 | Various html files used to be included in this directory but they were 2 | beginning to bloat the size of the source tarball so they have been 3 | removed in version 1.24 . 4 | 5 | Here are the urls of the files that were previously here plus a brief 6 | summary: 7 | 8 | https://sg.danny.cz/sg/sg3_utils.html 9 | - overview and examples of this package 10 | 11 | https://sg.danny.cz/sg/sg_dd.html 12 | - discussion and examples of the sg_dd utility which is a dd variant 13 | (also discusses the sgm_dd, sgp_dd and sg_read utilities) 14 | 15 | https://sg.danny.cz/sg/sg_ses.html 16 | - discussion and examples of the sg_ses utility. SCSI Enclosure 17 | Services (SES) devices may contain a lot of information, 18 | structured in a non-trivial way. 19 | 20 | https://sg.danny.cz/sg/sg_io.html 21 | - discussion of Linux SG_IO ioctl (SCSI pass-through) 22 | 23 | https://sg.danny.cz/sg/tools.html 24 | - overview of around 25 storage and SCSI tools 25 | 26 | Many of those pages are also found at: https://doug-gilbert.github.io/ 27 | 28 | 29 | There are two versions of sg_scan: one for Linux and the other for Windows. 30 | They have different man pages: sg_scan.8.linux and sg_scan.8.win32 with 31 | the Makefile logic (rule in Makefile.am) copying the appropriate one to 32 | sg_scan.8 . sg_scan is not supported for other ports. 33 | 34 | Syntax checking 35 | =============== 36 | Use 'mandoc -W style {man_page} > /dev/null' 37 | 38 | The: 'cannot parse date, using it verbatim: TH February 2019' warning 39 | is ignored. 40 | 41 | Douglas Gilbert 42 | 19th January 2023 43 | -------------------------------------------------------------------------------- /inhex/rep_density_typem.hex: -------------------------------------------------------------------------------- 1 | # 2 | # This file contains the response to SCSI REPORT DENSITY SUPPORTED command 3 | # using the sg_rep_density utility. This file was generated with: 4 | # sg_rep_density --typem -HHH /dev/sg4 > rep_density_typem.hex 5 | # where /dev/sg4 was a LTO-4 tape drive. To decode that file containing 6 | # hexadecimal in ASCII use: 7 | # sg_rep_density --typem -i rep_density_typem.hex 8 | # The --typem option is required in the decode invocation. 9 | 10 | 01 52 00 00 00 00 00 34 01 44 00 00 00 00 00 00 11 | 00 00 00 7f 02 a8 00 00 48 50 20 20 20 20 20 20 12 | 4c 54 4f 33 44 61 74 61 55 6c 74 72 69 75 6d 20 13 | 33 20 44 61 74 61 20 54 61 70 65 20 00 00 00 34 14 | 01 46 00 00 00 00 00 00 00 00 00 7f 03 34 00 00 15 | 48 50 20 20 20 20 20 20 4c 54 4f 34 44 61 74 61 16 | 55 6c 74 72 69 75 6d 20 34 20 44 61 74 61 20 54 17 | 61 70 65 20 00 00 00 34 01 58 00 00 00 00 00 00 18 | 00 00 00 7f 03 4e 00 00 48 50 20 20 20 20 20 20 19 | 4c 54 4f 35 44 61 74 61 55 6c 74 72 69 75 6d 20 20 | 35 20 44 61 74 61 20 54 61 70 65 20 01 00 00 34 21 | 01 44 00 00 00 00 00 00 00 00 00 7f 02 a8 00 00 22 | 48 50 20 20 20 20 20 20 4c 54 4f 33 57 4f 52 4d 23 | 55 6c 74 72 69 75 6d 20 33 20 57 4f 52 4d 20 54 24 | 61 70 65 20 01 00 00 34 01 46 00 00 00 00 00 00 25 | 00 00 00 7f 03 34 00 00 48 50 20 20 20 20 20 20 26 | 4c 54 4f 34 57 4f 52 4d 55 6c 74 72 69 75 6d 20 27 | 34 20 57 4f 52 4d 20 54 61 70 65 20 01 00 00 34 28 | 01 58 00 00 00 00 00 00 00 00 00 7f 03 4e 00 00 29 | 48 50 20 20 20 20 20 20 4c 54 4f 35 57 4f 52 4d 30 | 55 6c 74 72 69 75 6d 20 35 20 57 4f 52 4d 20 54 31 | 61 70 65 20 32 | -------------------------------------------------------------------------------- /doc/scsi_satl.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_SATL "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_satl \- check SCSI to ATA Translation (SAT) device support 4 | .SH SYNOPSIS 5 | .B scsi_satl 6 | [\fI\-\-help\fR] [\fI\-\-log\fR] [\fI\-\-quiet\fR] [\fI\-\-verbose\fR] 7 | \fIDEVICE\fR 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls several SCSI commands on the given 11 | \fIDEVICE\fR that is assumed to be an ATA device behind a SCSI 12 | to ATA Translation (SAT) layer (SATL). The results of each test 13 | and a pass/fail count are output. 14 | .SH OPTIONS 15 | Arguments to long options are mandatory for short options as well. 16 | .TP 17 | \fB\-h\fR, \fB\-\-help\fR 18 | print out the usage message then exit. 19 | .TP 20 | \fB\-L\fR, \fB\-\-log\fR 21 | the output to stderr (from each SCSI command executed) is appended to 22 | a file called 'scsi_satl.err' in the current working directory. 23 | .TP 24 | \fB\-q\fR, \fB\-\-quiet\fR 25 | the amount of output is reduced and typically only the pass/fail 26 | count is output. 27 | .TP 28 | \fB\-v\fR, \fB\-\-verbose\fR 29 | increase level or verbosity. 30 | .SH EXIT STATUS 31 | The exit status of this script is the number of "bad" errors found. 32 | So an exit status of 0 means all mandatory SCSI commands worked as 33 | expected. 34 | .SH AUTHORS 35 | Written by D. Gilbert 36 | .SH COPYRIGHT 37 | Copyright \(co 2011\-2013 Douglas Gilbert 38 | .br 39 | This software is distributed under a BSD\-2\-Clause license. There is NO 40 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 41 | .SH "SEE ALSO" 42 | .B sg_inq, sg_luns, sg_turs, sg_requests, sg_vpd, sg_senddiag, sg_modes, 43 | .B sg_sat_identify (sg3_utils) 44 | -------------------------------------------------------------------------------- /scripts/scsi_stop: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | ################################################ 4 | # 5 | # Spin down the given SCS disk(s). 6 | # 7 | # SCSI disks (or disks that understand SCSI commands) 8 | # are assumed. By default, the immediate bit is set so the 9 | # command should return immediately. The disk however will 10 | # take 10 seconds or more to spin down. The '-w' option 11 | # causes each stop to wait until the disk reports that it 12 | # has stopped. 13 | # 14 | # This script assumes the sg3_utils package is installed. 15 | # 16 | ############################################### 17 | 18 | verbose="" 19 | immediate="-i" 20 | 21 | usage() 22 | { 23 | echo "Usage: scsi_stop [-h] [-v] [-w] +" 24 | echo " where:" 25 | echo " -h, --help print usage message" 26 | echo " -v, --verbose more verbose output" 27 | echo " -w, --wait wait for each stop to complete" 28 | echo "" 29 | echo "Send SCSI START STOP UNIT command to stop each " 30 | } 31 | 32 | opt="$1" 33 | while test ! -z "$opt" -a -z "${opt##-*}"; do 34 | opt=${opt#-} 35 | case "$opt" in 36 | h|-help) usage ; exit 0 ;; 37 | v|-verbose) verbose="-v" ;; 38 | w|-wait) immediate="" ;; 39 | *) echo "Unknown option: -$opt " ; exit 1 ;; 40 | esac 41 | shift 42 | opt="$1" 43 | done 44 | 45 | if [ $# -lt 1 ] 46 | then 47 | usage 48 | exit 1 49 | fi 50 | 51 | for i 52 | do 53 | # Use '-r' (read-only) otherwise using a block device node 54 | # (e.g. 'sg_start 0 /dev/sdb') can result in a change of state 55 | # event causing the disk to spin up again immediately. 56 | echo "sg_start -r $immediate 0 $verbose $i" 57 | sg_start -r $immediate 0 $verbose $i 58 | done 59 | -------------------------------------------------------------------------------- /doc/scsi_mandat.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_MANDAT "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_mandat \- check SCSI device support for mandatory commands 4 | .SH SYNOPSIS 5 | .B scsi_mandat 6 | [\fI\-\-help\fR] [\fI\-\-log\fR] [\fI\-\-quiet\fR] [\fI\-\-verbose\fR] 7 | \fIDEVICE\fR 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls several SCSI commands on the given 11 | \fIDEVICE\fR. These SCSI commands are considered mandatory (although 12 | that varies a little depending on which standard/draft the \fIDEVICE\fR 13 | complies with). The results of each test and a pass/fail count are 14 | output. 15 | .SH OPTIONS 16 | Arguments to long options are mandatory for short options as well. 17 | .TP 18 | \fB\-h\fR, \fB\-\-help\fR 19 | print out the usage message then exit. 20 | .TP 21 | \fB\-L\fR, \fB\-\-log\fR 22 | the output to stderr (from each SCSI command executed) is appended to 23 | a file called 'scsi_mandat.err' in the current working directory. 24 | .TP 25 | \fB\-q\fR, \fB\-\-quiet\fR 26 | the amount of output is reduced and typically only the pass/fail 27 | count is output. 28 | .TP 29 | \fB\-v\fR, \fB\-\-verbose\fR 30 | increase level or verbosity. 31 | .SH EXIT STATUS 32 | The exit status of this script is the number of "bad" errors found. 33 | So an exit status of 0 means all mandatory SCSI commands worked as 34 | expected. 35 | .SH AUTHORS 36 | Written by D. Gilbert 37 | .SH COPYRIGHT 38 | Copyright \(co 2011\-2013 Douglas Gilbert 39 | .br 40 | This software is distributed under a BSD\-2\-Clause license. There is NO 41 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 42 | .SH "SEE ALSO" 43 | .B sg_inq,sg_luns,sg_turs,sg_requests,sg_vpd,sg_senddiag (sg3_utils) 44 | -------------------------------------------------------------------------------- /examples/sg_unmap_example.txt: -------------------------------------------------------------------------------- 1 | # sg_unmap_example.txt 2 | # This is an example of the contents of a file that can be given to sg_unmap 3 | # For example, assume the /dev/sdc is a scratch disk (e.g. one made by the 4 | # scsi_debug kernel module) then: 5 | # sg_unmap --in=sg_unmap_example.txt /dev/sdc 6 | 7 | 0x12345677,1 # unmap LBA 0x12345677 8 | 0x12345678 2 # unmap LBA 0x12345678 and 0x12345679 9 | 0x12340000 3333 # unmap 3333 blocks starting at LBA 0x12340000 10 | 11 | 0X5a5a5a5a5a 0 # unmaps 0 blocks (i.e. does nothing) 12 | 13 | a5a5a5h 14 | 7 # unmap 7 blocks starting at LBA 0xa5a5a5 15 | 16 | # Note that there can be leading and trailing whitespace and whitespace 17 | # (plus comma) can be a separator. 18 | # 19 | # Example invocation: 20 | # $ sg_unmap --in=../examples/sg_unmap_example.txt -vv /dev/sdc 21 | # open /dev/sg2 with flags=0x802 22 | # unmap cdb: 42 00 00 00 00 00 00 00 58 00 23 | # unmap parameter list: 24 | # 00 56 00 50 00 00 00 00 00 00 00 00 12 34 56 77 25 | # 00 00 00 01 00 00 00 00 00 00 00 00 12 34 56 78 26 | # 00 00 00 02 00 00 00 00 00 00 00 00 12 34 00 00 27 | # 00 00 0d 05 00 00 00 00 00 00 00 5a 5a 5a 5a 5a 28 | # 00 00 00 00 00 00 00 00 00 00 00 00 00 a5 a5 a5 29 | # 00 00 00 07 00 00 00 00 30 | # sg_cmds_process_resp: slen=18 31 | # unmap: Fixed format, current; Sense key: Illegal Request 32 | # Additional sense: Invalid command operation code 33 | # Raw sense data (in hex): 34 | # 70 00 05 00 00 00 00 0a 00 00 00 00 20 00 00 00 35 | # 00 00 36 | # UNMAP not supported 37 | # 38 | # -------------------------------------------------------- 39 | # Notice the 8 byte header then 5 descriptors in the parameter 40 | # list 41 | -------------------------------------------------------------------------------- /doc/sg_rdac.8: -------------------------------------------------------------------------------- 1 | .TH SG_RDAC "8" "November 2017" "sg3_utils\-1.43" SG3_UTILS 2 | .SH NAME 3 | sg_rdac \- display or modify SCSI RDAC Redundant Controller mode page 4 | .SH SYNOPSIS 5 | .B sg_rdac 6 | [\fI\-6\fR] [\fI\-a\fR] [\fI\-f=LUN\fR] [\fI\-v\fR] [\fI\-V\fR] \fIDEVICE\fR 7 | .SH DESCRIPTION 8 | .\" Add any additional description here 9 | sg_rdac displays or modifies the RDAC controller settings via the 10 | Redundant Controller mode page (0x2C). When modifying the settings it 11 | allows one to transfer the ownership of individual drives to the 12 | controller the command was received on. 13 | .SH OPTIONS 14 | .TP 15 | \fB\-6\fR 16 | Use the 6 byte cdb variants of the SCSI MODE SENSE and MODE SELECT commands. 17 | The default action (in the absence of this option) is to use the 10 byte 18 | cdb variants. 19 | .TP 20 | \fB\-a\fR 21 | Transfer all (visible) devices 22 | .TP 23 | \fB\-f\fR=\fILUN\fR 24 | Transfer the device identified by \fILUN\fR. This command will only work 25 | if the controller supports 'Dual Active Mode' (aka active/active mode). 26 | \fILUN\fR is a decimal number which cannot exceed 31 when the \fI\-6\fR 27 | option is given, otherwise is cannot exceed 255. 28 | .TP 29 | \fB\-v\fR 30 | be verbose 31 | .TP 32 | \fB\-V\fR 33 | print version string then exit 34 | .SH EXIT STATUS 35 | The exit status of sg_rdac is 0 when it is successful. Otherwise see 36 | the sg3_utils(8) man page. 37 | .SH AUTHOR 38 | Written by Hannes Reinecke , based on sg_emc_trespass. 39 | .SH "REPORTING BUGS" 40 | Report bugs to . 41 | .SH COPYRIGHT 42 | Copyright \(co 2006\-2017 Hannes Reinecke, Douglas Gilbert. 43 | .br 44 | This software is distributed under the GPL version 2. There is NO 45 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 46 | -------------------------------------------------------------------------------- /doc/Makefile.am: -------------------------------------------------------------------------------- 1 | 2 | dist_man_MANS = \ 3 | scsi_mandat.8 scsi_readcap.8 scsi_ready.8 scsi_satl.8 scsi_start.8 \ 4 | scsi_stop.8 scsi_temperature.8 sg3_utils.8 sg3_utils_json.8 \ 5 | sg_bg_ctl.8 sg_compare_and_write.8 sg_decode_sense.8 sg_format.8 \ 6 | sg_get_config.8 sg_get_elem_status.8 sg_get_lba_status.8 sg_ident.8 \ 7 | sg_inq.8 sg_logs.8 sg_luns.8 sg_modes.8 sg_opcodes.8 sg_persist.8 \ 8 | sg_prevent.8 sg_raw.8 sg_rdac.8 sg_read_attr.8 \ 9 | sg_read_block_limits.8 sg_read_buffer.8 sg_read_long.8 sg_readcap.8 \ 10 | sg_reassign.8 sg_referrals.8 sg_rem_rest_elem.8 sg_rep_density.8 \ 11 | sg_rep_pip.8 sg_rep_zones.8 sg_requests.8 sg_reset_wp.8 sg_rmsn.8 \ 12 | sg_rtpg.8 sg_safte.8 sg_sanitize.8 sg_sat_datetime.8 \ 13 | sg_sat_identify.8 sg_sat_phy_event.8 sg_sat_read_gplog.8 \ 14 | sg_sat_set_features.8 sg_seek.8 sg_senddiag.8 sg_ses.8 \ 15 | sg_ses_microcode.8 sg_start.8 sg_stpg.8 sg_stream_ctl.8 sg_sync.8 \ 16 | sg_timestamp.8 sg_turs.8 sg_unmap.8 sg_verify.8 sg_vpd.8 sg_wr_mode.8 \ 17 | sg_write_attr.8 sg_write_buffer.8 sg_write_long.8 sg_write_same.8 \ 18 | sg_write_verify.8 sg_write_x.8 sg_zone.8 sg_z_act_query.8 19 | CLEANFILES = 20 | 21 | if OS_LINUX 22 | dist_man_MANS += \ 23 | rescan-scsi-bus.sh.8 scsi_logging_level.8 sg_copy_results.8 sg_dd.8 \ 24 | sg_emc_trespass.8 sg_map.8 sg_map26.8 sg_rbuf.8 sg_read.8 sg_reset.8 \ 25 | sg_scan.8 sg_test_rwbuf.8 sg_xcopy.8 sginfo.8 sgm_dd.8 sgp_dd.8 26 | CLEANFILES += sg_scan.8 27 | sg_scan.8: sg_scan.8.linux 28 | cp -p $< $@ 29 | endif 30 | 31 | if OS_WIN32_MINGW 32 | dist_man_MANS += sg_scan.8 33 | CLEANFILES += sg_scan.8 34 | sg_scan.8: sg_scan.8.win32 35 | cp -p $< $@ 36 | endif 37 | 38 | if OS_WIN32_CYGWIN 39 | dist_man_MANS += sg_scan.8 40 | CLEANFILES += sg_scan.8 41 | sg_scan.8: sg_scan.8.win32 42 | cp -p $< $@ 43 | endif 44 | 45 | EXTRA_DIST = \ 46 | sg_scan.8.linux \ 47 | sg_scan.8.win32 48 | -------------------------------------------------------------------------------- /debian/control: -------------------------------------------------------------------------------- 1 | Source: sg3-utils 2 | Section: admin 3 | Priority: optional 4 | Maintainer: Eric Schwartz (Skif) 5 | Build-Depends: debhelper (>> 7), libtool, libcam-dev [kfreebsd-i386 kfreebsd-amd64] 6 | Standards-Version: 3.8.2 7 | 8 | Package: sg3-utils 9 | Architecture: any 10 | Depends: ${shlibs:Depends} 11 | Conflicts: sg-utils, cdwrite 12 | Replaces: sg-utils 13 | Description: utilities for devices using the SCSI command set. 14 | Most OSes have SCSI pass-through interfaces that enable user space programs 15 | to send SCSI commands to a device and fetch the response. With SCSI to ATA 16 | Translation (SAT) many ATA disks now can process SCSI commands. Typically 17 | each utility in this package implements one SCSI command. See the draft 18 | standards at www.t10.org for SCSI command definitions plus SAT. ATA 19 | commands are defined in the draft standards at www.t13.org . For a mapping 20 | between supported SCSI and ATA commands and utility names in this package 21 | see the COVERAGE file. Also some support for NVMe devices, especially via 22 | sg_ses to NVMe enclsoures. 23 | 24 | Package: libsgutils2-2 25 | Section: libs 26 | Depends: ${shlibs:Depends} 27 | Architecture: any 28 | Conflicts: libsgutils2 29 | Replaces: libsgutils2 30 | Suggests: sg3-utils 31 | Description: utilities for devices using the SCSI command set (shared libraries) 32 | Shared library used by the utilities in the sg3-utils package. 33 | 34 | Package: libsgutils2-dev 35 | Section: libdevel 36 | Architecture: any 37 | Depends: libsgutils2-2 (= ${binary:Version}), ${shlibs:Depends}, ${kfreebsd:Depends} 38 | Conflicts: libsgutils1-dev 39 | Suggests: sg3-utils 40 | Description: utilities for devices using the SCSI command set (developer files) 41 | Developer files (i.e. headers and a static library) which are associated with 42 | the utilities in the sg3-utils package. 43 | 44 | -------------------------------------------------------------------------------- /inhex/rep_zones.hex: -------------------------------------------------------------------------------- 1 | # This is the output (in hex) of the SCSI REPORT ZONES command 2 | # from a simulated ZBC device from the scsi_debug driver in Linux. 3 | # The parameters to the scsi_debug driver given to modprobe were: 4 | # dev_size_mb=512 zbc=managed zone_size_mb=128 zone_nr_conv=1 5 | # 6 | # The hex bytes in this file were generated by: 7 | # sg_rep_zones /dev/sg1 -HHH > /tmp/rep_zones.hex 8 | # where /dev/sg1 was a scsi_debug device. 9 | 10 | # An example invocation: 11 | # sg_rep_zones --inhex=rep_zones.hex 12 | 13 | 14 | # parameter data header (64 bytes) 15 | 00 00 01 00 00 00 00 00 00 00 00 00 00 0f ff ff 16 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 17 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 18 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 19 | 20 | # first zone descriptor, zone type: conventional 21 | 01 00 00 00 00 00 00 00 00 00 00 00 00 04 00 00 22 | 00 00 00 00 00 00 00 00 ff ff ff ff ff ff ff ff 23 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 24 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 25 | # second zone descriptor, zone type: sequential write required 26 | 02 10 00 00 00 00 00 00 00 00 00 00 00 04 00 00 27 | 00 00 00 00 00 04 00 00 00 00 00 00 00 04 00 00 28 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 29 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 30 | # third zone descriptor, zone type: sequential write required 31 | 02 10 00 00 00 00 00 00 00 00 00 00 00 04 00 00 32 | 00 00 00 00 00 08 00 00 00 00 00 00 00 08 00 00 33 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 34 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 35 | # fourth and last zone descriptor, zone type: sequential write required 36 | 02 10 00 00 00 00 00 00 00 00 00 00 00 04 00 00 37 | 00 00 00 00 00 0c 00 00 00 00 00 00 00 0c 00 00 38 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 39 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 40 | -------------------------------------------------------------------------------- /include/sg_json_sg_lib.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_JSON_SENSE_H 2 | #define SG_JSON_SENSE_H 3 | 4 | /* 5 | * Copyright (c) 2023 Douglas Gilbert. 6 | * All rights reserved. 7 | * Use of this source code is governed by a BSD-style 8 | * license that can be found in the BSD_LICENSE file. 9 | * 10 | * SPDX-License-Identifier: BSD-2-Clause 11 | */ 12 | 13 | #include 14 | #include 15 | #include 16 | 17 | #include "sg_json.h" 18 | 19 | #ifdef __cplusplus 20 | extern "C" { 21 | #endif 22 | 23 | /* These functions' implementations depend on code in sg_lib.c */ 24 | 25 | /* This function only produces JSON output if jsp is non-NULL and 26 | * jsp->pr_as_json is true. 'sbp' is assumed to point to sense data as 27 | * defined by T10 with a length of 'sb_len' bytes. Returns false if an 28 | * issue is detected, else it returns true. */ 29 | bool sgj_js_sense(sgj_state * jsp, sgj_opaque_p jop, const uint8_t * sbp, 30 | int sb_len); 31 | 32 | /* Decodes a designation descriptor (e.g. as found in the Device 33 | * Identification VPD page (0x83)) into JSON at position 'jop'. 34 | * Returns true if successful. */ 35 | bool sgj_js_designation_descriptor(sgj_state * jsp, sgj_opaque_p jop, 36 | const uint8_t * ddp, int dd_len); 37 | 38 | /* The in-core JSON tree is printed to 'fp' (typically stdout) by this call. 39 | * If jsp is NULL, jsp->pr_as_json is false or jsp->basep is NULL then this 40 | * function does nothing. If jsp->exit_status is true then a new JSON object 41 | * named "exit_status" and the 'exit_status' value rendered as a JSON integer 42 | * is appended to jsp->basep. The in-core JSON tree with jsp->basep as its 43 | * root is streamed to 'fp'. 44 | * Uses exit_status to call sg_lib::sg_exit2str() and then calls 45 | * sg_json::xxxxxx */ 46 | void sgj_js2file(sgj_state * jsp, sgj_opaque_p jop, int exit_status, 47 | FILE * fp); 48 | 49 | #ifdef __cplusplus 50 | } 51 | #endif 52 | 53 | #endif 54 | -------------------------------------------------------------------------------- /inhex/nvme_write_ctl.hex: -------------------------------------------------------------------------------- 1 | # 64 byte NVMe, Write command (a NVM command) that is suitable for: 2 | # sg_raw --cmdfile= --nvm --request=2048 3 | # 4 | # The address field (at byte offset 24, 8 bytes and little endian) gives 5 | # special meaning to the highest address pointers: 6 | # ffffffff fffffffe use address of data-in buffer 7 | # ffffffff fffffffd use address of data-out buffer 8 | # 9 | # The data length field (at byte offset 36, 4 bytes and little endian) 10 | # gives special meaning to the highest block counts: 11 | # fffffffe use byte length of data-in buffer 12 | # fffffffd use byte length of data-out buffer 13 | # 14 | # 512 byte logical block size is assumed. Write 4 blocks hence 2048 bytes. 15 | # The first LBA written is 0x12345 and the namespace is 1. If successful the 16 | # four blocks will be written out of the data-out buffer. Submission queue 17 | # is used (the same queue that Admin commands use). The NVM opcode for the 18 | # Write command is 0x1 and appears in the first command byte. 19 | 20 | 01 00 00 00 01 00 00 00 00 00 00 00 00 00 00 00 21 | 00 00 00 00 00 00 00 00 fd ff ff ff ff ff ff ff 22 | 00 00 00 00 fd ff ff ff 45 23 01 00 00 00 00 00 23 | 03 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 24 | 25 | # Notice NVMe uses its quirky "0's based" number of blocks so 26 | # 03 appears at byte offset 48 to mean "write 4 blocks". 27 | # 28 | # A typical invocation in Linux and FreeBSD would look like this: 29 | # sg_raw --cmdfile=nvme_write_ctl.hex --nvm -s 2048 30 | # --infile=t.bin /dev/nvme0 31 | # 32 | # Notice the '--nvm' option which is needed to distinguish a NVM 33 | # command from an Admin command as Admin commands are the default 34 | # in this utility. 35 | # 36 | # This utility (and most others in the package) aligns data-in and 37 | # data-out buffers to the beginning of pages which are 4096 bytes 38 | # long at a minimum. This is the way NVMe likes things as well. 39 | -------------------------------------------------------------------------------- /scripts/cciss_id: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # 3 | # cciss_id 4 | # 5 | # Generates device node names according to the cciss naming rules 6 | # 7 | # Copyright (C) 2011 SUSE Linux Products GmbH 8 | # Author: 9 | # Hannes Reinecke 10 | # 11 | # 12 | # This program is free software; you can redistribute it and/or modify it 13 | # under the terms of the GNU General Public License as published by the 14 | # Free Software Foundation version 2 of the License. 15 | # 16 | # This script generates a device node name which is compatible 17 | # with the 'cciss' device naming rules. 18 | # It is intended to provide backward-compatible names for the 19 | # 'hpsa' driver. 20 | # 21 | 22 | cciss_enumerate() 23 | { 24 | local last_pci_dev=${1##0000:} 25 | local cur_pci_dev 26 | local cciss_num=0 27 | 28 | for cur_pci_dev in $(lspci -n | tac | sed -n 's/\(..:..\..\) .* 103c:\(3220\|3230\|3238\|323a\|323b\) .*/\1/p') ; do 29 | if [ "$cur_pci_dev" == "$last_pci_dev" ] ; then 30 | echo "$cciss_num" 31 | return; 32 | fi 33 | cciss_num=$(($cciss_num + 1)) 34 | done 35 | echo "$cciss_num" 36 | } 37 | 38 | hpsa_lun_offset() 39 | { 40 | local scsi_host=$1 41 | 42 | scsi_id=$(lsscsi 2>/dev/null | sed -n "s/.\(${scsi_host}:[0-9]*:[0-9]*:[0-9]*\)..*disk .*/\1/p" | head -1) 43 | echo ${scsi_id##*:} 44 | } 45 | 46 | DEVPATH=$1 47 | SCSIPATH=$(cd -P /sys$DEVPATH/device; echo $PWD) 48 | SCSIID=${SCSIPATH##*/} 49 | HOSTID=${SCSIID%%:*} 50 | LUNID=${SCSIID##*:} 51 | PCIPATH=${SCSIPATH%%/host*} 52 | PCIDEV=${PCIPATH##*/} 53 | HOSTPATH=${PCIPATH}/host${HOSTID}/scsi_host/host${HOSTID} 54 | read controller 2>/dev/null <${HOSTPATH}/ctlr_num || controller=$(cciss_enumerate $PCIDEV) 55 | 56 | # hpsa lies about the LUN ... 57 | disk_offset=$(hpsa_lun_offset $HOSTID) 58 | if [ "$disk_offset" ] ; then 59 | disk=$(( $LUNID - $disk_offset )) 60 | else 61 | disk=$LUNID 62 | fi 63 | 64 | if [ "$controller" ] && [ "$disk" ] ; then 65 | echo "ID_CCISS=c${controller}d${disk}" 66 | fi 67 | -------------------------------------------------------------------------------- /testing/sg_json_builder_test.c: -------------------------------------------------------------------------------- 1 | // SPDX-License-Identifier: (GPL-2.0-or-later OR BSD-2-Clause) 2 | /* 3 | * Simple streaming JSON writer 4 | * 5 | * This takes care of the annoying bits of JSON syntax like the commas 6 | * after elements 7 | * 8 | * Authors: Stephen Hemminger 9 | * 10 | * Borrowed from Linux kernel [5.17.0]: tools/bpf/bpftool/json_writer.[hc] 11 | */ 12 | 13 | #include 14 | #include 15 | #include 16 | #include 17 | #include 18 | #include 19 | #include 20 | 21 | #include "../lib/sg_json_builder.h" 22 | 23 | int main(int argc, char **argv) 24 | { 25 | json_writer_t *wr = jsonw_new(stdout); 26 | 27 | jsonw_start_object(wr); 28 | jsonw_pretty(wr, true); 29 | jsonw_name(wr, "Vyatta"); 30 | jsonw_start_object(wr); 31 | jsonw_string_field(wr, "url", "http://vyatta.com"); 32 | jsonw_uint_field(wr, "downloads", 2000000ul); 33 | jsonw_float_field(wr, "stock", 8.16); 34 | 35 | jsonw_name(wr, "ARGV"); 36 | jsonw_start_array(wr); 37 | while (--argc) 38 | jsonw_string(wr, *++argv); 39 | jsonw_end_array(wr); 40 | 41 | jsonw_name(wr, "empty"); 42 | jsonw_start_array(wr); 43 | jsonw_end_array(wr); 44 | 45 | jsonw_name(wr, "NIL"); 46 | jsonw_start_object(wr); 47 | jsonw_end_object(wr); 48 | 49 | jsonw_null_field(wr, "my_null"); 50 | 51 | jsonw_name(wr, "special chars"); 52 | jsonw_start_array(wr); 53 | jsonw_string_field(wr, "slash", "/"); 54 | jsonw_string_field(wr, "newline", "\n"); 55 | jsonw_string_field(wr, "tab", "\t"); 56 | jsonw_string_field(wr, "ff", "\f"); 57 | jsonw_string_field(wr, "quote", "\""); 58 | jsonw_string_field(wr, "tick", "\'"); 59 | jsonw_string_field(wr, "backslash", "\\"); 60 | jsonw_end_array(wr); 61 | 62 | jsonw_name(wr, "ARGV"); 63 | jsonw_start_array(wr); 64 | jsonw_string(wr, "boo: appended or new entry?"); 65 | jsonw_end_array(wr); 66 | 67 | jsonw_end_object(wr); 68 | 69 | jsonw_end_object(wr); 70 | jsonw_destroy(&wr); 71 | return 0; 72 | } 73 | 74 | -------------------------------------------------------------------------------- /inhex/nvme_read_ctl.hex: -------------------------------------------------------------------------------- 1 | # 64 byte NVMe, Read command (a NVM command) that is suitable for: 2 | # sg_raw --cmdfile= --nvm --request=2048 3 | # 4 | # The address field (at byte offset 24, 8 bytes and little endian) gives 5 | # special meaning to the highest address pointers: 6 | # ffffffff fffffffe use address of data-in buffer 7 | # ffffffff fffffffd use address of data-out buffer 8 | # 9 | # The data length field (at byte offset 36, 4 bytes and little endian) 10 | # gives special meaning to the highest block counts: 11 | # fffffffe use byte length of data-in buffer 12 | # fffffffd use byte length of data-out buffer 13 | # 14 | # 512 byte logical block size is assumed. Read 4 blocks hence 2048 bytes. 15 | # The first LBA read is 0x12345 and the namespace is 1. If successful 16 | # the four blocks will be read into the data-in buffer. Submission queue 17 | # 0 is used (the same queue that Admin commands use). The NVM opcode for 18 | # the Read command is 0x2 and appears in the first command byte. 19 | 20 | 02 00 00 00 01 00 00 00 00 00 00 00 00 00 00 00 21 | 00 00 00 00 00 00 00 00 fe ff ff ff ff ff ff ff 22 | 00 00 00 00 fe ff ff ff 45 23 01 00 00 00 00 00 23 | 03 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 24 | 25 | # Notice NVMe uses its quirky "0's based" number of blocks so 26 | # 03 appears at byte offset 48 to mean "read 4 blocks". 27 | # 28 | # A typical invocation in Linux and FreeBSD would look like this: 29 | # sg_raw --cmdfile=nvme_read_ctl.hex --nvm -r 2048 30 | # --outfile=t.bin /dev/nvme0n1 31 | # In FreeBSD the device name would be /dev/nvme0ns1 32 | # 33 | # Notice the '--nvm' option which is needed to distinguish a NVM 34 | # command from an Admin command as Admin commands are the default 35 | # in this utility. 36 | # 37 | # This utility (and most others in the package) aligns data-in and 38 | # data-out buffers to the beginning of pages which are 4096 bytes 39 | # long at a minimum. This is the way NVMe likes things as well. 40 | -------------------------------------------------------------------------------- /include/sg_pt_linux_missing.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_PT_LINUX_MISSING_H 2 | #define SG_PT_LINUX_MISSING_H 3 | 4 | /* 5 | * Copyright (c) 2023 Douglas Gilbert. 6 | * All rights reserved. 7 | * Use of this source code is governed by a BSD-style 8 | * license that can be found in the BSD_LICENSE file. 9 | * 10 | * SPDX-License-Identifier: BSD-2-Clause 11 | */ 12 | 13 | #include 14 | #include 15 | 16 | 17 | /* This header is for internal use by the sg3_utils library (libsgutils) 18 | * and is Linux specific. Best not to include it directly in code that 19 | * is meant to be OS independent. 20 | * This header is only used with Linux if linux/types.h and linux/major.h 21 | * are not available. This is the case with MUSL libc for example. */ 22 | 23 | #ifdef __cplusplus 24 | extern "C" { 25 | #endif 26 | 27 | #ifndef HAVE___U64 28 | /* typedefs if linux/types.h header not available */ 29 | 30 | typedef uint64_t __u64; 31 | typedef int64_t __s64; 32 | typedef uint32_t __u32; 33 | typedef int32_t __s32; 34 | typedef uint16_t __u16; 35 | typedef int16_t __s16; 36 | #endif 37 | 38 | 39 | /* Following if linux/major.h header is not available */ 40 | #define MEM_MAJOR 1 41 | #define IDE0_MAJOR 3 42 | #define SCSI_DISK0_MAJOR 8 43 | #define SCSI_TAPE_MAJOR 9 44 | #define SCSI_CDROM_MAJOR 11 45 | #define SCSI_GENERIC_MAJOR 21 46 | #define IDE1_MAJOR 22 47 | #define IDE2_MAJOR 33 48 | #define IDE3_MAJOR 34 49 | #define IDE4_MAJOR 56 50 | #define IDE5_MAJOR 57 51 | #define SCSI_DISK1_MAJOR 65 52 | #define SCSI_DISK2_MAJOR 66 53 | #define SCSI_DISK3_MAJOR 67 54 | #define SCSI_DISK4_MAJOR 68 55 | #define SCSI_DISK5_MAJOR 69 56 | #define SCSI_DISK6_MAJOR 70 57 | #define SCSI_DISK7_MAJOR 71 58 | #define IDE6_MAJOR 88 59 | #define IDE7_MAJOR 89 60 | #define IDE8_MAJOR 90 61 | #define IDE9_MAJOR 91 62 | 63 | #ifdef __cplusplus 64 | } 65 | #endif 66 | 67 | #endif /* end of SG_PT_LINUX_MISSING_H */ 68 | -------------------------------------------------------------------------------- /doc/scsi_readcap.8: -------------------------------------------------------------------------------- 1 | .TH SCSI_READCAP "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | scsi_readcap \- do SCSI READ CAPACITY command on disks 4 | .SH SYNOPSIS 5 | .B scsi_readcap 6 | [\fI\-\-brief\fR] [\fI\-\-help\fR] [\fI\-\-long\fR] [\fI\-\-verbose\fR] 7 | \fIDEVICE\fR [\fIDEVICE\fR]* 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | This bash shell script calls the sg_readcap utility on each given 11 | \fIDEVICE\fR. This will send a SCSI READ CAPACITY command to each 12 | \fIDEVICE\fR. 13 | .PP 14 | The default action of this script is to send the 10 byte cdb READ 15 | CAPACITY(10) command to each \fIDEVICE\fR. If a response indicates 16 | the number of blocks is greater than or equal to '2**32 \- 1' then 17 | the READ CAPACITY(16) is sent and its response is output. 18 | .SH OPTIONS 19 | Arguments to long options are mandatory for short options as well. 20 | .TP 21 | \fB\-b\fR, \fB\-\-brief\fR 22 | shortens the output to two hexadecimal numbers, both prefixed by '0x'. 23 | The first number is the number of blocks available and the second is 24 | the size of each blocks in bytes (e.g. '0x12a19eb0 0x200'). If an error 25 | is detected '0x0 0x0' is output and the script continues if there are 26 | more \fIDEVICE\fRs. 27 | .TP 28 | \fB\-h\fR, \fB\-\-help\fR 29 | print out the usage message then exit. 30 | .TP 31 | \fB\-l\fR, \fB\-\-long\fR 32 | the default is to send the READ CAPACITY(10) command (i.e. the 10 byte 33 | cdb variant). When this option is given the READ CAPACITY(16) command 34 | is sent. The latter command yields more information in its response. 35 | .TP 36 | \fB\-v\fR, \fB\-\-verbose\fR 37 | increase level or verbosity. 38 | .SH EXIT STATUS 39 | The exit status of this script is 0 when it is successful. Otherwise the 40 | exit status is that of the last sg_readcap utility called. See 41 | the sg3_utils(8) man page. 42 | .SH AUTHORS 43 | Written by D. Gilbert 44 | .SH COPYRIGHT 45 | Copyright \(co 2009\-2013 Douglas Gilbert 46 | .br 47 | This software is distributed under a BSD\-2\-Clause license. There is NO 48 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 49 | .SH "SEE ALSO" 50 | .B sg_readcap (sg3_utils) 51 | -------------------------------------------------------------------------------- /doc/sg_emc_trespass.8: -------------------------------------------------------------------------------- 1 | .TH SG_EMC_TRESPASS "8" "December 2012" "sg3_utils\-1.35" SG3_UTILS 2 | .SH NAME 3 | sg_emc_trespass \- change ownership of SCSI LUN from another 4 | Service\-Processor to this one 5 | .SH SYNOPSIS 6 | .B sg_emc_trespass 7 | [\fI\-d\fR] [\fI\-hr\fR] [\fI\-s\fR] 8 | [\fI\-V\fR] \fIDEVICE\fR 9 | .SH DESCRIPTION 10 | .\" Add any additional description here 11 | sg_emc_trespass sends an EMC\-specific Trespass Command to the \fIDEVICE\fR 12 | with the selected options. This Mode Select changes the ownership of the LUN 13 | of the device from another Service\-Processor to the one the command was 14 | received on. 15 | .SH OPTIONS 16 | Arguments to long options are mandatory for short options as well. 17 | .TP 18 | \fB\-d\fR 19 | outputs some extra debug information associated with executing this command 20 | .TP 21 | \fB\-hr\fR 22 | Sets the 'Honor Reservation' bit in the command. If set, the trespass 23 | will only succeed to change the ownership from the Peer SP if the Peer 24 | SP does not have an outstanding SCSI reservation for the LUN. By 25 | default, the reservation state will be ignored. 26 | .TP 27 | \fB\-s\fR 28 | Send the short version of the trespass command instead of the long 29 | version. The short version is supported on the EMC FC5300, FC4500 and 30 | FC4700. The long version (default) is supported on the CLARiiON CX and 31 | AX family arrays. 32 | .TP 33 | \fB\-V\fR 34 | print out version string then exit. 35 | .PP 36 | In the 2.4 series of Linux kernels the \fIDEVICE\fR must be a SCSI 37 | generic (sg) device. In the 2.6 series block devices (e.g. SCSI disks 38 | and DVD drives) can also be specified. For example "sg_start 0 /dev/sda" 39 | will work in the 2.6 series kernels. 40 | .SH EXIT STATUS 41 | The exit status of sg_emc_trespass is 0 when it is successful. Otherwise see 42 | the sg3_utils(8) man page. 43 | .SH AUTHOR 44 | Written by Lars Marowsky\-Bree, based on sg_start. 45 | .SH "REPORTING BUGS" 46 | Report bugs to . 47 | .SH COPYRIGHT 48 | Copyright \(co 2004\-2012 Lars Marowsky\-Bree, Douglas Gilbert. 49 | .br 50 | This software is distributed under the GPL version 2. There is NO 51 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 52 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Please keep the entries in this file sorted with the following vi command: 2 | # :3,$!LC_ALL=C sort -fu 3 | 4 | *.exe 5 | *.la 6 | *.lo 7 | *.o 8 | *~ 9 | .deps/ 10 | .libs/ 11 | /aclocal.m4 12 | /ar-lib 13 | /autom4te.cache/ 14 | /compile 15 | /config.guess 16 | /config.h 17 | /config.h.in 18 | /config.log 19 | /config.status 20 | /config.sub 21 | /configure 22 | /depcomp 23 | /doc/Makefile 24 | /doc/sg_scan.8 25 | /include/Makefile 26 | /install-sh 27 | /lib/Makefile 28 | /libtool 29 | /ltmain.sh 30 | /Makefile 31 | /missing 32 | /scripts/Makefile 33 | /sg3_utils-*.tar.gz 34 | /src/Makefile 35 | /src/sginfo 36 | /src/sgm_dd 37 | /src/sgp_dd 38 | /src/sg_bg_ctl 39 | /src/sg_compare_and_write 40 | /src/sg_copy_results 41 | /src/sg_dd 42 | /src/sg_decode_sense 43 | /src/sg_emc_trespass 44 | /src/sg_format 45 | /src/sg_get_config 46 | /src/sg_get_elem_status 47 | /src/sg_get_lba_status 48 | /src/sg_ident 49 | /src/sg_inq 50 | /src/sg_logs 51 | /src/sg_luns 52 | /src/sg_map 53 | /src/sg_map26 54 | /src/sg_modes 55 | /src/sg_opcodes 56 | /src/sg_persist 57 | /src/sg_prevent 58 | /src/sg_raw 59 | /src/sg_rbuf 60 | /src/sg_rdac 61 | /src/sg_read 62 | /src/sg_readcap 63 | /src/sg_read_attr 64 | /src/sg_read_block_limits 65 | /src/sg_read_buffer 66 | /src/sg_read_long 67 | /src/sg_reassign 68 | /src/sg_referrals 69 | /src/sg_rem_rest_elem 70 | /src/sg_rep_density 71 | /src/sg_rep_pip 72 | /src/sg_rep_zones 73 | /src/sg_requests 74 | /src/sg_reset 75 | /src/sg_reset_wp 76 | /src/sg_rmsn 77 | /src/sg_rtpg 78 | /src/sg_safte 79 | /src/sg_sanitize 80 | /src/sg_sat_identify 81 | /src/sg_sat_phy_event 82 | /src/sg_sat_read_gplog 83 | /src/sg_sat_set_features 84 | /src/sg_scan 85 | /src/sg_seek 86 | /src/sg_senddiag 87 | /src/sg_ses 88 | /src/sg_ses_microcode 89 | /src/sg_start 90 | /src/sg_stpg 91 | /src/sg_stream_ctl 92 | /src/sg_sync 93 | /src/sg_test_rwbuf 94 | /src/sg_timestamp 95 | /src/sg_turs 96 | /src/sg_unmap 97 | /src/sg_verify 98 | /src/sg_vpd 99 | /src/sg_write_buffer 100 | /src/sg_write_long 101 | /src/sg_write_same 102 | /src/sg_write_verify 103 | /src/sg_write_x 104 | /src/sg_wr_mode 105 | /src/sg_xcopy 106 | /src/sg_zone 107 | /src/sg_z_act_query 108 | /stamp-h1 109 | Makefile.in 110 | -------------------------------------------------------------------------------- /include/sg_linux_inc.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_LINUX_INC_H 2 | #define SG_LINUX_INC_H 3 | 4 | #ifdef SG_KERNEL_INCLUDES 5 | #include /* C99 header for exact integer types */ 6 | #define __user 7 | typedef uint8_t u8; 8 | #include "/usr/src/linux/include/scsi/sg.h" 9 | #include "/usr/src/linux/include/scsi/scsi.h" 10 | #else 11 | #ifdef SG_TRICK_GNU_INCLUDES 12 | #include 13 | #include 14 | #else 15 | #define __user 16 | #include 17 | #include 18 | #endif 19 | #endif 20 | 21 | #ifdef BLKGETSIZE64 22 | #ifndef u64 23 | #include /* C99 header for exact integer types */ 24 | typedef uint64_t u64; /* problems with BLKGETSIZE64 ioctl in lk 2.4 */ 25 | #endif 26 | #endif 27 | 28 | /* 29 | Getting the correct include files for the sg interface can be an ordeal. 30 | In a perfect world, one would just write: 31 | #include 32 | #include 33 | This would include the files found in the /usr/include/scsi directory. 34 | Those files are maintained with the GNU library which may or may not 35 | agree with the kernel and version of sg driver that is running. Any 36 | many cases this will not matter. However in some it might, for example 37 | glibc 2.1's include files match the sg driver found in the lk 2.2 38 | series. Hence if glibc 2.1 is used with lk 2.4 then the additional 39 | sg v3 interface will not be visible. 40 | If this is a problem then defining SG_KERNEL_INCLUDES will access the 41 | kernel supplied header files (assuming they are in the normal place). 42 | The GNU library maintainers and various kernel people don't like 43 | this approach (but it does work). 44 | The technique selected by defining SG_TRICK_GNU_INCLUDES worked (and 45 | was used) prior to glibc 2.2 . Prior to that version /usr/include/linux 46 | was a symbolic link to /usr/src/linux/include/linux . 47 | 48 | There are other approaches if this include "mixup" causes pain. These 49 | would involve include files being copied or symbolic links being 50 | introduced. 51 | 52 | Sorry about the inconvenience. Typically neither SG_KERNEL_INCLUDES 53 | nor SG_TRICK_GNU_INCLUDES is defined. 54 | 55 | dpg 20010415, 20030522 56 | */ 57 | 58 | #endif 59 | -------------------------------------------------------------------------------- /include/sg_cmds_mmc.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_CMDS_MMC_H 2 | #define SG_CMDS_MMC_H 3 | 4 | /* 5 | * Copyright (c) 2008-2017 Douglas Gilbert. 6 | * All rights reserved. 7 | * Use of this source code is governed by a BSD-style 8 | * license that can be found in the BSD_LICENSE file. 9 | * 10 | * SPDX-License-Identifier: BSD-2-Clause 11 | */ 12 | 13 | #ifdef __cplusplus 14 | extern "C" { 15 | #endif 16 | 17 | 18 | /* Invokes a SCSI GET CONFIGURATION command (MMC-3...6). 19 | * Returns 0 when successful, SG_LIB_CAT_INVALID_OP if command not 20 | * supported, SG_LIB_CAT_ILLEGAL_REQ if field in cdb not supported, 21 | * SG_LIB_CAT_UNIT_ATTENTION, SG_LIB_CAT_ABORTED_COMMAND, else -1 */ 22 | int sg_ll_get_config(int sg_fd, int rt, int starting, void * resp, 23 | int mx_resp_len, bool noisy, int verbose); 24 | 25 | /* Invokes a SCSI GET PERFORMANCE command (MMC-3...6). 26 | * Returns 0 when successful, SG_LIB_CAT_INVALID_OP if command not 27 | * supported, SG_LIB_CAT_ILLEGAL_REQ if field in cdb not supported, 28 | * SG_LIB_CAT_UNIT_ATTENTION, SG_LIB_CAT_ABORTED_COMMAND, else -1 */ 29 | int sg_ll_get_performance(int sg_fd, int data_type, unsigned int starting_lba, 30 | int max_num_desc, int type, void * resp, 31 | int mx_resp_len, bool noisy, int verbose); 32 | 33 | /* Invokes a SCSI SET CD SPEED command (MMC). 34 | * Return of 0 -> success, SG_LIB_CAT_INVALID_OP -> command not supported, 35 | * SG_LIB_CAT_ILLEGAL_REQ -> bad field in cdb, SG_LIB_CAT_UNIT_ATTENTION, 36 | * SG_LIB_CAT_NOT_READY -> device not ready, SG_LIB_CAT_ABORTED_COMMAND, 37 | * -1 -> other failure */ 38 | int sg_ll_set_cd_speed(int sg_fd, int rot_control, int drv_read_speed, 39 | int drv_write_speed, bool noisy, int verbose); 40 | 41 | /* Invokes a SCSI SET STREAMING command (MMC). Return of 0 -> success, 42 | * SG_LIB_CAT_INVALID_OP -> Set Streaming not supported, 43 | * SG_LIB_CAT_ILLEGAL_REQ -> bad field in cdb, SG_LIB_CAT_ABORTED_COMMAND, 44 | * SG_LIB_CAT_UNIT_ATTENTION, SG_LIB_CAT_NOT_READY -> device not ready, 45 | * -1 -> other failure */ 46 | int sg_ll_set_streaming(int sg_fd, int type, void * paramp, int param_len, 47 | bool noisy, int verbose); 48 | 49 | 50 | #ifdef __cplusplus 51 | } 52 | #endif 53 | 54 | #endif 55 | -------------------------------------------------------------------------------- /examples/Makefile.freebsd: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/man 6 | 7 | # In Linux the default C compiler is GCC while in FreeBSD (since release 10 ?) 8 | # the default C compiler is clang. Swap the comment marks (lines starting 9 | # with '#') on the next 4 (non-blank) lines. 10 | # CC = gcc 11 | # CC = clang 12 | 13 | # LD = gcc 14 | # LD = clang 15 | 16 | 17 | EXECS = sg_simple5 18 | 19 | # EXTRAS = sgq_dd 20 | 21 | MAN_PGS = 22 | MAN_PREF = man8 23 | 24 | OS_FLAGS = -DSG_LIB_FREEBSD 25 | EXTRA_FLAGS = $(OS_FLAGS) 26 | 27 | # CFLAGS = -O2 -Wall -W $(EXTRA_FLAGS) -I ../include 28 | CFLAGS = -g -O2 -Wall -W $(EXTRA_FLAGS) -I ../include 29 | # CFLAGS = -g -O2 -Wall -W -pedantic -std=c99 $(EXTRA_FLAGS) -I ../include 30 | 31 | CFLAGS_PTHREADS = -D_REENTRANT 32 | 33 | # there is no rule to make the following in the parent directory, 34 | # it is assumed they are already built. 35 | D_FILES = ../lib/sg_lib.o ../lib/sg_lib_data.o ../lib/sg_pr2serr.o ../lib/sg_cmds_basic.o ../lib/sg_pt_common.o ../lib/sg_pt_freebsd.o 36 | 37 | LDFLAGS = -lcam 38 | 39 | all: $(EXECS) 40 | 41 | extras: $(EXTRAS) 42 | 43 | 44 | depend dep: 45 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 46 | done > .depend 47 | 48 | clean: 49 | /bin/rm -f *.o $(EXECS) $(EXTRAS) core .depend 50 | 51 | sg_simple5: sg_simple5.o $(D_FILES) 52 | $(CC) -o $@ $(LDFLAGS) $@.o $(D_FILES) 53 | 54 | 55 | install: $(EXECS) 56 | install -d $(INSTDIR) 57 | for name in $^; \ 58 | do install -s -o root -g root -m 755 $$name $(INSTDIR); \ 59 | done 60 | install -d $(MANDIR)/$(MAN_PREF) 61 | for mp in $(MAN_PGS); \ 62 | do install -o root -g root -m 644 $$mp $(MANDIR)/$(MAN_PREF); \ 63 | gzip -9f $(MANDIR)/$(MAN_PREF)/$$mp; \ 64 | done 65 | 66 | uninstall: 67 | dists="$(EXECS)"; \ 68 | for name in $$dists; do \ 69 | rm -f $(INSTDIR)/$$name; \ 70 | done 71 | for mp in $(MAN_PGS); do \ 72 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 73 | done 74 | 75 | # Linux uses GNU make and FreeBSD uses Berkely make. The following lines 76 | # only work in Linux. Possible solutions in FreeBSD: 77 | # a) use 'gmake'; b) comment out the next 3 lines, starting with 'ifeq' 78 | # c) build with 'make -f Makefile.freebsd' 79 | # In Linux one can install bmake (but that won't help here). 80 | # ifeq (.depend,$(wildcard .depend)) 81 | # include .depend 82 | # endif 83 | -------------------------------------------------------------------------------- /testing/README: -------------------------------------------------------------------------------- 1 | 2 | 3 | The utilities in this directory are _not_ built automatically. So: 4 | cd 5 | ./configure ; make ; make install 6 | will _not_ build and install them. The make command (or some variant 7 | of it) needs to be run in this directory as outlined below. 8 | 9 | Building files in this directory depends on several files being already 10 | built in the ../lib directory. So to build files here, the ./configure 11 | needs to be executed in the parent directory followed by changing 12 | directory to the lib directory and calling 'make' there. 13 | Another way is to do a top level 'make' after the ./configure which 14 | will make the libraries followed by all the utilities in the src/ 15 | directory. To make them in FreeBSD use 'make -f Makefile.freebsd' . 16 | 17 | The utilities in this directory do not have manpages. They have 18 | relatively complete but terse help messages, typically seen by using 19 | the '--help' option one or more times. If called several times, the 20 | shorter form of the help option is more convenient, for example: '-hhh'. 21 | And of course there is the source code. Unfortunately where the code 22 | implements many different options, it can become a bit dense. There 23 | is also a large amount of error checking, as many of these utilities 24 | were used to test new features placed in the sg v4 driver in Linux. 25 | 26 | The sg_chk_asc utility decodes the SCSI additional sense code table 27 | found at https://www.t10.org/lists/asc-num.txt and checks it against 28 | the table found in sg_lib_data.c in the lib/ subdirectory. It is 29 | designed to keep the table in sg_lib_data.c in "sync" with the 30 | table at the t10.org web site. 31 | 32 | The tst_sg_lib utility exercises several functions found in sg_lib.c 33 | and related files in the 'lib' sibling directory. Use 'tst_sg_lib -h' 34 | to get more information. 35 | 36 | There are both C and C++ files in this directory, they have extensions 37 | '.c' and '.cpp' respectively. Now both are built with rules in Makefile 38 | (at least in Linux). A gcc/g++ compiler of 4.7.3 vintage or later 39 | (or a recent clang compiler) will be required. To make them in FreeBSD 40 | use 'make -f Makefile.freebsd'. 41 | 42 | The sgh_dd utility (C++) uses 'libatomic' which may not be installed 43 | on some systems. On Debian based systems 'apt install libatomic1' fixes 44 | this. 45 | 46 | Douglas Gilbert 47 | 17th September 2019 48 | -------------------------------------------------------------------------------- /doc/sg_read_block_limits.8: -------------------------------------------------------------------------------- 1 | .TH SG_READ_BLOCK_LIMITS "8" "November 2022" "sg3_utils\-1.48" SG3_UTILS 2 | .SH NAME 3 | sg_read_block_limits \- send SCSI READ BLOCK LIMITS command 4 | .SH SYNOPSIS 5 | .B sg_read_block_limits 6 | [\fI\-\-help\fR] [\fI\-\-hex\fR] [--mloi] [\fI\-\-raw\fR] 7 | [\fI\-\-readonly\fR] [\fI\-\-verbose\fR] [\fI\-\-version\fR] 8 | \fIDEVICE\fR 9 | .SH DESCRIPTION 10 | .\" Add any additional description here 11 | Send a SCSI READ BLOCK LIMITS command to \fIDEVICE\fR and outputs the 12 | response. This command is defined for tape (drives) and its description 13 | is found in the SSC documents at https://www.t10.org . 14 | .SH OPTIONS 15 | Arguments to long options are mandatory for short options as well. 16 | .TP 17 | \fB\-h\fR, \fB\-\-help\fR 18 | output the usage message then exit. 19 | .TP 20 | \fB\-H\fR, \fB\-\-hex\fR 21 | output response in hex (rather than decode it). 22 | .TP 23 | \fB\-m\fR, \fB\-\-mloi\fR 24 | sets the MLOI bit in the READ BLOCK LIMITS command and if that 25 | succeeds, prints out the Maximum Logical Object Identifier (MLOI) 26 | value. The MLOI bit was introduced in the ssc4r02.pdf draft. 27 | .TP 28 | \fB\-r\fR, \fB\-\-raw\fR 29 | output response in binary to stdout. 30 | .TP 31 | \fB\-R\fR, \fB\-\-readonly\fR 32 | open \fIDEVICE\fR in read\-only mode. The default is to open it in 33 | read\-write mode. 34 | .TP 35 | \fB\-v\fR, \fB\-\-verbose\fR 36 | increase the level of verbosity, (i.e. debug output). 37 | .TP 38 | \fB\-V\fR, \fB\-\-version\fR 39 | print the version string and then exit. 40 | .SH EXIT STATUS 41 | The exit status of sg_read_block_limits is 0 when it is successful. Otherwise 42 | see the sg3_utils(8) man page. 43 | .SH EXAMPLES 44 | It is usually okay to use no options. Here is an invocation (on the first 45 | line following the "#" command prompt) followed by some typical output: 46 | .PP 47 | # sg_read_block_limits /dev/st0 48 | Read Block Limits results: 49 | Minimum block size: 1 byte(s) 50 | Maximum block size: 16777215 byte(s), 16383 KB, 15 MB 51 | Granularity: 0 52 | .SH AUTHORS 53 | Written by Douglas Gilbert. 54 | .SH "REPORTING BUGS" 55 | Report bugs to . 56 | .SH COPYRIGHT 57 | Copyright \(co 2009\-2022 Douglas Gilbert 58 | .br 59 | This software is distributed under a BSD\-2\-Clause license. There is NO 60 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 61 | .SH "SEE ALSO" 62 | .B sg3_utils(sg3_utils) 63 | -------------------------------------------------------------------------------- /debian/rules: -------------------------------------------------------------------------------- 1 | #!/usr/bin/make -f 2 | # Sample debian/rules that uses debhelper. 3 | # GNU copyright 1997 by Joey Hess. 4 | # 5 | # This version is for a hypothetical package that builds an 6 | # architecture-dependant package, as well as an architecture-independent 7 | # package. 8 | 9 | # Uncomment this to turn on verbose mode. 10 | # export DH_VERBOSE=1 11 | 12 | DEB_HOST_ARCH_OS := $(shell dpkg-architecture -qDEB_HOST_ARCH_OS 2>/dev/null) 13 | 14 | configure: configure-stamp 15 | configure-stamp: 16 | dh_testdir 17 | # Add here commands to configure the package. 18 | CFLAGS="$(CFLAGS)" ./configure --host=$(DEB_HOST_GNU_TYPE) --build=$(DEB_BUILD_GNU_TYPE) --bindir=/usr/bin --prefix=/usr --mandir=\$${prefix}/share/man 19 | touch configure-stamp 20 | 21 | build: configure-stamp build-stamp 22 | build-stamp: 23 | dh_testdir 24 | 25 | # Add here commands to compile the package. 26 | PREFIX=/usr MANDIR=/usr/share/man $(MAKE) -e 27 | 28 | touch build-stamp 29 | 30 | clean: 31 | dh_testdir 32 | dh_testroot 33 | 34 | # Add here commands to clean up after the build process. 35 | -$(MAKE) distclean 36 | 37 | rm -f build-stamp configure-stamp debian/substvars 38 | 39 | dh_clean 40 | 41 | install: DH_OPTIONS= 42 | install: build 43 | dh_testdir 44 | dh_testroot 45 | dh_clean 46 | dh_installdirs 47 | 48 | # Add here commands to install the package into debian/tmp 49 | $(MAKE) -e install DESTDIR=$(CURDIR)/debian/tmp PREFIX=/usr 50 | 51 | dh_install --autodest --sourcedir=debian/tmp 52 | 53 | dh_installman 54 | 55 | # Build architecture-independent files here. 56 | # Pass -i to all debhelper commands in this target to reduce clutter. 57 | binary-indep: build install 58 | # nothing to do here 59 | 60 | # Build architecture-dependent files here. 61 | binary-arch: build install 62 | dh_testdir -a 63 | dh_testroot -a 64 | dh_installdocs -a 65 | dh_installexamples -a 66 | dh_installmenu -a 67 | dh_installchangelogs ChangeLog -a 68 | dh_strip -a 69 | dh_link -a 70 | dh_compress -a -X archive -X .c -X .h 71 | dh_fixperms -a 72 | dh_makeshlibs -V -v 73 | dh_installdeb -a 74 | ifeq ($(DEB_HOST_ARCH_OS),kfreebsd) 75 | echo kfreebsd:Depends=libcam-dev >>debian/libsgutils2-dev.substvars 76 | endif 77 | dh_shlibdeps -ldebian/tmp/usr/lib -L libsgutils2 78 | dh_gencontrol -a 79 | dh_md5sums -a 80 | dh_builddeb -a 81 | 82 | binary: binary-indep binary-arch 83 | .PHONY: build clean binary-indep binary-arch binary install configure 84 | -------------------------------------------------------------------------------- /doc/sg_rep_pip.8: -------------------------------------------------------------------------------- 1 | .TH SG_REP_PIP "8" "January 2022" "sg3_utils\-1.48" SG3_UTILS 2 | .SH NAME 3 | sg_rep_pip \- send SCSI REPORT PROVISIONING INITIALIZATION PATTERN command 4 | .SH SYNOPSIS 5 | .B sg_rep_pip 6 | [\fI\-\-help\fR] [\fI\-\-hex\fR] [\fI\-\-maxlen=LEN\fR] [\fI\-\-raw\fR] 7 | [\fI\-\-readonly\fR] [\fI\-\-verbose\fR] [\fI\-\-version\fR] 8 | \fIDEVICE\fR 9 | .SH DESCRIPTION 10 | .\" Add any additional description here 11 | Sends a SCSI REPORT PROVISIONING INITIALIZATION PATTERN command to 12 | \fIDEVICE\fR and outputs the data returned. This command is found in the 13 | SBC\-4 draft standard, revision 21 (sbc4r21.pdf). 14 | .SH OPTIONS 15 | Arguments to long options are mandatory for short options as well. 16 | .TP 17 | \fB\-h\fR, \fB\-\-help\fR 18 | output the usage message then exit. 19 | .TP 20 | \fB\-H\fR, \fB\-\-hex\fR 21 | output the response in hexadecimal to stdout. When used once the whole 22 | response is output in ASCII hexadecimal, prefixed by an address (starting at 23 | 0) on each line. When used twice the whole response is output in hexadecimal 24 | with no leading address (on each line). The default action is the same as 25 | giving the \fI\-\-hex\fR option once. 26 | .TP 27 | \fB\-m\fR, \fB\-\-maxlen\fR=\fILEN\fR 28 | where \fILEN\fR is the (maximum) response length in bytes. It is placed in 29 | the cdb's "allocation length" field. If not given (or \fILEN\fR is zero) 30 | then 8192 is used. The maximum allowed value of \fILEN\fR is 1048576. 31 | .TP 32 | \fB\-r\fR, \fB\-\-raw\fR 33 | output the SCSI response (i.e. the data\-out buffer) in binary (to stdout). 34 | .TP 35 | \fB\-R\fR, \fB\-\-readonly\fR 36 | open the \fIDEVICE\fR read\-only (e.g. in Unix with the O_RDONLY flag). 37 | The default is to open it read\-write. 38 | .TP 39 | \fB\-v\fR, \fB\-\-verbose\fR 40 | increase the level of verbosity, (i.e. debug output). 41 | .TP 42 | \fB\-V\fR, \fB\-\-version\fR 43 | print the version string and then exit. 44 | .SH EXIT STATUS 45 | The exit status of sg_rep_pip is 0 when it is successful. Otherwise see 46 | the sg3_utils(8) man page. 47 | .SH AUTHORS 48 | Written by Douglas Gilbert. 49 | .SH "REPORTING BUGS" 50 | Report bugs to . 51 | .SH COPYRIGHT 52 | Copyright \(co 2020\-2022 Douglas Gilbert 53 | .br 54 | This software is distributed under a BSD\-2\-Clause license. There is NO 55 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 56 | .SH "SEE ALSO" 57 | .B sg3_utils(sg3_utils) 58 | -------------------------------------------------------------------------------- /doc/sg_rtpg.8: -------------------------------------------------------------------------------- 1 | .TH SG_RTPG "8" "May 2014" "sg3_utils\-1.39" SG3_UTILS 2 | .SH NAME 3 | sg_rtpg \- send SCSI REPORT TARGET PORT GROUPS command 4 | .SH SYNOPSIS 5 | .B sg_rtpg 6 | [\fI\-\-decode\fR] [\fI\-\-help\fR] [\fI\-\-hex\fR] [\fI\-\-raw\fR] 7 | [\fI\-\-readonly\fR] [\fI\-\-verbose\fR] [\fI\-\-version\fR] \fIDEVICE\fR 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | Send a SCSI REPORT TARGET PORT GROUPS command to \fIDEVICE\fR and 11 | outputs the response. 12 | .PP 13 | Target port group access is described in SPC\-3 and SPC\-4 found at 14 | www.t10.org . The most recent draft of SPC\-4 is revision 37 in which 15 | target port groups are described in section 5.15 . 16 | .SH OPTIONS 17 | Arguments to long options are mandatory for short options as well. 18 | .TP 19 | \fB\-d\fR, \fB\-\-decode\fR 20 | decodes the status code and asymmetric access state from each 21 | target port group descriptor returned. The default action is not 22 | to decode these values. 23 | .TP 24 | \fB\-e\fR, \fB\-\-extended\fR 25 | use extended header format for parameter data. This sets the PARAMETER DATA 26 | FORMAT field in the cdb to 1. 27 | .TP 28 | \fB\-h\fR, \fB\-\-help\fR 29 | output the usage message then exit. 30 | .TP 31 | \fB\-H\fR, \fB\-\-hex\fR 32 | output response in hex (rather than partially or fully decode it). 33 | .TP 34 | \fB\-r\fR, \fB\-\-raw\fR 35 | output response in binary to stdout. 36 | .TP 37 | \fB\-R\fR, \fB\-\-readonly\fR 38 | open the \fIDEVICE\fR read\-only (e.g. in Unix with the O_RDONLY flag). 39 | The default is to open it read\-write. 40 | .TP 41 | \fB\-v\fR, \fB\-\-verbose\fR 42 | increase the level of verbosity, (i.e. debug output). 43 | .TP 44 | \fB\-V\fR, \fB\-\-version\fR 45 | print the version string and then exit. 46 | .SH NOTES 47 | The Report Target Port Groups command should be supported whenever the TPGS 48 | bits in a standard INQUIRY response are greater than zero. [View with 49 | sg_inq utility.] 50 | .SH EXIT STATUS 51 | The exit status of sg_rtpg is 0 when it is successful. Otherwise see 52 | the sg3_utils(8) man page. 53 | .SH AUTHORS 54 | Written by Douglas Gilbert. 55 | .SH "REPORTING BUGS" 56 | Report bugs to . 57 | .SH COPYRIGHT 58 | Copyright \(co 2004\-2014 Christophe Varoqui and Douglas Gilbert 59 | .br 60 | This software is distributed under a BSD\-2\-Clause license. There is NO 61 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 62 | .SH "SEE ALSO" 63 | .B sg_inq(sg3_utils) 64 | -------------------------------------------------------------------------------- /inhex/nvme_read_oob_ctl.hex: -------------------------------------------------------------------------------- 1 | # 64 byte NVMe, Read command (a NVM command) which what should be an 2 | # Out-of-Bounds LBA (around 377 TB with 512 byte sectors. This file is 3 | # suitable for: 4 | # sg_raw --cmdfile= --nvm --request=2048 5 | # 6 | # The address field (at byte offset 24, 8 bytes and little endian) gives 7 | # special meaning to the highest address pointers: 8 | # ffffffff fffffffe use address of data-in buffer 9 | # ffffffff fffffffd use address of data-out buffer 10 | # 11 | # The data length field (at byte offset 36, 4 bytes and little endian) 12 | # gives special meaning to the highest block counts: 13 | # fffffffe use byte length of data-in buffer 14 | # fffffffd use byte length of data-out buffer 15 | # 16 | # vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv 17 | # This NVMe (NVM) Read command purposely has a very large starting LBA 18 | # in order to get a "Attempted write to read only range" error. This is 19 | # to test error reporting. 20 | # ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 21 | # 22 | # 512 byte logical block size is assumed. Read 4 blocks hence 2048 bytes. 23 | # The first LBA read is 0xabcd012345 and the namespace is 1. If successful 24 | # the four blocks will be read into the data-in buffer. Submission queue 25 | # 0 is used (the same queue that Admin commands use). The NVM opcode for 26 | # the Read command is 0x2 and appears in the first command byte. 27 | 28 | 02 00 00 00 01 00 00 00 00 00 00 00 00 00 00 00 29 | 00 00 00 00 00 00 00 00 fe ff ff ff ff ff ff ff 30 | 00 00 00 00 fe ff ff ff 45 23 01 cd ab 00 00 00 31 | 03 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 32 | 33 | # Notice NVMe uses its quirky "0's based" number of blocks so 34 | # 03 appears at byte offset 48 to mean "read 4 blocks". 35 | # 36 | # A typical invocation in Linux and FreeBSD would look like this: 37 | # sg_raw --cmdfile=nvme_read_oob_ctl.hex --nvm -r 2048 38 | # --outfile=t.bin /dev/nvme0n1 39 | # In FreeBSD the device name would be /dev/nvme0ns1 40 | # 41 | # Notice the '--nvm' option which is needed to distinguish a NVM 42 | # command from an Admin command as Admin commands are the default 43 | # in this utility. 44 | # 45 | # This utility (and most others in the package) aligns data-in and 46 | # data-out buffers to the beginning of pages which are 4096 bytes 47 | # long at a minimum. This is the way NVMe likes things as well. 48 | -------------------------------------------------------------------------------- /scripts/README: -------------------------------------------------------------------------------- 1 | README for sg3_utils/scripts 2 | ============================ 3 | Introduction 4 | ============ 5 | This directory contains bash shell scripts. Most of them call one or 6 | more utilities from the sg3_utils package. They assume the sg3_utils 7 | package utilities are on the PATH of the user. 8 | 9 | rescan-scsi-bus.sh is written by Kurt Garloff (formerly from Suse Labs) 10 | with patches from Hannes Reinecke (Suse) and Redhat. 11 | 12 | scsi_logging_level is written by Andreas Herrmann . It sets the logging level of the SCSI subsystem in the Linux 14 | 2.6 series kernels. See that file for more information. 15 | 16 | The other scripts are written by the author. Some do testing while others 17 | do bulk tasks (e.g. stopping multiple disks). 18 | 19 | Details 20 | ======= 21 | Each script supplies more information, typically by supplying a '-h' 22 | or '--help' option. The script source often contains explanatory 23 | information. Following is a usage summary with a one line description: 24 | rescan-scsi-bus.sh [OPTIONS] 25 | - see the output of 'rescan-scsi-bus.sh --help' 26 | scsi_logging_level [OPTIONS] 27 | - set Linux SCSI subsystem logging level 28 | scsi_mandat [-h] [-L] [-q] 29 | - check for mandatory SCSI command support 30 | scsi_readcap [-b] [-h] [-v] + 31 | - fetch capacity/size information for each 32 | scsi_ready [-h] [-v] + 33 | - check the media ready status on each 34 | scsi_satl [-h] [-L] [-q] [-v] 35 | - check for SCSI to ATA Translation Layer (SATL) 36 | scsi_start [-h] [-v] [-w] + 37 | - start media (i.e. spin up) in each 38 | scsi_stop [-h] [-v] [-w] + 39 | - stop media (i.e. spin down) in each 40 | scsi_temperature [-h] [-v] + 41 | - check temperature in each 42 | 43 | These scripts assume that the main sg3_utils utilities are installed 44 | and are on the user's PATH. 45 | 46 | This directory, prior to sg3_utils-1.28, contained the sas_disk_blink 47 | script. Since it depends on the sdparm utility it has been moved to 48 | the sdparm package in its scripts directory. 49 | 50 | 59-scsi-sg3_utils.rules is a Linux specific file for udev. These rules use 51 | 'sg_inq --export' to help udev create identifying device nodes, for example 52 | /dev/disk/by-id/wwn-0x5001501234567890-part1. 53 | 54 | Douglas Gilbert 55 | 4th October 2021 56 | -------------------------------------------------------------------------------- /inhex/get_elem_status.hex: -------------------------------------------------------------------------------- 1 | # 2 | # The is a real response to the SCSI GET PHYSICAL ELEMENT STATUS command. 3 | # The storage elements are associated with heads on this hard disk and 4 | # one of them (element_id: 10) is "out of spec". The same output was 5 | # obtained with --report-type=1 (report only storage elements) as this 6 | # invocation (where --report-type defaults to 0: report all physical 7 | # elements): 8 | # sg_get_elem_status -HHH 9 | # 10 | # The hard disk had 9 platters and thus had 18 heads as both side of each 11 | # platter are used. 12 | 13 | 00 00 00 12 00 00 00 12 00 00 00 00 00 00 00 00 14 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 15 | 00 00 00 00 00 00 00 01 00 00 00 00 00 00 01 01 16 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 17 | 00 00 00 00 00 00 00 02 00 00 00 00 00 00 01 01 18 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 19 | 00 00 00 00 00 00 00 03 00 00 00 00 00 00 01 01 20 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 21 | 00 00 00 00 00 00 00 04 00 00 00 00 00 00 01 01 22 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 23 | 00 00 00 00 00 00 00 05 00 00 00 00 00 00 01 01 24 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 25 | 00 00 00 00 00 00 00 06 00 00 00 00 00 00 01 01 26 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 27 | 00 00 00 00 00 00 00 07 00 00 00 00 00 00 01 01 28 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 29 | 00 00 00 00 00 00 00 08 00 00 00 00 00 00 01 01 30 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 31 | 00 00 00 00 00 00 00 09 00 00 00 00 00 00 01 01 32 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 33 | 00 00 00 00 00 00 00 0a 00 00 00 00 00 00 01 65 34 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 35 | 00 00 00 00 00 00 00 0b 00 00 00 00 00 00 01 01 36 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 37 | 00 00 00 00 00 00 00 0c 00 00 00 00 00 00 01 01 38 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 39 | 00 00 00 00 00 00 00 0d 00 00 00 00 00 00 01 01 40 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 41 | 00 00 00 00 00 00 00 0e 00 00 00 00 00 00 01 01 42 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 43 | 00 00 00 00 00 00 00 0f 00 00 00 00 00 00 01 01 44 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 45 | 00 00 00 00 00 00 00 10 00 00 00 00 00 00 01 01 46 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 47 | 00 00 00 00 00 00 00 11 00 00 00 00 00 00 01 01 48 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 49 | 00 00 00 00 00 00 00 12 00 00 00 00 00 00 01 01 50 | ff ff ff ff ff ff ff ff 00 00 00 00 00 00 00 00 51 | 52 | -------------------------------------------------------------------------------- /scripts/54-before-scsi-sg3_id.rules: -------------------------------------------------------------------------------- 1 | # do not edit this file, it will be overwritten on update 2 | 3 | # persistent storage links: /dev/disk/{by-id,by-path} 4 | # scheme based on "Linux persistent device names", 2004, Hannes Reinecke 5 | 6 | # This file contains rules for setting udev environment variables based on 7 | # hardware properties (serial numbers etc), which can be obtained without 8 | # actually reading from the device. 9 | # 10 | # Hopefully this will be integrated into systemd/udev soon (as 54-storage-hardware.rules). 11 | # Until then, we ship it here in sg3-utils. 12 | # It's important that rules dealing with low-level hardware attributes run 13 | # before the generic SCSI rules in 55-scsi-sg3_utils.rules. 14 | 15 | ACTION=="remove", GOTO="storage_hardware_end" 16 | SUBSYSTEM!="block", GOTO="block_storage_end" 17 | KERNEL!="sd*|sr*|cciss*", GOTO="block_storage_end" 18 | 19 | # ignore partitions that span the entire disk 20 | TEST=="whole_disk", GOTO="block_storage_end" 21 | 22 | # for partitions import parent information 23 | ENV{DEVTYPE}=="partition", ENV{ID_SERIAL}!="?*", IMPORT{parent}="ID_*" 24 | 25 | # ATA 26 | KERNEL=="sd*[!0-9]|sr*", ENV{ID_SERIAL}!="?*", SUBSYSTEMS=="scsi", ATTRS{vendor}=="ATA", IMPORT{program}="ata_id --export $devnode" 27 | 28 | # ATAPI devices (SPC-3 or later) 29 | KERNEL=="sd*[!0-9]|sr*", ENV{ID_SERIAL}!="?*", SUBSYSTEMS=="scsi", ATTRS{type}=="5", ATTRS{scsi_level}=="[6-9]*", IMPORT{program}="ata_id --export $devnode" 30 | 31 | # Run ata_id on non-removable USB Mass Storage (SATA/PATA disks in enclosures) 32 | KERNEL=="sd*[!0-9]|sr*", ENV{ID_SERIAL}!="?*", ATTR{removable}=="0", SUBSYSTEMS=="usb", IMPORT{program}="ata_id --export $devnode" 33 | 34 | # Fall back usb_id for USB devices 35 | KERNEL=="sd*[!0-9]|sr*", ENV{ID_SERIAL}!="?*", SUBSYSTEMS=="usb", IMPORT{builtin}="usb_id" 36 | 37 | # FireWire 38 | ENV{ID_IEEE1394}!="?*", KERNEL=="sd*|sr*", ATTRS{ieee1394_id}=="?*", ENV{ID_IEEE1394}="$attr{ieee1394_id}" 39 | 40 | # by-path 41 | ENV{ID_PATH}!="?*", ENV{DEVTYPE}=="disk", DEVPATH!="*/virtual/*", IMPORT{builtin}="path_id" 42 | 43 | LABEL="block_storage_end" 44 | 45 | # SCSI tape devices 46 | SUBSYSTEM!="scsi_tape", GOTO="storage_hardware_end" 47 | KERNEL!="st*[0-9]|nst*[0-9]", GOTO="storage_hardware_end" 48 | 49 | ENV{ID_SERIAL}!="?*", ATTRS{ieee1394_id}=="?*", ENV{ID_SERIAL}="$attr{ieee1394_id}", ENV{ID_BUS}="ieee1394" 50 | ENV{ID_SERIAL}!="?*", SUBSYSTEMS=="usb", ATTRS{serial}=="?*", IMPORT{builtin}="usb_id" 51 | 52 | # by-path 53 | ENV{ID_PATH}!="?*", IMPORT{builtin}="path_id" 54 | 55 | LABEL="storage_hardware_end" 56 | -------------------------------------------------------------------------------- /doc/sg_rmsn.8: -------------------------------------------------------------------------------- 1 | .TH SG_RMSN "8" "November 2012" "sg3_utils\-1.31" SG3_UTILS 2 | .SH NAME 3 | sg_rmsn \- send SCSI READ MEDIA SERIAL NUMBER command 4 | .SH SYNOPSIS 5 | .B sg_rmsn 6 | [\fI\-\-help\fR] [\fI\-\-raw\fR] [\fI\-\-readonly\fR] [\fI\-\-verbose\fR] 7 | [\fI\-\-version\fR] 8 | \fIDEVICE\fR 9 | .SH DESCRIPTION 10 | .\" Add any additional description here 11 | Send a SCSI READ MEDIA SERIAL NUMBER command to \fIDEVICE\fR and outputs 12 | the response. 13 | .PP 14 | This command is described in SPC\-3 found at www.t10.org . It was originally 15 | added to SPC\-3 in revision 11 (2003/2/12). It is not an mandatory command 16 | and the author has not seen any SCSI devices that support it. 17 | .SH OPTIONS 18 | Arguments to long options are mandatory for short options as well. 19 | .TP 20 | \fB\-h\fR, \fB\-\-help\fR 21 | output the usage message then exit. 22 | .TP 23 | \fB\-r\fR, \fB\-\-raw\fR 24 | sends the serial number (if found) to stdout. This output may contain 25 | non\-printable characters (e.g. the serial number is padded with NULLs 26 | at the end so its length is a multiple of 4). The default action is 27 | to print the serial number out in ASCII\-HEX with ASCII characters to 28 | the right. All error messages are sent to stderr. 29 | .TP 30 | \fB\-R\fR, \fB\-\-readonly\fR 31 | opens the DEVICE read\-only rather than read\-write which is the 32 | default. The Linux sg driver needs read\-write access for the SCSI 33 | READ MEDIA SERIAL NUMBER command but other access methods may require 34 | read\-only access. 35 | .TP 36 | \fB\-v\fR, \fB\-\-verbose\fR 37 | increase the level of verbosity, (i.e. debug output). 38 | .TP 39 | \fB\-V\fR, \fB\-\-version\fR 40 | print the version string and then exit. 41 | .SH NOTES 42 | Device identification information is also found in a standard INQUIRY 43 | response and its VPD pages (see sg_vpd). The relevant VPD pages are 44 | the "device identification page" (VPD page 0x83) and the "unit serial 45 | number" page (VPD page 0x80). 46 | .PP 47 | The MMC\-4 command set for CD/DVD/HD-DVD/BD drives has a "media serial number" 48 | feature (0x109) [and a "logical unit serial number" feature]. These 49 | can be viewed with sg_get_config. 50 | .SH EXIT STATUS 51 | The exit status of sg_rmsn is 0 when it is successful. Otherwise see 52 | the sg3_utils(8) man page. 53 | .SH AUTHORS 54 | Written by Douglas Gilbert. 55 | .SH "REPORTING BUGS" 56 | Report bugs to . 57 | .SH COPYRIGHT 58 | Copyright \(co 2005\-2012 Douglas Gilbert 59 | .br 60 | This software is distributed under a BSD\-2\-Clause license. There is NO 61 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 62 | .SH "SEE ALSO" 63 | .B sg_vpd(sg3_utils), sg_get_config(sg3_utils) 64 | -------------------------------------------------------------------------------- /examples/sg_compare_and_write.txt: -------------------------------------------------------------------------------- 1 | # sg_compare_and_write.txt 2 | # This file provides a usage example of sg_compare_and_write. 3 | # sg_compare_and_write accepts a buffer containing 2 logical instances: 4 | # - the verify instance: used to match the current content of the LBA range 5 | # - the write instance: used to write to the LBA if the verify succeeds 6 | # 7 | # In case of failure to verify the data, the command will return with check 8 | # condition with the sense code set to MISCOMPARE DURING VERIFY OPERATION. 9 | # 10 | # The following example shows initialization, successful and unsuccessful 11 | # compare and write using sg3_utils. I am using caw_buf_zero2one and 12 | # caw_buf_one2zero as shown below. 13 | 14 | $ hexdump /tmp/caw_buf_zero2one 15 | 0000000 0000 0000 0000 0000 0000 0000 0000 0000 16 | * 17 | 0000200 1111 1111 1111 1111 1111 1111 1111 1111 18 | * 19 | 0000400 20 | 21 | $ hexdump /tmp/caw_buf_one2zero 22 | 0000000 1111 1111 1111 1111 1111 1111 1111 1111 23 | * 24 | 0000200 0000 0000 0000 0000 0000 0000 0000 0000 25 | * 26 | 0000400 27 | 28 | $ sg_map -i -x 29 | /dev/sg0 0 0 0 0 0 /dev/sda ATA ST3320613AS CC2H 30 | /dev/sg1 3 0 0 0 5 /dev/scd0 HL-DT-ST DVD-RAM GH22NS30 1.01 31 | /dev/sg2 5 0 0 0 0 /dev/sdb KMNRIO K2 0000 32 | /dev/sg3 5 0 0 1 0 /dev/sdc KMNRIO K2 0000 33 | 34 | # First I zero out the volume to make sure that the first compare and write 35 | # will succeed 36 | $ sg_write_same --16 -i /dev/zero -n 0x200000 -x 512 /dev/sdc 37 | 38 | $ dd if=/dev/sdc bs=512 count=1 skip=100 2>/dev/null | hexdump 39 | 0000000 0000 0000 0000 0000 0000 0000 0000 0000 40 | * 41 | 0000200 42 | 43 | $ ./sg_compare_and_write --in=/tmp/caw_buf_zero2one --lba=100 --xferlen=1024 /dev/sdc 44 | 45 | # contents of LBA 100 are a block of ones 46 | $ dd if=/dev/sdc bs=512 count=1 skip=100 2>/dev/null | hexdump 47 | 0000000 1111 1111 1111 1111 1111 1111 1111 1111 48 | * 49 | 0000200 50 | 51 | # We repeat the same compare and write command (zero2one input buffer). 52 | # compare and write fails since the verify failed (compared the zero block to 53 | # the actual 1 block in LBA 100 54 | $ ./sg_compare_and_write --in=/tmp/caw_buf_zero2one --lba=100 --xferlen=1024 /dev/sdc 55 | COMPARE AND WRITE: Fixed format, current; Sense key: Miscompare 56 | Additional sense: Miscompare during verify operation 57 | sg_compare_and_write: SCSI COMPARE AND WRITE failed 58 | 59 | # Now we use the second buffer (one2zero) 60 | $ ./sg_compare_and_write --in=/tmp/caw_buf_one2zero --lba=100 --xferlen=1024 /dev/sdc 61 | 62 | # operation succeeded, contents of LBA 100 are back to zero 63 | $ dd if=/dev/sdc bs=512 count=1 skip=100 2>/dev/null | hexdump 64 | 0000000 0000 0000 0000 0000 0000 0000 0000 0000 65 | * 66 | 0000200 67 | 68 | -------------------------------------------------------------------------------- /.github/workflows/ci.yml: -------------------------------------------------------------------------------- 1 | # See also https://docs.github.com/en/actions/learn-github-actions/expressions 2 | # See also https://github.com/marketplace/actions/setup-android-ndk 3 | 4 | name: CI 5 | 6 | on: [push, pull_request] 7 | 8 | jobs: 9 | build: 10 | runs-on: ubuntu-latest 11 | strategy: 12 | fail-fast: false 13 | matrix: 14 | build: 15 | - android-23 16 | - android-33 17 | - linux-gcc 18 | - linux-clang 19 | - linux-x86-gcc 20 | - linux-powerpc64-gcc 21 | - linux-mingw64-gcc 22 | - macos 23 | include: 24 | - build: android-23 25 | cc: clang 26 | host: aarch64-linux-android23 27 | - build: android-33 28 | cc: clang 29 | host: aarch64-linux-android33 30 | - build: linux-gcc 31 | cc: gcc 32 | - build: linux-clang 33 | cc: clang 34 | - build: linux-x86-gcc 35 | cc: gcc 36 | arch: x86 37 | - build: linux-powerpc64-gcc 38 | cc: gcc 39 | host: powerpc64-linux-gnu 40 | - build: linux-mingw64-gcc 41 | cc: gcc 42 | host: x86_64-w64-mingw32 43 | - build: macos 44 | cc: clang 45 | os: macos-latest 46 | steps: 47 | - uses: actions/checkout@v3 48 | - name: Install Android NDK 49 | run: | 50 | case ${{matrix.build}} \ 51 | in android*) \ 52 | wget --quiet https://dl.google.com/android/repository/android-ndk-r25c-linux.zip; \ 53 | unzip -q android-ndk-r25c-linux.zip;; \ 54 | esac 55 | - name: Install Ubuntu packages 56 | run: | 57 | sudo apt-get -q update 58 | case "${{matrix.host}}" in \ 59 | x86_64-w64-mingw32) \ 60 | sudo apt-get -q install -y binutils-mingw-w64 gcc-mingw-w64;; \ 61 | powerpc64-linux-gnu) \ 62 | sudo apt-get -q install -y binutils-powerpc64-linux-gnu \ 63 | gcc-powerpc64-linux-gnu;; \ 64 | esac 65 | - name: Build 66 | run: | 67 | echo "HOST=${{matrix.host}}" 68 | NDK=$PWD/android-ndk-r25c/toolchains/llvm/prebuilt/linux-x86_64/bin 69 | export PATH="$NDK:$PATH" 70 | ./autogen.sh 71 | ./configure --host=${{matrix.host}} \ 72 | CC=${{ matrix.host && format('{0}-{1}', matrix.host, matrix.cc) || matrix.cc }} \ 73 | CFLAGS="-Wall -Wextra -Werror -Wno-sign-compare -Wno-unused-function -Wno-unused-parameter ${{matrix.cflags}}" 74 | make -j$(nproc) 75 | -------------------------------------------------------------------------------- /doc/sg_prevent.8: -------------------------------------------------------------------------------- 1 | .TH SG_PREVENT "8" "November 2012" "sg3_utils\-1.35" SG3_UTILS 2 | .SH NAME 3 | sg_prevent \- send SCSI PREVENT ALLOW MEDIUM REMOVAL command 4 | .SH SYNOPSIS 5 | .B sg_prevent 6 | [\fI\-\-allow\fR] [\fI\-\-help\fR] [\fI\-\-prevent=PC\fR] 7 | [\fI\-\-verbose\fR] [\fI\-\-version\fR] \fIDEVICE\fR 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | Sends a SCSI PREVENT ALLOW MEDIUM REMOVAL command to \fIDEVICE\fR. 11 | The default action of this utility is to prevent the removing or 12 | ejecting of the medium from a drive. This is done by ignoring the 13 | SCSI START STOP UNIT command (see sg_start) and ignoring the eject 14 | button on the drive when the user presses it. Drives that hold removable 15 | disks, tape cartridges or cd/dvd media typically implement this command. 16 | The definition of the "prevent" codes for this command differ between 17 | disks and tapes (covered by SBC\-3 and SSC\-3) and cd/dvd drives (covered 18 | by MMC\-5). The "prevent codes" described here are from MMC\-5. 19 | .SH OPTIONS 20 | Arguments to long options are mandatory for short options as well. 21 | .TP 22 | \fB\-a\fR, \fB\-\-allow\fR 23 | allow medium removal. This is equivalent to setting to '\-\-prevent=2'. 24 | Cannot be used with \fI\-\-prevent=PC\fR option (i.e. either use 25 | no options (hence prevent removal), this option or \fI\-\-prevent=PC\fR). 26 | .TP 27 | \fB\-h\fR, \fB\-\-help\fR 28 | output the usage message then exit. 29 | .TP 30 | \fB\-p\fR, \fB\-\-prevent\fR=\fIPC\fR 31 | where \fIPC\fR is a prevent code value. Defined values are: 0 allows removal, 32 | 1 prevents removal (default), 2 allows persistent removal while 3 prevents 33 | persistent removal. "Persistent" in this context means that the 34 | initiator (port) that successfully uses code 3 blocks other initiators (ports) 35 | from allowing removal. A "persistent prevent" state can be cleared by the 36 | owner allowing persistent removal (code 2) or a power cycle (or anything that 37 | resets the device (LU)) or some special commands (e.g. various service 38 | actions of Persistent Reserve Out, see SPC\-3). 39 | .TP 40 | \fB\-v\fR, \fB\-\-verbose\fR 41 | increase the level of verbosity, (i.e. debug output). 42 | .TP 43 | \fB\-V\fR, \fB\-\-version\fR 44 | print the version string and then exit. 45 | .SH EXIT STATUS 46 | The exit status of sg_prevent is 0 when it is successful. Otherwise see 47 | the sg3_utils(8) man page. 48 | .SH AUTHORS 49 | Written by Douglas Gilbert. 50 | .SH "REPORTING BUGS" 51 | Report bugs to . 52 | .SH COPYRIGHT 53 | Copyright \(co 2004\-2012 Douglas Gilbert 54 | .br 55 | This software is distributed under a BSD\-2\-Clause license. There is NO 56 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 57 | .SH "SEE ALSO" 58 | .B sg_start(sg3_utils), sg_persist(sg3_utils) 59 | -------------------------------------------------------------------------------- /doc/sg_reset_wp.8: -------------------------------------------------------------------------------- 1 | .TH SG_RESET_WP "8" "February 2022" "sg3_utils\-1.48" SG3_UTILS 2 | .SH NAME 3 | sg_reset_wp \- send SCSI RESET WRITE POINTER command 4 | .SH SYNOPSIS 5 | .B sg_reset_wp 6 | [\fI\-\-all\fR] [\fI\-\-count=ZC\fR] [\fI\-\-help\fR] [\fI\-\-verbose\fR] 7 | [\fI\-\-version\fR] [\fI\-\-zone=ID\fR] \fIDEVICE\fR 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | Sends a SCSI RESET WRITE POINTER command to the \fIDEVICE\fR. This command 11 | is described in ZBC standard (INCITS 536\-2016) and the draft ZBC\-2 12 | documents at T10 (e.g. zbc2r12.pdf). 13 | .SH OPTIONS 14 | Arguments to long options are mandatory for short options as well. 15 | .TP 16 | \fB\-a\fR, \fB\-\-all\fR 17 | sets the ALL field in the cdb. This causes a reset write pointer operation of 18 | all open zones and full zones. When this option is given then the 19 | \fI\-\-zone=ID\fR option is ignored. Either this option or the 20 | \fI\-\-zone=ID\fR option is required. 21 | .TP 22 | \fB\-C\fR, \fB\-\-count\fR=\fIZC\fR 23 | ZC is placed in the Zone Count field in the cdb of the RESET WRITE POINTER 24 | command supported by this utility. ZC should be a value from 0 to 25 | 65535 (0xffff) inclusive. 26 | .br 27 | The action that the \fIDEVICE\fR takes with this option depends on whether 28 | the \fI\-\-all\fR option is set. See the RESET WRITE POINTER command 29 | description (e.g. section 5.9, table 46 in zbc2r12.pdf). 30 | .TP 31 | \fB\-h\fR, \fB\-\-help\fR 32 | output the usage message then exit. 33 | .TP 34 | \fB\-v\fR, \fB\-\-verbose\fR 35 | increase the level of verbosity, (i.e. debug output). 36 | .TP 37 | \fB\-V\fR, \fB\-\-version\fR 38 | print the version string and then exit. 39 | .TP 40 | \fB\-z\fR, \fB\-\-zone\fR=\fIID\fR 41 | where \fIID\fR is placed in the cdb's ZONE ID field. A zone id is a zone 42 | start logical block address (LBA). This causes a reset write pointer 43 | operation on the zone identified by the ZONE ID field. The default value is 44 | 0. Either this option or the \fI\-\-all\fR option is required. 45 | \fIID\fR is assumed to be in decimal unless prefixed with '0x' or has a 46 | trailing 'h' which indicate hexadecimal. 47 | .SH NOTES 48 | The Zones Emptied log parameter in the Zoned Block Device Statistics log 49 | page counts the number of times the RESET WRITE POINTER command has 50 | been (successfully) invoked. 51 | .SH EXIT STATUS 52 | The exit status of sg_reset_wp is 0 when it is successful. Otherwise see 53 | the sg3_utils(8) man page. 54 | .SH AUTHORS 55 | Written by Douglas Gilbert. 56 | .SH "REPORTING BUGS" 57 | Report bugs to . 58 | .SH COPYRIGHT 59 | Copyright \(co 2014\-2022 Douglas Gilbert 60 | .br 61 | This software is distributed under a BSD\-2\-Clause license. There is NO 62 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 63 | .SH "SEE ALSO" 64 | .B sg_rep_zones,sg_zone(sg3_utils) 65 | -------------------------------------------------------------------------------- /doc/sg_referrals.8: -------------------------------------------------------------------------------- 1 | .TH SG_REFERRALS "8" "May 2014" "sg3_utils\-1.39" SG3_UTILS 2 | .SH NAME 3 | sg_referrals \- send SCSI REPORT REFERRALS command 4 | .SH SYNOPSIS 5 | .B sg_referrals 6 | [\fI\-\-help\fR] [\fI\-\-hex\fR] [\fI\-\-lba=LBA\fR] [\fI\-\-maxlen=LEN\fR] 7 | [\fI\-\-one-segment\fR] [\fI\-\-raw\fR] [\fI\-\-readonly\fR] 8 | [\fI\-\-verbose\fR] [\fI\-\-version\fR] \fIDEVICE\fR 9 | .SH DESCRIPTION 10 | .\" Add any additional description here 11 | Send the SCSI REPORT REFERRALS command to the \fIDEVICE\fR and outputs the 12 | response. This command was introduced in (draft) SBC\-3 revision 24 and 13 | devices that support referrals should support this command. 14 | .PP 15 | The default action is to decode the response for all user data segment 16 | referral descriptors. The amount of output can be reduced by the 17 | \fI\-\-lba\fR and \fI\-\-one-segment\fR options. 18 | .SH OPTIONS 19 | Arguments to long options are mandatory for short options as well. 20 | .TP 21 | \fB\-h\fR, \fB\-\-help\fR 22 | output the usage message then exit. 23 | .TP 24 | \fB\-H\fR, \fB\-\-hex\fR 25 | output response to this command in ASCII hex. 26 | .TP 27 | \fB\-l\fR, \fB\-\-lba\fR=\fILBA\fR 28 | where \fILBA\fR is the Logical Block Address (LBA) in the first user 29 | data segment the \fIDEVICE\fR should report the referrals parameter 30 | data for. 31 | .TP 32 | \fB\-m\fR, \fB\-\-maxlen\fR=\fILEN\fR 33 | where \fILEN\fR is the (maximum) response length in bytes. It is placed in 34 | the cdb's "allocation length" field. If not given then 256 is used. 256 is 35 | enough space for the response header and user data segment descriptors. 36 | .TP 37 | \fB\-s\fR, \fB\-\-one-segment\fR 38 | report the user data segment of the segment specified by the \fILBA\fR 39 | parameter only. 40 | .TP 41 | \fB\-r\fR, \fB\-\-raw\fR 42 | output response in binary (to stdout). 43 | .TP 44 | \fB\-R\fR, \fB\-\-readonly\fR 45 | open the \fIDEVICE\fR read\-only (e.g. in Unix with the O_RDONLY flag). 46 | The default is to open it read\-write. 47 | .TP 48 | \fB\-v\fR, \fB\-\-verbose\fR 49 | increase the level of verbosity, (i.e. debug output). Additional output 50 | caused by this option is sent to stderr. 51 | .TP 52 | \fB\-V\fR, \fB\-\-version\fR 53 | print the version string and then exit. 54 | .SH NOTES 55 | For a discussion of referrals see section 4.25 of sbc3r25.pdf 56 | at https://www.t10.org (or the corresponding section of a later draft). 57 | .SH EXIT STATUS 58 | The exit status of sg_referrals is 0 when it is successful. Otherwise 59 | see the sg3_utils(8) man page. 60 | .SH AUTHORS 61 | Written by Douglas Gilbert and Hannes Reinecke. 62 | .SH "REPORTING BUGS" 63 | Report bugs to . 64 | .SH COPYRIGHT 65 | Copyright \(co 2009\-2014 Douglas Gilbert and Hannes Reinecke 66 | .br 67 | This software is distributed under a BSD\-2\-Clause license. There is NO 68 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 69 | .SH "SEE ALSO" 70 | .B sg_vpd(8) 71 | -------------------------------------------------------------------------------- /testing/Makefile.freebsd: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/man 6 | 7 | # In Linux the default C compiler is GCC while in FreeBSD (since release 10 ?) 8 | # the default C compiler is clang. Swap the comment marks (lines starting 9 | # with '#') on the next 4 (non-blank) lines. 10 | # CC = gcc 11 | # CC = clang 12 | 13 | # LD = gcc 14 | # LD = clang 15 | 16 | EXECS = sg_sense_test sg_chk_asc sg_tst_nvme tst_sg_lib 17 | 18 | EXTRAS = 19 | 20 | MAN_PGS = 21 | MAN_PREF = man8 22 | 23 | OS_FLAGS = -DSG_LIB_FREEBSD -DHAVE_NVME 24 | EXTRA_FLAGS = $(OS_FLAGS) 25 | 26 | # For C++/clang testing 27 | ## CC = gcc 28 | ## CC = g++ 29 | ## CC = clang 30 | ## CC = clang++ 31 | 32 | # CFLAGS = -O2 -Wall -W $(EXTRA_FLAGS) -I ../include 33 | CFLAGS = -g -O2 -Wall -W $(EXTRA_FLAGS) -I ../include 34 | # CFLAGS = -g -O2 -Wall -W -pedantic -std=c99 $(EXTRA_FLAGS) -I ../include 35 | 36 | CFLAGS_PTHREADS = -D_REENTRANT 37 | 38 | # there is no rule to make the following in the parent directory, 39 | # it is assumed they are already built. 40 | D_FILES = ../lib/sg_lib.o ../lib/sg_lib_data.o ../lib/sg_pr2serr.o \ 41 | ../lib/sg_json_builder.o ../lib/sg_json.o ../lib/sg_json_sg_lib.o \ 42 | ../lib/sg_cmds_basic.o ../lib/sg_pt_common.o ../lib/sg_pt_freebsd.o 43 | 44 | LDFLAGS = -lcam 45 | 46 | all: $(EXECS) 47 | 48 | extras: $(EXTRAS) 49 | 50 | 51 | depend dep: 52 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 53 | done > .depend 54 | 55 | clean: 56 | /bin/rm -f *.o $(EXECS) $(EXTRAS) core .depend 57 | 58 | sg_sense_test: sg_sense_test.o $(D_FILES) 59 | $(CC) -o $@ $(LDFLAGS) $@.o $(D_FILES) 60 | 61 | # building sg_chk_asc depends on a prior successful make in ../lib 62 | sg_chk_asc: sg_chk_asc.o $(D_FILES) 63 | $(CC) -o $@ $(LDFLAGS) $@.o $(D_FILES) 64 | 65 | sg_tst_nvme: sg_tst_nvme.o $(D_FILES) 66 | $(CC) -o $@ $(LDFLAGS) $@.o $(D_FILES) 67 | 68 | tst_sg_lib: tst_sg_lib.o $(D_FILES) 69 | $(CC) -o $@ $(LDFLAGS) $@.o $(D_FILES) 70 | 71 | install: $(EXECS) 72 | install -d $(INSTDIR) 73 | for name in $(EXECS) ; \ 74 | do install -s -o root -g wheel -m 755 $$name $(INSTDIR); \ 75 | done 76 | install -d $(MANDIR)/$(MAN_PREF) 77 | for mp in $(MAN_PGS); \ 78 | do install -o root -g wheel -m 644 $$mp $(MANDIR)/$(MAN_PREF); \ 79 | gzip -9f $(MANDIR)/$(MAN_PREF)/$$mp; \ 80 | done 81 | 82 | uninstall: 83 | dists="$(EXECS)"; \ 84 | for name in $$dists; do \ 85 | rm -f $(INSTDIR)/$$name; \ 86 | done 87 | for mp in $(MAN_PGS); do \ 88 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 89 | done 90 | 91 | # Linux uses GNU make and FreeBSD uses Berkely make. The following lines 92 | # only work in Linux. Possible solutions in FreeBSD: 93 | # a) use 'gmake'; b) comment out the next 3 lines, starting with 'ifeq' 94 | # c) build with 'make -f Makefile.freebsd' 95 | # In Linux one can install bmake (but that won't help here). 96 | # ifeq (.depend,$(wildcard .depend)) 97 | # include .depend 98 | # endif 99 | -------------------------------------------------------------------------------- /include/sg_pr2serr.h: -------------------------------------------------------------------------------- 1 | #ifndef SG_PR2SERR_H 2 | #define SG_PR2SERR_H 3 | 4 | /* 5 | * Copyright (c) 2004-2023 Douglas Gilbert. 6 | * All rights reserved. 7 | * Use of this source code is governed by a BSD-style 8 | * license that can be found in the BSD_LICENSE file. 9 | * 10 | * SPDX-License-Identifier: BSD-2-Clause 11 | */ 12 | 13 | #include 14 | #include 15 | #include 16 | 17 | #ifdef __cplusplus 18 | extern "C" { 19 | #endif 20 | 21 | /* pr2serr and pr2ws are convenience functions that replace the somewhat 22 | * long-winded fprintf(stderr, ....). The second form (i.e. pr2ws() ) is for 23 | * internal library use and may place its output somewhere other than stderr; 24 | * it depends on the external variable sg_warnings_strm which can be set 25 | * with sg_set_warnings_strm(). By default it uses stderr. 26 | * Note that this header and its implementation do not depend on sg_lib.[hc] 27 | * or any other sg3_utils components. */ 28 | 29 | #if __USE_MINGW_ANSI_STDIO -0 == 1 30 | #define __printf(a, b) __attribute__((__format__(gnu_printf, a, b))) 31 | #elif defined(__GNUC__) || defined(__clang__) 32 | #define __printf(a, b) __attribute__((__format__(printf, a, b))) 33 | #else 34 | #define __printf(a, b) 35 | #endif 36 | 37 | int pr2serr(const char * fmt, ...) __printf(1, 2); 38 | 39 | extern FILE * sg_warnings_strm; 40 | 41 | /* Only difference between pr2serr() and pr2ws() is that the former always 42 | * send output to stderr. By default, pr2ws() also sends it output to 43 | * stderr. The sg_set_warnings_strm() function found in sg_lib.h (if used) 44 | * set another FILE * value. The functions in sg_lib.h send their error 45 | * output to pr2ws() . */ 46 | int pr2ws(const char * fmt, ...) __printf(1, 2); 47 | 48 | /* Want safe, 'n += snprintf(b + n, blen - n, ...);' pattern that can 49 | * be called repeatedly. However snprintf() takes an unsigned second argument 50 | * (size_t) that explodes if 'blen - n' goes negative. This function instead 51 | * uses signed integers (second argument and return value) and is safe if the 52 | * second argument is negative. It returns number of chars actually 53 | * placed in cp excluding the trailing null char. So for cp_max_len > 0 the 54 | * return value is always < cp_max_len; for cp_max_len <= 1 the return value 55 | * is 0 and no chars are written to cp. Note this means that when 56 | * cp_max_len = 1, this function assumes that cp[0] is the null character 57 | * and does nothing (and returns 0). Linux kernel has a similar function 58 | * called scnprintf(). */ 59 | int sg_scnpr(char * cp, int cp_max_len, const char * fmt, ...) __printf(3, 4); 60 | 61 | /* This function is similar to sg_scnpr() but takes the "n" in that pattern 62 | * as an extra, third argument where it is renamed 'off'. This function will 63 | * start writing chars at 'fcp + off' for no more than 'fcp_len - off - 1' 64 | * characters. The return value is the same as sg_scnpr(). */ 65 | int sg_scn3pr(char * fcp, int fcp_len, int off, 66 | const char * fmt, ...) __printf(4, 5); 67 | 68 | #ifdef __cplusplus 69 | } 70 | #endif 71 | 72 | #endif 73 | -------------------------------------------------------------------------------- /README.tru64: -------------------------------------------------------------------------------- 1 | Introduction 2 | ============ 3 | The Tru64 port of sg3_utils contains those utilities that are _not_ 4 | specific to Linux. In some cases a utility could be ported but 5 | requires more work. An example is sg_dd which needs more work 6 | beyond the SCSI command pass through mechanism. 7 | 8 | Supported Utilities 9 | =================== 10 | Here is a list of utilities that have been ported: 11 | sg_compare_and_write 12 | sg_decode_sense 13 | sg_format 14 | sg_get_config 15 | sg_get_lba_status 16 | sg_ident 17 | sg_inq [dropped ATA IDENTIFY DEVICE capability] 18 | sg_logs 19 | sg_luns 20 | sg_modes 21 | sg_opcodes 22 | sg_persist 23 | sg_prevent 24 | sg_raw 25 | sg_rdac 26 | sg_read_block_limits 27 | sg_read_buffer 28 | sg_read_long 29 | sg_readcap 30 | sg_reassign 31 | sg_referrals 32 | sg_requests 33 | sg_rmsn 34 | sg_rtpg 35 | sg_safte 36 | sg_sanitize 37 | sg_sat_identify 38 | sg_sat_phy_event 39 | sg_sat_set_features 40 | sg_senddiag 41 | sg_ses 42 | sg_start 43 | sg_stpg 44 | sg_sync 45 | sg_turs 46 | sg_unmap 47 | sg_verify 48 | sg_vpd 49 | sg_wr_mode 50 | sg_write_buffer 51 | sg_write_long 52 | sg_write_same 53 | 54 | Most utility names are indicative of the main SCSI command 55 | that they execute. Some utilities are slightly higher level, for 56 | example sg_ses fetches SCSI Enclosure Services (SES) status pages and 57 | can send control pages. Each utility has a man page (placed in 58 | section 8). An overview of sg3_utils can be found at: 59 | https://sg.danny.cz/sg/sg3_utils.html . 60 | A copy of the "sg3_utils.html" file is in the "doc" subdirectory. 61 | 62 | This package uses autotools infrastructure with the now common 63 | "./configure ; make ; make install" sequence needed to build and install 64 | from the source found in the tarball. If the "./configure" sequence 65 | fails try using the ./autogen.sh prior to that sequence. 66 | 67 | Some man pages have examples which use Linux device names which hopefully 68 | will not confuse Tru64 users. 69 | 70 | 71 | Details 72 | ======= 73 | Most of the ported utilities listed above use SCSI command functions 74 | declared in sg_cmds_*.h headers . Those SCSI command functions are 75 | implemented in the corresponding ".c" files. The ".c" files pass SCSI 76 | commands to the host operating system via an interface declared in sg_pt.h . 77 | There are currently five implementations of that interface depending on 78 | the host operating system: 79 | system: 80 | - sg_pt_linux.c 81 | - sg_pt_osf1.c [Tru64] 82 | - sg_pt_freebsd.c 83 | - sg_pt_solaris.c 84 | - sg_pt_win32.c 85 | 86 | The sg_pt_osf1.c file uses the Tru64 CAM SCSI pass through mechanism. 87 | 88 | Tru64 does not have general library support for "long" options 89 | (e.g. "--verbose") which are used extensively by most of the 90 | utilities in this package. Rather than change all the utilities 91 | and their man/web pages a local implementation of the missing 92 | function "getopt_long()" has been placed in the "getopt_long" 93 | subdirectory. Currently only the Tru64 port uses it. 94 | 95 | 96 | Douglas Gilbert 97 | 14th January 2013 98 | -------------------------------------------------------------------------------- /doc/sg_scan.8.linux: -------------------------------------------------------------------------------- 1 | .TH SG_SCAN "8" "May 2013" "sg3_utils\-1.36" SG3_UTILS 2 | .SH NAME 3 | sg_scan \- scans sg devices (or SCSI/ATAPI/ATA devices) and prints 4 | results 5 | .SH SYNOPSIS 6 | .B sg_scan 7 | [\fI\-a\fR] 8 | [\fI\-i\fR] 9 | [\fI\-n\fR] 10 | [\fI\-w\fR] 11 | [\fI\-x\fR] 12 | [\fIDEVICE\fR]* 13 | .SH DESCRIPTION 14 | .\" Add any additional description here 15 | If no \fIDEVICE\fR names are given, sg_scan does a scan of the sg 16 | devices and outputs a line of information for each sg device that is 17 | currently bound to a SCSI device. If one or more \fIDEVICE\fRs are given 18 | only those devices are scanned. 19 | Each device is opened with the O_NONBLOCK flag so that the scan will 20 | not "hang" on any device that another process holds an O_EXCL lock on. 21 | .PP 22 | Any given \fIDEVICE\fR name is expected to comply 23 | with (to some extent) the Storage Architecture Model (SAM see www.t10.org). 24 | Any device names associated with the Linux SCSI subsystem (e.g. /dev/sda 25 | and /dev/st0m) are suitable. Devices names associated with ATAPI 26 | devices (e.g. most CD/DVD drives and ATAPI tape drives) are also suitable. 27 | If the device does not fall into the above categories then an ATA 28 | IDENTIFY command is tried. 29 | .PP 30 | In Linux 2.6 and 3 series kernels, the lsscsi utility may be helpful. Apart 31 | from providing more information (by data\-mining in the sysfs pseudo file 32 | system), it does not need root permissions to execute, as this utility 33 | would typically need. 34 | .SH OPTIONS 35 | .TP 36 | \fB\-a\fR 37 | do alphabetical scan (i.e. sga, sgb, sgc). Note that sg device nodes with 38 | an alphabetical index have been deprecated since the Linux kernel 2.2 39 | series. 40 | .TP 41 | \fB\-i\fR 42 | do a SCSI INQUIRY, output results in a second (indented) line. If the device 43 | is an ATA disk then output information from an ATA IDENTIFY command 44 | .TP 45 | \fB\-n\fR 46 | do numeric scan (i.e. sg0, sg1...) [default] 47 | .TP 48 | \fB\-w\fR 49 | use a read/write flag when opening sg device (default is read\-only) 50 | .TP 51 | \fB\-x\fR 52 | extra information output about queueing 53 | .SH NOTES 54 | This utility was written at a time when hotplugging of SCSI devices 55 | was not supported in Linux. It used a simple algorithm to scan sg 56 | device nodes in ascending numeric or alphabetical order, stopping 57 | after there were 4 consecutive errors. 58 | .PP 59 | In the Linux kernel 2.6 series, this utility uses sysfs to find which 60 | sg device nodes are active and only checks those. Hence there can be 61 | large "holes" in the numbering of sg device nodes (e.g. after an 62 | adapter has been removed) and still all active sg device nodes will 63 | be listed. This utility assumes that sg device nodes are named using 64 | the normal conventions and searches from /dev/sg0 to /dev/sg4095 65 | inclusive. 66 | .SH EXIT STATUS 67 | The exit status of sg_scan is 0 when it is successful. Otherwise see 68 | the sg3_utils(8) man page. 69 | .SH AUTHORS 70 | Written by D. Gilbert and F. Jansen 71 | .SH COPYRIGHT 72 | Copyright \(co 1999\-2013 Douglas Gilbert 73 | .br 74 | This software is distributed under the GPL version 2. There is NO 75 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 76 | .SH "SEE ALSO" 77 | .B lsscsi(8) 78 | -------------------------------------------------------------------------------- /testing/Makefile.cyg: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/man 6 | 7 | # In Linux the default C compiler is GCC while in FreeBSD (since release 10 ?) 8 | # the default C compiler is clang. Swap the comment marks (lines starting 9 | # with '#') on the next 4 (non-blank) lines. 10 | CC = gcc 11 | # CC = clang 12 | 13 | LD = gcc 14 | # LD = clang 15 | 16 | EXECS = sg_sense_test sg_chk_asc sg_tst_nvme tst_sg_lib 17 | 18 | EXTRAS = 19 | 20 | BSG_EXTRAS = 21 | 22 | 23 | MAN_PGS = 24 | MAN_PREF = man8 25 | 26 | LARGE_FILE_FLAGS = -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 27 | 28 | # For C++/clang testing 29 | ## CC = gcc 30 | ## CC = g++ 31 | ## CC = clang 32 | ## CC = clang++ 33 | 34 | CPPFLAGS = -iquote ../include -iquote .. -D_REENTRANT $(LARGE_FILE_FLAGS) -DHAVE_CONFIG_H -DHAVE_NVME 35 | CFLAGS = -g -O2 -W -Wall 36 | # CFLAGS = -g -O2 -Wall -DSG_KERNEL_INCLUDES 37 | # CFLAGS = -g -O2 -Wall -pedantic 38 | # CFLAGS = -Wall -W -pedantic -std=c11 --analyze 39 | # CFLAGS = -Wall -W -pedantic -std=c++14 -fPIC 40 | 41 | LDFLAGS = 42 | 43 | LIBFILESOLD = ../lib/sg_lib.o ../lib/sg_lib_data.o 44 | LIBFILESNEW = ../lib/sg_lib.o ../lib/sg_lib_data.o \ 45 | ../lib/sg_pt_win32.o ../lib/sg_pt_common.o ../lib/sg_cmds_basic.o 46 | 47 | all: $(EXECS) 48 | 49 | extras: $(EXTRAS) 50 | 51 | bsg: $(BSG_EXTRAS) 52 | 53 | 54 | depend dep: 55 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 56 | done > .depend 57 | 58 | clean: 59 | /bin/rm -f *.o $(EXECS) $(EXTRAS) $(BSG_EXTRAS) core .depend 60 | 61 | sg_iovec_tst: sg_iovec_tst.o $(LIBFILESOLD) 62 | $(LD) -o $@ $(LDFLAGS) $^ 63 | 64 | sg_sense_test: sg_sense_test.o $(LIBFILESOLD) 65 | $(LD) -o $@ $(LDFLAGS) $^ 66 | 67 | sg_queue_tst: sg_queue_tst.o $(LIBFILESOLD) 68 | $(LD) -o $@ $(LDFLAGS) $^ 69 | 70 | bsg_queue_tst: bsg_queue_tst.o $(LIBFILESOLD) 71 | $(LD) -o $@ $(LDFLAGS) $^ 72 | 73 | # building sg_chk_asc depends on a prior successful make in ../lib 74 | sg_chk_asc: sg_chk_asc.o ../lib/sg_lib.o ../lib/sg_lib_data.o 75 | $(LD) -o $@ $(LDFLAGS) $^ 76 | 77 | sg_tst_nvme: sg_tst_nvme.o $(LIBFILESNEW) 78 | $(LD) -o $@ $(LDFLAGS) $^ 79 | 80 | tst_sg_lib: tst_sg_lib.o ../lib/sg_lib.o ../lib/sg_lib_data.o 81 | $(LD) -o $@ $(LDFLAGS) $^ 82 | 83 | install: $(EXECS) 84 | install -d $(INSTDIR) 85 | for name in $^; \ 86 | do install -s -o root -g root -m 755 $$name $(INSTDIR); \ 87 | done 88 | install -d $(MANDIR)/$(MAN_PREF) 89 | for mp in $(MAN_PGS); \ 90 | do install -o root -g root -m 644 $$mp $(MANDIR)/$(MAN_PREF); \ 91 | gzip -9f $(MANDIR)/$(MAN_PREF)/$$mp; \ 92 | done 93 | 94 | uninstall: 95 | dists="$(EXECS)"; \ 96 | for name in $$dists; do \ 97 | rm -f $(INSTDIR)/$$name; \ 98 | done 99 | for mp in $(MAN_PGS); do \ 100 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 101 | done 102 | 103 | # Linux uses GNU make and FreeBSD uses Berkely make. The following lines 104 | # only work in Linux. Possible solutions in FreeBSD: 105 | # a) use 'gmake'; b) comment out the next 3 lines, starting with 'ifeq' 106 | # c) build with 'make -f Makefile.freebsd' 107 | # In Linux one can install bmake (but that won't help here). 108 | ifeq (.depend,$(wildcard .depend)) 109 | include .depend 110 | endif 111 | -------------------------------------------------------------------------------- /lib/Makefile.am: -------------------------------------------------------------------------------- 1 | libsgutils2_la_SOURCES = \ 2 | sg_lib.c \ 3 | sg_json.c \ 4 | sg_json_sg_lib.c \ 5 | sg_pr2serr.c \ 6 | sg_lib_data.c \ 7 | sg_lib_names.c \ 8 | sg_cmds_basic.c \ 9 | sg_cmds_basic2.c \ 10 | sg_cmds_extra.c \ 11 | sg_cmds_mmc.c \ 12 | sg_pt_common.c \ 13 | sg_json_builder.c 14 | 15 | if OS_LINUX 16 | if PT_DUMMY 17 | libsgutils2_la_SOURCES += sg_pt_dummy.c 18 | else 19 | libsgutils2_la_SOURCES += \ 20 | sg_pt_linux.c \ 21 | sg_io_linux.c \ 22 | sg_pt_linux_nvme.c 23 | endif 24 | endif 25 | 26 | if OS_WIN32_MINGW 27 | libsgutils2_la_SOURCES += sg_pt_win32.c 28 | endif 29 | 30 | if OS_WIN32_CYGWIN 31 | libsgutils2_la_SOURCES += sg_pt_win32.c 32 | endif 33 | 34 | if OS_FREEBSD 35 | if PT_DUMMY 36 | libsgutils2_la_SOURCES += sg_pt_dummy.c 37 | else 38 | libsgutils2_la_SOURCES += sg_pt_freebsd.c 39 | endif 40 | endif 41 | 42 | if OS_SOLARIS 43 | libsgutils2_la_SOURCES += sg_pt_solaris.c 44 | endif 45 | 46 | if OS_OSF 47 | libsgutils2_la_SOURCES += sg_pt_osf1.c 48 | endif 49 | 50 | if OS_HAIKU 51 | if PT_DUMMY 52 | libsgutils2_la_SOURCES += sg_pt_dummy.c 53 | else 54 | libsgutils2_la_SOURCES += sg_pt_haiku.c 55 | endif 56 | endif 57 | 58 | if OS_NETBSD 59 | libsgutils2_la_SOURCES += sg_pt_netbsd.c 60 | endif 61 | 62 | if OS_OPENBSD 63 | libsgutils2_la_SOURCES += sg_pt_dummy.c 64 | endif 65 | 66 | if OS_OTHER 67 | libsgutils2_la_SOURCES += sg_pt_dummy.c 68 | endif 69 | 70 | if DEBUG 71 | # This is active if --enable-debug given to ./configure 72 | # removed -Wduplicated-branches because needs gcc-8 73 | DBG_CFLAGS = -Wextra -Wmisleading-indentation -Wduplicated-cond -Wlogical-op -Wnull-dereference -Wshadow -Wjump-misses-init -Wunused -Wsizeof-array-argument 74 | DBG_CXXFLAGS = -Wextra -Wmisleading-indentation -Wduplicated-cond -Wlogical-op -Wnull-dereference -Wshadow -Wunused -Wsizeof-array-argument 75 | DBG_CPPFLAGS = -DDEBUG 76 | else 77 | DBG_CFLAGS = 78 | DBG_CXXFLAGS = 79 | DBG_CPPFLAGS = 80 | endif 81 | 82 | # For C++/clang testing 83 | ## CC = gcc-9 84 | ## CXX = g++ 85 | ## CC = g++ 86 | ## CC = clang 87 | ## CXX = clang++ 88 | ## CC = clang++ 89 | ## CC = powerpc64-linux-gnu-gcc 90 | 91 | # -std= can be c99, c11, gnu11, etc. Default is gnu11 for C code 92 | # -Wall is no longer all warnings. Add -W (since renamed to -Wextra) for more 93 | AM_CPPFLAGS = -iquote ${top_srcdir}/include -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 $(DBG_CPPFLAGS) 94 | AM_CFLAGS = -Wall -W $(DBG_CFLAGS) 95 | # AM_CFLAGS = -Wall -W -flto=auto $(DBG_CFLAGS) 96 | # AM_CFLAGS = -Wall -W $(DBG_CFLAGS) -fanalyzer 97 | # AM_CFLAGS = -Wall -W -pedantic -std=c99 98 | # AM_CFLAGS = -Wall -W -pedantic -std=c11 99 | # AM_CFLAGS = -Wall -W -pedantic -std=c11 --analyze 100 | # AM_CFLAGS = -Wall -W -pedantic -std=c++11 101 | # AM_CFLAGS = -Wall -W -pedantic -std=c++14 102 | # AM_CFLAGS = -Wall -W -pedantic -std=c++17 $(DBG_CXXFLAGS) 103 | # AM_CFLAGS = -Wall -W -pedantic -std=c++20 --analyze $(DBG_CXXFLAGS) 104 | # AM_CFLAGS = -Wall -W -pedantic -std=c++20 $(DBG_CXXFLAGS) 105 | # AM_CFLAGS = -Wall -W -pedantic -std=c++23 $(DBG_CXXFLAGS) 106 | 107 | lib_LTLIBRARIES = libsgutils2.la 108 | 109 | libsgutils2_la_LDFLAGS = -version-info 2:0:0 -no-undefined -release ${PACKAGE_VERSION} 110 | 111 | libsgutils2_la_LIBADD = @GETOPT_O_FILES@ 112 | libsgutils2_la_DEPENDENCIES = @GETOPT_O_FILES@ 113 | 114 | EXTRA_DIST = \ 115 | sg_json_builder.h \ 116 | BSD_LICENSE 117 | -------------------------------------------------------------------------------- /lib/sg_pr2serr.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022-2023 Douglas Gilbert. 3 | * All rights reserved. 4 | * Use of this source code is governed by a BSD-style 5 | * license that can be found in the BSD_LICENSE file. 6 | * 7 | * SPDX-License-Identifier: BSD-2-Clause 8 | */ 9 | 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | 18 | #include "sg_pr2serr.h" 19 | 20 | FILE * sg_warnings_strm = NULL; /* would like to default to stderr */ 21 | 22 | 23 | int 24 | pr2serr(const char * fmt, ...) 25 | { 26 | va_list args; 27 | int n; 28 | 29 | va_start(args, fmt); 30 | n = vfprintf(stderr, fmt, args); 31 | va_end(args); 32 | return n; 33 | } 34 | 35 | int 36 | pr2ws(const char * fmt, ...) 37 | { 38 | va_list args; 39 | int n; 40 | 41 | va_start(args, fmt); 42 | n = vfprintf(sg_warnings_strm ? sg_warnings_strm : stderr, fmt, args); 43 | va_end(args); 44 | return n; 45 | } 46 | 47 | /* Want safe, 'n += snprintf(b + n, blen - n, ...);' pattern that can 48 | * be called repeatedly. However snprintf() takes an unsigned second argument 49 | * (size_t) that explodes if 'blen - n' goes negative. This function instead 50 | * uses signed integers (second argument and return value) and is safe if the 51 | * second argument is negative. It returns number of chars actually 52 | * placed in cp excluding the trailing null char. So for cp_max_len > 0 the 53 | * return value is always < cp_max_len; for cp_max_len <= 1 the return value 54 | * is 0 and no chars are written to cp. Note this means that when 55 | * cp_max_len = 1, this function assumes that cp[0] is the null character 56 | * and does nothing (and returns 0). Linux kernel has a similar function 57 | * called scnprintf(). */ 58 | int 59 | sg_scnpr(char * cp, int cp_max_len, const char * fmt, ...) 60 | { 61 | va_list args; 62 | int n; 63 | 64 | #ifdef DEBUG 65 | if (cp_max_len < 2) { 66 | /* stack backtrace would be good here ... */ 67 | pr2ws("%s: buffer would overrun, 'fmt' string: %s\n", __func__, fmt); 68 | return 0; 69 | } 70 | #else 71 | if (cp_max_len < 2) 72 | return 0; 73 | #endif 74 | va_start(args, fmt); 75 | n = vsnprintf(cp, cp_max_len, fmt, args); 76 | va_end(args); 77 | return (n < cp_max_len) ? n : (cp_max_len - 1); 78 | } 79 | 80 | /* This function is similar to sg_scnpr() but takes the "n" in that pattern 81 | * as an extra, third argument where it is renamed 'off'. This function will 82 | * start writing chars at 'fcp + off' for no more than 'fcp_len - off - 1' 83 | * characters. The return value is the same as sg_scnpr(). */ 84 | int 85 | sg_scn3pr(char * fcp, int fcp_len, int off, const char * fmt, ...) 86 | { 87 | va_list args; 88 | const int cp_max_len = fcp_len - off; 89 | int n; 90 | 91 | #ifdef DEBUG 92 | if (cp_max_len < 2) { 93 | /* stack backtrace would be good here ... */ 94 | pr2ws("%s: buffer would overrun, 'fmt' string: %s\n", __func__, fmt); 95 | return 0; 96 | } 97 | #else 98 | if (cp_max_len < 2) 99 | return 0; 100 | #endif 101 | va_start(args, fmt); 102 | n = vsnprintf(fcp + off, fcp_len - off, fmt, args); 103 | va_end(args); 104 | return (n < cp_max_len) ? n : (cp_max_len - 1); 105 | } 106 | -------------------------------------------------------------------------------- /getopt_long/getopt.h: -------------------------------------------------------------------------------- 1 | /* $NetBSD: getopt.h,v 1.7 2005/02/03 04:39:32 perry Exp $ */ 2 | 3 | /*- 4 | * Copyright (c) 2000 The NetBSD Foundation, Inc. 5 | * All rights reserved. 6 | * 7 | * This code is derived from software contributed to The NetBSD Foundation 8 | * by Dieter Baron and Thomas Klausner. 9 | * 10 | * Redistribution and use in source and binary forms, with or without 11 | * modification, are permitted provided that the following conditions 12 | * are met: 13 | * 1. Redistributions of source code must retain the above copyright 14 | * notice, this list of conditions and the following disclaimer. 15 | * 2. Redistributions in binary form must reproduce the above copyright 16 | * notice, this list of conditions and the following disclaimer in the 17 | * documentation and/or other materials provided with the distribution. 18 | * 3. All advertising materials mentioning features or use of this software 19 | * must display the following acknowledgement: 20 | * This product includes software developed by the NetBSD 21 | * Foundation, Inc. and its contributors. 22 | * 4. Neither the name of The NetBSD Foundation nor the names of its 23 | * contributors may be used to endorse or promote products derived 24 | * from this software without specific prior written permission. 25 | * 26 | * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 27 | * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 28 | * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 29 | * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 30 | * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 31 | * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 32 | * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 33 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 34 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 35 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 36 | * POSSIBILITY OF SUCH DAMAGE. 37 | */ 38 | 39 | /* 40 | * modified May 12, 2005 by Jim Basney 41 | * 42 | * removed #include of non-POSIX and 43 | * removed references to _NETBSD_SOURCE and HAVE_NBTOOL_CONFIG_H 44 | * added #if !HAVE_GETOPT_LONG 45 | * removed __BEGIN_DECLS and __END_DECLS 46 | */ 47 | 48 | #ifndef _MYPROXY_GETOPT_H_ 49 | #define _MYPROXY_GETOPT_H_ 50 | 51 | #if !HAVE_GETOPT_LONG 52 | 53 | #include 54 | 55 | /* 56 | * Gnu like getopt_long() and BSD4.4 getsubopt()/optreset extensions 57 | */ 58 | #define no_argument 0 59 | #define required_argument 1 60 | #define optional_argument 2 61 | 62 | extern char *optarg; 63 | extern int optind; 64 | extern int optopt; 65 | extern int opterr; 66 | 67 | struct option { 68 | /* name of long option */ 69 | const char *name; 70 | /* 71 | * one of no_argument, required_argument, and optional_argument: 72 | * whether option takes an argument 73 | */ 74 | int has_arg; 75 | /* if not NULL, set *flag to val when option found */ 76 | int *flag; 77 | /* if flag not NULL, value to set *flag to; else return value */ 78 | int val; 79 | }; 80 | 81 | int getopt_long(int, char * const *, const char *, 82 | const struct option *, int *); 83 | 84 | #endif /* !HAVE_GETOPT_LONG */ 85 | 86 | #endif /* !_MYPROXY_GETOPT_H_ */ 87 | -------------------------------------------------------------------------------- /inhex/tst_script.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | # Any Bourne style shell should be okay 3 | 4 | # Test the hex "inhex" files in this directory using the corresponding 5 | # sg3_utils utility which is assumed to be installed. 6 | 7 | # Get each utility to send its version string and command line options 8 | # to stderr. Comment out the next line to stop that. 9 | export SG3_UTILS_INVOCATION=1 10 | 11 | # In all cases below the '-i ' or '-I < filename>' option can be 12 | # replaced by '--inhex=' . 13 | 14 | sg_decode_sense -i descriptor_sense.hex 15 | sg_decode_sense -i fixed_sense.hex 16 | sg_decode_sense -i forwarded_sense.hex 17 | 18 | sg_get_elem_status -i get_elem_status.hex 19 | 20 | sg_get_lba_status -i get_lba_status.hex 21 | 22 | sg_inq -I inq_standard.hex 23 | 24 | sg_luns -i luns_lu_cong.hex 25 | sg_luns -i luns_wlun.hex 26 | 27 | # modes_mm_sdeb.hex and modes_sdeb.hex are output by sg_modes which is 28 | # unable to decode mode pages. For that there is the sdparm utility in 29 | # a package of the same name. Won't assume it is installed so skip. 30 | 31 | # The nvme*.hex files are meant as input to the sg_raw utility where 32 | # the corresponding DEVICE is a NVMe (storage) device. Will skip in this 33 | # script as they require the appropriate hardware. 34 | 35 | sg_opcodes -i opcodes.hex 36 | 37 | sg_readcap -i readcap_zbc.hex 38 | 39 | sg_decode_sense -i ref_sense.hex 40 | 41 | sg_rep_density -i rep_density.hex 42 | sg_rep_density -i rep_density_media.hex 43 | sg_rep_density --typem -i rep_density_media_typem.hex 44 | sg_rep_density --typem -i rep_density_typem.hex 45 | 46 | sg_rep_zones --realm --i rep_realms.hex 47 | sg_rep_zones --domain --i rep_zdomains.hex 48 | sg_rep_zones --i rep_zones.hex 49 | 50 | echo "" 51 | echo ">>>>>>>>>>>>>>>> sg_ses tests" 52 | sg_ses --all --inhex=ses_areca_all.hex 53 | # test indexing on Voltage sensor ('vs') element type [0x12] 54 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,-1 55 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,-1:-1 56 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,-1:0 57 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,-1:1 58 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,-1:2 59 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,-1:255 60 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,1 61 | echo "" 62 | echo "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" 63 | echo "expect error cause only 2 individual Voltage sensors" 64 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs,2 65 | echo "" 66 | # The Voltage sensor element type number given rather than abbreviation 67 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=_0x12,1 68 | # In the config dpage Voltage sensor is entry 5 in the type desc. header 69 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=5,1 70 | # Voltage sensor given but no individual index so defaults to overall 71 | sg_ses --get=disable --inhex=ses_areca_all.hex --index=vs 72 | 73 | echo "" 74 | echo ">>>>>>>>>>>>>>>> sg_vpd tests" 75 | sg_vpd -I vpd_bdce.hex 76 | sg_vpd -I vpd_constituents.hex 77 | sg_vpd -I vpd_cpr.hex 78 | sg_vpd -I vpd_dev_id.hex 79 | sg_vpd -I vpd_di_all.hex 80 | sg_vpd -I vpd_fp.hex 81 | sg_vpd -I vpd_lbpro.hex 82 | sg_vpd -I vpd_lbpv.hex 83 | sg_vpd -I vpd_ref.hex 84 | sg_vpd -I vpd_sbl.hex 85 | sg_vpd -I vpd_sdeb.hex 86 | sg_vpd -I vpd_sfs.hex 87 | sg_vpd -I vpd_tpc.hex 88 | sg_vpd -I vpd_zbdc.hex 89 | 90 | sg_z_act_query --inhex=z_act_query.hex 91 | 92 | # D. Gilbert, last updated 20230420 93 | 94 | -------------------------------------------------------------------------------- /doc/sg_bg_ctl.8: -------------------------------------------------------------------------------- 1 | .TH SG_BG_CTL "8" "May 2016" "sg3_utils\-1.43" SG3_UTILS 2 | .SH NAME 3 | sg_bg_ctl \- send SCSI BACKGROUND CONTROL command 4 | .SH SYNOPSIS 5 | .B sg_bg_ctl 6 | [\fI\-\-ctl=CTL\fR] [\fI\-\-help\fR] [\fI\-\-time=TN\fR] [\fI\-\-verbose\fR] 7 | [\fI\-\-version\fR] \fIDEVICE\fR 8 | .SH DESCRIPTION 9 | .\" Add any additional description here 10 | Sends a SCSI BACKGROUND CONTROL command to the \fIDEVICE\fR. This command 11 | was first found in the SBC\-4 draft standard revision 8 (sbc4r08.pdf). It can 12 | be used to start and stop 'advanced background operations' on the 13 | \fIDEVICE\fR. Only resource or thin provisioned devices (logical units which 14 | are typically (solid state) disks) support this command. Those advanced 15 | background operations often include garbage collection type operations which 16 | may degrade the disk's performance while they are being performed. 17 | .SH OPTIONS 18 | Arguments to long options are mandatory for short options as well. 19 | .TP 20 | \fB\-c\fR, \fB\-\-ctl\fR=\fICTL\fR 21 | \fICTL\fR is the value placed in the BO_CTL field of the BACKGROUND CONTROL 22 | command (cdb). It is a two bit field so has 4 variants: 0 does not change 23 | the host initiated advanced background operations; 1 starts these operations; 24 | 2 stops these operations and 3 is reserved. The default value is 0. 25 | .TP 26 | \fB\-h\fR, \fB\-\-help\fR 27 | output the usage message then exit. 28 | .TP 29 | \fB\-t\fR, \fB\-\-time\fR=\fITN\fR 30 | \fITN\fR is a maximum time (with a unit of 100 ms or 1/10 second) that 31 | advanced background operations can occur. This value is ignored if the 32 | \fICTL\fR argument is other than 1. The default value is 0 which means there 33 | is no maximum time limit. Only values 0 to 255 (which is 25.5 seconds) can 34 | be given. This value is place in the BO_TIME field of the BACKGROUND CONTROL 35 | command. 36 | .TP 37 | \fB\-v\fR, \fB\-\-verbose\fR 38 | increase the level of verbosity, (i.e. debug output). 39 | .TP 40 | \fB\-V\fR, \fB\-\-version\fR 41 | print the version string and then exit. 42 | .SH NOTES 43 | According to T10, support for 'background control operations' is indicated by 44 | the BOCS bit being set in the Block device characteristics VPD page [0xb1]. 45 | The setting of the BOCS bit can be checked with the sg_vpd and sdparm 46 | utilities (and it is read only). There is a Background operations control 47 | mode page [0xa, 0x6] with a BO_MODE field for modifying the action of this 48 | operation. The BO_MODE field can be accessed and possibly modified with the 49 | sdparm utility. The BO_STATUS field can be found in the Background operation 50 | log page [0x15, 0x2] and that can be viewed with the sg_logs utility. 51 | .PP 52 | The current draft describing this area is SBC\-4 revision 10 (sbc4r10.pdf) 53 | in clause 4.33 . That contains the following example of a background 54 | operation: "Advanced background operation may include NAND block erase 55 | operations, media read operations, and media write operations (e.g., 56 | garbage collection), which may impact response time for normal read requests 57 | or write requests from the application client." 58 | .SH EXIT STATUS 59 | The exit status of sg_bg_ctl is 0 when it is successful. Otherwise see 60 | the sg3_utils(8) man page. 61 | .SH AUTHORS 62 | Written by Douglas Gilbert. 63 | .SH "REPORTING BUGS" 64 | Report bugs to . 65 | .SH COPYRIGHT 66 | Copyright \(co 2016 Douglas Gilbert 67 | .br 68 | This software is distributed under a BSD\-2\-Clause license. There is NO 69 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 70 | .SH "SEE ALSO" 71 | .B sg_vpd,sg_logs(sg3_utils); sdparm(sdparm) 72 | -------------------------------------------------------------------------------- /examples/Makefile: -------------------------------------------------------------------------------- 1 | SHELL = /bin/sh 2 | 3 | PREFIX=/usr/local 4 | INSTDIR=$(DESTDIR)/$(PREFIX)/bin 5 | MANDIR=$(DESTDIR)/$(PREFIX)/man 6 | 7 | # In Linux the default C compiler is GCC while in FreeBSD (since release 10 ?) 8 | # the default C compiler is clang. Swap the comment marks (lines starting 9 | # with '#') on the next 4 (non-blank) lines. 10 | CC = gcc 11 | # CC = clang 12 | 13 | LD = gcc 14 | # LD = clang 15 | 16 | 17 | EXECS = sg_simple1 sg_simple2 sg_simple3 sg_simple4 sg_simple16 \ 18 | scsi_inquiry sg_excl sg_simple5 sg__sat_identify \ 19 | sg__sat_phy_event sg__sat_set_features sg_sat_chk_power \ 20 | sg_sat_smart_rd_data 21 | 22 | EXTRAS = sgq_dd 23 | 24 | BSG_EXTRAS = 25 | 26 | 27 | MAN_PGS = 28 | MAN_PREF = man8 29 | 30 | LARGE_FILE_FLAGS = -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 31 | 32 | CPPFLAGS = -iquote ../include -D_REENTRANT $(LARGE_FILE_FLAGS) 33 | # CPPFLAGS = -iquote ../include -D_REENTRANT $(LARGE_FILE_FLAGS) -DDEBUG 34 | 35 | CFLAGS = -g -O2 -W -Wall 36 | # CFLAGS = -g -O2 -Wall -DSG_KERNEL_INCLUDES 37 | # CFLAGS = -g -O2 -Wall -pedantic 38 | 39 | LDFLAGS = 40 | 41 | LIBFILESOLD = ../lib/sg_lib.o ../lib/sg_lib_data.o ../lib/sg_pr2serr.o ../lib/sg_io_linux.o 42 | LIBFILESNEW = ../lib/sg_lib.o ../lib/sg_lib_data.o ../lib/sg_pr2serr.o ../lib/sg_pt_common.o ../lib/sg_pt_linux.o ../lib/sg_pt_linux_nvme.o 43 | 44 | all: $(EXECS) 45 | 46 | extras: $(EXTRAS) 47 | 48 | bsg: $(BSG_EXTRAS) 49 | 50 | 51 | depend dep: 52 | for i in *.c; do $(CC) $(INCLUDES) $(CFLAGS) -M $$i; \ 53 | done > .depend 54 | 55 | clean: 56 | /bin/rm -f *.o $(EXECS) $(EXTRAS) $(BSG_EXTRAS) core .depend 57 | 58 | sg_simple1: sg_simple1.o $(LIBFILESOLD) 59 | $(LD) -o $@ $(LDFLAGS) $^ 60 | 61 | sg_simple2: sg_simple2.o 62 | $(LD) -o $@ $(LDFLAGS) $^ 63 | 64 | sg_simple3: sg_simple3.o $(LIBFILESOLD) 65 | $(LD) -o $@ $(LDFLAGS) $^ 66 | 67 | sg_simple4: sg_simple4.o $(LIBFILESOLD) 68 | $(LD) -o $@ $(LDFLAGS) $^ 69 | 70 | sg_simple16: sg_simple16.o $(LIBFILESOLD) 71 | $(LD) -o $@ $(LDFLAGS) $^ 72 | 73 | scsi_inquiry: scsi_inquiry.o 74 | $(LD) -o $@ $(LDFLAGS) $^ 75 | 76 | sg_excl: sg_excl.o $(LIBFILESOLD) 77 | $(LD) -o $@ $(LDFLAGS) $^ 78 | 79 | sg_simple5: sg_simple5.o $(LIBFILESNEW) 80 | $(LD) -o $@ $(LDFLAGS) $^ 81 | 82 | sg__sat_identify: sg__sat_identify.o $(LIBFILESOLD) 83 | $(LD) -o $@ $(LDFLAGS) $^ 84 | 85 | sg__sat_phy_event: sg__sat_phy_event.o $(LIBFILESOLD) 86 | $(LD) -o $@ $(LDFLAGS) $^ 87 | 88 | sg__sat_set_features: sg__sat_set_features.o $(LIBFILESOLD) 89 | $(LD) -o $@ $(LDFLAGS) $^ 90 | 91 | sg_sat_chk_power: sg_sat_chk_power.o $(LIBFILESOLD) 92 | $(LD) -o $@ $(LDFLAGS) $^ 93 | 94 | sg_sat_smart_rd_data: sg_sat_smart_rd_data.o $(LIBFILESOLD) 95 | $(LD) -o $@ $(LDFLAGS) $^ 96 | 97 | sgq_dd: sgq_dd.o $(LIBFILESOLD) 98 | $(LD) -o $@ $(LDFLAGS) $^ 99 | 100 | install: $(EXECS) 101 | install -d $(INSTDIR) 102 | for name in $^; \ 103 | do install -s -o root -g root -m 755 $$name $(INSTDIR); \ 104 | done 105 | install -d $(MANDIR)/$(MAN_PREF) 106 | for mp in $(MAN_PGS); \ 107 | do install -o root -g root -m 644 $$mp $(MANDIR)/$(MAN_PREF); \ 108 | gzip -9f $(MANDIR)/$(MAN_PREF)/$$mp; \ 109 | done 110 | 111 | uninstall: 112 | dists="$(EXECS)"; \ 113 | for name in $$dists; do \ 114 | rm -f $(INSTDIR)/$$name; \ 115 | done 116 | for mp in $(MAN_PGS); do \ 117 | rm -f $(MANDIR)/$(MAN_PREF)/$$mp.gz; \ 118 | done 119 | 120 | # Linux uses GNU make and FreeBSD uses Berkely make. The following lines 121 | # only work in Linux. Possible solutions in FreeBSD: 122 | # a) use 'gmake'; b) comment out the next 3 lines, starting with 'ifeq' 123 | # c) build with 'make -f Makefile.freebsd' 124 | # In Linux one can install bmake (but that won't help here). 125 | ifeq (.depend,$(wildcard .depend)) 126 | include .depend 127 | endif 128 | -------------------------------------------------------------------------------- /doc/sg_test_rwbuf.8: -------------------------------------------------------------------------------- 1 | .TH SG_TEST_RWBUF "8" "January 2018" "sg3_utils\-1.43" SG3_UTILS 2 | .SH NAME 3 | sg_test_rwbuf \- test a SCSI host adapter by issuing dummy writes 4 | and reads 5 | .SH SYNOPSIS 6 | .B sg_test_rwbuf 7 | [\fI\-\-addrd=AR\fR] [\fI\-\-addwr=AW\fR] [\fI\-\-help\fR] 8 | [\fI\-\-quick\fR] \fI\-\-size=SZ\fR [\fI\-\-times=NUM\fR] [\fI\-\-verbose\fR] 9 | [\fI\-\-version\fR] \fIDEVICE\fR 10 | .PP 11 | or an older deprecated format 12 | .B sg_test_rwbuf 13 | \fIDEVICE\fR \fISZ\fR [\fIAW\fR] [\fIAR\fR] 14 | .SH DESCRIPTION 15 | .\" Add any additional description here 16 | sg_test_rwbuf writes and reads back \fISZ\fR bytes to the internal buffer of 17 | \fIDEVICE\fR (e.g. /dev/sda or /dev/sg0). A pseudo random pattern is 18 | written to the data buffer on the device then read back. If the same pattern 19 | is found 'Success' is reported. If they do not match (checksums unequal) then 20 | this is reported and up to 24 bytes from the first point of mismatch are 21 | reported; the first line shows what was written and the second line shows 22 | what was received. For testing purposes, you can ask it to write \fIAW\fR or 23 | read \fIAR\fR additional bytes. 24 | .SH OPTIONS 25 | Arguments to long options are mandatory for short options as well. 26 | .TP 27 | \fB\-r\fR, \fB\-\-addrd\fR=\fIAR\fR 28 | Read an additional \fIAR\fR bytes (more than indicated by \fISZ\fR) from the 29 | data buffer. Checksum is performed over the first \fISZ\fR bytes. 30 | .TP 31 | \fB\-w\fR, \fB\-\-addwr\fR=\fIAW\fR 32 | Write an additional \fIAW\fR bytes (more than indicated by \fISZ\fR) of 33 | zeros into the data buffer. Checksum is generated over the first \fISZ\fR 34 | bytes. 35 | .TP 36 | \fB\-h\fR, \fB\-\-help\fR 37 | Print out a usage message the exit. 38 | .TP 39 | \fB\-q\fR, \fB\-\-quick\fR 40 | Perform a READ BUFFER descriptor command to find out the available data 41 | buffer length and offset, print them out then exit (without testing 42 | with write/read sequences). 43 | .TP 44 | \fB\-s\fR, \fB\-\-size\fR=\fISZ\fR 45 | where \fISZ\fR is the size of buffer in bytes to be written then read and 46 | checked. This number needs to be less than or equal to the size of the 47 | device's data buffer which can be seen from the \fI\-\-quick\fR option. 48 | Either this option or the \fI\-\-quick\fR option should be given. 49 | .TP 50 | \fB\-t\fR, \fB\-\-times\fR=\fINUM\fR 51 | where \fINUM\fR is the number of times to repeat the write/read to buffer 52 | test. Default value is 1 . 53 | .TP 54 | \fB\-v\fR, \fB\-\-verbose\fR 55 | increase verbosity of output. 56 | .TP 57 | \fB\-V\fR, \fB\-\-version\fR 58 | print version number (and data of last change) then exit. 59 | .SH NOTES 60 | The microcode in a SCSI device is _not_ modified by doing a WRITE BUFFER 61 | command with its mode set to "data" (0x2) as done by this utility. Therefore 62 | this utility is safe in that respect. [Mode values 0x4, 0x5, 0x6 and 0x7 63 | are the dangerous ones :\-)] 64 | .PP 65 | \fBWARNING\fR: If you access the device at the same time (e.g. because it's 66 | a hard disk with a mounted file system on it) the device's buffer may be 67 | used by the device itself for other data at the same time, and overwriting 68 | it may or may not cause data corruption! \fBHOWEVER\fR the SPC\-3 draft 69 | standard does state in its WRITE BUFFER command: "This command shall not 70 | alter any medium of the logical unit when data mode ... is specified". This 71 | implies that it _is_ safe to use this utility with devices that have mounted 72 | file systems on them. 73 | Following this theme further, a disk with active mounted file systems may 74 | cause the data read back to be different (due to caching activity) to what 75 | was written and hence a checksum error. 76 | .SH EXIT STATUS 77 | The exit status of sg_test_rwbuf is 0 when it is successful. Otherwise see 78 | the sg3_utils(8) man page. 79 | .SH AUTHORS 80 | Written by D. Gilbert and K. Garloff 81 | .SH COPYRIGHT 82 | Copyright \(co 2000\-2018 Douglas Gilbert, Kurt Garloff 83 | .br 84 | This software is distributed under the GPL version 2. There is NO 85 | warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 86 | -------------------------------------------------------------------------------- /inhex/modes_mm_sdeb.hex: -------------------------------------------------------------------------------- 1 | # See the EXAMPLES section in the sg_modes(8) manpage 2 | # 3 | # The output shown below was generated by: 4 | # sg_modes -A -HHHH -M /dev/sg0 5 | # where /dev/sg0 was a scsi_debug device in Linux. 6 | # 7 | 8 | # Mode parameter header from MODE SENSE(10): 9 | 00 ee 00 10 00 00 00 08 10 | 11 | # Block descriptors from MODE SENSE(10): 12 | 00 80 00 00 00 00 02 00 13 | 14 | # Read-Write error recovery mode page [0x1]: 15 | # current page control: 16 | 01 0a c0 0b f0 00 00 00 05 00 ff ff 17 | # changeable page control: 18 | 01 0a 00 00 00 00 00 00 00 00 00 00 19 | # default page control: 20 | 01 0a c0 0b f0 00 00 00 05 00 ff ff 21 | 22 | # Disconnect-Reconnect mode page [0x2]: 23 | # current page control: 24 | 02 0e 80 80 00 0a 00 00 00 00 00 00 00 00 00 00 25 | # changeable page control: 26 | 02 0e 00 00 00 00 00 00 00 00 00 00 00 00 00 00 27 | # default page control: 28 | 02 0e 80 80 00 0a 00 00 00 00 00 00 00 00 00 00 29 | 30 | # Format (obsolete) mode page [0x3]: 31 | # current page control: 32 | 03 16 00 00 00 00 00 00 00 00 00 3f 02 00 00 00 33 | 00 00 00 00 40 00 00 00 34 | # changeable page control: 35 | 03 16 00 00 00 00 00 00 00 00 00 00 00 00 00 00 36 | 00 00 00 00 00 00 00 00 37 | # default page control: 38 | 03 16 00 00 00 00 00 00 00 00 00 3f 02 00 00 00 39 | 00 00 00 00 40 00 00 00 40 | 41 | # Caching mode page [0x8]: 42 | # current page control: 43 | 08 12 14 00 ff ff 00 00 ff ff ff ff 80 14 00 00 44 | 00 00 00 00 45 | # changeable page control: 46 | 08 12 04 00 00 00 00 00 00 00 00 00 00 00 00 00 47 | 00 00 00 00 48 | # default page control: 49 | 08 12 14 00 ff ff 00 00 ff ff ff ff 80 14 00 00 50 | 00 00 00 00 51 | 52 | # Control mode page [0xa]: 53 | # current page control: 54 | 0a 0a 02 00 00 80 00 00 00 00 02 4b 55 | # changeable page control: 56 | 0a 0a 06 00 00 00 00 00 00 00 00 00 57 | # default page control: 58 | 0a 0a 02 00 00 00 00 00 00 00 02 4b 59 | 60 | # Protocol specific port (SPL) mode page [0x19]: 61 | # current page control: 62 | 19 06 06 00 07 d0 00 00 63 | # changeable page control: 64 | 19 06 00 00 00 00 00 00 65 | # default page control: 66 | 19 06 06 00 07 d0 00 00 67 | 68 | # Phy control and discover (SPL) mode page [0x19,0x1]: 69 | # current page control: 70 | 59 01 00 64 00 06 00 02 00 00 00 00 10 09 08 00 71 | 32 22 22 20 00 00 07 ce 31 11 11 10 00 00 00 01 72 | 02 00 00 00 00 00 00 00 88 99 00 00 00 00 00 00 73 | 00 00 00 00 00 00 00 00 00 01 00 00 10 09 08 00 74 | 32 22 22 20 00 00 07 cf 31 11 11 10 00 00 00 01 75 | 03 00 00 00 00 00 00 00 88 99 00 00 00 00 00 00 76 | 00 00 00 00 00 00 00 00 77 | # changeable page control: 78 | 59 01 00 64 00 00 00 00 00 00 00 00 00 00 00 00 79 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 80 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 81 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 82 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 83 | 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 84 | 00 00 00 00 00 00 00 00 85 | # default page control: 86 | 59 01 00 64 00 06 00 02 00 00 00 00 10 09 08 00 87 | 32 22 22 20 00 00 07 ce 31 11 11 10 00 00 00 01 88 | 02 00 00 00 00 00 00 00 88 99 00 00 00 00 00 00 89 | 00 00 00 00 00 00 00 00 00 01 00 00 10 09 08 00 90 | 32 22 22 20 00 00 07 cf 31 11 11 10 00 00 00 01 91 | 03 00 00 00 00 00 00 00 88 99 00 00 00 00 00 00 92 | 00 00 00 00 00 00 00 00 93 | 94 | # Shared port control (SPL) mode page [0x19,0x2]: 95 | # current page control: 96 | 59 02 00 0c 00 06 10 00 00 00 00 00 00 00 00 00 97 | # changeable page control: 98 | 59 02 00 0c 00 00 00 00 00 00 00 00 00 00 00 00 99 | # default page control: 100 | 59 02 00 0c 00 06 10 00 00 00 00 00 00 00 00 00 101 | 102 | # Informational exceptions control mode page [0x1c]: 103 | # current page control: 104 | 1c 0a 08 00 00 00 00 00 00 00 00 00 105 | # changeable page control: 106 | 1c 0a 04 0f 00 00 00 00 00 00 00 00 107 | # default page control: 108 | 1c 0a 08 00 00 00 00 00 00 00 00 00 109 | -------------------------------------------------------------------------------- /inhex/README: -------------------------------------------------------------------------------- 1 | Hex data for various sg3_utils utilities 2 | ======================================== 3 | 4 | The files in this folder contain hexadecimal data (in ASCII) and associated 5 | comments (prefixed with the hash mark symbol: '#' ). Files containing 6 | hexadecimal data have the extension ".hex". There is at least one file 7 | containing binary data and it has the extension ".raw". 8 | 9 | The utility that each hex file is associated with can be determined in most 10 | case by prepending "sg_" to these filenames. Then go to the 'src' folder (a 11 | sibling folder to this one) and look for a match or partial match on 12 | the name. 13 | 14 | For example: 15 | vpd_dev_id.hex 16 | after prepending 'sg_' becomes: 17 | sg_vpd_dev_id.hex 18 | which is a partial match on the sg_vpd utility. 19 | The remaining 'dev_id.hex' is meant to suggest that the 'device identifier' 20 | VPD page is what is being represented. The 'device identifier' VPD page is 21 | mandatory for SCSI devices since SPC-2 (INCITS 351-2001). 22 | 23 | Assuming sg3_utils is installed, it can be tested like this: 24 | sg_vpd --inhex=/inhex/vpd_dev_id.hex 25 | 26 | And should output this: 27 | 28 | Device Identification VPD page: 29 | Addressed logical unit: 30 | designator type: NAA, code set: Binary 31 | 0x5000c5003011cb2b 32 | Target port: 33 | designator type: NAA, code set: Binary 34 | transport: Serial Attached SCSI Protocol (SPL-4) 35 | 0x5000c5003011cb29 36 | designator type: Relative target port, code set: Binary 37 | transport: Serial Attached SCSI Protocol (SPL-4) 38 | Relative target port: 0x1 39 | Target device that contains addressed lu: 40 | designator type: NAA, code set: Binary 41 | transport: Serial Attached SCSI Protocol (SPL-4) 42 | 0x5000c5003011cb28 43 | designator type: SCSI name string, code set: UTF-8 44 | SCSI name string: 45 | naa.5000C5003011CB28 46 | 47 | Not all the hex files follow the "prepend sg_" pattern. Those hex files 48 | starting with 'nvme_' are examples of invoking NVMe commands with the 49 | sg_raw utility. 50 | 51 | Binary <--> Hexadecimal 52 | ----------------------- 53 | The vpd_zbdc.raw file is binary and was created by: 54 | sg_decode_sense --inhex=vpd_zbdc.hex --nodecode --write=vpd_zbdc.raw 55 | as an example of converting a file in ASCII hexadecimal byte oriented 56 | format to binary. 57 | 58 | Turning binary output into hexadecimal can be done several ways. For 59 | viewing in byte oriented ASCII hex these Unix commands can be used: 60 | od -t x1 vpd_zbdc.raw 61 | hexdump -C vpd_zbdc.raw 62 | 63 | Each line starts with a "input offset" which is a running count of 64 | bytes, starting at zero. The hexdump example shows an ASCII rendering 65 | of those 16 bytes to the right of each line. The sg_decode_sense utility 66 | may also be used: 67 | sg_decode_sense --binary=vpd_zbdc.raw -H 68 | sg_decode_sense --binary=vpd_zbdc.raw -HH 69 | 70 | The second form of sg_decode_sense appends an ASCII rendering of the 16 71 | bytes to the right of each line. 72 | 73 | When ASCII hexadecimal is being used as input to a utility in this 74 | package, the "input offset" at the start of each line (and the optional 75 | ASCII rendering to the right of each line) must not be given. 76 | That can be done with hexdump: 77 | hexdump -An -C -v vpd_zbdc.raw 78 | ^^^ 79 | That is a syntax error, there is no 'A' option <<<<<<<< check 80 | 81 | And the sg_decode_sense utility can do it with (with the --nodecode option): 82 | sg_decode_sense -N --binary=vpd_zbdc.raw -HHH 83 | That will print suitable lines of hexadecimal (16 bytes per line) to the 84 | console (stdout) To go the other way (i.e. hexadecimal to binary): 85 | sg_decode_sense -N --inhex=vpd_zbdc.hex --write=vpd_zbdc.bin 86 | 87 | 88 | Conclusion 89 | ---------- 90 | Users are encouraged to send the author any ASCII hex files for utilities 91 | that support --inhex and don't have hex data already. Special cases are 92 | also welcome. They help the author test this code. 93 | 94 | Douglas Gilbert 95 | 18th July 2022 96 | -------------------------------------------------------------------------------- /examples/sg_simple16.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include "sg_lib.h" 12 | #include "sg_io_linux.h" 13 | 14 | /* This program performs a READ_16 command as scsi mid-level support 15 | 16 byte commands from lk 2.4.15 16 | 17 | * Copyright (C) 2001-2018 D. Gilbert 18 | * This program is free software; you can redistribute it and/or modify 19 | * it under the terms of the GNU General Public License as published by 20 | * the Free Software Foundation; either version 2, or (at your option) 21 | * any later version. 22 | 23 | Invocation: sg_simple16 24 | 25 | Version 1.04 (20180218) 26 | 27 | */ 28 | 29 | #define READ16_REPLY_LEN 512 30 | #define READ16_CMD_LEN 16 31 | 32 | #define EBUFF_SZ 256 33 | 34 | int main(int argc, char * argv[]) 35 | { 36 | int sg_fd, k, ok; 37 | uint8_t r16_cdb [READ16_CMD_LEN] = 38 | {0x88, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0}; 39 | sg_io_hdr_t io_hdr; 40 | char * file_name = 0; 41 | char ebuff[EBUFF_SZ]; 42 | uint8_t inBuff[READ16_REPLY_LEN]; 43 | uint8_t sense_buffer[32]; 44 | 45 | for (k = 1; k < argc; ++k) { 46 | if (*argv[k] == '-') { 47 | printf("Unrecognized switch: %s\n", argv[k]); 48 | file_name = 0; 49 | break; 50 | } 51 | else if (0 == file_name) 52 | file_name = argv[k]; 53 | else { 54 | printf("too many arguments\n"); 55 | file_name = 0; 56 | break; 57 | } 58 | } 59 | if (0 == file_name) { 60 | printf("Usage: 'sg_simple16 '\n"); 61 | return 1; 62 | } 63 | 64 | if ((sg_fd = open(file_name, O_RDWR)) < 0) { 65 | snprintf(ebuff, EBUFF_SZ, 66 | "sg_simple16: error opening file: %s", file_name); 67 | perror(ebuff); 68 | return 1; 69 | } 70 | /* Just to be safe, check we have a new sg device by trying an ioctl */ 71 | if ((ioctl(sg_fd, SG_GET_VERSION_NUM, &k) < 0) || (k < 30000)) { 72 | printf("sg_simple16: %s doesn't seem to be an new sg device\n", 73 | file_name); 74 | close(sg_fd); 75 | return 1; 76 | } 77 | 78 | /* Prepare READ_16 command */ 79 | memset(&io_hdr, 0, sizeof(sg_io_hdr_t)); 80 | io_hdr.interface_id = 'S'; 81 | io_hdr.cmd_len = sizeof(r16_cdb); 82 | /* io_hdr.iovec_count = 0; */ /* memset takes care of this */ 83 | io_hdr.mx_sb_len = sizeof(sense_buffer); 84 | io_hdr.dxfer_direction = SG_DXFER_FROM_DEV; 85 | io_hdr.dxfer_len = READ16_REPLY_LEN; 86 | io_hdr.dxferp = inBuff; 87 | io_hdr.cmdp = r16_cdb; 88 | io_hdr.sbp = sense_buffer; 89 | io_hdr.timeout = 20000; /* 20000 millisecs == 20 seconds */ 90 | /* io_hdr.flags = 0; */ /* take defaults: indirect IO, etc */ 91 | /* io_hdr.pack_id = 0; */ 92 | /* io_hdr.usr_ptr = NULL; */ 93 | 94 | if (ioctl(sg_fd, SG_IO, &io_hdr) < 0) { 95 | perror("sg_simple16: Inquiry SG_IO ioctl error"); 96 | close(sg_fd); 97 | return 1; 98 | } 99 | 100 | /* now for the error processing */ 101 | ok = 0; 102 | switch (sg_err_category3(&io_hdr)) { 103 | case SG_LIB_CAT_CLEAN: 104 | ok = 1; 105 | break; 106 | case SG_LIB_CAT_RECOVERED: 107 | printf("Recovered error on READ_16, continuing\n"); 108 | ok = 1; 109 | break; 110 | default: /* won't bother decoding other categories */ 111 | sg_chk_n_print3("READ_16 command error", &io_hdr, 1); 112 | break; 113 | } 114 | 115 | if (ok) { /* output result if it is available */ 116 | printf("READ_16 duration=%u millisecs, resid=%d, msg_status=%d\n", 117 | io_hdr.duration, io_hdr.resid, (int)io_hdr.msg_status); 118 | } 119 | 120 | close(sg_fd); 121 | return 0; 122 | } 123 | -------------------------------------------------------------------------------- /testing/random_write_cp_verify.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | 4 | verbose=0 5 | force=0 6 | immediate="-i" 7 | my_name="random_write_cp_verify.sh" 8 | sdeb_s="scsi_debug" 9 | # for dd clones by this author, bs=BS is the logical block size 10 | bs=512 11 | # bpt is Blocks Per Transfer and BS*BPT will be the segment size 12 | # in bytes. Large copies are done a segment at a time. 13 | bpt=64 14 | # Other suitable dd clones are sg_dd (in main sg3_utils src directory 15 | # and ddpt in a package of that name. sgh_dd is in the testing 16 | # directory of the sg3_utils package and needs to be made by hand 17 | # (e.g. 'cd sg3_utils_src ; ./bootstrap ; ./configure ; make ; 18 | # cd testing ; make sgh_dd' 19 | ## dd_clone="/home/dougg/scsi/sg3_utils/svn/testing/sgh_dd" 20 | dd_clone="sg_dd" 21 | ## dd_clone="ddpt" 22 | 23 | usage() 24 | { 25 | echo "Usage: random_write_cp_verify [-f] [-h] [-v] [-w] " 26 | echo " where:" 27 | echo " -f, --force needed if or is not" 28 | echo " generated by the scsi_debug module" 29 | echo " -h, --help print usage message" 30 | echo " -v, --verbose more verbose output" 31 | echo " -w, --wait wait for each start to complete" 32 | echo " random data will be written to this device" 33 | echo " data on copied to this device" 34 | echo "" 35 | echo "Writes random data to first disk/device then copies that to second" 36 | echo "disk/device. Then it does a verify/compare of the two devices." 37 | echo "BEWARE: the contents of and will be DESTROYED." 38 | } 39 | 40 | # Additional command line options/operands can be added to or removed from 41 | # th SDP_OPTS array 42 | SDP_OPTS=( "bs=${bs}" "bpt=${bpt}" -v iflag=sgio oflag=sgio ) 43 | ##SDP_OPTS=( "bs=${bs}" "bpt=${bpt}" -v iflag=pt oflag=pt ) 44 | # echo "${SDP_OPTS[@]}" 45 | 46 | 47 | opt="$1" 48 | while test ! -z "$opt" -a -z "${opt##-*}"; do 49 | opt=${opt#-} 50 | case "$opt" in 51 | f|-force) force=$((${force} + 1)) ;; 52 | h|-help) usage ; exit 0 ;; 53 | v|-verbose) verbose=$((${verbose} + 1)) ;; 54 | w|-wait) immediate="" ;; 55 | *) echo "Unknown option: -$opt " ; echo "" ; usage ;exit 1 ;; 56 | esac 57 | shift 58 | opt="$1" 59 | done 60 | 61 | if [ $# -lt 2 ] 62 | then 63 | echo "Missing arguments ..." 64 | echo "" 65 | usage 66 | exit 1 67 | fi 68 | 69 | echo "verbose=${verbose}" 70 | 71 | if [ -d /sys/class/scsi_host ] && [ ! -w /sys/class/scsi_host ]; then 72 | echo "You need to run ${my_name} as root" 73 | exit 2 74 | fi 75 | 76 | INQ=$(sg_inq --maxlen=36 ${1} 2>/dev/null) 77 | if [ ${?} -ne 0 ]; then 78 | echo "unable to open ${1} with sg_inq" 79 | exit 80 | fi 81 | IPROD=$(echo "$INQ" | grep 'Product identification:' | sed 's/^[^:]*: \(.*\)$/\1/') 82 | if [ ${IPROD} != ${sdeb_s} ]; then 83 | if [ ${force} -lt 2 ]; then 84 | echo -n "need to give use scsi_debug device or use '--force' " 85 | echo "twice" 86 | exit 2 87 | fi 88 | fi 89 | INQ=$(sg_inq --maxlen=36 ${2} 2>/dev/null) 90 | if [ ${?} -ne 0 ]; then 91 | echo "unable to open ${2} with sg_inq" 92 | exit 93 | fi 94 | IPROD=$(echo "$INQ" | grep 'Product identification:' | sed 's/^[^:]*: \(.*\)$/\1/') 95 | if [ ${IPROD} != ${sdeb_s} ]; then 96 | if [ ${force} -lt 2 ]; then 97 | echo -n "need to give use scsi_debug device or use '--force' " 98 | echo "twice" 99 | exit 2 100 | fi 101 | fi 102 | 103 | # Write random data to $1 104 | echo ${dd_clone} iflag=random of=${1} "${SDP_OPTS[@]}" 105 | ${dd_clone} iflag=random of=${1} "${SDP_OPTS[@]}" 106 | if [ ${?} -ne 0 ]; then 107 | exit 108 | fi 109 | 110 | # Copy $1 to $2 111 | echo ${dd_clone} if=${1} of=${2} "${SDP_OPTS[@]}" 112 | ${dd_clone} if=${1} of=${2} "${SDP_OPTS[@]}" 113 | if [ ${?} -ne 0 ]; then 114 | exit 115 | fi 116 | 117 | # Compare/verify that $1 and $2 are the same. Reports miscompare 118 | # on first segment/lock/byte that isn't the same. 119 | echo ${dd_clone} --verify if=${1} of=${2} "${SDP_OPTS[@]}" 120 | ${dd_clone} --verify if=${1} of=${2} "${SDP_OPTS[@]}" 121 | if [ ${?} -ne 0 ]; then 122 | exit 123 | fi 124 | 125 | -------------------------------------------------------------------------------- /scripts/scsi_mandat: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # scsi_mandat 3 | # 4 | # Script to test compliance with SCSI mandatory commands. 5 | # The vintage is SPC-3 and SPC-4 (see www.t10.org). 6 | # 7 | # Coverage: 8 | # Command Standard/Draft (is mandatory in) 9 | # ------------------------------------------------------- 10 | # INQUIRY (standard) SCSI-2, SPC, SPC-2, SPC-3, SPC-4 11 | # INQUIRY (VPD pages 0, 0x83) SPC-2, SPC-3, SPC-4 12 | # REPORT LUNS SPC-3, SPC-4 13 | # TEST UNIT READY SCSI-2, SPC, SPC-2, SPC-3, SPC-4 14 | # REQUEST SENSE SCSI-2, SBC, SBC-2,3, MMC-4,5, SSC-2,3 15 | # SEND DIAGNOSTIC SBC, SBC-2,3, SSC-2,3 16 | # 17 | # This script uses utilities frim sg3_utils package (version 18 | # 1.21 or later) 19 | # 20 | # Douglas Gilbert 20131016 21 | 22 | 23 | log=0 24 | quiet=0 25 | verbose="" 26 | 27 | file_err=0 28 | inv_opcode=0 29 | illeg_req=0 30 | not_ready=0 31 | medium=0 32 | other_err=0 33 | recovered=0 34 | sanity=0 35 | syntax=0 36 | timeout=0 37 | unit_attention=0 38 | aborted_command=0 39 | 40 | ## total_err=0 41 | 42 | usage() 43 | { 44 | echo "Usage: scsi_mandat [-h] [-L] [-q] [-v] " 45 | echo " where: -h, --help print usage message" 46 | echo " -L, --log append stderr to 'scsi_mandat.err'" 47 | echo " -q, --quiet suppress some output" 48 | echo " -v, --verbose increase verbosity of output" 49 | echo "" 50 | echo "Check for mandatory SCSI command support" 51 | } 52 | 53 | 54 | opt="$1" 55 | while test ! -z "$opt" -a -z "${opt##-*}"; do 56 | opt=${opt#-} 57 | case "$opt" in 58 | h|-help) usage ; exit 0 ;; 59 | L|-log) let log=$log+1 ;; 60 | q|-quiet) let quiet=$quiet+1 ;; 61 | v|-verbose) verbose="-v" ;; 62 | vv) verbose="-vv" ;; 63 | vvv) verbose="-vvv" ;; 64 | *) echo "Unknown option: -$opt " ; exit 1 ;; 65 | esac 66 | shift 67 | opt="$1" 68 | done 69 | 70 | if [ $# -lt 1 ] 71 | then 72 | usage 73 | exit 1 74 | fi 75 | 76 | for command in "sg_inq" "sg_luns" "sg_turs" "sg_requests" "sg_vpd" \ 77 | "sg_vpd -i" "sg_senddiag -t" 78 | do 79 | if [ $quiet -eq 0 ] 80 | then echo "$command" $verbose "$1" 81 | fi 82 | 83 | if [ $verbose ] 84 | then 85 | if [ $log -eq 0 ] 86 | then 87 | $command $verbose "$1" 88 | else 89 | $command $verbose "$1" >> scsi_mandat.err 2>> scsi_mandat.err 90 | fi 91 | else 92 | if [ $log -eq 0 ] 93 | then 94 | $command "$1" > /dev/null 2>> /dev/null 95 | else 96 | $command "$1" > /dev/null 2>> scsi_mandat.err 97 | fi 98 | fi 99 | res=$? 100 | case "$res" in 101 | 0) ;; 102 | 1) echo " syntax error" ; let syntax=$syntax+1 ;; 103 | 2) echo " not ready" ; let not_ready=$not_ready+1 ;; 104 | 3) echo " medium error" ; let medium=$medium+1 ;; 105 | 5) echo " illegal request, general" ; let illeg_req=$illeg_req+1 ;; 106 | 6) echo " unit attention" ; let unit_attention=$unit_attention+1 ;; 107 | 9) echo " illegal request, invalid opcode" ; let inv_opcode=$inv_opcode+1 ;; 108 | 11) echo " aborted command" ; let aborted_command=$aborted_command+1 ;; 109 | 15) echo " file error with $1 " ; let file_err=$file_err+1 ;; 110 | 20) echo " no sense" ; let other_err=$other_err+1 ;; 111 | 21) echo " recovered error" ; let recovered=$recovered+1 ;; 112 | 33) echo " timeout" ; let timeout=$timeout+1 ;; 113 | 97) echo " response fails sanity" ; let sanity=$sanity+1 ;; 114 | 98) echo " other SCSI error" ; let other_err=$other_err+1 ;; 115 | 99) echo " other error" ; let other_err=$other_err+1 ;; 116 | *) echo " unknown exit status for sg_inq: $res" ; let other_err=$other_err+1 ;; 117 | esac 118 | done 119 | 120 | echo "" 121 | let total_bad_err=$file_err+$inv_opcode+$illeg_req+$medium+$aborted_command 122 | let total_bad_err+=$other_err+$recovered+$sanity+$syntax+$timeout 123 | 124 | let total_allow_err=$not_ready+$unit_attention 125 | 126 | echo "total number of bad errors: $total_bad_err " 127 | 128 | if [ $total_allow_err -gt 0 ] 129 | then 130 | echo "total number of allowable errors: $total_allow_err " 131 | fi 132 | 133 | exit $total_bad_err 134 | --------------------------------------------------------------------------------