Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(719)

Side by Side Diff: net/socket/ssl_client_socket_impl.cc

Issue 2593063003: Add Socket::ReadIfReady() (Closed)
Patch Set: self review. remove unused include Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/socket/ssl_client_socket_impl.h" 5 #include "net/socket/ssl_client_socket_impl.h"
6 6
7 #include <errno.h> 7 #include <errno.h>
8 #include <string.h> 8 #include <string.h>
9 9
10 #include <algorithm> 10 #include <algorithm>
(...skipping 847 matching lines...) Expand 10 before | Expand all | Expand 10 after
858 858
859 // static 859 // static
860 void SSLClientSocketImpl::DumpSSLClientSessionMemoryStats( 860 void SSLClientSocketImpl::DumpSSLClientSessionMemoryStats(
861 base::trace_event::ProcessMemoryDump* pmd) { 861 base::trace_event::ProcessMemoryDump* pmd) {
862 SSLContext::GetInstance()->session_cache()->DumpMemoryStats(pmd); 862 SSLContext::GetInstance()->session_cache()->DumpMemoryStats(pmd);
863 } 863 }
864 864
865 int SSLClientSocketImpl::Read(IOBuffer* buf, 865 int SSLClientSocketImpl::Read(IOBuffer* buf,
866 int buf_len, 866 int buf_len,
867 const CompletionCallback& callback) { 867 const CompletionCallback& callback) {
868 user_read_buf_ = buf; 868 int rv = ReadIfReady(buf, buf_len, callback);
869 user_read_buf_len_ = buf_len; 869 if (rv == ERR_IO_PENDING) {
870 user_read_buf_ = buf;
871 user_read_buf_len_ = buf_len;
872 }
873 return rv;
874 }
870 875
871 int rv = DoPayloadRead(); 876 int SSLClientSocketImpl::ReadIfReady(IOBuffer* buf,
877 int buf_len,
878 const CompletionCallback& callback) {
879 int rv = DoPayloadRead(buf, buf_len);
872 880
873 if (rv == ERR_IO_PENDING) { 881 if (rv == ERR_IO_PENDING) {
874 user_read_callback_ = callback; 882 user_read_callback_ = callback;
875 } else { 883 } else {
876 if (rv > 0) 884 if (rv > 0)
877 was_ever_used_ = true; 885 was_ever_used_ = true;
878 user_read_buf_ = NULL;
879 user_read_buf_len_ = 0;
880 } 886 }
881
882 return rv; 887 return rv;
883 } 888 }
884 889
885 int SSLClientSocketImpl::Write(IOBuffer* buf, 890 int SSLClientSocketImpl::Write(IOBuffer* buf,
886 int buf_len, 891 int buf_len,
887 const CompletionCallback& callback) { 892 const CompletionCallback& callback) {
888 user_write_buf_ = buf; 893 user_write_buf_ = buf;
889 user_write_buf_len_ = buf_len; 894 user_write_buf_len_ = buf_len;
890 895
891 int rv = DoPayloadWrite(); 896 int rv = DoPayloadWrite();
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after
1054 SSL_set_renegotiate_mode(ssl_.get(), ssl_renegotiate_freely); 1059 SSL_set_renegotiate_mode(ssl_.get(), ssl_renegotiate_freely);
1055 1060
1056 return OK; 1061 return OK;
1057 } 1062 }
1058 1063
1059 void SSLClientSocketImpl::DoReadCallback(int rv) { 1064 void SSLClientSocketImpl::DoReadCallback(int rv) {
1060 // Since Run may result in Read being called, clear |user_read_callback_| 1065 // Since Run may result in Read being called, clear |user_read_callback_|
1061 // up front. 1066 // up front.
1062 if (rv > 0) 1067 if (rv > 0)
1063 was_ever_used_ = true; 1068 was_ever_used_ = true;
1064 user_read_buf_ = NULL; 1069 user_read_buf_ = nullptr;
Bence 2017/03/03 16:33:41 Nice!
xunjieli 2017/03/03 19:41:06 Acknowledged.
1065 user_read_buf_len_ = 0; 1070 user_read_buf_len_ = 0;
1066 base::ResetAndReturn(&user_read_callback_).Run(rv); 1071 base::ResetAndReturn(&user_read_callback_).Run(rv);
1067 } 1072 }
1068 1073
1069 void SSLClientSocketImpl::DoWriteCallback(int rv) { 1074 void SSLClientSocketImpl::DoWriteCallback(int rv) {
1070 // Since Run may result in Write being called, clear |user_write_callback_| 1075 // Since Run may result in Write being called, clear |user_write_callback_|
1071 // up front. 1076 // up front.
1072 if (rv > 0) 1077 if (rv > 0)
1073 was_ever_used_ = true; 1078 was_ever_used_ = true;
1074 user_write_buf_ = NULL; 1079 user_write_buf_ = NULL;
(...skipping 334 matching lines...) Expand 10 before | Expand all | Expand 10 after
1409 case STATE_NONE: 1414 case STATE_NONE:
1410 default: 1415 default:
1411 rv = ERR_UNEXPECTED; 1416 rv = ERR_UNEXPECTED;
1412 NOTREACHED() << "unexpected state" << state; 1417 NOTREACHED() << "unexpected state" << state;
1413 break; 1418 break;
1414 } 1419 }
1415 } while (rv != ERR_IO_PENDING && next_handshake_state_ != STATE_NONE); 1420 } while (rv != ERR_IO_PENDING && next_handshake_state_ != STATE_NONE);
1416 return rv; 1421 return rv;
1417 } 1422 }
1418 1423
1419 int SSLClientSocketImpl::DoPayloadRead() { 1424 int SSLClientSocketImpl::DoPayloadRead(IOBuffer* buf, int buf_len) {
1420 crypto::OpenSSLErrStackTracer err_tracer(FROM_HERE); 1425 crypto::OpenSSLErrStackTracer err_tracer(FROM_HERE);
1421 1426
1422 DCHECK_LT(0, user_read_buf_len_); 1427 DCHECK_LT(0, buf_len);
1423 DCHECK(user_read_buf_.get()); 1428 DCHECK(buf);
1424 1429
1425 int rv; 1430 int rv;
1426 if (pending_read_error_ != kNoPendingResult) { 1431 if (pending_read_error_ != kNoPendingResult) {
1427 rv = pending_read_error_; 1432 rv = pending_read_error_;
1428 pending_read_error_ = kNoPendingResult; 1433 pending_read_error_ = kNoPendingResult;
1429 if (rv == 0) { 1434 if (rv == 0) {
1430 net_log_.AddByteTransferEvent(NetLogEventType::SSL_SOCKET_BYTES_RECEIVED, 1435 net_log_.AddByteTransferEvent(NetLogEventType::SSL_SOCKET_BYTES_RECEIVED,
1431 rv, user_read_buf_->data()); 1436 rv, buf->data());
1432 } else { 1437 } else {
1433 net_log_.AddEvent( 1438 net_log_.AddEvent(
1434 NetLogEventType::SSL_READ_ERROR, 1439 NetLogEventType::SSL_READ_ERROR,
1435 CreateNetLogOpenSSLErrorCallback(rv, pending_read_ssl_error_, 1440 CreateNetLogOpenSSLErrorCallback(rv, pending_read_ssl_error_,
1436 pending_read_error_info_)); 1441 pending_read_error_info_));
1437 } 1442 }
1438 pending_read_ssl_error_ = SSL_ERROR_NONE; 1443 pending_read_ssl_error_ = SSL_ERROR_NONE;
1439 pending_read_error_info_ = OpenSSLErrorInfo(); 1444 pending_read_error_info_ = OpenSSLErrorInfo();
1440 return rv; 1445 return rv;
1441 } 1446 }
1442 1447
1443 int total_bytes_read = 0; 1448 int total_bytes_read = 0;
1444 int ssl_ret; 1449 int ssl_ret;
1445 do { 1450 do {
1446 ssl_ret = SSL_read(ssl_.get(), user_read_buf_->data() + total_bytes_read, 1451 ssl_ret = SSL_read(ssl_.get(), buf->data() + total_bytes_read,
1447 user_read_buf_len_ - total_bytes_read); 1452 buf_len - total_bytes_read);
1448 if (ssl_ret > 0) 1453 if (ssl_ret > 0)
1449 total_bytes_read += ssl_ret; 1454 total_bytes_read += ssl_ret;
1450 } while (total_bytes_read < user_read_buf_len_ && ssl_ret > 0); 1455 } while (total_bytes_read < buf_len && ssl_ret > 0);
1451 1456
1452 // Although only the final SSL_read call may have failed, the failure needs to 1457 // Although only the final SSL_read call may have failed, the failure needs to
1453 // processed immediately, while the information still available in OpenSSL's 1458 // processed immediately, while the information still available in OpenSSL's
1454 // error queue. 1459 // error queue.
1455 if (ssl_ret <= 0) { 1460 if (ssl_ret <= 0) {
1456 // A zero return from SSL_read may mean any of: 1461 // A zero return from SSL_read may mean any of:
1457 // - The underlying BIO_read returned 0. 1462 // - The underlying BIO_read returned 0.
1458 // - The peer sent a close_notify. 1463 // - The peer sent a close_notify.
1459 // - Any arbitrary error. https://crbug.com/466303 1464 // - Any arbitrary error. https://crbug.com/466303
1460 // 1465 //
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
1497 pending_read_error_ = kNoPendingResult; 1502 pending_read_error_ = kNoPendingResult;
1498 } else { 1503 } else {
1499 // No bytes were returned. Return the pending read error immediately. 1504 // No bytes were returned. Return the pending read error immediately.
1500 DCHECK_NE(kNoPendingResult, pending_read_error_); 1505 DCHECK_NE(kNoPendingResult, pending_read_error_);
1501 rv = pending_read_error_; 1506 rv = pending_read_error_;
1502 pending_read_error_ = kNoPendingResult; 1507 pending_read_error_ = kNoPendingResult;
1503 } 1508 }
1504 1509
1505 if (rv >= 0) { 1510 if (rv >= 0) {
1506 net_log_.AddByteTransferEvent(NetLogEventType::SSL_SOCKET_BYTES_RECEIVED, 1511 net_log_.AddByteTransferEvent(NetLogEventType::SSL_SOCKET_BYTES_RECEIVED,
1507 rv, user_read_buf_->data()); 1512 rv, buf->data());
1508 } else if (rv != ERR_IO_PENDING) { 1513 } else if (rv != ERR_IO_PENDING) {
1509 net_log_.AddEvent( 1514 net_log_.AddEvent(
1510 NetLogEventType::SSL_READ_ERROR, 1515 NetLogEventType::SSL_READ_ERROR,
1511 CreateNetLogOpenSSLErrorCallback(rv, pending_read_ssl_error_, 1516 CreateNetLogOpenSSLErrorCallback(rv, pending_read_ssl_error_,
1512 pending_read_error_info_)); 1517 pending_read_error_info_));
1513 pending_read_ssl_error_ = SSL_ERROR_NONE; 1518 pending_read_ssl_error_ = SSL_ERROR_NONE;
1514 pending_read_error_info_ = OpenSSLErrorInfo(); 1519 pending_read_error_info_ = OpenSSLErrorInfo();
1515 } 1520 }
1516 return rv; 1521 return rv;
1517 } 1522 }
(...skipping 28 matching lines...) Expand all
1546 // operation may be remembered to retry only the blocked ones.) 1551 // operation may be remembered to retry only the blocked ones.)
1547 1552
1548 if (next_handshake_state_ == STATE_HANDSHAKE) { 1553 if (next_handshake_state_ == STATE_HANDSHAKE) {
1549 // In handshake phase. The parameter to OnHandshakeIOComplete is unused. 1554 // In handshake phase. The parameter to OnHandshakeIOComplete is unused.
1550 OnHandshakeIOComplete(OK); 1555 OnHandshakeIOComplete(OK);
1551 return; 1556 return;
1552 } 1557 }
1553 1558
1554 int rv_read = ERR_IO_PENDING; 1559 int rv_read = ERR_IO_PENDING;
1555 int rv_write = ERR_IO_PENDING; 1560 int rv_write = ERR_IO_PENDING;
1556 if (user_read_buf_) 1561 if (user_read_buf_) {
1557 rv_read = DoPayloadRead(); 1562 rv_read = DoPayloadRead(user_read_buf_.get(), user_read_buf_len_);
1563 } else if (!user_read_callback_.is_null()) {
1564 // When ReadIfReady() is used, skip DoPayloadRead().
Bence 2017/03/03 16:33:41 Read() calls into ReadIfReady(), so ReadIfReady()
Bence 2017/03/03 16:33:41 I'm sorry, I do not understand how changing |rv_re
xunjieli 2017/03/03 19:41:06 Done.
xunjieli 2017/03/03 19:41:06 Done. Clarified in the comment. Hopefully it's cle
1565 rv_read = OK;
1566 }
1567
1558 if (user_write_buf_) 1568 if (user_write_buf_)
1559 rv_write = DoPayloadWrite(); 1569 rv_write = DoPayloadWrite();
1560 1570
1561 // Performing the Read callback may cause |this| to be deleted. If this 1571 // Performing the Read callback may cause |this| to be deleted. If this
1562 // happens, the Write callback should not be invoked. Guard against this by 1572 // happens, the Write callback should not be invoked. Guard against this by
1563 // holding a WeakPtr to |this| and ensuring it's still valid. 1573 // holding a WeakPtr to |this| and ensuring it's still valid.
1564 base::WeakPtr<SSLClientSocketImpl> guard(weak_factory_.GetWeakPtr()); 1574 base::WeakPtr<SSLClientSocketImpl> guard(weak_factory_.GetWeakPtr());
1565 if (rv_read != ERR_IO_PENDING) 1575 if (rv_read != ERR_IO_PENDING)
1566 DoReadCallback(rv_read); 1576 DoReadCallback(rv_read);
1567 1577
(...skipping 483 matching lines...) Expand 10 before | Expand all | Expand 10 after
2051 if (ERR_GET_REASON(info->error_code) == SSL_R_TLSV1_ALERT_ACCESS_DENIED && 2061 if (ERR_GET_REASON(info->error_code) == SSL_R_TLSV1_ALERT_ACCESS_DENIED &&
2052 !certificate_requested_) { 2062 !certificate_requested_) {
2053 net_error = ERR_SSL_PROTOCOL_ERROR; 2063 net_error = ERR_SSL_PROTOCOL_ERROR;
2054 } 2064 }
2055 } 2065 }
2056 2066
2057 return net_error; 2067 return net_error;
2058 } 2068 }
2059 2069
2060 } // namespace net 2070 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698