diff --git a/ctdb/utils/scsi_io/scsi_io.c b/ctdb/utils/scsi_io/scsi_io.c
deleted file mode 100644
index 1d771de7c02..00000000000
--- a/ctdb/utils/scsi_io/scsi_io.c
+++ /dev/null
@@ -1,1152 +0,0 @@
-/* a tool to open a scsi device and issue some useful commands
- such as INQUIRY and helpers to call various PERSISTENT RESERVATION
- functions
-
- Copyright ronnie sahlberg 2007
-
- 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 3 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, see .
-*/
-
-/* Very incomplete and needs to be enhanced with nice command line options
- to drive it.
- We need access to an array that supports the PERSISTENT RESERVATION cdb's
- before we can proceed
-*/
-/* scsi bugs:
- INQUIRY takes a 2 byte allocation_length parameter but it appears that
- it only looks at the low byte. If you specify 0x00ff all is well
- but if you specify 0x0100 it gets confused and returns garbage data
- for (e.g) SupportedVPDPages. Same goes for UnitSerialNumber and probably all
- other inq pages as well.
-
-*/
-
-#include
-#include
-#include
-#include
-#include
-#include
-#include
-#include "popt.h"
-
-
-#define SCSI_TIMEOUT 5000 /* ms */
-
-static char *command = NULL;
-static char *device = NULL;
-static char *key = NULL;
-static char *rmkey = NULL;
-static int scope = -1;
-static int type = -1;
-
-const char *sensetable[16]={
- "no sense",
- "recovered error",
- "not ready",
- "medium error",
- "hardware error",
- "illegal request",
- "unit attention",
- "data protect",
- "blank check",
- "vendor specific",
- "copy aborted",
- "aboreted command",
- "unknown",
- "unknown",
- "unknown",
- "unknown"
-};
-
-int scsi_io(int fd, unsigned char *cdb, unsigned char cdb_size, int xfer_dir, unsigned char *data, unsigned int *data_size, unsigned char *sense, unsigned int *sense_len)
-{
- sg_io_hdr_t io_hdr;
-
- memset(&io_hdr, 0, sizeof(sg_io_hdr_t));
- io_hdr.interface_id = 'S';
-
- /* CDB */
- io_hdr.cmdp = cdb;
- io_hdr.cmd_len = cdb_size;
-
- /* Where to store the sense_data, if there was an error */
- io_hdr.sbp = sense;
- io_hdr.mx_sb_len = *sense_len;
- *sense_len=0;
-
- /* Transfer direction, either in or out. Linux does not yet
- support bidirectional SCSI transfers ?
- */
- io_hdr.dxfer_direction = xfer_dir;
-
- /* Where to store the DATA IN/OUT from the device and how big the
- buffer is
- */
- io_hdr.dxferp = data;
- io_hdr.dxfer_len = *data_size;
-
- /* SCSI timeout in ms */
- io_hdr.timeout = SCSI_TIMEOUT;
-
-
- if(ioctl(fd, SG_IO, &io_hdr) < 0){
- perror("SG_IO ioctl failed");
- return -1;
- }
-
- /* now for the error processing */
- if((io_hdr.info & SG_INFO_OK_MASK) != SG_INFO_OK){
- if(io_hdr.sb_len_wr > 0){
- *sense_len=io_hdr.sb_len_wr;
- return 0;
- }
- }
- if(io_hdr.masked_status){
- printf("status=0x%x\n", io_hdr.status);
- printf("masked_status=0x%x\n", io_hdr.masked_status);
- return -2;
- }
- if(io_hdr.host_status){
- printf("host_status=0x%x\n", io_hdr.host_status);
- return -3;
- }
- if(io_hdr.driver_status){
- printf("driver_status=0x%x\n", io_hdr.driver_status);
- return -4;
- }
-
-#if 0
-{int i;
-printf("CDB:\n");
-for(i=0;istring){
- if(vs->value==v){
- return vs->string;
- }
- vs++;
- }
- return "";
-}
-
-void print_sense_data(unsigned char *sense, int sense_len)
-{
- int i;
- unsigned char asc, ascq;
-
- printf("Device returned sense information\n");
- if(sense[0]==0x70){
- printf("filemark:%d eom:%d ili:%d sense-key:0x%02x (%s)\n",
- !!(sense[2]&0x80),
- !!(sense[2]&0x40),
- !!(sense[2]&0x20),
- sense[2]&0x0f,
- sensetable[sense[2]&0x0f]);
- printf("command specific info: 0x%02x 0x%02x 0x%02x 0x%02x\n",
- sense[8],sense[9],sense[10],sense[11]);
-
- asc=sense[12];
- printf("additional sense code:0x%02x\n", asc);
-
- ascq=sense[13];
- printf("additional sense code qualifier:0x%02x\n", ascq);
-
- printf("field replaceable unit code:0x%02x\n", sense[14]);
-
- if((asc==0x20)&&(ascq==0x00))
- printf("INVALID COMMAND OPERATION CODE\n");
- }
-
- printf("Sense data:\n");
- for(i=0;i>8)&0xff;
- cdb[4]=data_size&0xff;
-
-
- printf("Standard INQUIRY Data:\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* Peripheral Qualifier */
- printf("Peripheral Qualifier:%c%c%cb\n",
- '0'+!!(data[0]&0x80),
- '0'+!!(data[0]&0x40),
- '0'+!!(data[0]&0x20));
-
- /* Peripheral Device Type */
- printf("Peripheral Device Type: 0x%02x (%s)\n",
- data[0]&0x1f,
- val_to_str(peripheral_device_types, data[0]&0x1f));
-
- /* RMB */
- printf("RMB: %s device\n", data[1]&0x80?"REMOVABLE":"NON-REMOVABLE");
-
- /* SCSI Version */
- printf("SCSI Version: 0x%02x (%s)\n",
- data[2],
- val_to_str(scsi_versions, data[2]));
-
- /* NormACA, HiSUP, Response Data Format */
- printf("NormACA:%d HiSup:%d ResponseDataFormat:%d\n",
- !!(data[3]&0x20),
- !!(data[3]&0x10),
- data[3]&0x0f);
-
- switch(data[3]&0x0f){
- /*SPC-2/SPC-3/SPC-4*/
- case 2:
- /*SPC (not strictly correct but we print it like 2 anyway)*/
- case 1:
- /* SCCS ... */
- printf("SCCS:%d ACC:%d TPGS:%c%cb 3PC:%d PROTECT:%d\n",
- !!(data[5]&0x80),
- !!(data[5]&0x40),
- '0'+!!(data[5]&0x20),
- '0'+!!(data[5]&0x10),
- !!(data[5]&0x08),
- !!(data[5]&0x01));
-
- /* Encserv ... */
- printf("Encserv:%d VS:%d MultiP:%d ADDR16:%d\n",
- !!(data[6]&0x40),
- !!(data[6]&0x20),
- !!(data[6]&0x10),
- !!(data[6]&0x01));
-
- /* WBUS16 ... */
- printf("WBUS16:%d SYNC:%d CmdQue:%d VS:%d\n",
- !!(data[7]&0x20),
- !!(data[7]&0x10),
- !!(data[7]&0x02),
- !!(data[7]&0x01));
-
-
- /* T10 vendor Identification */
- printf("Vendor:");
- for(i=0;i<8;i++)printf("%c",data[8+i]);printf("\n");
-
- /* Product Identification */
- printf("Product:");
- for(i=0;i<16;i++)printf("%c",data[16+i]);printf("\n");
-
- /* Product Revision Level */
- printf("Product Revision:");
- for(i=0;i<4;i++)printf("%c",data[32+i]);printf("\n");
-
- break;
- }
-
- return 0;
-}
-
-int scsi_inquiry_supported_vpd_pages(int fd)
-{
- unsigned char cdb[]={0x12,0x01,0,0,0,0};
-
- unsigned int data_size=0xff;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
-
- int res, pl, i;
-
- cdb[3]=(data_size>>8)&0xff;
- cdb[4]=data_size&0xff;
-
-
- printf("INQUIRY Supported VPD Pages:\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* Page Length */
- pl=data[3];
-
- /* Pages */
- for(i=4;i<(pl+4);i++){
- printf("Page:%02xh (%s)\n",
- data[i],
- val_to_str(vpd_pages, data[i]));
- }
-
- return 0;
-}
-
-int scsi_inquiry_unit_serial_number(int fd)
-{
- unsigned char cdb[]={0x12,0x01,0x80,0,0,0};
-
- unsigned int data_size=0x00ff;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
-
- int res, pl, i;
-
- cdb[3]=(data_size>>8)&0xff;
- cdb[4]=data_size&0xff;
-
-
- printf("INQUIRY Unit Serial Number:\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* Page Length */
- pl=data[3];
-
- /* Unit Serial Number */
- printf("Unit Serial Number:");
- for(i=4;i<(pl+4);i++)printf("%c",data[i]&0xff);printf("\n");
-
- return 0;
-}
-
-int scsi_persistent_reserve_in_read_keys(int fd)
-{
- unsigned char cdb[]={0x5e,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=0x00ff;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=0;
- int res, i;
- unsigned long prgeneration, additional_length;
-
- cdb[1]=service_action;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
-
- printf("PERSISTENT RESERVE IN: READ KEYS\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* PRGeneration */
- prgeneration=data[0];
- prgeneration<<=8;prgeneration|=data[1];
- prgeneration<<=8;prgeneration|=data[2];
- prgeneration<<=8;prgeneration|=data[3];
- printf("PRGeneration:%lu\n", prgeneration);
-
- /* Additional Length */
- additional_length=data[4];
- additional_length<<=8;additional_length|=data[5];
- additional_length<<=8;additional_length|=data[6];
- additional_length<<=8;additional_length|=data[7];
- printf("Additional Length:%lu\n", additional_length);
-
- /* print the registered keys */
- for(i=0;i>8)&0xff;
- cdb[8]=data_size&0xff;
-
-
- printf("PERSISTENT RESERVE IN: READ RESERVATION\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* PRGeneration */
- prgeneration=data[0];
- prgeneration<<=8;prgeneration|=data[1];
- prgeneration<<=8;prgeneration|=data[2];
- prgeneration<<=8;prgeneration|=data[3];
- printf("PRGeneration:%lu\n", prgeneration);
-
- /* Additional Length */
- additional_length=data[4];
- additional_length<<=8;additional_length|=data[5];
- additional_length<<=8;additional_length|=data[6];
- additional_length<<=8;additional_length|=data[7];
- printf("Additional Length:%lu\n", additional_length);
-
- if(additional_length==16){
- printf("Key:%02x%02x%02x%02x%02x%02x%02x%02x\n",
- data[8],
- data[9],
- data[10],
- data[11],
- data[12],
- data[13],
- data[14],
- data[15]);
- printf("Scope:%xh Type:%xh\n",data[21]>>4,data[21]&0x0f);
- }
-
- return 0;
-}
-
-int scsi_persistent_reserve_in_report_capabilities(int fd)
-{
- unsigned char cdb[]={0x5e,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=0x00ff;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=2;
- int res;
- unsigned short length, type_mask;
-
- cdb[1]=service_action;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
-
- printf("PERSISTENT RESERVE IN: REPORT CAPABILITIES\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* Length */
- length=data[0];
- length<<=8;length|=data[1];
- printf("Length:%d\n", length);
-
- /* CRH ... */
- printf("CRH:%d SIP_C:%d ATP_C:%d PTPL_C:%d\n",
- !!(data[2]&0x10),
- !!(data[2]&0x08),
- !!(data[2]&0x04),
- !!(data[2]&0x01));
-
- /* TMV ... */
- printf("TMV:%d ALLOW_COMMANDS:%c%c%cb PTPL_A:%d\n",
- !!(data[3]&0x80),
- '0'+(!!(data[3]&0x40)),
- '0'+(!!(data[3]&0x20)),
- '0'+(!!(data[3]&0x10)),
- !!(data[3]&0x01));
-
- /* Persistent Reservation Type Mask */
- type_mask=data[4];
- type_mask<<=8;type_mask|=data[5];
- printf("Persistent Reservation Type Mask:0x%04x\n", type_mask);
- printf("WR_EX_AR:%d EX_AC_RO:%d WR_EX_RO:%d EX_AC:%d WR_EX:%d EX_AC_AR:%d\n",
- !!(data[4]&0x80),
- !!(data[4]&0x40),
- !!(data[4]&0x20),
- !!(data[4]&0x08),
- !!(data[4]&0x02),
- !!(data[4]&0x01));
-
- return 0;
-}
-
-int scsi_persistent_reserve_in_read_full_status(int fd)
-{
- unsigned char cdb[]={0x5e,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=0x00ff;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=3;
- int res;
- unsigned long prgeneration, additional_length;
-
- cdb[1]=service_action;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
-
- printf("PERSISTENT RESERVE IN: READ FULL STATUS\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_FROM_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- /* PRGeneration */
- prgeneration=data[0];
- prgeneration<<=8;prgeneration|=data[1];
- prgeneration<<=8;prgeneration|=data[2];
- prgeneration<<=8;prgeneration|=data[3];
- printf("PRGeneration:%lu\n", prgeneration);
-
- /* Additional Length */
- additional_length=data[4];
- additional_length<<=8;additional_length|=data[5];
- additional_length<<=8;additional_length|=data[6];
- additional_length<<=8;additional_length|=data[7];
- printf("Additional Length:%lu\n", additional_length);
-
-/*XXX*/
-
- return 0;
-}
-
-int scsi_persistent_reserve_out_clear(int fd)
-{
- unsigned char cdb[]={0x5f,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=24;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=3;
- int res;
-
- long long k;
-
- if (scope==-1) {
- printf("Must specify scope\n");
- printf("scsi_io --device= --command=clear --scope= --type= --key=\n");
- _exit(10);
- }
- if (type==-1) {
- printf("Must specify type\n");
- printf("scsi_io --device= --command=clear --scope= --type= --key=\n");
- _exit(10);
- }
- if (!key) {
- printf("Must specify key\n");
- printf("scsi_io --device= --command=clear --scope= --type= --key=\n");
- _exit(10);
- }
-
- sscanf(key, "%llx", &k);
- cdb[1]=service_action;
- cdb[2]=(scope<<4)|type;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
- memset(data, 0, data_size);
-
- /* Reservation Key */
- data[0]=(k>>56)&0xff;
- data[1]=(k>>48)&0xff;
- data[2]=(k>>40)&0xff;
- data[3]=(k>>32)&0xff;
- data[4]=(k>>24)&0xff;
- data[5]=(k>>16)&0xff;
- data[6]=(k>> 8)&0xff;
- data[7]=(k )&0xff;
-
- /* Service Action Key */
- data[8]=0;
- data[9]=0;
- data[10]=0;
- data[11]=0;
- data[12]=0;
- data[13]=0;
- data[14]=0;
- data[15]=0;
-
- /* Spec_ip_ti=0 all_tg_pt=1 aptpl=0 */
- data[20]=0x04;
-
- printf("PERSISTENT RESERVE IN: CLEAR\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_TO_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- return 0;
-}
-
-int scsi_persistent_reserve_out_reserve(int fd)
-{
- unsigned char cdb[]={0x5f,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=24;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=1;
- int res;
- long long k;
-
- if (scope==-1) {
- printf("Must specify scope\n");
- printf("scsi_io --device= --command=reserve --scope= --type= --key=\n");
- _exit(10);
- }
- if (type==-1) {
- printf("Must specify type\n");
- printf("scsi_io --device= --command=reserve --scope= --type= --key=\n");
- _exit(10);
- }
- if (!key) {
- printf("Must specify key\n");
- printf("scsi_io --device= --command=reserve --scope= --type= --key=\n");
- _exit(10);
- }
-
- sscanf(key, "%llx", &k);
-
-
- cdb[1]=service_action;
- cdb[2]=(scope<<4)|type;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
- memset(data, 0, data_size);
-
- /* Reservation Key */
- data[0]=(k>>56)&0xff;
- data[1]=(k>>48)&0xff;
- data[2]=(k>>40)&0xff;
- data[3]=(k>>32)&0xff;
- data[4]=(k>>24)&0xff;
- data[5]=(k>>16)&0xff;
- data[6]=(k>> 8)&0xff;
- data[7]=(k )&0xff;
-
- /* Service Action Key */
- data[8]=0;
- data[9]=0;
- data[10]=0;
- data[11]=0;
- data[12]=0;
- data[13]=0;
- data[14]=0;
- data[15]=0;
-
- /* Spec_ip_ti=0 all_tg_pt=1 aptpl=0 */
- data[20]=0x04;
-
- printf("PERSISTENT RESERVE IN: RESERVE\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_TO_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- return 0;
-}
-
-int scsi_persistent_reserve_out_preempt(int fd)
-{
- unsigned char cdb[]={0x5f,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=24;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=4;
- int res;
- long long k;
-
- if (scope==-1) {
- printf("Must specify scope\n");
- printf("scsi_io --device= --command=preempt --scope= --type= --key= --rmkey=\n");
- _exit(10);
- }
- if (type==-1) {
- printf("Must specify type\n");
- printf("scsi_io --device= --command=preempt --scope= --type= --key= --rmkey=\n");
- _exit(10);
- }
- if (!key) {
- printf("Must specify key\n");
- printf("scsi_io --device= --command=preempt --scope= --type= --key= --rmkey=\n");
- _exit(10);
- }
- if (!rmkey) {
- printf("Must specify rmkey\n");
- printf("scsi_io --device= --command=preempt --scope= --type= --key= --rmkey=\n");
- _exit(10);
- }
-
-
-
- cdb[1]=service_action;
- cdb[2]=(scope<<4)|type;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
- memset(data, 0, data_size);
-
- /* Reservation Key */
- sscanf(key, "%llx", &k);
- data[0]=(k>>56)&0xff;
- data[1]=(k>>48)&0xff;
- data[2]=(k>>40)&0xff;
- data[3]=(k>>32)&0xff;
- data[4]=(k>>24)&0xff;
- data[5]=(k>>16)&0xff;
- data[6]=(k>> 8)&0xff;
- data[7]=(k )&0xff;
-
- /* Service Action Key */
- sscanf(rmkey, "%llx", &k);
- data[8] =(k>>56)&0xff;
- data[9] =(k>>48)&0xff;
- data[10]=(k>>40)&0xff;
- data[11]=(k>>32)&0xff;
- data[12]=(k>>24)&0xff;
- data[13]=(k>>16)&0xff;
- data[14]=(k>> 8)&0xff;
- data[15]=(k )&0xff;
-
- /* Spec_ip_ti=0 all_tg_pt=1 aptpl=0 */
- data[20]=0x04;
-
- printf("PERSISTENT RESERVE IN: RESERVE\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_TO_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- return 0;
-}
-
-int scsi_persistent_reserve_out_register_and_ignore_existing_key(int fd)
-{
- unsigned char cdb[]={0x5f,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=24;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=6;
- int res;
- long long k;
-
- if (scope==-1) {
- printf("Must specify scope\n");
- printf("scsi_io --device= --command=registerkey --scope= --type= --key=\n");
- _exit(10);
- }
- if (type==-1) {
- printf("Must specify type\n");
- printf("scsi_io --device= --command=registerkey --scope= --type= --key=\n");
- _exit(10);
- }
- if (!key) {
- printf("Must specify key\n");
- printf("scsi_io --device= --command=registerkey --scope= --type= --key=\n");
- _exit(10);
- }
-
- sscanf(key, "%llx", &k);
-
- cdb[1]=service_action;
- cdb[2]=(scope<<4)|type;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
- memset(data, 0, data_size);
-
- /* Reservation Key */
- data[0]=0;
- data[1]=0;
- data[2]=0;
- data[3]=0;
- data[4]=0;
- data[5]=0;
- data[6]=0;
- data[7]=0;
-
- /* Service Action Key */
- data[8] =(k>>56)&0xff;
- data[9] =(k>>48)&0xff;
- data[10]=(k>>40)&0xff;
- data[11]=(k>>32)&0xff;
- data[12]=(k>>24)&0xff;
- data[13]=(k>>16)&0xff;
- data[14]=(k>> 8)&0xff;
- data[15]=(k )&0xff;
-
- /* Spec_ip_ti=0 all_tg_pt=1 aptpl=0 */
- data[20]=0x04;
-
- printf("PERSISTENT RESERVE IN: REGISTER AND IGNORE EXISTING KEY\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_TO_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- return 0;
-}
-
-int scsi_persistent_reserve_out_unregister_key(int fd)
-{
- unsigned char cdb[]={0x5f,0,0,0,0,0,0,0,0,0};
-
- unsigned int data_size=24;
- unsigned char data[data_size];
-
- unsigned int sense_len=32;
- unsigned char sense[sense_len];
- unsigned char service_action=6;
- int res;
- long long k;
-
- if (scope==-1) {
- printf("Must specify scope\n");
- printf("scsi_io --device= --command=unregisterkey --scope= --type= --key=\n");
- _exit(10);
- }
- if (type==-1) {
- printf("Must specify type\n");
- printf("scsi_io --device= --command=unregisterkey --scope= --type= --key=\n");
- _exit(10);
- }
- if (!key) {
- printf("Must specify key\n");
- printf("scsi_io --device= --command=unregisterkey --scope= --type= --key=\n");
- _exit(10);
- }
-
- sscanf(key, "%llx", &k);
-
- cdb[1]=service_action;
- cdb[2]=(scope<<4)|type;
- cdb[7]=(data_size>>8)&0xff;
- cdb[8]=data_size&0xff;
-
- memset(data, 0, data_size);
-
- /* Reservation Key */
- data[0]=(k>>56)&0xff;
- data[1]=(k>>48)&0xff;
- data[2]=(k>>40)&0xff;
- data[3]=(k>>32)&0xff;
- data[4]=(k>>24)&0xff;
- data[5]=(k>>16)&0xff;
- data[6]=(k>> 8)&0xff;
- data[7]=(k )&0xff;
-
- /* Service Action Key */
- data[8]=0;
- data[9]=0;
- data[10]=0;
- data[11]=0;
- data[12]=0;
- data[13]=0;
- data[14]=0;
- data[15]=0;
-
- /* Spec_ip_ti=0 all_tg_pt=1 aptpl=0 */
- data[20]=0x04;
-
- printf("PERSISTENT RESERVE IN: UNREGISTER KEY\n");
-
- res=scsi_io(fd, cdb, sizeof(cdb), SG_DXFER_TO_DEV, data, &data_size, sense, &sense_len);
- if(res){
- printf("SCSI_IO failed\n");
- return -1;
- }
- if(sense_len){
- print_sense_data(sense, sense_len);
- return -1;
- }
-
- return 0;
-}
-
-
-
-
-int open_scsi_device(const char *dev)
-{
- int fd, vers;
-
- if((fd=open(dev, O_RDWR))<0){
- printf("ERROR could not open device %s\n", dev);
- return -1;
- }
- if ((ioctl(fd, SG_GET_VERSION_NUM, &vers) < 0) || (vers < 30000)) {
- printf("/dev is not an sg device, or old sg driver\n");
- close(fd);
- return -1;
- }
-
- return fd;
-}
-
-typedef int (*scsi_func_t)(int fd);
-typedef struct _cmds_t {
- const char *cmd;
- scsi_func_t func;
- const char *comment;
-} cmds_t;
-cmds_t cmds[] = {
- {"inq", scsi_inquiry, "Standard INQUIRY output"},
- {"vpd", scsi_inquiry_supported_vpd_pages, "Supported VPD Pages"},
- {"usn", scsi_inquiry_unit_serial_number, "Unit serial number"},
- {"readkeys", scsi_persistent_reserve_in_read_keys, "Read SCSI Reservation Keys"},
- {"readrsvr", scsi_persistent_reserve_in_read_reservation, "Read SCSI Reservation Data"},
- {"reportcap", scsi_persistent_reserve_in_report_capabilities, "Report reservation Capabilities"},
- {"registerkey", scsi_persistent_reserve_out_register_and_ignore_existing_key, "Register and ignore existing key"},
- {"unregisterkey", scsi_persistent_reserve_out_unregister_key, "Unregister a key"},
- {"clear", scsi_persistent_reserve_out_clear, "Clear all reservations and registrations"},
- {"reserve", scsi_persistent_reserve_out_reserve, "Reserve"},
- {"preempt", scsi_persistent_reserve_out_preempt, "Preempt (remove someone elses registration)"},
-};
-
-void usage(void)
-{
- int i;
- printf("Usage: scsi_io --command --device \n");
- printf("Commands:\n");
- for (i=0;i