1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-  */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3  * License, v. 2.0. If a copy of the MPL was not distributed with this
4  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 
6 #ifndef _MORKATOMMAP_
7 #define _MORKATOMMAP_ 1
8 
9 #ifndef _MORK_
10 #  include "mork.h"
11 #endif
12 
13 #ifndef _MORKNODE_
14 #  include "morkNode.h"
15 #endif
16 
17 #ifndef _MORKMAP_
18 #  include "morkMap.h"
19 #endif
20 
21 #ifndef _MORKPROBEMAP_
22 #  include "morkProbeMap.h"
23 #endif
24 
25 #ifndef _MORKINTMAP_
26 #  include "morkIntMap.h"
27 #endif
28 
29 // 456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
30 
31 #define morkDerived_kAtomAidMap /*i*/ 0x6141 /* ascii 'aA' */
32 
33 #define morkAtomAidMap_kStartSlotCount 23
34 
35 /*| morkAtomAidMap: keys of morkBookAtom organized by atom ID
36 |*/
37 #ifdef MORK_ENABLE_PROBE_MAPS
38 class morkAtomAidMap : public morkProbeMap {  // for mapping tokens to maps
39 #else                                         /*MORK_ENABLE_PROBE_MAPS*/
40 class morkAtomAidMap : public morkMap {  // for mapping tokens to maps
41 #endif                                        /*MORK_ENABLE_PROBE_MAPS*/
42 
43   // { ===== begin morkNode interface =====
44  public:  // morkNode virtual methods
45   virtual void CloseMorkNode(
46       morkEnv* ev) override;  // CloseAtomAidMap() only if open
47   virtual ~morkAtomAidMap();  // assert that CloseAtomAidMap() executed earlier
48 
49  public:  // morkMap construction & destruction
50   morkAtomAidMap(morkEnv* ev, const morkUsage& inUsage, nsIMdbHeap* ioHeap,
51                  nsIMdbHeap* ioSlotHeap);
52   void CloseAtomAidMap(morkEnv* ev);  // called by CloseMorkNode();
53 
54  public:  // dynamic type identification
IsAtomAidMap()55   mork_bool IsAtomAidMap() const {
56     return IsNode() && mNode_Derived == morkDerived_kAtomAidMap;
57   }
58   // } ===== end morkNode methods =====
59 
60  public:
61 #ifdef MORK_ENABLE_PROBE_MAPS
62   // { ===== begin morkProbeMap methods =====
63   virtual mork_test  // hit(a,b) implies hash(a) == hash(b)
64   MapTest(morkEnv* ev, const void* inMapKey,
65           const void* inAppKey) const override;
66 
67   virtual mork_u4  // hit(a,b) implies hash(a) == hash(b)
68   MapHash(morkEnv* ev, const void* inAppKey) const override;
69 
70   virtual mork_u4 ProbeMapHashMapKey(morkEnv* ev,
71                                      const void* inMapKey) const override;
72 
73   // virtual mork_bool ProbeMapIsKeyNil(morkEnv* ev, void* ioMapKey);
74 
75   // virtual void ProbeMapClearKey(morkEnv* ev, // put 'nil' into all keys
76   // inside map
77   //   void* ioMapKey, mork_count inKeyCount); // array of keys inside map
78 
79   // virtual void ProbeMapPushIn(morkEnv* ev, // move (key,val) into the map
80   //   const void* inAppKey, const void* inAppVal, // (key,val) outside map
81   //   void* outMapKey, void* outMapVal);      // (key,val) inside map
82 
83   // virtual void ProbeMapPullOut(morkEnv* ev, // move (key,val) out from the
84   // map
85   //   const void* inMapKey, const void* inMapVal, // (key,val) inside map
86   //   void* outAppKey, void* outAppVal) const;    // (key,val) outside map
87   // } ===== end morkProbeMap methods =====
88 #else  /*MORK_ENABLE_PROBE_MAPS*/
89   // { ===== begin morkMap poly interface =====
90   virtual mork_bool  // note: equal(a,b) implies hash(a) == hash(b)
91   Equal(morkEnv* ev, const void* inKeyA, const void* inKeyB) const override;
92   // implemented using morkBookAtom::HashAid()
93 
94   virtual mork_u4  // note: equal(a,b) implies hash(a) == hash(b)
95   Hash(morkEnv* ev, const void* inKey) const override;
96   // implemented using morkBookAtom::EqualAid()
97 // } ===== end morkMap poly interface =====
98 #endif /*MORK_ENABLE_PROBE_MAPS*/
99 
100  public:  // other map methods
101   mork_bool AddAtom(morkEnv* ev, morkBookAtom* ioAtom);
102   // AddAtom() returns ev->Good()
103 
104   morkBookAtom* CutAtom(morkEnv* ev, const morkBookAtom* inAtom);
105   // CutAtom() returns the atom removed equal to inAtom, if there was one
106 
107   morkBookAtom* GetAtom(morkEnv* ev, const morkBookAtom* inAtom);
108   // GetAtom() returns the atom equal to inAtom, or else nil
109 
110   morkBookAtom* GetAid(morkEnv* ev, mork_aid inAid);
111   // GetAid() returns the atom equal to inAid, or else nil
112 
113   // note the atoms are owned elsewhere, usually by morkAtomSpace
114 
115  public:  // typesafe refcounting inlines calling inherited morkNode methods
SlotWeakAtomAidMap(morkAtomAidMap * me,morkEnv * ev,morkAtomAidMap ** ioSlot)116   static void SlotWeakAtomAidMap(morkAtomAidMap* me, morkEnv* ev,
117                                  morkAtomAidMap** ioSlot) {
118     morkNode::SlotWeakNode((morkNode*)me, ev, (morkNode**)ioSlot);
119   }
120 
SlotStrongAtomAidMap(morkAtomAidMap * me,morkEnv * ev,morkAtomAidMap ** ioSlot)121   static void SlotStrongAtomAidMap(morkAtomAidMap* me, morkEnv* ev,
122                                    morkAtomAidMap** ioSlot) {
123     morkNode::SlotStrongNode((morkNode*)me, ev, (morkNode**)ioSlot);
124   }
125 };
126 
127 #ifdef MORK_ENABLE_PROBE_MAPS
128 class morkAtomAidMapIter : public morkProbeMapIter {  // typesafe wrapper class
129 #else                                                 /*MORK_ENABLE_PROBE_MAPS*/
130 class morkAtomAidMapIter : public morkMapIter {  // typesafe wrapper class
131 #endif                                                /*MORK_ENABLE_PROBE_MAPS*/
132 
133  public:
134 #ifdef MORK_ENABLE_PROBE_MAPS
morkAtomAidMapIter(morkEnv * ev,morkAtomAidMap * ioMap)135   morkAtomAidMapIter(morkEnv* ev, morkAtomAidMap* ioMap)
136       : morkProbeMapIter(ev, ioMap) {}
137 
morkAtomAidMapIter()138   morkAtomAidMapIter() : morkProbeMapIter() {}
139 #else  /*MORK_ENABLE_PROBE_MAPS*/
140   morkAtomAidMapIter(morkEnv* ev, morkAtomAidMap* ioMap)
141       : morkMapIter(ev, ioMap) {}
142 
143   morkAtomAidMapIter() : morkMapIter() {}
144 #endif /*MORK_ENABLE_PROBE_MAPS*/
145 
InitAtomAidMapIter(morkEnv * ev,morkAtomAidMap * ioMap)146   void InitAtomAidMapIter(morkEnv* ev, morkAtomAidMap* ioMap) {
147     this->InitMapIter(ev, ioMap);
148   }
149 
FirstAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)150   mork_change* FirstAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
151     return this->First(ev, outAtomPtr, /*val*/ (void*)0);
152   }
153 
NextAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)154   mork_change* NextAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
155     return this->Next(ev, outAtomPtr, /*val*/ (void*)0);
156   }
157 
HereAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)158   mork_change* HereAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
159     return this->Here(ev, outAtomPtr, /*val*/ (void*)0);
160   }
161 
CutHereAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)162   mork_change* CutHereAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
163     return this->CutHere(ev, outAtomPtr, /*val*/ (void*)0);
164   }
165 };
166 
167 // 456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
168 
169 // 456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
170 
171 #define morkDerived_kAtomBodyMap /*i*/ 0x6142 /* ascii 'aB' */
172 
173 #define morkAtomBodyMap_kStartSlotCount 23
174 
175 /*| morkAtomBodyMap: keys of morkBookAtom organized by body bytes
176 |*/
177 #ifdef MORK_ENABLE_PROBE_MAPS
178 class morkAtomBodyMap : public morkProbeMap {  // for mapping tokens to maps
179 #else                                          /*MORK_ENABLE_PROBE_MAPS*/
180 class morkAtomBodyMap : public morkMap {  // for mapping tokens to maps
181 #endif                                         /*MORK_ENABLE_PROBE_MAPS*/
182 
183   // { ===== begin morkNode interface =====
184  public:  // morkNode virtual methods
185   virtual void CloseMorkNode(
186       morkEnv* ev) override;   // CloseAtomBodyMap() only if open
187   virtual ~morkAtomBodyMap();  // assert CloseAtomBodyMap() executed earlier
188 
189  public:  // morkMap construction & destruction
190   morkAtomBodyMap(morkEnv* ev, const morkUsage& inUsage, nsIMdbHeap* ioHeap,
191                   nsIMdbHeap* ioSlotHeap);
192   void CloseAtomBodyMap(morkEnv* ev);  // called by CloseMorkNode();
193 
194  public:  // dynamic type identification
IsAtomBodyMap()195   mork_bool IsAtomBodyMap() const {
196     return IsNode() && mNode_Derived == morkDerived_kAtomBodyMap;
197   }
198   // } ===== end morkNode methods =====
199 
200  public:
201 #ifdef MORK_ENABLE_PROBE_MAPS
202   // { ===== begin morkProbeMap methods =====
203   virtual mork_test  // hit(a,b) implies hash(a) == hash(b)
204   MapTest(morkEnv* ev, const void* inMapKey,
205           const void* inAppKey) const override;
206 
207   virtual mork_u4  // hit(a,b) implies hash(a) == hash(b)
208   MapHash(morkEnv* ev, const void* inAppKey) const override;
209 
210   virtual mork_u4 ProbeMapHashMapKey(morkEnv* ev,
211                                      const void* inMapKey) const override;
212 
213   // virtual mork_bool ProbeMapIsKeyNil(morkEnv* ev, void* ioMapKey);
214 
215   // virtual void ProbeMapClearKey(morkEnv* ev, // put 'nil' into all keys
216   // inside map
217   //   void* ioMapKey, mork_count inKeyCount); // array of keys inside map
218 
219   // virtual void ProbeMapPushIn(morkEnv* ev, // move (key,val) into the map
220   //   const void* inAppKey, const void* inAppVal, // (key,val) outside map
221   //   void* outMapKey, void* outMapVal);      // (key,val) inside map
222 
223   // virtual void ProbeMapPullOut(morkEnv* ev, // move (key,val) out from the
224   // map
225   //   const void* inMapKey, const void* inMapVal, // (key,val) inside map
226   //   void* outAppKey, void* outAppVal) const;    // (key,val) outside map
227   // } ===== end morkProbeMap methods =====
228 #else  /*MORK_ENABLE_PROBE_MAPS*/
229   // { ===== begin morkMap poly interface =====
230   virtual mork_bool  // note: equal(a,b) implies hash(a) == hash(b)
231   Equal(morkEnv* ev, const void* inKeyA, const void* inKeyB) const override;
232   // implemented using morkBookAtom::EqualFormAndBody()
233 
234   virtual mork_u4  // note: equal(a,b) implies hash(a) == hash(b)
235   Hash(morkEnv* ev, const void* inKey) const override;
236   // implemented using morkBookAtom::HashFormAndBody()
237 // } ===== end morkMap poly interface =====
238 #endif /*MORK_ENABLE_PROBE_MAPS*/
239 
240  public:  // other map methods
241   mork_bool AddAtom(morkEnv* ev, morkBookAtom* ioAtom);
242   // AddAtom() returns ev->Good()
243 
244   morkBookAtom* CutAtom(morkEnv* ev, const morkBookAtom* inAtom);
245   // CutAtom() returns the atom removed equal to inAtom, if there was one
246 
247   morkBookAtom* GetAtom(morkEnv* ev, const morkBookAtom* inAtom);
248   // GetAtom() returns the atom equal to inAtom, or else nil
249 
250   // note the atoms are owned elsewhere, usually by morkAtomSpace
251 
252  public:  // typesafe refcounting inlines calling inherited morkNode methods
SlotWeakAtomBodyMap(morkAtomBodyMap * me,morkEnv * ev,morkAtomBodyMap ** ioSlot)253   static void SlotWeakAtomBodyMap(morkAtomBodyMap* me, morkEnv* ev,
254                                   morkAtomBodyMap** ioSlot) {
255     morkNode::SlotWeakNode((morkNode*)me, ev, (morkNode**)ioSlot);
256   }
257 
SlotStrongAtomBodyMap(morkAtomBodyMap * me,morkEnv * ev,morkAtomBodyMap ** ioSlot)258   static void SlotStrongAtomBodyMap(morkAtomBodyMap* me, morkEnv* ev,
259                                     morkAtomBodyMap** ioSlot) {
260     morkNode::SlotStrongNode((morkNode*)me, ev, (morkNode**)ioSlot);
261   }
262 };
263 
264 #ifdef MORK_ENABLE_PROBE_MAPS
265 class morkAtomBodyMapIter : public morkProbeMapIter {  // typesafe wrapper class
266 #else  /*MORK_ENABLE_PROBE_MAPS*/
267 class morkAtomBodyMapIter : public morkMapIter {  // typesafe wrapper class
268 #endif /*MORK_ENABLE_PROBE_MAPS*/
269 
270  public:
271 #ifdef MORK_ENABLE_PROBE_MAPS
morkAtomBodyMapIter(morkEnv * ev,morkAtomBodyMap * ioMap)272   morkAtomBodyMapIter(morkEnv* ev, morkAtomBodyMap* ioMap)
273       : morkProbeMapIter(ev, ioMap) {}
274 
morkAtomBodyMapIter()275   morkAtomBodyMapIter() : morkProbeMapIter() {}
276 #else  /*MORK_ENABLE_PROBE_MAPS*/
277   morkAtomBodyMapIter(morkEnv* ev, morkAtomBodyMap* ioMap)
278       : morkMapIter(ev, ioMap) {}
279 
280   morkAtomBodyMapIter() : morkMapIter() {}
281 #endif /*MORK_ENABLE_PROBE_MAPS*/
282 
InitAtomBodyMapIter(morkEnv * ev,morkAtomBodyMap * ioMap)283   void InitAtomBodyMapIter(morkEnv* ev, morkAtomBodyMap* ioMap) {
284     this->InitMapIter(ev, ioMap);
285   }
286 
FirstAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)287   mork_change* FirstAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
288     return this->First(ev, outAtomPtr, /*val*/ (void*)0);
289   }
290 
NextAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)291   mork_change* NextAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
292     return this->Next(ev, outAtomPtr, /*val*/ (void*)0);
293   }
294 
HereAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)295   mork_change* HereAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
296     return this->Here(ev, outAtomPtr, /*val*/ (void*)0);
297   }
298 
CutHereAtom(morkEnv * ev,morkBookAtom ** outAtomPtr)299   mork_change* CutHereAtom(morkEnv* ev, morkBookAtom** outAtomPtr) {
300     return this->CutHere(ev, outAtomPtr, /*val*/ (void*)0);
301   }
302 };
303 
304 // 456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
305 
306 #define morkDerived_kAtomRowMap /*i*/ 0x6152 /* ascii 'aR' */
307 
308 /*| morkAtomRowMap: maps morkAtom* -> morkRow*
309 |*/
310 class morkAtomRowMap : public morkIntMap {  // for mapping atoms to rows
311 
312  public:
313   mork_column mAtomRowMap_IndexColumn;  // row column being indexed
314 
315  public:
316   virtual ~morkAtomRowMap();
317   morkAtomRowMap(morkEnv* ev, const morkUsage& inUsage, nsIMdbHeap* ioHeap,
318                  nsIMdbHeap* ioSlotHeap, mork_column inIndexColumn);
319 
320  public:  // adding and cutting from morkRow instance candidate
321   void AddRow(morkEnv* ev, morkRow* ioRow);
322   // add ioRow only if it contains a cell in mAtomRowMap_IndexColumn.
323 
324   void CutRow(morkEnv* ev, morkRow* ioRow);
325   // cut ioRow only if it contains a cell in mAtomRowMap_IndexColumn.
326 
327  public:  // other map methods
AddAid(morkEnv * ev,mork_aid inAid,morkRow * ioRow)328   mork_bool AddAid(morkEnv* ev, mork_aid inAid, morkRow* ioRow) {
329     return this->AddInt(ev, inAid, ioRow);
330   }
331   // the AddAid() boolean return equals ev->Good().
332 
CutAid(morkEnv * ev,mork_aid inAid)333   mork_bool CutAid(morkEnv* ev, mork_aid inAid) {
334     return this->CutInt(ev, inAid);
335   }
336   // The CutAid() boolean return indicates whether removal happened.
337 
GetAid(morkEnv * ev,mork_aid inAid)338   morkRow* GetAid(morkEnv* ev, mork_aid inAid) {
339     return (morkRow*)this->GetInt(ev, inAid);
340   }
341   // Note the returned space does NOT have an increase in refcount for this.
342 
343  public:  // dynamic type identification
IsAtomRowMap()344   mork_bool IsAtomRowMap() const {
345     return IsNode() && mNode_Derived == morkDerived_kAtomRowMap;
346   }
347 
348  public:  // typesafe refcounting inlines calling inherited morkNode methods
SlotWeakAtomRowMap(morkAtomRowMap * me,morkEnv * ev,morkAtomRowMap ** ioSlot)349   static void SlotWeakAtomRowMap(morkAtomRowMap* me, morkEnv* ev,
350                                  morkAtomRowMap** ioSlot) {
351     morkNode::SlotWeakNode((morkNode*)me, ev, (morkNode**)ioSlot);
352   }
353 
SlotStrongAtomRowMap(morkAtomRowMap * me,morkEnv * ev,morkAtomRowMap ** ioSlot)354   static void SlotStrongAtomRowMap(morkAtomRowMap* me, morkEnv* ev,
355                                    morkAtomRowMap** ioSlot) {
356     morkNode::SlotStrongNode((morkNode*)me, ev, (morkNode**)ioSlot);
357   }
358 };
359 
360 class morkAtomRowMapIter : public morkMapIter {  // typesafe wrapper class
361 
362  public:
morkAtomRowMapIter(morkEnv * ev,morkAtomRowMap * ioMap)363   morkAtomRowMapIter(morkEnv* ev, morkAtomRowMap* ioMap)
364       : morkMapIter(ev, ioMap) {}
365 
morkAtomRowMapIter()366   morkAtomRowMapIter() : morkMapIter() {}
InitAtomRowMapIter(morkEnv * ev,morkAtomRowMap * ioMap)367   void InitAtomRowMapIter(morkEnv* ev, morkAtomRowMap* ioMap) {
368     this->InitMapIter(ev, ioMap);
369   }
370 
FirstAtomAndRow(morkEnv * ev,morkAtom ** outAtom,morkRow ** outRow)371   mork_change* FirstAtomAndRow(morkEnv* ev, morkAtom** outAtom,
372                                morkRow** outRow) {
373     return this->First(ev, outAtom, outRow);
374   }
375 
NextAtomAndRow(morkEnv * ev,morkAtom ** outAtom,morkRow ** outRow)376   mork_change* NextAtomAndRow(morkEnv* ev, morkAtom** outAtom,
377                               morkRow** outRow) {
378     return this->Next(ev, outAtom, outRow);
379   }
380 
HereAtomAndRow(morkEnv * ev,morkAtom ** outAtom,morkRow ** outRow)381   mork_change* HereAtomAndRow(morkEnv* ev, morkAtom** outAtom,
382                               morkRow** outRow) {
383     return this->Here(ev, outAtom, outRow);
384   }
385 
CutHereAtomAndRow(morkEnv * ev,morkAtom ** outAtom,morkRow ** outRow)386   mork_change* CutHereAtomAndRow(morkEnv* ev, morkAtom** outAtom,
387                                  morkRow** outRow) {
388     return this->CutHere(ev, outAtom, outRow);
389   }
390 };
391 
392 // 456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
393 
394 #endif /* _MORKATOMMAP_ */
395