Skip to content

Commit a6dd8f0

Browse files
committed
wrap useClientSuites() in WolfSSLSession, modify logic in WolfSSLEngineHelper
1 parent 1307631 commit a6dd8f0

5 files changed

Lines changed: 147 additions & 7 deletions

File tree

native/com_wolfssl_WolfSSLSession.c

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5874,6 +5874,23 @@ JNIEXPORT jint JNICALL Java_com_wolfssl_WolfSSLSession_hasTicket
58745874
#endif
58755875
}
58765876

5877+
JNIEXPORT jint JNICALL Java_com_wolfssl_WolfSSLSession_useClientSuites
5878+
(JNIEnv* jenv, jobject jcl, jlong sslPtr)
5879+
{
5880+
(void)jcl;
5881+
#if !defined(NO_WOLFSSL_CLIENT)
5882+
WOLFSSL* ssl = (WOLFSSL*)(uintptr_t)sslPtr;
5883+
if (jenv == NULL || ssl == NULL) {
5884+
return WOLFSSL_FAILURE;
5885+
}
5886+
return (jint)wolfSSL_UseClientSuites(ssl);
5887+
#else
5888+
(void)jenv;
5889+
(void)sslPtr;
5890+
return (jint)NOT_COMPILED_IN;
5891+
#endif
5892+
}
5893+
58775894
JNIEXPORT jint JNICALL Java_com_wolfssl_WolfSSLSession_interruptBlockedIO
58785895
(JNIEnv* jenv, jobject jcl, jlong sslPtr)
58795896
{

native/com_wolfssl_WolfSSLSession.h

Lines changed: 8 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/java/com/wolfssl/WolfSSLSession.java

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -693,6 +693,7 @@ private native int setTlsHmacInner(long ssl, byte[] inner, long sz,
693693
private native int useSupportedCurve(long ssl, int name);
694694
private native int disableExtendedMasterSecret(long ssl);
695695
private native int hasTicket(long session);
696+
private native int useClientSuites(long ssl);
696697
private native int interruptBlockedIO(long ssl);
697698
private native int getThreadsBlockedInPoll(long ssl);
698699
private native int setMTU(long ssl, int mtu);
@@ -2476,6 +2477,28 @@ public long getTimeout() throws IllegalStateException {
24762477
}
24772478
}
24782479

2480+
/**
2481+
*
2482+
* Set SSL session to use Client cipher suite order preference.
2483+
*
2484+
* @return <code>SSL_SUCCESS</code> upon success. <code>
2485+
* SSL_FAILURE</code> upon failure.
2486+
* @throws IllegalStateException WolfSSLSession has been freed
2487+
*
2488+
*/
2489+
public int useClientSuites() throws IllegalStateException {
2490+
2491+
confirmObjectIsActive();
2492+
2493+
synchronized (sslLock) {
2494+
WolfSSLDebug.log(getClass(), WolfSSLDebug.Component.JNI,
2495+
WolfSSLDebug.INFO, this.sslPtr,
2496+
() -> "entered useClientSuites()");
2497+
2498+
return useClientSuites(this.sslPtr);
2499+
}
2500+
}
2501+
24792502
/**
24802503
* Sets the cipher suite list for a given SSL session.
24812504
* The ciphers in the list should be sorted in order of preference from

src/java/com/wolfssl/provider/jsse/WolfSSLEngineHelper.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -759,6 +759,11 @@ private void setLocalCiphers(String[] suites)
759759
}
760760
}
761761

762+
if (this.ssl.getSide() == WolfSSL.WOLFSSL_SERVER_END &&
763+
!this.params.getUseCipherSuitesOrder()) {
764+
this.ssl.useClientSuites();
765+
}
766+
762767
} catch (IllegalStateException e) {
763768
throw new IllegalArgumentException(e);
764769
}

src/test/com/wolfssl/provider/jsse/test/WolfSSLSocketTest.java

Lines changed: 94 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -321,6 +321,93 @@ public void testGetSetEnabledCipherSuites()
321321
System.out.println("\t... passed");
322322
}
323323

324+
@Test
325+
public void testServerUsesClientCipherSuitePreference() throws Exception {
326+
327+
System.out.print("\tTesting client suite preference");
328+
329+
this.ctx = tf.createSSLContext("TLS", "wolfJSSE");
330+
331+
String[] serverSuites = {
332+
"TLS_AES_256_GCM_SHA384",
333+
"TLS_AES_128_GCM_SHA256"
334+
};
335+
336+
String[] clientSuites = {
337+
"TLS_AES_128_GCM_SHA256",
338+
"TLS_AES_256_GCM_SHA384"
339+
};
340+
341+
/* --- Case 1: default (server order) --- */
342+
SSLServerSocket ss1 = (SSLServerSocket)ctx.getServerSocketFactory()
343+
.createServerSocket(0);
344+
ss1.setEnabledCipherSuites(serverSuites);
345+
346+
SSLSocket cs1 = (SSLSocket)ctx.getSocketFactory().createSocket();
347+
cs1.setEnabledCipherSuites(clientSuites);
348+
cs1.connect(new InetSocketAddress(ss1.getLocalPort()));
349+
350+
final SSLSocket server1 = (SSLSocket)ss1.accept();
351+
352+
ExecutorService es = Executors.newSingleThreadExecutor();
353+
Future<Void> f1 = es.submit(() -> {
354+
server1.startHandshake();
355+
return null;
356+
});
357+
358+
cs1.startHandshake();
359+
f1.get();
360+
361+
String chosen1 = cs1.getSession().getCipherSuite();
362+
if (!"TLS_AES_256_GCM_SHA384".equals(chosen1)) {
363+
System.out.println("\t... failed");
364+
fail("Expected server preference cipher (AES_256), got "
365+
+ chosen1);
366+
}
367+
368+
cs1.close();
369+
server1.close();
370+
ss1.close();
371+
372+
/* --- Case 2: server honors client order --- */
373+
SSLServerSocket ss2 = (SSLServerSocket)ctx.getServerSocketFactory()
374+
.createServerSocket(0);
375+
ss2.setEnabledCipherSuites(serverSuites);
376+
377+
/* Do not honor local cipher suites preference */
378+
SSLParameters ss2Params = ss2.getSSLParameters();
379+
ss2Params.setUseCipherSuitesOrder(false);
380+
ss2.setSSLParameters(ss2Params);
381+
382+
SSLSocket cs2 = (SSLSocket)ctx.getSocketFactory().createSocket();
383+
cs2.setEnabledCipherSuites(clientSuites);
384+
cs2.connect(new InetSocketAddress(ss2.getLocalPort()));
385+
386+
final SSLSocket server2 = (SSLSocket)ss2.accept();
387+
388+
Future<Void> f2 = es.submit(() -> {
389+
server2.startHandshake();
390+
return null;
391+
});
392+
393+
cs2.startHandshake();
394+
f2.get();
395+
396+
String chosen2 = cs2.getSession().getCipherSuite();
397+
if (!"TLS_AES_128_GCM_SHA256".equals(chosen2)) {
398+
System.out.println("\t... failed");
399+
fail("Expected client preference cipher (AES_128), got "
400+
+ chosen2);
401+
}
402+
403+
cs2.close();
404+
server2.close();
405+
ss2.close();
406+
es.shutdown();
407+
408+
System.out.println("\t... passed");
409+
}
410+
324411
@Test
325412
public void testGetSupportedProtocols()
326413
throws NoSuchProviderException, NoSuchAlgorithmException {
@@ -3402,14 +3489,14 @@ public void testAutoSNIProperty() throws Exception {
34023489
public void testSNIMatchers() throws Exception {
34033490

34043491
System.out.print("\tTesting SNI Matchers");
3405-
3492+
34063493
/* create new CTX */
34073494
this.ctx = tf.createSSLContext("TLS", ctxProvider);
3408-
3495+
34093496
/* create SSLServerSocket first to get ephemeral port */
34103497
final SSLServerSocket ss = (SSLServerSocket)ctx.getServerSocketFactory()
34113498
.createServerSocket(0);
3412-
3499+
34133500
/* Configure SNI matcher for server*/
34143501
SNIMatcher matcher = SNIHostName.createSNIMatcher("www\\.example\\.com");
34153502
Collection<SNIMatcher> matchers = new ArrayList<>();
@@ -3436,7 +3523,7 @@ public void testSNIMatchers() throws Exception {
34363523
cs.setSSLParameters(cp);
34373524

34383525
final SSLSocket serverMatched = (SSLSocket)ss.accept();
3439-
3526+
34403527
ExecutorService es = Executors.newSingleThreadExecutor();
34413528
Future<Void> serverFuture = es.submit(new Callable<Void>() {
34423529
@Override
@@ -3451,10 +3538,10 @@ public Void call() throws Exception {
34513538
return null;
34523539
}
34533540
});
3454-
3541+
34553542
cs.startHandshake();
34563543
cs.close();
3457-
3544+
34583545
es.shutdown();
34593546
serverFuture.get();
34603547

@@ -3473,7 +3560,7 @@ public Void call() throws Exception {
34733560
cs.setSSLParameters(cp);
34743561

34753562
final SSLSocket serverUnmatched = (SSLSocket)ss.accept();
3476-
3563+
34773564
es = Executors.newSingleThreadExecutor();
34783565
serverFuture = es.submit(() -> {
34793566
try {

0 commit comments

Comments
 (0)