Open kito-cheng opened 6 months ago
cc @ved-rivos
My concern about this proposal is that, with the 32-bit bitmap, we can't have more than 32 extensions. That might be OK for x86-64 that is controlled only by Intel and AMD, but it is likely that we would have way more extensions than x86-64 for RISC-V. I'm not sure even 64 bits is enough. Maybe we should avoid the bitmap completely?
@rui314 GNU property is kind of key-value structure, key is 32 bit integer, and we have 536,870,912 can use for the key per the definition of GNU_PROPERTY_LOPROC and GNU_PROPERTY_HIPROC.
/* Processor-specific semantics, lo */
#define GNU_PROPERTY_LOPROC 0xc0000000
/* Processor-specific semantics, hi */
#define GNU_PROPERTY_HIPROC 0xdfffffff
So we have 536,870,912 * 32 rather than only 32-bit bitmap :)
@kito-cheng Ah, you are right. Even though I've implemented the feature to the linker, I forgot the actual on-file format. Thank you for pointing that out!
Thanks for the proposal. On Arm/x86, if all relocatable files contain .note.gnu.property
(which contains NT_GNU_PROPERTY_TYPE_0
notes) with the GNU_PROPERTY_X86_FEATURE_1_IBT
bit set, the linker will mark the output as compatible with the feature. Assembly files often lack .note.gnu.property
, making the CFI features difficult to deploy...
That said, this is most viable proposal. Defining GNU program property looks good for x86/Arm parity.
You may want to mention that n_type
is NT_GNU_PROPERTY_TYPE_0
.
Add property for CFI extension
"property" is a heavily overloaded term. Consider "program property" or just use .note.gnu.property
to be more specific.
@kito-cheng Isn't the usefulness of this degraded by the fact that we only allocate 1 32-bit property instead of the ~ 3 * 32768 allocated on x86? When we start to use the next bitmap, an old linker won't be able to propagate it, and so on.
Split base program property part into https://github.com/riscv-non-isa/riscv-elf-psabi-doc/pull/428
ChangeLog:
GNU_PROPERTY_RISCV_FEATURE_1_ZICFILP
to GNU_PROPERTY_RISCV_FEATURE_1_CFI_LP_SIMPLE
GNU_PROPERTY_RISCV_FEATURE_1_ZICFISS
to GNU_PROPERTY_RISCV_FEATURE_1_CFI_SS
GNU_PROPERTY_RISCV_FEATURE_1_CFI_LP_SIMPLE
, label will always set to 1
.Changes:
GNU_PROPERTY_RISCV_FEATURE_1_CFI_LP_SIMPLE
, label will always set to 0.Why do we need both the dynamic tag and the GNU property? Surely the type of the PLT entries should be part of what the GNU property encodes.
I'm not sure it's a good idea to merge this without simultaneously having a design for the multi-label case. There are a few things that I think are needed for multi-label, like software-guarded branches to and from the PLT and avoiding landing pads for symbols that cannot legally be called indirectly, that won't be well exercised by single labels and aren't even in this proposal.
@sorear
Why do we need both the dynamic tag and the GNU property? Surely the type of the PLT entries should be part of what the GNU property encodes.
Good point...I was try to learn from AArch64, they have define both GNU prop and dynamic tag, but I realized they didn't use that dynamic tag at all, so...let drop that :P
I'm not sure it's a good idea to merge this without simultaneously having a design for the multi-label case. There are a few things that I think are needed for multi-label, like software-guarded branches to and from the PLT and avoiding landing pads for symbols that cannot legally be called indirectly, that won't be well exercised by single labels and aren't even in this proposal.
Yeah, my plan is send out a separated PR for that, we have implement simple scheme with slight variant, so simple scheme version should be fine so far, and we gonna to design and implement complex scheme in next few month.
And here is the source tree for who is interesting on that : https://github.com/sifive/riscv-gnu-toolchain/tree/cfi-dev included qemu (Contribute by Rivos) and GNU toolchain.
Changes:
GNU_PROPERTY_RISCV_FEATURE_1_CFI_LP_SIMPLE
to GNU_PROPERTY_RISCV_FEATURE_1_CFI_LP_UNLABELED
We introduce .note.gnu.property section to store infomations that linker or runtime system may use, and we define two bit for landing pad and shadow stack.
Those two bit will checked by loader - and use that info to enable the landing pad checking and/or shadow stack feature.