Skip to content

Commit

Permalink
Reduce memory usage in staticExtFilteringEngine.HostnameBasedDB
Browse files Browse the repository at this point in the history
Using pairs of integers allows the use of a
single integer-only array to store lists of
string indices associated to a specific
hostname.

Memory usage of instances of HostnameBasedDB
as per Chromium's heap snaphshot (bytes):

Before:
    2,459,256 => specific cosmetic filters
      944,152 => scriptlet filtering
          736
    ---------
    3,404,144

After:
    1,947,448 => "
      757,936 => "
          632
    ---------
    2,706,016

Ultimately, using 2 integers for each entry
instead of a single one is still worth it
because this allows the use of one single
integer-only array instead of having to use
an array of arrays for hostnames which have
multiple entries.
  • Loading branch information
gorhill committed Sep 28, 2019
1 parent 4bf6503 commit e94024d
Showing 1 changed file with 15 additions and 28 deletions.
43 changes: 15 additions & 28 deletions src/js/static-ext-filtering.js
Original file line number Diff line number Diff line change
Expand Up @@ -516,10 +516,8 @@
this.timer = undefined;
this.strToIdMap = new Map();
this.hostnameToSlotIdMap = new Map();
// Avoid heterogeneous arrays. Thus:
this.hostnameSlots = []; // array of integers
// IMPORTANT: initialize with an empty array because -0 is NOT < 0.
this.hostnameSlotsEx = [ [] ]; // array of arrays of integers
// Array of integer pairs
this.hostnameSlots = [];
// Array of strings (selectors and pseudo-selectors)
this.strSlots = [];
this.size = 0;
Expand All @@ -540,26 +538,23 @@
}
}
const strId = iStr << this.nBits | bits;
const iHn = this.hostnameToSlotIdMap.get(hn);
let iHn = this.hostnameToSlotIdMap.get(hn);
if ( iHn === undefined ) {
this.hostnameToSlotIdMap.set(hn, this.hostnameSlots.length);
this.hostnameSlots.push(strId);
this.hostnameSlots.push(strId, 0);
return;
}
if ( iHn < 0 ) {
this.hostnameSlotsEx[-iHn].push(strId);
return;
// Add as last item.
while ( this.hostnameSlots[iHn+1] !== 0 ) {
iHn = this.hostnameSlots[iHn+1];
}
const strIdEx = -this.hostnameSlotsEx.length;
this.hostnameToSlotIdMap.set(hn, strIdEx);
this.hostnameSlotsEx.push([ this.hostnameSlots[iHn], strId ]);
this.hostnameSlots[iHn] = strIdEx;
this.hostnameSlots[iHn+1] = this.hostnameSlots.length;
this.hostnameSlots.push(strId, 0);
}

clear() {
this.hostnameToSlotIdMap.clear();
this.hostnameSlots.length = 0;
this.hostnameSlotsEx.length = 1; // IMPORTANT: 1, not 0
this.strSlots.length = 0;
this.strToIdMap.clear();
this.size = 0;
Expand Down Expand Up @@ -593,21 +588,15 @@
}
const mask = out.length - 1; // out.length must be power of two
for (;;) {
const filterId = this.hostnameToSlotIdMap.get(hostname);
if ( filterId !== undefined ) {
if ( filterId < 0 ) {
const bucket = this.hostnameSlotsEx[-filterId];
for ( const strId of bucket ) {
out[strId & mask].add(
this.strSlots[strId >>> this.nBits]
);
}
} else {
const strId = this.hostnameSlots[filterId];
let iHn = this.hostnameToSlotIdMap.get(hostname);
if ( iHn !== undefined ) {
do {
const strId = this.hostnameSlots[iHn+0];
out[strId & mask].add(
this.strSlots[strId >>> this.nBits]
);
}
iHn = this.hostnameSlots[iHn+1];
} while ( iHn !== 0 );
}
if ( hostname === '' ) { break; }
const pos = hostname.indexOf('.');
Expand All @@ -624,7 +613,6 @@
return {
hostnameToSlotIdMap: Array.from(this.hostnameToSlotIdMap),
hostnameSlots: this.hostnameSlots,
hostnameSlotsEx: this.hostnameSlotsEx,
strSlots: this.strSlots,
size: this.size
};
Expand All @@ -633,7 +621,6 @@
fromSelfie(selfie) {
this.hostnameToSlotIdMap = new Map(selfie.hostnameToSlotIdMap);
this.hostnameSlots = selfie.hostnameSlots;
this.hostnameSlotsEx = selfie.hostnameSlotsEx;
this.strSlots = selfie.strSlots;
this.size = selfie.size;
}
Expand Down

0 comments on commit e94024d

Please sign in to comment.