1 #include <magic/support/BitFieldAggregation.h> 2 3 using namespace llvm; 4 5 namespace llvm { 6 7 #define DEBUG_BFA 0 8 9 #define BitFieldAggregation_assert_or_return(R,RV,T,ET,X) do { \ 10 if(!(X)) { \ 11 if(R) return RV; \ 12 errs() << "Assertion failed, dumping types...\n"; \ 13 errs() << TypeUtil::getDescription(T, ET); \ 14 } \ 15 assert(X); \ 16 } while(0) 17 18 //===----------------------------------------------------------------------===// 19 // Constructors, destructor, and operators 20 //===----------------------------------------------------------------------===// 21 22 BitFieldAggregation::BitFieldAggregation(TYPECONST Type* type, std::vector<EDIType> EDITypes, unsigned typeIndex, unsigned EDITypeIndex, std::vector<DIDerivedType> members, unsigned counter) { 23 init(type, EDITypes, typeIndex, EDITypeIndex, members, counter); 24 } 25 26 BitFieldAggregation::BitFieldAggregation() { 27 type = NULL; 28 typeIndex = 0; 29 EDITypeIndex = 0; 30 name = ""; 31 } 32 33 void BitFieldAggregation::init(TYPECONST Type* type, std::vector<EDIType> EDITypes, unsigned typeIndex, unsigned EDITypeIndex, std::vector<DIDerivedType> members, unsigned counter) { 34 assert(members.size() == EDITypes.size()); 35 assert(typeIndex <= EDITypeIndex); 36 size = members.size(); 37 assert(size > 0); 38 39 this->type = type; 40 this->EDITypes = EDITypes; 41 this->typeIndex = typeIndex; 42 this->EDITypeIndex = EDITypeIndex; 43 this->members = members; 44 raw_string_ostream ostream(name); 45 ostream << bfaNamePrefix << counter; 46 ostream.flush(); 47 } 48 49 //===----------------------------------------------------------------------===// 50 // Getters 51 //===----------------------------------------------------------------------===// 52 53 const std::string BitFieldAggregation::getDescription() const { 54 std::string string; 55 raw_string_ostream ostream(string); 56 ostream << "[\nname = " << name << "\nmembers = "; 57 for(unsigned i=0;i<size;i++) { 58 ostream << (i==0 ? "" : ", ") << members[i].getName(); 59 } 60 ostream << "\ntype = \n" << TypeUtil::getDescription(getType()); 61 std::vector<EDIType> EDITypes = getEDITypes(); 62 for(unsigned i=0;i<EDITypes.size();i++) { 63 ostream << "\nEDIType" << i << " =\n" << TypeUtil::getDescription(&EDITypes[i]); 64 } 65 ostream << "\n]"; 66 ostream.flush(); 67 return string; 68 } 69 70 //===----------------------------------------------------------------------===// 71 // Public static methods 72 //===----------------------------------------------------------------------===// 73 74 bool BitFieldAggregation::getBitFieldAggregations(TYPECONST Type *type, const EDIType *aEDIType, std::vector<BitFieldAggregation> &bfas, bool returnOnError) { 75 std::vector<BitFieldAggregation> emptyBfas; 76 if(!hasBitFields(type, aEDIType)) { 77 return true; 78 } 79 unsigned typeIndex = 0; 80 unsigned EDITypeIndex = 0; 81 unsigned typeContainedTypes = type->getNumContainedTypes(); 82 unsigned aEDITypeContainedTypes = aEDIType->getNumContainedTypes(); 83 unsigned counter = 1; 84 const EDIType privateEDIType(*aEDIType); 85 aEDIType = &privateEDIType; 86 while(typeIndex < typeContainedTypes) { 87 TYPECONST Type *containedType = type->getContainedType(typeIndex); 88 if(EDITypeIndex >= aEDITypeContainedTypes && typeIndex == typeContainedTypes-1 && TypeUtil::isPaddedType(type)) { 89 break; 90 } 91 BitFieldAggregation_assert_or_return(returnOnError, false, type, aEDIType, EDITypeIndex < aEDITypeContainedTypes); 92 const EDIType containedEDIType = aEDIType->getContainedType(EDITypeIndex); 93 unsigned typeBits = TypeUtil::typeToBits(containedType); 94 if(typeBits > 0 && containedEDIType.isIntegerTy()) { 95 unsigned EDITypeBits = aEDIType->getMember(EDITypeIndex).getSizeInBits(); 96 assert(typeBits >= EDITypeBits); 97 if(typeBits > EDITypeBits) { 98 unsigned lastTypeIndex = typeIndex; 99 unsigned lastEDITypeIndex = EDITypeIndex; 100 while(lastEDITypeIndex+1 < aEDITypeContainedTypes && isBitField(type, aEDIType, lastEDITypeIndex+1)) { // grab all the bitfields following the first one found 101 lastEDITypeIndex++; 102 EDITypeBits += aEDIType->getMember(lastEDITypeIndex).getSizeInBits(); 103 } 104 while(lastTypeIndex+1 < typeContainedTypes && EDITypeBits > typeBits) { // grab all the necessary fields to cover all the bits found in the bitfields 105 lastTypeIndex++; 106 typeBits += TypeUtil::typeToBits(type->getContainedType(lastTypeIndex)); 107 } 108 BitFieldAggregation *bfa = BitFieldAggregation::getBitFieldAggregation(type, aEDIType, returnOnError, typeIndex, EDITypeIndex, lastTypeIndex, lastEDITypeIndex, counter++); 109 BitFieldAggregation_assert_or_return(returnOnError, false, type, aEDIType, bfa != NULL); 110 if(bfa->getSize() > 1) { 111 //we don't care about single-element aggregates 112 bfas.push_back(*bfa); 113 } 114 typeIndex++; 115 EDITypeIndex += bfa->getSize(); 116 continue; 117 } 118 } 119 typeIndex++; 120 EDITypeIndex++; 121 } 122 return true; 123 } 124 125 BitFieldAggregation *BitFieldAggregation::getBitFieldAggregation(TYPECONST Type *type, const EDIType *aEDIType, bool returnOnError, unsigned typeIndex, unsigned EDITypeIndex, unsigned lastTypeIndex, unsigned lastEDITypeIndex, unsigned counter) { 126 static BitFieldAggregation bfa; 127 TYPECONST Type *containedType = type->getContainedType(typeIndex); 128 unsigned typeBits = TypeUtil::typeToBits(containedType); 129 assert(typeBits > 0); 130 unsigned nextTypeBits = 0; 131 if (typeIndex < lastTypeIndex) { 132 nextTypeBits = TypeUtil::typeToBits(type->getContainedType(typeIndex+1)); 133 } 134 const int maxNumMembers = (lastEDITypeIndex - EDITypeIndex) - (lastTypeIndex - typeIndex) + 1; 135 unsigned index = EDITypeIndex; 136 std::vector<DIDerivedType> members; 137 std::vector<EDIType> containedEDITypes; 138 139 BitFieldAggregation_assert_or_return(returnOnError, NULL, type, aEDIType, maxNumMembers > 0); 140 #if DEBUG_BFA 141 BitFieldAggregationErr("getBitFieldAggregation(): typeIndex = " << typeIndex << ", EDITypeIndex = " << EDITypeIndex << ", maxNumMembers = " << maxNumMembers); 142 BitFieldAggregationErr("getBitFieldAggregation(): lastTypeIndex = " << lastTypeIndex << ", lastEDITypeIndex = " << lastEDITypeIndex); 143 BitFieldAggregationErr("getBitFieldAggregation(): " << TypeUtil::getDescription(type) << " VS " << TypeUtil::getDescription(aEDIType)); 144 #endif 145 while(index <= lastEDITypeIndex && members.size() < (unsigned)maxNumMembers) { 146 const EDIType containedEDIType = aEDIType->getContainedType(index); 147 #if DEBUG_BFA 148 BitFieldAggregationErr("Examining type " << TypeUtil::getDescription(&containedEDIType)); 149 #endif 150 BitFieldAggregation_assert_or_return(returnOnError, NULL, type, aEDIType, containedEDIType.isIntegerTy()); 151 DIDerivedType member = aEDIType->getMember(index); 152 unsigned EDITypeBits = member.getSizeInBits(); 153 #if DEBUG_BFA 154 BitFieldAggregationErr("Type bits = " << typeBits << ", next type bits = " << nextTypeBits << ", index = " << index); 155 BitFieldAggregationErr("This is member " << member.getName() << " with bits " << EDITypeBits); 156 #endif 157 if((index > EDITypeIndex && EDITypeBits == nextTypeBits) || EDITypeBits > typeBits) { 158 break; 159 } 160 typeBits -= EDITypeBits; 161 members.push_back(member); 162 containedEDITypes.push_back(containedEDIType); 163 index++; 164 } 165 bfa.init(containedType, containedEDITypes, typeIndex, EDITypeIndex, members, counter); 166 return &bfa; 167 } 168 169 std::string BitFieldAggregation::bfaNamePrefix = BFA_NAME_PREFIX; 170 171 } 172