1//===-- llvm/Support/Compression.h ---Compression----------------*- C++ -*-===// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8// 9// This file contains basic functions for compression/decompression. 10// 11//===----------------------------------------------------------------------===// 12 13#ifndef LLVM_SUPPORT_COMPRESSION_H 14#define LLVM_SUPPORT_COMPRESSION_H 15 16#include "llvm/ADT/ArrayRef.h" 17#include "llvm/Support/DataTypes.h" 18 19namespace llvm { 20template <typename T> class SmallVectorImpl; 21class Error; 22 23// None indicates no compression. The other members are a subset of 24// compression::Format, which is used for compressed debug sections in some 25// object file formats (e.g. ELF). This is a separate class as we may add new 26// compression::Format members for non-debugging purposes. 27enum class DebugCompressionType { 28 None, ///< No compression 29 Zlib, ///< zlib 30 Zstd, ///< Zstandard 31}; 32 33namespace compression { 34namespace zlib { 35 36constexpr int NoCompression = 0; 37constexpr int BestSpeedCompression = 1; 38constexpr int DefaultCompression = 6; 39constexpr int BestSizeCompression = 9; 40 41bool isAvailable(); 42 43void compress(ArrayRef<uint8_t> Input, 44 SmallVectorImpl<uint8_t> &CompressedBuffer, 45 int Level = DefaultCompression); 46 47Error decompress(ArrayRef<uint8_t> Input, uint8_t *Output, 48 size_t &UncompressedSize); 49 50Error decompress(ArrayRef<uint8_t> Input, SmallVectorImpl<uint8_t> &Output, 51 size_t UncompressedSize); 52 53} // End of namespace zlib 54 55namespace zstd { 56 57constexpr int NoCompression = -5; 58constexpr int BestSpeedCompression = 1; 59constexpr int DefaultCompression = 5; 60constexpr int BestSizeCompression = 12; 61 62bool isAvailable(); 63 64void compress(ArrayRef<uint8_t> Input, 65 SmallVectorImpl<uint8_t> &CompressedBuffer, 66 int Level = DefaultCompression); 67 68Error decompress(ArrayRef<uint8_t> Input, uint8_t *Output, 69 size_t &UncompressedSize); 70 71Error decompress(ArrayRef<uint8_t> Input, SmallVectorImpl<uint8_t> &Output, 72 size_t UncompressedSize); 73 74} // End of namespace zstd 75 76enum class Format { 77 Zlib, 78 Zstd, 79}; 80 81inline Format formatFor(DebugCompressionType Type) { 82 switch (Type) { 83 case DebugCompressionType::None: 84 llvm_unreachable("not a compression type"); 85 case DebugCompressionType::Zlib: 86 return Format::Zlib; 87 case DebugCompressionType::Zstd: 88 return Format::Zstd; 89 } 90 llvm_unreachable(""); 91} 92 93struct Params { 94 constexpr Params(Format F) 95 : format(F), level(F == Format::Zlib ? zlib::DefaultCompression 96 : zstd::DefaultCompression) {} 97 Params(DebugCompressionType Type) : Params(formatFor(Type)) {} 98 99 Format format; 100 int level; 101 // This may support multi-threading for zstd in the future. Note that 102 // different threads may produce different output, so be careful if certain 103 // output determinism is desired. 104}; 105 106// Return nullptr if LLVM was built with support (LLVM_ENABLE_ZLIB, 107// LLVM_ENABLE_ZSTD) for the specified compression format; otherwise 108// return a string literal describing the reason. 109const char *getReasonIfUnsupported(Format F); 110 111// Compress Input with the specified format P.Format. If Level is -1, use 112// *::DefaultCompression for the format. 113void compress(Params P, ArrayRef<uint8_t> Input, 114 SmallVectorImpl<uint8_t> &Output); 115 116// Decompress Input. The uncompressed size must be available. 117Error decompress(DebugCompressionType T, ArrayRef<uint8_t> Input, 118 uint8_t *Output, size_t UncompressedSize); 119Error decompress(Format F, ArrayRef<uint8_t> Input, 120 SmallVectorImpl<uint8_t> &Output, size_t UncompressedSize); 121Error decompress(DebugCompressionType T, ArrayRef<uint8_t> Input, 122 SmallVectorImpl<uint8_t> &Output, size_t UncompressedSize); 123 124} // End of namespace compression 125 126} // End of namespace llvm 127 128#endif 129