blob: b18eef43520548325e4b55e5824e2188076a98be [file] [log] [blame]
//===- subzero/src/IceIntrinsics.h - List of Ice Intrinsics -----*- C++ -*-===//
//
// The Subzero Code Generator
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
///
/// \file
/// \brief Declares the kinds of intrinsics supported by PNaCl.
///
//===----------------------------------------------------------------------===//
#ifndef SUBZERO_SRC_ICEINTRINSICS_H
#define SUBZERO_SRC_ICEINTRINSICS_H
#include "IceDefs.h"
#include "IceStringPool.h"
#include "IceTypes.h"
namespace Ice {
class InstIntrinsic;
static constexpr size_t kMaxIntrinsicParameters = 6;
namespace Intrinsics {
/// Some intrinsics allow overloading by type. This enum collapses all
/// overloads into a single ID, but the type can still be recovered by the
/// type of the intrinsic's return value and parameters.
enum IntrinsicID {
UnknownIntrinsic = 0,
// Arbitrary (alphabetical) order.
AtomicCmpxchg,
AtomicFence,
AtomicFenceAll,
AtomicIsLockFree,
AtomicLoad,
AtomicRMW,
AtomicStore,
Bswap,
Ctlz,
Ctpop,
Cttz,
Fabs,
Longjmp,
Memcpy,
Memmove,
Memset,
Setjmp,
Sqrt,
Stacksave,
Stackrestore,
Trap,
// The intrinsics below are not part of the PNaCl specification.
AddSaturateSigned,
AddSaturateUnsigned,
LoadSubVector,
MultiplyAddPairs,
MultiplyHighSigned,
MultiplyHighUnsigned,
Nearbyint,
Round,
SignMask,
StoreSubVector,
SubtractSaturateSigned,
SubtractSaturateUnsigned,
VectorPackSigned,
VectorPackUnsigned
};
/// Operations that can be represented by the AtomicRMW intrinsic.
///
/// Do not reorder these values: their order offers forward compatibility of
/// bitcode targeted to PNaCl.
enum AtomicRMWOperation {
AtomicInvalid = 0, // Invalid, keep first.
AtomicAdd,
AtomicSub,
AtomicOr,
AtomicAnd,
AtomicXor,
AtomicExchange,
AtomicNum // Invalid, keep last.
};
/// Memory orderings supported by PNaCl IR.
///
/// Do not reorder these values: their order offers forward compatibility of
/// bitcode targeted to PNaCl.
enum MemoryOrder {
MemoryOrderInvalid = 0, // Invalid, keep first.
MemoryOrderRelaxed,
MemoryOrderConsume,
MemoryOrderAcquire,
MemoryOrderRelease,
MemoryOrderAcquireRelease,
MemoryOrderSequentiallyConsistent,
MemoryOrderNum // Invalid, keep last.
};
/// Verify memory ordering rules for atomic intrinsics. For AtomicCmpxchg,
/// Order is the "success" ordering and OrderOther is the "failure" ordering.
/// Returns true if valid, false if invalid.
// TODO(stichnot,kschimpf): Perform memory order validation in the bitcode
// reader/parser, allowing LLVM and Subzero to share. See
// https://code.google.com/p/nativeclient/issues/detail?id=4126 .
bool isMemoryOrderValid(IntrinsicID ID, uint64_t Order,
uint64_t OrderOther = MemoryOrderInvalid);
enum SideEffects { SideEffects_F = 0, SideEffects_T = 1 };
enum ReturnsTwice { ReturnsTwice_F = 0, ReturnsTwice_T = 1 };
enum MemoryWrite { MemoryWrite_F = 0, MemoryWrite_T = 1 };
/// Basic attributes related to each intrinsic, that are relevant to code
/// generation.
struct IntrinsicInfo {
enum IntrinsicID ID : 29;
enum SideEffects HasSideEffects : 1;
enum ReturnsTwice ReturnsTwice : 1;
enum MemoryWrite IsMemoryWrite : 1;
};
static_assert(sizeof(IntrinsicInfo) == 4, "IntrinsicInfo should be 32 bits");
/// The types of validation values for FullIntrinsicInfo.validateIntrinsic.
enum ValidateIntrinsicValue {
IsValidIntrinsic, /// Valid use of instrinsic.
BadReturnType, /// Return type invalid for intrinsic.
WrongNumOfArgs, /// Wrong number of arguments for intrinsic.
WrongArgType, /// Argument of wrong type.
};
/// The complete set of information about an intrinsic.
struct FullIntrinsicInfo {
struct IntrinsicInfo Info; /// Information that CodeGen would care about.
// Sanity check during parsing.
Type Signature[kMaxIntrinsicParameters];
uint8_t NumTypes;
/// Validates that type signature matches intrinsic. If WrongArgumentType is
/// returned, ArgIndex is set to corresponding argument index.
ValidateIntrinsicValue validateIntrinsic(const Ice::InstIntrinsic *Intrinsic,
SizeT &ArgIndex) const;
/// Returns the return type of the intrinsic.
Type getReturnType() const {
assert(NumTypes > 0);
return Signature[0];
}
/// Returns number of arguments expected.
SizeT getNumArgs() const {
assert(NumTypes > 0);
return NumTypes - 1;
}
/// Returns type of Index-th argument.
Type getArgType(SizeT Index) const;
};
} // namespace Intrinsics
} // end of namespace Ice
#endif // SUBZERO_SRC_ICEINTRINSICS_H