Skip to content

Commit 01d7155

Browse files
author
Matthew Sackman
committed
merge bug 22089 into default
2 parents 3a1b632 + 55f6902 commit 01d7155

File tree

4 files changed

+86
-126
lines changed

4 files changed

+86
-126
lines changed

projects/client/RabbitMQ.Client/src/client/api/SslHelper.cs

Lines changed: 26 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -71,11 +71,13 @@ namespace RabbitMQ.Client
7171
public class SslHelper
7272
{
7373

74-
static X509Certificate CertificateSelectionCallback(object sender,
75-
string targetHost,
76-
X509CertificateCollection localCertificates,
77-
X509Certificate remoteCertificate,
78-
string[] acceptableIssuers)
74+
private SslOption m_sslOption;
75+
76+
private X509Certificate CertificateSelectionCallback(object sender,
77+
string targetHost,
78+
X509CertificateCollection localCertificates,
79+
X509Certificate remoteCertificate,
80+
string[] acceptableIssuers)
7981
{
8082
if (acceptableIssuers != null && acceptableIssuers.Length > 0 &&
8183
localCertificates != null && localCertificates.Count > 0)
@@ -92,21 +94,35 @@ static X509Certificate CertificateSelectionCallback(object sender,
9294
return null;
9395
}
9496

97+
private bool CertificateValidationCallback(object sender,
98+
X509Certificate certificate,
99+
X509Chain chain,
100+
SslPolicyErrors sslPolicyErrors)
101+
{
102+
return (sslPolicyErrors & ~m_sslOption.AcceptablePolicyErrors) == SslPolicyErrors.None;
103+
}
104+
95105
///<summary>Upgrade a Tcp stream to an Ssl stream using the SSL options
96106
///provided</summary>
97107
public static Stream TcpUpgrade(Stream tcpStream, SslOption sslOption)
98108
{
109+
SslHelper helper = new SslHelper(sslOption);
99110
SslStream sslStream = new SslStream(tcpStream, false,
100-
null,
101-
new LocalCertificateSelectionCallback(CertificateSelectionCallback));
111+
new RemoteCertificateValidationCallback(helper.CertificateValidationCallback),
112+
new LocalCertificateSelectionCallback(helper.CertificateSelectionCallback));
102113

103114
sslStream.AuthenticateAsClient(sslOption.ServerName,
104-
sslOption.Certs,
105-
sslOption.Version,
106-
false);
115+
sslOption.Certs,
116+
sslOption.Version,
117+
false);
107118

108119
return sslStream;
109120
}
110121

122+
private SslHelper(SslOption sslOption)
123+
{
124+
m_sslOption = sslOption;
125+
}
126+
111127
}
112128
}

projects/client/RabbitMQ.Client/src/client/api/SslOption.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@
5656
//---------------------------------------------------------------------------
5757
using System;
5858
using System.Collections;
59+
using System.Net.Security;
5960
using System.Security.Authentication;
6061
using System.Security.Cryptography.X509Certificates;
6162
using RabbitMQ.Client.Impl;
@@ -134,6 +135,15 @@ public string ServerName
134135
set { m_serverName = value; }
135136
}
136137

138+
private SslPolicyErrors m_acceptablePolicyErrors = SslPolicyErrors.None;
139+
140+
///<summary>Retrieve or set the set of ssl policy errors that
141+
///are deemed acceptable</summary>
142+
public SslPolicyErrors AcceptablePolicyErrors
143+
{
144+
get { return m_acceptablePolicyErrors; }
145+
set { m_acceptablePolicyErrors = value; }
146+
}
137147

138148

139149
///<summary>Construct an SslOption specifying both the server cannonical name

projects/client/Unit/src/unit/TestSslEndpointUnverified.cs renamed to projects/client/Unit/src/unit/TestSsl.cs

Lines changed: 50 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -56,51 +56,70 @@
5656
//---------------------------------------------------------------------------
5757
using NUnit.Framework;
5858
using System;
59+
using System.Net.Security;
5960
using RabbitMQ.Client;
6061

6162
[TestFixture]
62-
public class TestSslEndpointUnverified {
63+
public class TestSsl {
6364

64-
public void SendReceive(IConnection conn) {
65-
string message = "Hello C# SSL Client World";
65+
public void SendReceive(ConnectionFactory cf) {
66+
IProtocol proto = Protocols.DefaultProtocol;
67+
using (IConnection conn = cf.CreateConnection(proto, "localhost", 5671)) {
68+
IModel ch = conn.CreateModel();
69+
70+
ch.ExchangeDeclare("Exchange_TestSslEndPoint", ExchangeType.Direct);
71+
ch.QueueDeclare("Queue_TestSslEndpoint");
72+
ch.QueueBind("Queue_TestSslEndpoint", "Exchange_TestSslEndPoint", "Key_TestSslEndpoint", false, null);
73+
74+
string message = "Hello C# SSL Client World";
75+
byte[] msgBytes = System.Text.Encoding.UTF8.GetBytes(message);
76+
ch.BasicPublish("Exchange_TestSslEndPoint", "Key_TestSslEndpoint", null, msgBytes);
6677

67-
IModel ch = conn.CreateModel();
78+
bool noAck = false;
79+
BasicGetResult result = ch.BasicGet("Queue_TestSslEndpoint", noAck);
80+
byte[] body = result.Body;
81+
string resultMessage = System.Text.Encoding.UTF8.GetString(body);
6882

69-
ch.ExchangeDeclare("Exchange_TestSslEndPoint", ExchangeType.Direct);
70-
ch.QueueDeclare("Queue_TestSslEndpoint");
71-
ch.QueueBind("Queue_TestSslEndpoint", "Exchange_TestSslEndPoint", "Key_TestSslEndpoint", false, null);
72-
73-
byte[] msgBytes = System.Text.Encoding.UTF8.GetBytes(message);
74-
ch.BasicPublish("Exchange_TestSslEndPoint", "Key_TestSslEndpoint", null, msgBytes);
75-
76-
bool noAck = false;
83+
Assert.AreEqual(message, resultMessage);
84+
}
85+
}
7786

78-
BasicGetResult result = ch.BasicGet("Queue_TestSslEndpoint", noAck);
79-
byte[] body = result.Body;
87+
[Test]
88+
public void TestServerVerifiedIgnoringNameMismatch() {
89+
string sslDir = Environment.GetEnvironmentVariable("SSL_CERTS_DIR");
90+
if (null == sslDir) return;
8091

81-
string resultMessage = System.Text.Encoding.UTF8.GetString(body);
92+
ConnectionFactory cf = new ConnectionFactory();
93+
cf.Parameters.Ssl.ServerName = "*";
94+
cf.Parameters.Ssl.AcceptablePolicyErrors = SslPolicyErrors.RemoteCertificateNameMismatch;
95+
cf.Parameters.Ssl.Enabled = true;
96+
SendReceive(cf);
97+
}
8298

83-
ch.Close(200, "Closing the channel");
84-
conn.Close();
99+
[Test]
100+
public void TestServerVerified() {
101+
string sslDir = Environment.GetEnvironmentVariable("SSL_CERTS_DIR");
102+
if (null == sslDir) return;
85103

86-
Assert.AreEqual(message, resultMessage);
104+
ConnectionFactory cf = new ConnectionFactory();
105+
cf.Parameters.Ssl.ServerName = System.Net.Dns.GetHostName();
106+
cf.Parameters.Ssl.Enabled = true;
107+
SendReceive(cf);
87108
}
88109

89-
90110
[Test]
91-
public virtual void TestHostWithPort() {
111+
public void TestClientAndServerVerified() {
92112
string sslDir = Environment.GetEnvironmentVariable("SSL_CERTS_DIR");
93-
if (null == sslDir) {
94-
return;
95-
} else {
96-
ConnectionFactory cf = new ConnectionFactory();
97-
98-
cf.Parameters.Ssl.ServerName = System.Net.Dns.GetHostName();
99-
cf.Parameters.Ssl.Enabled = true;
113+
if (null == sslDir) return;
100114

101-
IProtocol proto = Protocols.DefaultProtocol;
102-
IConnection conn = cf.CreateConnection(proto, "localhost", 5671);
103-
SendReceive(conn);
104-
}
115+
ConnectionFactory cf = new ConnectionFactory();
116+
cf.Parameters.Ssl.ServerName = System.Net.Dns.GetHostName();
117+
Assert.IsNotNull(sslDir);
118+
cf.Parameters.Ssl.CertPath = sslDir + "/client/keycert.p12";
119+
string p12Password = Environment.GetEnvironmentVariable("PASSWORD");
120+
Assert.IsNotNull(p12Password, "missing PASSWORD env var");
121+
cf.Parameters.Ssl.CertPassphrase = p12Password;
122+
cf.Parameters.Ssl.Enabled = true;
123+
SendReceive(cf);
105124
}
106125
}

projects/client/Unit/src/unit/TestSslEndpointVerified.cs

Lines changed: 0 additions & 85 deletions
This file was deleted.

0 commit comments

Comments
 (0)