diff --git a/platform/firefox/vapi-background.js b/platform/firefox/vapi-background.js index e061e227a..d6817b21e 100644 --- a/platform/firefox/vapi-background.js +++ b/platform/firefox/vapi-background.js @@ -2173,7 +2173,7 @@ vAPI.onLoadAllCompleted = function() { var tabId = this.tabs.getTabId(tab); var browser = getBrowserForTab(tab); - µb.tabContextManager.commit(tabId, browser.currentURI.asciiSpec); + µb.tabContextManager.commit(tabId); µb.bindTabToPageStats(tabId, browser.currentURI.asciiSpec); browser.messageManager.sendAsyncMessage( location.host + '-load-completed' diff --git a/src/js/background.js b/src/js/background.js index 7e9e900c6..0638be3c3 100644 --- a/src/js/background.js +++ b/src/js/background.js @@ -88,7 +88,7 @@ return { // read-only systemSettings: { - compiledMagic: 'akjbdyreyxgm', + compiledMagic: 'eopszukpnrct', selfieMagic: 'spqmeuaftfra' }, diff --git a/src/js/tab.js b/src/js/tab.js index 26c90038b..1dda0a6c5 100644 --- a/src/js/tab.js +++ b/src/js/tab.js @@ -209,6 +209,10 @@ housekeep itself. if ( vAPI.isBehindTheSceneTabId(this.tabId) ) { return; } + var count = this.stack.length; + if ( count !== 0 && this.stack[count - 1] === url ) { + return; + } this.stack.push(url); this.update(); }; diff --git a/src/js/traffic.js b/src/js/traffic.js index e38d49bde..41db50732 100644 --- a/src/js/traffic.js +++ b/src/js/traffic.js @@ -287,6 +287,9 @@ var onHeadersReceived = function(details) { return { 'responseHeaders': details.responseHeaders }; }; + +/******************************************************************************/ + var onRootFrameHeadersReceived = function(details) { var tabId = details.tabId; var requestURL = details.url; @@ -297,6 +300,8 @@ var onRootFrameHeadersReceived = function(details) { // ... if ( headerValue(details.responseHeaders, 'content-disposition').lastIndexOf('attachment', 0) === 0 ) { µb.tabContextManager.unpush(tabId, requestURL); + } else { + µb.tabContextManager.push(tabId, requestURL); } // Lookup the page store associated with this tab id. @@ -304,7 +309,6 @@ var onRootFrameHeadersReceived = function(details) { if ( !pageStore ) { pageStore = µb.bindTabToPageStats(tabId, 'beforeRequest'); } - // I can't think of how pageStore could be null at this point. var context = pageStore.createContextFromPage(); context.requestURL = requestURL + '{inline-script}'; diff --git a/src/js/uritools.js b/src/js/uritools.js index fe905f301..971c0c4b3 100644 --- a/src/js/uritools.js +++ b/src/js/uritools.js @@ -72,10 +72,10 @@ var reIPAddressNaive = /^\d+\.\d+\.\d+\.\d+$|^\[[\da-zA-Z:]+\]$/; // Accurate tests // Source.: http://stackoverflow.com/questions/5284147/validating-ipv4-addresses-with-regexp/5284410#5284410 -var reIPv4 = /^((25[0-5]|2[0-4]\d|[01]?\d\d?)(\.|$)){4}/; +//var reIPv4 = /^((25[0-5]|2[0-4]\d|[01]?\d\d?)(\.|$)){4}/; // Source: http://forums.intermapper.com/viewtopic.php?p=1096#1096 -var reIPv6 = /^\s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:)))(%.+)?\s*$/; +//var reIPv6 = /^\s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:)))(%.+)?\s*$/; /******************************************************************************/ @@ -366,11 +366,18 @@ var domainCachePrune = function() { } }; +var domainCacheReset = function() { + domainCache = {}; + domainCacheCount = 0; +}; + var domainCache = {}; var domainCacheCount = 0; var domainCacheCountLowWaterMark = 75; var domainCacheCountHighWaterMark = 100; +psl.onChanged.addListener(domainCacheReset); + /******************************************************************************/ URI.domainFromURI = function(uri) { diff --git a/src/lib/publicsuffixlist.js b/src/lib/publicsuffixlist.js index fa1803704..89749867c 100644 --- a/src/lib/publicsuffixlist.js +++ b/src/lib/publicsuffixlist.js @@ -33,6 +33,8 @@ ;(function(root) { +'use strict'; + /******************************************************************************/ var exceptions = {}; @@ -45,6 +47,8 @@ var selfieMagic = 'iscjsfsaolnm'; var cutoffLength = 256; var mustPunycode = /[^a-z0-9.-]/; +var onChangedListeners = []; + /******************************************************************************/ // In the context of this code, a domain is defined as: @@ -234,6 +238,7 @@ function parse(text, toAscii) { } crystallize(exceptions); crystallize(rules); + callListeners(onChangedListeners); } /******************************************************************************/ @@ -302,11 +307,47 @@ function fromSelfie(selfie) { } rules = selfie.rules; exceptions = selfie.exceptions; + callListeners(onChangedListeners); return true; } /******************************************************************************/ +var addListener = function(listeners, callback) { + if ( typeof callback !== 'function' ) { + return; + } + if ( listeners.indexOf(callback) === -1 ) { + listeners.push(callback); + } +}; + +var removeListener = function(listeners, callback) { + var pos = listeners.indexOf(callback); + if ( pos !== -1 ) { + listeners.splice(pos, 1); + } +}; + +var callListeners = function(listeners) { + for ( var i = 0; i < listeners.length; i++ ) { + listeners[i](); + } +}; + +/******************************************************************************/ + +var onChanged = { + addListener: function(callback) { + addListener(onChangedListeners, callback); + }, + removeListener: function(callback) { + removeListener(onChangedListeners, callback); + } +}; + +/******************************************************************************/ + // Public API root = root || window; @@ -317,7 +358,8 @@ root.publicSuffixList = { 'getDomain': getDomain, 'getPublicSuffix': getPublicSuffix, 'toSelfie': toSelfie, - 'fromSelfie': fromSelfie + 'fromSelfie': fromSelfie, + 'onChanged': onChanged }; /******************************************************************************/