Uprobes and uretprobes do not work with the 2-byte NOP that is prefixed with 0x66
Issue
-
Uprobes and uretprobes do not work with the 2-byte NOP that is prefixed with 0x66
-
The icc "-hotpatch" option inserts a 2-byte NOP instruction encoded as "0x66 0x90" at the beginning of every function.
Example:
0x00000000127f0f00 <+0>: 66 90 xchg %ax,%ax <<< 2-byte NOP "0x66 0x90" added by icc hotpatch option
0x00000000127f0f02 <+2>: 55 push %rbp <<< begin regular function prologue
0x00000000127f0f03 <+3>: 48 89 e5 mov %rsp,%rbp
0x00000000127f0f06 <+6>: 48 81 ec e0 01 00 00 sub $0x1e0,%rsp
0x00000000127f0f0d <+13>: 48 89 5d e0 mov %rbx,-0x20(%rbp)
...
- The problem with this kind of NOP instruction is that it is not supported by the uprobes code in the Linux kernel. Specifically, the kernel function branch_setup_xol_ops in arch/x86/kernel/uprobes.c contains a check that returns ENOTSUPP if an instruction is prefixed with "0x66":
/x86/kernel/uprobes.c:
/*
* 16-bit overrides such as CALLW (66 e8 nn nn) are not supported.
* Intel and AMD behavior differ in 64-bit mode: Intel ignores 66 prefix.
* No one uses these insns, reject any branch insns with such prefix.
*/
for_each_insn_prefix(insn, i, p) {
if (p == 0x66)
return -ENOTSUPP;
}
- Due to this behavior, neither uprobes nor uretprobes can be used with applications that have been compiled with icc hotpatch support
Environment
- Red Hat Enterprise Linux 7 All
- Red Hat Enterprise Linux 8 All
- Intel icc compiler (-hotpatch option)
Subscriber exclusive content
A Red Hat subscription provides unlimited access to our knowledgebase, tools, and much more.