Skip to content

Commit

Permalink
libceph: distinguish two phases of connect sequence
Browse files Browse the repository at this point in the history
Currently a ceph connection enters a "CONNECTING" state when it
begins the process of (re-)connecting with its peer.  Once the two
ends have successfully exchanged their banner and addresses, an
additional NEGOTIATING bit is set in the ceph connection's state to
indicate the connection information exhange has begun.  The
CONNECTING bit/state continues to be set during this phase.

Rather than have the CONNECTING state continue while the NEGOTIATING
bit is set, interpret these two phases as distinct states.  In other
words, when NEGOTIATING is set, clear CONNECTING.  That way only
one of them will be active at a time.

Signed-off-by: Alex Elder <elder@inktank.com>
Reviewed-by: Sage Weil <sage@inktank.com>
  • Loading branch information
Alex Elder authored and Sage Weil committed Jul 6, 2012
1 parent ab166d5 commit 7593af9
Showing 1 changed file with 28 additions and 24 deletions.
52 changes: 28 additions & 24 deletions net/ceph/messenger.c
Original file line number Diff line number Diff line change
Expand Up @@ -1559,7 +1559,6 @@ static int process_connect(struct ceph_connection *con)
return -1;
}
clear_bit(NEGOTIATING, &con->state);
clear_bit(CONNECTING, &con->state);
set_bit(CONNECTED, &con->state);
con->peer_global_seq = le32_to_cpu(con->in_reply.global_seq);
con->connect_seq++;
Expand Down Expand Up @@ -2000,7 +1999,8 @@ static int try_write(struct ceph_connection *con)
}

do_next:
if (!test_bit(CONNECTING, &con->state)) {
if (!test_bit(CONNECTING, &con->state) &&
!test_bit(NEGOTIATING, &con->state)) {
/* is anything else pending? */
if (!list_empty(&con->out_queue)) {
prepare_write_message(con);
Expand Down Expand Up @@ -2057,25 +2057,29 @@ static int try_read(struct ceph_connection *con)
}

if (test_bit(CONNECTING, &con->state)) {
if (!test_bit(NEGOTIATING, &con->state)) {
dout("try_read connecting\n");
ret = read_partial_banner(con);
if (ret <= 0)
goto out;
ret = process_banner(con);
if (ret < 0)
goto out;

/* Banner is good, exchange connection info */
ret = prepare_write_connect(con);
if (ret < 0)
goto out;
prepare_read_connect(con);
set_bit(NEGOTIATING, &con->state);

/* Send connection info before awaiting response */
dout("try_read connecting\n");
ret = read_partial_banner(con);
if (ret <= 0)
goto out;
}
ret = process_banner(con);
if (ret < 0)
goto out;

clear_bit(CONNECTING, &con->state);
set_bit(NEGOTIATING, &con->state);

/* Banner is good, exchange connection info */
ret = prepare_write_connect(con);
if (ret < 0)
goto out;
prepare_read_connect(con);

/* Send connection info before awaiting response */
goto out;
}

if (test_bit(NEGOTIATING, &con->state)) {
dout("try_read negotiating\n");
ret = read_partial_connect(con);
if (ret <= 0)
goto out;
Expand Down Expand Up @@ -2197,12 +2201,12 @@ static void con_work(struct work_struct *work)
if (test_and_clear_bit(SOCK_CLOSED, &con->flags)) {
if (test_and_clear_bit(CONNECTED, &con->state))
con->error_msg = "socket closed";
else if (test_and_clear_bit(CONNECTING, &con->state)) {
clear_bit(NEGOTIATING, &con->state);
else if (test_and_clear_bit(NEGOTIATING, &con->state))
con->error_msg = "negotiation failed";
else if (test_and_clear_bit(CONNECTING, &con->state))
con->error_msg = "connection failed";
} else {
else
con->error_msg = "unrecognized con state";
}
goto fault;
}

Expand Down

0 comments on commit 7593af9

Please sign in to comment.