[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-changelog] [xen-unstable] [IA64] hwclock support



# HG changeset patch
# User awilliam@xxxxxxxxxxx
# Node ID 9fed76231248e5416dd71c55f9a4bfd690868043
# Parent  1bab7d65171b762bb3cf1ae426bc6c403f847ebf
[IA64] hwclock support

This patch supports the hwclock on Domain-0.
It adds the following EFI runtime service emulations for the 
hwclock support.
 1. SetTime
 2. Get/SetWakeupTime

Signed-off-by: Masaki Kanno <kanno.masaki@xxxxxxxxxxxxxx>
---
 xen/arch/ia64/xen/fw_emul.c |  136 +++++++++++++++++++++++++++++++++++++++-----
 1 files changed, 123 insertions(+), 13 deletions(-)

diff -r 1bab7d65171b -r 9fed76231248 xen/arch/ia64/xen/fw_emul.c
--- a/xen/arch/ia64/xen/fw_emul.c       Fri Sep 01 13:04:02 2006 -0600
+++ b/xen/arch/ia64/xen/fw_emul.c       Mon Sep 04 14:45:20 2006 -0600
@@ -395,28 +395,124 @@ efi_emulate_get_time(
        unsigned long tv_addr, unsigned long tc_addr,
        IA64FAULT *fault)
 {
-       unsigned long tv = 0, tc = 0;
+       unsigned long tv, tc = 0;
        struct page_info *tv_page = NULL;
        struct page_info *tc_page = NULL;
-       efi_status_t status;
+       efi_status_t status = 0;
 
        //printf("efi_get_time(%016lx,%016lx) called\n", tv_addr, tc_addr);
        tv = efi_translate_domain_addr(tv_addr, fault, &tv_page);
        if (*fault != IA64_NO_FAULT)
-               return 0;
+               goto errout;
        if (tc_addr) {
                tc = efi_translate_domain_addr(tc_addr, fault, &tc_page);
-               if (*fault != IA64_NO_FAULT) {
-                       put_page(tv_page);
-                       return 0;
-               }
-       }
+               if (*fault != IA64_NO_FAULT)
+                       goto errout;
+       }
+
        //printf("efi_get_time(%016lx,%016lx) translated to xen virtual 
address\n", tv, tc);
        status = (*efi.get_time)((efi_time_t *) tv, (efi_time_cap_t *) tc);
        //printf("efi_get_time returns %lx\n", status);
+
+errout:
        if (tc_page != NULL)
                put_page(tc_page);
-       put_page(tv_page);
+       if (tv_page != NULL)
+               put_page(tv_page);
+
+       return status;
+}
+
+static efi_status_t
+efi_emulate_set_time(
+       unsigned long tv_addr, IA64FAULT *fault)
+{
+       unsigned long tv;
+       struct page_info *tv_page = NULL;
+       efi_status_t status = 0;
+
+       if (current->domain != dom0)
+               return EFI_UNSUPPORTED;
+
+       tv = efi_translate_domain_addr(tv_addr, fault, &tv_page);
+       if (*fault != IA64_NO_FAULT)
+               goto errout;
+
+       status = (*efi.set_time)((efi_time_t *)tv);
+
+errout:
+       if (tv_page != NULL)
+               put_page(tv_page);
+
+       return status;
+}
+
+static efi_status_t
+efi_emulate_get_wakeup_time(
+       unsigned long e_addr, unsigned long p_addr,
+       unsigned long tv_addr, IA64FAULT *fault)
+{
+       unsigned long enabled, pending, tv;
+       struct page_info *e_page = NULL, *p_page = NULL,
+                        *tv_page = NULL;
+       efi_status_t status = 0;
+
+       if (current->domain != dom0)
+               return EFI_UNSUPPORTED;
+
+       if (!e_addr || !p_addr || !tv_addr)
+               return EFI_INVALID_PARAMETER;
+
+       enabled = efi_translate_domain_addr(e_addr, fault, &e_page);
+       if (*fault != IA64_NO_FAULT)
+               goto errout;
+       pending = efi_translate_domain_addr(p_addr, fault, &p_page);
+       if (*fault != IA64_NO_FAULT)
+               goto errout;
+       tv = efi_translate_domain_addr(tv_addr, fault, &tv_page);
+       if (*fault != IA64_NO_FAULT)
+               goto errout;
+
+       status = (*efi.get_wakeup_time)((efi_bool_t *)enabled,
+                                       (efi_bool_t *)pending,
+                                       (efi_time_t *)tv);
+
+errout:
+       if (e_page != NULL)
+               put_page(e_page);
+       if (p_page != NULL)
+               put_page(p_page);
+       if (tv_page != NULL)
+               put_page(tv_page);
+
+       return status;
+}
+
+static efi_status_t
+efi_emulate_set_wakeup_time(
+       unsigned long enabled, unsigned long tv_addr,
+       IA64FAULT *fault)
+{
+       unsigned long tv = 0;
+       struct page_info *tv_page = NULL;
+       efi_status_t status = 0;
+
+       if (current->domain != dom0)
+               return EFI_UNSUPPORTED;
+
+       if (tv_addr) {
+               tv = efi_translate_domain_addr(tv_addr, fault, &tv_page);
+               if (*fault != IA64_NO_FAULT)
+                       goto errout;
+       }
+
+       status = (*efi.set_wakeup_time)((efi_bool_t)enabled,
+                                       (efi_time_t *)tv);
+
+errout:
+       if (tv_page != NULL)
+               put_page(tv_page);
+
        return status;
 }
 
@@ -663,6 +759,24 @@ efi_emulator (struct pt_regs *regs, IA64
                                vcpu_get_gr(v,33),
                                fault);
                break;
+           case FW_HYPERCALL_EFI_SET_TIME:
+               status = efi_emulate_set_time (
+                               vcpu_get_gr(v,32),
+                               fault);
+               break;
+           case FW_HYPERCALL_EFI_GET_WAKEUP_TIME:
+               status = efi_emulate_get_wakeup_time (
+                               vcpu_get_gr(v,32),
+                               vcpu_get_gr(v,33),
+                               vcpu_get_gr(v,34),
+                               fault);
+               break;
+           case FW_HYPERCALL_EFI_SET_WAKEUP_TIME:
+               status = efi_emulate_set_wakeup_time (
+                               vcpu_get_gr(v,32),
+                               vcpu_get_gr(v,33),
+                               fault);
+               break;
            case FW_HYPERCALL_EFI_GET_VARIABLE:
                status = efi_emulate_get_variable (
                                vcpu_get_gr(v,32),
@@ -695,10 +809,6 @@ efi_emulator (struct pt_regs *regs, IA64
                                (u32) vcpu_get_gr(v,34),
                                (efi_memory_desc_t *) vcpu_get_gr(v,35));
                break;
-           case FW_HYPERCALL_EFI_SET_TIME:
-           case FW_HYPERCALL_EFI_GET_WAKEUP_TIME:
-           case FW_HYPERCALL_EFI_SET_WAKEUP_TIME:
-               // FIXME: need fixes in efi.h from 2.6.9
            case FW_HYPERCALL_EFI_GET_NEXT_HIGH_MONO_COUNT:
                // FIXME: need fixes in efi.h from 2.6.9
                status = EFI_UNSUPPORTED;

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.