Skip to content

Support to offload certificate selection to different thread.#430

Merged
normanmaurer merged 2 commits intomasterfrom
ssl_task
Feb 18, 2019
Merged

Support to offload certificate selection to different thread.#430
normanmaurer merged 2 commits intomasterfrom
ssl_task

Conversation

@normanmaurer
Copy link
Copy Markdown
Member

Motiviation:

Sometimes selection of the certificate can take a long time as it may be stored on a remote system (for example). We should support to offload selection of the certificate to an other thread and be able to retry the SSL operation after it is done.

This will also allow us to support the SSLEngine abstraction of SSLEngine.getDelegatingTask() and SSLEngineResult.HandshakeStatus.NEED_TASK.

Modification:

  • Introduce SSLContest.setUseTasks(...) which allows to enable / disable the usage of tasks to offload certificate selection to an other thread.
  • Introduce SSL.getTask(...) which allows to retrieve the task that will do the certificate selection ( and also other tasks in the future )

Result:

Be able to execute long running tasks for certificate selection ( and also others in the future) without blocking the I/O thread.

@normanmaurer normanmaurer requested a review from ejona86 February 11, 2019 10:37
@normanmaurer
Copy link
Copy Markdown
Member Author

normanmaurer commented Feb 11, 2019

/cc @njhill @doom369 @johnou @slandelle

@normanmaurer normanmaurer added this to the 2.0.21.Final milestone Feb 12, 2019
Motiviation:

Sometimes selection of the certificate can take a long time as it may be stored on a remote system (for example). We should support to offload selection of the certificate to an other thread and be able to retry the SSL operation after it is done.

This will also allow us to support the SSLEngine abstraction of SSLEngine.getDelegatingTask() and SSLEngineResult.HandshakeStatus.NEED_TASK.

Modification:

- Introduce SSLContest.setUseTasks(...) which allows to enable / disable the usage of tasks to offload certificate selection to an other thread.
- Introduce SSL.getTask(...) which allows to retrieve the task that will do the certificate selection ( and also other tasks in the future )

Result:

Be able to execute long running tasks for certificate selection ( and also others in the future) without blocking the I/O thread.
if (c->use_tasks != 0) {
// Lets create the CertificateCallbackTask and store it on the SSL object. We then later retrieve it via
// SSL.getTask(ssl) and run it.
jobject task = (*e)->NewObject(e, certificateCallbackTask_class, certificateCallbackTask_init, P2J(ssl), types, issuers, c->certificate_callback);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

I think you need to check for an exception after this line.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

the constructor does not throw so I guess the only exception that could happen is a OOME.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Can you put that as a comment in CertificateCallbackTask's ctor, so it's clear it can't throw in the future too?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

done

try {
callback.handle(ssl, keyTypeBytes, asn1DerEncodedPrincipals);
return 1;
} catch (Exception e) {
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

It would be nice if this was logged at least.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

In netty we do before rethrow... we dont have any dependencies on a logging framework here. We could use java.util.logger ....

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

That's what I was implying. Else, you could just rethrow it as RuntimeException.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

@carl-mastrangelo the problem is that rethrowing here is really "useless" as we will process it as part of an openssl c callback which needs to return 0 for an error to abort the handshake.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

@carl-mastrangelo also I think we don't want to log as we rethrow it on the Netty level correctly after the SSL.doHandshake(...) method returns and so fail the handshake with an SSLHandshakeException.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

so to make it short I think it is all fine as it is... Maybe I should add some comments tho ?

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Comment is fine.

Copy link
Copy Markdown
Member

@carl-mastrangelo carl-mastrangelo left a comment

Choose a reason for hiding this comment

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

No other comments, generally LGTM

if (c->use_tasks != 0) {
// Lets create the CertificateCallbackTask and store it on the SSL object. We then later retrieve it via
// SSL.getTask(ssl) and run it.
jobject task = (*e)->NewObject(e, certificateCallbackTask_class, certificateCallbackTask_init, P2J(ssl), types, issuers, c->certificate_callback);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Can you put that as a comment in CertificateCallbackTask's ctor, so it's clear it can't throw in the future too?

// SSL.getTask(ssl) and run it.
jobject task = (*e)->NewObject(e, certificateCallbackTask_class, certificateCallbackTask_init, P2J(ssl), types, issuers, c->certificate_callback);
sslTask = (tcn_ssl_task_t*) OPENSSL_malloc(sizeof(tcn_ssl_task_t));
sslTask->task = (*e)->NewGlobalRef(e, task);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

sorry to be nitpicky, but this can fail too. Normally in Java I wouldn't care so much, but in C the risk is greater and it's much harder to debug.

try {
callback.handle(ssl, keyTypeBytes, asn1DerEncodedPrincipals);
return 1;
} catch (Exception e) {
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Comment is fine.

@normanmaurer
Copy link
Copy Markdown
Member Author

@carl-mastrangelo addressed your comments

@normanmaurer normanmaurer merged commit 11120b2 into master Feb 18, 2019
@normanmaurer normanmaurer deleted the ssl_task branch February 18, 2019 13:07
@normanmaurer normanmaurer self-assigned this Feb 18, 2019
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.

3 participants