@@ -95,6 +95,7 @@ struct iscsi_context {
|
|||||||
int is_loggedin;
|
int is_loggedin;
|
||||||
int is_reconnecting;
|
int is_reconnecting;
|
||||||
int bind_interfaces_cnt;
|
int bind_interfaces_cnt;
|
||||||
|
int nops_in_flight;
|
||||||
|
|
||||||
int chap_a;
|
int chap_a;
|
||||||
int chap_i;
|
int chap_i;
|
||||||
@@ -217,7 +218,8 @@ struct iscsi_pdu {
|
|||||||
|
|
||||||
struct iscsi_data outdata; /* Header for PDU to send */
|
struct iscsi_data outdata; /* Header for PDU to send */
|
||||||
uint32_t out_offset; /* Offset into data-out iovector */
|
uint32_t out_offset; /* Offset into data-out iovector */
|
||||||
uint32_t out_len; /* Amount of data to sent */
|
uint32_t out_len; /* Amount of data to sent starting at out_offset */
|
||||||
|
uint32_t out_written; /* Number of bytes written to socket */
|
||||||
|
|
||||||
struct iscsi_data indata;
|
struct iscsi_data indata;
|
||||||
|
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ struct sockaddr;
|
|||||||
|
|
||||||
/* FEATURES */
|
/* FEATURES */
|
||||||
#define LIBISCSI_FEATURE_IOVECTOR (1)
|
#define LIBISCSI_FEATURE_IOVECTOR (1)
|
||||||
|
#define LIBISCSI_FEATURE_NOP_COUNTER (1)
|
||||||
|
|
||||||
#define MAX_STRING_SIZE (255)
|
#define MAX_STRING_SIZE (255)
|
||||||
|
|
||||||
@@ -474,10 +475,17 @@ struct iscsi_discovery_address {
|
|||||||
* structure containing the data returned from
|
* structure containing the data returned from
|
||||||
* the server.
|
* the server.
|
||||||
* ISCSI_STATUS_CANCELLED: Discovery was aborted. Command_data is NULL.
|
* ISCSI_STATUS_CANCELLED: Discovery was aborted. Command_data is NULL.
|
||||||
|
*
|
||||||
|
* The callback may be NULL if you only want to let libiscsi count the in-flight
|
||||||
|
* NOPs.
|
||||||
*/
|
*/
|
||||||
EXTERN int iscsi_nop_out_async(struct iscsi_context *iscsi, iscsi_command_cb cb,
|
EXTERN int iscsi_nop_out_async(struct iscsi_context *iscsi, iscsi_command_cb cb,
|
||||||
unsigned char *data, int len, void *private_data);
|
unsigned char *data, int len, void *private_data);
|
||||||
|
|
||||||
|
|
||||||
|
/* read out the number of consecutive nop outs that did not receive an answer */
|
||||||
|
EXTERN int iscsi_get_nops_in_flight(struct iscsi_context *iscsi);
|
||||||
|
|
||||||
struct scsi_task;
|
struct scsi_task;
|
||||||
|
|
||||||
enum iscsi_task_mgmt_funcs {
|
enum iscsi_task_mgmt_funcs {
|
||||||
|
|||||||
+7
-23
@@ -288,6 +288,12 @@ try_again:
|
|||||||
goto try_again;
|
goto try_again;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
while (old_iscsi->outqueue) {
|
||||||
|
struct iscsi_pdu *pdu = old_iscsi->outqueue;
|
||||||
|
SLIST_REMOVE(&old_iscsi->outqueue, pdu);
|
||||||
|
SLIST_ADD_END(&old_iscsi->waitpdu, pdu);
|
||||||
|
}
|
||||||
|
|
||||||
while (old_iscsi->waitpdu) {
|
while (old_iscsi->waitpdu) {
|
||||||
struct iscsi_pdu *pdu = old_iscsi->waitpdu;
|
struct iscsi_pdu *pdu = old_iscsi->waitpdu;
|
||||||
|
|
||||||
@@ -296,29 +302,6 @@ try_again:
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
pdu->itt = iscsi_itt_post_increment(iscsi);
|
|
||||||
iscsi_pdu_set_itt(pdu, pdu->itt);
|
|
||||||
|
|
||||||
/* do not increase cmdsn for PDUs marked for immediate delivery
|
|
||||||
* this will result in a protocol error */
|
|
||||||
pdu->cmdsn = (pdu->outdata.data[0] & ISCSI_PDU_IMMEDIATE)?iscsi->cmdsn:iscsi->cmdsn++;
|
|
||||||
iscsi_pdu_set_cmdsn(pdu, pdu->cmdsn);
|
|
||||||
|
|
||||||
iscsi_pdu_set_expstatsn(pdu, iscsi->statsn);
|
|
||||||
iscsi->statsn++;
|
|
||||||
|
|
||||||
pdu->written = 0;
|
|
||||||
iscsi_add_to_outqueue(iscsi, pdu);
|
|
||||||
}
|
|
||||||
|
|
||||||
while (old_iscsi->outqueue) {
|
|
||||||
struct iscsi_pdu *pdu = old_iscsi->outqueue;
|
|
||||||
|
|
||||||
SLIST_REMOVE(&old_iscsi->outqueue, pdu);
|
|
||||||
if (pdu->itt == 0xffffffff) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (pdu->flags & ISCSI_PDU_DROP_ON_RECONNECT) {
|
if (pdu->flags & ISCSI_PDU_DROP_ON_RECONNECT) {
|
||||||
/* We dont want to requeue things like DATA-OUT since these guys
|
/* We dont want to requeue things like DATA-OUT since these guys
|
||||||
* will be reissued automatically anyway once the corresponding
|
* will be reissued automatically anyway once the corresponding
|
||||||
@@ -341,6 +324,7 @@ try_again:
|
|||||||
iscsi->statsn++;
|
iscsi->statsn++;
|
||||||
|
|
||||||
pdu->written = 0;
|
pdu->written = 0;
|
||||||
|
pdu->out_written = 0;
|
||||||
iscsi_add_to_outqueue(iscsi, pdu);
|
iscsi_add_to_outqueue(iscsi, pdu);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ iscsi_get_fd
|
|||||||
iscsi_get_lba_status_sync
|
iscsi_get_lba_status_sync
|
||||||
iscsi_get_lba_status_task
|
iscsi_get_lba_status_task
|
||||||
iscsi_get_target_address
|
iscsi_get_target_address
|
||||||
|
iscsi_get_nops_in_flight
|
||||||
iscsi_inquiry_sync
|
iscsi_inquiry_sync
|
||||||
iscsi_inquiry_task
|
iscsi_inquiry_task
|
||||||
iscsi_is_logged_in
|
iscsi_is_logged_in
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ iscsi_get_fd
|
|||||||
iscsi_get_lba_status_sync
|
iscsi_get_lba_status_sync
|
||||||
iscsi_get_lba_status_task
|
iscsi_get_lba_status_task
|
||||||
iscsi_get_target_address
|
iscsi_get_target_address
|
||||||
|
iscsi_get_nops_in_flight
|
||||||
iscsi_inquiry_sync
|
iscsi_inquiry_sync
|
||||||
iscsi_inquiry_task
|
iscsi_inquiry_task
|
||||||
iscsi_is_logged_in
|
iscsi_is_logged_in
|
||||||
|
|||||||
@@ -81,6 +81,8 @@ iscsi_nop_out_async(struct iscsi_context *iscsi, iscsi_command_cb cb,
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
iscsi->nops_in_flight++;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -130,6 +132,12 @@ iscsi_process_nop_out_reply(struct iscsi_context *iscsi, struct iscsi_pdu *pdu,
|
|||||||
{
|
{
|
||||||
struct iscsi_data data;
|
struct iscsi_data data;
|
||||||
|
|
||||||
|
iscsi->nops_in_flight = 0;
|
||||||
|
|
||||||
|
if (pdu->callback == NULL) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
data.data = NULL;
|
data.data = NULL;
|
||||||
data.size = 0;
|
data.size = 0;
|
||||||
|
|
||||||
@@ -137,7 +145,13 @@ iscsi_process_nop_out_reply(struct iscsi_context *iscsi, struct iscsi_pdu *pdu,
|
|||||||
data.data = in->data;
|
data.data = in->data;
|
||||||
data.size = in->data_pos;
|
data.size = in->data_pos;
|
||||||
}
|
}
|
||||||
|
|
||||||
pdu->callback(iscsi, SCSI_STATUS_GOOD, &data, pdu->private_data);
|
pdu->callback(iscsi, SCSI_STATUS_GOOD, &data, pdu->private_data);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int iscsi_get_nops_in_flight(struct iscsi_context *iscsi)
|
||||||
|
{
|
||||||
|
return iscsi->nops_in_flight;
|
||||||
|
}
|
||||||
|
|||||||
+7
-10
@@ -517,11 +517,11 @@ iscsi_write_to_socket(struct iscsi_context *iscsi)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Write any iovectors that might have been passed to us */
|
/* Write any iovectors that might have been passed to us */
|
||||||
while (pdu->out_len > 0) {
|
while (pdu->out_written < pdu->out_len) {
|
||||||
unsigned char *buf;
|
unsigned char *buf;
|
||||||
|
|
||||||
count = pdu->out_len;
|
count = pdu->out_len - pdu->out_written;
|
||||||
buf = iscsi_get_user_out_buffer(iscsi, pdu, pdu->out_offset, &count);
|
buf = iscsi_get_user_out_buffer(iscsi, pdu, pdu->out_offset + pdu->out_written, &count);
|
||||||
if (buf == NULL) {
|
if (buf == NULL) {
|
||||||
iscsi_set_error(iscsi, "Can't find iovector data for DATA-OUT");
|
iscsi_set_error(iscsi, "Can't find iovector data for DATA-OUT");
|
||||||
return -1;
|
return -1;
|
||||||
@@ -539,16 +539,13 @@ iscsi_write_to_socket(struct iscsi_context *iscsi)
|
|||||||
"socket :%d", errno);
|
"socket :%d", errno);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
pdu->out_offset += count;
|
pdu->out_written += count;
|
||||||
pdu->out_len -= count;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pdu->written == total) {
|
if (pdu->flags & ISCSI_PDU_DELETE_WHEN_SENT) {
|
||||||
if (pdu->flags & ISCSI_PDU_DELETE_WHEN_SENT) {
|
iscsi_free_pdu(iscsi, pdu);
|
||||||
iscsi_free_pdu(iscsi, pdu);
|
|
||||||
}
|
|
||||||
iscsi->outqueue_current = NULL;
|
|
||||||
}
|
}
|
||||||
|
iscsi->outqueue_current = NULL;
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user