/*FieldCreateFactory.cpp*/ /** * Copyright - See the COPYRIGHT that is included with this distribution. * EPICS pvDataCPP is distributed subject to a Software License Agreement found * in file LICENSE that is included with this distribution. */ #include #include #include #include #include #include "pvIntrospect.h" #include "factory.h" namespace epics { namespace pvData { static DebugLevel debugLevel = lowDebug; static void newLine(StringBuilder buffer, int indentLevel) { *buffer += "\n"; for(int i=0; ifieldName.c_str()); } int Field::getReferenceCount() const { Lock xx(globalMutex); return pImpl->referenceCount; } String Field::getFieldName() const {return pImpl->fieldName;} Type Field::getType() const {return pImpl->type;} void Field::incReferenceCount() const { Lock xx(globalMutex); pImpl->referenceCount++; totalReferenceCount++; } void Field::decReferenceCount() const { Lock xx(globalMutex); if(pImpl->referenceCount<=0) { String message("logicError field "); message += pImpl->fieldName; throw std::logic_error(message); } pImpl->referenceCount--; totalReferenceCount--; if(pImpl->referenceCount==0) delete this; } void Field::toString(StringBuilder buffer,int indentLevel) const{ *buffer += " "; *buffer += pImpl->fieldName.c_str(); } Scalar::Scalar(String fieldName,ScalarType scalarType) : Field(fieldName,scalar),scalarType(scalarType){} Scalar::~Scalar(){} void Scalar::toString(StringBuilder buffer,int indentLevel) const{ ScalarTypeFunc::toString(buffer,scalarType); Field::toString(buffer,indentLevel); } ScalarArray::ScalarArray(String fieldName,ScalarType elementType) : Field(fieldName,scalarArray),elementType(elementType){} ScalarArray::~ScalarArray() {} void ScalarArray::toString(StringBuilder buffer,int indentLevel) const{ String temp = String(); ScalarTypeFunc::toString(&temp,elementType); temp += "Array"; *buffer += temp; Field::toString(buffer,indentLevel); } StructureArray::StructureArray(String fieldName,StructureConstPtr structure) : Field(fieldName,structureArray),pstructure(structure) { pstructure->incReferenceCount(); } StructureArray::~StructureArray() { if(debugLevel==highDebug) printf("~StructureArray\n"); pstructure->decReferenceCount(); } void StructureArray::toString(StringBuilder buffer,int indentLevel) const { *buffer += " structureArray "; Field::toString(buffer,indentLevel); newLine(buffer,indentLevel + 1); pstructure->toString(buffer,indentLevel + 1); } Structure::Structure (String fieldName, int numberFields, FieldConstPtrArray infields) : Field(fieldName,structure), numberFields(numberFields), fields(new FieldConstPtr[numberFields]) { for(int i=0; igetFieldName(); // look for duplicates for(int j=i+1; jgetFieldName(); int result = name.compare(otherName); if(result==0) { String message("duplicate fieldName "); message += name; throw std::invalid_argument(message); } } // inc reference counter fields[i]->incReferenceCount(); } } Structure::~Structure() { if(debugLevel==highDebug) printf("~Structure %s\n",Field::getFieldName().c_str()); for(int i=0; idecReferenceCount(); } delete[] fields; } FieldConstPtr Structure::getField(String fieldName) const { for(int i=0; igetFieldName()); if(result==0) return pfield; } return 0; } int Structure::getFieldIndex(String fieldName) const { for(int i=0; igetFieldName()); if(result==0) return i; } return -1; } void Structure::toString(StringBuilder buffer,int indentLevel) const{ *buffer += "structure"; Field::toString(buffer,indentLevel); newLine(buffer,indentLevel+1); for(int i=0; itoString(buffer,indentLevel+1); if(igetType(); switch(type) { case scalar: { ScalarConstPtr pscalar = dynamic_cast(pfield); return createScalar(fieldName,pscalar->getScalarType()); } case scalarArray: { ScalarArrayConstPtr pscalarArray = dynamic_cast(pfield); return createScalarArray(fieldName,pscalarArray->getElementType()); } case structure: { StructureConstPtr pstructure = dynamic_cast(pfield); return createStructure(fieldName,pstructure->getNumberFields(),pstructure->getFields()); } case structureArray: { StructureArrayConstPtr pstructureArray = dynamic_cast(pfield); return createStructureArray(fieldName,pstructureArray->getStructure()); } } String message("field "); message += fieldName; throw std::logic_error(message); } static FieldCreate* fieldCreate = 0; FieldCreate::FieldCreate() { init(); } FieldCreate * getFieldCreate() { static Mutex mutex = Mutex(); Lock xx(&mutex); if(fieldCreate==0) fieldCreate = new FieldCreate(); return fieldCreate; } }}