Liste des Groupes | Revenir à c arch |
On 3/9/2024 9:09 AM, Scott Lurndal wrote:Capabilities sounds like something previously implemented in mainframe class computers. It reminds me of games where the units have capabilities.mitchalsup@aol.com (MitchAlsup1) writes:It is doable, at least.I have been in CPU design for a very long time. I did a HS level>
design (calculator) in 1968 3 years before the Bomar Brain, did
a #60 design in college as a Jr, and started doing professional
designs (Mc 88100) in 1983.
>
With all this background and long term in this career, I can say
without a trace of doubt, that I am not <yet> smart enough to do
a capabilities ISA/system and get it out the door without errors.
>
On the other hand, My 66000 Architecture is immune to most attack
strategies now in vogue:: Return Oriented Programming, RowHammer,
Spectré, GOT overwrites, Buffer Overflows,... All without having
any semblance of capabilities; and all without any performance
degradations other than typical cache and TLB effects.
On the gripping hand, the Burroughs Large systems capability based
design is still processing data almost sixty years after the original
B5500 was introduced.
>
There CHERI designs on silicon in existence
>
https://www.morello-project.org/
Main open question is if they can deliver enough on their claims in a way that justifies the cost of the memory tagging (eg, where one needs to tag whether or not each memory location holds a valid capability).
As I see it, "locking things down" would likely require turning things like "malloc()/free()", "dlopen()/dlsym()/...", etc, into system calls (and generally giving the kernel a much more active role in this process).I think this may not be necessary, but I have to read some more. The capabilities have transfer rules which might make it possible to use existing code. They have ported things over to Riscv. It cannot be too mountainous a task.
Or, change the description, as being mostly a tool to eliminate things like buffer overflow exploits and memory corruption, and as a fairly powerful debugging feature.Yeah, IMO explicit upper and lower bounds would be better even though it uses more memory. The whole manipulation of the bounds is complex. I sketched out using a 256b capability descriptor. Some of the bits can be trimmed from the bounds if things are page aligned.
But, say, note that it would not be sufficient, say, for things like sandboxing hostile code within a shared address space with another program that needs to be kept protected.
Granted, the strength could likely be improved (in the face of trying to prevent hostile code from being able to steal capabilities) through creative use of ASLR. Along with ABI features, such as "scratch register scrubbing" (say, loading zeroes into scratch registers on function return, such as to prevent capabilities from being leaked through via registers), marking function pointers as "Execute Only" etc.
As noted, a capability system would likely still be pretty strong against things like buffer overflows (but if only being used to mitigate buffer overflows, is a bit overkill; so the main "interesting" case is if it can be used to make an "unbreakable sandbox" for potentially hostile machine code).
*: If it is possible to perform a Load or (worse, Capability Load) through a function pointer, this is likely to be a significant attack vector. Need to make it so that function pointers can only be used to call things. Protecting against normal data loads would be needed mostly to try to prevent code from being able to gain access to a known pointer and possibly side-step the ASLR (say, if it can figure out that the address it wants to access is reachable from a capability that the code has access to).
Though, on my side of things, it is possible I could revive a modified form of the 128-bit ABI, while dropping the VAS back down to 48 bits, and turn it into a more CHERI-like form (with explicit upper and lower bounds and access-enable flags, rather than a shared-exponent size and bias scheme).
Can note the XMOV.x and XLEA.x instructions were already defined as having the needed semantics, unlike with 64-bit pointers, where the bounds-checking semantics were opt-in. Would need to add instructions for things like sub-setting the capabilities, etc.
In this case, register and memory tagging could be added, possibly with a "Capability Enable" flag somewhere, which would modify some behaviors:
XMOV.x will trap if the address is not flagged as a valid capability;
The normal MOV.x instructions would be disallowed with this flag set.
With possibly a partial exception for PC rel.
Handling of global registers may need some rethinking.
The XMOV instruction would be required to MOV capabilities;
A pair of MOV instructions would no longer be valid.
Though, likely, this could be used in combination with the existing security model, and with ASLR (well, because, if one has a good RNG, this can be moderately effective; can't forge access to things if there is no way to figure out where they are; and ASLR and page-level protection can still offer a line of defense if the program can figure out a hole to sidestep the capability system).
Though, still unclear how to prevent a program from "stealing" other images global registers. Could ALSR the PBO indices (used for reloading the Global Pointer), and if it is not possible to read through a function pointer, it may make it difficult to guess the PBO index for something like a shared library.
An approach used by something like ELF FDPIC would not be ideal, as the function call mechanism would itself expose the capability of the callee's GOT, which could likely be mined for capabilities to other things, ...
It is likely that the capability memory tagging would need to be managed by the L2 cache. Would need some mechanism for the tag-bits memory (say, 2MB for 256MB at 1b per 16B line). Would also need to somehow work this flag bit into the ringbus messaging.
Though, in the immediate future, this wouldn't gain much in my case.
...
Les messages affichés proviennent d'usenet.