aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--BSD_LICENSE3
-rw-r--r--ChangeLog3
-rw-r--r--examples/scsi_inquiry.c40
-rw-r--r--examples/sg_excl.c46
-rw-r--r--examples/sg_sat_chk_power.c5
-rw-r--r--examples/sg_sat_smart_rd_data.c5
-rw-r--r--examples/sg_simple1.c54
-rw-r--r--examples/sgq_dd.c59
-rw-r--r--include/sg_cmds_basic.h2
-rw-r--r--include/sg_cmds_extra.h2
-rw-r--r--include/sg_cmds_mmc.h2
-rw-r--r--include/sg_io_linux.h2
-rw-r--r--include/sg_lib.h2
-rw-r--r--include/sg_lib_data.h2
-rw-r--r--include/sg_pr2serr.h2
-rw-r--r--include/sg_pt.h2
-rw-r--r--include/sg_pt_linux.h2
-rw-r--r--include/sg_pt_nvme.h2
-rw-r--r--include/sg_unaligned.h2
-rw-r--r--lib/BSD_LICENSE2
-rw-r--r--lib/sg_cmds_basic.c2
-rw-r--r--lib/sg_cmds_basic2.c2
-rw-r--r--lib/sg_cmds_extra.c2
-rw-r--r--lib/sg_cmds_mmc.c2
-rw-r--r--lib/sg_io_linux.c2
-rw-r--r--lib/sg_lib.c2
-rw-r--r--lib/sg_lib_data.c2
-rw-r--r--lib/sg_pt_common.c2
-rw-r--r--lib/sg_pt_freebsd.c2
-rw-r--r--lib/sg_pt_linux.c2
-rw-r--r--lib/sg_pt_linux_nvme.c2
-rw-r--r--lib/sg_pt_osf1.c2
-rw-r--r--lib/sg_pt_solaris.c2
-rw-r--r--lib/sg_pt_win32.c2
-rw-r--r--src/sg_bg_ctl.c2
-rw-r--r--src/sg_compare_and_write.c2
-rw-r--r--src/sg_copy_results.c27
-rw-r--r--src/sg_dd.c2
-rw-r--r--src/sg_decode_sense.c2
-rw-r--r--src/sg_emc_trespass.c2
-rw-r--r--src/sg_format.c2
-rw-r--r--src/sg_get_config.c2
-rw-r--r--src/sg_get_lba_status.c2
-rw-r--r--src/sg_ident.c2
-rw-r--r--src/sg_inq.c2
-rw-r--r--src/sg_inq_data.c24
-rw-r--r--src/sg_logs.c2
-rw-r--r--src/sg_luns.c2
-rw-r--r--src/sg_map.c15
-rw-r--r--src/sg_map26.c2
-rw-r--r--src/sg_modes.c6
-rw-r--r--src/sg_opcodes.c2
-rw-r--r--src/sg_persist.c2
-rw-r--r--src/sg_prevent.c2
-rw-r--r--src/sg_raw.c2
-rw-r--r--src/sg_rbuf.c2
-rw-r--r--src/sg_rdac.c2
-rw-r--r--src/sg_read.c15
-rw-r--r--src/sg_read_attr.c2
-rw-r--r--src/sg_read_block_limits.c2
-rw-r--r--src/sg_read_buffer.c2
-rw-r--r--src/sg_read_long.c2
-rw-r--r--src/sg_readcap.c2
-rw-r--r--src/sg_reassign.c2
-rw-r--r--src/sg_referrals.c2
-rw-r--r--src/sg_rep_zones.c2
-rw-r--r--src/sg_requests.c2
-rw-r--r--src/sg_reset.c2
-rw-r--r--src/sg_reset_wp.c2
-rw-r--r--src/sg_rmsn.c2
-rw-r--r--src/sg_rtpg.c2
-rw-r--r--src/sg_safte.c2
-rw-r--r--src/sg_sanitize.c2
-rw-r--r--src/sg_sat_identify.c2
-rw-r--r--src/sg_sat_phy_event.c2
-rw-r--r--src/sg_sat_read_gplog.c2
-rw-r--r--src/sg_sat_set_features.c2
-rw-r--r--src/sg_scan_linux.c2
-rw-r--r--src/sg_scan_win32.c2
-rw-r--r--src/sg_seek.c2
-rw-r--r--src/sg_senddiag.c15
-rw-r--r--src/sg_ses.c2
-rw-r--r--src/sg_ses_microcode.c2
-rw-r--r--src/sg_start.c2
-rw-r--r--src/sg_stpg.c2
-rw-r--r--src/sg_stream_ctl.c2
-rw-r--r--src/sg_sync.c2
-rw-r--r--src/sg_test_rwbuf.c2
-rw-r--r--src/sg_timestamp.c2
-rw-r--r--src/sg_turs.c1
-rw-r--r--src/sg_unmap.c2
-rw-r--r--src/sg_verify.c2
-rw-r--r--src/sg_vpd.c2
-rw-r--r--src/sg_vpd_vendor.c2
-rw-r--r--src/sg_wr_mode.c2
-rw-r--r--src/sg_write_buffer.c2
-rw-r--r--src/sg_write_long.c2
-rw-r--r--src/sg_write_same.c2
-rw-r--r--src/sg_write_verify.c2
-rw-r--r--src/sg_write_x.c2
-rw-r--r--src/sg_xcopy.c2
-rw-r--r--src/sg_zone.c2
-rw-r--r--src/sginfo.c2
-rw-r--r--src/sgm_dd.c2
-rw-r--r--src/sgp_dd.c2
-rw-r--r--testing/Makefile11
-rw-r--r--testing/sg_chk_asc.c4
-rw-r--r--testing/sg_iovec_tst.c34
-rw-r--r--testing/sg_queue_tst.c35
-rw-r--r--testing/sg_sense_test.c4
-rw-r--r--testing/sg_tst_async.cpp6
-rw-r--r--testing/sg_tst_context.cpp6
-rw-r--r--testing/sg_tst_excl.cpp8
-rw-r--r--testing/sg_tst_excl2.cpp6
-rw-r--r--testing/sg_tst_excl3.cpp8
-rw-r--r--testing/sg_tst_ioctl.c25
-rw-r--r--testing/sg_tst_nvme.c4
-rw-r--r--testing/sgs_dd.c732
-rw-r--r--testing/tst_sg_lib.c4
-rw-r--r--testing/uapi_sg.h4
-rw-r--r--utils/hxascdmp.c4
121 files changed, 890 insertions, 503 deletions
diff --git a/BSD_LICENSE b/BSD_LICENSE
index 7f1906bb..609967d6 100644
--- a/BSD_LICENSE
+++ b/BSD_LICENSE
@@ -22,3 +22,6 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+Above is the:
+SPDX-License-Identifier: BSD-2-Clause
diff --git a/ChangeLog b/ChangeLog
index dd82b41a..42d67de5 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -2,7 +2,7 @@ Each utility has its own version number, date of last change and
some description at the top of its ".c" file. All utilities in the main
directory have their own "man" pages. There is also a sg3_utils man page.
-Changelog for sg3_utils-1.45 [20181127] [svn: r796]
+Changelog for sg3_utils-1.45 [20181207] [svn: r797]
- sg_ses: bug: --page= being overridden when --control
and --data= also given; fix
- sg_opcodes: expand MLU (18-102r0)
@@ -13,6 +13,7 @@ Changelog for sg3_utils-1.45 [20181127] [svn: r796]
- testing/sg_tst_async: fix free_list issue
- testing/sg_tst_ioctl: for sg 3.9 driver
- testing/sgs_dd: for share in sg 3.9.02 driver
+ - add: SPDX-License-Identifier: BSD-2-Clause
Changelog for sg3_utils-1.44 [20180912] [svn: r791]
- same code as release 1.43 20180911 svn rev 789;
diff --git a/examples/scsi_inquiry.c b/examples/scsi_inquiry.c
index 32fe74d6..99497490 100644
--- a/examples/scsi_inquiry.c
+++ b/examples/scsi_inquiry.c
@@ -1,3 +1,24 @@
+/*
+ * Copyright (C) 1999-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * Test code for D. Gilbert's extensions to the Linux OS SCSI generic ("sg")
+ * device driver.
+ * This program does a SCSI inquiry command on the given device and
+ * outputs some of the result. This program highlights the use of the
+ * SCSI_IOCTL_SEND_COMMAND ioctl. This should be able to be applied to
+ * any SCSI device file descriptor (not just one related to sg). [Whether
+ * this is a good idea on a disk while it is mounted is debatable.
+ * No detrimental effects when this was tested ...]
+ *
+ * Version 0.16 20181207
+ */
+
#include <unistd.h>
#include <signal.h>
#include <fcntl.h>
@@ -11,25 +32,6 @@
#include <scsi/scsi.h>
/* #include <scsi/scsi_ioctl.h> */ /* glibc hides this file sometimes */
-/* Test code for D. Gilbert's extensions to the Linux OS SCSI generic ("sg")
- device driver.
-* Copyright (C) 1999 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- This program does a SCSI inquiry command on the given device and
- outputs some of the result. This program highlights the use of the
- SCSI_IOCTL_SEND_COMMAND ioctl. This should be able to be applied to
- any SCSI device file descriptor (not just one related to sg). [Whether
- this is a good idea on a disk while it is mounted is debatable.
- No detrimental effects when this was tested ...]
-
-Version 0.15 20160528
-*/
-
-
typedef struct my_scsi_ioctl_command {
unsigned int inlen; /* _excluding_ scsi command length */
unsigned int outlen;
diff --git a/examples/sg_excl.c b/examples/sg_excl.c
index 8cbab750..38645252 100644
--- a/examples/sg_excl.c
+++ b/examples/sg_excl.c
@@ -1,3 +1,28 @@
+/*
+ * Copyright (C) 2003-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * This is a simple program that tests the O_EXCL flag in sg while
+ * executing a SCSI INQUIRY command and a
+ * TEST UNIT READY command using the SCSI generic (sg) driver
+ *
+ * Invocation: sg_excl [-x] <sg_device>
+ *
+ * Version 3.61 (20181207)
+ *
+ * 6 byte INQUIRY command:
+ * [0x12][ |lu][pg cde][res ][al len][cntrl ]
+ *
+ * 6 byte TEST UNIT READY command:
+ * [0x00][ |lu][res ][res ][res ][res ]
+ *
+ */
+
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
@@ -11,27 +36,6 @@
#include "sg_lib.h"
#include "sg_io_linux.h"
-/* This is a simple program that tests the O_EXCL flag in sg while
- executing a SCSI INQUIRY command and a
- TEST UNIT READY command using the SCSI generic (sg) driver
-
-* Copyright (C) 2003-2018 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- Invocation: sg_excl [-x] <sg_device>
-
- Version 3.60 (20180220)
-
-6 byte INQUIRY command:
-[0x12][ |lu][pg cde][res ][al len][cntrl ]
-
-6 byte TEST UNIT READY command:
-[0x00][ |lu][res ][res ][res ][res ]
-
-*/
#define INQ_REPLY_LEN 96
#define INQ_CMD_LEN 6
diff --git a/examples/sg_sat_chk_power.c b/examples/sg_sat_chk_power.c
index b5ea18ae..ca24f665 100644
--- a/examples/sg_sat_chk_power.c
+++ b/examples/sg_sat_chk_power.c
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -25,6 +23,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
@@ -59,7 +58,7 @@
#define EBUFF_SZ 256
-static const char * version_str = "1.07 20180706";
+static const char * version_str = "1.08 20181207";
#if 0
diff --git a/examples/sg_sat_smart_rd_data.c b/examples/sg_sat_smart_rd_data.c
index 1e7295d3..223da2a7 100644
--- a/examples/sg_sat_smart_rd_data.c
+++ b/examples/sg_sat_smart_rd_data.c
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -25,6 +23,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
@@ -58,7 +57,7 @@
#define EBUFF_SZ 256
-static char * version_str = "1.04 20180220";
+static char * version_str = "1.05 20181207";
int main(int argc, char * argv[])
{
diff --git a/examples/sg_simple1.c b/examples/sg_simple1.c
index d8352678..b8ef3491 100644
--- a/examples/sg_simple1.c
+++ b/examples/sg_simple1.c
@@ -1,3 +1,32 @@
+/*
+ * Copyright (C) 1999-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * This is a simple program executing a SCSI INQUIRY command and a
+ * TEST UNIT READY command using the SCSI generic (sg) driver
+ * There is another variant of this program called "sg_simple2"
+ * which does not include the sg_lib.h header and logic and so has
+ * simpler but more primitive error processing.
+ * In the lk 2.6 series devices nodes such as /dev/sda also support
+ * the SG_IO ioctl.
+ *
+ * Invocation: sg_simple1 [-x] <scsi_device>
+ *
+ * Version 3.60 (20181207)
+ *
+ * 6 byte INQUIRY command:
+ * [0x12][ |lu][pg cde][res ][al len][cntrl ]
+ *
+ * 6 byte TEST UNIT READY command:
+ * [0x00][ |lu][res ][res ][res ][res ]
+ *
+ */
+
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
@@ -10,31 +39,6 @@
#include "sg_lib.h"
#include "sg_io_linux.h"
-/* This is a simple program executing a SCSI INQUIRY command and a
- TEST UNIT READY command using the SCSI generic (sg) driver
- There is another variant of this program called "sg_simple2"
- which does not include the sg_lib.h header and logic and so has
- simpler but more primitive error processing.
- In the lk 2.6 series devices nodes such as /dev/sda also support
- the SG_IO ioctl.
-
-* Copyright (C) 1999-2007 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- Invocation: sg_simple1 [-x] <scsi_device>
-
- Version 03.59 (20160528)
-
-6 byte INQUIRY command:
-[0x12][ |lu][pg cde][res ][al len][cntrl ]
-
-6 byte TEST UNIT READY command:
-[0x00][ |lu][res ][res ][res ][res ]
-
-*/
#define INQ_REPLY_LEN 96
#define INQ_CMD_LEN 6
diff --git a/examples/sgq_dd.c b/examples/sgq_dd.c
index debbe377..00a98aad 100644
--- a/examples/sgq_dd.c
+++ b/examples/sgq_dd.c
@@ -1,3 +1,32 @@
+/*
+ * A utility program for the Linux OS SCSI generic ("sg") device driver.
+ * Copyright (C) 1999-2018 D. Gilbert and P. Allworth
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * This program is a specialization of the Unix "dd" command in which
+ * one or both of the given files is a scsi generic device or a raw
+ * device. A block size ('bs') is assumed to be 512 if not given. This
+ * program complains if 'ibs' or 'obs' are given with some other value
+ * than 'bs'. If 'if' is not given or 'if=-' then stdin is assumed. If
+ * 'of' is not given or 'of=-' then stdout assumed. Multipliers:
+ * 'c','C' *1 'b','B' *512 'k' *1024 'K' *1000
+ * 'm' *(1024^2) 'M' *(1000^2) 'g' *(1024^3) 'G' *(1000^3)
+ *
+ * A non-standard argument "bpt" (blocks per transfer) is added to control
+ * the maximum number of blocks in each transfer. The default value is 128.
+ * For example if "bs=512" and "bpt=32" then a maximum of 32 blocks (16KB
+ * in this case) are transferred to or from the sg device in a single SCSI
+ * command.
+ *
+ * This version should compile with Linux sg drivers with version numbers
+ * >= 30000 . This version uses queuing within the Linux sg driver.
+ */
+
#define _XOPEN_SOURCE 500
#include <unistd.h>
@@ -23,34 +52,8 @@ typedef uint8_t u_char; /* horrible, for scsi.h */
#include "sg_io_linux.h"
#include "sg_unaligned.h"
-/* A utility program for the Linux OS SCSI generic ("sg") device driver.
-* Copyright (C) 1999-2018 D. Gilbert and P. Allworth
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- This program is a specialization of the Unix "dd" command in which
- one or both of the given files is a scsi generic device or a raw
- device. A block size ('bs') is assumed to be 512 if not given. This
- program complains if 'ibs' or 'obs' are given with some other value
- than 'bs'. If 'if' is not given or 'if=-' then stdin is assumed. If
- 'of' is not given or 'of=-' then stdout assumed. Multipliers:
- 'c','C' *1 'b','B' *512 'k' *1024 'K' *1000
- 'm' *(1024^2) 'M' *(1000^2) 'g' *(1024^3) 'G' *(1000^3)
-
- A non-standard argument "bpt" (blocks per transfer) is added to control
- the maximum number of blocks in each transfer. The default value is 128.
- For example if "bs=512" and "bpt=32" then a maximum of 32 blocks (16KB
- in this case) are transferred to or from the sg device in a single SCSI
- command.
-
- This version should compile with Linux sg drivers with version numbers
- >= 30000 . This version uses queuing within the Linux sg driver.
-
-*/
-
-static char * version_str = "0.61 20180627";
+
+static char * version_str = "0.62 20181207";
/* resurrected from "0.55 20020509" */
#define DEF_BLOCK_SIZE 512
diff --git a/include/sg_cmds_basic.h b/include/sg_cmds_basic.h
index 4fb0ddf7..d6ded5a4 100644
--- a/include/sg_cmds_basic.h
+++ b/include/sg_cmds_basic.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/include/sg_cmds_extra.h b/include/sg_cmds_extra.h
index 974d17c1..dde22983 100644
--- a/include/sg_cmds_extra.h
+++ b/include/sg_cmds_extra.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdint.h>
diff --git a/include/sg_cmds_mmc.h b/include/sg_cmds_mmc.h
index 3988b1d6..c9b7d73d 100644
--- a/include/sg_cmds_mmc.h
+++ b/include/sg_cmds_mmc.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#ifdef __cplusplus
diff --git a/include/sg_io_linux.h b/include/sg_io_linux.h
index b57aa63e..afbd3657 100644
--- a/include/sg_io_linux.h
+++ b/include/sg_io_linux.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/include/sg_lib.h b/include/sg_lib.h
index 4e26c296..a5f8a3d5 100644
--- a/include/sg_lib.h
+++ b/include/sg_lib.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/include/sg_lib_data.h b/include/sg_lib_data.h
index a8700439..9f573b97 100644
--- a/include/sg_lib_data.h
+++ b/include/sg_lib_data.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/include/sg_pr2serr.h b/include/sg_pr2serr.h
index c317f5bb..351b3e31 100644
--- a/include/sg_pr2serr.h
+++ b/include/sg_pr2serr.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* These are convenience functions that replace the somewhat long-winded
diff --git a/include/sg_pt.h b/include/sg_pt.h
index c882893b..b75a8d46 100644
--- a/include/sg_pt.h
+++ b/include/sg_pt.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdint.h>
diff --git a/include/sg_pt_linux.h b/include/sg_pt_linux.h
index 00010ba8..bf1a1691 100644
--- a/include/sg_pt_linux.h
+++ b/include/sg_pt_linux.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdint.h>
diff --git a/include/sg_pt_nvme.h b/include/sg_pt_nvme.h
index a910b052..daca8fce 100644
--- a/include/sg_pt_nvme.h
+++ b/include/sg_pt_nvme.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdint.h>
diff --git a/include/sg_unaligned.h b/include/sg_unaligned.h
index ca702e86..0a65b391 100644
--- a/include/sg_unaligned.h
+++ b/include/sg_unaligned.h
@@ -6,6 +6,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdbool.h>
diff --git a/lib/BSD_LICENSE b/lib/BSD_LICENSE
index 7f1906bb..02f13c10 100644
--- a/lib/BSD_LICENSE
+++ b/lib/BSD_LICENSE
@@ -22,3 +22,5 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+Above is the:
+SPDX-License-Identifier: BSD-2-Clause
diff --git a/lib/sg_cmds_basic.c b/lib/sg_cmds_basic.c
index e625465e..5e16b44c 100644
--- a/lib/sg_cmds_basic.c
+++ b/lib/sg_cmds_basic.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/lib/sg_cmds_basic2.c b/lib/sg_cmds_basic2.c
index e77e290d..f4605d44 100644
--- a/lib/sg_cmds_basic2.c
+++ b/lib/sg_cmds_basic2.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/lib/sg_cmds_extra.c b/lib/sg_cmds_extra.c
index 97f80fef..1b86d23d 100644
--- a/lib/sg_cmds_extra.c
+++ b/lib/sg_cmds_extra.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdio.h>
diff --git a/lib/sg_cmds_mmc.c b/lib/sg_cmds_mmc.c
index e1358591..64ed9997 100644
--- a/lib/sg_cmds_mmc.c
+++ b/lib/sg_cmds_mmc.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdio.h>
diff --git a/lib/sg_io_linux.c b/lib/sg_io_linux.c
index cab93fe2..127a49e7 100644
--- a/lib/sg_io_linux.c
+++ b/lib/sg_io_linux.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdio.h>
diff --git a/lib/sg_lib.c b/lib/sg_lib.c
index c2c58916..0a98f0e8 100644
--- a/lib/sg_lib.c
+++ b/lib/sg_lib.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* NOTICE:
diff --git a/lib/sg_lib_data.c b/lib/sg_lib_data.c
index d5ca380b..d66b1c7a 100644
--- a/lib/sg_lib_data.c
+++ b/lib/sg_lib_data.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdlib.h>
diff --git a/lib/sg_pt_common.c b/lib/sg_pt_common.c
index 2a7a4799..14e48ae6 100644
--- a/lib/sg_pt_common.c
+++ b/lib/sg_pt_common.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdio.h>
diff --git a/lib/sg_pt_freebsd.c b/lib/sg_pt_freebsd.c
index b24d9e64..b4c5e303 100644
--- a/lib/sg_pt_freebsd.c
+++ b/lib/sg_pt_freebsd.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* sg_pt_freebsd version 1.32 20180627 */
diff --git a/lib/sg_pt_linux.c b/lib/sg_pt_linux.c
index 64956b3e..f3cb6ea0 100644
--- a/lib/sg_pt_linux.c
+++ b/lib/sg_pt_linux.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* sg_pt_linux version 1.43 20180603 */
diff --git a/lib/sg_pt_linux_nvme.c b/lib/sg_pt_linux_nvme.c
index 18b1374b..abb928cc 100644
--- a/lib/sg_pt_linux_nvme.c
+++ b/lib/sg_pt_linux_nvme.c
@@ -4,6 +4,8 @@
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
*
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
* The code to use the NVMe Management Interface (MI) SES pass-through
* was provided by WDC in November 2017.
*/
diff --git a/lib/sg_pt_osf1.c b/lib/sg_pt_osf1.c
index 35ca067c..f041ec00 100644
--- a/lib/sg_pt_osf1.c
+++ b/lib/sg_pt_osf1.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <fcntl.h>
diff --git a/lib/sg_pt_solaris.c b/lib/sg_pt_solaris.c
index dffb084a..9c3904f6 100644
--- a/lib/sg_pt_solaris.c
+++ b/lib/sg_pt_solaris.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* sg_pt_solaris version 1.10 20180808 */
diff --git a/lib/sg_pt_win32.c b/lib/sg_pt_win32.c
index 1cbc8de3..2b5fb837 100644
--- a/lib/sg_pt_win32.c
+++ b/lib/sg_pt_win32.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* sg_pt_win32 version 1.28 20180615 */
diff --git a/src/sg_bg_ctl.c b/src/sg_bg_ctl.c
index 2c62b1d6..dfdcbc46 100644
--- a/src/sg_bg_ctl.c
+++ b/src/sg_bg_ctl.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_compare_and_write.c b/src/sg_compare_and_write.c
index 159e8774..2ac3304f 100644
--- a/src/sg_compare_and_write.c
+++ b/src/sg_compare_and_write.c
@@ -23,6 +23,8 @@
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
* This command performs a SCSI COMPARE AND WRITE. See SBC-3 at
* http://www.t10.org
*
diff --git a/src/sg_copy_results.c b/src/sg_copy_results.c
index 864ca8e6..17012be2 100644
--- a/src/sg_copy_results.c
+++ b/src/sg_copy_results.c
@@ -25,18 +25,21 @@
#include "sg_unaligned.h"
#include "sg_pr2serr.h"
-/* A utility program for the Linux OS SCSI subsystem.
- * Copyright (C) 2004-2010 D. Gilbert
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2, or (at your option)
- * any later version.
-
- This program issues the SCSI command RECEIVE COPY RESULTS to a given
- SCSI device.
- It sends the command with the service action passed as the sa argument,
- and the optional list identifier passed as the list_id argument.
-*/
+/*
+ * A utility program for the Linux OS SCSI subsystem.
+ * Copyright (C) 2004-2010 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * This program issues the SCSI command RECEIVE COPY RESULTS to a given
+ * SCSI device.
+ * It sends the command with the service action passed as the sa argument,
+ * and the optional list identifier passed as the list_id argument.
+ */
static const char * version_str = "1.23 20180625";
diff --git a/src/sg_dd.c b/src/sg_dd.c
index edd8f9c3..28e6be92 100644
--- a/src/sg_dd.c
+++ b/src/sg_dd.c
@@ -7,6 +7,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program is a specialisation of the Unix "dd" command in which
* either the input or the output file is a scsi generic device, raw
* device, a block device or a normal file. The block size ('bs') is
diff --git a/src/sg_decode_sense.c b/src/sg_decode_sense.c
index 6bb08ec8..8dd682db 100644
--- a/src/sg_decode_sense.c
+++ b/src/sg_decode_sense.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_emc_trespass.c b/src/sg_emc_trespass.c
index fc3219a9..146e26b2 100644
--- a/src/sg_emc_trespass.c
+++ b/src/sg_emc_trespass.c
@@ -11,6 +11,8 @@
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
*/
#include <stdio.h>
diff --git a/src/sg_format.c b/src/sg_format.c
index af1a033d..8113b097 100644
--- a/src/sg_format.c
+++ b/src/sg_format.c
@@ -13,6 +13,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* See http://www.t10.org for relevant standards and drafts. The most recent
* draft is SBC-4 revision 2.
*/
diff --git a/src/sg_get_config.c b/src/sg_get_config.c
index 28af720a..ad3bce9e 100644
--- a/src/sg_get_config.c
+++ b/src/sg_get_config.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_get_lba_status.c b/src/sg_get_lba_status.c
index 91c7a96d..6018d4f1 100644
--- a/src/sg_get_lba_status.c
+++ b/src/sg_get_lba_status.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_ident.c b/src/sg_ident.c
index f75fb110..2bf00bb8 100644
--- a/src/sg_ident.c
+++ b/src/sg_ident.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_inq.c b/src/sg_inq.c
index b32ab879..61f4fdb3 100644
--- a/src/sg_inq.c
+++ b/src/sg_inq.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program outputs information provided by a SCSI INQUIRY command.
* It is mainly based on the SCSI SPC-5 document at http://www.t10.org .
*
diff --git a/src/sg_inq_data.c b/src/sg_inq_data.c
index 5b6b5331..96792c58 100644
--- a/src/sg_inq_data.c
+++ b/src/sg_inq_data.c
@@ -1,14 +1,16 @@
-/* A utility program originally written for the Linux OS SCSI subsystem.
-* Copyright (C) 2000-2018 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- This is an auxiliary file holding data tables for the sg_inq utility.
- It is mainly based on the SCSI SPC-5 document at http://www.t10.org .
-
-*/
+/*
+ * A utility program originally written for the Linux OS SCSI subsystem.
+ * Copyright (C) 2000-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * This is an auxiliary file holding data tables for the sg_inq utility.
+ * It is mainly based on the SCSI SPC-5 document at http://www.t10.org .
+ */
#include <unistd.h>
#include <fcntl.h>
diff --git a/src/sg_logs.c b/src/sg_logs.c
index 61443ff1..65eb3947 100644
--- a/src/sg_logs.c
+++ b/src/sg_logs.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program outputs information provided by a SCSI LOG SENSE command
* and in some cases issues a LOG SELECT command.
*
diff --git a/src/sg_luns.c b/src/sg_luns.c
index 904b2cef..d1a5030e 100644
--- a/src/sg_luns.c
+++ b/src/sg_luns.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_map.c b/src/sg_map.c
index 824334a2..ebf2c2e4 100644
--- a/src/sg_map.c
+++ b/src/sg_map.c
@@ -1,9 +1,12 @@
-/* Utility program for the Linux OS SCSI generic ("sg") device driver.
-* Copyright (C) 2000-2017 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
+/*
+ * Utility program for the Linux OS SCSI generic ("sg") device driver.
+ * Copyright (C) 2000-2017 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
This shows the mapping from "sg" devices to other scsi devices
(i.e. sd, scd or st) if any.
diff --git a/src/sg_map26.c b/src/sg_map26.c
index a48fcda5..b96eb042 100644
--- a/src/sg_map26.c
+++ b/src/sg_map26.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/* A utility program for the Linux OS SCSI subsystem.
diff --git a/src/sg_modes.c b/src/sg_modes.c
index babb05d2..ee0378e4 100644
--- a/src/sg_modes.c
+++ b/src/sg_modes.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program outputs information provided by a SCSI MODE SENSE command.
* Does 10 byte MODE SENSE commands by default, Trent Piepho added a "-6"
* switch for force 6 byte mode sense commands.
@@ -30,7 +32,7 @@
#include "sg_unaligned.h"
#include "sg_pr2serr.h"
-static const char * version_str = "1.66 20180909";
+static const char * version_str = "1.67 20181203";
#define DEF_ALLOC_LEN (1024 * 4)
#define DEF_6_ALLOC_LEN 252
@@ -133,7 +135,7 @@ static struct page_code_desc pc_desc_disk[] = {
{0x1, 0x0, "rw", "Read-Write error recovery"},
{0x3, 0x0, "fo", "Format (obsolete)"},
{0x4, 0x0, "rd", "Rigid disk geometry (obsolete)"},
- {0x5, 0x0, "fg", "Flexible geometry (obsolete)"},
+ {0x5, 0x0, "fd", "Flexible disk (obsolete)"},
{0x7, 0x0, "ve", "Verify error recovery"},
{0x8, 0x0, "ca", "Caching"},
{0xa, 0x2, "atag", "Application tag"},
diff --git a/src/sg_opcodes.c b/src/sg_opcodes.c
index a6c3d2ef..16d7c6c9 100644
--- a/src/sg_opcodes.c
+++ b/src/sg_opcodes.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program outputs information provided by a SCSI REPORT SUPPORTED
* OPERATION CODES [0xa3/0xc] and REPORT SUPPORTED TASK MANAGEMENT
* FUNCTIONS [0xa3/0xd] commands.
diff --git a/src/sg_persist.c b/src/sg_persist.c
index f582d32e..c1324c43 100644
--- a/src/sg_persist.c
+++ b/src/sg_persist.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program issues the SCSI PERSISTENT IN and OUT commands.
*/
diff --git a/src/sg_prevent.c b/src/sg_prevent.c
index 40ab1638..487315ac 100644
--- a/src/sg_prevent.c
+++ b/src/sg_prevent.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_raw.c b/src/sg_raw.c
index 92c22875..9cc0ab2b 100644
--- a/src/sg_raw.c
+++ b/src/sg_raw.c
@@ -8,6 +8,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program can be used to send raw SCSI commands (with an optional
* data phase) through a Generic SCSI interface.
*/
diff --git a/src/sg_rbuf.c b/src/sg_rbuf.c
index 61604d38..9f5055e8 100644
--- a/src/sg_rbuf.c
+++ b/src/sg_rbuf.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program uses the SCSI command READ BUFFER on the given
* device, first to find out how big it is and then to read that
* buffer (data mode, buffer id 0).
diff --git a/src/sg_rdac.c b/src/sg_rdac.c
index 73f4684a..b0d1cdcf 100644
--- a/src/sg_rdac.c
+++ b/src/sg_rdac.c
@@ -11,6 +11,8 @@
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
*/
#include <stdio.h>
diff --git a/src/sg_read.c b/src/sg_read.c
index 135d7408..a356aa35 100644
--- a/src/sg_read.c
+++ b/src/sg_read.c
@@ -1,9 +1,12 @@
-/* A utility program for the Linux OS SCSI generic ("sg") device driver.
-* Copyright (C) 2001 - 2018 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
+/*
+ * A utility program for the Linux OS SCSI generic ("sg") device driver.
+ * Copyright (C) 2001 - 2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
This program reads data from the given SCSI device (typically a disk
or cdrom) and discards that data. Its primary goal is to time
diff --git a/src/sg_read_attr.c b/src/sg_read_attr.c
index 2ae51bf8..4925b905 100644
--- a/src/sg_read_attr.c
+++ b/src/sg_read_attr.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_read_block_limits.c b/src/sg_read_block_limits.c
index 597c9b64..804dccc0 100644
--- a/src/sg_read_block_limits.c
+++ b/src/sg_read_block_limits.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_read_buffer.c b/src/sg_read_buffer.c
index 23564029..823fed73 100644
--- a/src/sg_read_buffer.c
+++ b/src/sg_read_buffer.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_read_long.c b/src/sg_read_long.c
index d094aabb..0a5e6a68 100644
--- a/src/sg_read_long.c
+++ b/src/sg_read_long.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program issues the SCSI command READ LONG to a given SCSI device.
* It sends the command with the logical block address passed as the lba
* argument, and the transfer length set to the xfer_len argument. the
diff --git a/src/sg_readcap.c b/src/sg_readcap.c
index 70b40bf3..a383ef84 100644
--- a/src/sg_readcap.c
+++ b/src/sg_readcap.c
@@ -7,6 +7,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program was originally written with Linux 2.4 kernel series.
* It now builds for the Linux 2.6, 3 and 4 kernel series and various other
* operating systems.
diff --git a/src/sg_reassign.c b/src/sg_reassign.c
index 73565c37..f522ed70 100644
--- a/src/sg_reassign.c
+++ b/src/sg_reassign.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_referrals.c b/src/sg_referrals.c
index 89775605..35cf50e6 100644
--- a/src/sg_referrals.c
+++ b/src/sg_referrals.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_rep_zones.c b/src/sg_rep_zones.c
index a0d01d25..c9619344 100644
--- a/src/sg_rep_zones.c
+++ b/src/sg_rep_zones.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_requests.c b/src/sg_requests.c
index 76053c4e..a13cab63 100644
--- a/src/sg_requests.c
+++ b/src/sg_requests.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_reset.c b/src/sg_reset.c
index 9f5648e8..a84c3d83 100644
--- a/src/sg_reset.c
+++ b/src/sg_reset.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program send either device, bus or host resets to device,
* or bus or host associated with the given sg device. This is a Linux
* only utility (perhaps Android as well).
diff --git a/src/sg_reset_wp.c b/src/sg_reset_wp.c
index 42ece34b..1dc6cab6 100644
--- a/src/sg_reset_wp.c
+++ b/src/sg_reset_wp.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_rmsn.c b/src/sg_rmsn.c
index 332a9c70..c413ea43 100644
--- a/src/sg_rmsn.c
+++ b/src/sg_rmsn.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_rtpg.c b/src/sg_rtpg.c
index ab955987..48ee4a02 100644
--- a/src/sg_rtpg.c
+++ b/src/sg_rtpg.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_safte.c b/src/sg_safte.c
index 3a102e00..588d47f8 100644
--- a/src/sg_safte.c
+++ b/src/sg_safte.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_sanitize.c b/src/sg_sanitize.c
index b45462fb..6d6fc11a 100644
--- a/src/sg_sanitize.c
+++ b/src/sg_sanitize.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_sat_identify.c b/src/sg_sat_identify.c
index 7016ef97..334ac832 100644
--- a/src/sg_sat_identify.c
+++ b/src/sg_sat_identify.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_sat_phy_event.c b/src/sg_sat_phy_event.c
index dc9372b0..a6e89610 100644
--- a/src/sg_sat_phy_event.c
+++ b/src/sg_sat_phy_event.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_sat_read_gplog.c b/src/sg_sat_read_gplog.c
index 3ea7f5cc..233ceae2 100644
--- a/src/sg_sat_read_gplog.c
+++ b/src/sg_sat_read_gplog.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_sat_set_features.c b/src/sg_sat_set_features.c
index 34336523..81313f96 100644
--- a/src/sg_sat_set_features.c
+++ b/src/sg_sat_set_features.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_scan_linux.c b/src/sg_scan_linux.c
index 5c0fc2f0..7354ad4e 100644
--- a/src/sg_scan_linux.c
+++ b/src/sg_scan_linux.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program scans the "sg" device space (ie actual + simulated SCSI
* generic devices). Optionally sg_scan can be given other device names
* to scan (in place of the sg devices).
diff --git a/src/sg_scan_win32.c b/src/sg_scan_win32.c
index d9349feb..4ba59836 100644
--- a/src/sg_scan_win32.c
+++ b/src/sg_scan_win32.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
/*
diff --git a/src/sg_seek.c b/src/sg_seek.c
index 093c6b79..9084fd75 100644
--- a/src/sg_seek.c
+++ b/src/sg_seek.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_senddiag.c b/src/sg_senddiag.c
index 60144e12..38d4e40d 100644
--- a/src/sg_senddiag.c
+++ b/src/sg_senddiag.c
@@ -1,9 +1,12 @@
-/* A utility program originally written for the Linux OS SCSI subsystem
-* Copyright (C) 2003-2018 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
+/*
+ * A utility program originally written for the Linux OS SCSI subsystem
+ * Copyright (C) 2003-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
This program issues the SCSI SEND DIAGNOSTIC command and in one case
the SCSI RECEIVE DIAGNOSTIC command to list supported diagnostic pages.
diff --git a/src/sg_ses.c b/src/sg_ses.c
index 0cce8bd1..a62f6faf 100644
--- a/src/sg_ses.c
+++ b/src/sg_ses.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_ses_microcode.c b/src/sg_ses_microcode.c
index 4f9d70ea..25011d5c 100644
--- a/src/sg_ses_microcode.c
+++ b/src/sg_ses_microcode.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_start.c b/src/sg_start.c
index a5bf6780..ccf98aa6 100644
--- a/src/sg_start.c
+++ b/src/sg_start.c
@@ -4,6 +4,8 @@
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
Start/Stop parameter by Kurt Garloff <garloff at suse dot de>, 6/2000
Sync cache parameter by Kurt Garloff <garloff at suse dot de>, 1/2001
diff --git a/src/sg_stpg.c b/src/sg_stpg.c
index c592e804..6cb78932 100644
--- a/src/sg_stpg.c
+++ b/src/sg_stpg.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_stream_ctl.c b/src/sg_stream_ctl.c
index 7e977a10..3f5eef2d 100644
--- a/src/sg_stream_ctl.c
+++ b/src/sg_stream_ctl.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_sync.c b/src/sg_sync.c
index 26867917..d300354a 100644
--- a/src/sg_sync.c
+++ b/src/sg_sync.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_test_rwbuf.c b/src/sg_test_rwbuf.c
index f187ba06..8eb604b0 100644
--- a/src/sg_test_rwbuf.c
+++ b/src/sg_test_rwbuf.c
@@ -16,6 +16,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* $Id: sg_test_rwbuf.c,v 1.1 2000/03/02 13:50:03 garloff Exp $
*
* 2003/11/11 switch sg3_utils version to use SG_IO ioctl [dpg]
diff --git a/src/sg_timestamp.c b/src/sg_timestamp.c
index 3168997c..18ddab4f 100644
--- a/src/sg_timestamp.c
+++ b/src/sg_timestamp.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_turs.c b/src/sg_turs.c
index b68f1a42..8c6e3792 100644
--- a/src/sg_turs.c
+++ b/src/sg_turs.c
@@ -5,6 +5,7 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
*/
/*
diff --git a/src/sg_unmap.c b/src/sg_unmap.c
index 726eb239..2deb71ad 100644
--- a/src/sg_unmap.c
+++ b/src/sg_unmap.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_verify.c b/src/sg_verify.c
index 0e186a9a..ad0057b8 100644
--- a/src/sg_verify.c
+++ b/src/sg_verify.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_vpd.c b/src/sg_vpd.c
index a15ed742..70e1fddf 100644
--- a/src/sg_vpd.c
+++ b/src/sg_vpd.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_vpd_vendor.c b/src/sg_vpd_vendor.c
index 3c751775..99325c94 100644
--- a/src/sg_vpd_vendor.c
+++ b/src/sg_vpd_vendor.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_wr_mode.c b/src/sg_wr_mode.c
index ce900ff0..9db253b3 100644
--- a/src/sg_wr_mode.c
+++ b/src/sg_wr_mode.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_write_buffer.c b/src/sg_write_buffer.c
index d3b02942..37dcc295 100644
--- a/src/sg_write_buffer.c
+++ b/src/sg_write_buffer.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_write_long.c b/src/sg_write_long.c
index 41c6b8bc..af323cc7 100644
--- a/src/sg_write_long.c
+++ b/src/sg_write_long.c
@@ -5,6 +5,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program issues the SCSI command WRITE LONG to a given SCSI device.
* It sends the command with the logical block address passed as the lba
* argument, and the transfer length set to the xfer_len argument. the
diff --git a/src/sg_write_same.c b/src/sg_write_same.c
index f589d0ea..d1e7d4e9 100644
--- a/src/sg_write_same.c
+++ b/src/sg_write_same.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sg_write_verify.c b/src/sg_write_verify.c
index 55b715ea..781cdd4c 100644
--- a/src/sg_write_verify.c
+++ b/src/sg_write_verify.c
@@ -4,6 +4,8 @@
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
*
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
* This program issues the SCSI command WRITE AND VERIFY to a given SCSI
* device. It sends the command with the logical block address passed as the
* LBA argument, for the given number of blocks. The number of bytes sent is
diff --git a/src/sg_write_x.c b/src/sg_write_x.c
index 3b8f0919..fa84c76b 100644
--- a/src/sg_write_x.c
+++ b/src/sg_write_x.c
@@ -4,6 +4,8 @@
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
*
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
* The utility can send six variants of the SCSI WRITE command: (normal)
* WRITE(16 or 32), WRITE ATOMIC(16 or 32), ORWRITE(16 or 32),
* WRITE SAME(16 or 32), WRITE SCATTERED (16 or 32) or WRITE
diff --git a/src/sg_xcopy.c b/src/sg_xcopy.c
index 5facfc84..6bfd1dba 100644
--- a/src/sg_xcopy.c
+++ b/src/sg_xcopy.c
@@ -11,6 +11,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program is a specialisation of the Unix "dd" command in which
* either the input or the output file is a scsi generic device, raw
* device, a block device or a normal file. The block size ('bs') is
diff --git a/src/sg_zone.c b/src/sg_zone.c
index 9c5cda21..b7f8391f 100644
--- a/src/sg_zone.c
+++ b/src/sg_zone.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
diff --git a/src/sginfo.c b/src/sginfo.c
index bddc9641..6a514fc1 100644
--- a/src/sginfo.c
+++ b/src/sginfo.c
@@ -62,6 +62,8 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* Michael Weller (eowmob at exp-math dot uni-essen dot de)
* 11/23/94 massive extensions from 1.4a
* 08/23/97 fix problems with defect lists
diff --git a/src/sgm_dd.c b/src/sgm_dd.c
index c3b8c717..0b6cf044 100644
--- a/src/sgm_dd.c
+++ b/src/sgm_dd.c
@@ -6,6 +6,8 @@
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
This program is a specialisation of the Unix "dd" command in which
either the input or the output file is a scsi generic device. The block
diff --git a/src/sgp_dd.c b/src/sgp_dd.c
index db871776..b129d575 100644
--- a/src/sgp_dd.c
+++ b/src/sgp_dd.c
@@ -7,6 +7,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program is a specialisation of the Unix "dd" command in which
* one or both of the given files is a scsi generic device or a raw
* device. A block size ('bs') is assumed to be 512 if not given. This
diff --git a/testing/Makefile b/testing/Makefile
index 9878c04e..c4dfbc30 100644
--- a/testing/Makefile
+++ b/testing/Makefile
@@ -4,15 +4,6 @@ PREFIX=/usr/local
INSTDIR=$(DESTDIR)/$(PREFIX)/bin
MANDIR=$(DESTDIR)/$(PREFIX)/man
-# In Linux the default C compiler is GCC while in FreeBSD (since release 10 ?)
-# the default C compiler is clang. Swap the comment marks (lines starting
-# with '#') on the next 4 (non-blank) lines.
-CC = gcc
-# CC = clang
-
-LD = gcc
-# LD = clang
-
EXECS = sg_iovec_tst sg_sense_test sg_queue_tst bsg_queue_tst sg_chk_asc \
sg_tst_nvme sg_tst_ioctl tst_sg_lib sgs_dd
@@ -32,6 +23,8 @@ LARGE_FILE_FLAGS = -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64
## CC = clang
## CC = clang++
+LD = $(CC)
+
CPPFLAGS = -iquote ../include -iquote .. -D_REENTRANT $(LARGE_FILE_FLAGS) -DHAVE_CONFIG_H -DHAVE_NVME
# CPPFLAGS = -iquote ../include -iquote .. -D_REENTRANT $(LARGE_FILE_FLAGS) -DHAVE_CONFIG_H -DHAVE_NVME -DDEBUG
CFLAGS = -g -O2 -W -Wall
diff --git a/testing/sg_chk_asc.c b/testing/sg_chk_asc.c
index ef37729f..dd320fd5 100644
--- a/testing/sg_chk_asc.c
+++ b/testing/sg_chk_asc.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
@@ -25,7 +27,7 @@
* http://www.t10.org/lists/asc-num.txt
*/
-static const char * version_str = "1.06 20180119";
+static const char * version_str = "1.07 20181207";
#define MAX_LINE_LEN 1024
diff --git a/testing/sg_iovec_tst.c b/testing/sg_iovec_tst.c
index a968e385..b066e8b0 100644
--- a/testing/sg_iovec_tst.c
+++ b/testing/sg_iovec_tst.c
@@ -1,3 +1,22 @@
+/*
+ * Copyright (C) 2003-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * Test code for D. Gilbert's extensions to the Linux OS SCSI generic ("sg")
+ * device driver.
+ * This program will read a certain number of blocks of a given block size
+ * from a given sg device node and write what is retrieved out to a
+ * normal file. The purpose is to test the sg_iovec mechanism within the
+ * sg_io_hdr structure.
+ *
+ * Version 0.17 (20181207)
+ */
+
#include <unistd.h>
#include <signal.h>
#include <fcntl.h>
@@ -14,21 +33,6 @@
#include "sg_io_linux.h"
#include "sg_unaligned.h"
-/* Test code for D. Gilbert's extensions to the Linux OS SCSI generic ("sg")
- device driver.
-* Copyright (C) 2003-2018 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- This program will read a certain number of blocks of a given block size
- from a given sg device node and write what is retrieved out to a
- normal file. The purpose is to test the sg_iovec mechanism within the
- sg_io_hdr structure.
-
- Version 0.16 (20180219)
-*/
#define ME "sg_iovec_tst: "
diff --git a/testing/sg_queue_tst.c b/testing/sg_queue_tst.c
index e9c03af1..a3f8dc0c 100644
--- a/testing/sg_queue_tst.c
+++ b/testing/sg_queue_tst.c
@@ -1,3 +1,23 @@
+/*
+ * Copyright (C) 2010-2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ *
+ * This program was used to test SCSI mid level queue ordering.
+ * The default behaviour is to "queue at head" which is useful for
+ * error processing but not for streaming READ and WRITE commands.
+ *
+ * Invocation: sg_queue_tst [-l=Q_LEN] [-t] <sg_device>
+ * -t queue at tail
+ *
+ * Version 0.93 (20181207)
+ */
+
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
@@ -13,22 +33,7 @@
#include "sg_io_linux.h"
#include "sg_linux_inc.h"
-/* This program was used to test SCSI mid level queue ordering.
- The default behaviour is to "queue at head" which is useful for
- error processing but not for streaming READ and WRITE commands.
-
-* Copyright (C) 2010-2018 D. Gilbert
-* This program is free software; you can redistribute it and/or modify
-* it under the terms of the GNU General Public License as published by
-* the Free Software Foundation; either version 2, or (at your option)
-* any later version.
-
- Invocation: sg_queue_tst [-l=Q_LEN] [-t] <sg_device>
- -t queue at tail
-
- Version 0.92 (20181011)
-*/
#define INQ_REPLY_LEN 96
#define INQ_CMD_LEN 6
diff --git a/testing/sg_sense_test.c b/testing/sg_sense_test.c
index ea8bfd54..ce66cf3e 100644
--- a/testing/sg_sense_test.c
+++ b/testing/sg_sense_test.c
@@ -4,6 +4,8 @@
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
*/
/* This is a simple program that tests the sense data descriptor format
@@ -24,7 +26,7 @@
#define ME "sg_sense_test: "
-static const char * version_str = "2.03 20180220";
+static const char * version_str = "2.04 20181207";
static struct option long_options[] = {
{"help", no_argument, 0, 'h'},
diff --git a/testing/sg_tst_async.cpp b/testing/sg_tst_async.cpp
index 485bae83..a6ac65ee 100644
--- a/testing/sg_tst_async.cpp
+++ b/testing/sg_tst_async.cpp
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -24,6 +22,8 @@
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <iostream>
@@ -82,7 +82,7 @@
#include "sg_pt.h"
#include "sg_cmds.h"
-static const char * version_str = "1.21 20181107";
+static const char * version_str = "1.22 20181207";
static const char * util_name = "sg_tst_async";
/* This is a test program for checking the async usage of the Linux sg
diff --git a/testing/sg_tst_context.cpp b/testing/sg_tst_context.cpp
index b811c56e..89b7a7d2 100644
--- a/testing/sg_tst_context.cpp
+++ b/testing/sg_tst_context.cpp
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -24,6 +22,8 @@
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <iostream>
@@ -46,7 +46,7 @@
#include "sg_lib.h"
#include "sg_pt.h"
-static const char * version_str = "1.03 20180712";
+static const char * version_str = "1.04 20181207";
static const char * util_name = "sg_tst_context";
/* This is a test program for checking that file handles keep their
diff --git a/testing/sg_tst_excl.cpp b/testing/sg_tst_excl.cpp
index 5b4e6956..d5c0bec8 100644
--- a/testing/sg_tst_excl.cpp
+++ b/testing/sg_tst_excl.cpp
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2013-2014 Douglas Gilbert.
+ * Copyright (c) 2013-2018 Douglas Gilbert.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -24,6 +22,8 @@
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <iostream>
@@ -46,7 +46,7 @@
#include "sg_lib.h"
#include "sg_io_linux.h"
-static const char * version_str = "1.09 20140828";
+static const char * version_str = "1.10 20181207";
static const char * util_name = "sg_tst_excl";
/* This is a test program for checking O_EXCL on open() works. It uses
diff --git a/testing/sg_tst_excl2.cpp b/testing/sg_tst_excl2.cpp
index 24d3677b..9a03906c 100644
--- a/testing/sg_tst_excl2.cpp
+++ b/testing/sg_tst_excl2.cpp
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -24,6 +22,8 @@
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <iostream>
@@ -46,7 +46,7 @@
#include "sg_lib.h"
#include "sg_pt.h"
-static const char * version_str = "1.07 20140828";
+static const char * version_str = "1.08 20181207";
static const char * util_name = "sg_tst_excl2";
/* This is a test program for checking O_EXCL on open() works. It uses
diff --git a/testing/sg_tst_excl3.cpp b/testing/sg_tst_excl3.cpp
index 6b6b880b..bd15389a 100644
--- a/testing/sg_tst_excl3.cpp
+++ b/testing/sg_tst_excl3.cpp
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2013-2014 Douglas Gilbert.
+ * Copyright (c) 2013-2018 Douglas Gilbert.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -10,8 +10,6 @@
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
- * 3. The name of the author may not be used to endorse or promote products
- * derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
@@ -24,6 +22,8 @@
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <iostream>
@@ -46,7 +46,7 @@
#include "sg_lib.h"
#include "sg_pt.h"
-static const char * version_str = "1.05 20140828";
+static const char * version_str = "1.06 20181207";
static const char * util_name = "sg_tst_excl3";
/* This is a test program for checking O_EXCL on open() works. It uses
diff --git a/testing/sg_tst_ioctl.c b/testing/sg_tst_ioctl.c
index b37be2e6..d7dc227b 100644
--- a/testing/sg_tst_ioctl.c
+++ b/testing/sg_tst_ioctl.c
@@ -1,3 +1,16 @@
+/*
+ * Copyright (C) 2018 D. Gilbert
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2, or (at your option)
+ * any later version.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
+ * Invocation: See usage() function below.
+ *
+ */
+
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
@@ -31,18 +44,8 @@
/* This program tests ioctl() calls added and modified in version 3.9 and
* later of the Linux sg driver. */
-/*
- * Copyright (C) 2018 D. Gilbert
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2, or (at your option)
- * any later version.
- *
- * Invocation: See usage() function below.
- *
- */
-static const char * version_str = "Version: 0.97 20181121";
+static const char * version_str = "Version: 0.98 20181207";
#define INQ_REPLY_LEN 96
#define INQ_CMD_LEN 6
diff --git a/testing/sg_tst_nvme.c b/testing/sg_tst_nvme.c
index bded6b69..6ba16476 100644
--- a/testing/sg_tst_nvme.c
+++ b/testing/sg_tst_nvme.c
@@ -4,6 +4,8 @@
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
*
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
* This program issues a NVMe Identify command (controller or namespace)
* or a Device self-test command via the "SCSI" pass-through interface of
* this packages sg_utils library. That interface is primarily shown in
@@ -37,7 +39,7 @@
#include "sg_unaligned.h"
#include "sg_pr2serr.h"
-static const char * version_str = "1.04 20180220";
+static const char * version_str = "1.05 20181207";
#define ME "sg_tst_nvme: "
diff --git a/testing/sgs_dd.c b/testing/sgs_dd.c
index a82ca80a..95d36fc2 100644
--- a/testing/sgs_dd.c
+++ b/testing/sgs_dd.c
@@ -7,6 +7,8 @@
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
* This program is a specialisation of the Unix "dd" command in which
* one or both of the given files is a scsi generic device.
* A block size ('bs') is assumed to be 512 if not given. This
@@ -58,6 +60,7 @@
#include <sys/time.h>
#include <linux/major.h> /* for MEM_MAJOR, SCSI_GENERIC_MAJOR, etc */
#include <linux/fs.h> /* for BLKSSZGET and friends */
+#include <sys/mman.h> /* for mmap() system call */
#ifdef HAVE_CONFIG_H
#include "config.h"
@@ -85,7 +88,11 @@
#include "sg_pr2serr.h"
-static const char * version_str = "1.03 20181126";
+static const char * version_str = "1.04 20181207";
+
+#ifdef __GNUC__
+#pragma GCC diagnostic ignored "-Wclobbered"
+#endif
#define DEF_BLOCK_SIZE 512
#define DEF_BLOCKS_PER_TRANSFER 128
@@ -122,14 +129,17 @@ static const char * version_str = "1.03 20181126";
#define EBUFF_SZ 768
struct flags_t {
+ bool fds2; /* flag is called '2fds' */
bool append;
bool coe;
+ bool defres; /* without this res_sz==bs*bpt */
bool dio;
bool direct;
bool dpo;
bool dsync;
bool excl;
bool fua;
+ bool mmap;
bool noshare;
};
@@ -141,9 +151,9 @@ typedef struct global_collection
int cdbsz_in;
int help;
struct flags_t in_flags;
- int64_t in_blk; /* -\ next block address to read */
- int64_t in_count; /* | blocks remaining for next read */
- int64_t in_rem_count; /* | count of remaining in blocks */
+ int64_t in_blk; /* -\ next block address to read */
+ int64_t in_count; /* | blocks remaining for next read */
+ int64_t in_rem_count; /* | count of remaining in blocks */
int in_partial; /* | */
bool in_stop; /* | */
pthread_mutex_t in_mutex; /* -/ */
@@ -154,20 +164,22 @@ typedef struct global_collection
int out2_type;
int cdbsz_out;
struct flags_t out_flags;
- int64_t out_blk; /* -\ next block address to write */
- int64_t out_count; /* | blocks remaining for next write */
- int64_t out_rem_count; /* | count of remaining out blocks */
+ int64_t out_blk; /* -\ next block address to write */
+ int64_t out_count; /* | blocks remaining for next write */
+ int64_t out_rem_count; /* | count of remaining out blocks */
int out_partial; /* | */
bool out_stop; /* | */
pthread_mutex_t out_mutex; /* | */
- pthread_cond_t out_sync_cv; /* -/ hold writes until "in order" */
+ pthread_cond_t out_sync_cv; /* | hold writes until "in order" */
+ pthread_cond_t hold_1st_cv; /* -/ wait for 1st thread to do 1 seg */
int bs;
int bpt;
int dio_incomplete_count; /* -\ */
- int sum_of_resids; /* | */
- pthread_mutex_t aux_mutex; /* -/ (also serializes some printf()s */
+ int sum_of_resids; /* -/ */
int debug; /* both -v and deb=VERB bump this field */
int dry_run;
+ const char * infp;
+ const char * outfp;
} Gbl_coll;
typedef struct request_element
@@ -190,6 +202,7 @@ typedef struct request_element
int resid;
int cdbsz_in;
int cdbsz_out;
+ int mmap_len;
struct flags_t in_flags;
struct flags_t out_flags;
int debug;
@@ -199,6 +212,7 @@ typedef struct thread_info
{
int id;
Gbl_coll * gcp;
+ pthread_t a_pthr;
} Thread_info;
static sigset_t signal_set;
@@ -206,12 +220,16 @@ static pthread_t sig_listen_thread_id;
static const char * proc_allow_dio = "/proc/scsi/sg/allow_dio";
-static void sg_in_operation(Gbl_coll * clp, Rq_elem * rep);
-static void sg_out_operation(Gbl_coll * clp, Rq_elem * rep);
-static bool normal_in_operation(Gbl_coll * clp, Rq_elem * rep, int blocks);
-static void normal_out_operation(Gbl_coll * clp, Rq_elem * rep, int blocks);
+static void sg_in_rd_cmd(Gbl_coll * clp, Rq_elem * rep);
+static void sg_out_wr_cmd(Gbl_coll * clp, Rq_elem * rep);
+static bool normal_in_rd(Gbl_coll * clp, Rq_elem * rep, int blocks);
+static void normal_out_wr(Gbl_coll * clp, Rq_elem * rep, int blocks);
static int sg_start_io(Rq_elem * rep);
-static int sg_finish_io(bool wr, Rq_elem * rep, pthread_mutex_t * a_mutp);
+static int sg_finish_io(bool wr, Rq_elem * rep);
+static int sg_in_open(Gbl_coll *clp, const char *inf, uint8_t **mmpp,
+ int *mmap_len);
+static int sg_out_open(Gbl_coll *clp, const char *outf, uint8_t **mmpp,
+ int *mmap_len);
#define STRERR_BUFF_LEN 128
@@ -275,6 +293,22 @@ pr_errno_lk(int e_no, const char * fmt, ...)
#endif
static void
+lk_print_command(uint8_t * cmdp)
+{
+ pthread_mutex_lock(&strerr_mut);
+ sg_print_command(cmdp);
+ pthread_mutex_unlock(&strerr_mut);
+}
+
+static void
+lk_chk_n_print3(const char * leadin, struct sg_io_hdr * hp, bool raw_sinfo)
+{
+ pthread_mutex_lock(&strerr_mut);
+ sg_chk_n_print3(leadin, hp, raw_sinfo);
+ pthread_mutex_unlock(&strerr_mut);
+}
+
+static void
calc_duration_throughput(int contin)
{
struct timeval end_tm, res_tm;
@@ -419,8 +453,11 @@ dd_filetype(const char * filename)
static void
usage(int pg_num)
{
- if (pg_num > 0)
+ if (pg_num > 2)
+ goto page3;
+ else if (pg_num > 1)
goto page2;
+
pr2serr("Usage: sgs_dd [bs=BS] [count=COUNT] [ibs=BS] [if=IFILE]"
" [iflag=FLAGS]\n"
" [obs=BS] [of=OFILE] [oflag=FLAGS] "
@@ -430,32 +467,28 @@ usage(int pg_num)
"[deb=VERB] [dio=0|1]\n"
" [fua=0|1|2|3] [of2=OFILE2] [sync=0|1] [thr=THR] "
"[time=0|1]\n"
- " [verbose=VERB] [--dry-run] [--verbose]\n"
+ " [verbose=VERB] [--dry-run] [--verbose]\n\n"
" where the main options (shown in first group above) are:\n"
" bs must be device block size (default 512)\n"
" count number of blocks to copy (def: device size)\n"
" if file or device to read from (def: stdin)\n"
- " iflag comma separated list from: [coe,dio,direct,dpo,"
- "dsync,excl,\n"
- " fua,noshare,null]\n"
+ " iflag comma separated list from: [2fds,coe,defres,dio,"
+ "direct,dpo,\n"
+ " dsync,excl,fua,mmap,noshare,null]\n"
" of file or device to write to (def: stdout), "
"OFILE of '.'\n"
" treated as /dev/null\n"
- " oflag comma separated list from: [append,coe,dio,"
- "direct,dpo,dsync,\n"
- " excl,fua,noshare,null]\n"
+ " oflag comma separated list from: [2fds,append,coe,dio,"
+ "direct,dpo,\n"
+ " dsync,excl,fua,mmap,noshare,null]\n"
" seek block position to start writing to OFILE\n"
" skip block position to start reading from IFILE\n"
" --help|-h output this usage message then exit\n"
" --version|-V output version string then exit\n\n"
"Copy from IFILE to OFILE, similar to dd command. This utility "
"is specialized\nfor SCSI devices and uses multiple POSIX "
- "threads. It expects one or both\nIFILE and OFILE to be SCSI "
- "generic devices. If both are sg devices 'shared'\nmode is "
- "selected unless 'noshare' is given to 'iflag=' or 'oflag='. "
- "If\n'of2=OFLAG2' is given, the read-side is output to OFLAG2. "
- "Without 'of2=' and\nwith IFILE and OFILE sg devices the copy "
- "is via a single in-kernel buffer.\n"
+ "threads. It expects one or both\nIFILE and OFILE to be sg "
+ "devices. Use '-hh' or '-hhh' for more information.\n"
);
return;
page2:
@@ -486,7 +519,40 @@ page2:
"throughput\n"
" verbose same as 'deb=VERB': increase verbosity\n"
" --dry-run|-d prepare but bypass copy/read\n"
- " --verbose|-v increase verbosity of utility\n"
+ " --verbose|-v increase verbosity of utility\n\n"
+ "Use '-hhh' for more information about flags.\n"
+ );
+ return;
+page3:
+ pr2serr("Syntax: sgs_dd [operands] [options]\n\n"
+ " where: iflag=' and 'oflag=' arguments are listed below:\n"
+ " 2fds only 2 file descriptors (1 each for IFILE and "
+ "OFILE) are\n"
+ " used. Default: a pair of fd_s for each thread\n"
+ " append append output to OFILE (assumes OFILE is "
+ "regular file)\n"
+ " coe continue of error (reading, fills with zeros)\n"
+ " defres keep default reserve buffer size (else its "
+ "bs*bpt)\n"
+ " dio sets the SG_FLAG_DIRECT_IO in sg requests\n"
+ " direct sets the O_DIRECT flag on open()\n"
+ " dpo sets the DPO (disable page out) in SCSI READs "
+ "and WRITEs\n"
+ " dsync sets the O_SYNC flag on open()\n"
+ " excl sets the O_EXCL flag on open()\n"
+ " fua sets the FUA (force unit access) in SCSI READs "
+ "and WRITEs\n"
+ " mmap setup mmap IO on IFILE or OFILE; OFILE only "
+ "with noshare\n"
+ " noshare if IFILE and OFILE are sg devices, don't set "
+ "up share\n"
+ " (def: do)\n"
+ "\n"
+ "If both are sg devices 'shared' mode is selected unless "
+ "'noshare' is given\nto 'iflag=' or 'oflag='. If 'of2=OFLAG2' "
+ "is given, the read-side is output\nto OFLAG2. Without 'of2=' "
+ "and with IFILE and OFILE sg devices the copy is\nvia a single "
+ "in-kernel buffer.\n"
);
}
@@ -609,12 +675,15 @@ sg_share_prepare(int slave_writer_fd, int master_reader_fd, int id, bool vb_b)
seip->valid_rd_mask |= SG_SEIM_SHARE_FD;
seip->share_fd = master_reader_fd;
if (ioctl(slave_writer_fd, SG_SET_GET_EXTENDED, seip) < 0) {
- if (vb_b)
- pr2serr_lk("tid=%d: ioctl(EXTENDED(shared_fd=%d), failed "
- "errno=%d %s\n", id, master_reader_fd, errno,
- strerror(errno));
+ pr2serr_lk("tid=%d: ioctl(EXTENDED(shared_fd=%d), failed "
+ "errno=%d %s\n", id, master_reader_fd, errno,
+ strerror(errno));
return false;
}
+ if (vb_b)
+ pr2serr_lk("%s: tid=%d: ioctl(EXTENDED(shared_fd)) ok, master_fd=%d, "
+ "slave_fd=%d\n", __func__, id, master_reader_fd,
+ slave_writer_fd);
return true;
}
@@ -635,7 +704,7 @@ cleanup_out(void * v_clp)
{
Gbl_coll * clp = (Gbl_coll *)v_clp;
- pr2serr("thread cancelled while out mutex held\n");
+ pr2serr("thread cancelled while out_mutex held\n");
clp->out_stop = true;
pthread_mutex_unlock(&clp->out_mutex);
guarded_stop_in(clp);
@@ -649,9 +718,13 @@ read_write_thread(void * v_tip)
Gbl_coll * clp;
Rq_elem rel;
Rq_elem * rep = &rel;
- int sz, blocks, status, vb;
+ int sz, blocks, status, vb, err, res;
int64_t seek_skip;
volatile bool stop_after_write = false;
+ bool own_infd = false;
+ bool own_outfd = false;
+ bool is_first = true;
+ bool share_and_of2;
tip = (Thread_info *)v_tip;
clp = tip->gcp;
@@ -659,12 +732,14 @@ read_write_thread(void * v_tip)
sz = clp->bpt * clp->bs;
seek_skip = clp->seek - clp->skip;
memset(rep, 0, sizeof(Rq_elem));
- rep->buffp = sg_memalign(sz, 0 /* page align */, &rep->alloc_bp, false);
- if (NULL == rep->buffp)
- err_exit(ENOMEM, "out of memory creating user buffers\n");
-
/* Following clp members are constant during lifetime of thread */
rep->id = tip->id;
+ if (! clp->in_flags.mmap) {
+ rep->buffp = sg_memalign(sz, 0 /* page align */, &rep->alloc_bp,
+ false);
+ if (NULL == rep->buffp)
+ err_exit(ENOMEM, "out of memory creating user buffers\n");
+ }
rep->bs = clp->bs;
rep->infd = clp->infd;
@@ -675,17 +750,56 @@ read_write_thread(void * v_tip)
rep->cdbsz_out = clp->cdbsz_out;
rep->in_flags = clp->in_flags;
rep->out_flags = clp->out_flags;
+ if (rep->in_flags.fds2 || rep->out_flags.fds2)
+ ;
+ else {
+ int fd;
+
+ if ((FT_SG == clp->in_type) && clp->infp) {
+ fd = sg_in_open(clp, clp->infp,
+ (rep->in_flags.mmap ? &rep->buffp : NULL),
+ (rep->in_flags.mmap ? &rep->mmap_len : NULL));
+ if (fd < 0)
+ goto fini;
+ rep->infd = fd;
+ own_infd = true;
+ if (vb > 2)
+ pr2serr_lk("thread=%d: opened local sg IFILE\n", rep->id);
+ }
+ if ((FT_SG == clp->out_type) && clp->outfp) {
+ fd = sg_out_open(clp, clp->outfp,
+ (rep->out_flags.mmap ? &rep->buffp : NULL),
+ (rep->out_flags.mmap ? &rep->mmap_len : NULL));
+ if (fd < 0)
+ goto fini;
+ rep->outfd = fd;
+ own_outfd = true;
+ if (vb > 2)
+ pr2serr_lk("thread=%d: opened local sg OFILE\n", rep->id);
+ }
+ }
+ if (vb > 2) {
+ if (! own_infd)
+ pr2serr_lk("thread=%d: using global sg IFILE\n", rep->id);
+ if (! own_outfd)
+ pr2serr_lk("thread=%d: using global sg OFILE\n", rep->id);
+ }
if (rep->in_flags.noshare || rep->out_flags.noshare) {
if (vb)
- pr2serr_lk("Skipping share on both IFILE and OFILE\n");
- } else
- rep->has_share = sg_share_prepare(clp->outfd, clp->infd, rep->id,
- clp->debug);
+ pr2serr_lk("thread=%d: Skipping share on both IFILE and OFILE\n",
+ rep->id);
+ } else if ((FT_SG == clp->in_type) && (FT_SG == clp->out_type))
+ rep->has_share = sg_share_prepare(rep->outfd, rep->infd, rep->id,
+ rep->debug);
if (vb > 0)
pr2serr_lk("starting thread %d, has_share=%s\n", rep->id,
(rep->has_share ? "true" : "false"));
+ share_and_of2 = (rep->has_share && (rep->out2fd >= 0));
- while(1) {
+ /* vvvvvvvvvvvvvv Main segment copy loop vvvvvvvvvvvvvvvvvvvvvvv */
+ while (1) {
+ rep->wr = false;
+ /* Start of READ half of a segment */
status = pthread_mutex_lock(&clp->in_mutex);
if (0 != status) err_exit(status, "lock in_mutex");
if (clp->in_stop || (clp->in_count <= 0)) {
@@ -695,7 +809,6 @@ read_write_thread(void * v_tip)
break;
}
blocks = (clp->in_count > clp->bpt) ? clp->bpt : clp->in_count;
- rep->wr = false;
rep->blk = clp->in_blk;
rep->num_blks = blocks;
clp->in_blk += blocks;
@@ -703,17 +816,19 @@ read_write_thread(void * v_tip)
pthread_cleanup_push(cleanup_in, (void *)clp);
if (FT_SG == clp->in_type)
- sg_in_operation(clp, rep); /* go off in_mutex mid operation */
+ sg_in_rd_cmd(clp, rep); /* unlocks in_mutex mid operation */
else {
- stop_after_write = normal_in_operation(clp, rep, blocks);
+ stop_after_write = normal_in_rd(clp, rep, blocks);
status = pthread_mutex_unlock(&clp->in_mutex);
if (0 != status) err_exit(status, "unlock in_mutex");
}
pthread_cleanup_pop(0);
+ /* Start of WRITE part of a segment */
+ rep->wr = true;
status = pthread_mutex_lock(&clp->out_mutex);
if (0 != status) err_exit(status, "lock out_mutex");
- if (FT_DEV_NULL != clp->out_type) {
+ if (share_and_of2 || (FT_DEV_NULL != clp->out_type)) {
while ((! clp->out_stop) &&
((rep->blk + seek_skip) != clp->out_blk)) {
/* if write would be out of sequence then wait */
@@ -733,7 +848,6 @@ read_write_thread(void * v_tip)
}
if (stop_after_write)
clp->out_stop = true;
- rep->wr = true;
rep->blk = clp->out_blk;
clp->out_blk += blocks;
clp->out_count -= blocks;
@@ -747,8 +861,15 @@ read_write_thread(void * v_tip)
}
pthread_cleanup_push(cleanup_out, (void *)clp);
+ if (share_and_of2) {
+ res = write(rep->out2fd, rep->buffp, rep->bs * rep->num_blks);
+ err = errno;
+ if (res < 0)
+ pr2serr_lk("%s: tid=%d: write(out2fd) failed: %s\n", __func__,
+ rep->id, strerror(err));
+ }
if (FT_SG == clp->out_type)
- sg_out_operation(clp, rep); /* releases out_mutex mid oper */
+ sg_out_wr_cmd(clp, rep); /* releases out_mutex mid oper */
else if (FT_DEV_NULL == clp->out_type) {
/* skip actual write operation */
clp->out_rem_count -= blocks;
@@ -756,17 +877,32 @@ read_write_thread(void * v_tip)
if (0 != status) err_exit(status, "unlock out_mutex");
}
else {
- normal_out_operation(clp, rep, blocks);
+ normal_out_wr(clp, rep, blocks);
status = pthread_mutex_unlock(&clp->out_mutex);
if (0 != status) err_exit(status, "unlock out_mutex");
}
pthread_cleanup_pop(0);
+ // if ((! rep->has_share) && (FT_DEV_NULL != clp->out_type))
+ pthread_cond_broadcast(&clp->out_sync_cv);
+ if ((0 == rep->id) && is_first) {
+ is_first = false; /* allow rest of threads to start */
+ pthread_cond_broadcast(&clp->hold_1st_cv);
+ }
if (stop_after_write)
break;
- pthread_cond_broadcast(&clp->out_sync_cv);
- } /* end of while loop */
- if (rep->alloc_bp)
+ } /* end of while loop which copies segments */
+
+ if (rep->mmap_len > 0) {
+ if (munmap(rep->buffp, rep->mmap_len) < 0) {
+ int err = errno;
+ char bb[64];
+
+ pr2serr_lk("thread=%d: munmap() failed: %s\n", rep->id,
+ tsafe_strerror(err, bb));
+ }
+
+ } else if (rep->alloc_bp)
free(rep->alloc_bp);
status = pthread_mutex_lock(&clp->in_mutex);
if (0 != status) err_exit(status, "lock in_mutex");
@@ -774,12 +910,17 @@ read_write_thread(void * v_tip)
clp->in_stop = true; /* flag other workers to stop */
status = pthread_mutex_unlock(&clp->in_mutex);
if (0 != status) err_exit(status, "unlock in_mutex");
+fini:
+ if (own_infd)
+ close(rep->infd);
+ if (own_outfd)
+ close(rep->outfd);
pthread_cond_broadcast(&clp->out_sync_cv);
return stop_after_write ? NULL : clp;
}
static bool
-normal_in_operation(Gbl_coll * clp, Rq_elem * rep, int blocks)
+normal_in_rd(Gbl_coll * clp, Rq_elem * rep, int blocks)
{
bool stop_after_write = false;
int res;
@@ -826,7 +967,7 @@ normal_in_operation(Gbl_coll * clp, Rq_elem * rep, int blocks)
}
static void
-normal_out_operation(Gbl_coll * clp, Rq_elem * rep, int blocks)
+normal_out_wr(Gbl_coll * clp, Rq_elem * rep, int blocks)
{
int res;
char strerr_buff[STRERR_BUFF_LEN];
@@ -932,13 +1073,13 @@ sg_build_scsi_cdb(uint8_t * cdbp, int cdb_sz, unsigned int blocks,
return 0;
}
+/* Enters this function holding in_mutex */
static void
-sg_in_operation(Gbl_coll * clp, Rq_elem * rep)
+sg_in_rd_cmd(Gbl_coll * clp, Rq_elem * rep)
{
int res;
int status;
- /* enters holding in_mutex */
while (1) {
res = sg_start_io(rep);
if (1 == res)
@@ -955,7 +1096,7 @@ sg_in_operation(Gbl_coll * clp, Rq_elem * rep)
status = pthread_mutex_unlock(&clp->in_mutex);
if (0 != status) err_exit(status, "unlock in_mutex");
- res = sg_finish_io(rep->wr, rep, &clp->aux_mutex);
+ res = sg_finish_io(rep->wr, rep);
switch (res) {
case SG_LIB_CAT_ABORTED_COMMAND:
case SG_LIB_CAT_UNIT_ATTENTION:
@@ -964,7 +1105,7 @@ sg_in_operation(Gbl_coll * clp, Rq_elem * rep)
/* N.B. This re-read could now be out of read sequence */
status = pthread_mutex_lock(&clp->in_mutex);
if (0 != status) err_exit(status, "lock in_mutex");
- break;
+ break; /* will loop again */
case SG_LIB_CAT_MEDIUM_HARD:
if (0 == clp->in_flags.coe) {
pr2serr_lk("error finishing sg in command (medium)\n");
@@ -985,16 +1126,12 @@ sg_in_operation(Gbl_coll * clp, Rq_elem * rep)
#endif
#endif
case 0:
+ status = pthread_mutex_lock(&clp->in_mutex);
+ if (0 != status) err_exit(status, "lock in_mutex");
if (rep->dio_incomplete_count || rep->resid) {
- status = pthread_mutex_lock(&clp->aux_mutex);
- if (0 != status) err_exit(status, "lock aux_mutex");
clp->dio_incomplete_count += rep->dio_incomplete_count;
clp->sum_of_resids += rep->resid;
- status = pthread_mutex_unlock(&clp->aux_mutex);
- if (0 != status) err_exit(status, "unlock aux_mutex");
}
- status = pthread_mutex_lock(&clp->in_mutex);
- if (0 != status) err_exit(status, "lock in_mutex");
clp->in_rem_count -= rep->num_blks;
status = pthread_mutex_unlock(&clp->in_mutex);
if (0 != status) err_exit(status, "unlock in_mutex");
@@ -1007,17 +1144,16 @@ sg_in_operation(Gbl_coll * clp, Rq_elem * rep)
guarded_stop_both(clp);
return;
}
- }
+ } /* end of while (1) loop */
}
+/* Enters this function holding out_mutex */
static void
-sg_out_operation(Gbl_coll * clp, Rq_elem * rep)
+sg_out_wr_cmd(Gbl_coll * clp, Rq_elem * rep)
{
int res;
int status;
-
- /* enters holding out_mutex */
while (1) {
res = sg_start_io(rep);
if (1 == res)
@@ -1034,7 +1170,7 @@ sg_out_operation(Gbl_coll * clp, Rq_elem * rep)
status = pthread_mutex_unlock(&clp->out_mutex);
if (0 != status) err_exit(status, "unlock out_mutex");
- res = sg_finish_io(rep->wr, rep, &clp->aux_mutex);
+ res = sg_finish_io(rep->wr, rep);
switch (res) {
case SG_LIB_CAT_ABORTED_COMMAND:
case SG_LIB_CAT_UNIT_ATTENTION:
@@ -1043,7 +1179,7 @@ sg_out_operation(Gbl_coll * clp, Rq_elem * rep)
/* N.B. This re-write could now be out of write sequence */
status = pthread_mutex_lock(&clp->out_mutex);
if (0 != status) err_exit(status, "lock out_mutex");
- break;
+ break; /* loops around */
case SG_LIB_CAT_MEDIUM_HARD:
if (0 == clp->out_flags.coe) {
pr2serr_lk("error finishing sg out command (medium)\n");
@@ -1061,16 +1197,12 @@ sg_out_operation(Gbl_coll * clp, Rq_elem * rep)
#endif
#endif
case 0:
+ status = pthread_mutex_lock(&clp->out_mutex);
+ if (0 != status) err_exit(status, "lock out_mutex");
if (rep->dio_incomplete_count || rep->resid) {
- status = pthread_mutex_lock(&clp->aux_mutex);
- if (0 != status) err_exit(status, "lock aux_mutex");
clp->dio_incomplete_count += rep->dio_incomplete_count;
clp->sum_of_resids += rep->resid;
- status = pthread_mutex_unlock(&clp->aux_mutex);
- if (0 != status) err_exit(status, "unlock aux_mutex");
}
- status = pthread_mutex_lock(&clp->out_mutex);
- if (0 != status) err_exit(status, "lock out_mutex");
clp->out_rem_count -= rep->num_blks;
status = pthread_mutex_unlock(&clp->out_mutex);
if (0 != status) err_exit(status, "unlock out_mutex");
@@ -1082,7 +1214,7 @@ sg_out_operation(Gbl_coll * clp, Rq_elem * rep)
guarded_stop_both(clp);
return;
}
- }
+ } /* end of while (1) loop */
}
static int
@@ -1092,14 +1224,16 @@ sg_start_io(Rq_elem * rep)
bool fua = wr ? rep->out_flags.fua : rep->in_flags.fua;
bool dpo = wr ? rep->out_flags.dpo : rep->in_flags.dpo;
bool dio = wr ? rep->out_flags.dio : rep->in_flags.dio;
+ bool mmap = wr ? rep->out_flags.mmap : rep->in_flags.mmap;
int cdbsz = wr ? rep->cdbsz_out : rep->cdbsz_in;
- int res;
+ int res, err;
struct sg_io_hdr * hp = &rep->io_hdr;
const char * cp = "";
const char * c2p = "";
+ const char * c3p = "";
if (sg_build_scsi_cdb(rep->cmd, cdbsz, rep->num_blks, rep->blk,
- rep->wr, fua, dpo)) {
+ wr, fua, dpo)) {
pr2serr_lk("%sbad cdb build, start_blk=%" PRId64 ", blocks=%d\n",
my_name, rep->blk, rep->num_blks);
return -1;
@@ -1116,6 +1250,10 @@ sg_start_io(Rq_elem * rep)
hp->timeout = DEF_TIMEOUT;
hp->usr_ptr = rep;
hp->pack_id = (int)rep->blk;
+ if (mmap && (rep->out2fd >= 0)) {
+ hp->flags |= SG_FLAG_MMAP_IO;
+ c3p = " mmap";
+ }
if (dio)
hp->flags |= SG_FLAG_DIRECT_IO;
if (rep->has_share) {
@@ -1131,20 +1269,22 @@ sg_start_io(Rq_elem * rep)
} else
cp = (wr ? " slave not sharing" : " master not sharing");
if (rep->debug > 3) {
- pr2serr_lk("%s tid=%d: SCSI %s%s%s, blk=%" PRId64 " num_blks=%d\n",
+ pr2serr_lk("%s tid=%d: SCSI %s%s%s%s, blk=%" PRId64 " num_blks=%d\n",
__func__, rep->id, (rep->wr ? "WRITE" : "READ"), cp,
- c2p, rep->blk, rep->num_blks);
- sg_print_command(hp->cmdp);
+ c2p, c3p, rep->blk, rep->num_blks);
+ lk_print_command(hp->cmdp);
}
while (((res = write(rep->wr ? rep->outfd : rep->infd, hp,
sizeof(struct sg_io_hdr))) < 0) &&
((EINTR == errno) || (EAGAIN == errno)))
;
+ err = errno;
if (res < 0) {
- if (ENOMEM == errno)
+ if (ENOMEM == err)
return 1;
- perror("starting io on sg device, error");
+ pr2serr_lk("%s tid=%d: %s%s%s write(2) failed: %s\n", __func__,
+ rep->id, cp, c2p, c3p, strerror(err));
return -1;
}
return 0;
@@ -1154,9 +1294,9 @@ sg_start_io(Rq_elem * rep)
-> try again, SG_LIB_CAT_NOT_READY, SG_LIB_CAT_MEDIUM_HARD,
-1 other errors */
static int
-sg_finish_io(bool wr, Rq_elem * rep, pthread_mutex_t * a_mutp)
+sg_finish_io(bool wr, Rq_elem * rep)
{
- int res, err, status;
+ int res;
struct sg_io_hdr io_hdr;
struct sg_io_hdr * hp;
#if 0
@@ -1187,13 +1327,13 @@ sg_finish_io(bool wr, Rq_elem * rep, pthread_mutex_t * a_mutp)
case SG_LIB_CAT_CLEAN:
break;
case SG_LIB_CAT_RECOVERED:
- sg_chk_n_print3((wr ? "writing continuing":
+ lk_chk_n_print3((wr ? "writing continuing":
"reading continuing"), hp, false);
break;
case SG_LIB_CAT_ABORTED_COMMAND:
case SG_LIB_CAT_UNIT_ATTENTION:
if (rep->debug > 3)
- sg_chk_n_print3((wr ? "writing": "reading"), hp, false);
+ lk_chk_n_print3((wr ? "writing": "reading"), hp, false);
return res;
case SG_LIB_CAT_NOT_READY:
default:
@@ -1202,11 +1342,7 @@ sg_finish_io(bool wr, Rq_elem * rep, pthread_mutex_t * a_mutp)
snprintf(ebuff, EBUFF_SZ, "%s blk=%" PRId64,
wr ? "writing": "reading", rep->blk);
- status = pthread_mutex_lock(a_mutp);
- if (0 != status) err_exit(status, "lock aux_mutex");
- sg_chk_n_print3(ebuff, hp, false);
- status = pthread_mutex_unlock(a_mutp);
- if (0 != status) err_exit(status, "unlock aux_mutex");
+ lk_chk_n_print3(ebuff, hp, false);
return res;
}
}
@@ -1219,45 +1355,47 @@ sg_finish_io(bool wr, Rq_elem * rep, pthread_mutex_t * a_mutp)
else
rep->dio_incomplete_count = 0;
rep->resid = hp->resid;
- if ((! wr) && (rep->out2fd >= 0)) {
- status = pthread_mutex_lock(a_mutp);
- if (0 != status) err_exit(status, "lock aux_mutex");
- res = write(rep->out2fd, rep->buffp, rep->bs * rep->num_blks);
- err = errno;
- status = pthread_mutex_unlock(a_mutp);
- if (0 != status) err_exit(status, "unlock aux_mutex");
- if (res < 0)
- pr2serr_lk("%s: tid=%d: write(out2fd) failed: %s\n", __func__,
- rep->id, strerror(err));
- }
if (rep->debug > 3)
pr2serr_lk("%s: tid=%d: completed %s\n", __func__, rep->id,
wr ? "WRITE" : "READ");
return 0;
}
+/* Returns reserved_buffer_size/mmap_size if success, else 0 for failure */
static int
-sg_prepare(int fd, int bs, int bpt)
+sg_prepare(int fd, int bs, int bpt, bool def_res, uint8_t **mmpp)
{
- int res, t;
+ int res, t, num;
+ uint8_t *mmp;
res = ioctl(fd, SG_GET_VERSION_NUM, &t);
if ((res < 0) || (t < 30902)) {
pr2serr_lk("%ssg driver prior to 3.9.02\n", my_name);
- return 1;
+ return 0;
+ }
+ if (! def_res) {
+ num = bs * bpt;
+ res = ioctl(fd, SG_SET_RESERVED_SIZE, &num);
+ if (res < 0)
+ perror("sgs_dd: SG_SET_RESERVED_SIZE error");
+ else if (mmpp) {
+ mmp = (uint8_t *)mmap(NULL, num, PROT_READ | PROT_WRITE,
+ MAP_SHARED, fd, 0);
+ if (MAP_FAILED == mmp) {
+ perror("error using mmap()");
+ return 0;
+ }
+ *mmpp = mmp;
+ }
}
- t = bs * bpt;
- res = ioctl(fd, SG_SET_RESERVED_SIZE, &t);
- if (res < 0)
- perror("sgs_dd: SG_SET_RESERVED_SIZE error");
t = 1;
res = ioctl(fd, SG_SET_FORCE_PACK_ID, &t);
if (res < 0)
perror("sgs_dd: SG_SET_FORCE_PACK_ID error");
- return 0;
+ return (res < 0) ? 0 : num;
}
-static int
+static bool
process_flags(const char * arg, struct flags_t * fp)
{
char buff[256];
@@ -1268,17 +1406,21 @@ process_flags(const char * arg, struct flags_t * fp)
buff[sizeof(buff) - 1] = '\0';
if ('\0' == buff[0]) {
pr2serr("no flag found\n");
- return 1;
+ return false;
}
cp = buff;
do {
np = strchr(cp, ',');
if (np)
*np++ = '\0';
- if (0 == strcmp(cp, "append"))
+ if (0 == strcmp(cp, "2fds"))
+ fp->fds2 = true;
+ else if (0 == strcmp(cp, "append"))
fp->append = true;
else if (0 == strcmp(cp, "coe"))
fp->coe = true;
+ else if (0 == strcmp(cp, "defres"))
+ fp->defres = true;
else if (0 == strcmp(cp, "dio"))
fp->dio = true;
else if (0 == strcmp(cp, "direct"))
@@ -1291,17 +1433,19 @@ process_flags(const char * arg, struct flags_t * fp)
fp->excl = true;
else if (0 == strcmp(cp, "fua"))
fp->fua = true;
+ else if (0 == strcmp(cp, "mmap"))
+ fp->mmap = true;
else if (0 == strcmp(cp, "noshare"))
fp->noshare = true;
else if (0 == strcmp(cp, "null"))
;
else {
pr2serr("unrecognised flag: %s\n", cp);
- return 1;
+ return false;
}
cp = np;
} while (cp);
- return 0;
+ return true;
}
/* Returns the number of times 'ch' is found in string 's' given the
@@ -1319,9 +1463,9 @@ num_chs_in_str(const char * s, int slen, int ch)
}
static int
-sg_in_open(Gbl_coll *clp, const char *inf)
+sg_in_open(Gbl_coll *clp, const char *inf, uint8_t **mmpp, int * mmap_lenp)
{
- int fd, err;
+ int fd, err, n;
int flags = O_RDWR;
char ebuff[EBUFF_SZ];
@@ -1339,15 +1483,18 @@ sg_in_open(Gbl_coll *clp, const char *inf)
perror(ebuff);
return -sg_convert_errno(err);;
}
- if (sg_prepare(fd, clp->bs, clp->bpt))
+ n = sg_prepare(fd, clp->bs, clp->bpt, clp->in_flags.defres, mmpp);
+ if (n <= 0)
return -SG_LIB_FILE_ERROR;
+ if (mmap_lenp)
+ *mmap_lenp = n;
return fd;
}
static int
-sg_out_open(Gbl_coll *clp, const char *outf)
+sg_out_open(Gbl_coll *clp, const char *outf, uint8_t **mmpp, int * mmap_lenp)
{
- int fd, err;
+ int fd, err, n;
int flags = O_RDWR;
char ebuff[EBUFF_SZ];
@@ -1365,11 +1512,11 @@ sg_out_open(Gbl_coll *clp, const char *outf)
perror(ebuff);
return -sg_convert_errno(err);
}
- if (sg_prepare(fd, clp->bs, clp->bpt))
+ n = sg_prepare(fd, clp->bs, clp->bpt, clp->out_flags.defres, mmpp);
+ if (n <= 0)
return -SG_LIB_FILE_ERROR;
- else if (gcoll.debug > 1)
- pr2serr("Sharing writer's fd (%d) with reader (fd=%d) "
- "successful\n", clp->infd, fd);
+ if (mmap_lenp)
+ *mmap_lenp = n;
return fd;
}
@@ -1398,7 +1545,8 @@ main(int argc, char * argv[])
int64_t out_num_sect = 0;
int in_sect_sz, out_sect_sz, status, n, flags;
void * vp;
- pthread_t threads[MAX_NUM_THREADS];
+ Gbl_coll * clp = &gcoll;
+ Thread_info thread_arr[MAX_NUM_THREADS];
char ebuff[EBUFF_SZ];
#if SG_LIB_ANDROID
struct sigaction actions;
@@ -1409,12 +1557,13 @@ main(int argc, char * argv[])
actions.sa_handler = thread_exit_handler;
sigaction(SIGUSR1, &actions, NULL);
#endif
- memset(&gcoll, 0, sizeof(Gbl_coll));
- gcoll.bpt = DEF_BLOCKS_PER_TRANSFER;
- gcoll.in_type = FT_OTHER;
- gcoll.out_type = FT_OTHER;
- gcoll.cdbsz_in = DEF_SCSI_CDBSZ;
- gcoll.cdbsz_out = DEF_SCSI_CDBSZ;
+ memset(clp, 0, sizeof(*clp));
+ memset(thread_arr, 0, sizeof(thread_arr));
+ clp->bpt = DEF_BLOCKS_PER_TRANSFER;
+ clp->in_type = FT_OTHER;
+ clp->out_type = FT_OTHER;
+ clp->cdbsz_in = DEF_SCSI_CDBSZ;
+ clp->cdbsz_out = DEF_SCSI_CDBSZ;
inf[0] = '\0';
outf[0] = '\0';
out2f[0] = '\0';
@@ -1432,25 +1581,25 @@ main(int argc, char * argv[])
*buf++ = '\0';
keylen = strlen(key);
if (0 == strcmp(key,"bpt")) {
- gcoll.bpt = sg_get_num(buf);
- if (-1 == gcoll.bpt) {
+ clp->bpt = sg_get_num(buf);
+ if (-1 == clp->bpt) {
pr2serr("%sbad argument to 'bpt='\n", my_name);
return SG_LIB_SYNTAX_ERROR;
}
bpt_given = 1;
} else if (0 == strcmp(key,"bs")) {
- gcoll.bs = sg_get_num(buf);
- if (-1 == gcoll.bs) {
+ clp->bs = sg_get_num(buf);
+ if (-1 == clp->bs) {
pr2serr("%sbad argument to 'bs='\n", my_name);
return SG_LIB_SYNTAX_ERROR;
}
} else if (0 == strcmp(key,"cdbsz")) {
- gcoll.cdbsz_in = sg_get_num(buf);
- gcoll.cdbsz_out = gcoll.cdbsz_in;
+ clp->cdbsz_in = sg_get_num(buf);
+ clp->cdbsz_out = clp->cdbsz_in;
cdbsz_given = 1;
} else if (0 == strcmp(key,"coe")) {
- gcoll.in_flags.coe = !! sg_get_num(buf);
- gcoll.out_flags.coe = gcoll.in_flags.coe;
+ clp->in_flags.coe = !! sg_get_num(buf);
+ clp->out_flags.coe = clp->in_flags.coe;
} else if (0 == strcmp(key,"count")) {
if (0 != strcmp("-1", buf)) {
dd_count = sg_get_llnum(buf);
@@ -1461,16 +1610,16 @@ main(int argc, char * argv[])
} /* treat 'count=-1' as calculate count (same as not given) */
} else if ((0 == strncmp(key,"deb", 3)) ||
(0 == strncmp(key,"verb", 4)))
- gcoll.debug = sg_get_num(buf);
+ clp->debug = sg_get_num(buf);
else if (0 == strcmp(key,"dio")) {
- gcoll.in_flags.dio = !! sg_get_num(buf);
- gcoll.out_flags.dio = gcoll.in_flags.dio;
+ clp->in_flags.dio = !! sg_get_num(buf);
+ clp->out_flags.dio = clp->in_flags.dio;
} else if (0 == strcmp(key,"fua")) {
n = sg_get_num(buf);
if (n & 1)
- gcoll.out_flags.fua = true;
+ clp->out_flags.fua = true;
if (n & 2)
- gcoll.in_flags.fua = true;
+ clp->in_flags.fua = true;
} else if (0 == strcmp(key,"ibs")) {
ibs = sg_get_num(buf);
if (-1 == ibs) {
@@ -1484,7 +1633,7 @@ main(int argc, char * argv[])
} else
snprintf(inf, INOUTF_SZ, "%s", buf);
} else if (0 == strcmp(key, "iflag")) {
- if (process_flags(buf, &gcoll.in_flags)) {
+ if (! process_flags(buf, &clp->in_flags)) {
pr2serr("%sbad argument to 'iflag='\n", my_name);
return SG_LIB_SYNTAX_ERROR;
}
@@ -1507,7 +1656,7 @@ main(int argc, char * argv[])
} else
snprintf(outf, INOUTF_SZ, "%s", buf);
} else if (0 == strcmp(key, "oflag")) {
- if (process_flags(buf, &gcoll.out_flags)) {
+ if (! process_flags(buf, &clp->out_flags)) {
pr2serr("%sbad argument to 'oflag='\n", my_name);
return SG_LIB_SYNTAX_ERROR;
}
@@ -1532,15 +1681,15 @@ main(int argc, char * argv[])
else if ((keylen > 1) && ('-' == key[0]) && ('-' != key[1])) {
res = 0;
n = num_chs_in_str(key + 1, keylen - 1, 'd');
- gcoll.dry_run += n;
+ clp->dry_run += n;
res += n;
n = num_chs_in_str(key + 1, keylen - 1, 'h');
- gcoll.help += n;
+ clp->help += n;
res += n;
n = num_chs_in_str(key + 1, keylen - 1, 'v');
if (n > 0)
verbose_given = true;
- gcoll.debug += n; /* -v ---> --verbose */
+ clp->debug += n; /* -v ---> --verbose */
res += n;
n = num_chs_in_str(key + 1, keylen - 1, 'V');
if (n > 0)
@@ -1554,13 +1703,13 @@ main(int argc, char * argv[])
}
} else if ((0 == strncmp(key, "--dry-run", 9)) ||
(0 == strncmp(key, "--dry_run", 9)))
- ++gcoll.dry_run;
+ ++clp->dry_run;
else if ((0 == strncmp(key, "--help", 6)) ||
(0 == strcmp(key, "-?")))
- ++gcoll.help;
+ ++clp->help;
else if (0 == strncmp(key, "--verb", 6)) {
verbose_given = true;
- ++gcoll.debug; /* --verbose */
+ ++clp->debug; /* --verbose */
} else if (0 == strncmp(key, "--vers", 6))
version_given = true;
else {
@@ -1576,12 +1725,12 @@ main(int argc, char * argv[])
pr2serr("but override: '-vV' given, zero verbose and continue\n");
verbose_given = false;
version_given = false;
- gcoll.debug = 0;
+ clp->debug = 0;
} else if (! verbose_given) {
pr2serr("set '-vv'\n");
- gcoll.debug = 2;
+ clp->debug = 2;
} else
- pr2serr("keep verbose=%d\n", gcoll.debug);
+ pr2serr("keep verbose=%d\n", clp->debug);
#else
if (verbose_given && version_given)
pr2serr("Not in DEBUG mode, so '-vV' has no special action\n");
@@ -1590,18 +1739,15 @@ main(int argc, char * argv[])
pr2serr("%s%s\n", my_name, version_str);
return 0;
}
- if (gcoll.help > 0) {
- if (1 == gcoll.help)
- usage(0);
- else
- usage(1);
+ if (clp->help > 0) {
+ usage(clp->help);
return 0;
}
- if (gcoll.bs <= 0) {
- gcoll.bs = DEF_BLOCK_SIZE;
- pr2serr("Assume default 'bs' (block size) of %d bytes\n", gcoll.bs);
+ if (clp->bs <= 0) {
+ clp->bs = DEF_BLOCK_SIZE;
+ pr2serr("Assume default 'bs' (block size) of %d bytes\n", clp->bs);
}
- if ((ibs && (ibs != gcoll.bs)) || (obs && (obs != gcoll.bs))) {
+ if ((ibs && (ibs != clp->bs)) || (obs && (obs != clp->bs))) {
pr2serr("If 'ibs' or 'obs' given must be same as 'bs'\n");
usage(0);
return SG_LIB_SYNTAX_ERROR;
@@ -1610,25 +1756,39 @@ main(int argc, char * argv[])
pr2serr("skip and seek cannot be negative\n");
return SG_LIB_SYNTAX_ERROR;
}
- if (gcoll.out_flags.append && (seek > 0)) {
+ if (clp->out_flags.append && (seek > 0)) {
pr2serr("Can't use both append and seek switches\n");
return SG_LIB_SYNTAX_ERROR;
}
- if (gcoll.bpt < 1) {
+ if (clp->bpt < 1) {
pr2serr("bpt must be greater than 0\n");
return SG_LIB_SYNTAX_ERROR;
}
+ if (clp->in_flags.mmap && clp->out_flags.mmap) {
+ pr2serr("mmap flag on both IFILE and OFILE doesn't work\n");
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ if (clp->out_flags.mmap && !(clp->in_flags.noshare ||
+ clp->out_flags.noshare)) {
+ pr2serr("oflag=mmap needs either iflag=noshare or oflag=noshare\n");
+ return SG_LIB_SYNTAX_ERROR;
+ }
+ if ((clp->in_flags.mmap || clp->out_flags.mmap) &&
+ (clp->in_flags.fds2 || clp->in_flags.fds2)) {
+ pr2serr("can't have both 'mmap' and '2fds' flags\n");
+ return SG_LIB_SYNTAX_ERROR;
+ }
/* defaulting transfer size to 128*2048 for CD/DVDs is too large
for the block layer in lk 2.6 and results in an EIO on the
SG_IO ioctl. So reduce it in that case. */
- if ((gcoll.bs >= 2048) && (0 == bpt_given))
- gcoll.bpt = DEF_BLOCKS_PER_2048TRANSFER;
+ if ((clp->bs >= 2048) && (0 == bpt_given))
+ clp->bpt = DEF_BLOCKS_PER_2048TRANSFER;
if ((num_threads < 1) || (num_threads > MAX_NUM_THREADS)) {
pr2serr("too few or too many threads requested\n");
usage(1);
return SG_LIB_SYNTAX_ERROR;
}
- if (gcoll.debug)
+ if (clp->debug)
pr2serr("%sif=%s skip=%" PRId64 " of=%s seek=%" PRId64 " count=%"
PRId64 "\n", my_name, inf, skip, outf, seek, dd_count);
@@ -1637,42 +1797,41 @@ main(int argc, char * argv[])
install_handler(SIGPIPE, interrupt_handler);
install_handler(SIGUSR1, siginfo_handler);
- gcoll.infd = STDIN_FILENO;
- gcoll.outfd = STDOUT_FILENO;
+ clp->infd = STDIN_FILENO;
+ clp->outfd = STDOUT_FILENO;
if (inf[0] && ('-' != inf[0])) {
- gcoll.in_type = dd_filetype(inf);
+ clp->in_type = dd_filetype(inf);
- if (FT_ERROR == gcoll.in_type) {
+ if (FT_ERROR == clp->in_type) {
pr2serr("%sunable to access %s\n", my_name, inf);
return SG_LIB_FILE_ERROR;
- } else if (FT_ST == gcoll.in_type) {
+ } else if (FT_ST == clp->in_type) {
pr2serr("%sunable to use scsi tape device %s\n", my_name, inf);
return SG_LIB_FILE_ERROR;
- } else if (FT_SG == gcoll.in_type) {
- gcoll.infd = sg_in_open(&gcoll, inf);
- if (gcoll.infd < 0)
- return -gcoll.infd;
+ } else if (FT_SG == clp->in_type) {
+ clp->infd = sg_in_open(clp, inf, NULL, NULL);
+ if (clp->infd < 0)
+ return -clp->infd;
} else {
flags = O_RDONLY;
- if (gcoll.in_flags.direct)
+ if (clp->in_flags.direct)
flags |= O_DIRECT;
- if (gcoll.in_flags.excl)
+ if (clp->in_flags.excl)
flags |= O_EXCL;
- if (gcoll.in_flags.dsync)
+ if (clp->in_flags.dsync)
flags |= O_SYNC;
- if ((gcoll.infd = open(inf, flags)) < 0) {
+ if ((clp->infd = open(inf, flags)) < 0) {
err = errno;
snprintf(ebuff, EBUFF_SZ, "%scould not open %s for reading",
my_name, inf);
perror(ebuff);
return sg_convert_errno(err);
- }
- else if (skip > 0) {
+ } else if (skip > 0) {
off64_t offset = skip;
- offset *= gcoll.bs; /* could exceed 32 here! */
- if (lseek64(gcoll.infd, offset, SEEK_SET) < 0) {
+ offset *= clp->bs; /* could exceed 32 here! */
+ if (lseek64(clp->infd, offset, SEEK_SET) < 0) {
err = errno;
snprintf(ebuff, EBUFF_SZ, "%scouldn't skip to required "
"position on %s", my_name, inf);
@@ -1681,34 +1840,35 @@ main(int argc, char * argv[])
}
}
}
+ clp->infp = inf;
}
if (outf[0] && ('-' != outf[0])) {
- gcoll.out_type = dd_filetype(outf);
+ clp->out_type = dd_filetype(outf);
- if (FT_ST == gcoll.out_type) {
+ if (FT_ST == clp->out_type) {
pr2serr("%sunable to use scsi tape device %s\n", my_name, outf);
return SG_LIB_FILE_ERROR;
}
- else if (FT_SG == gcoll.out_type) {
- gcoll.outfd = sg_out_open(&gcoll, outf);
- if (gcoll.outfd < 0)
- return -gcoll.outfd;
+ else if (FT_SG == clp->out_type) {
+ clp->outfd = sg_out_open(clp, outf, NULL, NULL);
+ if (clp->outfd < 0)
+ return -clp->outfd;
}
- else if (FT_DEV_NULL == gcoll.out_type)
- gcoll.outfd = -1; /* don't bother opening */
+ else if (FT_DEV_NULL == clp->out_type)
+ clp->outfd = -1; /* don't bother opening */
else {
- if (FT_RAW != gcoll.out_type) {
+ if (FT_RAW != clp->out_type) {
flags = O_WRONLY | O_CREAT;
- if (gcoll.out_flags.direct)
+ if (clp->out_flags.direct)
flags |= O_DIRECT;
- if (gcoll.out_flags.excl)
+ if (clp->out_flags.excl)
flags |= O_EXCL;
- if (gcoll.out_flags.dsync)
+ if (clp->out_flags.dsync)
flags |= O_SYNC;
- if (gcoll.out_flags.append)
+ if (clp->out_flags.append)
flags |= O_APPEND;
- if ((gcoll.outfd = open(outf, flags, 0666)) < 0) {
+ if ((clp->outfd = open(outf, flags, 0666)) < 0) {
err = errno;
snprintf(ebuff, EBUFF_SZ, "%scould not open %s for "
"writing", my_name, outf);
@@ -1717,7 +1877,7 @@ main(int argc, char * argv[])
}
}
else { /* raw output file */
- if ((gcoll.outfd = open(outf, O_WRONLY)) < 0) {
+ if ((clp->outfd = open(outf, O_WRONLY)) < 0) {
err = errno;
snprintf(ebuff, EBUFF_SZ, "%scould not open %s for raw "
"writing", my_name, outf);
@@ -1728,8 +1888,8 @@ main(int argc, char * argv[])
if (seek > 0) {
off64_t offset = seek;
- offset *= gcoll.bs; /* could exceed 32 bits here! */
- if (lseek64(gcoll.outfd, offset, SEEK_SET) < 0) {
+ offset *= clp->bs; /* could exceed 32 bits here! */
+ if (lseek64(clp->outfd, offset, SEEK_SET) < 0) {
err = errno;
snprintf(ebuff, EBUFF_SZ, "%scouldn't seek to required "
"position on %s", my_name, outf);
@@ -1738,30 +1898,31 @@ main(int argc, char * argv[])
}
}
}
+ clp->outfp = outf;
}
if (out2f[0]) {
- gcoll.out2_type = dd_filetype(out2f);
- if ((gcoll.out2fd = open(out2f, O_WRONLY | O_CREAT, 0666)) < 0) {
+ clp->out2_type = dd_filetype(out2f);
+ if ((clp->out2fd = open(out2f, O_WRONLY | O_CREAT, 0666)) < 0) {
err = errno;
snprintf(ebuff, EBUFF_SZ, "could not open %s for writing", out2f);
perror(ebuff);
return sg_convert_errno(err);
}
} else
- gcoll.out2fd = -1;
+ clp->out2fd = -1;
- if ((STDIN_FILENO == gcoll.infd) && (STDOUT_FILENO == gcoll.outfd)) {
+ if ((STDIN_FILENO == clp->infd) && (STDOUT_FILENO == clp->outfd)) {
pr2serr("Won't default both IFILE to stdin _and_ OFILE to stdout\n");
pr2serr("For more information use '--help'\n");
return SG_LIB_SYNTAX_ERROR;
}
if (dd_count < 0) {
in_num_sect = -1;
- if (FT_SG == gcoll.in_type) {
- res = scsi_read_capacity(gcoll.infd, &in_num_sect, &in_sect_sz);
+ if (FT_SG == clp->in_type) {
+ res = scsi_read_capacity(clp->infd, &in_num_sect, &in_sect_sz);
if (2 == res) {
pr2serr("Unit attention, media changed(in), continuing\n");
- res = scsi_read_capacity(gcoll.infd, &in_num_sect,
+ res = scsi_read_capacity(clp->infd, &in_num_sect,
&in_sect_sz);
}
if (0 != res) {
@@ -1773,15 +1934,15 @@ main(int argc, char * argv[])
pr2serr("Unable to read capacity on %s\n", inf);
in_num_sect = -1;
}
- } else if (FT_BLOCK == gcoll.in_type) {
- if (0 != read_blkdev_capacity(gcoll.infd, &in_num_sect,
+ } else if (FT_BLOCK == clp->in_type) {
+ if (0 != read_blkdev_capacity(clp->infd, &in_num_sect,
&in_sect_sz)) {
pr2serr("Unable to read block capacity on %s\n", inf);
in_num_sect = -1;
}
- if (gcoll.bs != in_sect_sz) {
+ if (clp->bs != in_sect_sz) {
pr2serr("block size on %s confusion; bs=%d, from device=%d\n",
- inf, gcoll.bs, in_sect_sz);
+ inf, clp->bs, in_sect_sz);
in_num_sect = -1;
}
}
@@ -1789,11 +1950,11 @@ main(int argc, char * argv[])
in_num_sect -= skip;
out_num_sect = -1;
- if (FT_SG == gcoll.out_type) {
- res = scsi_read_capacity(gcoll.outfd, &out_num_sect, &out_sect_sz);
+ if (FT_SG == clp->out_type) {
+ res = scsi_read_capacity(clp->outfd, &out_num_sect, &out_sect_sz);
if (2 == res) {
pr2serr("Unit attention, media changed(out), continuing\n");
- res = scsi_read_capacity(gcoll.outfd, &out_num_sect,
+ res = scsi_read_capacity(clp->outfd, &out_num_sect,
&out_sect_sz);
}
if (0 != res) {
@@ -1805,15 +1966,15 @@ main(int argc, char * argv[])
pr2serr("Unable to read capacity on %s\n", outf);
out_num_sect = -1;
}
- } else if (FT_BLOCK == gcoll.out_type) {
- if (0 != read_blkdev_capacity(gcoll.outfd, &out_num_sect,
+ } else if (FT_BLOCK == clp->out_type) {
+ if (0 != read_blkdev_capacity(clp->outfd, &out_num_sect,
&out_sect_sz)) {
pr2serr("Unable to read block capacity on %s\n", outf);
out_num_sect = -1;
}
- if (gcoll.bs != out_sect_sz) {
+ if (clp->bs != out_sect_sz) {
pr2serr("block size on %s confusion: bs=%d, from device=%d\n",
- outf, gcoll.bs, out_sect_sz);
+ outf, clp->bs, out_sect_sz);
out_num_sect = -1;
}
}
@@ -1830,7 +1991,7 @@ main(int argc, char * argv[])
else
dd_count = out_num_sect;
}
- if (gcoll.debug > 2)
+ if (clp->debug > 2)
pr2serr("Start of loop, count=%" PRId64 ", in_num_sect=%" PRId64
", out_num_sect=%" PRId64 "\n", dd_count, in_num_sect,
out_num_sect);
@@ -1839,38 +2000,36 @@ main(int argc, char * argv[])
return SG_LIB_CAT_OTHER;
}
if (! cdbsz_given) {
- if ((FT_SG == gcoll.in_type) && (MAX_SCSI_CDBSZ != gcoll.cdbsz_in) &&
- (((dd_count + skip) > UINT_MAX) || (gcoll.bpt > USHRT_MAX))) {
+ if ((FT_SG == clp->in_type) && (MAX_SCSI_CDBSZ != clp->cdbsz_in) &&
+ (((dd_count + skip) > UINT_MAX) || (clp->bpt > USHRT_MAX))) {
pr2serr("Note: SCSI command size increased to 16 bytes (for "
"'if')\n");
- gcoll.cdbsz_in = MAX_SCSI_CDBSZ;
+ clp->cdbsz_in = MAX_SCSI_CDBSZ;
}
- if ((FT_SG == gcoll.out_type) && (MAX_SCSI_CDBSZ != gcoll.cdbsz_out) &&
- (((dd_count + seek) > UINT_MAX) || (gcoll.bpt > USHRT_MAX))) {
+ if ((FT_SG == clp->out_type) && (MAX_SCSI_CDBSZ != clp->cdbsz_out) &&
+ (((dd_count + seek) > UINT_MAX) || (clp->bpt > USHRT_MAX))) {
pr2serr("Note: SCSI command size increased to 16 bytes (for "
"'of')\n");
- gcoll.cdbsz_out = MAX_SCSI_CDBSZ;
+ clp->cdbsz_out = MAX_SCSI_CDBSZ;
}
}
- gcoll.in_count = dd_count;
- gcoll.in_rem_count = dd_count;
- gcoll.skip = skip;
- gcoll.in_blk = skip;
- gcoll.out_count = dd_count;
- gcoll.out_rem_count = dd_count;
- gcoll.seek = seek;
- gcoll.out_blk = seek;
- status = pthread_mutex_init(&gcoll.in_mutex, NULL);
+ clp->in_count = dd_count;
+ clp->in_rem_count = dd_count;
+ clp->skip = skip;
+ clp->in_blk = skip;
+ clp->out_count = dd_count;
+ clp->out_rem_count = dd_count;
+ clp->seek = seek;
+ clp->out_blk = seek;
+ status = pthread_mutex_init(&clp->in_mutex, NULL);
if (0 != status) err_exit(status, "init in_mutex");
- status = pthread_mutex_init(&gcoll.out_mutex, NULL);
+ status = pthread_mutex_init(&clp->out_mutex, NULL);
if (0 != status) err_exit(status, "init out_mutex");
- status = pthread_mutex_init(&gcoll.aux_mutex, NULL);
- if (0 != status) err_exit(status, "init aux_mutex");
- status = pthread_cond_init(&gcoll.out_sync_cv, NULL);
+ status = pthread_cond_init(&clp->out_sync_cv, NULL);
if (0 != status) err_exit(status, "init out_sync_cv");
- if (gcoll.dry_run > 0) {
+ if (clp->dry_run > 0) {
pr2serr("Due to --dry-run option, bypass copy/read\n");
goto fini;
}
@@ -1879,7 +2038,7 @@ main(int argc, char * argv[])
status = pthread_sigmask(SIG_BLOCK, &signal_set, NULL);
if (0 != status) err_exit(status, "pthread_sigmask");
status = pthread_create(&sig_listen_thread_id, NULL,
- sig_listen_thread, (void *)&gcoll);
+ sig_listen_thread, (void *)clp);
if (0 != status) err_exit(status, "pthread_create, sig...");
if (do_time) {
@@ -1889,46 +2048,47 @@ main(int argc, char * argv[])
}
/* vvvvvvvvvvv Start worker threads vvvvvvvvvvvvvvvvvvvvvvvv */
- if ((gcoll.out_rem_count > 0) && (num_threads > 0)) {
- Thread_info ti;
+ if ((clp->out_rem_count > 0) && (num_threads > 0)) {
+ Thread_info *tip = thread_arr + 0;
- ti.gcp = &gcoll;
- ti.id = 0;
+ tip->gcp = clp;
+ tip->id = 0;
/* Run 1 work thread to shake down infant retryable stuff */
- status = pthread_mutex_lock(&gcoll.out_mutex);
+ status = pthread_mutex_lock(&clp->out_mutex);
if (0 != status) err_exit(status, "lock out_mutex");
- status = pthread_create(&threads[0], NULL, read_write_thread,
- (void *)&ti);
+ status = pthread_create(&tip->a_pthr, NULL, read_write_thread,
+ (void *)tip);
if (0 != status) err_exit(status, "pthread_create");
- if (gcoll.debug > 1)
- pr2serr_lk("Starting worker thread k=0\n");
+ if (clp->debug > 1)
+ pr2serr_lk("Starting worker thread k=0 alone\n");
- /* wait for any broadcast */
- pthread_cleanup_push(cleanup_out, (void *)&gcoll);
- status = pthread_cond_wait(&gcoll.out_sync_cv, &gcoll.out_mutex);
- if (0 != status) err_exit(status, "cond out_sync_cv");
+ /* wait for a broadcast on hold_1st_cv, implies tid=0 thread has
+ * completed one READ/WRITE cycle (segment). */
+ pthread_cleanup_push(cleanup_out, (void *)clp);
+ status = pthread_cond_wait(&clp->hold_1st_cv, &clp->out_mutex);
+ if (0 != status) err_exit(status, "cond hold_1st_cv");
pthread_cleanup_pop(0);
- status = pthread_mutex_unlock(&gcoll.out_mutex);
+ status = pthread_mutex_unlock(&clp->out_mutex);
if (0 != status) err_exit(status, "unlock out_mutex");
/* now start the rest of the threads */
for (k = 1; k < num_threads; ++k) {
- Thread_info tinfo;
-
- tinfo.gcp = &gcoll;
- tinfo.id = k;
- status = pthread_create(&threads[k], NULL, read_write_thread,
- (void *)&tinfo);
+ tip = thread_arr + k;
+ tip->gcp = clp;
+ tip->id = k;
+ status = pthread_create(&tip->a_pthr, NULL, read_write_thread,
+ (void *)tip);
if (0 != status) err_exit(status, "pthread_create");
- if (gcoll.debug > 1)
+ if (clp->debug > 1)
pr2serr_lk("Starting worker thread k=%d\n", k);
}
/* now wait for worker threads to finish */
for (k = 0; k < num_threads; ++k) {
- status = pthread_join(threads[k], &vp);
+ tip = thread_arr + k;
+ status = pthread_join(tip->a_pthr, &vp);
if (0 != status) err_exit(status, "pthread_join");
- if (gcoll.debug > 0)
+ if (clp->debug > 0)
pr2serr_lk("Worker thread k=%d terminated\n", k);
}
} /* started worker threads and here after they have all exited */
@@ -1937,12 +2097,12 @@ main(int argc, char * argv[])
calc_duration_throughput(0);
if (do_sync) {
- if (FT_SG == gcoll.out_type) {
+ if (FT_SG == clp->out_type) {
pr2serr_lk(">> Synchronizing cache on %s\n", outf);
- res = sg_ll_sync_cache_10(gcoll.outfd, 0, 0, 0, 0, 0, false, 0);
+ res = sg_ll_sync_cache_10(clp->outfd, 0, 0, 0, 0, 0, false, 0);
if (SG_LIB_CAT_UNIT_ATTENTION == res) {
pr2serr_lk("Unit attention(out), continuing\n");
- res = sg_ll_sync_cache_10(gcoll.outfd, 0, 0, 0, 0, 0, false,
+ res = sg_ll_sync_cache_10(clp->outfd, 0, 0, 0, 0, 0, false,
0);
}
if (0 != res)
@@ -1958,26 +2118,26 @@ main(int argc, char * argv[])
fini:
- if (STDIN_FILENO != gcoll.infd)
- close(gcoll.infd);
- if ((STDOUT_FILENO != gcoll.outfd) && (FT_DEV_NULL != gcoll.out_type))
- close(gcoll.outfd);
- if ((STDOUT_FILENO != gcoll.out2fd) && (FT_DEV_NULL != gcoll.out2_type))
- close(gcoll.out2fd);
+ if (STDIN_FILENO != clp->infd)
+ close(clp->infd);
+ if ((STDOUT_FILENO != clp->outfd) && (FT_DEV_NULL != clp->out_type))
+ close(clp->outfd);
+ if ((STDOUT_FILENO != clp->out2fd) && (FT_DEV_NULL != clp->out2_type))
+ close(clp->out2fd);
res = exit_status;
- if ((0 != gcoll.out_count) && (0 == gcoll.dry_run)) {
+ if ((0 != clp->out_count) && (0 == clp->dry_run)) {
pr2serr(">>>> Some error occurred, remaining blocks=%" PRId64 "\n",
- gcoll.out_count);
+ clp->out_count);
if (0 == res)
res = SG_LIB_CAT_OTHER;
}
print_stats("");
- if (gcoll.dio_incomplete_count) {
+ if (clp->dio_incomplete_count) {
int fd;
char c;
pr2serr(">> Direct IO requested but incomplete %d times\n",
- gcoll.dio_incomplete_count);
+ clp->dio_incomplete_count);
if ((fd = open(proc_allow_dio, O_RDONLY)) >= 0) {
if (1 == read(fd, &c, 1)) {
if ('0' == c)
@@ -1987,8 +2147,8 @@ fini:
close(fd);
}
}
- if (gcoll.sum_of_resids)
+ if (clp->sum_of_resids)
pr2serr(">> Non-zero sum of residual counts=%d\n",
- gcoll.sum_of_resids);
+ clp->sum_of_resids);
return (res >= 0) ? res : SG_LIB_CAT_OTHER;
}
diff --git a/testing/tst_sg_lib.c b/testing/tst_sg_lib.c
index 027e6fb2..ff59ebc7 100644
--- a/testing/tst_sg_lib.c
+++ b/testing/tst_sg_lib.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <unistd.h>
@@ -42,7 +44,7 @@
* related to snprintf().
*/
-static const char * version_str = "1.11 20180715";
+static const char * version_str = "1.12 20181207";
#define MAX_LINE_LEN 1024
diff --git a/testing/uapi_sg.h b/testing/uapi_sg.h
index 1485c2e8..38087a71 100644
--- a/testing/uapi_sg.h
+++ b/testing/uapi_sg.h
@@ -13,7 +13,7 @@
* Version 2 and 3 extensions to driver:
* Copyright (C) 1998 - 2018 Douglas Gilbert
*
- * Version: 3.9.02 (20181118)
+ * Version: 3.9.02 (20181203)
* This version is for Linux 2.6, 3 and 4 series kernels.
*
* Documentation
@@ -105,7 +105,7 @@ typedef struct sg_io_hdr {
*/
#define SGV4_FLAG_DIRECT_IO SG_FLAG_DIRECT_IO
#define SGV4_FLAG_MMAP_IO SG_FLAG_MMAP_IO
-#define SGV4_FLAG_SYNC 0x8 /* similar to ioctl(SG_IO) */
+#define SGV4_FLAG_V3_MAP 0x8 /* used internally */
#define SGV4_FLAG_Q_AT_TAIL SG_FLAG_Q_AT_TAIL
#define SGV4_FLAG_Q_AT_HEAD SG_FLAG_Q_AT_HEAD
/* Following 2 flags for request::tag (type: int) manipulations */
diff --git a/utils/hxascdmp.c b/utils/hxascdmp.c
index 077fd93e..9f6566d3 100644
--- a/utils/hxascdmp.c
+++ b/utils/hxascdmp.c
@@ -3,6 +3,8 @@
* All rights reserved.
* Use of this source code is governed by a BSD-style
* license that can be found in the BSD_LICENSE file.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
*/
#include <stdlib.h>
@@ -17,7 +19,7 @@
static int bytes_per_line = DEF_BYTES_PER_LINE;
-static const char * version_str = "1.14 20140213";
+static const char * version_str = "1.15 20181207";
#define CHARS_PER_HEX_BYTE 3
#define BINARY_START_COL 6