mirror of
https://github.com/nasa/trick.git
synced 2024-12-19 21:27:54 +00:00
ATTRIBUTES for classes with non-locally typedef'd members is wrong
Interesting case. I found that we should process the canonical type names where we were not before. This resolves all typedefs and should be be more accurate in the future. When we process the canonical type we need to ignore the processing of the non-canonical type. We set a flag after the canonical type is processed to ignore any type that is processed after. refs #198
This commit is contained in:
parent
0f76eec7a1
commit
1754995396
@ -37,6 +37,7 @@ FieldDescription::FieldDescription(
|
||||
is_record(0) ,
|
||||
is_static(0) ,
|
||||
has_type(0) ,
|
||||
has_dims(0) ,
|
||||
num_dims(0) ,
|
||||
array_sizes() {} ;
|
||||
|
||||
@ -385,6 +386,14 @@ bool FieldDescription::hasType() {
|
||||
return has_type ;
|
||||
}
|
||||
|
||||
void FieldDescription::setHasDims( bool yes_no ) {
|
||||
has_dims = yes_no ;
|
||||
}
|
||||
|
||||
bool FieldDescription::hasDims() {
|
||||
return has_dims ;
|
||||
}
|
||||
|
||||
unsigned int FieldDescription::getNumDims() {
|
||||
return num_dims ;
|
||||
}
|
||||
|
@ -77,6 +77,8 @@ class FieldDescription : public ConstructValues {
|
||||
bool isVirtualInherited() ;
|
||||
void setHasType( bool yes_no ) ;
|
||||
bool hasType() ;
|
||||
void setHasDims( bool yes_no ) ;
|
||||
bool hasDims() ;
|
||||
void setAccess( clang::AccessSpecifier in_val ) ;
|
||||
clang::AccessSpecifier getAccess() ;
|
||||
|
||||
@ -158,6 +160,9 @@ class FieldDescription : public ConstructValues {
|
||||
/** Have we resolved the type for this parameter? */
|
||||
bool has_type ;
|
||||
|
||||
/** Have we resolved the dimensions for this parameter? */
|
||||
bool has_dims ;
|
||||
|
||||
/** map of strings to io numbers. One copy for all fields */
|
||||
static std::map<std::string , unsigned int> io_map ;
|
||||
|
||||
|
@ -130,7 +130,9 @@ bool FieldVisitor::VisitBuiltinType(clang::BuiltinType *bt) {
|
||||
|
||||
bool FieldVisitor::VisitConstantArrayType(clang::ConstantArrayType *cat) {
|
||||
//cat->dump() ; std::cout << std::endl ;
|
||||
fdes->addArrayDim(cat->getSize().getZExtValue()) ;
|
||||
if ( ! fdes->hasDims() ) {
|
||||
fdes->addArrayDim(cat->getSize().getZExtValue()) ;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -209,16 +211,31 @@ bool FieldVisitor::VisitFieldDecl( clang::FieldDecl *field ) {
|
||||
fdes->setBitFieldStart( 32 - (field_offset_bits % 32) - fdes->getBitFieldWidth()) ;
|
||||
fdes->setBitFieldByteOffset((field_offset_bits / 32) * 4 ) ;
|
||||
}
|
||||
|
||||
clang::QualType qt = field->getType() ;
|
||||
// If the current type is not canonical because of typedefs, traverse the canonical type
|
||||
if ( !qt.isCanonical() ) {
|
||||
clang::QualType ct = qt.getCanonicalType() ;
|
||||
TraverseType(ct) ;
|
||||
// Traversing the canonical type will set the has_type flag. Set the has_dims flag too so
|
||||
// when we continue parsing the AST and the non-canonical type, we don't double add dimensions.
|
||||
fdes->setHasDims(true) ;
|
||||
}
|
||||
return true ;
|
||||
}
|
||||
|
||||
bool FieldVisitor::VisitElaboratedType(clang::ElaboratedType *et) {
|
||||
if ( debug_level >= 4 ) {
|
||||
std::cout << "FieldVisitor VisitElaboratedType" << std::endl ;
|
||||
}
|
||||
//et->dump() ; std::cout << std::endl ;
|
||||
return true ;
|
||||
}
|
||||
|
||||
bool FieldVisitor::VisitPointerType(clang::PointerType *p) {
|
||||
fdes->addArrayDim(-1) ;
|
||||
if ( ! fdes->hasDims() ) {
|
||||
fdes->addArrayDim(-1) ;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -244,8 +261,17 @@ bool FieldVisitor::VisitRecordType(clang::RecordType *rt) {
|
||||
//std::cout << "hasNameForLinkage " << rt->getDecl()->hasNameForLinkage() << std::endl ;
|
||||
if ( rt->getDecl()->hasNameForLinkage() ) {
|
||||
if ( rt->getDecl()->getDeclName() ) {
|
||||
//std::cout << "getDeclName " << rt->getDecl()->getDeclName().getAsString() << std::endl ;
|
||||
fdes->setTypeName(rt->getDecl()->getQualifiedNameAsString()) ;
|
||||
std::string type_name = rt->getDecl()->getQualifiedNameAsString() ;
|
||||
// Handle the string class differently than regular records.
|
||||
if ( ! type_name.compare("std::basic_string") || !type_name.compare("std::__1::basic_string")) {
|
||||
fdes->setEnumString("TRICK_STRING") ;
|
||||
fdes->setTypeName("std::string") ;
|
||||
fdes->setHasType(true) ;
|
||||
return true ;
|
||||
} else {
|
||||
//std::cout << "getDeclName " << type_name << std::endl ;
|
||||
fdes->setTypeName(type_name) ;
|
||||
}
|
||||
} else {
|
||||
//std::cout << "getTypedefNameForAnonDecl " << rt->getDecl()->getTypedefNameForAnonDecl() << std::endl ;
|
||||
fdes->setTypeName(rt->getDecl()->getTypedefNameForAnonDecl()->getQualifiedNameAsString()) ;
|
||||
@ -453,6 +479,11 @@ bool FieldVisitor::VisitTypedefType(clang::TypedefType *tt) {
|
||||
|
||||
fdes->setHasType(true) ;
|
||||
} else if ( tt->isRecordType() ) {
|
||||
|
||||
if ( debug_level >= 4 ) {
|
||||
std::cout << "FieldVisitor isRecordType" << std::endl ;
|
||||
}
|
||||
|
||||
std::string type_name = tt->desugar().getAsString() ;
|
||||
if ((pos = type_name.find("class ")) != std::string::npos ) {
|
||||
type_name.erase(pos , 6) ;
|
||||
|
Loading…
Reference in New Issue
Block a user