Bug 1257979 - Use a GCHashSet for a hash in the JSON stringifying algorithm. r=sfink

--HG--
extra : rebase_source : c6e2b22de7467ac4c99fa6e010a88c2f2ca1d981
This commit is contained in:
Jeff Walden 2016-03-18 16:43:53 -07:00
parent 4fceffbb3c
commit 1a0903f98c
6 changed files with 25 additions and 15 deletions

View File

@ -303,6 +303,7 @@ class MutableGCHashSetOperations
bool init(uint32_t len = 16) { return set().init(len); } bool init(uint32_t len = 16) { return set().init(len); }
void clear() { set().clear(); } void clear() { set().clear(); }
void finish() { set().finish(); } void finish() { set().finish(); }
void remove(Ptr p) { set().remove(p); }
void remove(const Lookup& l) { set().remove(l); } void remove(const Lookup& l) { set().remove(l); }
template<typename TInput> template<typename TInput>

View File

@ -27,11 +27,15 @@
#include "js/TypeDecls.h" #include "js/TypeDecls.h"
#include "js/Utility.h" #include "js/Utility.h"
namespace js {
template <typename T> struct DefaultHasher;
} // namespace js
struct jsid struct jsid
{ {
size_t asBits; size_t asBits;
bool operator==(jsid rhs) const { return asBits == rhs.asBits; } bool operator==(const jsid& rhs) const { return asBits == rhs.asBits; }
bool operator!=(jsid rhs) const { return asBits != rhs.asBits; } bool operator!=(const jsid& rhs) const { return asBits != rhs.asBits; }
} JS_HAZ_GC_POINTER; } JS_HAZ_GC_POINTER;
#define JSID_BITS(id) (id.asBits) #define JSID_BITS(id) (id.asBits)
@ -168,6 +172,18 @@ extern JS_PUBLIC_DATA(const JS::HandleId) JSID_EMPTYHANDLE;
namespace js { namespace js {
template <>
struct DefaultHasher<jsid>
{
typedef jsid Lookup;
static HashNumber hash(jsid id) {
return JSID_BITS(id);
}
static bool match(jsid id1, jsid id2) {
return id1 == id2;
}
};
template <> template <>
struct GCPolicy<jsid> struct GCPolicy<jsid>
{ {

View File

@ -13,6 +13,7 @@
#include "gc/Zone.h" #include "gc/Zone.h"
#include "js/GCVector.h" #include "js/GCVector.h"
#include "js/Id.h"
#include "vm/NativeObject.h" #include "vm/NativeObject.h"
#include "vm/ProxyObject.h" #include "vm/ProxyObject.h"
@ -121,7 +122,7 @@ class IndirectBindingMap
RelocatablePtrShape shape; RelocatablePtrShape shape;
}; };
typedef HashMap<jsid, Binding, JsidHasher, ZoneAllocPolicy> Map; typedef HashMap<jsid, Binding, DefaultHasher<jsid>, ZoneAllocPolicy> Map;
Map map_; Map map_;
}; };

View File

@ -31,17 +31,6 @@ HashId(jsid id)
return mozilla::HashGeneric(JSID_BITS(id)); return mozilla::HashGeneric(JSID_BITS(id));
} }
struct JsidHasher
{
typedef jsid Lookup;
static HashNumber hash(const Lookup& l) {
return HashNumber(JSID_BITS(l));
}
static bool match(const jsid& id, const Lookup& l) {
return id == l;
}
};
/* /*
* Return a printable, lossless char[] representation of a string-type atom. * Return a printable, lossless char[] representation of a string-type atom.
* The lifetime of the result matches the lifetime of bytes. * The lifetime of the result matches the lifetime of bytes.

View File

@ -635,7 +635,7 @@ js::Stringify(JSContext* cx, MutableHandleValue vp, JSObject* replacer_, Value s
// is passed in. If we end up having to add elements past this // is passed in. If we end up having to add elements past this
// size, the set will naturally resize to accommodate them. // size, the set will naturally resize to accommodate them.
const uint32_t MaxInitialSize = 32; const uint32_t MaxInitialSize = 32;
HashSet<jsid, JsidHasher> idSet(cx); Rooted<GCHashSet<jsid>> idSet(cx, GCHashSet<jsid>(cx));
if (!idSet.init(Min(len, MaxInitialSize))) if (!idSet.init(Min(len, MaxInitialSize)))
return false; return false;

View File

@ -925,6 +925,9 @@ js::CloneRegExpObject(JSContext* cx, JSObject* obj_)
if (!currentStatics) if (!currentStatics)
return nullptr; return nullptr;
if (!EmptyShape::ensureInitialCustomShape<RegExpObject>(cx, clone))
return nullptr;
Rooted<JSAtom*> source(cx, regex->getSource()); Rooted<JSAtom*> source(cx, regex->getSource());
RegExpFlag origFlags = regex->getFlags(); RegExpFlag origFlags = regex->getFlags();