x86: XENPF_set_processor_pminfo handler adjustments
authorKeir Fraser <keir.fraser@citrix.com>
Thu, 24 Jul 2008 13:16:47 +0000 (14:16 +0100)
committerKeir Fraser <keir.fraser@citrix.com>
Thu, 24 Jul 2008 13:16:47 +0000 (14:16 +0100)
Only handle information passed up from dom0 when actually controlling
the respective functionality. Only count up CPUs once for each CPU.
Allow dom0 to provide information incrementally.

Signed-off-by: Jan Beulich <jbeulich@novell.com>
xen/arch/x86/platform_hypercall.c

index 0e2579d23d1f4811f038ff7b362ba738cf796ae3..5a882c7057200376ea19dcf3015760ca5d87d4c3 100644 (file)
@@ -355,6 +355,11 @@ ret_t do_platform_op(XEN_GUEST_HANDLE(xen_platform_op_t) u_xenpf_op)
             struct processor_pminfo *pmpt;
             struct processor_performance *pxpt;
 
+            if ( !(xen_processor_pmbits & XEN_PROCESSOR_PM_PX) )
+            {
+                ret = -ENOSYS;
+                break;
+            }
             if ( cpuid < 0 )
             {
                 ret = -EINVAL;
@@ -373,6 +378,7 @@ ret_t do_platform_op(XEN_GUEST_HANDLE(xen_platform_op_t) u_xenpf_op)
                 memcpy ((void *)&pxpt->status_register,
                     (void *)&xenpxpt->status_register,
                     sizeof(struct xen_pct_register));
+                pxpt->init |= XEN_PX_PCT;
             }
             if ( xenpxpt->flags & XEN_PX_PSS ) 
             {
@@ -390,6 +396,7 @@ ret_t do_platform_op(XEN_GUEST_HANDLE(xen_platform_op_t) u_xenpf_op)
                     break;
                 }
                 pxpt->state_count = xenpxpt->state_count;
+                pxpt->init |= XEN_PX_PSS;
             }
             if ( xenpxpt->flags & XEN_PX_PSD )
             {
@@ -397,14 +404,18 @@ ret_t do_platform_op(XEN_GUEST_HANDLE(xen_platform_op_t) u_xenpf_op)
                 memcpy ((void *)&pxpt->domain_info,
                     (void *)&xenpxpt->domain_info,
                     sizeof(struct xen_psd_package));
+                pxpt->init |= XEN_PX_PSD;
             }
             if ( xenpxpt->flags & XEN_PX_PPC )
+            {
                 pxpt->ppc = xenpxpt->ppc;
+                pxpt->init |= XEN_PX_PPC;
+            }
 
-            if ( xenpxpt->flags == ( XEN_PX_PCT | XEN_PX_PSS | 
-                XEN_PX_PSD | XEN_PX_PPC ) )
+            if ( pxpt->init == ( XEN_PX_PCT | XEN_PX_PSS |
+                                 XEN_PX_PSD | XEN_PX_PPC ) )
             {
-                pxpt->init =1;
+                pxpt->init |= 0x80000000;
                 cpu_count++;
             }
             if ( cpu_count == num_online_cpus() )
@@ -418,10 +429,20 @@ ret_t do_platform_op(XEN_GUEST_HANDLE(xen_platform_op_t) u_xenpf_op)
         }
  
         case XEN_PM_CX:
+            if ( !(xen_processor_pmbits & XEN_PROCESSOR_PM_CX) )
+            {
+                ret = -ENOSYS;
+                break;
+            }
             ret = set_cx_pminfo(op->u.set_pminfo.id, &op->u.set_pminfo.power);
             break;
 
         case XEN_PM_TX:
+            if ( !(xen_processor_pmbits & XEN_PROCESSOR_PM_TX) )
+            {
+                ret = -ENOSYS;
+                break;
+            }
             ret = -EINVAL;
             break;