155 lines · c
1//===- TypeDetail.h - MLIR Type storage details -----------------*- 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-exception6//7//===----------------------------------------------------------------------===//8//9// This holds implementation details of Type.10//11//===----------------------------------------------------------------------===//12#ifndef TYPEDETAIL_H_13#define TYPEDETAIL_H_14 15#include "mlir/IR/AffineMap.h"16#include "mlir/IR/BuiltinTypes.h"17#include "mlir/IR/MLIRContext.h"18#include "mlir/IR/OperationSupport.h"19#include "mlir/IR/TypeRange.h"20#include "llvm/ADT/bit.h"21#include "llvm/Support/TrailingObjects.h"22 23namespace mlir {24 25namespace detail {26 27/// Integer Type Storage and Uniquing.28struct IntegerTypeStorage : public TypeStorage {29 IntegerTypeStorage(unsigned width,30 IntegerType::SignednessSemantics signedness)31 : width(width), signedness(signedness) {}32 33 /// The hash key used for uniquing.34 using KeyTy = std::tuple<unsigned, IntegerType::SignednessSemantics>;35 36 static llvm::hash_code hashKey(const KeyTy &key) {37 return llvm::hash_value(key);38 }39 40 bool operator==(const KeyTy &key) const {41 return KeyTy(width, signedness) == key;42 }43 44 static IntegerTypeStorage *construct(TypeStorageAllocator &allocator,45 KeyTy key) {46 return new (allocator.allocate<IntegerTypeStorage>())47 IntegerTypeStorage(std::get<0>(key), std::get<1>(key));48 }49 50 KeyTy getAsKey() const { return KeyTy(width, signedness); }51 52 unsigned width : 30;53 IntegerType::SignednessSemantics signedness : 2;54};55 56/// Function Type Storage and Uniquing.57struct FunctionTypeStorage : public TypeStorage {58 FunctionTypeStorage(unsigned numInputs, unsigned numResults,59 Type const *inputsAndResults)60 : numInputs(numInputs), numResults(numResults),61 inputsAndResults(inputsAndResults) {}62 63 /// The hash key used for uniquing.64 using KeyTy = std::tuple<TypeRange, TypeRange>;65 bool operator==(const KeyTy &key) const {66 if (std::get<0>(key) == getInputs())67 return std::get<1>(key) == getResults();68 return false;69 }70 71 /// Construction.72 static FunctionTypeStorage *construct(TypeStorageAllocator &allocator,73 const KeyTy &key) {74 auto [inputs, results] = key;75 76 // Copy the inputs and results into the bump pointer.77 SmallVector<Type, 16> types;78 types.reserve(inputs.size() + results.size());79 types.append(inputs.begin(), inputs.end());80 types.append(results.begin(), results.end());81 auto typesList = allocator.copyInto(ArrayRef<Type>(types));82 83 // Initialize the memory using placement new.84 return new (allocator.allocate<FunctionTypeStorage>())85 FunctionTypeStorage(inputs.size(), results.size(), typesList.data());86 }87 88 ArrayRef<Type> getInputs() const {89 return ArrayRef<Type>(inputsAndResults, numInputs);90 }91 ArrayRef<Type> getResults() const {92 return ArrayRef<Type>(inputsAndResults + numInputs, numResults);93 }94 95 KeyTy getAsKey() const { return KeyTy(getInputs(), getResults()); }96 97 unsigned numInputs;98 unsigned numResults;99 Type const *inputsAndResults;100};101 102/// A type representing a collection of other types.103struct TupleTypeStorage final104 : public TypeStorage,105 private llvm::TrailingObjects<TupleTypeStorage, Type> {106 friend llvm::TrailingObjects<TupleTypeStorage, Type>;107 using KeyTy = TypeRange;108 109 TupleTypeStorage(unsigned numTypes) : numElements(numTypes) {}110 111 /// Construction.112 static TupleTypeStorage *construct(TypeStorageAllocator &allocator,113 TypeRange key) {114 // Allocate a new storage instance.115 auto byteSize = TupleTypeStorage::totalSizeToAlloc<Type>(key.size());116 auto *rawMem = allocator.allocate(byteSize, alignof(TupleTypeStorage));117 auto *result = ::new (rawMem) TupleTypeStorage(key.size());118 119 // Copy in the element types into the trailing storage.120 llvm::uninitialized_copy(key, result->getTrailingObjects());121 return result;122 }123 124 bool operator==(const KeyTy &key) const { return key == getTypes(); }125 126 /// Return the number of held types.127 unsigned size() const { return numElements; }128 129 /// Return the held types.130 ArrayRef<Type> getTypes() const { return getTrailingObjects(size()); }131 132 KeyTy getAsKey() const { return getTypes(); }133 134 /// The number of tuple elements.135 unsigned numElements;136};137 138/// Checks if the memorySpace has supported Attribute type.139bool isSupportedMemorySpace(Attribute memorySpace);140 141/// Wraps deprecated integer memory space to the new Attribute form.142Attribute wrapIntegerMemorySpace(unsigned memorySpace, MLIRContext *ctx);143 144/// Replaces default memorySpace (integer == `0`) with empty Attribute.145Attribute skipDefaultMemorySpace(Attribute memorySpace);146 147/// [deprecated] Returns the memory space in old raw integer representation.148/// New `Attribute getMemorySpace()` method should be used instead.149unsigned getMemorySpaceAsInt(Attribute memorySpace);150 151} // namespace detail152} // namespace mlir153 154#endif // TYPEDETAIL_H_155