diff options
author | Justin Bogner <mail@justinbogner.com> | 2014-03-19 02:20:42 +0000 |
---|---|---|
committer | Justin Bogner <mail@justinbogner.com> | 2014-03-19 02:20:42 +0000 |
commit | fb007bb98c8943b734111ab601e4481ed266713e (patch) | |
tree | 2e61cd7264a55beb4660532b996438cf3a446d16 /tools/llvm-profdata | |
parent | 94ec09ae32e03ca0cfcaf8df5a8efa17bd3cbe8c (diff) | |
download | llvm-fb007bb98c8943b734111ab601e4481ed266713e.tar.gz llvm-fb007bb98c8943b734111ab601e4481ed266713e.tar.bz2 llvm-fb007bb98c8943b734111ab601e4481ed266713e.tar.xz |
llvm-profdata: Update to use the naive text format with function hash
This also uses line_iterator to simplify the parsing logic.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@204210 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'tools/llvm-profdata')
-rw-r--r-- | tools/llvm-profdata/llvm-profdata.cpp | 154 |
1 files changed, 53 insertions, 101 deletions
diff --git a/tools/llvm-profdata/llvm-profdata.cpp b/tools/llvm-profdata/llvm-profdata.cpp index b338efd27e..b4dd55c833 100644 --- a/tools/llvm-profdata/llvm-profdata.cpp +++ b/tools/llvm-profdata/llvm-profdata.cpp @@ -13,6 +13,7 @@ #include "llvm/ADT/StringRef.h" #include "llvm/Support/CommandLine.h" +#include "llvm/Support/LineIterator.h" #include "llvm/Support/ManagedStatic.h" #include "llvm/Support/MemoryBuffer.h" #include "llvm/Support/PrettyStackTrace.h" @@ -32,56 +33,6 @@ static cl::opt<std::string> OutputFilename("output", cl::value_desc("output"), static cl::alias OutputFilenameA("o", cl::desc("Alias for --output"), cl::aliasopt(OutputFilename)); -static bool readLine(const char *&Start, const char *End, StringRef &S) { - if (Start == End) - return false; - - for (const char *I = Start; I != End; ++I) { - assert(*I && "unexpected binary data"); - if (*I == '\n') { - S = StringRef(Start, I - Start); - Start = I + 1; - return true; - } - } - - S = StringRef(Start, End - Start); - Start = End; - return true; -} - -static StringRef getWord(const char *&Start, const char *End) { - for (const char *I = Start; I != End; ++I) - if (*I == ' ') { - StringRef S(Start, I - Start); - Start = I + 1; - return S; - } - StringRef S(Start, End - Start); - Start = End; - return S; -} - -static size_t splitWords(const StringRef &Line, std::vector<StringRef> &Words) { - const char *Start = Line.data(); - const char *End = Line.data() + Line.size(); - Words.clear(); - while (Start != End) - Words.push_back(getWord(Start, End)); - return Words.size(); -} - -static bool getNumber(const StringRef &S, uint64_t &N) { - N = 0; - for (StringRef::iterator I = S.begin(), E = S.end(); I != E; ++I) - if (*I >= '0' && *I <= '9') - N = N * 10 + (*I - '0'); - else - return false; - - return true; -} - static void exitWithError(const std::string &Message, const std::string &Filename, int64_t Line = -1) { errs() << "error: " << Filename; @@ -115,63 +66,64 @@ int main(int argc, char **argv) { if (!ErrorInfo.empty()) exitWithError(ErrorInfo, OutputFilename); - const char *Start1 = File1->getBufferStart(); - const char *Start2 = File2->getBufferStart(); - const char *End1 = File1->getBufferEnd(); - const char *End2 = File2->getBufferEnd(); - const char *P1 = Start1; - const char *P2 = Start2; - - StringRef Line1, Line2; - int64_t Num = 0; - while (readLine(P1, End1, Line1)) { - ++Num; - if (!readLine(P2, End2, Line2)) - exitWithError("truncated file", Filename2, Num); - - std::vector<StringRef> Words1, Words2; - if (splitWords(Line1, Words1) != splitWords(Line2, Words2)) - exitWithError("data mismatch", Filename2, Num); - - if (Words1.size() > 2) - exitWithError("invalid data", Filename1, Num); - - if (Words1.empty()) { + enum {ReadName, ReadHash, ReadCount, ReadCounters} State = ReadName; + uint64_t N1, N2, NumCounters; + line_iterator I1(*File1, '#'), I2(*File2, '#'); + for (; !I1.is_at_end() && !I2.is_at_end(); ++I1, ++I2) { + if (I1->empty()) { + if (!I2->empty()) + exitWithError("data mismatch", Filename2, I2.line_number()); Output << "\n"; continue; } - - if (Words1.size() == 2) { - if (Words1[0] != Words2[0]) - exitWithError("function name mismatch", Filename2, Num); - - uint64_t N1, N2; - if (!getNumber(Words1[1], N1)) - exitWithError("bad function count", Filename1, Num); - if (!getNumber(Words2[1], N2)) - exitWithError("bad function count", Filename2, Num); - + switch (State) { + case ReadName: + if (*I1 != *I2) + exitWithError("function name mismatch", Filename2, I2.line_number()); + Output << *I1 << "\n"; + State = ReadHash; + break; + case ReadHash: + if (I1->getAsInteger(10, N1)) + exitWithError("bad function hash", Filename1, I1.line_number()); + if (I2->getAsInteger(10, N2)) + exitWithError("bad function hash", Filename2, I2.line_number()); if (N1 != N2) - exitWithError("function count mismatch", Filename2, Num); - - Output << Line1 << "\n"; - continue; + exitWithError("function hash mismatch", Filename2, I2.line_number()); + Output << N1 << "\n"; + State = ReadCount; + break; + case ReadCount: + if (I1->getAsInteger(10, N1)) + exitWithError("bad function count", Filename1, I1.line_number()); + if (I2->getAsInteger(10, N2)) + exitWithError("bad function count", Filename2, I2.line_number()); + if (N1 != N2) + exitWithError("function count mismatch", Filename2, I2.line_number()); + Output << N1 << "\n"; + NumCounters = N1; + State = ReadCounters; + break; + case ReadCounters: + if (I1->getAsInteger(10, N1)) + exitWithError("invalid counter", Filename1, I1.line_number()); + if (I2->getAsInteger(10, N2)) + exitWithError("invalid counter", Filename2, I2.line_number()); + uint64_t Sum = N1 + N2; + if (Sum < N1) + exitWithError("counter overflow", Filename2, I2.line_number()); + Output << N1 + N2 << "\n"; + if (--NumCounters == 0) + State = ReadName; + break; } - - uint64_t N1, N2; - if (!getNumber(Words1[0], N1)) - exitWithError("invalid counter", Filename1, Num); - if (!getNumber(Words2[0], N2)) - exitWithError("invalid counter", Filename2, Num); - - uint64_t Sum = N1 + N2; - if (Sum < N1) - exitWithError("counter overflow", Filename2, Num); - - Output << N1 + N2 << "\n"; } - if (readLine(P2, End2, Line2)) - exitWithError("truncated file", Filename1, Num + 1); + if (!I1.is_at_end()) + exitWithError("truncated file", Filename1, I1.line_number()); + if (!I2.is_at_end()) + exitWithError("truncated file", Filename2, I2.line_number()); + if (State != ReadName) + exitWithError("truncated file", Filename1, I1.line_number()); return 0; } |