Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow 0 byte read/write in SSL_{read,write}_ex #1316

Merged
merged 5 commits into from
Nov 27, 2023

Conversation

WillChilds-Klein
Copy link
Contributor

Issues:

Addresses CryptoAlg-2136

Description of changes:

The primary motivation of this change is to match OpenSSL's behavior for these functions. Relevant links:

Call-outs:

  • n/a

Testing:

  • CI checks

By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license and the ISC license.

@codecov-commenter
Copy link

codecov-commenter commented Nov 20, 2023

Codecov Report

All modified and coverable lines are covered by tests ✅

Comparison is base (a9f7a06) 76.43% compared to head (cec39a7) 76.38%.

Additional details and impacted files
@@            Coverage Diff             @@
##             main    #1316      +/-   ##
==========================================
- Coverage   76.43%   76.38%   -0.06%     
==========================================
  Files         421      421              
  Lines       70974    70980       +6     
==========================================
- Hits        54250    54218      -32     
- Misses      16724    16762      +38     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@WillChilds-Klein WillChilds-Klein marked this pull request as ready for review November 20, 2023 23:28
@WillChilds-Klein WillChilds-Klein requested a review from a team as a code owner November 20, 2023 23:28
@@ -1026,6 +1026,10 @@ static int ssl_read_impl(SSL *ssl) {
}

int SSL_read_ex(SSL *ssl, void *buf, size_t num, size_t *read_bytes) {
if (num == 0 && read_bytes != nullptr) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is the null pointer needed here? Should we always set read_bytes to 0 and return 1 when num == 0?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My goal here was to balance safety with compatibility. from my reading, OpenSSL won't return 1 in that case; it'll segfault. Admittedly, because of the amount of indirection via function pointers in OpenSSL's libssl, I'm not 100% confident in this reading of that code (see below).

So, if indeed my reading is correct and they segfault, I guess the expected behavior of passing null pointer here is "undefined" for OpenSSL. I thought it would be good for us to return an error in that case (as opposed to returning success) because the API's contract is for *read_bytes to be set to the number of bytes read on success. Since we can't do that with a null pointer, per the contract, returning success doesn't make sense in my opinion.


My reading of OpenSSL's relevant code:

  • SSL_read_ex calls ssl_read_internal, which in turn calls the ssl_read implementation on s->method.
  • I believe the implementation for our purposes here (i.e. not DTLS) is ssl3_write, which in turn calls an ssl_write_bytes implementation attached to s->method.
  • Presumably, that implementation is ssl3_write_bytes, which never checks the written pointer before dereferencing in the case when 0 bytes have been requested to be written (and 0 bytes have been written, i.e. len == tot == 0 in the code).

Side note -- somebody summed up the whole situation pretty well in an internal comment:

/*
 * This is for the SSLv3/TLSv1.0 differences in crypto/hash stuff It is a bit
 * of a mess of functions, but hell, think of it as an opaque structure :-)
 */

ssl/ssl_test.cc Outdated Show resolved Hide resolved
include/openssl/ssl.h Outdated Show resolved Hide resolved
include/openssl/ssl.h Outdated Show resolved Hide resolved
WillChilds-Klein and others added 5 commits November 22, 2023 16:31
The primary motivation of this change is to match OpenSSL's behavior for
these functions. Relevant links:

- [SSL_read_ex docs][1]
- [SSL_write_ex docs][2]
- [CPython update accounting for this behavior][3]

[1]: https://www.openssl.org/docs/man1.1.1/man3/SSL_read_ex.html
[2]: https://www.openssl.org/docs/man1.1.1/man3/SSL_write_ex.html
[3]: python/cpython#75892 (comment)
Co-authored-by: Samuel Chiang <samuelchungchiang@gmail.com>
Co-authored-by: Samuel Chiang <samuelchungchiang@gmail.com>
@WillChilds-Klein WillChilds-Klein enabled auto-merge (squash) November 22, 2023 17:01
@WillChilds-Klein WillChilds-Klein merged commit 89e1fd0 into aws:main Nov 27, 2023
20 checks passed
@WillChilds-Klein WillChilds-Klein deleted the libssl-allow-0-byte-io branch November 27, 2023 17:32
WillChilds-Klein added a commit to WillChilds-Klein/aws-lc that referenced this pull request Nov 30, 2023
WillChilds-Klein added a commit to WillChilds-Klein/aws-lc that referenced this pull request Dec 4, 2023
@justsmth justsmth mentioned this pull request Dec 4, 2023
WillChilds-Klein added a commit to WillChilds-Klein/aws-lc that referenced this pull request Dec 14, 2023
WillChilds-Klein added a commit to WillChilds-Klein/aws-lc that referenced this pull request Dec 15, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants