aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorDouglas Gilbert <dgilbert@interlog.com>2014-05-27 23:26:04 +0000
committerDouglas Gilbert <dgilbert@interlog.com>2014-05-27 23:26:04 +0000
commit4d770f100b237146adc51e9f4bdd194e83252d50 (patch)
treefa2f096759f5d40aadd57d15e3798fb2a796b859 /src
parenteebe59ce63d30da476a04e294a3c06ff5ae20aab (diff)
downloadsg3_utils-4d770f100b237146adc51e9f4bdd194e83252d50.tar.gz
new utils: sg_rep_zones+sg_reset_wp; new Linux udev scripts; sg_inq --export work; sg_logs lto5+6 work
git-svn-id: https://svn.bingwo.ca/repos/sg3_utils/trunk@584 6180dd3e-e324-4e3e-922d-17de1ae2f315
Diffstat (limited to 'src')
-rw-r--r--src/Makefile.am99
-rw-r--r--src/Makefile.in59
-rw-r--r--src/sg_inq.c116
-rw-r--r--src/sg_inq_data.c2
-rw-r--r--src/sg_logs.c196
-rw-r--r--src/sg_rep_zones.c451
-rw-r--r--src/sg_reset_wp.c257
-rw-r--r--src/sg_vpd.c10
8 files changed, 981 insertions, 209 deletions
diff --git a/src/Makefile.am b/src/Makefile.am
index b4f2eb7a..50b1fa3b 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -13,11 +13,12 @@ bin_PROGRAMS = \
sg_ident sginfo sg_inq sg_logs sg_luns sg_map26 sg_map sgm_dd \
sg_modes sg_opcodes sgp_dd sg_persist sg_prevent sg_raw sg_rbuf \
sg_rdac sg_read sg_readcap sg_read_block_limits sg_read_buffer \
- sg_read_long sg_reassign sg_referrals sg_requests sg_reset sg_rmsn \
- sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
- sg_sat_set_features sg_scan sg_senddiag sg_ses sg_start sg_stpg \
- sg_sync sg_test_rwbuf sg_turs sg_unmap sg_verify sg_vpd \
- sg_write_buffer sg_write_long sg_write_same sg_wr_mode sg_xcopy
+ sg_read_long sg_reassign sg_referrals sg_rep_zones sg_requests \
+ sg_reset sg_reset_wp sg_rmsn sg_rtpg sg_safte sg_sanitize \
+ sg_sat_identify sg_sat_phy_event sg_sat_set_features sg_scan \
+ sg_senddiag sg_ses sg_start sg_stpg sg_sync sg_test_rwbuf sg_turs \
+ sg_unmap sg_verify sg_vpd sg_write_buffer sg_write_long \
+ sg_write_same sg_wr_mode sg_xcopy
distclean-local:
rm -f sg_scan.c
@@ -35,11 +36,11 @@ bin_PROGRAMS = \
sg_get_lba_status sg_ident sg_inq sg_logs sg_luns sg_modes \
sg_opcodes sg_persist sg_prevent sg_raw sg_rdac sg_readcap \
sg_read_block_limits sg_read_buffer sg_read_long sg_reassign \
- sg_referrals sg_requests sg_rmsn sg_rtpg sg_safte sg_sanitize \
- sg_sat_identify sg_sat_phy_event sg_sat_set_features sg_scan \
- sg_senddiag sg_ses sg_start sg_stpg sg_sync sg_turs sg_unmap \
- sg_verify sg_vpd sg_write_buffer sg_write_long sg_write_same \
- sg_wr_mode
+ sg_referrals sg_rep_zones sg_requests sg_reset_wp sg_rmsn \
+ sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
+ sg_sat_set_features sg_scan sg_senddiag sg_ses sg_start sg_stpg \
+ sg_sync sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer \
+ sg_write_long sg_write_same sg_wr_mode
distclean-local:
rm -f sg_scan.c
@@ -53,15 +54,15 @@ endif
if OS_WIN32_CYGWIN
bin_PROGRAMS = \
- sg_compare_and_write \
- sg_decode_sense sg_format sg_get_config sg_get_lba_status sg_ident \
- sg_inq sg_logs sg_luns sg_modes sg_opcodes sg_persist \
- sg_prevent sg_raw sg_rdac sg_readcap sg_read_block_limits \
- sg_read_buffer sg_read_long sg_reassign sg_referrals sg_requests \
- sg_rmsn sg_rtpg sg_safte sg_sanitize sg_sat_identify \
- sg_sat_phy_event sg_sat_set_features sg_scan sg_senddiag sg_ses \
- sg_start sg_stpg sg_sync sg_turs sg_unmap sg_verify sg_vpd \
- sg_write_buffer sg_write_long sg_write_same sg_wr_mode
+ sg_compare_and_write sg_decode_sense sg_format sg_get_config \
+ sg_get_lba_status sg_ident sg_inq sg_logs sg_luns sg_modes \
+ sg_opcodes sg_persist sg_prevent sg_raw sg_rdac sg_readcap \
+ sg_read_block_limits sg_read_buffer sg_read_long sg_reassign \
+ sg_referrals sg_rep_zones sg_requests sg_reset_wp sg_rmsn \
+ sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
+ sg_sat_set_features sg_scan sg_senddiag sg_ses sg_start sg_stpg \
+ sg_sync sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer \
+ sg_write_long sg_write_same sg_wr_mode
distclean-local:
rm -f sg_scan.c
@@ -75,15 +76,15 @@ endif
if OS_FREEBSD
bin_PROGRAMS = \
- sg_compare_and_write \
- sg_decode_sense sg_format sg_get_config sg_get_lba_status sg_ident \
- sg_inq sg_logs sg_luns sg_modes sg_opcodes sg_persist \
- sg_prevent sg_raw sg_rdac sg_readcap sg_read_block_limits \
- sg_read_buffer sg_read_long sg_reassign sg_referrals sg_requests \
- sg_rmsn sg_rtpg sg_safte sg_sanitize sg_sat_identify \
- sg_sat_phy_event sg_sat_set_features sg_senddiag sg_ses sg_start \
- sg_stpg sg_sync sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer \
- sg_write_long sg_write_same sg_wr_mode
+ sg_compare_and_write sg_decode_sense sg_format sg_get_config \
+ sg_get_lba_status sg_ident sg_inq sg_logs sg_luns sg_modes \
+ sg_opcodes sg_persist sg_prevent sg_raw sg_rdac sg_readcap
+ sg_read_block_limits sg_read_buffer sg_read_long sg_reassign \
+ sg_referrals sg_rep_zones sg_requests sg_reset_wp sg_rmsn \
+ sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
+ sg_sat_set_features sg_senddiag sg_ses sg_start sg_stpg sg_sync \
+ sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer sg_write_long \
+ sg_write_same sg_wr_mode
endif
@@ -91,15 +92,15 @@ endif
if OS_SOLARIS
bin_PROGRAMS = \
- sg_compare_and_write \
- sg_decode_sense sg_format sg_get_config sg_get_lba_status sg_ident \
- sg_inq sg_logs sg_luns sg_modes sg_opcodes sg_persist \
- sg_prevent sg_raw sg_rdac sg_readcap sg_read_block_limits \
- sg_read_buffer sg_read_long sg_reassign sg_referrals sg_requests \
- sg_rmsn sg_rtpg sg_safte sg_sanitize sg_sat_identify \
- sg_sat_phy_event sg_sat_set_features sg_senddiag sg_ses sg_start \
- sg_stpg sg_sync sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer \
- sg_write_long sg_write_same sg_wr_mode
+ sg_compare_and_write sg_decode_sense sg_format sg_get_config \
+ sg_get_lba_status sg_ident sg_inq sg_logs sg_luns sg_modes \
+ sg_opcodes sg_persist sg_prevent sg_raw sg_rdac sg_readcap \
+ sg_read_block_limits sg_read_buffer sg_read_long sg_reassign \
+ sg_referrals sg_rep_zones sg_requests sg_reset_wp sg_rmsn \
+ sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
+ sg_sat_set_features sg_senddiag sg_ses sg_start sg_stpg sg_sync \
+ sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer sg_write_long \
+ sg_write_same sg_wr_mode
endif
@@ -107,15 +108,15 @@ endif
if OS_OSF
bin_PROGRAMS = \
- sg_compare_and_write \
- sg_decode_sense sg_format sg_get_config sg_get_lba_status sg_ident \
- sg_inq sg_logs sg_luns sg_modes sg_opcodes sg_persist \
- sg_prevent sg_raw sg_rdac sg_readcap sg_read_block_limits \
- sg_read_buffer sg_read_long sg_reassign sg_referrals sg_requests \
- sg_rmsn sg_rtpg sg_safte sg_sanitize sg_sat_identify \
- sg_sat_phy_event sg_sat_set_features sg_senddiag sg_ses sg_start \
- sg_stpg sg_sync sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer \
- sg_write_long sg_write_same sg_wr_mode
+ sg_compare_and_write sg_decode_sense sg_format sg_get_config \
+ sg_get_lba_status sg_ident sg_inq sg_logs sg_luns sg_modes \
+ sg_opcodes sg_persist sg_prevent sg_raw sg_rdac sg_readcap \
+ sg_read_block_limits sg_read_buffer sg_read_long sg_reassign \
+ sg_referrals sg_rep_zones sg_requests sg_reset_wp sg_rmsn \
+ sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
+ sg_sat_set_features sg_senddiag sg_ses sg_start sg_stpg sg_sync \
+ sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer sg_write_long \
+ sg_write_same sg_wr_mode
endif
@@ -297,3 +298,9 @@ sg_copy_results_LDADD = ../lib/libsgutils2.la @os_libs@
sg_compare_and_write_SOURCES = sg_compare_and_write.c
sg_compare_and_write_LDADD = ../lib/libsgutils2.la @os_libs@
+
+sg_rep_zones_SOURCES = sg_rep_zones.c
+sg_rep_zones_LDADD = ../lib/libsgutils2.la @os_libs@
+
+sg_reset_wp_SOURCES = sg_reset_wp.c
+sg_reset_wp_LDADD = ../lib/libsgutils2.la @os_libs@
diff --git a/src/Makefile.in b/src/Makefile.in
index b7f3e00a..0c496526 100644
--- a/src/Makefile.in
+++ b/src/Makefile.in
@@ -99,7 +99,9 @@ host_triplet = @host@
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_read_long$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_reassign$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_referrals$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_rep_zones$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_requests$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_reset_wp$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_rmsn$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_rtpg$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_FALSE@@OS_WIN32_MINGW_TRUE@ sg_safte$(EXEEXT) \
@@ -142,7 +144,9 @@ host_triplet = @host@
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_read_long$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_reassign$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_referrals$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_rep_zones$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_requests$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_reset_wp$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_rmsn$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_rtpg$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_FALSE@@OS_WIN32_CYGWIN_TRUE@ sg_safte$(EXEEXT) \
@@ -185,7 +189,9 @@ host_triplet = @host@
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_read_long$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_reassign$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_referrals$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_rep_zones$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_requests$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_reset_wp$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_rmsn$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_rtpg$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_FALSE@@OS_SOLARIS_TRUE@ sg_safte$(EXEEXT) \
@@ -227,7 +233,9 @@ host_triplet = @host@
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_read_long$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_reassign$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_referrals$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_rep_zones$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_requests$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_reset_wp$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_rmsn$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_rtpg$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_FALSE@@OS_OSF_TRUE@ sg_safte$(EXEEXT) \
@@ -279,8 +287,10 @@ host_triplet = @host@
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_read_long$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_reassign$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_referrals$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_rep_zones$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_requests$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_reset$(EXEEXT) \
+@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_reset_wp$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_rmsn$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_rtpg$(EXEEXT) \
@OS_FREEBSD_FALSE@@OS_LINUX_TRUE@ sg_safte$(EXEEXT) \
@@ -312,22 +322,7 @@ host_triplet = @host@
@OS_FREEBSD_TRUE@ sg_luns$(EXEEXT) sg_modes$(EXEEXT) \
@OS_FREEBSD_TRUE@ sg_opcodes$(EXEEXT) sg_persist$(EXEEXT) \
@OS_FREEBSD_TRUE@ sg_prevent$(EXEEXT) sg_raw$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_rdac$(EXEEXT) sg_readcap$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_read_block_limits$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_read_buffer$(EXEEXT) sg_read_long$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_reassign$(EXEEXT) sg_referrals$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_requests$(EXEEXT) sg_rmsn$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_rtpg$(EXEEXT) sg_safte$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_sanitize$(EXEEXT) sg_sat_identify$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_sat_phy_event$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_sat_set_features$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_senddiag$(EXEEXT) sg_ses$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_start$(EXEEXT) sg_stpg$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_sync$(EXEEXT) sg_turs$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_unmap$(EXEEXT) sg_verify$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_vpd$(EXEEXT) sg_write_buffer$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_write_long$(EXEEXT) sg_write_same$(EXEEXT) \
-@OS_FREEBSD_TRUE@ sg_wr_mode$(EXEEXT)
+@OS_FREEBSD_TRUE@ sg_rdac$(EXEEXT) sg_readcap$(EXEEXT)
subdir = src
DIST_COMMON = $(srcdir)/Makefile.in $(srcdir)/Makefile.am \
$(top_srcdir)/depcomp
@@ -429,12 +424,18 @@ sg_reassign_DEPENDENCIES = ../lib/libsgutils2.la
am_sg_referrals_OBJECTS = sg_referrals.$(OBJEXT)
sg_referrals_OBJECTS = $(am_sg_referrals_OBJECTS)
sg_referrals_DEPENDENCIES = ../lib/libsgutils2.la
+am_sg_rep_zones_OBJECTS = sg_rep_zones.$(OBJEXT)
+sg_rep_zones_OBJECTS = $(am_sg_rep_zones_OBJECTS)
+sg_rep_zones_DEPENDENCIES = ../lib/libsgutils2.la
am_sg_requests_OBJECTS = sg_requests.$(OBJEXT)
sg_requests_OBJECTS = $(am_sg_requests_OBJECTS)
sg_requests_DEPENDENCIES = ../lib/libsgutils2.la
am_sg_reset_OBJECTS = sg_reset.$(OBJEXT)
sg_reset_OBJECTS = $(am_sg_reset_OBJECTS)
sg_reset_DEPENDENCIES =
+am_sg_reset_wp_OBJECTS = sg_reset_wp.$(OBJEXT)
+sg_reset_wp_OBJECTS = $(am_sg_reset_wp_OBJECTS)
+sg_reset_wp_DEPENDENCIES = ../lib/libsgutils2.la
am_sg_rmsn_OBJECTS = sg_rmsn.$(OBJEXT)
sg_rmsn_OBJECTS = $(am_sg_rmsn_OBJECTS)
sg_rmsn_DEPENDENCIES = ../lib/libsgutils2.la
@@ -559,7 +560,8 @@ SOURCES = $(sg_compare_and_write_SOURCES) $(sg_copy_results_SOURCES) \
$(sg_read_block_limits_SOURCES) $(sg_read_buffer_SOURCES) \
$(sg_read_long_SOURCES) $(sg_readcap_SOURCES) \
$(sg_reassign_SOURCES) $(sg_referrals_SOURCES) \
- $(sg_requests_SOURCES) $(sg_reset_SOURCES) $(sg_rmsn_SOURCES) \
+ $(sg_rep_zones_SOURCES) $(sg_requests_SOURCES) \
+ $(sg_reset_SOURCES) $(sg_reset_wp_SOURCES) $(sg_rmsn_SOURCES) \
$(sg_rtpg_SOURCES) $(sg_safte_SOURCES) $(sg_sanitize_SOURCES) \
$(sg_sat_identify_SOURCES) $(sg_sat_phy_event_SOURCES) \
$(sg_sat_set_features_SOURCES) $(sg_scan_SOURCES) \
@@ -583,7 +585,8 @@ DIST_SOURCES = $(sg_compare_and_write_SOURCES) \
$(sg_read_block_limits_SOURCES) $(sg_read_buffer_SOURCES) \
$(sg_read_long_SOURCES) $(sg_readcap_SOURCES) \
$(sg_reassign_SOURCES) $(sg_referrals_SOURCES) \
- $(sg_requests_SOURCES) $(sg_reset_SOURCES) $(sg_rmsn_SOURCES) \
+ $(sg_rep_zones_SOURCES) $(sg_requests_SOURCES) \
+ $(sg_reset_SOURCES) $(sg_reset_wp_SOURCES) $(sg_rmsn_SOURCES) \
$(sg_rtpg_SOURCES) $(sg_safte_SOURCES) $(sg_sanitize_SOURCES) \
$(sg_sat_identify_SOURCES) $(sg_sat_phy_event_SOURCES) \
$(sg_sat_set_features_SOURCES) $(sg_scan_SOURCES) \
@@ -855,6 +858,10 @@ sg_copy_results_SOURCES = sg_copy_results.c
sg_copy_results_LDADD = ../lib/libsgutils2.la @os_libs@
sg_compare_and_write_SOURCES = sg_compare_and_write.c
sg_compare_and_write_LDADD = ../lib/libsgutils2.la @os_libs@
+sg_rep_zones_SOURCES = sg_rep_zones.c
+sg_rep_zones_LDADD = ../lib/libsgutils2.la @os_libs@
+sg_reset_wp_SOURCES = sg_reset_wp.c
+sg_reset_wp_LDADD = ../lib/libsgutils2.la @os_libs@
all: all-am
.SUFFIXES:
@@ -1051,6 +1058,10 @@ sg_referrals$(EXEEXT): $(sg_referrals_OBJECTS) $(sg_referrals_DEPENDENCIES) $(EX
@rm -f sg_referrals$(EXEEXT)
$(AM_V_CCLD)$(LINK) $(sg_referrals_OBJECTS) $(sg_referrals_LDADD) $(LIBS)
+sg_rep_zones$(EXEEXT): $(sg_rep_zones_OBJECTS) $(sg_rep_zones_DEPENDENCIES) $(EXTRA_sg_rep_zones_DEPENDENCIES)
+ @rm -f sg_rep_zones$(EXEEXT)
+ $(AM_V_CCLD)$(LINK) $(sg_rep_zones_OBJECTS) $(sg_rep_zones_LDADD) $(LIBS)
+
sg_requests$(EXEEXT): $(sg_requests_OBJECTS) $(sg_requests_DEPENDENCIES) $(EXTRA_sg_requests_DEPENDENCIES)
@rm -f sg_requests$(EXEEXT)
$(AM_V_CCLD)$(LINK) $(sg_requests_OBJECTS) $(sg_requests_LDADD) $(LIBS)
@@ -1059,6 +1070,10 @@ sg_reset$(EXEEXT): $(sg_reset_OBJECTS) $(sg_reset_DEPENDENCIES) $(EXTRA_sg_reset
@rm -f sg_reset$(EXEEXT)
$(AM_V_CCLD)$(LINK) $(sg_reset_OBJECTS) $(sg_reset_LDADD) $(LIBS)
+sg_reset_wp$(EXEEXT): $(sg_reset_wp_OBJECTS) $(sg_reset_wp_DEPENDENCIES) $(EXTRA_sg_reset_wp_DEPENDENCIES)
+ @rm -f sg_reset_wp$(EXEEXT)
+ $(AM_V_CCLD)$(LINK) $(sg_reset_wp_OBJECTS) $(sg_reset_wp_LDADD) $(LIBS)
+
sg_rmsn$(EXEEXT): $(sg_rmsn_OBJECTS) $(sg_rmsn_DEPENDENCIES) $(EXTRA_sg_rmsn_DEPENDENCIES)
@rm -f sg_rmsn$(EXEEXT)
$(AM_V_CCLD)$(LINK) $(sg_rmsn_OBJECTS) $(sg_rmsn_LDADD) $(LIBS)
@@ -1198,8 +1213,10 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_readcap.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_reassign.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_referrals.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_rep_zones.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_requests.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_reset.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_reset_wp.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_rmsn.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_rtpg.Po@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sg_safte.Po@am__quote@
@@ -1480,6 +1497,12 @@ uninstall-am: uninstall-binPROGRAMS
@OS_WIN32_CYGWIN_TRUE@sg_scan.c : sg_scan.c.win32
@OS_WIN32_CYGWIN_TRUE@ cp sg_scan.c.win32 sg_scan.c
+@OS_FREEBSD_TRUE@ sg_read_block_limits sg_read_buffer sg_read_long sg_reassign \
+@OS_FREEBSD_TRUE@ sg_referrals sg_rep_zones sg_requests sg_reset_wp sg_rmsn \
+@OS_FREEBSD_TRUE@ sg_rtpg sg_safte sg_sanitize sg_sat_identify sg_sat_phy_event \
+@OS_FREEBSD_TRUE@ sg_sat_set_features sg_senddiag sg_ses sg_start sg_stpg sg_sync \
+@OS_FREEBSD_TRUE@ sg_turs sg_unmap sg_verify sg_vpd sg_write_buffer sg_write_long \
+@OS_FREEBSD_TRUE@ sg_write_same sg_wr_mode
# Tell versions [3.59,3.63) of GNU make to not export all variables.
# Otherwise a system limit (for SysV at least) may be exceeded.
diff --git a/src/sg_inq.c b/src/sg_inq.c
index 642d75d5..3d83ba41 100644
--- a/src/sg_inq.c
+++ b/src/sg_inq.c
@@ -41,7 +41,7 @@
#include "sg_cmds_basic.h"
#include "sg_pt.h"
-static const char * version_str = "1.38 20140518"; /* SPC-4 rev 37 */
+static const char * version_str = "1.39 20140527"; /* SPC-4 rev 37 */
/* INQUIRY notes:
* It is recommended that the initial allocation length given to a
@@ -1765,7 +1765,7 @@ decode_dev_ids(const char * leadin, unsigned char * buff, int len, int do_hex)
}
static void
-export_dev_ids(unsigned char * buff, int len)
+export_dev_ids(unsigned char * buff, int len, int verbose)
{
int u, j, m, id_len, c_set, assoc, desig_type, i_len;
int off, d_id, naa, k, p_id;
@@ -1795,9 +1795,10 @@ export_dev_ids(unsigned char * buff, int len)
i_len = ucp[3];
id_len = i_len + 4;
if ((off + id_len) > len) {
- pr2serr("Device Identification VPD page error: designator "
- "length longer than\n remaining response length=%d\n",
- (len - off));
+ if (verbose)
+ pr2serr("Device Identification VPD page error: designator "
+ "length longer than\n remaining response "
+ "length=%d\n", (len - off));
return;
}
ip = ucp + 4;
@@ -1817,7 +1818,8 @@ export_dev_ids(unsigned char * buff, int len)
assoc_str = "TARGET";
break;
default:
- pr2serr(" Invalid association %d\n", assoc);
+ if (verbose)
+ pr2serr(" Invalid association %d\n", assoc);
return;
}
switch (desig_type) {
@@ -1837,6 +1839,10 @@ export_dev_ids(unsigned char * buff, int len)
if ((2 == c_set) || (3 == c_set)) {
k = encode_whitespaces(ip, i_len);
printf("%.*s\n", k, ip);
+ if (!memcmp(ip, "ATA_", 4)) {
+ printf("SCSI_IDENT_%s_ATA=%.*s\n", assoc_str,
+ k - 4, ip + 4);
+ }
} else {
for (m = 0; m < i_len; ++m)
printf("%02x", (unsigned int)ip[m]);
@@ -1845,8 +1851,10 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 2: /* EUI-64 based */
if (1 != c_set) {
- pr2serr(" << expected binary code_set (1)>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << expected binary code_set (1)>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
printf("SCSI_IDENT_%s_EUI64=", assoc_str);
@@ -1856,21 +1864,27 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 3: /* NAA */
if (1 != c_set) {
- pr2serr(" << expected binary code_set (1)>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << expected binary code_set (1)>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
naa = (ip[0] >> 4) & 0xff;
if ((naa < 2) || (naa > 6) || (4 == naa)) {
- pr2serr(" << unexpected naa [0x%x]>>\n", naa);
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << unexpected naa [0x%x]>>\n", naa);
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
if (6 != naa) {
if (8 != i_len) {
- pr2serr(" << unexpected NAA 2 identifier "
- "length: 0x%x>>\n", i_len);
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << unexpected NAA 2 identifier "
+ "length: 0x%x>>\n", i_len);
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
printf("SCSI_IDENT_%s_NAA=", assoc_str);
@@ -1879,9 +1893,11 @@ export_dev_ids(unsigned char * buff, int len)
printf("\n");
} else { /* NAA IEEE Registered extended */
if (16 != i_len) {
- pr2serr(" << unexpected NAA 6 identifier "
- "length: 0x%x>>\n", i_len);
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << unexpected NAA 6 identifier "
+ "length: 0x%x>>\n", i_len);
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
printf("SCSI_IDENT_%s_NAA=", assoc_str);
@@ -1892,9 +1908,11 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 4: /* Relative target port */
if ((1 != c_set) || (1 != assoc) || (4 != i_len)) {
- pr2serr(" << expected binary code_set, target "
- "port association, length 4>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << expected binary code_set, target "
+ "port association, length 4>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
d_id = ((ip[2] << 8) | ip[3]);
@@ -1902,9 +1920,11 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 5: /* (primary) Target port group */
if ((1 != c_set) || (1 != assoc) || (4 != i_len)) {
- pr2serr(" << expected binary code_set, target "
- "port association, length 4>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << expected binary code_set, target "
+ "port association, length 4>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
d_id = ((ip[2] << 8) | ip[3]);
@@ -1912,9 +1932,11 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 6: /* Logical unit group */
if ((1 != c_set) || (0 != assoc) || (4 != i_len)) {
- pr2serr(" << expected binary code_set, logical "
- "unit association, length 4>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << expected binary code_set, logical "
+ "unit association, length 4>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
d_id = ((ip[2] << 8) | ip[3]);
@@ -1922,9 +1944,11 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 7: /* MD5 logical unit identifier */
if ((1 != c_set) || (0 != assoc)) {
- pr2serr(" << expected binary code_set, logical "
- "unit association>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << expected binary code_set, logical "
+ "unit association>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
printf("SCSI_IDENT_%s_MD5=", assoc_str);
@@ -1932,8 +1956,10 @@ export_dev_ids(unsigned char * buff, int len)
break;
case 8: /* SCSI name string */
if (3 != c_set) {
- pr2serr(" << expected UTF-8 code_set>>\n");
- dStrHexErr((const char *)ip, i_len, -1);
+ if (verbose) {
+ pr2serr(" << expected UTF-8 code_set>>\n");
+ dStrHexErr((const char *)ip, i_len, -1);
+ }
break;
}
printf("SCSI_IDENT_%s_NAME=%.*s\n", assoc_str, i_len,
@@ -1942,9 +1968,11 @@ export_dev_ids(unsigned char * buff, int len)
case 9: /* Protocol specific port identifier */
if (TPROTO_UAS == p_id) {
if ((4 != i_len) || (1 != assoc)) {
- pr2serr(" << UAS (USB) expected target "
- "port association>>\n");
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << UAS (USB) expected target "
+ "port association>>\n");
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
printf("SCSI_IDENT_%s_UAS_DEVICE_ADDRESS=0x%x\n", assoc_str,
@@ -1953,9 +1981,11 @@ export_dev_ids(unsigned char * buff, int len)
ip[2]);
} else if (TPROTO_SOP == p_id) {
if ((4 != i_len) && (8 != i_len)) { /* spc4r36h confused */
- pr2serr(" << SOP (PCIe) descriptor "
- "length=%d >>\n", i_len);
- dStrHexErr((const char *)ip, i_len, 0);
+ if (verbose) {
+ pr2serr(" << SOP (PCIe) descriptor "
+ "length=%d >>\n", i_len);
+ dStrHexErr((const char *)ip, i_len, 0);
+ }
break;
}
printf("SCSI_IDENT_%s_SOP_ROUTING_ID=0x%x\n", assoc_str,
@@ -1966,12 +1996,14 @@ export_dev_ids(unsigned char * buff, int len)
}
break;
default: /* reserved */
- pr2serr(" reserved designator=0x%x\n", desig_type);
- dStrHexErr((const char *)ip, i_len, -1);
+ if (verbose) {
+ pr2serr(" reserved designator=0x%x\n", desig_type);
+ dStrHexErr((const char *)ip, i_len, -1);
+ }
break;
}
}
- if (-2 == u)
+ if (-2 == u && verbose)
pr2serr("Device identification VPD page error: "
"around offset=%d\n", off);
}
@@ -3233,7 +3265,7 @@ vpd_decode(int sg_fd, const struct opts_t * op, int inhex_len)
else if (op->do_hex > 2)
dStrHex((const char *)rp, len, -1);
else if (op->do_export)
- export_dev_ids(rp + 4, len - 4);
+ export_dev_ids(rp + 4, len - 4, op->do_verbose);
else
decode_id_vpd(rp, len, op->do_hex);
break;
diff --git a/src/sg_inq_data.c b/src/sg_inq_data.c
index 2dc08a7f..77dea3a5 100644
--- a/src/sg_inq_data.c
+++ b/src/sg_inq_data.c
@@ -30,7 +30,7 @@ const char * sg_ansi_version_arr[] =
"SPC-2",
"SPC-3",
"SPC-4",
- "reserved [7h]",
+ "SPC-5",
"ecma=1, [8h]",
"ecma=1, [9h]",
"ecma=1, [Ah]",
diff --git a/src/sg_logs.c b/src/sg_logs.c
index ee539116..81fd8e94 100644
--- a/src/sg_logs.c
+++ b/src/sg_logs.c
@@ -28,7 +28,7 @@
#include "sg_cmds_basic.h"
#include "sg_pt.h" /* needed for scsi_pt_win32_direct() */
-static const char * version_str = "1.23 20140518"; /* spc4r37 + sbc4r01 */
+static const char * version_str = "1.24 20140523"; /* spc4r37 + sbc4r01 */
#define MX_ALLOC_LEN (0xfffc)
#define SHORT_RESP_LEN 128
@@ -1018,11 +1018,11 @@ show_page_name(int pg_code, int subpg_code,
if (0x15 == pg_code) {
switch (inq_dat->peripheral_type) {
case PDT_DISK: case PDT_WO: case PDT_OPTICAL: case PDT_RBC:
- if (0 == subpg_code) {
- printf("%sBackground scan results (sbc-3)\n", b);
+ if (0 == subpg_code) { /* introduced: SBC-3 */
+ printf("%sBackground scan results\n", b);
return;
- } else if (1 == subpg_code) {
- printf("%sPending defects (sbc-4)\n", b);
+ } else if (1 == subpg_code) { /* introduced: SBC-4 */
+ printf("%sPending defects\n", b);
return;
}
break;
@@ -1041,21 +1041,21 @@ show_page_name(int pg_code, int subpg_code,
/* disk (direct access) type devices */
{
switch (pg_code) {
- case FORMAT_STATUS_LPAGE:
- printf("%sFormat status (sbc-2)\n", b);
+ case FORMAT_STATUS_LPAGE: /* introduced: SBC-2 */
+ printf("%sFormat status\n", b);
break;
- case LB_PROV_LPAGE: /* 0xc */
- printf("%sLogical block provisioning (sbc-3)\n", b);
+ case LB_PROV_LPAGE: /* 0xc introduced: SBC-3 */
+ printf("%sLogical block provisioning\n", b);
break;
/* case 0x15: has subpage in sbc4 */
- case SOLID_STATE_MEDIA_LPAGE: /* 0x11 */
- printf("%sSolid state media (sbc-3)\n", b);
+ case SOLID_STATE_MEDIA_LPAGE: /* 0x11 introduced: SBC-3 */
+ printf("%sSolid state media\n", b);
break;
- case SAT_ATA_RESULTS_LPAGE:
- printf("%sATA pass-through results (sat-2)\n", b);
+ case SAT_ATA_RESULTS_LPAGE: /* introduced: SAT-2 */
+ printf("%sATA pass-through results (sat)\n", b);
break;
- case 0x17:
- printf("%sNon-volatile cache (sbc-2)\n", b);
+ case 0x17: /* introduced: SBC-2 */
+ printf("%sNon-volatile cache\n", b);
break;
case 0x30:
printf("%sPerformance counters (Hitachi)\n", b);
@@ -1076,72 +1076,75 @@ show_page_name(int pg_code, int subpg_code,
/* tape (streaming) and printer (obsolete) devices */
{
switch (pg_code) {
- case 0xc:
- printf("%sSequential access device (ssc-2)\n", b);
+ case 0xc: /* introduced: SSC-2 */
+ printf("%sSequential access device\n", b);
break;
- case 0x11:
- printf("%sDT Device status (ssc-3)\n", b);
+ case 0x11: /* introduced: SSC-3 */
+ printf("%sDT Device status\n", b);
break;
- case 0x12:
- printf("%sTape alert response (ssc-3)\n", b);
+ case 0x12: /* introduced: SSC-3 */
+ printf("%sTape alert response\n", b);
break;
- case 0x13:
- printf("%sRequested recovery (ssc-3)\n", b);
+ case 0x13: /* introduced: SSC-3 */
+ printf("%sRequested recovery\n", b);
break;
- case 0x14:
- printf("%sDevice statistics (ssc-3)\n", b);
+ case 0x14: /* introduced: SSC-3 */
+ printf("%sDevice statistics\n", b);
break;
- case 0x16:
- printf("%sTape diagnostic (ssc-3)\n", b);
+ case 0x16: /* introduced: SSC-3 */
+ printf("%sTape diagnostic\n", b);
break;
- case 0x17:
- printf("%sVolume statistics (ssc-4)\n", b);
+ case 0x17: /* introduced: SSC-4 */
+ printf("%sVolume statistics\n", b);
break;
- case 0x1b:
- printf("%sData compression (ssc-4)\n", b);
+ case 0x1b: /* introduced: SSC-4 */
+ printf("%sData compression\n", b);
break;
- case 0x2d:
- printf("%sCurrent service information (ssc-3)\n", b);
+ case 0x2d: /* introduced: SSC-3 */
+ printf("%sCurrent service information\n", b);
break;
- case TAPE_ALERT_LPAGE:
- printf("%sTapeAlert (ssc-2)\n", b);
+ case TAPE_ALERT_LPAGE: /* introduced: SSC-2 */
+ printf("%sTapeAlert\n", b);
break;
case 0x30:
- printf("%sTape usage (IBM specific)\n", b);
+ printf("%sTape usage (LTO-5 and 6 specific)\n", b);
break;
case 0x31:
- printf("%sTape capacity (IBM specific)\n", b);
+ printf("%sTape capacity (LTO-5 and 6 specific)\n", b);
break;
case 0x32:
- printf("%sData compression (IBM specific)\n", b);
+ printf("%sData compression (LTO-5 specific, LTO-6 use "
+ "0x1b)\n", b);
break;
- case 0x33:
- printf("%sWrite errors (IBM specific)\n", b);
+ case 0x33: /* in LTO-6 this is 'Device Wellness' page */
+ printf("%sWrite errors (LTO-5 specific)\n", b);
break;
- case 0x34:
- printf("%sRead forward errors (IBM specific)\n", b);
+ case 0x34: /* in LTO-6 this is Performance data page */
+ printf("%sRead forward errors (LTO-5 specific)\n", b);
break;
+ /* case 0x35: in LTO-6 this is DT Device Error page */
case 0x37:
- printf("%sPerformance characteristics (IBM specific)\n", b);
+ printf("%sPerformance characteristics (LTO-5 specific)\n", b);
break;
case 0x38:
- printf("%sBlocks/bytes transferred (IBM specific)\n", b);
+ printf("%sBlocks/bytes transferred (LTO-5 specific)\n", b);
break;
case 0x39:
- printf("%sHost port 0 interface errors (IBM specific)\n", b);
+ printf("%sHost port 0 interface errors (LTO-5 specific)\n", b);
break;
case 0x3a:
- printf("%sDrive control verification (IBM specific)\n", b);
+ printf("%sDrive control verification (LTO-5 specific)\n", b);
break;
case 0x3b:
- printf("%sHost port 1 interface errors (IBM specific)\n", b);
+ printf("%sHost port 1 interface errors (LTO-5 specific)\n", b);
break;
case 0x3c:
- printf("%sDrive usage information (IBM specific)\n", b);
+ printf("%sDrive usage information (LTO-5 specific)\n", b);
break;
case 0x3d:
- printf("%sSubsystem statistics (IBM specific)\n", b);
+ printf("%sSubsystem statistics (LTO-5 specific)\n", b);
break;
+ /* case 0x3e: in LTO-6 this is Device Status page */
default:
done = 0;
break;
@@ -1235,7 +1238,7 @@ get_pcb_str(int pcb, char * outp, int maxoutlen)
outp[0] = '\0';
}
-/* BUFF_OVER_UNDER_LPAGE [0x1] */
+/* BUFF_OVER_UNDER_LPAGE [0x1] introduced: SPC-2 */
static void
show_buffer_under_over_run_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1247,7 +1250,7 @@ show_buffer_under_over_run_page(unsigned char * resp, int len,
char pcb_str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Buffer over-run/under-run page (spc-2) [0x1]\n");
+ printf("Buffer over-run/under-run page [0x1]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -1362,7 +1365,7 @@ skip:
}
/* WRITE_ERR_LPAGE; READ_ERR_LPAGE; READ_REV_ERR_LPAGE; VERIFY_ERR_LPAGE */
-/* [0x2, 0x3, 0x4, 0x5] */
+/* [0x2, 0x3, 0x4, 0x5] introduced: SPC-3 */
static void
show_error_counter_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1375,17 +1378,17 @@ show_error_counter_page(unsigned char * resp, int len,
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex))) {
switch(pg_code) {
case WRITE_ERR_LPAGE:
- printf("Write error counter page (spc-3) [0x%x]\n", pg_code);
+ printf("Write error counter page [0x%x]\n", pg_code);
break;
case READ_ERR_LPAGE:
- printf("Read error counter page (spc-3) [0x%x]\n", pg_code);
+ printf("Read error counter page [0x%x]\n", pg_code);
break;
case READ_REV_ERR_LPAGE:
- printf("Read Reverse error counter page (spc-3) [0x%x]\n",
+ printf("Read Reverse error counter page [0x%x]\n",
pg_code);
break;
case VERIFY_ERR_LPAGE:
- printf("Verify error counter page (spc-3) [0x%x]\n", pg_code);
+ printf("Verify error counter page [0x%x]\n", pg_code);
break;
default:
pr2serr("expecting error counter page, got page = 0x%x\n",
@@ -1436,7 +1439,7 @@ skip:
}
}
-/* NON_MEDIUM_LPAGE [0x6] */
+/* NON_MEDIUM_LPAGE [0x6] introduced: SPC-2 */
static void
show_non_medium_error_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1446,7 +1449,7 @@ show_non_medium_error_page(unsigned char * resp, int len,
char pcb_str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Non-medium error page (spc-2) [0x6]\n");
+ printf("Non-medium error page [0x6]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -1489,7 +1492,7 @@ skip:
}
}
-/* PCT_LPAGE [0x1a] */
+/* PCT_LPAGE [0x1a] introduced: SPC-4 */
static void
show_power_condition_transitions_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1499,7 +1502,7 @@ show_power_condition_transitions_page(unsigned char * resp, int len,
char pcb_str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Power condition transitions page (spc-4) [0x1a]\n");
+ printf("Power condition transitions page [0x1a]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -1547,7 +1550,7 @@ skip:
}
}
-/* Tape usage: Vendor specific (IBM): 0x30 */
+/* Tape usage: Vendor specific (LTO-5 and LTO-6): 0x30 */
static void
show_tape_usage_log_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1565,7 +1568,7 @@ show_tape_usage_log_page(unsigned char * resp, int len,
return;
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Tape usage page (IBM specific) [0x30]\n");
+ printf("Tape usage page (LTO-5 and LTO-6 specific) [0x30]\n");
for (k = num; k > 0; k -= extra, ucp += extra) {
pc = (ucp[0] << 8) + ucp[1];
pcb = ucp[2];
@@ -1827,7 +1830,7 @@ skip_para:
}
}
-/* LAST_N_ERR_LPAGE [0x7] */
+/* LAST_N_ERR_LPAGE [0x7] introduced: SPC-2 */
static void
show_last_n_error_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1843,7 +1846,7 @@ show_last_n_error_page(unsigned char * resp, int len,
return;
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Last n error events page (spc-2) [0x7]\n");
+ printf("Last n error events page [0x7]\n");
for (k = num; k > 0; k -= pl, ucp += pl) {
if (k < 3) {
printf("short Last n error events page\n");
@@ -1884,7 +1887,7 @@ show_last_n_error_page(unsigned char * resp, int len,
}
}
-/* LAST_N_DEFERRED_LPAGE [0xb] */
+/* LAST_N_DEFERRED_LPAGE [0xb] introduced: SPC-2 */
static void
show_last_n_deferred_error_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -1900,7 +1903,7 @@ show_last_n_deferred_error_page(unsigned char * resp, int len,
return;
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Last n deferred errors page (spc-2) [0xb]\n");
+ printf("Last n deferred errors page [0xb]\n");
for (k = num; k > 0; k -= pl, ucp += pl) {
if (k < 3) {
printf("short Last n deferred errors page\n");
@@ -1949,7 +1952,7 @@ static const char * self_test_result[] = {
"reserved",
"self test in progress"};
-/* SELF_TEST_LPAGE [0x10] */
+/* SELF_TEST_LPAGE [0x10] introduced: SPC-3 */
static void
show_self_test_page(unsigned char * resp, int len, const struct opts_t * op)
{
@@ -1967,7 +1970,7 @@ show_self_test_page(unsigned char * resp, int len, const struct opts_t * op)
return;
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Self-test results page (spc-3) [0x10]\n");
+ printf("Self-test results page [0x10]\n");
for (k = 0, ucp = resp + 4; k < 20; ++k, ucp += 20 ) {
pcb = ucp[2];
pl = ucp[3] + 4;
@@ -2019,7 +2022,7 @@ show_self_test_page(unsigned char * resp, int len, const struct opts_t * op)
}
}
-/* TEMPERATURE_LPAGE [0xd] */
+/* TEMPERATURE_LPAGE [0xd] introduced: SPC-3 */
static void
show_temperature_page(unsigned char * resp, int len,
const struct opts_t * op, int show_extra)
@@ -2036,7 +2039,7 @@ show_temperature_page(unsigned char * resp, int len,
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex))) {
if (show_extra)
- printf("Temperature page (spc-3) [0xd]\n");
+ printf("Temperature page [0xd]\n");
}
for (k = num; k > 0; k -= extra, ucp += extra) {
if (k < 3) {
@@ -2094,7 +2097,7 @@ show_temperature_page(unsigned char * resp, int len,
}
}
-/* START_STOP_LPAGE [0xe] */
+/* START_STOP_LPAGE [0xe] introduced: SPC-3 */
static void
show_start_stop_page(unsigned char * resp, int len, const struct opts_t * op)
{
@@ -2110,7 +2113,7 @@ show_start_stop_page(unsigned char * resp, int len, const struct opts_t * op)
return;
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Start-stop cycle counter page (spc-3) [0xe]\n");
+ printf("Start-stop cycle counter page [0xe]\n");
for (k = num; k > 0; k -= extra, ucp += extra) {
if (k < 3) {
pr2serr("short Start-stop cycle counter page\n");
@@ -2208,7 +2211,7 @@ show_start_stop_page(unsigned char * resp, int len, const struct opts_t * op)
}
}
-/* APP_CLIENT_LPAGE [0xf] */
+/* APP_CLIENT_LPAGE [0xf] introduced: SPC-3 */
static void
show_app_client_page(unsigned char * resp, int len, const struct opts_t * op)
{
@@ -2223,7 +2226,7 @@ show_app_client_page(unsigned char * resp, int len, const struct opts_t * op)
return;
}
if (op->do_verbose || ((op->do_raw == 0) && (op->do_hex == 0)))
- printf("Application client page (spc-3) [0xf]\n");
+ printf("Application client page [0xf]\n");
if (0 == op->filter_given) {
if ((len > 128) && (0 == op->do_hex)) {
dStrHex((const char *)resp, 64, 1);
@@ -2263,7 +2266,7 @@ show_app_client_page(unsigned char * resp, int len, const struct opts_t * op)
}
}
-/* IE_LPAGE [0x2f] */
+/* IE_LPAGE [0x2f] introduced: SPC-3 */
static void
show_ie_page(unsigned char * resp, int len, const struct opts_t * op,
int full)
@@ -2281,7 +2284,7 @@ show_ie_page(unsigned char * resp, int len, const struct opts_t * op,
}
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex))) {
if (full)
- printf("Informational Exceptions page (spc-3) [0x2f]\n");
+ printf("Informational Exceptions page [0x2f]\n");
}
for (k = num; k > 0; k -= extra, ucp += extra) {
if (k < 3) {
@@ -2736,7 +2739,7 @@ skip:
}
/* Returns 1 if processed page, 0 otherwise */
-/* STATS_LPAGE [0x19], subpages: 0x0 to 0x1f */
+/* STATS_LPAGE [0x19], subpages: 0x0 to 0x1f introduced: SPC-4 */
static int
show_stats_perform_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -2760,10 +2763,9 @@ show_stats_perform_page(unsigned char * resp, int len,
printf("log_subpage=0x%x\n", subpg_code);
} else {
if (0 == subpg_code)
- printf("General Statistics and Performance (spc-4) "
- "[0x19]\n");
+ printf("General Statistics and Performance [0x19]\n");
else
- printf("Group Statistics and Performance (%d) (spc-4) "
+ printf("Group Statistics and Performance (%d) "
"[0x19,0x%x]\n", subpg_code, subpg_code);
}
}
@@ -3100,7 +3102,7 @@ show_stats_perform_page(unsigned char * resp, int len,
}
/* Returns 1 if processed page, 0 otherwise */
-/* STATS_LPAGE [0x19], CACHE_STATS_SUBPG [0x20] */
+/* STATS_LPAGE [0x19], CACHE_STATS_SUBPG [0x20] introduced: SPC-4 */
static int
show_cache_stats_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -3127,7 +3129,7 @@ show_cache_stats_page(unsigned char * resp, int len,
if (subpg_code > 0)
printf("log_subpage=0x%x\n", subpg_code);
} else
- printf("Cache memory statistics page (spc-4) [0x19,0x20]\n");
+ printf("Cache memory statistics page [0x19,0x20]\n");
}
for (k = num; k > 0; k -= extra, ucp += extra) {
@@ -3249,7 +3251,7 @@ show_cache_stats_page(unsigned char * resp, int len,
return 1;
}
-/* FORMAT_STATUS_LPAGE [0x8] */
+/* FORMAT_STATUS_LPAGE [0x8] introduced: SBC-2 */
static void
show_format_status_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -3261,7 +3263,7 @@ show_format_status_page(unsigned char * resp, int len,
char pcb_str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Format status page (sbc-2) [0x8]\n");
+ printf("Format status page [0x8]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -3335,7 +3337,7 @@ skip:
}
}
-/* Non-volatile cache page [0x17] */
+/* Non-volatile cache page [0x17] introduced: SBC-2 */
static void
show_non_volatile_cache_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -3345,7 +3347,7 @@ show_non_volatile_cache_page(unsigned char * resp, int len,
char pcb_str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Non-volatile cache page (sbc-2) [0x17]\n");
+ printf("Non-volatile cache page [0x17]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -3423,7 +3425,7 @@ skip:
}
}
-/* LB_PROV_LPAGE [0xc] */
+/* LB_PROV_LPAGE [0xc] introduced: SBC-3 */
static void
show_lb_provisioning_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -3434,7 +3436,7 @@ show_lb_provisioning_page(unsigned char * resp, int len,
char str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Logical block provisioning page (sbc-3) [0xc]\n");
+ printf("Logical block provisioning page [0xc]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -3513,7 +3515,7 @@ skip:
}
}
-/* SOLID_STATE_MEDIA_LPAGE [0x11] */
+/* SOLID_STATE_MEDIA_LPAGE [0x11] introduced: SBC-3 */
static void
show_solid_state_media_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -3523,7 +3525,7 @@ show_solid_state_media_page(unsigned char * resp, int len,
char str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Solid state media page (sbc-3) [0x11]\n");
+ printf("Solid state media page [0x11]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -3799,7 +3801,7 @@ static const char * reassign_status[] = {
"Logical block unsuccessfully reassigned by application client", /* 8 */
};
-/* Background scan results [0x15,0] for disk */
+/* Background scan results [0x15,0] for disk introduced: SBC-3 */
static void
show_background_scan_results_page(unsigned char * resp, int len,
const struct opts_t * op)
@@ -3809,7 +3811,7 @@ show_background_scan_results_page(unsigned char * resp, int len,
char str[PCB_STR_LEN];
if (op->do_verbose || ((0 == op->do_raw) && (0 == op->do_hex)))
- printf("Background scan results page (sbc-3) [0x15]\n");
+ printf("Background scan results page [0x15]\n");
num = len - 4;
ucp = &resp[0] + 4;
while (num > 3) {
@@ -5033,8 +5035,8 @@ show_ascii_page(unsigned char * resp, int len,
subpg_code = spf ? resp[1] : 0;
if ((SUPP_PAGES_LPAGE != pg_code ) && (SUPP_SPGS_SUBPG == subpg_code)) {
- printf("Supported subpages for log page=0x%x (spc-4) [0x%x, 0x%x]"
- "\n", pg_code, pg_code, subpg_code);
+ printf("Supported subpages for log page=0x%x [0x%x, 0x%x]\n",
+ pg_code, pg_code, subpg_code); /* introduced: SPC-4 */
for (k = 0; k < num; k += 2)
show_page_name((int)resp[4 + k], (int)resp[4 + k + 1],
inq_dat);
@@ -5043,13 +5045,13 @@ show_ascii_page(unsigned char * resp, int len,
switch (pg_code) {
case SUPP_PAGES_LPAGE: /* 0x0 */
if (spf) {
- printf("Supported log pages and subpages (spc-4) [0x%x, 0x%x]:"
- "\n", pg_code, subpg_code);
+ printf("Supported log pages and subpages [0x%x, 0x%x]:\n",
+ pg_code, subpg_code); /* introduced: SPC-4 */
for (k = 0; k < num; k += 2)
show_page_name((int)resp[4 + k], (int)resp[4 + k + 1],
inq_dat);
} else {
- printf("Supported log pages (spc-2) [0x0]:\n");
+ printf("Supported log pages [0x0]:\n"); /* introduced: SPC-2 */
for (k = 0; k < num; ++k)
show_page_name((int)resp[4 + k], 0, inq_dat);
}
diff --git a/src/sg_rep_zones.c b/src/sg_rep_zones.c
new file mode 100644
index 00000000..99d4f5d3
--- /dev/null
+++ b/src/sg_rep_zones.c
@@ -0,0 +1,451 @@
+/*
+ * Copyright (c) 2014 Douglas Gilbert.
+ * All rights reserved.
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the BSD_LICENSE file.
+ */
+
+#include <unistd.h>
+#include <fcntl.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdarg.h>
+#include <string.h>
+#include <ctype.h>
+#include <getopt.h>
+#define __STDC_FORMAT_MACROS 1
+#include <inttypes.h>
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+#include "sg_lib.h"
+#include "sg_pt.h"
+#include "sg_cmds_basic.h"
+
+/* A utility program originally written for the Linux OS SCSI subsystem.
+ *
+ *
+ * This program issues the SCSI REPORT ZONES command to the given SCSI device
+ * and decodes the response.
+ */
+
+static const char * version_str = "1.01 20140527";
+
+#define MAX_RZONES_BUFF_LEN (1024 * 1024)
+#define DEF_RZONES_BUFF_LEN (1024 * 8)
+
+#define SERVICE_ACTION_IN_16_CMD 0x9e
+#define SERVICE_ACTION_IN_16_CMDLEN 16
+#define REPORT_ZONES_SA 0x14
+
+#define SENSE_BUFF_LEN 64 /* Arbitrary, could be larger */
+#define DEF_PT_TIMEOUT 60 /* 60 seconds */
+
+
+static struct option long_options[] = {
+ {"help", no_argument, 0, 'h'},
+ {"hex", no_argument, 0, 'H'},
+ {"maxlen", required_argument, 0, 'm'},
+ {"raw", no_argument, 0, 'r'},
+ {"readonly", no_argument, 0, 'R'},
+ {"report", required_argument, 0, 'o'},
+ {"start", required_argument, 0, 's'},
+ {"verbose", no_argument, 0, 'v'},
+ {"version", no_argument, 0, 'V'},
+ {0, 0, 0, 0},
+};
+
+
+#ifdef __GNUC__
+static int pr2serr(const char * fmt, ...)
+ __attribute__ ((format (printf, 1, 2)));
+#else
+static int pr2serr(const char * fmt, ...);
+#endif
+
+
+static int
+pr2serr(const char * fmt, ...)
+{
+ va_list args;
+ int n;
+
+ va_start(args, fmt);
+ n = vfprintf(stderr, fmt, args);
+ va_end(args);
+ return n;
+}
+
+static void
+usage()
+{
+ pr2serr("Usage: "
+ "sg_rep_zones [--help] [--hex] [--maxlen=LEN] [--raw]\n"
+ " [--readonly] [--report=OPT] "
+ "[--start=LBA]\n"
+ " [--verbose] [--version] DEVICE\n");
+ pr2serr(" where:\n"
+ " --help|-h print out usage message\n"
+ " --hex|-H output response in hexadecimal; used "
+ "twice\n"
+ " shows decoded values in hex\n"
+ " --maxlen=LEN|-m LEN max response length (allocation "
+ "length in cdb)\n"
+ " (def: 0 -> 8192 bytes)\n"
+ " --raw|-r output response in binary\n"
+ " --readonly|-R open DEVICE read-only (def: read-write)\n"
+ " --report=OPT|-o OP reporting option (def: 0)\n"
+ " --start=LBA|-s LBA report zones from the LBA (def: 0)\n"
+ " must be a zone starting LBA\n"
+ " --verbose|-v increase verbosity\n"
+ " --version|-V print version string and exit\n\n"
+ "Performs a SCSI REPORT ZONES command.\n");
+}
+
+/* Invokes a SCSI REPORT ZONES command (ZBC). Return of 0 -> success,
+ * various SG_LIB_CAT_* positive values or -1 -> other errors */
+static int
+sg_ll_report_zones(int sg_fd, uint64_t zs_lba, int report_opts, void * resp,
+ int mx_resp_len, int * residp, int noisy, int verbose)
+{
+ int k, ret, res, sense_cat;
+ unsigned char rzCmdBlk[SERVICE_ACTION_IN_16_CMDLEN] =
+ {SERVICE_ACTION_IN_16_CMD, REPORT_ZONES_SA, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0};
+ unsigned char sense_b[SENSE_BUFF_LEN];
+ struct sg_pt_base * ptvp;
+
+ if ((zs_lba >> 56) & 0xff) {
+ pr2serr("%s: zone start LBA too large\n", __func__);
+ return SG_LIB_CAT_MALFORMED;
+ }
+ /* a 7 byte field as zbc-r01a claims ?? */
+ rzCmdBlk[3] = (zs_lba >> 48) & 0xff;
+ rzCmdBlk[4] = (zs_lba >> 40) & 0xff;
+ rzCmdBlk[5] = (zs_lba >> 32) & 0xff;
+ rzCmdBlk[6] = (zs_lba >> 24) & 0xff;
+ rzCmdBlk[7] = (zs_lba >> 16) & 0xff;
+ rzCmdBlk[8] = (zs_lba >> 8) & 0xff;
+ rzCmdBlk[9] = zs_lba & 0xff;
+ rzCmdBlk[10] = (mx_resp_len >> 24) & 0xff;
+ rzCmdBlk[11] = (mx_resp_len >> 16) & 0xff;
+ rzCmdBlk[12] = (mx_resp_len >> 8) & 0xff;
+ rzCmdBlk[13] = mx_resp_len & 0xff;
+ rzCmdBlk[14] = report_opts & 0xf;
+ if (verbose) {
+ pr2serr(" Report zones cdb: ");
+ for (k = 0; k < SERVICE_ACTION_IN_16_CMDLEN; ++k)
+ pr2serr("%02x ", rzCmdBlk[k]);
+ pr2serr("\n");
+ }
+
+ ptvp = construct_scsi_pt_obj();
+ if (NULL == ptvp) {
+ pr2serr("Report zones: out of memory\n");
+ return -1;
+ }
+ set_scsi_pt_cdb(ptvp, rzCmdBlk, sizeof(rzCmdBlk));
+ set_scsi_pt_sense(ptvp, sense_b, sizeof(sense_b));
+ set_scsi_pt_data_in(ptvp, (unsigned char *)resp, mx_resp_len);
+ res = do_scsi_pt(ptvp, sg_fd, DEF_PT_TIMEOUT, verbose);
+ ret = sg_cmds_process_resp(ptvp, "report zones", res, mx_resp_len,
+ sense_b, noisy, verbose, &sense_cat);
+ if (-1 == ret)
+ ;
+ else if (-2 == ret) {
+ switch (sense_cat) {
+ case SG_LIB_CAT_RECOVERED:
+ case SG_LIB_CAT_NO_SENSE:
+ ret = 0;
+ break;
+ default:
+ ret = sense_cat;
+ break;
+ }
+ } else
+ ret = 0;
+ if (residp)
+ *residp = get_scsi_pt_resid(ptvp);
+ destruct_scsi_pt_obj(ptvp);
+ return ret;
+}
+
+static void
+dStrRaw(const char* str, int len)
+{
+ int k;
+
+ for (k = 0 ; k < len; ++k)
+ printf("%c", str[k]);
+}
+
+static const char *
+zone_type_str(int zt, char * b, int blen, int vb)
+{
+ const char * cp;
+
+ if (NULL == b)
+ return "zone_type_str: NULL ptr)";
+ switch (zt) {
+ case 1:
+ cp = "Conventional";
+ break;
+ case 2:
+ cp = "Sequential write required";
+ break;
+ case 3:
+ cp = "Sequential write preferred";
+ break;
+ default:
+ cp = NULL;
+ break;
+ }
+ if (cp) {
+ if (vb)
+ snprintf(b, blen, "%s [0x%x]", cp, zt);
+ else
+ snprintf(b, blen, "%s", cp);
+ } else
+ snprintf(b, blen, "Reserved [0x%x]", zt);
+ return b;
+}
+
+static const char *
+zone_condition_str(int zc, char * b, int blen, int vb)
+{
+ const char * cp;
+
+ if (NULL == b)
+ return "zone_condition_str: NULL ptr)";
+ switch (zc) {
+ case 1:
+ cp = "Empty";
+ break;
+ case 2:
+ cp = "Open";
+ break;
+ case 0xd:
+ cp = "Read only";
+ break;
+ case 0xe:
+ cp = "Full";
+ break;
+ case 0xf:
+ cp = "Offline";
+ break;
+ default:
+ cp = NULL;
+ break;
+ }
+ if (cp) {
+ if (vb)
+ snprintf(b, blen, "%s [0x%x]", cp, zc);
+ else
+ snprintf(b, blen, "%s", cp);
+ } else
+ snprintf(b, blen, "Reserved [0x%x]", zc);
+ return b;
+}
+
+
+int
+main(int argc, char * argv[])
+{
+ int sg_fd, k, m, res, c, zl_len, len, zones, resid, rlen, zt, zc;
+ int do_hex = 0;
+ int maxlen = 0;
+ int do_raw = 0;
+ int o_readonly = 0;
+ int reporting_opt = 0;
+ int verbose = 0;
+ uint64_t st_lba = 0;
+ int64_t ll;
+ const char * device_name = NULL;
+ unsigned char * reportZonesBuff = NULL;
+ unsigned char * ucp;
+ int ret = 0;
+ char b[80];
+
+ while (1) {
+ int option_index = 0;
+
+ c = getopt_long(argc, argv, "hHm:o:rRs:vV", long_options,
+ &option_index);
+ if (c == -1)
+ break;
+
+ switch (c) {
+ case 'h':
+ case '?':
+ usage();
+ return 0;
+ case 'H':
+ ++do_hex;
+ break;
+ case 'm':
+ maxlen = sg_get_num(optarg);
+ if ((maxlen < 0) || (maxlen > MAX_RZONES_BUFF_LEN)) {
+ pr2serr("argument to '--maxlen' should be %d or "
+ "less\n", MAX_RZONES_BUFF_LEN);
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ break;
+ case 'o':
+ reporting_opt = sg_get_num(optarg);
+ if ((reporting_opt < 0) || (reporting_opt > 15)) {
+ pr2serr("bad argument to '--report=OPT', expect 0 to "
+ "15\n");
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ break;
+ case 'r':
+ ++do_raw;
+ break;
+ case 'R':
+ ++o_readonly;
+ break;
+ case 's':
+ ll = sg_get_llnum(optarg);
+ if (-1 == ll) {
+ fprintf(stderr, "bad argument to '--start=LBA'\n");
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ st_lba = (uint64_t)ll;
+ break;
+ case 'v':
+ ++verbose;
+ break;
+ case 'V':
+ pr2serr("version: %s\n", version_str);
+ return 0;
+ default:
+ pr2serr("unrecognised option code 0x%x ??\n", c);
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ }
+ if (optind < argc) {
+ if (NULL == device_name) {
+ device_name = argv[optind];
+ ++optind;
+ }
+ if (optind < argc) {
+ for (; optind < argc; ++optind)
+ pr2serr("Unexpected extra argument: %s\n",
+ argv[optind]);
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ }
+
+ if (NULL == device_name) {
+ pr2serr("missing device name!\n");
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+
+ if (do_raw) {
+ if (sg_set_binary_mode(STDOUT_FILENO) < 0) {
+ perror("sg_set_binary_mode");
+ return SG_LIB_FILE_ERROR;
+ }
+ }
+
+ sg_fd = sg_cmds_open_device(device_name, o_readonly, verbose);
+ if (sg_fd < 0) {
+ pr2serr("open error: %s: %s\n", device_name,
+ safe_strerror(-sg_fd));
+ return SG_LIB_FILE_ERROR;
+ }
+
+ if (0 == maxlen)
+ maxlen = DEF_RZONES_BUFF_LEN;
+ reportZonesBuff = (unsigned char *)calloc(1, maxlen);
+ if (NULL == reportZonesBuff) {
+ pr2serr("unable to malloc %d bytes\n", maxlen);
+ return SG_LIB_CAT_OTHER;
+ }
+
+ res = sg_ll_report_zones(sg_fd, st_lba, reporting_opt, reportZonesBuff,
+ maxlen, &resid, 1, verbose);
+ ret = res;
+ if (0 == res) {
+ rlen = maxlen - resid;
+ if (rlen < 4) {
+ pr2serr("Response length (%d) too short\n", rlen);
+ ret = SG_LIB_CAT_MALFORMED;
+ goto the_end;
+ }
+ zl_len = (reportZonesBuff[0] << 24) + (reportZonesBuff[1] << 16) +
+ (reportZonesBuff[2] << 8) + reportZonesBuff[3] + 64;
+ if (zl_len > rlen) {
+ if (verbose)
+ pr2serr("zl_len available is %d, response length is %d\n",
+ zl_len, rlen);
+ len = rlen;
+ } else
+ len = zl_len;
+ if (do_raw) {
+ dStrRaw((const char *)reportZonesBuff, len);
+ goto the_end;
+ }
+ if (do_hex && (2 != do_hex)) {
+ dStrHex((const char *)reportZonesBuff, len,
+ ((1 == do_hex) ? 1 : -1));
+ goto the_end;
+ }
+ printf("Report zones response:\n");
+ if (len < 64) {
+ pr2serr("Zone length [%d] too short (perhaps after truncation\n)",
+ len);
+ ret = SG_LIB_CAT_MALFORMED;
+ goto the_end;
+ }
+ printf(" Same=%d\n\n", reportZonesBuff[4] & 1);
+ zones = (len - 64) / 64;
+ for (k = 0, ucp = reportZonesBuff + 64; k < zones; ++k, ucp += 64) {
+ printf(" Zone descriptor: %d\n", k);
+ if (do_hex) {
+ dStrHex((const char *)ucp, len, -1);
+ continue;
+ }
+ zt = ucp[0] & 0xf;
+ zc = (ucp[1] >> 4) & 0xf;
+ printf(" Zone type: %s\n", zone_type_str(zt, b, sizeof(b),
+ verbose));
+ printf(" Zone condition: %s\n", zone_condition_str(zc, b,
+ sizeof(b), verbose));
+ printf(" Reset: %d\n", ucp[1] & 0x1);
+ printf(" Zone Length: 0x");
+ for (m = 0; m < 8; ++m)
+ printf("%02x", ucp[8 + m]);
+ printf("\n Zone start LBA: 0x");
+ for (m = 0; m < 8; ++m)
+ printf("%02x", ucp[64 + m]);
+ printf("\n Write pointer LBA: 0x");
+ for (m = 0; m < 8; ++m)
+ printf("%02x", ucp[64 + m]);
+ printf("\n");
+ }
+ if ((64 + (64 * zones)) < zl_len)
+ printf("\n>>> Beware: Zone list truncated, may need another "
+ "call\n");
+ } else if (SG_LIB_CAT_INVALID_OP == res)
+ pr2serr("Report zones command not supported\n");
+ else {
+ sg_get_category_sense_str(res, sizeof(b), b, verbose);
+ pr2serr("Report zones command: %s\n", b);
+ }
+
+the_end:
+ if (reportZonesBuff)
+ free(reportZonesBuff);
+ res = sg_cmds_close_device(sg_fd);
+ if (res < 0) {
+ pr2serr("close error: %s\n", safe_strerror(-res));
+ if (0 == ret)
+ return SG_LIB_FILE_ERROR;
+ }
+ return (ret >= 0) ? ret : SG_LIB_CAT_OTHER;
+}
diff --git a/src/sg_reset_wp.c b/src/sg_reset_wp.c
new file mode 100644
index 00000000..cdc1f5d4
--- /dev/null
+++ b/src/sg_reset_wp.c
@@ -0,0 +1,257 @@
+/*
+ * Copyright (c) 2014 Douglas Gilbert.
+ * All rights reserved.
+ * Use of this source code is governed by a BSD-style
+ * license that can be found in the BSD_LICENSE file.
+ */
+
+#include <unistd.h>
+#include <fcntl.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdarg.h>
+#include <string.h>
+#include <ctype.h>
+#include <getopt.h>
+#define __STDC_FORMAT_MACROS 1
+#include <inttypes.h>
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+#include "sg_lib.h"
+#include "sg_pt.h"
+#include "sg_cmds_basic.h"
+
+/* A utility program originally written for the Linux OS SCSI subsystem.
+ *
+ *
+ * This program issues the SCSI RESET WRITE POINTER command to the given SCSI
+ * device.
+ */
+
+static const char * version_str = "1.00 20140527";
+
+#define SERVICE_ACTION_OUT_16_CMD 0x9f
+#define SERVICE_ACTION_OUT_16_CMDLEN 16
+#define RESET_WRITE_POINTER_SA 0x14
+
+#define SENSE_BUFF_LEN 64 /* Arbitrary, could be larger */
+#define DEF_PT_TIMEOUT 60 /* 60 seconds */
+
+
+static struct option long_options[] = {
+ {"help", no_argument, 0, 'h'},
+ {"reset-all", no_argument, 0, 'R'},
+ {"reset_all", no_argument, 0, 'R'},
+ {"verbose", no_argument, 0, 'v'},
+ {"version", no_argument, 0, 'V'},
+ {"zone", required_argument, 0, 'z'},
+ {0, 0, 0, 0},
+};
+
+
+#ifdef __GNUC__
+static int pr2serr(const char * fmt, ...)
+ __attribute__ ((format (printf, 1, 2)));
+#else
+static int pr2serr(const char * fmt, ...);
+#endif
+
+
+static int
+pr2serr(const char * fmt, ...)
+{
+ va_list args;
+ int n;
+
+ va_start(args, fmt);
+ n = vfprintf(stderr, fmt, args);
+ va_end(args);
+ return n;
+}
+
+static void
+usage()
+{
+ pr2serr("Usage: "
+ "sg_reset_wp [--help] [--reset-all] [--verbose] [--version]\n"
+ " [--zone=ID] DEVICE\n");
+ pr2serr(" where:\n"
+ " --help|-h print out usage message\n"
+ " --reset-all|-R sets the RESET ALL flag in the cdb\n"
+ " --verbose|-v increase verbosity\n"
+ " --version|-V print version string and exit\n\n"
+ " --zone=ID|-z ID ID is the starting LBA of the zone "
+ "whose\n"
+ " write pointer is to be reset\n"
+ "Performs a SCSI RESET WRITE POINTER command. ID is decimal by "
+ "default,\nfor hex use a leading '0x' or a trailing 'h'. "
+ "Either the --zone=ID\nor --reset-all needs to be given.\n");
+}
+
+/* Invokes a SCSI RESET WRITE POINTER command (ZBC). Return of 0 -> success,
+ * various SG_LIB_CAT_* positive values or -1 -> other errors */
+static int
+sg_ll_reset_write_pointer(int sg_fd, uint64_t zid, int reset_all, int noisy,
+ int verbose)
+{
+ int k, ret, res, sense_cat;
+ unsigned char rwpCmdBlk[SERVICE_ACTION_OUT_16_CMDLEN] =
+ {SERVICE_ACTION_OUT_16_CMD, RESET_WRITE_POINTER_SA, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
+ unsigned char sense_b[SENSE_BUFF_LEN];
+ struct sg_pt_base * ptvp;
+
+ if ((zid >> 56) & 0xff) {
+ pr2serr("%s: zone id (LBA) too large\n", __func__);
+ return SG_LIB_CAT_MALFORMED;
+ }
+ /* a 7 byte field as zbc-r01a claims ?? */
+ rwpCmdBlk[3] = (zid >> 48) & 0xff;
+ rwpCmdBlk[4] = (zid >> 40) & 0xff;
+ rwpCmdBlk[5] = (zid >> 32) & 0xff;
+ rwpCmdBlk[6] = (zid >> 24) & 0xff;
+ rwpCmdBlk[7] = (zid >> 16) & 0xff;
+ rwpCmdBlk[8] = (zid >> 8) & 0xff;
+ rwpCmdBlk[9] = zid & 0xff;
+ if (reset_all)
+ rwpCmdBlk[14] = 0x1;
+ if (verbose) {
+ pr2serr(" Reset write pointer cdb: ");
+ for (k = 0; k < SERVICE_ACTION_OUT_16_CMDLEN; ++k)
+ pr2serr("%02x ", rwpCmdBlk[k]);
+ pr2serr("\n");
+ }
+
+ ptvp = construct_scsi_pt_obj();
+ if (NULL == ptvp) {
+ pr2serr("Reset write pointer: out of memory\n");
+ return -1;
+ }
+ set_scsi_pt_cdb(ptvp, rwpCmdBlk, sizeof(rwpCmdBlk));
+ set_scsi_pt_sense(ptvp, sense_b, sizeof(sense_b));
+ res = do_scsi_pt(ptvp, sg_fd, DEF_PT_TIMEOUT, verbose);
+ ret = sg_cmds_process_resp(ptvp, "reset write pointer", res, 0, sense_b,
+ noisy, verbose, &sense_cat);
+ if (-1 == ret)
+ ;
+ else if (-2 == ret) {
+ switch (sense_cat) {
+ case SG_LIB_CAT_RECOVERED:
+ case SG_LIB_CAT_NO_SENSE:
+ ret = 0;
+ break;
+ default:
+ ret = sense_cat;
+ break;
+ }
+ } else
+ ret = 0;
+ destruct_scsi_pt_obj(ptvp);
+ return ret;
+}
+
+
+int
+main(int argc, char * argv[])
+{
+ int sg_fd, res, c;
+ int reset_all = 0;
+ int verbose = 0;
+ int zid_given = 0;
+ uint64_t zid = 0;
+ int64_t ll;
+ const char * device_name = NULL;
+ int ret = 0;
+
+ while (1) {
+ int option_index = 0;
+
+ c = getopt_long(argc, argv, "hRvVz:", long_options,
+ &option_index);
+ if (c == -1)
+ break;
+
+ switch (c) {
+ case 'h':
+ case '?':
+ usage();
+ return 0;
+ case 'R':
+ ++reset_all;
+ break;
+ case 'v':
+ ++verbose;
+ break;
+ case 'V':
+ pr2serr("version: %s\n", version_str);
+ return 0;
+ case 'z':
+ ll = sg_get_llnum(optarg);
+ if (-1 == ll) {
+ fprintf(stderr, "bad argument to '--zone=ID'\n");
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ zid = (uint64_t)ll;
+ ++zid_given;
+ break;
+ default:
+ pr2serr("unrecognised option code 0x%x ??\n", c);
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ }
+ if (optind < argc) {
+ if (NULL == device_name) {
+ device_name = argv[optind];
+ ++optind;
+ }
+ if (optind < argc) {
+ for (; optind < argc; ++optind)
+ pr2serr("Unexpected extra argument: %s\n",
+ argv[optind]);
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ }
+
+ if ((! zid_given) && (0 == reset_all)) {
+ pr2serr("either the --zone=ID or --reset-all option is required\n");
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ if (NULL == device_name) {
+ pr2serr("missing device name!\n");
+ usage();
+ return SG_LIB_SYNTAX_ERROR;
+ }
+
+ sg_fd = sg_cmds_open_device(device_name, 0, verbose);
+ if (sg_fd < 0) {
+ pr2serr("open error: %s: %s\n", device_name,
+ safe_strerror(-sg_fd));
+ return SG_LIB_FILE_ERROR;
+ }
+
+ res = sg_ll_reset_write_pointer(sg_fd, zid, reset_all, 1, verbose);
+ ret = res;
+ if (res) {
+ if (SG_LIB_CAT_INVALID_OP == res)
+ pr2serr("Reset write pointer command not supported\n");
+ else {
+ char b[80];
+
+ sg_get_category_sense_str(res, sizeof(b), b, verbose);
+ pr2serr("Reset write pointer command: %s\n", b);
+ }
+ }
+
+ res = sg_cmds_close_device(sg_fd);
+ if (res < 0) {
+ pr2serr("close error: %s\n", safe_strerror(-res));
+ if (0 == ret)
+ return SG_LIB_FILE_ERROR;
+ }
+ return (ret >= 0) ? ret : SG_LIB_CAT_OTHER;
+}
diff --git a/src/sg_vpd.c b/src/sg_vpd.c
index 0cb1cfef..84e9c248 100644
--- a/src/sg_vpd.c
+++ b/src/sg_vpd.c
@@ -33,7 +33,7 @@
*/
-static const char * version_str = "0.85 20140522"; /* spc4r37 + sbc4r01 */
+static const char * version_str = "0.86 20140527"; /* spc4r37 + sbc4r01 */
/* And with sbc3r35, vale Mark Evans */
void svpd_enumerate_vendor(int vp_num);
@@ -664,7 +664,7 @@ const char * sg_ansi_version_arr[] =
"SPC-2",
"SPC-3",
"SPC-4",
- "reserved [7h]",
+ "SPC-5",
"ecma=1, [8h]",
"ecma=1, [9h]",
"ecma=1, [Ah]",
@@ -2410,9 +2410,9 @@ decode_b1_vpd(unsigned char * buff, int len, int do_hex, int pdt)
printf(": reserved\n");
break;
}
- printf(" HAW_ZBC=%d\n", buff[8] & 0x10); /* sbc4r01 */
- printf(" FUAB=%d\n", buff[8] & 0x2);
- printf(" VBULS=%d\n", buff[8] & 0x1);
+ printf(" HAW_ZBC=%d\n", !!(buff[8] & 0x10)); /* sbc4r01 */
+ printf(" FUAB=%d\n", !!(buff[8] & 0x2));
+ printf(" VBULS=%d\n", !!(buff[8] & 0x1));
break;
case PDT_TAPE: case PDT_MCHANGER: case PDT_ADC:
printf(" Manufacturer-assigned serial number: %.*s\n",