Bug 1103120 - Part 15: Client: Compare server cert to advertisement. r=past

This commit is contained in:
J. Ryan Stinnett 2015-01-26 12:47:13 -06:00
Родитель c627aeda11
Коммит 3c721a669a
2 изменённых файлов: 82 добавлений и 6 удалений

Просмотреть файл

@ -9,6 +9,8 @@
let { Ci, Cc } = require("chrome");
let Services = require("Services");
let promise = require("promise");
let DevToolsUtils = require("devtools/toolkit/DevToolsUtils");
let { dumpn, dumpv } = DevToolsUtils;
loader.lazyRequireGetter(this, "prompt",
"devtools/toolkit/security/prompt");
loader.lazyRequireGetter(this, "cert",
@ -91,6 +93,27 @@ Prompt.Client.prototype = {
mode: Prompt.mode,
/**
* When client has just made a new socket connection, validate the connection
* to ensure it meets the authenticator's policies.
*
* @param host string
* The host name or IP address of the debugger server.
* @param port number
* The port number of the debugger server.
* @param encryption boolean (optional)
* Whether the server requires encryption. Defaults to false.
* @param cert object (optional)
* The server's cert details.
* @param s nsISocketTransport
* Underlying socket transport, in case more details are needed.
* @return boolean
* Whether the connection is valid.
*/
validateConnection() {
return true;
},
/**
* Work with the server to complete any additional steps required by this
* authenticator's policies.
@ -233,6 +256,38 @@ OOBCert.Client.prototype = {
mode: OOBCert.mode,
/**
* When client has just made a new socket connection, validate the connection
* to ensure it meets the authenticator's policies.
*
* @param host string
* The host name or IP address of the debugger server.
* @param port number
* The port number of the debugger server.
* @param encryption boolean (optional)
* Whether the server requires encryption. Defaults to false.
* @param cert object (optional)
* The server's cert details.
* @param socket nsISocketTransport
* Underlying socket transport, in case more details are needed.
* @return boolean
* Whether the connection is valid.
*/
validateConnection({ cert, socket }) {
// Step B.7
// Client verifies that Server's cert matches hash(ServerCert) from the
// advertisement
dumpv("Validate server cert hash");
let serverCert = socket.securityInfo.QueryInterface(Ci.nsISSLStatusProvider)
.SSLStatus.serverCert;
let advertisedCert = cert;
if (serverCert.sha256Fingerprint != advertisedCert.sha256) {
dumpn("Server cert hash doesn't match advertisement");
return false;
}
return true;
},
/**
* Work with the server to complete any additional steps required by this
* authenticator's policies.

Просмотреть файл

@ -72,12 +72,12 @@ let DebuggerSocket = {};
* Resolved to a DebuggerTransport instance.
*/
DebuggerSocket.connect = Task.async(function*(settings) {
// Default to PROMPT |Authenticator| instance if not supplied
if (!settings.authenticator) {
settings.authenticator = new (Authenticators.get().Client)();
}
let { host, port, encryption, authenticator, cert } = settings;
let transport = yield _getTransport(settings);
// Default to PROMPT |Authenticator| instance if not supplied
authenticator = authenticator || new (Authenticators.get().Client)();
yield authenticator.authenticate({
host,
port,
@ -98,6 +98,11 @@ DebuggerSocket.connect = Task.async(function*(settings) {
* The port number of the debugger server.
* @param encryption boolean (optional)
* Whether the server requires encryption. Defaults to false.
* @param authenticator Authenticator
* |Authenticator| instance matching the mode in use by the server.
* Defaults to a PROMPT instance if not supplied.
* @param cert object (optional)
* The server's cert details. Used with OOB_CERT authentication.
* @return transport DebuggerTransport
* A possible DevTools transport (if connection succeeded and streams
* are actually alive and working)
@ -141,6 +146,11 @@ let _getTransport = Task.async(function*(settings) {
* The port number of the debugger server.
* @param encryption boolean (optional)
* Whether the server requires encryption. Defaults to false.
* @param authenticator Authenticator
* |Authenticator| instance matching the mode in use by the server.
* Defaults to a PROMPT instance if not supplied.
* @param cert object (optional)
* The server's cert details. Used with OOB_CERT authentication.
* @return transport DebuggerTransport
* A possible DevTools transport (if connection succeeded and streams
* are actually alive and working)
@ -149,16 +159,27 @@ let _getTransport = Task.async(function*(settings) {
* @return s nsISocketTransport
* Underlying socket transport, in case more details are needed.
*/
let _attemptTransport = Task.async(function*({ host, port, encryption }) {
let _attemptTransport = Task.async(function*(settings) {
let { authenticator } = settings;
// _attemptConnect only opens the streams. Any failures at that stage
// aborts the connection process immedidately.
let { s, input, output } = yield _attemptConnect({ host, port, encryption });
let { s, input, output } = yield _attemptConnect(settings);
// Check if the input stream is alive. If encryption is enabled, we need to
// watch out for cert errors by testing the input stream.
let { alive, certError } = yield _isInputAlive(input);
dumpv("Server cert accepted? " + !certError);
// The |Authenticator| examines the connection as well and may determine it
// should be dropped.
alive = alive && authenticator.validateConnection({
host: settings.host,
port: settings.port,
encryption: settings.encryption,
cert: settings.cert,
socket: s
});
let transport;
if (alive) {
transport = new DebuggerTransport(input, output);