https://discourse.llvm.org/t/rfc-enhancing-function-alignment-attributes/88019/17 The recently-introduced .prefalign only worked when each function was in its own section (-ffunction-sections), because the section size gave the function body size needed for the alignment rule. This led to -ffunction-sections and -fno-function-sections AsmPrinter differences (#155529), which is rather unusual. This patch fixes this AsmPrinter difference by extending .prefalign to accept an end symbol and a required fill operand: .prefalign <log2_align>, <end_sym>, nop .prefalign <log2_align>, <end_sym>, <fill_byte> The first operand is a log2 alignment value (e.g. 4 means 16-byte alignment). The body size (end_sym_offset - start_offset) determines the alignment: body_size < pref_align => ComputedAlign = std::bit_ceil(body_size) body_size >= pref_align => ComputedAlign = pref_align To also enforce a minimum alignment, emit a .p2align before .prefalign. The fill operand is required: `nop` generates target-appropriate NOP instructions via writeNopData, while an integer in [0,255] fills the padding with that byte value. Initialize MCSection::CurFragList to nullptr and add a null check to skip ELFObjectWriter-created sections like .strtab/.symtab that never receive changeSection calls. relaxPrefAlign is called in both layoutSection and relaxFragment. The layoutSection call ensures correct initial padding before relaxOnce, and is also needed for the post-finishLayout re-layout where relaxOnce is not used. relaxPrefAlign walks forward to the end symbol to compute BodySize (summing fragment sizes), avoiding dependence on stale downstream symbol offsets.
23 lines
710 B
LLVM
23 lines
710 B
LLVM
; RUN: llc < %s -mtriple=i686-pc-win32 | FileCheck -check-prefix=CHECK -check-prefix=WIN32 %s
|
|
; RUN: llc < %s -mtriple=x86_64-pc-win32 | FileCheck -check-prefix=CHECK -check-prefix=WIN64 %s
|
|
; RUN: llc < %s -mtriple=i386-linux-gnu | FileCheck -check-prefix=LINUX %s
|
|
|
|
target datalayout = "e-m:x-p:32:32-i64:64-f80:32-n8:16:32-a:0:32-S32"
|
|
target triple = "i686-pc-windows-msvc18.0.0"
|
|
|
|
; Don't emit empty functions on Windows; it can lead to duplicate entries
|
|
; (multiple functions sharing the same RVA) in the Guard CF Function Table which
|
|
; the kernel refuses to load.
|
|
|
|
define void @f() {
|
|
entry:
|
|
unreachable
|
|
|
|
; CHECK-LABEL: f:
|
|
; WIN32: nop
|
|
; WIN64: nop
|
|
; LINUX-NOT: {{^[[:space:]]+}}nop
|
|
; LINUX-NOT: ud2
|
|
|
|
}
|