[PATCH 2/4] domctl: Provide appropriate error code when PIRQs are not supported

Milan Djokic posted 4 patches 6 days, 22 hours ago
[PATCH 2/4] domctl: Provide appropriate error code when PIRQs are not supported
Posted by Milan Djokic 6 days, 22 hours ago
When PIRQs are not supported (e.g. for arm), XEN_DOMCTL_irq_permission
command is not handled.
This results with default (-ENOSYS) error code returned to control domain.
Update command handling to return -EOPNOTSUPP if control domain
invokes it by mistake when PIRQs are not supported.
Also exclude xsm_irq_permission hooks from compilation when
PIRQs are not supported.

Signed-off-by: Milan Djokic <milan_djokic@epam.com>
---
 xen/common/domctl.c     | 6 ++++--
 xen/include/xsm/dummy.h | 4 ++--
 xen/include/xsm/xsm.h   | 6 ++++--
 xen/xsm/dummy.c         | 2 ++
 xen/xsm/flask/hooks.c   | 5 ++++-
 5 files changed, 16 insertions(+), 7 deletions(-)

diff --git a/xen/common/domctl.c b/xen/common/domctl.c
index 29a7726d32..159864bc99 100644
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -638,9 +638,9 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xen_domctl_t) u_domctl)
         }
         break;
 
-#ifdef CONFIG_HAS_PIRQ
     case XEN_DOMCTL_irq_permission:
     {
+#ifdef CONFIG_HAS_PIRQ
         unsigned int pirq = op->u.irq_permission.pirq, irq;
         int allow = op->u.irq_permission.allow_access;
 
@@ -656,9 +656,11 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xen_domctl_t) u_domctl)
             ret = irq_permit_access(d, irq);
         else
             ret = irq_deny_access(d, irq);
+#else
+        ret = -EOPNOTSUPP;
+#endif
         break;
     }
-#endif
 
     case XEN_DOMCTL_iomem_permission:
     {
diff --git a/xen/include/xsm/dummy.h b/xen/include/xsm/dummy.h
index e801dbcdba..6f6de161f9 100644
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -555,14 +555,14 @@ static XSM_INLINE int cf_check xsm_unmap_domain_irq(
     XSM_ASSERT_ACTION(XSM_HOOK);
     return xsm_default_action(action, current->domain, d);
 }
-
+#ifdef CONFIG_HAS_PIRQ
 static XSM_INLINE int cf_check xsm_irq_permission(
     XSM_DEFAULT_ARG struct domain *d, int pirq, uint8_t allow)
 {
     XSM_ASSERT_ACTION(XSM_HOOK);
     return xsm_default_action(action, current->domain, d);
 }
-
+#endif
 static XSM_INLINE int cf_check xsm_iomem_permission(
     XSM_DEFAULT_ARG struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
 {
diff --git a/xen/include/xsm/xsm.h b/xen/include/xsm/xsm.h
index 2d831d7745..b85cf9933a 100644
--- a/xen/include/xsm/xsm.h
+++ b/xen/include/xsm/xsm.h
@@ -113,7 +113,9 @@ struct xsm_ops {
     int (*unmap_domain_irq)(struct domain *d, int irq, const void *data);
     int (*bind_pt_irq)(struct domain *d, struct xen_domctl_bind_pt_irq *bind);
     int (*unbind_pt_irq)(struct domain *d, struct xen_domctl_bind_pt_irq *bind);
+#ifdef CONFIG_HAS_PIRQ
     int (*irq_permission)(struct domain *d, int pirq, uint8_t allow);
+#endif
     int (*iomem_permission)(struct domain *d, uint64_t s, uint64_t e,
                             uint8_t allow);
     int (*iomem_mapping)(struct domain *d, uint64_t s, uint64_t e,
@@ -504,13 +506,13 @@ static inline int xsm_unbind_pt_irq(
 {
     return alternative_call(xsm_ops.unbind_pt_irq, d, bind);
 }
-
+#ifdef CONFIG_HAS_PIRQ
 static inline int xsm_irq_permission(
     xsm_default_t def, struct domain *d, int pirq, uint8_t allow)
 {
     return alternative_call(xsm_ops.irq_permission, d, pirq, allow);
 }
-
+#endif
 static inline int xsm_iomem_permission(
     xsm_default_t def, struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
 {
diff --git a/xen/xsm/dummy.c b/xen/xsm/dummy.c
index 96dc82ac2e..28ef4a0beb 100644
--- a/xen/xsm/dummy.c
+++ b/xen/xsm/dummy.c
@@ -73,7 +73,9 @@ static const struct xsm_ops __initconst_cf_clobber dummy_ops = {
     .unmap_domain_irq              = xsm_unmap_domain_irq,
     .bind_pt_irq                   = xsm_bind_pt_irq,
     .unbind_pt_irq                 = xsm_unbind_pt_irq,
+#ifdef CONFIG_HAS_PIRQ
     .irq_permission                = xsm_irq_permission,
+#endif
     .iomem_permission              = xsm_iomem_permission,
     .iomem_mapping                 = xsm_iomem_mapping,
     .pci_config_permission         = xsm_pci_config_permission,
diff --git a/xen/xsm/flask/hooks.c b/xen/xsm/flask/hooks.c
index 9f3915617c..63e4b4c353 100644
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -1110,13 +1110,14 @@ static int cf_check flask_unbind_pt_irq(
 {
     return current_has_perm(d, SECCLASS_RESOURCE, RESOURCE__REMOVE);
 }
-
+#ifdef CONFIG_HAS_PIRQ
 static int cf_check flask_irq_permission(
     struct domain *d, int pirq, uint8_t access)
 {
     /* the PIRQ number is not useful; real IRQ is checked during mapping */
     return current_has_perm(d, SECCLASS_RESOURCE, resource_to_perm(access));
 }
+#endif
 
 struct iomem_has_perm_data {
     uint32_t ssid;
@@ -1943,7 +1944,9 @@ static const struct xsm_ops __initconst_cf_clobber flask_ops = {
     .unmap_domain_irq = flask_unmap_domain_irq,
     .bind_pt_irq = flask_bind_pt_irq,
     .unbind_pt_irq = flask_unbind_pt_irq,
+#ifdef CONFIG_HAS_PIRQ
     .irq_permission = flask_irq_permission,
+#endif
     .iomem_permission = flask_iomem_permission,
     .iomem_mapping = flask_iomem_mapping,
     .pci_config_permission = flask_pci_config_permission,
-- 
2.43.0
Re: [PATCH 2/4] domctl: Provide appropriate error code when PIRQs are not supported
Posted by Grygorii Strashko 3 days, 21 hours ago
Hi Milan,

Thank you for your patch.

On 05.12.25 22:36, Milan Djokic wrote:
> When PIRQs are not supported (e.g. for arm), XEN_DOMCTL_irq_permission
> command is not handled.
> This results with default (-ENOSYS) error code returned to control domain.
> Update command handling to return -EOPNOTSUPP if control domain
> invokes it by mistake when PIRQs are not supported.

> Also exclude xsm_irq_permission hooks from compilation when
> PIRQs are not supported.

Could you please do not mix such a clean up a changes with functional changes?
It deserve to be standalone patch.

> 
> Signed-off-by: Milan Djokic <milan_djokic@epam.com>
> ---
>   xen/common/domctl.c     | 6 ++++--
>   xen/include/xsm/dummy.h | 4 ++--
>   xen/include/xsm/xsm.h   | 6 ++++--
>   xen/xsm/dummy.c         | 2 ++
>   xen/xsm/flask/hooks.c   | 5 ++++-
>   5 files changed, 16 insertions(+), 7 deletions(-)
> 
> diff --git a/xen/common/domctl.c b/xen/common/domctl.c
> index 29a7726d32..159864bc99 100644
> --- a/xen/common/domctl.c
> +++ b/xen/common/domctl.c
> @@ -638,9 +638,9 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xen_domctl_t) u_domctl)
>           }
>           break;
>   
> -#ifdef CONFIG_HAS_PIRQ
>       case XEN_DOMCTL_irq_permission:
>       {
> +#ifdef CONFIG_HAS_PIRQ
>           unsigned int pirq = op->u.irq_permission.pirq, irq;
>           int allow = op->u.irq_permission.allow_access;
>   
> @@ -656,9 +656,11 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xen_domctl_t) u_domctl)
>               ret = irq_permit_access(d, irq);
>           else
>               ret = irq_deny_access(d, irq);
> +#else
> +        ret = -EOPNOTSUPP;
> +#endif
>           break;
>       }
> -#endif
>   
>       case XEN_DOMCTL_iomem_permission:
>       {
> diff --git a/xen/include/xsm/dummy.h b/xen/include/xsm/dummy.h
> index e801dbcdba..6f6de161f9 100644
> --- a/xen/include/xsm/dummy.h
> +++ b/xen/include/xsm/dummy.h
> @@ -555,14 +555,14 @@ static XSM_INLINE int cf_check xsm_unmap_domain_irq(
>       XSM_ASSERT_ACTION(XSM_HOOK);
>       return xsm_default_action(action, current->domain, d);
>   }
> -
> +#ifdef CONFIG_HAS_PIRQ
>   static XSM_INLINE int cf_check xsm_irq_permission(
>       XSM_DEFAULT_ARG struct domain *d, int pirq, uint8_t allow)
>   {
>       XSM_ASSERT_ACTION(XSM_HOOK);
>       return xsm_default_action(action, current->domain, d);
>   }
> -

[...]

-- 
Best regards,
-grygorii
Re: [PATCH 2/4] domctl: Provide appropriate error code when PIRQs are not supported
Posted by Jan Beulich 4 days, 6 hours ago
On 05.12.2025 21:36, Milan Djokic wrote:
> When PIRQs are not supported (e.g. for arm), XEN_DOMCTL_irq_permission
> command is not handled.
> This results with default (-ENOSYS) error code returned to control domain.
> Update command handling to return -EOPNOTSUPP if control domain
> invokes it by mistake when PIRQs are not supported.

Did you consider simply replacing the bogus ENOSYS by EOPNOTSUPP? (Assuming
the difference in error code really makes a difference to callers.)

> --- a/xen/include/xsm/dummy.h
> +++ b/xen/include/xsm/dummy.h
> @@ -555,14 +555,14 @@ static XSM_INLINE int cf_check xsm_unmap_domain_irq(
>      XSM_ASSERT_ACTION(XSM_HOOK);
>      return xsm_default_action(action, current->domain, d);
>  }
> -
> +#ifdef CONFIG_HAS_PIRQ
>  static XSM_INLINE int cf_check xsm_irq_permission(
>      XSM_DEFAULT_ARG struct domain *d, int pirq, uint8_t allow)
>  {
>      XSM_ASSERT_ACTION(XSM_HOOK);
>      return xsm_default_action(action, current->domain, d);
>  }
> -
> +#endif
>  static XSM_INLINE int cf_check xsm_iomem_permission(
>      XSM_DEFAULT_ARG struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
>  {

Why would you zap blank lines like this (also elsewhere)?

Jan
Re: [PATCH 2/4] domctl: Provide appropriate error code when PIRQs are not supported
Posted by Milan Djokic 3 days, 6 hours ago
On 12/8/25 14:08, Jan Beulich wrote:
> On 05.12.2025 21:36, Milan Djokic wrote:
>> When PIRQs are not supported (e.g. for arm), XEN_DOMCTL_irq_permission
>> command is not handled.
>> This results with default (-ENOSYS) error code returned to control domain.
>> Update command handling to return -EOPNOTSUPP if control domain
>> invokes it by mistake when PIRQs are not supported.
> 
> Did you consider simply replacing the bogus ENOSYS by EOPNOTSUPP? (Assuming
> the difference in error code really makes a difference to callers.)
> 

Yes, this is the simplest approach. I didn’t do it because I wanted to 
keep a distinction between commands that are part of the Xen interface 
but not supported on the current configuration/platform, and commands 
that don’t exist at all. I also tried to follow the existing pattern, 
where unsupported commands are handled explicitly rather than falling 
through to the default case (e.g. set_llc_colors, soft_reset, etc).
If this distinction isn’t useful, then yes, I can definitely just rely 
on a default-case error.

>> --- a/xen/include/xsm/dummy.h
>> +++ b/xen/include/xsm/dummy.h
>> @@ -555,14 +555,14 @@ static XSM_INLINE int cf_check xsm_unmap_domain_irq(
>>       XSM_ASSERT_ACTION(XSM_HOOK);
>>       return xsm_default_action(action, current->domain, d);
>>   }
>> -
>> +#ifdef CONFIG_HAS_PIRQ
>>   static XSM_INLINE int cf_check xsm_irq_permission(
>>       XSM_DEFAULT_ARG struct domain *d, int pirq, uint8_t allow)
>>   {
>>       XSM_ASSERT_ACTION(XSM_HOOK);
>>       return xsm_default_action(action, current->domain, d);
>>   }
>> -
>> +#endif
>>   static XSM_INLINE int cf_check xsm_iomem_permission(
>>       XSM_DEFAULT_ARG struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
>>   {
> 
> Why would you zap blank lines like this (also elsewhere)?


Will fix this.

Re: [PATCH 2/4] domctl: Provide appropriate error code when PIRQs are not supported
Posted by Jan Beulich 3 days, 6 hours ago
On 09.12.2025 13:48, Milan Djokic wrote:
> On 12/8/25 14:08, Jan Beulich wrote:
>> On 05.12.2025 21:36, Milan Djokic wrote:
>>> When PIRQs are not supported (e.g. for arm), XEN_DOMCTL_irq_permission
>>> command is not handled.
>>> This results with default (-ENOSYS) error code returned to control domain.
>>> Update command handling to return -EOPNOTSUPP if control domain
>>> invokes it by mistake when PIRQs are not supported.
>>
>> Did you consider simply replacing the bogus ENOSYS by EOPNOTSUPP? (Assuming
>> the difference in error code really makes a difference to callers.)
> 
> Yes, this is the simplest approach. I didn’t do it because I wanted to 
> keep a distinction between commands that are part of the Xen interface 
> but not supported on the current configuration/platform, and commands 
> that don’t exist at all. I also tried to follow the existing pattern, 
> where unsupported commands are handled explicitly rather than falling 
> through to the default case (e.g. set_llc_colors, soft_reset, etc).
> If this distinction isn’t useful, then yes, I can definitely just rely 
> on a default-case error.

Before you (possibly) follow this route, maybe I should mention that there
have been discussions around this in the past (sorry, no pointers, too
long ago). IOW ahead of any consolidation (and making things consistent),
imo as a community we need to settle on where exactly we consider ENOSYS
valid to be used. My take is that almost all of the uses we (still) have
are wrong. In particular all the ones for "unknown sub-op".

Jan