xref: /freebsd-src/contrib/llvm-project/llvm/include/llvm/DWP/DWPStringPool.h (revision 81ad626541db97eb356e2c1d4a20eb2a26a766ab)
1fe6060f1SDimitry Andric #ifndef LLVM_DWP_DWPSTRINGPOOL_H
2fe6060f1SDimitry Andric #define LLVM_DWP_DWPSTRINGPOOL_H
3fe6060f1SDimitry Andric 
4fe6060f1SDimitry Andric #include "llvm/ADT/DenseMap.h"
5fe6060f1SDimitry Andric #include "llvm/MC/MCSection.h"
6fe6060f1SDimitry Andric #include "llvm/MC/MCStreamer.h"
7fe6060f1SDimitry Andric #include <cassert>
8fe6060f1SDimitry Andric 
9fe6060f1SDimitry Andric namespace llvm {
10fe6060f1SDimitry Andric class DWPStringPool {
11fe6060f1SDimitry Andric 
12fe6060f1SDimitry Andric   struct CStrDenseMapInfo {
getEmptyKeyCStrDenseMapInfo13fe6060f1SDimitry Andric     static inline const char *getEmptyKey() {
14fe6060f1SDimitry Andric       return reinterpret_cast<const char *>(~static_cast<uintptr_t>(0));
15fe6060f1SDimitry Andric     }
getTombstoneKeyCStrDenseMapInfo16fe6060f1SDimitry Andric     static inline const char *getTombstoneKey() {
17fe6060f1SDimitry Andric       return reinterpret_cast<const char *>(~static_cast<uintptr_t>(1));
18fe6060f1SDimitry Andric     }
getHashValueCStrDenseMapInfo19fe6060f1SDimitry Andric     static unsigned getHashValue(const char *Val) {
20fe6060f1SDimitry Andric       assert(Val != getEmptyKey() && "Cannot hash the empty key!");
21fe6060f1SDimitry Andric       assert(Val != getTombstoneKey() && "Cannot hash the tombstone key!");
22fe6060f1SDimitry Andric       return (unsigned)hash_value(StringRef(Val));
23fe6060f1SDimitry Andric     }
isEqualCStrDenseMapInfo24fe6060f1SDimitry Andric     static bool isEqual(const char *LHS, const char *RHS) {
25fe6060f1SDimitry Andric       if (RHS == getEmptyKey())
26fe6060f1SDimitry Andric         return LHS == getEmptyKey();
27fe6060f1SDimitry Andric       if (RHS == getTombstoneKey())
28fe6060f1SDimitry Andric         return LHS == getTombstoneKey();
29fe6060f1SDimitry Andric       return strcmp(LHS, RHS) == 0;
30fe6060f1SDimitry Andric     }
31fe6060f1SDimitry Andric   };
32fe6060f1SDimitry Andric 
33fe6060f1SDimitry Andric   MCStreamer &Out;
34fe6060f1SDimitry Andric   MCSection *Sec;
35fe6060f1SDimitry Andric   DenseMap<const char *, uint32_t, CStrDenseMapInfo> Pool;
36fe6060f1SDimitry Andric   uint32_t Offset = 0;
37fe6060f1SDimitry Andric 
38fe6060f1SDimitry Andric public:
DWPStringPool(MCStreamer & Out,MCSection * Sec)39fe6060f1SDimitry Andric   DWPStringPool(MCStreamer &Out, MCSection *Sec) : Out(Out), Sec(Sec) {}
40fe6060f1SDimitry Andric 
getOffset(const char * Str,unsigned Length)41fe6060f1SDimitry Andric   uint32_t getOffset(const char *Str, unsigned Length) {
42fe6060f1SDimitry Andric     assert(strlen(Str) + 1 == Length && "Ensure length hint is correct");
43fe6060f1SDimitry Andric 
44fe6060f1SDimitry Andric     auto Pair = Pool.insert(std::make_pair(Str, Offset));
45fe6060f1SDimitry Andric     if (Pair.second) {
46*81ad6265SDimitry Andric       Out.switchSection(Sec);
47fe6060f1SDimitry Andric       Out.emitBytes(StringRef(Str, Length));
48fe6060f1SDimitry Andric       Offset += Length;
49fe6060f1SDimitry Andric     }
50fe6060f1SDimitry Andric 
51fe6060f1SDimitry Andric     return Pair.first->second;
52fe6060f1SDimitry Andric   }
53fe6060f1SDimitry Andric };
54fe6060f1SDimitry Andric } // namespace llvm
55fe6060f1SDimitry Andric 
56fe6060f1SDimitry Andric #endif // LLVM_DWP_DWPSTRINGPOOL_H
57