1 // Copyright (c) 1996 James Clark
2 // See the file copying.txt for copying permission.
4 #ifndef Interpreter_INCLUDED
5 #define Interpreter_INCLUDED 1
8 #include "Expression.h"
10 #include "PointerTable.h"
11 #include "NamedTable.h"
12 #include "Collector.h"
13 #include "InputSource.h"
17 #include "SosofoObj.h"
18 #include "ProcessingMode.h"
19 #include "NumberCache.h"
20 #include "HashTable.h"
21 #include "FOTBuilder.h"
25 #include "GroveManager.h"
29 #ifdef DSSSL_NAMESPACE
30 namespace DSSSL_NAMESPACE {
35 class Identifier : public Named {
71 keyDeclareInitialValue,
72 keyDeclareCharacteristic,
73 keyDeclareFlowObjectClass,
74 keyDeclareCharCharacteristicAndProperty,
75 keyDeclareReferenceValueType,
76 keyDeclareDefaultLanguage,
77 keyDeclareCharProperty,
79 keyDefineColumnSetModel,
85 keyIsKeepWithPrevious,
106 keyEscapementDirection,
107 keyBreakBeforePriority,
108 keyBreakAfterPriority,
116 keyIsInputWhitespace,
118 keyIsDropAfterLineBreak,
119 keyIsDropUnlessBeforeLineBreak,
127 keyIsMayViolateKeepBefore,
128 keyIsMayViolateKeepAfter,
131 keyBeforeColumnBorder,
132 keyAfterColumnBorder,
161 keyDeclareClassAttribute,
162 keyDeclareIdAttribute,
163 keyDeclareFlowObjectMacro,
165 keyPositionPreference,
187 enum { lastSyntacticKey = keyWithMode };
188 Identifier(const StringC &name);
189 // Return 0 is value can't yet be computed.
190 ELObj *computeValue(bool force, Interpreter &) const;
191 ELObj *computeBuiltinValue(bool force, Interpreter &) const;
192 bool syntacticKey(SyntacticKey &) const;
193 void setSyntacticKey(SyntacticKey);
194 bool defined(unsigned &, Location &) const;
195 void setDefinition(Owner<Expression> &, unsigned part,
197 void setValue(ELObj *, unsigned defPart = unsigned(-1));
198 bool evaluated() const;
199 const ConstPtr<InheritedC> &inheritedC() const;
200 bool inheritedCDefined(unsigned &, Location &) const;
201 bool charNICDefined(unsigned &, Location &) const;
202 void setCharNIC(unsigned, const Location &);
203 void setInheritedC(const ConstPtr<InheritedC> &);
204 void setInheritedC(const ConstPtr<InheritedC> &, unsigned, const Location &);
205 FlowObj *flowObj() const;
206 bool flowObjDefined(unsigned &, Location &) const;
207 void setFlowObj(FlowObj *);
208 void setFlowObj(FlowObj *, unsigned part, const Location &);
211 Owner<Expression> def_;
213 // Value in top-level environment.
214 ELObj *value_; // must be permanent
215 FlowObj *flowObj_; // prototype FlowObj with this name
216 unsigned flowObjPart_;
217 Location flowObjLoc_;
219 SyntacticKey syntacticKey_;
222 ConstPtr<InheritedC> inheritedC_;
223 unsigned inheritedCPart_;
224 Location inheritedCLoc_;
225 void maybeSaveBuiltin();
226 Identifier *builtin_;
227 static bool preferBuiltin_;
230 class Unit : public Named {
232 Unit(const StringC &);
234 void setValue(double);
235 bool defined(unsigned &, Location &) const;
236 // return 0 if it can't be done
237 ELObj *resolveQuantity(bool force, Interpreter &, double val, int unitExp);
238 ELObj *resolveQuantity(bool force, Interpreter &, long val, int valExp);
239 void setDefinition(Owner<Expression> &, unsigned part, const Location &);
241 void tryCompute(bool force, Interpreter &);
242 static bool scale(long val, int valExp, long num, long &result);
246 Owner<Expression> def_;
262 class ELObjDynamicRoot : public Collector::DynamicRoot {
264 ELObjDynamicRoot(Collector &c, ELObj *obj = 0)
265 : Collector::DynamicRoot(c), obj_(obj) { }
266 void operator=(ELObj *obj) { obj_ = obj; }
267 operator ELObj *() const { return obj_; }
269 void trace(Collector &) const;
280 ELObjPart(ELObj *x, unsigned y);
281 void operator=(const ELObjPart &);
282 bool operator==(const ELObjPart &) const;
283 bool operator!=(const ELObjPart &) const;
289 CharMap<ELObjPart> *map;
296 public Pattern::MatchContext,
320 enum { nPortNames = portFooter + 1 };
321 Interpreter(GroveManager *, Messenger *, int unitsPerInch, bool debugMode,
322 bool dsssl2, bool strictMode, const FOTBuilder::Extension *);
325 FalseObj *makeFalse();
328 SymbolObj *makeSymbol(const StringC &);
329 KeywordObj *makeKeyword(const StringC &);
330 IntegerObj *makeInteger(long n);
331 ErrorObj *makeError();
332 UnspecifiedObj *makeUnspecified();
333 PairObj *makePair(ELObj *, ELObj *);
334 ELObj *convertGlyphId(const Char *, size_t, const Location &);
335 bool isError(const ELObj *) const;
336 bool isUnspecified(const ELObj *) const;
337 CharObj *makeChar(Char);
338 ELObj *makeLengthSpec(const FOTBuilder::LengthSpec &);
339 AddressObj *makeAddressNone();
340 NodeListObj *makeEmptyNodeList();
341 void dispatchMessage(Message &);
342 void dispatchMessage(const Message &);
343 Identifier *lookup(const StringC &);
344 Unit *lookupUnit(const StringC &);
345 FunctionObj *lookupExternalProc(const StringC &);
346 int unitsPerInch() const;
347 unsigned currentPartIndex() const;
349 static StringC makeStringC(const char *);
350 SymbolObj *portName(PortName);
351 ELObj *cValueSymbol(FOTBuilder::Symbol);
352 ELObj *charProperty(const StringC &, Char, const Location &, ELObj *);
353 void addCharProperty(const Identifier *, Owner<Expression> &);
354 void setCharProperty(const Identifier *, Char, Owner<Expression> &);
355 void compileCharProperties();
356 // Map of LexCategory
357 XcharMap<char> lexCategory_;
358 static void normalizeGeneralName(const NodePtr &, StringC &);
359 GroveManager *groveManager() const;
360 StyleObj *initialStyle() const;
361 StyleObj *borderTrueStyle() const;
362 StyleObj *borderFalseStyle() const;
363 bool convertBooleanC(ELObj *, const Identifier *, const Location &, bool &);
364 bool convertPublicIdC(ELObj *, const Identifier *, const Location &,
365 FOTBuilder::PublicId &);
366 bool convertStringC(ELObj *, const Identifier *, const Location &, StringC &);
367 bool convertLengthC(ELObj *, const Identifier *, const Location &, FOTBuilder::Length &);
368 bool convertLengthSpecC(ELObj *, const Identifier *, const Location &, FOTBuilder::LengthSpec &);
369 bool convertLetter2C(ELObj *, const Identifier *, const Location &, FOTBuilder::Letter2 &);
370 bool convertOptLengthSpecC(ELObj *, const Identifier *, const Location &, FOTBuilder::OptLengthSpec &);
371 bool convertCharC(ELObj *, const Identifier *, const Location &, Char &);
372 bool convertColorC(ELObj *, const Identifier *, const Location &, ColorObj *&);
373 bool convertOptColorC(ELObj *, const Identifier *, const Location &, ColorObj *&);
374 // FIXME allow inexact value
375 bool convertIntegerC(ELObj *, const Identifier *, const Location &, long &);
376 bool convertOptPositiveIntegerC(ELObj *, const Identifier *, const Location &, long &);
377 bool convertRealC(ELObj *, const Identifier *, const Location &, double &);
378 bool convertEnumC(const FOTBuilder::Symbol *, size_t,
379 ELObj *, const Identifier *, const Location &, FOTBuilder::Symbol &);
380 bool convertEnumC(ELObj *, const Identifier *, const Location &, FOTBuilder::Symbol &);
381 void invalidCharacteristicValue(const Identifier *ident, const Location &loc);
382 bool convertLengthSpec(ELObj *, FOTBuilder::LengthSpec &);
383 bool convertToPattern(ELObj *, const Location &, Pattern &);
384 const ConstPtr<InheritedC> &tableBorderC() const;
385 const ConstPtr<InheritedC> &cellBeforeRowBorderC() const;
386 const ConstPtr<InheritedC> &cellAfterRowBorderC() const;
387 const ConstPtr<InheritedC> &cellBeforeColumnBorderC() const;
388 const ConstPtr<InheritedC> &cellAfterColumnBorderC() const;
389 const ConstPtr<InheritedC> &fractionBarC() const;
390 const char *storePublicId(const Char *, size_t, const Location &);
391 unsigned allocGlyphSubstTableUniqueId();
392 bool lookupNodeProperty(const StringC &, ComponentName::Id &);
393 bool debugMode() const;
395 bool strictMode() const;
396 void setNodeLocation(const NodePtr &);
397 void setDefaultLanguage(Owner<Expression> &,unsigned part,const Location &);
398 ELObj *defaultLanguage() const;
399 bool defaultLanguageSet(unsigned &,Location &) const;
400 void compileDefaultLanguage();
401 void makeReadOnly(ELObj *);
402 ProcessingMode *lookupProcessingMode(const StringC &);
403 ProcessingMode *initialProcessingMode();
404 void addClassAttributeName(const StringC &name);
405 void addIdAttributeName(const StringC &name);
406 void installInitialValue(Identifier *, Owner<Expression> &);
407 void installExtensionInheritedC(Identifier *, const StringC &, const Location &);
408 void installExtensionCharNIC(Identifier *, const StringC &, const Location &);
409 void installExtensionFlowObjectClass(Identifier *, const StringC &, const Location &);
410 // Return 0 if an invalid number.
411 ELObj *convertNumber(const StringC &, int radix = 10);
412 bool convertCharName(const StringC &str, Char &c) const;
414 lexLetter, // a - z A - Z
415 lexOtherNameStart, // !$%&*/<=>?~_^:
418 lexOtherNumberStart, // -+.
420 lexDelimiter, // ;()"
424 LexCategory lexCategory(Xchar);
425 void addStandardChar(const StringC &, const StringC &);
426 void addSdataEntity(const StringC &, const StringC &, const StringC &);
427 void addNameChar(const StringC &);
428 void addSeparatorChar(const StringC &);
429 void setCharRepertoire(const StringC &);
431 Interpreter(const Interpreter &); // undefined
432 void operator=(const Interpreter &); // undefined
433 void installSyntacticKeys();
434 void installPortNames();
435 void installCValueSymbols();
436 void installPrimitives();
437 void installPrimitive(const char *, PrimitiveObj *);
438 void installXPrimitive(const char *, const char *, PrimitiveObj *);
439 void installBuiltins();
441 void installCharNames();
442 void installInheritedCs();
443 void installInheritedC(const char *, InheritedC *);
444 void installInheritedCProc(const Identifier *);
445 void installFlowObjs();
447 void installNodeProperties();
448 void installCharProperties();
449 void compileInitialValues();
450 bool sdataMap(GroveString, GroveString, GroveChar &) const;
451 static bool convertUnicodeCharName(const StringC &str, Char &c);
452 bool convertToPattern(ELObj *obj, const Location &loc,
453 bool isChild, IList<Pattern::Element> &list);
454 bool patternAddAttributeQualifiers(ELObj *obj,
456 Pattern::Element &elem);
458 convertAllowBoolean = 01,
459 convertAllowSymbol = 02,
460 convertAllowNumber = 04
462 ELObj *convertFromString(ELObj *, unsigned hints, const Location &);
463 ELObj *convertNumberFloat(const StringC &);
464 bool scanSignDigits(const StringC &str, size_t &i, int &n);
465 Unit *scanUnit(const StringC &str, size_t i, int &unitExp);
468 TrueObj *theTrueObj_;
469 FalseObj *theFalseObj_;
470 ErrorObj *theErrorObj_;
471 UnspecifiedObj *theUnspecifiedObj_;
472 typedef PointerTable<SymbolObj *, StringC, Hash, SymbolObj>
474 SymbolTable symbolTable_;
475 NamedTable<Identifier> identTable_;
476 NamedTable<Unit> unitTable_;
477 HashTable<StringC,FunctionObj *> externalProcTable_;
478 Messenger *messenger_;
479 const FOTBuilder::Extension *extensionTable_;
481 unsigned dPartIndex_;
483 unsigned nInheritedC_;
484 GroveManager *groveManager_;
485 ProcessingMode initialProcessingMode_;
486 NamedTable<ProcessingMode> processingModeTable_;
487 SymbolObj *portNames_[nPortNames];
488 ELObj *cValueSymbols_[FOTBuilder::nSymbols];
489 HashTable<StringC, CharPart> namedCharTable_;
490 HashTable<StringC, CharPart> sdataEntityNameTable_;
491 HashTable<StringC, CharPart> sdataEntityTextTable_;
492 Vector<const Identifier *> initialValueNames_;
493 NCVector<Owner<Expression> > initialValueValues_;
494 size_t currentPartFirstInitialValue_;
495 StyleObj *initialStyle_;
496 StyleObj *borderTrueStyle_;
497 StyleObj *borderFalseStyle_;
498 ConstPtr<InheritedC> tableBorderC_;
499 ConstPtr<InheritedC> cellBeforeRowBorderC_;
500 ConstPtr<InheritedC> cellAfterRowBorderC_;
501 ConstPtr<InheritedC> cellBeforeColumnBorderC_;
502 ConstPtr<InheritedC> cellAfterColumnBorderC_;
503 ConstPtr<InheritedC> fractionBarC_;
507 const char *store(String<char> &);
508 static unsigned long hash(const String<char> &);
509 static inline const String<char> &key(const String<char> &str) { return str; }
511 OwnerTable<String<char>, String<char>, StringSet, StringSet> table_;
513 StringSet publicIds_;
514 unsigned nextGlyphSubstTableUniqueId_;
515 AddressObj *addressNoneObj_;
516 NodeListObj *emptyNodeListObj_;
517 HashTable<StringC,int> nodePropertyTable_;
521 ELObj *defaultLanguage_;
522 Owner<Expression> defaultLanguageDef_;
523 unsigned defaultLanguageDefPart_;
524 Location defaultLanguageDefLoc_;
525 friend class Identifier;
526 HashTable<StringC, CharProp> charProperties_;
530 ErrorObj *Interpreter::makeError()
536 bool Interpreter::isError(const ELObj *obj) const
538 return obj == theErrorObj_;
542 bool Interpreter::isUnspecified(const ELObj *obj) const
544 return obj == theUnspecifiedObj_;
548 FalseObj *Interpreter::makeFalse()
554 TrueObj *Interpreter::makeTrue()
560 NilObj *Interpreter::makeNil()
566 UnspecifiedObj *Interpreter::makeUnspecified()
568 return theUnspecifiedObj_;
572 IntegerObj *Interpreter::makeInteger(long n)
574 return new (*this) IntegerObj(n);
578 PairObj *Interpreter::makePair(ELObj *car, ELObj *cdr)
580 return new (*this) PairObj(car, cdr);
584 CharObj *Interpreter::makeChar(Char c)
586 return new (*this) CharObj(c);
590 AddressObj *Interpreter::makeAddressNone()
592 return addressNoneObj_;
596 NodeListObj *Interpreter::makeEmptyNodeList()
598 return emptyNodeListObj_;
602 ELObj *Interpreter::cValueSymbol(FOTBuilder::Symbol sym)
604 return cValueSymbols_[sym];
608 SymbolObj *Interpreter::portName(PortName i)
610 return portNames_[i];
614 ProcessingMode *Interpreter::initialProcessingMode()
616 return &initialProcessingMode_;
620 int Interpreter::unitsPerInch() const
622 return unitsPerInch_;
626 unsigned Interpreter::currentPartIndex() const
632 KeywordObj *Interpreter::makeKeyword(const StringC &str)
634 return new (*this) KeywordObj(lookup(str));
638 StyleObj *Interpreter::initialStyle() const
640 return initialStyle_;
644 StyleObj *Interpreter::borderTrueStyle() const
646 return borderTrueStyle_;
650 StyleObj *Interpreter::borderFalseStyle() const
652 return borderFalseStyle_;
656 GroveManager *Interpreter::groveManager() const
658 return groveManager_;
662 const ConstPtr<InheritedC> &Interpreter::tableBorderC() const
664 return tableBorderC_;
668 const ConstPtr<InheritedC> &Interpreter::cellBeforeRowBorderC() const
670 return cellBeforeRowBorderC_;
674 const ConstPtr<InheritedC> &Interpreter::cellAfterRowBorderC() const
676 return cellAfterRowBorderC_;
680 const ConstPtr<InheritedC> &Interpreter::cellBeforeColumnBorderC() const
682 return cellBeforeColumnBorderC_;
686 const ConstPtr<InheritedC> &Interpreter::cellAfterColumnBorderC() const
688 return cellAfterColumnBorderC_;
692 const ConstPtr<InheritedC> &Interpreter::fractionBarC() const
694 return fractionBarC_;
698 FunctionObj *Interpreter::lookupExternalProc(const StringC &pubid)
700 FunctionObj *const *func = externalProcTable_.lookup(pubid);
701 return func ? *func : 0;
705 unsigned Interpreter::allocGlyphSubstTableUniqueId()
707 return nextGlyphSubstTableUniqueId_++;
711 bool Interpreter::debugMode() const
717 bool Interpreter::dsssl2() const
723 bool Interpreter::strictMode() const
729 void Interpreter::makeReadOnly(ELObj *obj)
732 Collector::makeReadOnly(obj);
736 void Interpreter::addClassAttributeName(const StringC &name)
738 classAttributeNames_.push_back(name);
742 void Interpreter::addIdAttributeName(const StringC &name)
744 idAttributeNames_.push_back(name);
748 Interpreter::LexCategory Interpreter::lexCategory(Xchar c)
750 return LexCategory(lexCategory_[c]);
754 bool Identifier::syntacticKey(SyntacticKey &key) const
756 if (syntacticKey_ == notKey)
763 void Identifier::setSyntacticKey(SyntacticKey key)
769 bool Identifier::evaluated() const
775 const ConstPtr<InheritedC> &Identifier::inheritedC() const
781 bool Identifier::inheritedCDefined(unsigned &part, Location &loc) const
783 if (inheritedC_.isNull())
785 part = inheritedCPart_;
786 loc = inheritedCLoc_;
791 bool Identifier::charNICDefined(unsigned &part, Location &loc) const
795 part = inheritedCPart_;
796 loc = inheritedCLoc_;
801 void Identifier::setCharNIC(unsigned part,
805 inheritedC_ = ConstPtr<InheritedC>(0);
806 inheritedCPart_ = part;
807 inheritedCLoc_ = loc;
811 void Identifier::setInheritedC(const ConstPtr<InheritedC> &ic, unsigned part,
815 inheritedCPart_ = part;
816 inheritedCLoc_ = loc;
820 void Identifier::setInheritedC(const ConstPtr<InheritedC> &ic)
823 inheritedCPart_ = unsigned(-1);
824 inheritedCLoc_ = Location();
828 FlowObj *Identifier::flowObj() const
834 bool Identifier::flowObjDefined(unsigned &part, Location &loc) const
844 void Identifier::setFlowObj(FlowObj *fo)
847 flowObjPart_ = unsigned(-1);
851 void Identifier::setFlowObj(FlowObj *fo, unsigned part, const Location &loc)
859 ELObjPart::ELObjPart()
865 ELObjPart::ELObjPart(ELObj *o, unsigned p)
871 void ELObjPart::operator=(const ELObjPart &x)
878 bool ELObjPart::operator==(const ELObjPart &x) const
880 return defPart == x.defPart && obj && x.obj && ELObj::eqv(*obj, *x.obj);
884 bool ELObjPart::operator!=(const ELObjPart &x) const
886 return !(*this == x);
890 #ifdef DSSSL_NAMESPACE
894 #endif /* not Interpreter_INCLUDED */