10b57cec5SDimitry Andric //===-- ARMBaseInfo.cpp - ARM Base encoding information------------===//
20b57cec5SDimitry Andric //
30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric //
70b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric //
90b57cec5SDimitry Andric // This file provides basic encoding and assembly information for ARM.
100b57cec5SDimitry Andric //
110b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
120b57cec5SDimitry Andric #include "ARMBaseInfo.h"
130b57cec5SDimitry Andric #include "llvm/ADT/ArrayRef.h"
140b57cec5SDimitry Andric #include "llvm/ADT/SmallVector.h"
150b57cec5SDimitry Andric
160b57cec5SDimitry Andric using namespace llvm;
170b57cec5SDimitry Andric namespace llvm {
expandPredBlockMask(ARM::PredBlockMask BlockMask,ARMVCC::VPTCodes Kind)185ffd83dbSDimitry Andric ARM::PredBlockMask expandPredBlockMask(ARM::PredBlockMask BlockMask,
195ffd83dbSDimitry Andric ARMVCC::VPTCodes Kind) {
205ffd83dbSDimitry Andric using PredBlockMask = ARM::PredBlockMask;
215ffd83dbSDimitry Andric assert(Kind != ARMVCC::None && "Cannot expand a mask with None!");
22*06c3fb27SDimitry Andric assert(llvm::countr_zero((unsigned)BlockMask) != 0 && "Mask is already full");
235ffd83dbSDimitry Andric
245ffd83dbSDimitry Andric auto ChooseMask = [&](PredBlockMask AddedThen, PredBlockMask AddedElse) {
255ffd83dbSDimitry Andric return Kind == ARMVCC::Then ? AddedThen : AddedElse;
265ffd83dbSDimitry Andric };
275ffd83dbSDimitry Andric
285ffd83dbSDimitry Andric switch (BlockMask) {
295ffd83dbSDimitry Andric case PredBlockMask::T:
305ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TT, PredBlockMask::TE);
315ffd83dbSDimitry Andric case PredBlockMask::TT:
325ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TTT, PredBlockMask::TTE);
335ffd83dbSDimitry Andric case PredBlockMask::TE:
345ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TET, PredBlockMask::TEE);
355ffd83dbSDimitry Andric case PredBlockMask::TTT:
365ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TTTT, PredBlockMask::TTTE);
375ffd83dbSDimitry Andric case PredBlockMask::TTE:
385ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TTET, PredBlockMask::TTEE);
395ffd83dbSDimitry Andric case PredBlockMask::TET:
405ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TETT, PredBlockMask::TETE);
415ffd83dbSDimitry Andric case PredBlockMask::TEE:
425ffd83dbSDimitry Andric return ChooseMask(PredBlockMask::TEET, PredBlockMask::TEEE);
435ffd83dbSDimitry Andric default:
445ffd83dbSDimitry Andric llvm_unreachable("Unknown Mask");
455ffd83dbSDimitry Andric }
465ffd83dbSDimitry Andric }
475ffd83dbSDimitry Andric
480b57cec5SDimitry Andric namespace ARMSysReg {
490b57cec5SDimitry Andric
500b57cec5SDimitry Andric // lookup system register using 12-bit SYSm value.
510b57cec5SDimitry Andric // Note: the search is uniqued using M1 mask
lookupMClassSysRegBy12bitSYSmValue(unsigned SYSm)520b57cec5SDimitry Andric const MClassSysReg *lookupMClassSysRegBy12bitSYSmValue(unsigned SYSm) {
530b57cec5SDimitry Andric return lookupMClassSysRegByM1Encoding12(SYSm);
540b57cec5SDimitry Andric }
550b57cec5SDimitry Andric
560b57cec5SDimitry Andric // returns APSR with _<bits> qualifier.
570b57cec5SDimitry Andric // Note: ARMv7-M deprecates using MSR APSR without a _<bits> qualifier
lookupMClassSysRegAPSRNonDeprecated(unsigned SYSm)580b57cec5SDimitry Andric const MClassSysReg *lookupMClassSysRegAPSRNonDeprecated(unsigned SYSm) {
590b57cec5SDimitry Andric return lookupMClassSysRegByM2M3Encoding8((1<<9)|(SYSm & 0xFF));
600b57cec5SDimitry Andric }
610b57cec5SDimitry Andric
620b57cec5SDimitry Andric // lookup system registers using 8-bit SYSm value
lookupMClassSysRegBy8bitSYSmValue(unsigned SYSm)630b57cec5SDimitry Andric const MClassSysReg *lookupMClassSysRegBy8bitSYSmValue(unsigned SYSm) {
640b57cec5SDimitry Andric return ARMSysReg::lookupMClassSysRegByM2M3Encoding8((1<<8)|(SYSm & 0xFF));
650b57cec5SDimitry Andric }
660b57cec5SDimitry Andric
670b57cec5SDimitry Andric #define GET_MCLASSSYSREG_IMPL
680b57cec5SDimitry Andric #include "ARMGenSystemRegister.inc"
690b57cec5SDimitry Andric
700b57cec5SDimitry Andric } // end namespace ARMSysReg
710b57cec5SDimitry Andric
720b57cec5SDimitry Andric namespace ARMBankedReg {
730b57cec5SDimitry Andric #define GET_BANKEDREG_IMPL
740b57cec5SDimitry Andric #include "ARMGenSystemRegister.inc"
750b57cec5SDimitry Andric } // end namespce ARMSysReg
760b57cec5SDimitry Andric } // end namespace llvm
77