Lines Matching +full:loc +full:- +full:code

1 // SPDX-License-Identifier: GPL-2.0-only
3 * Copyright (C) 2022 - Google LLC
19 // This minimal DWARF CFI parser is partially based on the code in
21 // https://refspecs.linuxbase.org/LSB_4.0.0/LSB-Core-generic/LSB-Core-generic/ehframechpt.html
64 static void __always_inline scs_patch_loc(u64 loc) in scs_patch_loc() argument
66 u32 insn = le32_to_cpup((void *)loc); in scs_patch_loc()
70 *(u32 *)loc = cpu_to_le32(SCS_PUSH); in scs_patch_loc()
73 *(u32 *)loc = cpu_to_le32(SCS_POP); in scs_patch_loc()
88 asm("dc civac, %0" :: "r"(loc)); in scs_patch_loc()
91 :: "r"(loc)); in scs_patch_loc()
104 size--; in skip_xleb128()
154 int size = frame->size - offsetof(struct eh_frame, opcodes) + 4; in scs_handle_fde_frame()
155 u64 loc = (u64)offset_to_ptr(&frame->initial_loc); in scs_handle_fde_frame() local
156 const u8 *opcode = frame->opcodes; in scs_handle_fde_frame()
160 loc = (u64)&frame->initial_loc64 + frame->initial_loc64; in scs_handle_fde_frame()
161 opcode = frame->opcodes64; in scs_handle_fde_frame()
162 size -= 8; in scs_handle_fde_frame()
171 size -= l + 1; in scs_handle_fde_frame()
174 * Starting from 'loc', apply the CFA opcodes that advance the location in scs_handle_fde_frame()
177 while (size-- > 0) { in scs_handle_fde_frame()
185 loc += *opcode++ * code_alignment_factor; in scs_handle_fde_frame()
186 size--; in scs_handle_fde_frame()
190 loc += *opcode++ * code_alignment_factor; in scs_handle_fde_frame()
191 loc += (*opcode++ << 8) * code_alignment_factor; in scs_handle_fde_frame()
192 size -= 2; in scs_handle_fde_frame()
210 scs_patch_loc(loc - 4); in scs_handle_fde_frame()
214 // advance loc in scs_handle_fde_frame()
215 loc += (opcode[-1] & 0x3f) * code_alignment_factor; in scs_handle_fde_frame()
238 if (frame->size == 0 || in scs_patch()
239 frame->size == U32_MAX || in scs_patch()
240 frame->size > size) in scs_patch()
243 if (frame->cie_id_or_pointer == 0) { in scs_patch()
249 if (strcmp(frame->augmentation_string, "zR")) in scs_patch()
253 * The code alignment factor is a uleb128 encoded field in scs_patch()
260 if ((frame->code_alignment_factor & BIT(7)) || in scs_patch()
261 (frame->data_alignment_factor & BIT(7)) || in scs_patch()
262 frame->return_address_register != 30 || in scs_patch()
263 frame->augmentation_data_size != 1) in scs_patch()
266 code_alignment_factor = frame->code_alignment_factor; in scs_patch()
268 switch (frame->fde_pointer_format) { in scs_patch()
287 p += sizeof(frame->size) + frame->size; in scs_patch()
288 size -= sizeof(frame->size) + frame->size; in scs_patch()