LLVM 24.0.0git
VEFrameLowering.cpp
Go to the documentation of this file.
1//===-- VEFrameLowering.cpp - VE Frame Information ------------------------===//
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 the VE implementation of TargetFrameLowering class.
10//
11// On VE, stack frames are structured as follows:
12//
13// The stack grows downward.
14//
15// All of the individual frame areas on the frame below are optional, i.e. it's
16// possible to create a function so that the particular area isn't present
17// in the frame.
18//
19// At function entry, the "frame" looks as follows:
20//
21// | | Higher address
22// |----------------------------------------------|
23// | Parameter area for this function |
24// |----------------------------------------------|
25// | Register save area (RSA) for this function |
26// |----------------------------------------------|
27// | Return address for this function |
28// |----------------------------------------------|
29// | Frame pointer for this function |
30// |----------------------------------------------| <- sp
31// | | Lower address
32//
33// VE doesn't use on demand stack allocation, so user code generated by LLVM
34// needs to call VEOS to allocate stack frame. VE's ABI want to reduce the
35// number of VEOS calls, so ABI requires to allocate not only RSA (in general
36// CSR, callee saved register) area but also call frame at the prologue of
37// caller function.
38//
39// After the prologue has run, the frame has the following general structure.
40// Note that technically the last frame area (VLAs) doesn't get created until
41// in the main function body, after the prologue is run. However, it's depicted
42// here for completeness.
43//
44// | | Higher address
45// |----------------------------------------------|
46// | Parameter area for this function |
47// |----------------------------------------------|
48// | Register save area (RSA) for this function |
49// |----------------------------------------------|
50// | Return address for this function |
51// |----------------------------------------------|
52// | Frame pointer for this function |
53// |----------------------------------------------| <- fp(=old sp)
54// |.empty.space.to.make.part.below.aligned.in....|
55// |.case.it.needs.more.than.the.standard.16-byte.| (size of this area is
56// |.alignment....................................| unknown at compile time)
57// |----------------------------------------------|
58// | Local variables of fixed size including spill|
59// | slots |
60// |----------------------------------------------| <- bp(not defined by ABI,
61// |.variable-sized.local.variables.(VLAs)........| LLVM chooses SX17)
62// |..............................................| (size of this area is
63// |..............................................| unknown at compile time)
64// |----------------------------------------------| <- stack top (returned by
65// | Parameter area for callee | alloca)
66// |----------------------------------------------|
67// | Register save area (RSA) for callee |
68// |----------------------------------------------|
69// | Return address for callee |
70// |----------------------------------------------|
71// | Frame pointer for callee |
72// |----------------------------------------------| <- sp
73// | | Lower address
74//
75// To access the data in a frame, at-compile time, a constant offset must be
76// computable from one of the pointers (fp, bp, sp) to access it. The size
77// of the areas with a dotted background cannot be computed at compile-time
78// if they are present, making it required to have all three of fp, bp and
79// sp to be set up to be able to access all contents in the frame areas,
80// assuming all of the frame areas are non-empty.
81//
82// For most functions, some of the frame areas are empty. For those functions,
83// it may not be necessary to set up fp or bp:
84// * A base pointer is definitely needed when there are both VLAs and local
85// variables with more-than-default alignment requirements.
86// * A frame pointer is definitely needed when there are local variables with
87// more-than-default alignment requirements.
88//
89// In addition, VE ABI defines RSA frame, return address, and frame pointer
90// as follows:
91//
92// |----------------------------------------------| <- sp+176
93// | %s18...%s33 |
94// |----------------------------------------------| <- sp+48
95// | Linkage area register (%s17) |
96// |----------------------------------------------| <- sp+40
97// | Procedure linkage table register (%plt=%s16) |
98// |----------------------------------------------| <- sp+32
99// | Global offset table register (%got=%s15) |
100// |----------------------------------------------| <- sp+24
101// | Thread pointer register (%tp=%s14) |
102// |----------------------------------------------| <- sp+16
103// | Return address |
104// |----------------------------------------------| <- sp+8
105// | Frame pointer |
106// |----------------------------------------------| <- sp+0
107//
108// NOTE: This description is based on VE ABI and description in
109// AArch64FrameLowering.cpp. Thanks a lot.
110//===----------------------------------------------------------------------===//
111
112#include "VEFrameLowering.h"
113#include "VEInstrInfo.h"
115#include "VESubtarget.h"
123
124using namespace llvm;
125
130
134 uint64_t NumBytes,
135 bool RequireFPUpdate) const {
137 DebugLoc DL;
138 const VEInstrInfo &TII = *STI.getInstrInfo();
139
140 // Insert following codes here as prologue
141 //
142 // st %fp, 0(, %sp) iff !isLeafProc
143 // st %lr, 8(, %sp) iff !isLeafProc
144 // st %got, 24(, %sp) iff hasGOT
145 // st %plt, 32(, %sp) iff hasGOT
146 // st %s17, 40(, %sp) iff hasBP
147 if (!FuncInfo->isLeafProc()) {
148 BuildMI(MBB, MBBI, DL, TII.get(VE::STrii))
149 .addReg(VE::SX11)
150 .addImm(0)
151 .addImm(0)
152 .addReg(VE::SX9);
153 BuildMI(MBB, MBBI, DL, TII.get(VE::STrii))
154 .addReg(VE::SX11)
155 .addImm(0)
156 .addImm(8)
157 .addReg(VE::SX10);
158 }
159 if (hasGOT(MF)) {
160 BuildMI(MBB, MBBI, DL, TII.get(VE::STrii))
161 .addReg(VE::SX11)
162 .addImm(0)
163 .addImm(24)
164 .addReg(VE::SX15);
165 BuildMI(MBB, MBBI, DL, TII.get(VE::STrii))
166 .addReg(VE::SX11)
167 .addImm(0)
168 .addImm(32)
169 .addReg(VE::SX16);
170 }
171 if (hasBP(MF))
172 BuildMI(MBB, MBBI, DL, TII.get(VE::STrii))
173 .addReg(VE::SX11)
174 .addImm(0)
175 .addImm(40)
176 .addReg(VE::SX17);
177}
178
182 uint64_t NumBytes,
183 bool RequireFPUpdate) const {
185 DebugLoc DL;
186 const VEInstrInfo &TII = *STI.getInstrInfo();
187
188 // Insert following codes here as epilogue
189 //
190 // ld %s17, 40(, %sp) iff hasBP
191 // ld %plt, 32(, %sp) iff hasGOT
192 // ld %got, 24(, %sp) iff hasGOT
193 // ld %lr, 8(, %sp) iff !isLeafProc
194 // ld %fp, 0(, %sp) iff !isLeafProc
195 if (hasBP(MF))
196 BuildMI(MBB, MBBI, DL, TII.get(VE::LDrii), VE::SX17)
197 .addReg(VE::SX11)
198 .addImm(0)
199 .addImm(40);
200 if (hasGOT(MF)) {
201 BuildMI(MBB, MBBI, DL, TII.get(VE::LDrii), VE::SX16)
202 .addReg(VE::SX11)
203 .addImm(0)
204 .addImm(32);
205 BuildMI(MBB, MBBI, DL, TII.get(VE::LDrii), VE::SX15)
206 .addReg(VE::SX11)
207 .addImm(0)
208 .addImm(24);
209 }
210 if (!FuncInfo->isLeafProc()) {
211 BuildMI(MBB, MBBI, DL, TII.get(VE::LDrii), VE::SX10)
212 .addReg(VE::SX11)
213 .addImm(0)
214 .addImm(8);
215 BuildMI(MBB, MBBI, DL, TII.get(VE::LDrii), VE::SX9)
216 .addReg(VE::SX11)
217 .addImm(0)
218 .addImm(0);
219 }
220}
221
222void VEFrameLowering::emitSPAdjustment(MachineFunction &MF,
225 int64_t NumBytes,
226 MaybeAlign MaybeAlign) const {
227 DebugLoc DL;
228 const VEInstrInfo &TII = *STI.getInstrInfo();
229
230 if (NumBytes == 0) {
231 // Nothing to do here.
232 } else if (isInt<7>(NumBytes)) {
233 // adds.l %s11, NumBytes@lo, %s11
234 BuildMI(MBB, MBBI, DL, TII.get(VE::ADDSLri), VE::SX11)
235 .addReg(VE::SX11)
236 .addImm(NumBytes);
237 } else if (isInt<32>(NumBytes)) {
238 // lea %s11, NumBytes@lo(, %s11)
239 BuildMI(MBB, MBBI, DL, TII.get(VE::LEArii), VE::SX11)
240 .addReg(VE::SX11)
241 .addImm(0)
242 .addImm(Lo_32(NumBytes));
243 } else {
244 // Emit following codes. This clobbers SX13 which we always know is
245 // available here.
246 // lea %s13, NumBytes@lo
247 // and %s13, %s13, (32)0
248 // lea.sl %sp, NumBytes@hi(%s13, %sp)
249 BuildMI(MBB, MBBI, DL, TII.get(VE::LEAzii), VE::SX13)
250 .addImm(0)
251 .addImm(0)
252 .addImm(Lo_32(NumBytes));
253 BuildMI(MBB, MBBI, DL, TII.get(VE::ANDrm), VE::SX13)
254 .addReg(VE::SX13)
255 .addImm(M0(32));
256 BuildMI(MBB, MBBI, DL, TII.get(VE::LEASLrri), VE::SX11)
257 .addReg(VE::SX11)
258 .addReg(VE::SX13)
259 .addImm(Hi_32(NumBytes));
260 }
261
262 if (MaybeAlign) {
263 // and %sp, %sp, Align-1
264 BuildMI(MBB, MBBI, DL, TII.get(VE::ANDrm), VE::SX11)
265 .addReg(VE::SX11)
266 .addImm(M1(64 - Log2_64(MaybeAlign.valueOrOne().value())));
267 }
268}
269
270void VEFrameLowering::emitSPExtend(MachineFunction &MF, MachineBasicBlock &MBB,
272 DebugLoc DL;
273 const VEInstrInfo &TII = *STI.getInstrInfo();
274
275 // Emit following codes. It is not possible to insert multiple
276 // BasicBlocks in PEI pass, so we emit two pseudo instructions here.
277 //
278 // EXTEND_STACK // pseudo instrcution
279 // EXTEND_STACK_GUARD // pseudo instrcution
280 //
281 // EXTEND_STACK pseudo will be converted by ExpandPostRA pass into
282 // following instructions with multiple basic blocks later.
283 //
284 // thisBB:
285 // brge.l.t %sp, %sl, sinkBB
286 // syscallBB:
287 // ld %s61, 0x18(, %tp) // load param area
288 // or %s62, 0, %s0 // spill the value of %s0
289 // lea %s63, 0x13b // syscall # of grow
290 // shm.l %s63, 0x0(%s61) // store syscall # at addr:0
291 // shm.l %sl, 0x8(%s61) // store old limit at addr:8
292 // shm.l %sp, 0x10(%s61) // store new limit at addr:16
293 // monc // call monitor
294 // or %s0, 0, %s62 // restore the value of %s0
295 // sinkBB:
296 //
297 // EXTEND_STACK_GUARD pseudo will be simply eliminated by ExpandPostRA
298 // pass. This pseudo is required to be at the next of EXTEND_STACK
299 // pseudo in order to protect iteration loop in ExpandPostRA.
300 BuildMI(MBB, MBBI, DL, TII.get(VE::EXTEND_STACK));
301 BuildMI(MBB, MBBI, DL, TII.get(VE::EXTEND_STACK_GUARD));
302}
303
305 MachineBasicBlock &MBB) const {
307 assert(&MF.front() == &MBB && "Shrink-wrapping not yet supported");
308 MachineFrameInfo &MFI = MF.getFrameInfo();
309 const VEInstrInfo &TII = *STI.getInstrInfo();
310 const VERegisterInfo &RegInfo = *STI.getRegisterInfo();
312 bool NeedsStackRealignment = RegInfo.shouldRealignStack(MF);
313
314 // Debug location must be unknown since the first debug location is used
315 // to determine the end of the prologue.
316 DebugLoc DL;
317
318 if (NeedsStackRealignment && !RegInfo.canRealignStack(MF))
319 report_fatal_error("Function \"" + Twine(MF.getName()) +
320 "\" required "
321 "stack re-alignment, but LLVM couldn't handle it "
322 "(probably because it has a dynamic alloca).");
323
324 // Get the number of bytes to allocate from the FrameInfo.
325 // This number of bytes is already aligned to ABI stack alignment.
326 uint64_t NumBytes = MFI.getStackSize();
327
328 // Adjust stack size if this function is not a leaf function since the
329 // VE ABI requires a reserved area at the top of stack as described in
330 // VEFrameLowering.cpp.
331 if (!FuncInfo->isLeafProc()) {
332 // NOTE: The number is aligned to ABI stack alignment after adjustment.
333 NumBytes = STI.getAdjustedFrameSize(NumBytes);
334 }
335
336 // Finally, ensure that the size is sufficiently aligned for the
337 // data on the stack.
338 NumBytes = alignTo(NumBytes, MFI.getMaxAlign());
339
340 // Update stack size with corrected value.
341 MFI.setStackSize(NumBytes);
342
343 // Emit Prologue instructions to save multiple registers.
344 emitPrologueInsns(MF, MBB, MBBI, NumBytes, true);
345
346 // Emit instructions to save SP in FP as follows if this is not a leaf
347 // function:
348 // or %fp, 0, %sp
349 if (!FuncInfo->isLeafProc())
350 BuildMI(MBB, MBBI, DL, TII.get(VE::ORri), VE::SX9)
351 .addReg(VE::SX11)
352 .addImm(0);
353
354 // Emit stack adjust instructions
355 MaybeAlign RuntimeAlign =
356 NeedsStackRealignment ? MaybeAlign(MFI.getMaxAlign()) : std::nullopt;
357 assert((RuntimeAlign == std::nullopt || !FuncInfo->isLeafProc()) &&
358 "SP has to be saved in order to align variable sized stack object!");
359 emitSPAdjustment(MF, MBB, MBBI, -(int64_t)NumBytes, RuntimeAlign);
360
361 if (hasBP(MF)) {
362 // Copy SP to BP.
363 BuildMI(MBB, MBBI, DL, TII.get(VE::ORri), VE::SX17)
364 .addReg(VE::SX11)
365 .addImm(0);
366 }
367
368 // Emit stack extend instructions
369 if (NumBytes != 0)
370 emitSPExtend(MF, MBB, MBBI);
371}
372
376 if (!hasReservedCallFrame(MF)) {
377 MachineInstr &MI = *I;
378 int64_t Size = MI.getOperand(0).getImm();
379 if (MI.getOpcode() == VE::ADJCALLSTACKDOWN)
380 Size = -Size;
381
382 if (Size)
383 emitSPAdjustment(MF, MBB, I, Size);
384 }
385 return MBB.erase(I);
386}
387
389 MachineBasicBlock &MBB) const {
391 DebugLoc DL;
392 MachineBasicBlock::iterator MBBI = MBB.getLastNonDebugInstr();
393 MachineFrameInfo &MFI = MF.getFrameInfo();
394 const VEInstrInfo &TII = *STI.getInstrInfo();
395
396 uint64_t NumBytes = MFI.getStackSize();
397
398 // Emit instructions to retrieve original SP.
399 if (!FuncInfo->isLeafProc()) {
400 // If SP is saved in FP, retrieve it as follows:
401 // or %sp, 0, %fp iff !isLeafProc
402 BuildMI(MBB, MBBI, DL, TII.get(VE::ORri), VE::SX11)
403 .addReg(VE::SX9)
404 .addImm(0);
405 } else {
406 // Emit stack adjust instructions.
407 emitSPAdjustment(MF, MBB, MBBI, NumBytes, std::nullopt);
408 }
409
410 // Emit Epilogue instructions to restore multiple registers.
411 emitEpilogueInsns(MF, MBB, MBBI, NumBytes, true);
412}
413
414// hasFPImpl - Return true if the specified function should have a dedicated
415// frame pointer register. This is true if the function has variable sized
416// allocas or if frame pointer elimination is disabled.
418 const TargetRegisterInfo *RegInfo = MF.getSubtarget().getRegisterInfo();
419
420 const MachineFrameInfo &MFI = MF.getFrameInfo();
421 return MF.disableFramePointerElim() || RegInfo->hasStackRealignment(MF) ||
423}
424
426 const MachineFrameInfo &MFI = MF.getFrameInfo();
427 const TargetRegisterInfo *TRI = STI.getRegisterInfo();
428
429 return MFI.hasVarSizedObjects() && TRI->hasStackRealignment(MF);
430}
431
434
435 // If a global base register is assigned (!= 0), GOT is used.
436 return FuncInfo->getGlobalBaseReg() != 0;
437}
438
440 int FI,
441 Register &FrameReg) const {
442 const MachineFrameInfo &MFI = MF.getFrameInfo();
443 const VERegisterInfo *RegInfo = STI.getRegisterInfo();
444 bool isFixed = MFI.isFixedObjectIndex(FI);
445
446 int64_t FrameOffset = MF.getFrameInfo().getObjectOffset(FI);
447
448 if (!hasFP(MF)) {
449 // If FP is not used, frame indexies are based on a %sp regiter.
450 FrameReg = VE::SX11; // %sp
451 return StackOffset::getFixed(FrameOffset +
453 }
454 if (RegInfo->hasStackRealignment(MF) && !isFixed) {
455 // If data on stack require realignemnt, frame indexies are based on a %sp
456 // or %s17 (bp) register. If there is a variable sized object, bp is used.
457 if (hasBP(MF))
458 FrameReg = VE::SX17; // %bp
459 else
460 FrameReg = VE::SX11; // %sp
461 return StackOffset::getFixed(FrameOffset +
463 }
464 // Use %fp by default.
465 FrameReg = RegInfo->getFrameRegister(MF);
466 return StackOffset::getFixed(FrameOffset);
467}
468
469bool VEFrameLowering::isLeafProc(MachineFunction &MF) const {
470
472 MachineFrameInfo &MFI = MF.getFrameInfo();
473
474 return !MFI.hasCalls() // No calls
475 && !MRI.isPhysRegUsed(VE::SX18) // Registers within limits
476 // (s18 is first CSR)
477 && !MRI.isPhysRegUsed(VE::SX11) // %sp un-used
478 && !hasFP(MF); // Don't need %fp
479}
480
482 BitVector &SavedRegs,
483 RegScavenger *RS) const {
485
486 // Functions having BP need to emit prologue and epilogue to allocate local
487 // buffer on the stack even if the function is a leaf function.
488 if (isLeafProc(MF) && !hasBP(MF)) {
490 FuncInfo->setLeafProc(true);
491 }
492}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock & MBB
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
MachineBasicBlock MachineBasicBlock::iterator MBBI
const HexagonInstrInfo * TII
IRTranslator LLVM IR MI
#define I(x, y, z)
Definition MD5.cpp:57
Register const TargetRegisterInfo * TRI
This file declares the machine register scavenger class.
A debug info location.
Definition DebugLoc.h:126
MachineInstrBundleIterator< MachineInstr > iterator
The MachineFrameInfo class represents an abstract stack frame until prolog/epilog code is inserted.
bool hasVarSizedObjects() const
This method may be called any time after instruction selection is complete to determine if the stack ...
uint64_t getStackSize() const
Return the number of bytes that must be allocated to hold all of the fixed size frame objects.
bool hasCalls() const
Return true if the current function has any function calls.
bool isFrameAddressTaken() const
This method may be called any time after instruction selection is complete to determine if there is a...
Align getMaxAlign() const
Return alignment of this function's frame.
int64_t getObjectOffset(int ObjectIdx) const
Return the assigned stack offset of the specified object from the incoming stack pointer.
void setStackSize(uint64_t Size)
Set the size of the stack.
bool isFixedObjectIndex(int ObjectIdx) const
Returns true if the specified index corresponds to a fixed stack object.
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
StringRef getName() const
getName - Return the name of the corresponding LLVM function.
MachineFrameInfo & getFrameInfo()
getFrameInfo - Return the frame info object for the current function.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
LLVM_ABI bool disableFramePointerElim() const
Returns true if frame pointer elimination should be disabled for this function.
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
const MachineBasicBlock & front() const
const MachineInstrBuilder & addReg(Register RegNo, RegState Flags={}, unsigned SubReg=0) const
Add a new virtual register operand.
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
Representation of each machine instruction.
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
LLVM_ABI bool isPhysRegUsed(MCRegister PhysReg, bool SkipRegMaskTest=false) const
Return true if the specified register is modified or read in this function.
Wrapper class representing virtual and physical registers.
Definition Register.h:20
StackOffset holds a fixed and a scalable offset in bytes.
Definition TypeSize.h:30
int64_t getFixed() const
Returns the fixed component of the stack.
Definition TypeSize.h:46
bool hasFP(const MachineFunction &MF) const
hasFP - Return true if the specified function should have a dedicated frame pointer register.
virtual void determineCalleeSaves(MachineFunction &MF, BitVector &SavedRegs, RegScavenger *RS=nullptr) const
This method determines which of the registers reported by TargetRegisterInfo::getCalleeSavedRegs() sh...
TargetFrameLowering(StackDirection D, Align StackAl, int LAO, Align TransAl=Align(1), bool StackReal=true)
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
virtual const TargetRegisterInfo * getRegisterInfo() const =0
Return the target's register information.
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition Twine.h:82
void emitEpilogueInsns(MachineFunction &MF, MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, uint64_t NumBytes, bool RequireFPUpdate) const
bool hasBP(const MachineFunction &MF) const
const VESubtarget & STI
void emitPrologueInsns(MachineFunction &MF, MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, uint64_t NumBytes, bool RequireFPUpdate) const
MachineBasicBlock::iterator eliminateCallFramePseudoInstr(MachineFunction &MF, MachineBasicBlock &MBB, MachineBasicBlock::iterator I) const override
This method is called during prolog/epilog code insertion to eliminate call frame setup and destroy p...
StackOffset getFrameIndexReference(const MachineFunction &MF, int FI, Register &FrameReg) const override
getFrameIndexReference - This method should return the base register and offset used to reference a f...
bool hasFPImpl(const MachineFunction &MF) const override
void determineCalleeSaves(MachineFunction &MF, BitVector &SavedRegs, RegScavenger *RS=nullptr) const override
This method determines which of the registers reported by TargetRegisterInfo::getCalleeSavedRegs() sh...
void emitEpilogue(MachineFunction &MF, MachineBasicBlock &MBB) const override
void emitPrologue(MachineFunction &MF, MachineBasicBlock &MBB) const override
emitProlog/emitEpilog - These methods insert prolog and epilog code into the function.
VEFrameLowering(const VESubtarget &ST)
bool hasGOT(const MachineFunction &MF) const
bool hasReservedCallFrame(const MachineFunction &MF) const override
hasReservedCallFrame - Under normal circumstances, when a frame pointer is not required,...
const VEInstrInfo * getInstrInfo() const override
Definition VESubtarget.h:52
This is an optimization pass for GlobalISel generic memory operations.
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
constexpr bool isInt(int64_t x)
Checks if an integer fits into the given bit width.
Definition MathExtras.h:166
unsigned Log2_64(uint64_t Value)
Return the floor log base 2 of the specified value, -1 if the value is zero.
Definition MathExtras.h:332
unsigned M1(unsigned Val)
Definition VE.h:377
constexpr uint32_t Hi_32(uint64_t Value)
Return the high 32 bits of a 64 bit value.
Definition MathExtras.h:151
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
Definition Error.cpp:163
constexpr uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.
Definition Alignment.h:144
constexpr uint32_t Lo_32(uint64_t Value)
Return the low 32 bits of a 64 bit value.
Definition MathExtras.h:156
unsigned M0(unsigned Val)
Definition VE.h:376
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition Alignment.h:39
constexpr uint64_t value() const
This is a hole in the type system and should not be abused.
Definition Alignment.h:77
This struct is a compact representation of a valid (power of two) or undefined (0) alignment.
Definition Alignment.h:106
Align valueOrOne() const
For convenience, returns a valid alignment or 1 if undefined.
Definition Alignment.h:130