The 05/03/2024 14:01, Joey Gouly wrote:
> Implement the PKEYS interface, using the Permission Overlay Extension.
...
> +#ifdef CONFIG_ARCH_HAS_PKEYS
> +int arch_set_user_pkey_access(struct task_struct *tsk, int pkey, unsigned 
> long init_val)
> +{
> +     u64 new_por = POE_RXW;
> +     u64 old_por;
> +     u64 pkey_shift;
> +
> +     if (!arch_pkeys_enabled())
> +             return -ENOSPC;
> +
> +     /*
> +      * This code should only be called with valid 'pkey'
> +      * values originating from in-kernel users.  Complain
> +      * if a bad value is observed.
> +      */
> +     if (WARN_ON_ONCE(pkey >= arch_max_pkey()))
> +             return -EINVAL;
> +
> +     /* Set the bits we need in POR:  */
> +     if (init_val & PKEY_DISABLE_ACCESS)
> +             new_por = POE_X;
> +     else if (init_val & PKEY_DISABLE_WRITE)
> +             new_por = POE_RX;
> +

given that the architecture allows r,w,x permissions to be
set independently, should we have a 'PKEY_DISABLE_EXEC' or
similar api flag?

(on other targets it can be some invalid value that fails)

> +     /* Shift the bits in to the correct place in POR for pkey: */
> +     pkey_shift = pkey * POR_BITS_PER_PKEY;
> +     new_por <<= pkey_shift;
> +
> +     /* Get old POR and mask off any old bits in place: */
> +     old_por = read_sysreg_s(SYS_POR_EL0);
> +     old_por &= ~(POE_MASK << pkey_shift);
> +
> +     /* Write old part along with new part: */
> +     write_sysreg_s(old_por | new_por, SYS_POR_EL0);
> +
> +     return 0;
> +}
> +#endif
> -- 
> 2.25.1
> 

Reply via email to