1226584Sdim//===-- DWARFDebugAbbrev.cpp ----------------------------------------------===// 2226584Sdim// 3226584Sdim// The LLVM Compiler Infrastructure 4226584Sdim// 5226584Sdim// This file is distributed under the University of Illinois Open Source 6226584Sdim// License. See LICENSE.TXT for details. 7226584Sdim// 8226584Sdim//===----------------------------------------------------------------------===// 9226584Sdim 10226584Sdim#include "DWARFDebugAbbrev.h" 11226584Sdim#include "llvm/Support/Format.h" 12226584Sdim#include "llvm/Support/raw_ostream.h" 13226584Sdimusing namespace llvm; 14226584Sdim 15226584Sdimbool DWARFAbbreviationDeclarationSet::extract(DataExtractor data, 16226584Sdim uint32_t* offset_ptr) { 17226584Sdim const uint32_t beginOffset = *offset_ptr; 18226584Sdim Offset = beginOffset; 19226584Sdim clear(); 20226584Sdim DWARFAbbreviationDeclaration abbrevDeclaration; 21226584Sdim uint32_t prevAbbrAode = 0; 22226584Sdim while (abbrevDeclaration.extract(data, offset_ptr)) { 23226584Sdim Decls.push_back(abbrevDeclaration); 24226584Sdim if (IdxOffset == 0) { 25226584Sdim IdxOffset = abbrevDeclaration.getCode(); 26226584Sdim } else { 27226584Sdim if (prevAbbrAode + 1 != abbrevDeclaration.getCode()) 28226584Sdim IdxOffset = UINT32_MAX;// Out of order indexes, we can't do O(1) lookups 29226584Sdim } 30226584Sdim prevAbbrAode = abbrevDeclaration.getCode(); 31226584Sdim } 32226584Sdim return beginOffset != *offset_ptr; 33226584Sdim} 34226584Sdim 35226584Sdimvoid DWARFAbbreviationDeclarationSet::dump(raw_ostream &OS) const { 36226584Sdim for (unsigned i = 0, e = Decls.size(); i != e; ++i) 37226584Sdim Decls[i].dump(OS); 38226584Sdim} 39226584Sdim 40226584Sdimconst DWARFAbbreviationDeclaration* 41226584SdimDWARFAbbreviationDeclarationSet::getAbbreviationDeclaration(uint32_t abbrCode) 42226584Sdim const { 43226584Sdim if (IdxOffset == UINT32_MAX) { 44226584Sdim DWARFAbbreviationDeclarationCollConstIter pos; 45226584Sdim DWARFAbbreviationDeclarationCollConstIter end = Decls.end(); 46226584Sdim for (pos = Decls.begin(); pos != end; ++pos) { 47226584Sdim if (pos->getCode() == abbrCode) 48226584Sdim return &(*pos); 49226584Sdim } 50226584Sdim } else { 51226584Sdim uint32_t idx = abbrCode - IdxOffset; 52226584Sdim if (idx < Decls.size()) 53226584Sdim return &Decls[idx]; 54226584Sdim } 55226584Sdim return NULL; 56226584Sdim} 57226584Sdim 58226584SdimDWARFDebugAbbrev::DWARFDebugAbbrev() : 59226584Sdim AbbrevCollMap(), 60226584Sdim PrevAbbrOffsetPos(AbbrevCollMap.end()) {} 61226584Sdim 62226584Sdim 63226584Sdimvoid DWARFDebugAbbrev::parse(DataExtractor data) { 64226584Sdim uint32_t offset = 0; 65226584Sdim 66226584Sdim while (data.isValidOffset(offset)) { 67226584Sdim uint32_t initial_cu_offset = offset; 68226584Sdim DWARFAbbreviationDeclarationSet abbrevDeclSet; 69226584Sdim 70226584Sdim if (abbrevDeclSet.extract(data, &offset)) 71226584Sdim AbbrevCollMap[initial_cu_offset] = abbrevDeclSet; 72226584Sdim else 73226584Sdim break; 74226584Sdim } 75226584Sdim PrevAbbrOffsetPos = AbbrevCollMap.end(); 76226584Sdim} 77226584Sdim 78226584Sdimvoid DWARFDebugAbbrev::dump(raw_ostream &OS) const { 79226584Sdim if (AbbrevCollMap.empty()) { 80226584Sdim OS << "< EMPTY >\n"; 81226584Sdim return; 82226584Sdim } 83226584Sdim 84226584Sdim DWARFAbbreviationDeclarationCollMapConstIter pos; 85226584Sdim for (pos = AbbrevCollMap.begin(); pos != AbbrevCollMap.end(); ++pos) { 86234353Sdim OS << format("Abbrev table for offset: 0x%8.8" PRIx64 "\n", pos->first); 87226584Sdim pos->second.dump(OS); 88226584Sdim } 89226584Sdim} 90226584Sdim 91226584Sdimconst DWARFAbbreviationDeclarationSet* 92226584SdimDWARFDebugAbbrev::getAbbreviationDeclarationSet(uint64_t cu_abbr_offset) const { 93226584Sdim DWARFAbbreviationDeclarationCollMapConstIter end = AbbrevCollMap.end(); 94226584Sdim DWARFAbbreviationDeclarationCollMapConstIter pos; 95226584Sdim if (PrevAbbrOffsetPos != end && 96226584Sdim PrevAbbrOffsetPos->first == cu_abbr_offset) { 97226584Sdim return &(PrevAbbrOffsetPos->second); 98226584Sdim } else { 99226584Sdim pos = AbbrevCollMap.find(cu_abbr_offset); 100226584Sdim PrevAbbrOffsetPos = pos; 101226584Sdim } 102226584Sdim 103226584Sdim if (pos != AbbrevCollMap.end()) 104226584Sdim return &(pos->second); 105226584Sdim return NULL; 106226584Sdim} 107