diff --git a/src/js/cosmetic-filtering.js b/src/js/cosmetic-filtering.js index 9f738fa05..939f6314f 100644 --- a/src/js/cosmetic-filtering.js +++ b/src/js/cosmetic-filtering.js @@ -665,6 +665,7 @@ var FilterContainer = function() { }; this.userScripts = new Map(); + this.userScriptCache = new µb.MRUCache(32); // Short-lived: content is valid only during one function call. These // is to prevent repeated allocation/deallocation overheads -- the @@ -722,7 +723,9 @@ FilterContainer.prototype.reset = function() { this.scriptTagFilters = {}; this.scriptTagFilterCount = 0; + this.userScripts.clear(); + this.userScriptCache.reset(); }; /******************************************************************************/ @@ -1734,19 +1737,26 @@ FilterContainer.prototype.retrieveUserScripts = function( FilterContainer.prototype._lookupUserScript = function(raw, reng, toInject) { if ( toInject.has(raw) ) { return; } - var token, args, - pos = raw.indexOf(','); - if ( pos === -1 ) { - token = raw; - } else { - token = raw.slice(0, pos).trim(); - args = raw.slice(pos + 1).trim(); + if ( this.userScriptCache.resetTime < reng.modifyTime ) { + this.userScriptCache.reset(); } - var content = reng.resourceContentFromName(token, 'application/javascript'); - if ( !content ) { return; } - if ( args ) { - content = this._fillupUserScript(content, args); + var content = this.userScriptCache.lookup(raw); + if ( content === undefined ) { + var token, args, + pos = raw.indexOf(','); + if ( pos === -1 ) { + token = raw; + } else { + token = raw.slice(0, pos).trim(); + args = raw.slice(pos + 1).trim(); + } + content = reng.resourceContentFromName(token, 'application/javascript'); if ( !content ) { return; } + if ( args ) { + content = this._fillupUserScript(content, args); + if ( !content ) { return; } + } + this.userScriptCache.add(raw, content); } toInject.set(raw, content); }; diff --git a/src/js/redirect-engine.js b/src/js/redirect-engine.js index 70912195a..47efae2a1 100644 --- a/src/js/redirect-engine.js +++ b/src/js/redirect-engine.js @@ -1,7 +1,7 @@ /******************************************************************************* uBlock Origin - a browser extension to block requests. - Copyright (C) 2015-2016 Raymond Hill + Copyright (C) 2015-2017 Raymond Hill This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -95,6 +95,7 @@ RedirectEngine.prototype.reset = function() { this.ruleTypes = new Set(); this.ruleSources = new Set(); this.ruleDestinations = new Set(); + this.modifyTime = Date.now(); }; /******************************************************************************/ @@ -189,6 +190,7 @@ RedirectEngine.prototype.addRule = function(src, des, type, pattern, redirect) { entries = this.rules.get(key); if ( entries === undefined ) { this.rules.set(key, [ { tok: redirect, pat: pattern } ]); + this.modifyTime = Date.now(); return; } var entry; @@ -363,6 +365,7 @@ RedirectEngine.prototype.fromSelfie = function(selfie) { this.ruleTypes = new Set(selfie.ruleTypes); this.ruleSources = new Set(selfie.ruleSources); this.ruleDestinations = new Set(selfie.ruleDestinations); + this.modifyTime = Date.now(); return true; }; diff --git a/src/js/utils.js b/src/js/utils.js index fdde0d3ec..970b72fe9 100644 --- a/src/js/utils.js +++ b/src/js/utils.js @@ -351,6 +351,7 @@ this.size = size; this.array = []; this.map = new Map(); + this.resetTime = Date.now(); }; µBlock.MRUCache.prototype = { @@ -380,6 +381,7 @@ reset: function() { this.array = []; this.map.clear(); + this.resetTime = Date.now(); } };