js/src/jspropertytree.h

branch
TOR_BUG_9701
changeset 15
b8a032363ba2
equal deleted inserted replaced
-1:000000000000 0:2eed8295fba8
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2 * vim: set ts=8 sts=4 et sw=4 tw=99:
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
7 #ifndef jspropertytree_h
8 #define jspropertytree_h
9
10 #include "jsalloc.h"
11 #include "jspubtd.h"
12
13 #include "js/HashTable.h"
14
15 namespace js {
16
17 class Shape;
18 struct StackShape;
19
20 struct ShapeHasher {
21 typedef Shape *Key;
22 typedef StackShape Lookup;
23
24 static inline HashNumber hash(const Lookup &l);
25 static inline bool match(Key k, const Lookup &l);
26 };
27
28 typedef HashSet<Shape *, ShapeHasher, SystemAllocPolicy> KidsHash;
29
30 class KidsPointer {
31 private:
32 enum {
33 SHAPE = 0,
34 HASH = 1,
35 TAG = 1
36 };
37
38 uintptr_t w;
39
40 public:
41 bool isNull() const { return !w; }
42 void setNull() { w = 0; }
43
44 bool isShape() const { return (w & TAG) == SHAPE && !isNull(); }
45 Shape *toShape() const {
46 JS_ASSERT(isShape());
47 return reinterpret_cast<Shape *>(w & ~uintptr_t(TAG));
48 }
49 void setShape(Shape *shape) {
50 JS_ASSERT(shape);
51 JS_ASSERT((reinterpret_cast<uintptr_t>(static_cast<Shape *>(shape)) & TAG) == 0);
52 w = reinterpret_cast<uintptr_t>(static_cast<Shape *>(shape)) | SHAPE;
53 }
54
55 bool isHash() const { return (w & TAG) == HASH; }
56 KidsHash *toHash() const {
57 JS_ASSERT(isHash());
58 return reinterpret_cast<KidsHash *>(w & ~uintptr_t(TAG));
59 }
60 void setHash(KidsHash *hash) {
61 JS_ASSERT(hash);
62 JS_ASSERT((reinterpret_cast<uintptr_t>(hash) & TAG) == 0);
63 w = reinterpret_cast<uintptr_t>(hash) | HASH;
64 }
65
66 #ifdef DEBUG
67 void checkConsistency(Shape *aKid) const;
68 #endif
69 };
70
71 class PropertyTree
72 {
73 friend class ::JSFunction;
74
75 JSCompartment *compartment_;
76
77 bool insertChild(ExclusiveContext *cx, Shape *parent, Shape *child);
78
79 PropertyTree();
80
81 public:
82 /*
83 * Use a lower limit for objects that are accessed using SETELEM (o[x] = y).
84 * These objects are likely used as hashmaps and dictionary mode is more
85 * efficient in this case.
86 */
87 enum {
88 MAX_HEIGHT = 512,
89 MAX_HEIGHT_WITH_ELEMENTS_ACCESS = 128
90 };
91
92 PropertyTree(JSCompartment *comp)
93 : compartment_(comp)
94 {
95 }
96
97 JSCompartment *compartment() { return compartment_; }
98
99 Shape *newShape(ExclusiveContext *cx);
100 Shape *getChild(ExclusiveContext *cx, Shape *parent, StackShape &child);
101 Shape *lookupChild(ThreadSafeContext *cx, Shape *parent, const StackShape &child);
102 };
103
104 } /* namespace js */
105
106 #endif /* jspropertytree_h */

mercurial