зеркало из https://github.com/mozilla/gecko-dev.git
mork performance improvements by davidmc, r=bienvenu
This commit is contained in:
Родитель
4e09e35e37
Коммит
13937da825
|
@ -2141,6 +2141,49 @@ public:
|
|||
nsIMdbRow* ioSourceRow) = 0; // row to duplicate
|
||||
// } ----- end row methods -----
|
||||
|
||||
// { ----- begin blob methods -----
|
||||
virtual mdb_err SetCellYarn(nsIMdbEnv* ev, // synonym for AddColumn()
|
||||
mdb_column inColumn, // column to write
|
||||
const mdbYarn* inYarn) = 0; // reads from yarn slots
|
||||
// make this text object contain content from the yarn's buffer
|
||||
|
||||
virtual mdb_err GetCellYarn(nsIMdbEnv* ev,
|
||||
mdb_column inColumn, // column to read
|
||||
mdbYarn* outYarn) = 0; // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
|
||||
virtual mdb_err AliasCellYarn(nsIMdbEnv* ev,
|
||||
mdb_column inColumn, // column to alias
|
||||
mdbYarn* outYarn) = 0; // writes ALL yarn slots
|
||||
|
||||
virtual mdb_err NextCellYarn(nsIMdbEnv* ev, // iterative version of GetCellYarn()
|
||||
mdb_column* ioColumn, // next column to read
|
||||
mdbYarn* outYarn) = 0; // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
//
|
||||
// The ioColumn argument is an inout parameter which initially contains the
|
||||
// last column accessed and returns the next column corresponding to the
|
||||
// content read into the yarn. Callers should start with a zero column
|
||||
// value to say 'no previous column', which causes the first column to be
|
||||
// read. Then the value returned in ioColumn is perfect for the next call
|
||||
// to NextCellYarn(), since it will then be the previous column accessed.
|
||||
// Callers need only examine the column token returned to see which cell
|
||||
// in the row is being read into the yarn. When no more columns remain,
|
||||
// and the iteration has ended, ioColumn will return a zero token again.
|
||||
// So iterating over cells starts and ends with a zero column token.
|
||||
|
||||
virtual mdb_err SeekCellYarn( // resembles nsIMdbRowCellCursor::SeekCell()
|
||||
nsIMdbEnv* ev, // context
|
||||
mdb_pos inPos, // position of cell in row sequence
|
||||
mdb_column* outColumn, // column for this particular cell
|
||||
mdbYarn* outYarn) = 0; // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
// Callers can pass nil for outYarn to indicate no interest in content, so
|
||||
// only the outColumn value is returned. NOTE to subclasses: you must be
|
||||
// able to ignore outYarn when the pointer is nil; please do not crash.
|
||||
|
||||
// } ----- end blob methods -----
|
||||
|
||||
// } ===== end nsIMdbRow methods =====
|
||||
};
|
||||
|
||||
|
@ -2361,3 +2404,4 @@ public:
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MDB_ */
|
||||
|
||||
|
|
|
@ -373,6 +373,11 @@ morkBookAtom::HashFormAndBody(morkEnv* ev) const
|
|||
size = ((const morkBigBookAtom*) this)->mBigBookAtom_Size;
|
||||
body = ((const morkBigBookAtom*) this)->mBigBookAtom_Body;
|
||||
}
|
||||
else if ( this->IsFarBook() )
|
||||
{
|
||||
size = ((const morkFarBookAtom*) this)->mFarBookAtom_Size;
|
||||
body = ((const morkFarBookAtom*) this)->mFarBookAtom_Body;
|
||||
}
|
||||
else
|
||||
this->NonBookAtomTypeError(ev);
|
||||
|
||||
|
@ -414,6 +419,12 @@ morkBookAtom::EqualFormAndBody(morkEnv* ev, const morkBookAtom* inAtom) const
|
|||
body = ((const morkBigBookAtom*) inAtom)->mBigBookAtom_Body;
|
||||
form = ((const morkBigBookAtom*) inAtom)->mBigBookAtom_Form;
|
||||
}
|
||||
else if ( inAtom->IsFarBook() )
|
||||
{
|
||||
size = ((const morkFarBookAtom*) inAtom)->mFarBookAtom_Size;
|
||||
body = ((const morkFarBookAtom*) inAtom)->mFarBookAtom_Body;
|
||||
form = ((const morkFarBookAtom*) inAtom)->mFarBookAtom_Form;
|
||||
}
|
||||
else
|
||||
inAtom->NonBookAtomTypeError(ev);
|
||||
|
||||
|
@ -433,6 +444,12 @@ morkBookAtom::EqualFormAndBody(morkEnv* ev, const morkBookAtom* inAtom) const
|
|||
thisBody = ((const morkBigBookAtom*) this)->mBigBookAtom_Body;
|
||||
thisForm = ((const morkBigBookAtom*) this)->mBigBookAtom_Form;
|
||||
}
|
||||
else if ( this->IsFarBook() )
|
||||
{
|
||||
thisSize = ((const morkFarBookAtom*) this)->mFarBookAtom_Size;
|
||||
thisBody = ((const morkFarBookAtom*) this)->mFarBookAtom_Body;
|
||||
thisForm = ((const morkFarBookAtom*) this)->mFarBookAtom_Form;
|
||||
}
|
||||
else
|
||||
this->NonBookAtomTypeError(ev);
|
||||
|
||||
|
@ -533,4 +550,30 @@ morkBigBookAtom::InitBigBookAtom(morkEnv* ev, const morkBuf& inBuf,
|
|||
ev->NilPointerError();
|
||||
}
|
||||
|
||||
void morkFarBookAtom::InitFarBookAtom(morkEnv* ev, const morkBuf& inBuf,
|
||||
mork_cscode inForm, morkAtomSpace* ioSpace, mork_aid inAid)
|
||||
{
|
||||
mAtom_Kind = 0;
|
||||
mAtom_Change = morkChange_kNil;
|
||||
if ( ioSpace )
|
||||
{
|
||||
if ( inAid )
|
||||
{
|
||||
mAtom_CellUses = 0;
|
||||
mAtom_Kind = morkAtom_kKindFarBook;
|
||||
mAtom_Size = 0;
|
||||
mBookAtom_Space = ioSpace;
|
||||
mBookAtom_Id = inAid;
|
||||
mFarBookAtom_Form = inForm;
|
||||
mFarBookAtom_Size = inBuf.mBuf_Fill;
|
||||
mFarBookAtom_Body = (mork_u1*) inBuf.mBuf_Body;
|
||||
}
|
||||
else
|
||||
this->ZeroAidError(ev);
|
||||
}
|
||||
else
|
||||
ev->NilPointerError();
|
||||
}
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -38,6 +38,7 @@
|
|||
#define morkAtom_kKindBigAnon 'A' /* means morkBigAnonAtom subclass */
|
||||
#define morkAtom_kKindWeeBook 'b' /* means morkWeeBookAtom subclass */
|
||||
#define morkAtom_kKindBigBook 'B' /* means morkBigBookAtom subclass */
|
||||
#define morkAtom_kKindFarBook 'f' /* means morkFarBookAtom subclass */
|
||||
#define morkAtom_kKindRowOid 'r' /* means morkOidAtom subclass */
|
||||
#define morkAtom_kKindTableOid 't' /* means morkOidAtom subclass */
|
||||
|
||||
|
@ -59,6 +60,7 @@ public:
|
|||
mork_bool IsBigAnon() const { return mAtom_Kind == morkAtom_kKindBigAnon; }
|
||||
mork_bool IsWeeBook() const { return mAtom_Kind == morkAtom_kKindWeeBook; }
|
||||
mork_bool IsBigBook() const { return mAtom_Kind == morkAtom_kKindBigBook; }
|
||||
mork_bool IsFarBook() const { return mAtom_Kind == morkAtom_kKindFarBook; }
|
||||
mork_bool IsRowOid() const { return mAtom_Kind == morkAtom_kKindRowOid; }
|
||||
mork_bool IsTableOid() const { return mAtom_Kind == morkAtom_kKindTableOid; }
|
||||
|
||||
|
@ -233,9 +235,11 @@ public: // Hash() and Equal() for atom ID maps are same for all subclasses:
|
|||
|
||||
public: // Hash() and Equal() for atom body maps know about subclasses:
|
||||
|
||||
// YOU CANNOT SUBCLASS morkBookAtom WITHOUT FIXING Hash and Equal METHODS:
|
||||
|
||||
mork_u4 HashFormAndBody(morkEnv* ev) const;
|
||||
mork_bool EqualFormAndBody(morkEnv* ev, const morkBookAtom* inAtom) const;
|
||||
|
||||
|
||||
public: // separation from containing space
|
||||
|
||||
void CutBookAtomFromSpace(morkEnv* ev);
|
||||
|
@ -245,6 +249,43 @@ private: // copying is not allowed
|
|||
morkBookAtom& operator=(const morkBookAtom& other);
|
||||
};
|
||||
|
||||
/*| FarBookAtom: this alternative format for book atoms was introduced
|
||||
**| in May 2000 in order to support finding atoms in hash tables without
|
||||
**| first copying the strings from original parsing buffers into a new
|
||||
**| atom format. This was consuming too much time. However, we can
|
||||
**| use morkFarBookAtom to stage a hash table query, as long as we then
|
||||
**| fix HashFormAndBody() and EqualFormAndBody() to use morkFarBookAtom
|
||||
**| correctly.
|
||||
**|
|
||||
**|| Note we do NOT intend that instances of morkFarBookAtom will ever
|
||||
**| be installed in hash tables, because this is not space efficient.
|
||||
**| We only expect to create temp instances for table lookups.
|
||||
|*/
|
||||
class morkFarBookAtom : public morkBookAtom { //
|
||||
|
||||
// mork_u1 mAtom_Kind; // identifies a specific atom subclass
|
||||
// mork_u1 mAtom_CellUses; // number of persistent uses in a cell
|
||||
// mork_change mAtom_Change; // how has this atom been changed?
|
||||
// mork_u1 mAtom_Size; // NOT USED IN "BIG" format atoms
|
||||
|
||||
// morkAtomSpace* mBookAtom_Space; // mBookAtom_Space->SpaceScope() is scope
|
||||
// mork_aid mBookAtom_Id; // identity token for this shared atom
|
||||
|
||||
public:
|
||||
mork_cscode mFarBookAtom_Form; // charset format encoding
|
||||
mork_size mFarBookAtom_Size; // size of content vector
|
||||
mork_u1* mFarBookAtom_Body; // bytes are elsewere, out of line
|
||||
|
||||
public: // empty construction does nothing
|
||||
morkFarBookAtom() { }
|
||||
void InitFarBookAtom(morkEnv* ev, const morkBuf& inBuf,
|
||||
mork_cscode inForm, morkAtomSpace* ioSpace, mork_aid inAid);
|
||||
|
||||
private: // copying is not allowed
|
||||
morkFarBookAtom(const morkFarBookAtom& other);
|
||||
morkFarBookAtom& operator=(const morkFarBookAtom& other);
|
||||
};
|
||||
|
||||
/*| WeeBookAtom: .
|
||||
|*/
|
||||
class morkWeeBookAtom : public morkBookAtom { //
|
||||
|
@ -339,3 +380,4 @@ private: // copying is not allowed
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKATOM_ */
|
||||
|
||||
|
|
|
@ -174,7 +174,7 @@ morkAtomSpace::CutAllAtoms(morkEnv* ev, morkPool* ioPool)
|
|||
|
||||
morkBookAtom*
|
||||
morkAtomSpace::MakeBookAtomCopyWithAid(morkEnv* ev,
|
||||
const morkBigBookAtom& inAtom, mork_aid inAid)
|
||||
const morkFarBookAtom& inAtom, mork_aid inAid)
|
||||
// Make copy of inAtom and put it in both maps, using specified ID.
|
||||
{
|
||||
morkBookAtom* outAtom = 0;
|
||||
|
@ -182,7 +182,7 @@ morkAtomSpace::MakeBookAtomCopyWithAid(morkEnv* ev,
|
|||
if ( ev->Good() && store )
|
||||
{
|
||||
morkPool* pool = this->GetSpaceStorePool();
|
||||
outAtom = pool->NewBookAtomCopy(ev, inAtom, &store->mStore_Zone);
|
||||
outAtom = pool->NewFarBookAtomCopy(ev, inAtom, &store->mStore_Zone);
|
||||
if ( outAtom )
|
||||
{
|
||||
if ( store->mStore_CanDirty )
|
||||
|
@ -207,7 +207,7 @@ morkAtomSpace::MakeBookAtomCopyWithAid(morkEnv* ev,
|
|||
}
|
||||
|
||||
morkBookAtom*
|
||||
morkAtomSpace::MakeBookAtomCopy(morkEnv* ev, const morkBigBookAtom& inAtom)
|
||||
morkAtomSpace::MakeBookAtomCopy(morkEnv* ev, const morkFarBookAtom& inAtom)
|
||||
// make copy of inAtom and put it in both maps, using a new ID as needed.
|
||||
{
|
||||
morkBookAtom* outAtom = 0;
|
||||
|
@ -217,7 +217,7 @@ morkAtomSpace::MakeBookAtomCopy(morkEnv* ev, const morkBigBookAtom& inAtom)
|
|||
if ( store->mStore_CanAutoAssignAtomIdentity )
|
||||
{
|
||||
morkPool* pool = this->GetSpaceStorePool();
|
||||
morkBookAtom* atom = pool->NewBookAtomCopy(ev, inAtom, &mSpace_Store->mStore_Zone);
|
||||
morkBookAtom* atom = pool->NewFarBookAtomCopy(ev, inAtom, &mSpace_Store->mStore_Zone);
|
||||
if ( atom )
|
||||
{
|
||||
mork_aid id = this->MakeNewAtomId(ev, atom);
|
||||
|
@ -289,3 +289,4 @@ morkAtomSpaceMap::morkAtomSpaceMap(morkEnv* ev, const morkUsage& inUsage,
|
|||
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -151,10 +151,10 @@ public: // other space methods
|
|||
// CutAllAtoms() puts all the atoms back in the pool.
|
||||
|
||||
morkBookAtom* MakeBookAtomCopyWithAid(morkEnv* ev,
|
||||
const morkBigBookAtom& inAtom, mork_aid inAid);
|
||||
const morkFarBookAtom& inAtom, mork_aid inAid);
|
||||
// Make copy of inAtom and put it in both maps, using specified ID.
|
||||
|
||||
morkBookAtom* MakeBookAtomCopy(morkEnv* ev, const morkBigBookAtom& inAtom);
|
||||
morkBookAtom* MakeBookAtomCopy(morkEnv* ev, const morkFarBookAtom& inAtom);
|
||||
// Make copy of inAtom and put it in both maps, using a new ID as needed.
|
||||
|
||||
mork_aid MakeNewAtomId(morkEnv* ev, morkBookAtom* ioAtom);
|
||||
|
@ -233,3 +233,4 @@ public:
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKATOMSPACE_ */
|
||||
|
||||
|
|
|
@ -104,11 +104,11 @@
|
|||
|
||||
/* ===== separating switchable features ===== */
|
||||
|
||||
//define MORK_ENABLE_ZONE_ARENAS 1 /* using morkZone for pooling */
|
||||
#define MORK_ENABLE_ZONE_ARENAS 1 /* using morkZone for pooling */
|
||||
|
||||
//define MORK_ENABLE_PROBE_MAPS 1 /* use smaller hash tables */
|
||||
#define MORK_ENABLE_PROBE_MAPS 1 /* use smaller hash tables */
|
||||
|
||||
//define MORK_BEAD_OVER_NODE_MAPS 1 /* use bead not node maps */
|
||||
#define MORK_BEAD_OVER_NODE_MAPS 1 /* use bead not node maps */
|
||||
|
||||
/* ===== pooling ===== */
|
||||
|
||||
|
@ -209,3 +209,4 @@ MORK_LIB(mork_size) mork_strlen(const void* inString);
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKCONFIG_ */
|
||||
|
||||
|
|
|
@ -525,7 +525,7 @@ void
|
|||
morkParser::ReadCell(morkEnv* ev)
|
||||
{
|
||||
mParser_CellMid.ClearMid();
|
||||
this->StartSpanOnLastByte(ev, &mParser_CellSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_CellSpan);
|
||||
morkMid* cellMid = 0; // if mid syntax is used for column
|
||||
morkBuf* cellBuf = 0; // if naked string is used for column
|
||||
|
||||
|
@ -533,7 +533,7 @@ morkParser::ReadCell(morkEnv* ev)
|
|||
register int c;
|
||||
if ( (c = s->Getc(ev)) != EOF && ev->Good() )
|
||||
{
|
||||
this->StartSpanOnLastByte(ev, &mParser_ColumnSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_ColumnSpan);
|
||||
if ( c == '^' )
|
||||
{
|
||||
cellMid = &mParser_CellMid;
|
||||
|
@ -547,7 +547,7 @@ morkParser::ReadCell(morkEnv* ev)
|
|||
}
|
||||
if ( ev->Good() )
|
||||
{
|
||||
this->EndSpanOnThisByte(ev, &mParser_ColumnSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_ColumnSpan);
|
||||
|
||||
mParser_InCell = morkBool_kTrue;
|
||||
this->OnNewCell(ev, *mParser_CellSpan.AsPlace(),
|
||||
|
@ -556,13 +556,13 @@ morkParser::ReadCell(morkEnv* ev)
|
|||
mParser_CellChange = morkChange_kNil;
|
||||
if ( (c = this->NextChar(ev)) != EOF && ev->Good() )
|
||||
{
|
||||
this->StartSpanOnLastByte(ev, &mParser_SlotSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_SlotSpan);
|
||||
if ( c == '=' )
|
||||
{
|
||||
morkBuf* buf = this->ReadValue(ev);
|
||||
if ( buf )
|
||||
{
|
||||
this->EndSpanOnThisByte(ev, &mParser_SlotSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_SlotSpan);
|
||||
this->OnValue(ev, mParser_SlotSpan, *buf);
|
||||
}
|
||||
}
|
||||
|
@ -570,7 +570,7 @@ morkParser::ReadCell(morkEnv* ev)
|
|||
{
|
||||
if ( this->ReadMid(ev, &mParser_Mid) )
|
||||
{
|
||||
this->EndSpanOnThisByte(ev, &mParser_SlotSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_SlotSpan);
|
||||
if ( (c = this->NextChar(ev)) != EOF && ev->Good() )
|
||||
{
|
||||
if ( c != ')' )
|
||||
|
@ -593,7 +593,7 @@ morkParser::ReadCell(morkEnv* ev)
|
|||
}
|
||||
}
|
||||
|
||||
this->EndSpanOnThisByte(ev, &mParser_CellSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_CellSpan);
|
||||
mParser_InCell = morkBool_kFalse;
|
||||
this->OnCellEnd(ev, mParser_CellSpan);
|
||||
}
|
||||
|
@ -623,7 +623,7 @@ void morkParser::ReadRow(morkEnv* ev, int c)
|
|||
{
|
||||
if ( ev->Good() )
|
||||
{
|
||||
this->StartSpanOnLastByte(ev, &mParser_RowSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_RowSpan);
|
||||
if ( mParser_Change )
|
||||
mParser_RowChange = mParser_Change;
|
||||
|
||||
|
@ -683,7 +683,7 @@ void morkParser::ReadRow(morkEnv* ev, int c)
|
|||
mParser_Stream->Ungetc(c);
|
||||
}
|
||||
|
||||
this->EndSpanOnThisByte(ev, &mParser_RowSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_RowSpan);
|
||||
mParser_InRow = morkBool_kFalse;
|
||||
this->OnRowEnd(ev, mParser_RowSpan);
|
||||
|
||||
|
@ -710,7 +710,7 @@ void morkParser::ReadRow(morkEnv* ev, int c)
|
|||
s->Ungetc(c);
|
||||
}
|
||||
|
||||
this->EndSpanOnThisByte(ev, &mParser_RowSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_RowSpan);
|
||||
mParser_InRow = morkBool_kFalse;
|
||||
this->OnRowEnd(ev, mParser_RowSpan);
|
||||
}
|
||||
|
@ -728,7 +728,7 @@ void morkParser::ReadTable(morkEnv* ev)
|
|||
// zm:TableItem ::= zm:MetaTable | zm:RowRef | zm:Row
|
||||
// zm:MetaTable ::= zm:S? '{' zm:S? zm:Cell* zm:S? '}' /* meta attributes */
|
||||
{
|
||||
this->StartSpanOnLastByte(ev, &mParser_TableSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_TableSpan);
|
||||
|
||||
if ( mParser_Change )
|
||||
mParser_TableChange = mParser_Change;
|
||||
|
@ -787,7 +787,7 @@ void morkParser::ReadTable(morkEnv* ev)
|
|||
}
|
||||
}
|
||||
|
||||
this->EndSpanOnThisByte(ev, &mParser_TableSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_TableSpan);
|
||||
mParser_InTable = morkBool_kFalse;
|
||||
this->OnTableEnd(ev, mParser_TableSpan);
|
||||
|
||||
|
@ -930,7 +930,7 @@ void morkParser::ReadAlias(morkEnv* ev)
|
|||
// zm:Alias ::= zm:S? '(' ('#')? zm:Hex+ zm:S? zm:Value ')'
|
||||
// zm:Value ::= '=' ([^)$\] | '\' zm:NonCRLF | zm:Continue | zm:Dollar)*
|
||||
{
|
||||
this->StartSpanOnLastByte(ev, &mParser_AliasSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_AliasSpan);
|
||||
|
||||
int nextChar;
|
||||
mork_id hex = this->ReadHex(ev, &nextChar);
|
||||
|
@ -949,7 +949,7 @@ void morkParser::ReadAlias(morkEnv* ev)
|
|||
mParser_Mid.mMid_Buf = this->ReadValue(ev);
|
||||
if ( mParser_Mid.mMid_Buf )
|
||||
{
|
||||
this->EndSpanOnThisByte(ev, &mParser_AliasSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_AliasSpan);
|
||||
this->OnAlias(ev, mParser_AliasSpan, mParser_Mid);
|
||||
}
|
||||
}
|
||||
|
@ -963,7 +963,7 @@ void morkParser::ReadMeta(morkEnv* ev, int inEndMeta)
|
|||
// zm:MetaTable ::= zm:S? '{' zm:S? zm:Cell* zm:S? '}' /* meta attributes */
|
||||
// zm:MetaRow ::= zm:S? '[' zm:S? zm:Cell* zm:S? ']' /* meta attributes */
|
||||
{
|
||||
this->StartSpanOnLastByte(ev, &mParser_MetaSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_MetaSpan);
|
||||
mParser_InMeta = morkBool_kTrue;
|
||||
this->OnNewMeta(ev, *mParser_MetaSpan.AsPlace());
|
||||
|
||||
|
@ -1014,7 +1014,7 @@ void morkParser::ReadMeta(morkEnv* ev, int inEndMeta)
|
|||
}
|
||||
}
|
||||
|
||||
this->EndSpanOnThisByte(ev, &mParser_MetaSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_MetaSpan);
|
||||
mParser_InMeta = morkBool_kFalse;
|
||||
this->OnMetaEnd(ev, mParser_MetaSpan);
|
||||
}
|
||||
|
@ -1062,7 +1062,7 @@ mork_bool morkParser::FindGroupEnd(morkEnv* ev)
|
|||
{
|
||||
if ( c == '@' ) // maybe start of group ending?
|
||||
{
|
||||
this->EndSpanOnThisByte(ev, &mParser_GroupSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_GroupSpan);
|
||||
if ( (c = s->Getc(ev)) == '$' ) // '$' follows '@' ?
|
||||
{
|
||||
if ( (c = s->Getc(ev)) == '$' ) // '$' follows "@$" ?
|
||||
|
@ -1070,7 +1070,7 @@ mork_bool morkParser::FindGroupEnd(morkEnv* ev)
|
|||
if ( (c = s->Getc(ev)) == '}' )
|
||||
{
|
||||
foundEnd = this->ReadEndGroupId(ev);
|
||||
this->EndSpanOnThisByte(ev, &mParser_GroupSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_GroupSpan);
|
||||
|
||||
}
|
||||
else
|
||||
|
@ -1095,6 +1095,7 @@ void morkParser::ReadGroup(morkEnv* ev)
|
|||
register int c;
|
||||
if ( (c = s->Getc(ev)) == '@' )
|
||||
{
|
||||
// we really need the following span inside morkBuilder::OnNewGroup():
|
||||
this->StartSpanOnThisByte(ev, &mParser_GroupSpan);
|
||||
mork_pos startPos = mParser_GroupSpan.mSpan_Start.mPlace_Pos;
|
||||
|
||||
|
@ -1216,7 +1217,7 @@ void morkParser::ReadDict(morkEnv* ev)
|
|||
mParser_Change = morkChange_kNil;
|
||||
mParser_AtomChange = morkChange_kNil;
|
||||
|
||||
this->StartSpanOnLastByte(ev, &mParser_DictSpan);
|
||||
// this->StartSpanOnLastByte(ev, &mParser_DictSpan);
|
||||
mParser_InDict = morkBool_kTrue;
|
||||
this->OnNewDict(ev, *mParser_DictSpan.AsPlace());
|
||||
|
||||
|
@ -1239,7 +1240,7 @@ void morkParser::ReadDict(morkEnv* ev)
|
|||
}
|
||||
}
|
||||
|
||||
this->EndSpanOnThisByte(ev, &mParser_DictSpan);
|
||||
// this->EndSpanOnThisByte(ev, &mParser_DictSpan);
|
||||
mParser_InDict = morkBool_kFalse;
|
||||
this->OnDictEnd(ev, mParser_DictSpan);
|
||||
|
||||
|
@ -1476,3 +1477,4 @@ morkParser::ParseMore( // return count of bytes consumed now
|
|||
}
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -504,6 +504,19 @@ protected: // protected parser helper methods
|
|||
|
||||
void StartSpanOnThisByte(morkEnv* ev, morkSpan* ioSpan);
|
||||
|
||||
|
||||
// void EndSpanOnThisByte(morkEnv* ev, morkSpan* ioSpan)
|
||||
// { MORK_USED_2(ev,ioSpan); }
|
||||
|
||||
// void EndSpanOnLastByte(morkEnv* ev, morkSpan* ioSpan)
|
||||
// { MORK_USED_2(ev,ioSpan); }
|
||||
|
||||
// void StartSpanOnLastByte(morkEnv* ev, morkSpan* ioSpan)
|
||||
// { MORK_USED_2(ev,ioSpan); }
|
||||
|
||||
// void StartSpanOnThisByte(morkEnv* ev, morkSpan* ioSpan)
|
||||
// { MORK_USED_2(ev,ioSpan); }
|
||||
|
||||
int eat_line_break(morkEnv* ev, int inLast);
|
||||
int eat_line_continue(morkEnv* ev); // last char was '\\'
|
||||
int eat_comment(morkEnv* ev); // last char was '/'
|
||||
|
@ -532,3 +545,4 @@ public: // typesafe refcounting inlines calling inherited morkNode methods
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKPARSER_ */
|
||||
|
||||
|
|
|
@ -520,6 +520,43 @@ morkPool::NewBookAtomCopy(morkEnv* ev, const morkBigBookAtom& inAtom,
|
|||
return newAtom;
|
||||
}
|
||||
|
||||
morkBookAtom*
|
||||
morkPool::NewFarBookAtomCopy(morkEnv* ev, const morkFarBookAtom& inAtom,
|
||||
morkZone* ioZone)
|
||||
// make the smallest kind of book atom that can hold content in inAtom.
|
||||
// The inAtom parameter is often expected to be a staged book atom in
|
||||
// the store, which was used to search an atom space for existing atoms.
|
||||
{
|
||||
morkBookAtom* newAtom = 0;
|
||||
|
||||
mork_cscode form = inAtom.mFarBookAtom_Form;
|
||||
mork_fill fill = inAtom.mFarBookAtom_Size;
|
||||
mork_bool needBig = ( form || fill > 255 );
|
||||
mork_size size = ( needBig )?
|
||||
morkBigBookAtom::SizeForFill(fill) :
|
||||
morkWeeBookAtom::SizeForFill(fill);
|
||||
|
||||
#ifdef morkZone_CONFIG_ARENA
|
||||
// a zone 'chip' remembers no size, and so cannot be deallocated:
|
||||
newAtom = (morkBookAtom*) ioZone->ZoneNewChip(ev, size);
|
||||
#else /*morkZone_CONFIG_ARENA*/
|
||||
MORK_USED_1(ioZone);
|
||||
mPool_Heap->Alloc(ev->AsMdbEnv(), size, (void**) &newAtom);
|
||||
#endif /*morkZone_CONFIG_ARENA*/
|
||||
if ( newAtom )
|
||||
{
|
||||
morkBuf buf(inAtom.mFarBookAtom_Body, fill);
|
||||
if ( needBig )
|
||||
((morkBigBookAtom*) newAtom)->InitBigBookAtom(ev,
|
||||
buf, form, inAtom.mBookAtom_Space, inAtom.mBookAtom_Id);
|
||||
else
|
||||
((morkWeeBookAtom*) newAtom)->InitWeeBookAtom(ev,
|
||||
buf, inAtom.mBookAtom_Space, inAtom.mBookAtom_Id);
|
||||
}
|
||||
return newAtom;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -41,6 +41,7 @@ class morkHandle;
|
|||
class morkHandleFrame;
|
||||
class morkHandleFace; // just an opaque cookie type
|
||||
class morkBigBookAtom;
|
||||
class morkFarBookAtom;
|
||||
|
||||
#define morkDerived_kPool /*i*/ 0x706C /* ascii 'pl' */
|
||||
|
||||
|
@ -149,6 +150,11 @@ public: // other pool methods
|
|||
// make the smallest kind of book atom that can hold content in inAtom.
|
||||
// The inAtom parameter is often expected to be a staged book atom in
|
||||
// the store, which was used to search an atom space for existing atoms.
|
||||
|
||||
morkBookAtom* NewFarBookAtomCopy(morkEnv* ev, const morkFarBookAtom& inAtom, morkZone* ioZone);
|
||||
// make the smallest kind of book atom that can hold content in inAtom.
|
||||
// The inAtom parameter is often expected to be a staged book atom in
|
||||
// the store, which was used to search an atom space for existing atoms.
|
||||
|
||||
public: // typesafe refcounting inlines calling inherited morkNode methods
|
||||
static void SlotWeakPool(morkPool* me,
|
||||
|
@ -163,3 +169,4 @@ public: // typesafe refcounting inlines calling inherited morkNode methods
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKPOOL_ */
|
||||
|
||||
|
|
|
@ -458,6 +458,59 @@ morkRow::NewCell(morkEnv* ev, mdb_column inColumn,
|
|||
return (morkCell*) 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void morkRow::SeekColumn(morkEnv* ev, mdb_pos inPos,
|
||||
mdb_column* outColumn, mdbYarn* outYarn)
|
||||
{
|
||||
morkCell* cells = mRow_Cells;
|
||||
if ( cells && inPos < mRow_Length && inPos >= 0 )
|
||||
{
|
||||
morkCell* c = cells + inPos;
|
||||
if ( outColumn )
|
||||
*outColumn = c->GetColumn();
|
||||
if ( outYarn )
|
||||
c->mCell_Atom->GetYarn(outYarn); // nil atom works okay here
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( outColumn )
|
||||
*outColumn = 0;
|
||||
if ( outYarn )
|
||||
((morkAtom*) 0)->GetYarn(outYarn); // yes this will work
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
morkRow::NextColumn(morkEnv* ev, mdb_column* ioColumn, mdbYarn* outYarn)
|
||||
{
|
||||
morkCell* cells = mRow_Cells;
|
||||
if ( cells )
|
||||
{
|
||||
mork_column last = 0;
|
||||
mork_column inCol = *ioColumn;
|
||||
morkCell* end = cells + mRow_Length;
|
||||
while ( cells < end )
|
||||
{
|
||||
if ( inCol == last ) // found column?
|
||||
{
|
||||
if ( outYarn )
|
||||
cells->mCell_Atom->GetYarn(outYarn); // nil atom works okay here
|
||||
*ioColumn = cells->GetColumn();
|
||||
return; // stop, we are done
|
||||
}
|
||||
else
|
||||
{
|
||||
last = cells->GetColumn();
|
||||
++cells;
|
||||
}
|
||||
}
|
||||
}
|
||||
*ioColumn = 0;
|
||||
if ( outYarn )
|
||||
((morkAtom*) 0)->GetYarn(outYarn); // yes this will work
|
||||
}
|
||||
|
||||
morkCell*
|
||||
morkRow::CellAt(morkEnv* ev, mork_pos inPos) const
|
||||
{
|
||||
|
@ -798,6 +851,18 @@ void morkRow::CutColumn(morkEnv* ev, mdb_column inColumn)
|
|||
}
|
||||
}
|
||||
|
||||
morkAtom* morkRow::GetColumnAtom(morkEnv* ev, mdb_column inColumn)
|
||||
{
|
||||
if ( ev->Good() )
|
||||
{
|
||||
mork_pos pos = -1;
|
||||
morkCell* cell = this->GetCell(ev, inColumn, &pos);
|
||||
if ( cell )
|
||||
return cell->mCell_Atom;
|
||||
}
|
||||
return (morkAtom*) 0;
|
||||
}
|
||||
|
||||
void morkRow::AddColumn(morkEnv* ev, mdb_column inColumn,
|
||||
const mdbYarn* inYarn, morkStore* ioStore)
|
||||
{
|
||||
|
@ -885,3 +950,4 @@ morkRow::NewRowCellCursor(morkEnv* ev, mdb_pos inPos)
|
|||
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -105,6 +105,9 @@ public: // flags bit twiddling
|
|||
|
||||
mork_bool IsRowDirty() const
|
||||
{ return ( mRow_Flags & morkRow_kDirtyBit ) != 0; }
|
||||
|
||||
mork_bool IsRowUsed() const
|
||||
{ return mRow_GcUses != 0; }
|
||||
|
||||
public: // other row methods
|
||||
morkRow( ) { }
|
||||
|
@ -172,6 +175,13 @@ public: // external row methods
|
|||
void AddColumn(morkEnv* ev, mdb_column inColumn,
|
||||
const mdbYarn* inYarn, morkStore* ioStore);
|
||||
|
||||
morkAtom* GetColumnAtom(morkEnv* ev, mdb_column inColumn);
|
||||
|
||||
void NextColumn(morkEnv* ev, mdb_column* ioColumn, mdbYarn* outYarn);
|
||||
|
||||
void SeekColumn(morkEnv* ev, mdb_pos inPos,
|
||||
mdb_column* outColumn, mdbYarn* outYarn);
|
||||
|
||||
void CutColumn(morkEnv* ev, mdb_column inColumn);
|
||||
|
||||
morkRowCellCursor* NewRowCellCursor(morkEnv* ev, mdb_pos inPos);
|
||||
|
@ -229,3 +239,4 @@ private: // copying is not allowed
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKROW_ */
|
||||
|
||||
|
|
|
@ -404,8 +404,8 @@ morkStore::AcquireStoreHandle(morkEnv* ev)
|
|||
}
|
||||
|
||||
|
||||
morkMaxBookAtom*
|
||||
morkStore::StageAliasAsBookAtom(morkEnv* ev, const morkMid* inMid,
|
||||
morkFarBookAtom*
|
||||
morkStore::StageAliasAsFarBookAtom(morkEnv* ev, const morkMid* inMid,
|
||||
morkAtomSpace* ioSpace, mork_cscode inForm)
|
||||
{
|
||||
if ( inMid && inMid->mMid_Buf )
|
||||
|
@ -415,19 +415,22 @@ morkStore::StageAliasAsBookAtom(morkEnv* ev, const morkMid* inMid,
|
|||
if ( length <= morkBookAtom_kMaxBodySize )
|
||||
{
|
||||
mork_aid dummyAid = 1;
|
||||
mStore_BookAtom.InitMaxBookAtom(ev, *buf,
|
||||
//mStore_BookAtom.InitMaxBookAtom(ev, *buf,
|
||||
// inForm, ioSpace, dummyAid);
|
||||
|
||||
mStore_FarBookAtom.InitFarBookAtom(ev, *buf,
|
||||
inForm, ioSpace, dummyAid);
|
||||
return &mStore_BookAtom;
|
||||
return &mStore_FarBookAtom;
|
||||
}
|
||||
}
|
||||
else
|
||||
ev->NilPointerError();
|
||||
|
||||
return (morkMaxBookAtom*) 0;
|
||||
return (morkFarBookAtom*) 0;
|
||||
}
|
||||
|
||||
morkMaxBookAtom*
|
||||
morkStore::StageYarnAsBookAtom(morkEnv* ev, const mdbYarn* inYarn,
|
||||
morkFarBookAtom*
|
||||
morkStore::StageYarnAsFarBookAtom(morkEnv* ev, const mdbYarn* inYarn,
|
||||
morkAtomSpace* ioSpace)
|
||||
{
|
||||
if ( inYarn && inYarn->mYarn_Buf )
|
||||
|
@ -437,25 +440,22 @@ morkStore::StageYarnAsBookAtom(morkEnv* ev, const mdbYarn* inYarn,
|
|||
{
|
||||
morkBuf buf(inYarn->mYarn_Buf, length);
|
||||
mork_aid dummyAid = 1;
|
||||
mStore_BookAtom.InitMaxBookAtom(ev, buf,
|
||||
//mStore_BookAtom.InitMaxBookAtom(ev, buf,
|
||||
// inYarn->mYarn_Form, ioSpace, dummyAid);
|
||||
mStore_FarBookAtom.InitFarBookAtom(ev, buf,
|
||||
inYarn->mYarn_Form, ioSpace, dummyAid);
|
||||
return &mStore_BookAtom;
|
||||
return &mStore_FarBookAtom;
|
||||
}
|
||||
}
|
||||
else
|
||||
ev->NilPointerError();
|
||||
|
||||
return (morkMaxBookAtom*) 0;
|
||||
return (morkFarBookAtom*) 0;
|
||||
}
|
||||
|
||||
morkMaxBookAtom*
|
||||
morkStore::StageStringAsBookAtom(morkEnv* ev, const char* inString,
|
||||
morkFarBookAtom*
|
||||
morkStore::StageStringAsFarBookAtom(morkEnv* ev, const char* inString,
|
||||
mork_cscode inForm, morkAtomSpace* ioSpace)
|
||||
// StageStringAsBookAtom() returns &mStore_BookAtom if inString is small
|
||||
// enough, such that strlen(inString) < morkBookAtom_kMaxBodySize. And
|
||||
// content inside mStore_BookAtom will be the valid atom format for
|
||||
// inString. This method is the standard way to stage a string as an
|
||||
// atom for searching or adding new atoms into an atom space hash table.
|
||||
{
|
||||
if ( inString )
|
||||
{
|
||||
|
@ -464,14 +464,15 @@ morkStore::StageStringAsBookAtom(morkEnv* ev, const char* inString,
|
|||
{
|
||||
morkBuf buf(inString, length);
|
||||
mork_aid dummyAid = 1;
|
||||
mStore_BookAtom.InitMaxBookAtom(ev, buf, inForm, ioSpace, dummyAid);
|
||||
return &mStore_BookAtom;
|
||||
//mStore_BookAtom.InitMaxBookAtom(ev, buf, inForm, ioSpace, dummyAid);
|
||||
mStore_FarBookAtom.InitFarBookAtom(ev, buf, inForm, ioSpace, dummyAid);
|
||||
return &mStore_FarBookAtom;
|
||||
}
|
||||
}
|
||||
else
|
||||
ev->NilPointerError();
|
||||
|
||||
return (morkMaxBookAtom*) 0;
|
||||
return (morkFarBookAtom*) 0;
|
||||
}
|
||||
|
||||
morkAtomSpace* morkStore::LazyGetOidAtomSpace(morkEnv* ev)
|
||||
|
@ -727,8 +728,8 @@ morkStore::YarnToAtom(morkEnv* ev, const mdbYarn* inYarn)
|
|||
morkAtomSpace* groundSpace = this->LazyGetGroundAtomSpace(ev);
|
||||
if ( groundSpace )
|
||||
{
|
||||
morkMaxBookAtom* keyAtom =
|
||||
this->StageYarnAsBookAtom(ev, inYarn, groundSpace);
|
||||
morkFarBookAtom* keyAtom =
|
||||
this->StageYarnAsFarBookAtom(ev, inYarn, groundSpace);
|
||||
|
||||
if ( keyAtom )
|
||||
{
|
||||
|
@ -775,8 +776,8 @@ morkStore::MidToOid(morkEnv* ev, const morkMid& inMid, mdbOid* outOid)
|
|||
{
|
||||
mork_cscode form = 0; // default
|
||||
mork_aid aid = 1; // dummy
|
||||
mStore_BookAtom.InitMaxBookAtom(ev, *buf, form, groundSpace, aid);
|
||||
morkMaxBookAtom* keyAtom = &mStore_BookAtom;
|
||||
mStore_FarBookAtom.InitFarBookAtom(ev, *buf, form, groundSpace, aid);
|
||||
morkFarBookAtom* keyAtom = &mStore_FarBookAtom;
|
||||
morkAtomBodyMap* map = &groundSpace->mAtomSpace_AtomBodies;
|
||||
morkBookAtom* bookAtom = map->GetAtom(ev, keyAtom);
|
||||
if ( bookAtom )
|
||||
|
@ -961,8 +962,8 @@ morkStore::AddAlias(morkEnv* ev, const morkMid& inMid, mork_cscode inForm)
|
|||
morkAtomSpace* atomSpace = this->LazyGetAtomSpace(ev, oid->mOid_Scope);
|
||||
if ( atomSpace )
|
||||
{
|
||||
morkMaxBookAtom* keyAtom =
|
||||
this->StageAliasAsBookAtom(ev, &inMid, atomSpace, inForm);
|
||||
morkFarBookAtom* keyAtom =
|
||||
this->StageAliasAsFarBookAtom(ev, &inMid, atomSpace, inForm);
|
||||
if ( keyAtom )
|
||||
{
|
||||
morkAtomAidMap* map = &atomSpace->mAtomSpace_AtomAids;
|
||||
|
@ -1040,12 +1041,13 @@ morkStore::BufToToken(morkEnv* ev, const morkBuf* inBuf)
|
|||
morkAtomSpace* space = this->LazyGetGroundColumnSpace(ev);
|
||||
if ( space )
|
||||
{
|
||||
morkMaxBookAtom* keyAtom = 0;
|
||||
morkFarBookAtom* keyAtom = 0;
|
||||
if ( length <= morkBookAtom_kMaxBodySize )
|
||||
{
|
||||
mork_aid aid = 1; // dummy
|
||||
mStore_BookAtom.InitMaxBookAtom(ev, *inBuf, form, space, aid);
|
||||
keyAtom = &mStore_BookAtom;
|
||||
//mStore_BookAtom.InitMaxBookAtom(ev, *inBuf, form, space, aid);
|
||||
mStore_FarBookAtom.InitFarBookAtom(ev, *inBuf, form, space, aid);
|
||||
keyAtom = &mStore_FarBookAtom;
|
||||
}
|
||||
if ( keyAtom )
|
||||
{
|
||||
|
@ -1087,8 +1089,8 @@ morkStore::StringToToken(morkEnv* ev, const char* inTokenName)
|
|||
morkAtomSpace* groundSpace = this->LazyGetGroundColumnSpace(ev);
|
||||
if ( groundSpace )
|
||||
{
|
||||
morkMaxBookAtom* keyAtom =
|
||||
this->StageStringAsBookAtom(ev, inTokenName, form, groundSpace);
|
||||
morkFarBookAtom* keyAtom =
|
||||
this->StageStringAsFarBookAtom(ev, inTokenName, form, groundSpace);
|
||||
if ( keyAtom )
|
||||
{
|
||||
morkAtomBodyMap* map = &groundSpace->mAtomSpace_AtomBodies;
|
||||
|
@ -1129,8 +1131,8 @@ morkStore::QueryToken(morkEnv* ev, const char* inTokenName)
|
|||
morkAtomSpace* groundSpace = this->LazyGetGroundColumnSpace(ev);
|
||||
if ( groundSpace )
|
||||
{
|
||||
morkMaxBookAtom* keyAtom =
|
||||
this->StageStringAsBookAtom(ev, inTokenName, form, groundSpace);
|
||||
morkFarBookAtom* keyAtom =
|
||||
this->StageStringAsFarBookAtom(ev, inTokenName, form, groundSpace);
|
||||
if ( keyAtom )
|
||||
{
|
||||
morkAtomBodyMap* map = &groundSpace->mAtomSpace_AtomBodies;
|
||||
|
@ -1334,3 +1336,4 @@ morkStore::OidToTable(morkEnv* ev, const mdbOid* inOid,
|
|||
}
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -178,7 +178,9 @@ public: // state is public because the entire Mork system is private
|
|||
morkPool mStore_Pool;
|
||||
|
||||
// we alloc a max size book atom to reuse space for atom map key searches:
|
||||
morkMaxBookAtom mStore_BookAtom; // staging area for atom map searches
|
||||
// morkMaxBookAtom mStore_BookAtom; // staging area for atom map searches
|
||||
|
||||
morkFarBookAtom mStore_FarBookAtom; // staging area for atom map searches
|
||||
|
||||
// GroupIdentity should be one more than largest seen in a parsed db file:
|
||||
mork_gid mStore_CommitGroupIdentity; // transaction ID number
|
||||
|
@ -241,21 +243,16 @@ public: // setting store and all subspaces canDirty:
|
|||
|
||||
void SetStoreAndAllSpacesCanDirty(morkEnv* ev, mork_bool inCanDirty);
|
||||
|
||||
public: // building an atom inside mStore_BookAtom from a char* string
|
||||
public: // building an atom inside mStore_FarBookAtom from a char* string
|
||||
|
||||
morkMaxBookAtom* StageAliasAsBookAtom(morkEnv* ev,
|
||||
morkFarBookAtom* StageAliasAsFarBookAtom(morkEnv* ev,
|
||||
const morkMid* inMid, morkAtomSpace* ioSpace, mork_cscode inForm);
|
||||
|
||||
morkMaxBookAtom* StageYarnAsBookAtom(morkEnv* ev,
|
||||
morkFarBookAtom* StageYarnAsFarBookAtom(morkEnv* ev,
|
||||
const mdbYarn* inYarn, morkAtomSpace* ioSpace);
|
||||
|
||||
morkMaxBookAtom* StageStringAsBookAtom(morkEnv* ev,
|
||||
morkFarBookAtom* StageStringAsFarBookAtom(morkEnv* ev,
|
||||
const char* inString, mork_cscode inForm, morkAtomSpace* ioSpace);
|
||||
// StageStringAsBookAtom() returns &mStore_BookAtom if inString is small
|
||||
// enough, such that strlen(inString) < morkBookAtom_kMaxBodySize. And
|
||||
// content inside mStore_BookAtom will be the valid atom format for
|
||||
// inString. This method is the standard way to stage a string as an
|
||||
// atom for searching or adding new atoms into an atom space hash table.
|
||||
|
||||
public: // determining whether incremental writing is a good use of time:
|
||||
|
||||
|
@ -410,3 +407,4 @@ public: // typesafe refcounting inlines calling inherited morkNode methods
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKSTORE_ */
|
||||
|
||||
|
|
|
@ -827,3 +827,4 @@ morkTableMap::morkTableMap(morkEnv* ev, const morkUsage& inUsage,
|
|||
}
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -143,7 +143,7 @@ public: // state is public because the entire Mork system is private
|
|||
mork_u1 mTable_Pad; // for u4 alignment
|
||||
|
||||
public: // flags bit twiddling
|
||||
|
||||
|
||||
void SetTableUnique() { mTable_Flags |= morkTable_kUniqueBit; }
|
||||
void SetTableVerbose() { mTable_Flags |= morkTable_kVerboseBit; }
|
||||
void SetTableNoted() { mTable_Flags |= morkTable_kNotedBit; }
|
||||
|
@ -260,6 +260,9 @@ public: // other table methods
|
|||
|
||||
mork_count GetRowCount() const { return mTable_RowArray.mArray_Fill; }
|
||||
|
||||
mork_bool IsTableUsed() const
|
||||
{ return (mTable_GcUses != 0 || this->GetRowCount() != 0); }
|
||||
|
||||
void GetTableOid(morkEnv* ev, mdbOid* outOid);
|
||||
mork_pos ArrayHasOid(morkEnv* ev, const mdbOid* inOid);
|
||||
mork_bool MapHasOid(morkEnv* ev, const mdbOid* inOid);
|
||||
|
@ -441,3 +444,4 @@ public:
|
|||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _MORKTABLE_ */
|
||||
|
||||
|
|
|
@ -547,7 +547,56 @@ morkWriter::WriteAtomSpaceAsDict(morkEnv* ev, morkAtomSpace* ioSpace)
|
|||
++mWriter_LineSize;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
(I'm putting the text of this message in file morkWriter.cpp.)
|
||||
|
||||
I'm making a change which should cause rows and tables to go away
|
||||
when a Mork db is compress committed, when the rows and tables
|
||||
are no longer needed. Because this is subtle, I'm describing it
|
||||
here in case misbehavior is ever observed. Otherwise you'll have
|
||||
almost no hope of fixing a related bug.
|
||||
|
||||
This is done entirely in morkWriter.cpp: morkWriter::DirtyAll(),
|
||||
which currently marks all rows and tables dirty so they will be
|
||||
written in a later phase of the commit. My change is to merely
|
||||
selectively not mark certain rows and tables dirty, when they seem
|
||||
to be superfluous.
|
||||
|
||||
A row is no longer needed when the mRow_GcUses slot hits zero, and
|
||||
this is used by the following inline morkRow method:
|
||||
|
||||
mork_bool IsRowUsed() const { return mRow_GcUses != 0; }
|
||||
|
||||
Naturally disaster ensues if mRow_GcUses is ever smaller than right.
|
||||
|
||||
Similarly, we should drop tables when mTable_GcUses hits zero, but
|
||||
only when a table contains no row members. We consider tables to
|
||||
self reference (and prevent collection) when they contain content.
|
||||
Again, disaster ensues if mTable_GcUses is ever smaller than right.
|
||||
|
||||
mork_count GetRowCount() const
|
||||
{ return mTable_RowArray.mArray_Fill; }
|
||||
|
||||
mork_bool IsTableUsed() const
|
||||
{ return (mTable_GcUses != 0 || this->GetRowCount() != 0); }
|
||||
|
||||
Now let's question why the design involves filtering what gets set
|
||||
to dirty. Why not apply a filter in the later phase when we write
|
||||
content? Because I'm afraid of missing some subtle interaction in
|
||||
updating table and row relationships. It seems safer to write a row
|
||||
or table when it starts out dirty, before morkWriter::DirtyAll() is
|
||||
called. So this design calls for writing out rows and tables when
|
||||
they are still clearly used, and additionally, <i>when we have just
|
||||
been actively writing to them right before this commit</i>.
|
||||
|
||||
Presumably if they are truly useless, they will no longer be dirtied
|
||||
in later sessions and will get collected during the next compress
|
||||
commit. So we wait to collect them until they become all dead, and
|
||||
not just mostly dead. (At which time you can feel free to go through
|
||||
their pockets looking for loose change.)
|
||||
*/
|
||||
|
||||
mork_bool
|
||||
morkWriter::DirtyAll(morkEnv* ev)
|
||||
// DirtyAll() visits every store sub-object and marks
|
||||
|
@ -638,10 +687,13 @@ morkWriter::DirtyAll(morkEnv* ev)
|
|||
for ( c = ri->FirstRow(ev, &row); c && ev->Good();
|
||||
c = ri->NextRow(ev, &row) )
|
||||
{
|
||||
if ( row && row->IsRow() )
|
||||
if ( row && row->IsRow() ) // need to dirty row?
|
||||
{
|
||||
row->DirtyAllRowContent(ev);
|
||||
++mWriter_TotalCount;
|
||||
if ( row->IsRowUsed() || row->IsRowDirty() )
|
||||
{
|
||||
row->DirtyAllRowContent(ev);
|
||||
++mWriter_TotalCount;
|
||||
}
|
||||
}
|
||||
else
|
||||
row->NonRowTypeWarning(ev);
|
||||
|
@ -666,13 +718,16 @@ morkWriter::DirtyAll(morkEnv* ev)
|
|||
c = ti->NextTable(ev, tableKey, &table) )
|
||||
#endif /*MORK_BEAD_OVER_NODE_MAPS*/
|
||||
{
|
||||
if ( table && table->IsTable() )
|
||||
if ( table && table->IsTable() ) // need to dirty table?
|
||||
{
|
||||
// table->DirtyAllTableContent(ev);
|
||||
// only necessary to mark table itself dirty:
|
||||
table->SetTableDirty();
|
||||
table->SetTableRewrite();
|
||||
++mWriter_TotalCount;
|
||||
if ( table->IsTableUsed() || table->IsTableDirty() )
|
||||
{
|
||||
// table->DirtyAllTableContent(ev);
|
||||
// only necessary to mark table itself dirty:
|
||||
table->SetTableDirty();
|
||||
table->SetTableRewrite();
|
||||
++mWriter_TotalCount;
|
||||
}
|
||||
}
|
||||
else
|
||||
table->NonTableTypeWarning(ev);
|
||||
|
@ -1043,7 +1098,7 @@ morkWriter::WriteAllStoreTables(morkEnv* ev)
|
|||
if ( row && row->IsRow() )
|
||||
{
|
||||
// later we should also check that table use count is nonzero:
|
||||
if ( row->IsRowDirty() )
|
||||
if ( row->IsRowDirty() ) // && row->IsRowUsed() ??
|
||||
{
|
||||
mWriter_BeVerbose = ev->mEnv_BeVerbose;
|
||||
if ( this->PutRowDict(ev, row) )
|
||||
|
@ -2107,3 +2162,4 @@ morkWriter::PutRow(morkEnv* ev, morkRow* ioRow)
|
|||
}
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -36,6 +36,10 @@
|
|||
#include "morkHandle.h"
|
||||
#endif
|
||||
|
||||
#ifndef _MORKATOM_
|
||||
#include "morkAtom.h"
|
||||
#endif
|
||||
|
||||
#ifndef _MORKROW_
|
||||
#include "morkRow.h"
|
||||
#endif
|
||||
|
@ -688,8 +692,142 @@ orkinRow::SetRow( // make exact duplicate of another row
|
|||
}
|
||||
// } ----- end row methods -----
|
||||
|
||||
// { ----- begin blob methods -----
|
||||
/*virtual*/ mdb_err
|
||||
orkinRow::SetCellYarn( // synonym for AddColumn()
|
||||
nsIMdbEnv* mev, // context
|
||||
mdb_column inColumn, // column to add
|
||||
const mdbYarn* inYarn)
|
||||
{
|
||||
mdb_err outErr = 0;
|
||||
morkRow* row = 0;
|
||||
morkEnv* ev = this->CanUseRow(mev, /*inMutable*/ morkBool_kFalse,
|
||||
&outErr, &row);
|
||||
if ( ev )
|
||||
{
|
||||
morkStore* store = this->CanUseRowStore(ev);
|
||||
if ( store )
|
||||
row->AddColumn(ev, inColumn, inYarn, store);
|
||||
|
||||
outErr = ev->AsErr();
|
||||
}
|
||||
return outErr;
|
||||
}
|
||||
/*virtual*/ mdb_err
|
||||
orkinRow::GetCellYarn(
|
||||
nsIMdbEnv* mev, // context
|
||||
mdb_column inColumn, // column to read
|
||||
mdbYarn* outYarn) // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
{
|
||||
mdb_err outErr = 0;
|
||||
morkRow* row = 0;
|
||||
morkEnv* ev = this->CanUseRow(mev, /*inMutable*/ morkBool_kFalse,
|
||||
&outErr, &row);
|
||||
if ( ev )
|
||||
{
|
||||
morkStore* store = this->CanUseRowStore(ev);
|
||||
if ( store )
|
||||
{
|
||||
morkAtom* atom = row->GetColumnAtom(ev, inColumn);
|
||||
atom->GetYarn(outYarn);
|
||||
// note nil atom works and sets yarn correctly
|
||||
}
|
||||
|
||||
outErr = ev->AsErr();
|
||||
}
|
||||
return outErr;
|
||||
}
|
||||
|
||||
/*virtual*/ mdb_err
|
||||
orkinRow::AliasCellYarn(
|
||||
nsIMdbEnv* mev, // context
|
||||
mdb_column inColumn, // column to alias
|
||||
mdbYarn* outYarn) // writes ALL yarn slots
|
||||
{
|
||||
mdb_err outErr = 0;
|
||||
morkRow* row = 0;
|
||||
morkEnv* ev = this->CanUseRow(mev, /*inMutable*/ morkBool_kFalse,
|
||||
&outErr, &row);
|
||||
if ( ev )
|
||||
{
|
||||
morkStore* store = this->CanUseRowStore(ev);
|
||||
if ( store )
|
||||
{
|
||||
morkAtom* atom = row->GetColumnAtom(ev, inColumn);
|
||||
atom->AliasYarn(outYarn);
|
||||
// note nil atom works and sets yarn correctly
|
||||
}
|
||||
outErr = ev->AsErr();
|
||||
}
|
||||
return outErr;
|
||||
}
|
||||
|
||||
/*virtual*/ mdb_err
|
||||
orkinRow::NextCellYarn(nsIMdbEnv* mev, // iterative version of GetCellYarn()
|
||||
mdb_column* ioColumn, // next column to read
|
||||
mdbYarn* outYarn) // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
//
|
||||
// The ioColumn argument is an inout parameter which initially contains the
|
||||
// last column accessed and returns the next column corresponding to the
|
||||
// content read into the yarn. Callers should start with a zero column
|
||||
// value to say 'no previous column', which causes the first column to be
|
||||
// read. Then the value returned in ioColumn is perfect for the next call
|
||||
// to NextCellYarn(), since it will then be the previous column accessed.
|
||||
// Callers need only examine the column token returned to see which cell
|
||||
// in the row is being read into the yarn. When no more columns remain,
|
||||
// and the iteration has ended, ioColumn will return a zero token again.
|
||||
// So iterating over cells starts and ends with a zero column token.
|
||||
{
|
||||
mdb_err outErr = 0;
|
||||
morkRow* row = 0;
|
||||
morkEnv* ev = this->CanUseRow(mev, /*inMutable*/ morkBool_kFalse,
|
||||
&outErr, &row);
|
||||
if ( ev )
|
||||
{
|
||||
morkStore* store = this->CanUseRowStore(ev);
|
||||
if ( store )
|
||||
row->NextColumn(ev, ioColumn, outYarn);
|
||||
|
||||
outErr = ev->AsErr();
|
||||
}
|
||||
return outErr;
|
||||
}
|
||||
|
||||
/*virtual*/ mdb_err
|
||||
orkinRow::SeekCellYarn( // resembles nsIMdbRowCellCursor::SeekCell()
|
||||
nsIMdbEnv* mev, // context
|
||||
mdb_pos inPos, // position of cell in row sequence
|
||||
mdb_column* outColumn, // column for this particular cell
|
||||
mdbYarn* outYarn) // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
// Callers can pass nil for outYarn to indicate no interest in content, so
|
||||
// only the outColumn value is returned. NOTE to subclasses: you must be
|
||||
// able to ignore outYarn when the pointer is nil; please do not crash.
|
||||
|
||||
{
|
||||
mdb_err outErr = 0;
|
||||
morkRow* row = 0;
|
||||
morkEnv* ev = this->CanUseRow(mev, /*inMutable*/ morkBool_kFalse,
|
||||
&outErr, &row);
|
||||
if ( ev )
|
||||
{
|
||||
morkStore* store = this->CanUseRowStore(ev);
|
||||
if ( store )
|
||||
row->SeekColumn(ev, inPos, outColumn, outYarn);
|
||||
|
||||
outErr = ev->AsErr();
|
||||
}
|
||||
return outErr;
|
||||
}
|
||||
|
||||
// } ----- end blob methods -----
|
||||
|
||||
|
||||
// } ===== end nsIMdbRow methods =====
|
||||
|
||||
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
|
|
|
@ -224,9 +224,53 @@ public: // type identification
|
|||
nsIMdbRow* ioSourceRow); // row to duplicate
|
||||
// } ----- end row methods -----
|
||||
|
||||
// { ----- begin blob methods -----
|
||||
virtual mdb_err SetCellYarn(nsIMdbEnv* ev, // synonym for AddColumn()
|
||||
mdb_column inColumn, // column to write
|
||||
const mdbYarn* inYarn); // reads from yarn slots
|
||||
// make this text object contain content from the yarn's buffer
|
||||
|
||||
virtual mdb_err GetCellYarn(nsIMdbEnv* ev,
|
||||
mdb_column inColumn, // column to read
|
||||
mdbYarn* outYarn); // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
|
||||
virtual mdb_err AliasCellYarn(nsIMdbEnv* ev,
|
||||
mdb_column inColumn, // column to alias
|
||||
mdbYarn* outYarn); // writes ALL yarn slots
|
||||
|
||||
virtual mdb_err NextCellYarn(nsIMdbEnv* ev, // iterative version of GetCellYarn()
|
||||
mdb_column* ioColumn, // next column to read
|
||||
mdbYarn* outYarn); // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
//
|
||||
// The ioColumn argument is an inout parameter which initially contains the
|
||||
// last column accessed and returns the next column corresponding to the
|
||||
// content read into the yarn. Callers should start with a zero column
|
||||
// value to say 'no previous column', which causes the first column to be
|
||||
// read. Then the value returned in ioColumn is perfect for the next call
|
||||
// to NextCellYarn(), since it will then be the previous column accessed.
|
||||
// Callers need only examine the column token returned to see which cell
|
||||
// in the row is being read into the yarn. When no more columns remain,
|
||||
// and the iteration has ended, ioColumn will return a zero token again.
|
||||
// So iterating over cells starts and ends with a zero column token.
|
||||
|
||||
virtual mdb_err SeekCellYarn( // resembles nsIMdbRowCellCursor::SeekCell()
|
||||
nsIMdbEnv* ev, // context
|
||||
mdb_pos inPos, // position of cell in row sequence
|
||||
mdb_column* outColumn, // column for this particular cell
|
||||
mdbYarn* outYarn); // writes some yarn slots
|
||||
// copy content into the yarn buffer, and update mYarn_Fill and mYarn_Form
|
||||
// Callers can pass nil for outYarn to indicate no interest in content, so
|
||||
// only the outColumn value is returned. NOTE to subclasses: you must be
|
||||
// able to ignore outYarn when the pointer is nil; please do not crash.
|
||||
|
||||
// } ----- end blob methods -----
|
||||
|
||||
// } ===== end nsIMdbRow methods =====
|
||||
};
|
||||
|
||||
//3456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789
|
||||
|
||||
#endif /* _ORKINROW_ */
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче