2 * CDE - Common Desktop Environment
4 * Copyright (c) 1993-2012, The Open Group. All rights reserved.
6 * These libraries and programs are free software; you can
7 * redistribute them and/or modify them under the terms of the GNU
8 * Lesser General Public License as published by the Free Software
9 * Foundation; either version 2 of the License, or (at your option)
12 * These libraries and programs are distributed in the hope that
13 * they will be useful, but WITHOUT ANY WARRANTY; without even the
14 * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU Lesser General Public License for more
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with these libraries and programs; if not, write
20 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21 * Floor, Boston, MA 02110-1301 USA
23 /* $XConsortium: Attribute.h /main/1 1996/07/29 16:46:39 cde-hp $ */
24 // Copyright (c) 1994 James Clark
25 // See the file COPYING for copying permission.
27 #ifndef Attribute_INCLUDED
28 #define Attribute_INCLUDED 1
38 #include "CopyOwner.h"
45 namespace SP_NAMESPACE {
52 class TokenizedAttributeValue;
53 class AttributeSemantics;
54 class AttributeContext;
57 class SP_API AttributeDefinitionDesc {
59 AttributeDefinitionDesc() { }
78 DeclaredValue declaredValue;
79 enum DefaultValueType {
87 DefaultValueType defaultValueType;
88 ConstPtr<AttributeValue> defaultValue;
89 Vector<StringC> allowedValues;
90 // Attribute definitions whose default value type is current and
91 // which have the same currentIndex share current values.
94 AttributeDefinitionDesc(const AttributeDefinitionDesc &); // undefined
95 void operator=(const AttributeDefinitionDesc &); // undefined
101 virtual ~DeclaredValue();
102 // This performs syntactic checking on the value.
103 virtual AttributeValue *makeValue(Text &, AttributeContext &,
105 unsigned &specLength) const = 0;
106 // This is used to avoid unnecessary syntactic checking in the
107 // case where the attribute name and vi have been omitted.
108 virtual AttributeValue *makeValueFromToken(Text &,
111 unsigned &specLength) const;
112 // This performs semantic checking on the value.
113 virtual AttributeSemantics *makeSemantics(const TokenizedAttributeValue &,
117 unsigned &nEntityNames) const;
118 virtual Boolean containsToken(const StringC &) const;
119 virtual Boolean tokenized() const = 0;
120 virtual Boolean isNotation() const;
121 virtual Boolean isEntity() const;
122 virtual Boolean isId() const;
123 virtual Boolean isIdref() const;
124 virtual const Vector<StringC> *getTokens() const;
125 virtual void buildDesc(AttributeDefinitionDesc &) const = 0;
126 virtual DeclaredValue *copy() const = 0;
129 class CdataDeclaredValue : public DeclaredValue {
131 CdataDeclaredValue();
132 Boolean tokenized() const;
133 AttributeValue *makeValue(Text &, AttributeContext &, const StringC &,
135 void buildDesc(AttributeDefinitionDesc &) const;
136 DeclaredValue *copy() const;
139 class TokenizedDeclaredValue : public DeclaredValue {
141 // must be in same order as AttributeDefinitionDesc
149 TokenizedDeclaredValue(TokenType type, Boolean isList);
150 AttributeValue *makeValue(Text &, AttributeContext &, const StringC &,
152 TokenizedAttributeValue *makeTokenizedValue(Text &, AttributeContext &,
153 const StringC &, unsigned &) const;
154 Boolean tokenized() const;
155 void buildDesc(AttributeDefinitionDesc &) const;
156 DeclaredValue *copy() const;
160 unsigned initialCategories_;
161 unsigned subsequentCategories_;
164 class GroupDeclaredValue : public TokenizedDeclaredValue {
166 GroupDeclaredValue(TokenType, Vector<StringC> &);
167 Boolean containsToken(const StringC &) const;
168 AttributeValue *makeValue(Text &, AttributeContext &, const StringC &,
170 AttributeValue *makeValueFromToken(Text &,
174 const Vector<StringC> *getTokens() const;
175 void buildDesc(AttributeDefinitionDesc &) const;
176 DeclaredValue *copy() const;
178 Vector<StringC> allowedValues_;
181 class NameTokenGroupDeclaredValue : public GroupDeclaredValue {
183 NameTokenGroupDeclaredValue(Vector<StringC> &);
184 void buildDesc(AttributeDefinitionDesc &) const;
185 DeclaredValue *copy() const;
188 class NotationDeclaredValue : public GroupDeclaredValue {
190 NotationDeclaredValue(Vector<StringC> &);
191 AttributeSemantics *makeSemantics(const TokenizedAttributeValue &,
195 unsigned &nEntityNames) const;
196 Boolean isNotation() const;
197 void buildDesc(AttributeDefinitionDesc &) const;
198 DeclaredValue *copy() const;
201 class EntityDeclaredValue : public TokenizedDeclaredValue {
203 EntityDeclaredValue(Boolean isList);
204 AttributeSemantics *makeSemantics(const TokenizedAttributeValue &,
208 unsigned &nEntityNames) const;
209 Boolean isEntity() const;
210 DeclaredValue *copy() const;
213 class IdDeclaredValue : public TokenizedDeclaredValue {
216 AttributeSemantics *makeSemantics(const TokenizedAttributeValue &,
220 unsigned &nEntityNames) const;
221 Boolean isId() const;
222 void buildDesc(AttributeDefinitionDesc &) const;
223 DeclaredValue *copy() const;
226 class IdrefDeclaredValue : public TokenizedDeclaredValue {
228 IdrefDeclaredValue(Boolean isList);
229 AttributeSemantics *makeSemantics(const TokenizedAttributeValue &,
233 unsigned &nEntityNames) const;
234 Boolean isIdref() const;
235 void buildDesc(AttributeDefinitionDesc &) const;
236 DeclaredValue *copy() const;
239 class SP_API AttributeDefinition {
241 AttributeDefinition(const StringC &, DeclaredValue *);
242 virtual ~AttributeDefinition();
243 virtual ConstPtr<AttributeValue>
244 makeMissingValue(AttributeContext &) const = 0;
245 virtual Boolean missingValueWouldMatch(const Text &,
246 const AttributeContext &) const;
247 virtual const AttributeValue *
248 defaultValue(const AttributeValue *impliedValue) const;
249 AttributeValue *makeValue(Text &, AttributeContext &, unsigned &) const;
250 AttributeValue *makeValueFromToken(Text &,
254 virtual Boolean isConref() const;
255 virtual Boolean isCurrent() const;
256 virtual Boolean isFixed() const;
257 AttributeSemantics *makeSemantics(const AttributeValue *,
260 unsigned &nEntityNames) const;
261 Boolean tokenized() const;
262 const StringC &name() const;
263 Boolean containsToken(const StringC &) const;
264 Boolean isNotation() const;
265 Boolean isEntity() const;
266 Boolean isId() const;
267 Boolean isIdref() const;
268 void getDesc(AttributeDefinitionDesc &) const;
269 const Vector<StringC> *getTokens() const;
270 virtual AttributeDefinition *copy() const = 0;
271 void setDeclaredValue(DeclaredValue *);
273 virtual void buildDesc(AttributeDefinitionDesc &) const = 0;
274 virtual AttributeValue *checkValue(AttributeValue *, AttributeContext &) const;
276 CopyOwner<DeclaredValue> declaredValue_;
279 class RequiredAttributeDefinition : public AttributeDefinition {
281 RequiredAttributeDefinition(const StringC &, DeclaredValue *);
282 ConstPtr<AttributeValue> makeMissingValue(AttributeContext &) const;
283 void buildDesc(AttributeDefinitionDesc &) const;
284 AttributeDefinition *copy() const;
287 class CurrentAttributeDefinition : public AttributeDefinition {
289 CurrentAttributeDefinition(const StringC &, DeclaredValue *, size_t index);
290 ConstPtr<AttributeValue> makeMissingValue(AttributeContext &) const;
291 Boolean missingValueWouldMatch(const Text &, const AttributeContext &) const;
292 AttributeValue *checkValue(AttributeValue *, AttributeContext &) const;
293 void buildDesc(AttributeDefinitionDesc &) const;
294 Boolean isCurrent() const;
295 AttributeDefinition *copy() const;
297 size_t currentIndex_;
300 class ImpliedAttributeDefinition : public AttributeDefinition {
302 ImpliedAttributeDefinition(const StringC &, DeclaredValue *);
303 ConstPtr<AttributeValue> makeMissingValue(AttributeContext &) const;
304 const AttributeValue *defaultValue(const AttributeValue *) const;
305 void buildDesc(AttributeDefinitionDesc &) const;
306 AttributeDefinition *copy() const;
309 class ConrefAttributeDefinition : public ImpliedAttributeDefinition {
311 ConrefAttributeDefinition(const StringC &, DeclaredValue *);
312 Boolean isConref() const;
313 void buildDesc(AttributeDefinitionDesc &) const;
314 AttributeDefinition *copy() const;
317 class DefaultAttributeDefinition : public AttributeDefinition {
319 DefaultAttributeDefinition(const StringC &, DeclaredValue *,
321 ConstPtr<AttributeValue> makeMissingValue(AttributeContext &) const;
322 Boolean missingValueWouldMatch(const Text &, const AttributeContext &) const;
323 void buildDesc(AttributeDefinitionDesc &) const;
324 AttributeDefinition *copy() const;
325 const AttributeValue *defaultValue(const AttributeValue *) const;
327 ConstPtr<AttributeValue> value_;
330 class FixedAttributeDefinition : public DefaultAttributeDefinition {
332 FixedAttributeDefinition(const StringC &, DeclaredValue *,
334 // check that it's equal to the default
335 AttributeValue *checkValue(AttributeValue *, AttributeContext &) const;
336 void buildDesc(AttributeDefinitionDesc &) const;
337 Boolean isFixed() const;
338 AttributeDefinition *copy() const;
341 class SP_API AttributeDefinitionList : public Resource {
343 AttributeDefinitionList(Vector<CopyOwner<AttributeDefinition> > &,
345 Boolean anyCurrent = 0,
346 size_t idIndex = size_t(-1),
347 size_t notationIndex = size_t(-1));
349 AttributeDefinition *def(size_t);
350 const AttributeDefinition *def(size_t) const;
351 Boolean tokenIndex(const StringC &, unsigned &) const;
352 Boolean attributeIndex(const StringC &, unsigned &) const;
353 size_t index() const;
354 size_t idIndex() const;
355 size_t notationIndex() const;
356 Boolean anyCurrent() const;
357 void append(AttributeDefinition *);
359 Vector<CopyOwner<AttributeDefinition> > defs_;
361 size_t idIndex_; // -1 if no ID attribute
362 size_t notationIndex_; // -1 if no notation attribute
366 class AttributeSemantics {
368 AttributeSemantics();
369 virtual ~AttributeSemantics();
370 virtual size_t nEntities() const;
371 virtual ConstPtr<Entity> entity(size_t) const;
372 virtual ConstPtr<Notation> notation() const;
373 virtual AttributeSemantics *copy() const = 0;
376 class EntityAttributeSemantics : public AttributeSemantics {
378 EntityAttributeSemantics(Vector<ConstPtr<Entity> > &);
379 size_t nEntities() const;
380 ConstPtr<Entity> entity(size_t) const;
381 AttributeSemantics *copy() const;
383 Vector<ConstPtr<Entity> > entity_;
386 class NotationAttributeSemantics : public AttributeSemantics {
388 NotationAttributeSemantics(const ConstPtr<Notation> &);
389 ConstPtr<Notation> notation() const;
390 AttributeSemantics *copy() const;
392 ConstPtr<Notation> notation_;
395 class AttributeValue : public Resource {
403 virtual ~AttributeValue();
404 virtual AttributeSemantics *makeSemantics(const DeclaredValue *,
409 virtual Type info(const Text *&, const StringC *&) const = 0;
410 virtual const Text *text() const;
411 virtual Boolean recoverUnquoted(const StringC &, const Location &,
412 AttributeContext &, const StringC &);
413 static Boolean handleAsUnterminated(const Text &, AttributeContext &);
416 class SP_API ImpliedAttributeValue : public AttributeValue {
418 ImpliedAttributeValue();
419 Type info(const Text *&, const StringC *&) const;
422 class CdataAttributeValue : public AttributeValue {
424 CdataAttributeValue(Text &);
425 Type info(const Text *&, const StringC *&) const;
426 const Text *text() const;
427 Boolean recoverUnquoted(const StringC &, const Location &,
428 AttributeContext &, const StringC &);
433 class TokenizedAttributeValue : public AttributeValue {
435 TokenizedAttributeValue(Text &, const Vector<size_t> &);
436 size_t nTokens() const;
437 AttributeSemantics *makeSemantics(const DeclaredValue *,
442 Type info(const Text *&, const StringC *&) const;
443 const Text *text() const;
444 const StringC &string() const;
445 StringC token(size_t) const;
446 void token(size_t, const Char *&, size_t &) const;
447 Location tokenLocation(size_t) const;
448 Boolean recoverUnquoted(const StringC &, const Location &,
449 AttributeContext &, const StringC &);
451 TokenizedAttributeValue(const TokenizedAttributeValue &); // undefined
452 void operator=(const TokenizedAttributeValue &); // undefined
454 // index into value of each space
455 // length is number of tokens - 1
456 Vector<size_t> spaceIndex_;
459 class SP_API Attribute {
462 Boolean specified() const;
463 size_t specIndex() const;
464 const AttributeValue *value() const;
465 const ConstPtr<AttributeValue> &valuePointer() const;
466 const AttributeSemantics *semantics() const;
467 void setSpec(size_t);
468 void setValue(const ConstPtr<AttributeValue> &);
469 void setSemantics(AttributeSemantics *);
472 size_t specIndexPlus_;
473 ConstPtr<AttributeValue> value_;
474 CopyOwner<AttributeSemantics> semantics_;
477 class SP_API AttributeList {
480 AttributeList(const ConstPtr<AttributeDefinitionList> &);
481 void init(const ConstPtr<AttributeDefinitionList> &);
482 // was a conref attribute specified?
483 Boolean conref() const;
485 const StringC &name(unsigned) const;
486 const AttributeValue *value(unsigned) const;
487 size_t specIndex(size_t) const;
488 const ConstPtr<AttributeValue> &valuePointer(unsigned) const;
489 const AttributeSemantics *semantics(unsigned) const;
490 Boolean tokenized(unsigned index) const;
491 Boolean tokenIndex(const StringC &, unsigned &) const;
492 Boolean attributeIndex(const StringC &, unsigned &) const;
493 void finish(AttributeContext &);
494 Boolean setValue(unsigned index, Text &, AttributeContext &,
495 unsigned &specLength);
496 void setValueToken(unsigned index, Text &, AttributeContext &,
497 unsigned &specLength);
498 void setSpec(unsigned index, AttributeContext &);
499 Boolean recoverUnquoted(const StringC &, const Location &,
501 Boolean handleAsUnterminated(AttributeContext &context);
502 void swap(AttributeList &);
503 size_t nSpec() const;
504 size_t defIndex() const;
505 // is the attribute #current
506 Boolean current(unsigned) const;
507 Boolean anyCurrent() const;
508 Boolean specified(unsigned) const;
509 Boolean id(unsigned) const;
510 Boolean idref(unsigned) const;
511 const Vector<StringC> *getAllowedTokens(unsigned) const;
512 const StringC *getId() const; // null if none
513 Boolean idIndex(unsigned &) const;
514 void noteInvalidSpec();
516 const AttributeDefinition *def(size_t) const;
517 PackedBoolean conref_;
519 unsigned nEntityNames_;
521 Vector<Attribute> vec_;
522 ConstPtr<AttributeDefinitionList> def_;
525 class SP_API AttributeContext : public Messenger {
528 virtual ~AttributeContext();
529 virtual Boolean defineId(const StringC &, const Location &, Location &);
530 virtual void noteIdref(const StringC &, const Location &);
531 virtual void noteCurrentAttribute(size_t, AttributeValue *);
532 virtual ConstPtr<AttributeValue> getCurrentAttribute(size_t) const;
533 virtual ConstPtr<Entity> getAttributeEntity(const StringC &,
535 virtual ConstPtr<Notation> getAttributeNotation(const StringC &,
537 virtual const Syntax &attributeSyntax() const = 0;
539 ConstPtr<AttributeValue> makeImpliedAttributeValue();
540 Boolean mayDefaultAttribute() const;
542 Boolean mayDefaultAttribute_;
544 ConstPtr<AttributeValue> impliedAttributeValue_;
548 Boolean AttributeDefinition::tokenized() const
550 return declaredValue_->tokenized();
554 Boolean AttributeDefinition::isNotation() const
556 return declaredValue_->isNotation();
560 Boolean AttributeDefinition::isEntity() const
562 return declaredValue_->isEntity();
566 Boolean AttributeDefinition::isId() const
568 return declaredValue_->isId();
572 Boolean AttributeDefinition::isIdref() const
574 return declaredValue_->isIdref();
578 const Vector<StringC> *AttributeDefinition::getTokens() const
580 return declaredValue_->getTokens();
585 AttributeDefinition::makeSemantics(const AttributeValue *value,
586 AttributeContext &context,
588 unsigned &nEntityNames) const
590 return value->makeSemantics(declaredValue_.pointer(), context, name_,
591 nIdrefs, nEntityNames);
595 AttributeValue *AttributeDefinition::makeValue(Text &text,
596 AttributeContext &context,
597 unsigned &specLength) const
599 return checkValue(declaredValue_->makeValue(text, context, name_,
606 AttributeDefinition::makeValueFromToken(Text &text,
607 AttributeContext &context,
608 unsigned &specLength) const
610 return checkValue(declaredValue_->makeValueFromToken(text, context,
616 Boolean AttributeDefinition::containsToken(const StringC &token) const
618 return declaredValue_->containsToken(token);
622 const StringC &AttributeDefinition::name() const
628 void AttributeDefinition::setDeclaredValue(DeclaredValue *declaredValue)
630 declaredValue_ = declaredValue;
634 size_t AttributeDefinitionList::size() const
640 size_t AttributeDefinitionList::index() const
646 size_t AttributeDefinitionList::idIndex() const
652 size_t AttributeDefinitionList::notationIndex() const
654 return notationIndex_;
658 Boolean AttributeDefinitionList::anyCurrent() const
664 AttributeDefinition *AttributeDefinitionList::def(size_t i)
666 return defs_[i].pointer();
670 const AttributeDefinition *AttributeDefinitionList::def(size_t i) const
672 return defs_[i].pointer();
676 size_t TokenizedAttributeValue::nTokens() const
678 return spaceIndex_.size() + 1;
682 const StringC &TokenizedAttributeValue::string() const
684 return text_.string();
688 void TokenizedAttributeValue::token(size_t i,
689 const Char *&ptr, size_t &len) const
691 size_t startIndex = i == 0 ? 0 : spaceIndex_[i - 1] + 1;
692 ptr = text_.string().data() + startIndex;
693 len = (i == spaceIndex_.size() ? text_.size() : spaceIndex_[i]) - startIndex;
697 StringC TokenizedAttributeValue::token(size_t i) const
702 return StringC(ptr, len);
706 Location TokenizedAttributeValue::tokenLocation(size_t i) const
708 return text_.charLocation(i == 0 ? 0 : spaceIndex_[i - 1] + 1);
712 size_t Attribute::specIndex() const
714 return specIndexPlus_ - 1;
718 Boolean Attribute::specified() const
720 return specIndexPlus_ != 0;
724 const AttributeValue *Attribute::value() const
726 return value_.pointer();
730 const ConstPtr<AttributeValue> &Attribute::valuePointer() const
736 const AttributeSemantics *Attribute::semantics() const
738 return semantics_.pointer();
742 void Attribute::setSpec(size_t index)
744 specIndexPlus_ = index + 1;
748 void Attribute::setValue(const ConstPtr<AttributeValue> &value)
754 void Attribute::setSemantics(AttributeSemantics *semantics)
756 semantics_ = semantics;
760 size_t AttributeList::size() const
766 const AttributeDefinition *AttributeList::def(size_t i) const
772 Boolean AttributeList::tokenized(unsigned i) const
774 return def(i)->tokenized();
778 Boolean AttributeList::tokenIndex(const StringC &name, unsigned &index) const
780 return !def_.isNull() && def_->tokenIndex(name, index);
784 Boolean AttributeList::attributeIndex(const StringC &name, unsigned &index) const
786 return !def_.isNull() && def_->attributeIndex(name, index);
790 const StringC &AttributeList::name(unsigned i) const
792 return def(i)->name();
796 const Vector<StringC> *AttributeList::getAllowedTokens(unsigned i) const
798 return def(i)->getTokens();
802 const AttributeValue *AttributeList::value(unsigned i) const
804 return vec_[i].value();
808 const ConstPtr<AttributeValue> &AttributeList::valuePointer(unsigned i)
811 return vec_[i].valuePointer();
815 const AttributeSemantics *AttributeList::semantics(unsigned i) const
817 return vec_[i].semantics();
821 size_t AttributeList::specIndex(size_t i) const
823 return vec_[i].specIndex();
827 size_t AttributeList::nSpec() const
833 Boolean AttributeList::conref() const
839 size_t AttributeList::defIndex() const
841 return def_.isNull() ? size_t(-1) : def_->index();
845 Boolean AttributeList::current(unsigned i) const
847 return def(i)->isCurrent();
851 Boolean AttributeList::anyCurrent() const
853 return !def_.isNull() && def_->anyCurrent();
857 const AttributeValue *
858 DefaultAttributeDefinition::defaultValue(const AttributeValue *)
861 return value_.pointer();
865 Boolean AttributeList::idIndex(unsigned &ind) const
867 if (def_.isNull() || def_->idIndex() == size_t(-1))
870 ind = def_->idIndex();
876 Boolean AttributeList::id(unsigned i) const
878 return def(i)->isId();
882 Boolean AttributeList::idref(unsigned i) const
884 return def(i)->isIdref();
888 Boolean AttributeList::specified(unsigned i) const
890 return vec_[i].specified();
894 Boolean AttributeContext::mayDefaultAttribute() const
896 return mayDefaultAttribute_;
903 #endif /* not Attribute_INCLUDED */