From c9a8da65fe45378e05337c590c12517efc62ef8a Mon Sep 17 00:00:00 2001 From: Mark Donnelly Date: Fri, 31 Jul 2015 15:24:17 -0400 Subject: [PATCH] Ensure init_sec_context endpoint is the document host. * Hook calls to import_name and remember the hostname associated with the result * Check on calls to init_sec_context that the hostname for the supplied target handle --- browsers/common/contentscript.js | 91 +++++++++++++++++++++++++++++++++++----- 1 file changed, 81 insertions(+), 10 deletions(-) diff --git a/browsers/common/contentscript.js b/browsers/common/contentscript.js index b425ad3..a786197 100644 --- a/browsers/common/contentscript.js +++ b/browsers/common/contentscript.js @@ -31,8 +31,6 @@ * OF THE POSSIBILITY OF SUCH DAMAGE. * */ -console.log("Loading content script #6..."); - function addScript(url) { var elt = document.createElement("script"); elt.setAttribute("src", @@ -42,6 +40,8 @@ function addScript(url) { var port; var browser; +var gssHostNames = {}; +var pendingGssHostNames = {}; if ("undefined" != typeof(chrome) && "undefined" != typeof(chrome.extension) && @@ -60,14 +60,36 @@ if ("undefined" != typeof(chrome) && addScript( gss_script_name ); sendReplyToWebpage = function(gssReplyJSON) { - var appTag = gssReplyJSON.cookies.app_tag; - - console.log("[" + appTag + "] Extension port listener received message: [" + - JSON.stringify(gssReplyJSON) + "]" - ); - window.postMessage(gssReplyJSON, "*"); + var appTag = gssReplyJSON.cookies.app_tag; + var csTag = gssReplyJSON.cookies.cs_tag; + + gssReplyJSON.cookies.cs_tag = undefined; + + /* Save off the hostnames of any reply to GSSImportName if: + * + There is a csTag + * + The invoked method was 'gss_import_name' + * + The method completed successfully + * + There is a hostname wating in the pendingGssHostNames hash + * indexed by csTag + */ + if ( typeof(csTag) != 'undefined' && + gssReplyJSON.method == 'gss_import_name' && + typeof(gssReplyJSON.return_values) != 'undefined' && + gssReplyJSON.return_values.major_status == '0' && + typeof(pendingGssHostNames[csTag]) != 'undefined' ) + { + gssHostNames[gssReplyJSON.return_values.gss_name] = + pendingGssHostNames[csTag]; + delete pendingGssHostNames[csTag]; } + console.log("[" + appTag + + "] Extension port listener received message: [" + + JSON.stringify(gssReplyJSON) + "]" + ); + window.postMessage(gssReplyJSON, "*"); +} + /* When we get a message back from the extension * background script @@ -94,9 +116,58 @@ window.addEventListener("message", function(event) { } var appTag = event.data.cookies.app_tag; - console.log("[" + appTag + "] Window message listener received message: [" + + console.log("[" + appTag + + "] Window message listener received message: [" + JSON.stringify(event.data) + "]" - ); + ); + + /* + * Deny calls to init_sec_context where we don't know that the + * target has the same hostname as the origin. + */ + if(event.data.method == "gss_init_sec_context" && + typeof(event.data.arguments) != 'undefined' && + gssHostNames[event.data.arguments.target_name] != + document.location.hostname) + { + console.log("[" + appTag + "] Window message listener received " + + "gss_init_sec_context, but the hostname in the " + + "target_name could not be found to match the document " + + "location hostname."); + sendReplyToWebpage({ + 'method':'gss_init_sec_context', + 'return_values': { + 'major_status': -2, + 'minor_status': -1, + 'major_status_message': 'The GSS call cannot be completed', + 'minor_status_message': 'init_sec_context requires a target ' + + 'that matches your page origin.' + }, + 'cookies': event.data.cookies; + }); + return; + } + + /* Add a content script tag, csTag */ + var csTag = navigator.generateNonce(); + event.data.cookies.cs_tag = csTag; + + /* Save out the hostname from calls to import_name with an + * NT hostbased name + */ + if(event.data.method == 'gss_import_name') + { + if( typeof(event.data.arguments) != 'undefined' && + ( event.data.arguments.input_name_type == + "{1 2 840 113554 1 2 1 4 }" || + event.data.arguments.input_name_type == + "1.2.840.113554.1.2.1.4" ) ) + { + var hostname = /[^@]*$/.exec(event.data.arguments.input_name)[0]; + pendingGssHostNames[csTag] = hostname; + } + } + if ("Chrome" == browser) { port.postMessage(event.data); -- 2.1.4