xen-vtx-unstable
changeset 4849:a68686aaebc3
bitkeeper revision 1.1389.15.13 (42821f23dLMLc5Ql8Y-rUwoatYBI6g)
Split out context fetching into separate DOM0 op
make GETDOMAININFO a little more sensible with respect to MP
make coredump dump all cpu contexts
Signed-off-by: Kip Macy <kmacy@netapp.com>
Signed-off-by: Christian Limpach <Christian.Limpach@cl.cam.ac.uk>
Split out context fetching into separate DOM0 op
make GETDOMAININFO a little more sensible with respect to MP
make coredump dump all cpu contexts
Signed-off-by: Kip Macy <kmacy@netapp.com>
Signed-off-by: Christian Limpach <Christian.Limpach@cl.cam.ac.uk>
author | cl349@firebug.cl.cam.ac.uk[cl349] |
---|---|
date | Wed May 11 15:05:07 2005 +0000 (2005-05-11) |
parents | 3ac0994c8240 |
children | b78b16c06b85 |
files | tools/libxc/xc.h tools/libxc/xc_core.c tools/libxc/xc_domain.c tools/libxc/xc_linux_build.c tools/libxc/xc_linux_restore.c tools/libxc/xc_linux_save.c tools/libxc/xc_plan9_build.c tools/libxc/xc_private.c tools/libxc/xc_ptrace.c tools/libxc/xc_vmx_build.c xen/common/dom0_ops.c xen/include/public/dom0_ops.h |
line diff
1.1 --- a/tools/libxc/xc.h Wed May 11 14:15:56 2005 +0000 1.2 +++ b/tools/libxc/xc.h Wed May 11 15:05:07 2005 +0000 1.3 @@ -110,8 +110,10 @@ int xc_waitdomain_core(int domain, 1.4 1.5 typedef struct { 1.6 u32 domid; 1.7 - unsigned int cpu; 1.8 + unsigned int flags; 1.9 + unsigned int processors; 1.10 unsigned int vcpus; 1.11 + u16 n_vcpus; 1.12 unsigned int dying:1, crashed:1, shutdown:1, 1.13 paused:1, blocked:1, running:1; 1.14 unsigned int shutdown_reason; /* only meaningful if shutdown==1 */ 1.15 @@ -199,11 +201,11 @@ int xc_domain_getinfo(int xc_handle, 1.16 * domain 1.17 * @return 0 on success, -1 on failure 1.18 */ 1.19 -int xc_domain_getfullinfo(int xc_handle, 1.20 - u32 domid, 1.21 - u32 vcpu, 1.22 - xc_domaininfo_t *info, 1.23 - vcpu_guest_context_t *ctxt); 1.24 +int xc_domain_get_vcpu_context(int xc_handle, 1.25 + u32 domid, 1.26 + u32 vcpu, 1.27 + vcpu_guest_context_t *ctxt); 1.28 + 1.29 int xc_domain_setcpuweight(int xc_handle, 1.30 u32 domid, 1.31 float weight);
2.1 --- a/tools/libxc/xc_core.c Wed May 11 14:15:56 2005 +0000 2.2 +++ b/tools/libxc/xc_core.c Wed May 11 15:05:07 2005 +0000 2.3 @@ -7,6 +7,7 @@ 2.4 /* number of pages to write at a time */ 2.5 #define DUMP_INCREMENT 4 * 1024 2.6 #define round_pgup(_p) (((_p)+(PAGE_SIZE-1))&PAGE_MASK) 2.7 + 2.8 static int 2.9 copy_from_domain_page(int xc_handle, 2.10 u32 domid, 2.11 @@ -28,13 +29,14 @@ xc_domain_dumpcore(int xc_handle, 2.12 u32 domid, 2.13 const char *corename) 2.14 { 2.15 - vcpu_guest_context_t st_ctxt, *ctxt = &st_ctxt; 2.16 unsigned long nr_pages; 2.17 unsigned long *page_array; 2.18 - xc_domaininfo_t st_info, *info = &st_info; 2.19 + xc_dominfo_t info; 2.20 int i, dump_fd; 2.21 char *dump_mem, *dump_mem_start = NULL; 2.22 struct xc_core_header header; 2.23 + vcpu_guest_context_t ctxt[MAX_VIRT_CPUS]; 2.24 + 2.25 2.26 if ((dump_fd = open(corename, O_CREAT|O_RDWR, S_IWUSR|S_IRUSR)) < 0) { 2.27 PERROR("Could not open corefile %s: %s", corename, strerror(errno)); 2.28 @@ -46,14 +48,22 @@ xc_domain_dumpcore(int xc_handle, 2.29 goto error_out; 2.30 } 2.31 2.32 - if (xc_domain_getfullinfo(xc_handle, domid, 0/* XXX hardcode */, info, ctxt)) { 2.33 - PERROR("Could not get full info for domain"); 2.34 + if (xc_domain_getinfo(xc_handle, domid, 1, &info)) { 2.35 + PERROR("Could not get info for domain"); 2.36 goto error_out; 2.37 } 2.38 + 2.39 + for (i = 0; i < info.n_vcpus; i++) { 2.40 + if (xc_domain_get_vcpu_context(xc_handle, domid, i, &ctxt[i])) { 2.41 + PERROR("Could not get all vcpu contexts for domain"); 2.42 + goto error_out; 2.43 + } 2.44 + } 2.45 + 2.46 + nr_pages = info.nr_pages; 2.47 2.48 - nr_pages = info->tot_pages; 2.49 header.xch_magic = 0xF00FEBED; 2.50 - header.xch_nr_vcpus = 1; /* no interface to query at the moment */ 2.51 + header.xch_nr_vcpus = info.n_vcpus; 2.52 header.xch_nr_pages = nr_pages; 2.53 header.xch_ctxt_offset = sizeof(struct xc_core_header); 2.54 header.xch_index_offset = sizeof(struct xc_core_header) + 2.55 @@ -62,7 +72,7 @@ xc_domain_dumpcore(int xc_handle, 2.56 sizeof(vcpu_guest_context_t) + nr_pages * sizeof(unsigned long)); 2.57 2.58 write(dump_fd, &header, sizeof(struct xc_core_header)); 2.59 - write(dump_fd, ctxt, sizeof(st_ctxt)); 2.60 + write(dump_fd, &ctxt, sizeof(ctxt[0]) * info.n_vcpus); 2.61 2.62 if ((page_array = malloc(nr_pages * sizeof(unsigned long))) == NULL) { 2.63 printf("Could not allocate memory\n");
3.1 --- a/tools/libxc/xc_domain.c Wed May 11 14:15:56 2005 +0000 3.2 +++ b/tools/libxc/xc_domain.c Wed May 11 15:05:07 2005 +0000 3.3 @@ -112,14 +112,12 @@ int xc_domain_getinfo(int xc_handle, 3.4 { 3.5 op.cmd = DOM0_GETDOMAININFO; 3.6 op.u.getdomaininfo.domain = (domid_t)next_domid; 3.7 - op.u.getdomaininfo.exec_domain = 0; // FIX ME?!? 3.8 - op.u.getdomaininfo.ctxt = NULL; /* no exec context info, thanks. */ 3.9 if ( (rc = do_dom0_op(xc_handle, &op)) < 0 ) 3.10 break; 3.11 - info->domid = (u16)op.u.getdomaininfo.domain; 3.12 - 3.13 - info->cpu = 3.14 - (op.u.getdomaininfo.flags>>DOMFLAGS_CPUSHIFT) & DOMFLAGS_CPUMASK; 3.15 + info->domid = (u16)op.u.getdomaininfo.domain; 3.16 + info->processors = op.u.getdomaininfo.processors; 3.17 + info->n_vcpus = op.u.getdomaininfo.n_active_vcpus; 3.18 + info->flags = op.u.getdomaininfo.flags; 3.19 3.20 info->dying = !!(op.u.getdomaininfo.flags & DOMFLAGS_DYING); 3.21 info->crashed = !!(op.u.getdomaininfo.flags & DOMFLAGS_CRASHED); 3.22 @@ -142,28 +140,27 @@ int xc_domain_getinfo(int xc_handle, 3.23 memcpy(&info->cpumap, &op.u.getdomaininfo.cpumap, 3.24 sizeof(info->cpumap)); 3.25 3.26 - next_domid = (u16)op.u.getdomaininfo.domain + 1; 3.27 - info++; 3.28 + next_domid = (u16)op.u.getdomaininfo.domain + 1; 3.29 + info++; 3.30 } 3.31 3.32 - if(!nr_doms) return rc; 3.33 + if( !nr_doms ) return rc; 3.34 3.35 return nr_doms; 3.36 } 3.37 3.38 -int xc_domain_getfullinfo(int xc_handle, 3.39 - u32 domid, 3.40 - u32 vcpu, 3.41 - xc_domaininfo_t *info, 3.42 - vcpu_guest_context_t *ctxt) 3.43 +int xc_domain_get_vcpu_context(int xc_handle, 3.44 + u32 domid, 3.45 + u32 vcpu, 3.46 + vcpu_guest_context_t *ctxt) 3.47 { 3.48 int rc, errno_saved; 3.49 dom0_op_t op; 3.50 3.51 - op.cmd = DOM0_GETDOMAININFO; 3.52 - op.u.getdomaininfo.domain = (domid_t)domid; 3.53 - op.u.getdomaininfo.exec_domain = (u16)vcpu; 3.54 - op.u.getdomaininfo.ctxt = ctxt; 3.55 + op.cmd = DOM0_GETVCPUCONTEXT; 3.56 + op.u.getvcpucontext.domain = (domid_t)domid; 3.57 + op.u.getvcpucontext.exec_domain = (u16)vcpu; 3.58 + op.u.getvcpucontext.ctxt = ctxt; 3.59 3.60 if ( (ctxt != NULL) && 3.61 ((rc = mlock(ctxt, sizeof(*ctxt))) != 0) ) 3.62 @@ -178,10 +175,7 @@ int xc_domain_getfullinfo(int xc_handle, 3.63 errno = errno_saved; 3.64 } 3.65 3.66 - if ( info != NULL ) 3.67 - memcpy(info, &op.u.getdomaininfo, sizeof(*info)); 3.68 - 3.69 - if ( ((u16)op.u.getdomaininfo.domain != domid) && (rc > 0) ) 3.70 + if ( rc > 0 ) 3.71 return -ESRCH; 3.72 else 3.73 return rc;
4.1 --- a/tools/libxc/xc_linux_build.c Wed May 11 14:15:56 2005 +0000 4.2 +++ b/tools/libxc/xc_linux_build.c Wed May 11 15:05:07 2005 +0000 4.3 @@ -356,14 +356,19 @@ int xc_linux_build(int xc_handle, 4.4 4.5 op.cmd = DOM0_GETDOMAININFO; 4.6 op.u.getdomaininfo.domain = (domid_t)domid; 4.7 - op.u.getdomaininfo.exec_domain = 0; 4.8 - op.u.getdomaininfo.ctxt = ctxt; 4.9 if ( (do_dom0_op(xc_handle, &op) < 0) || 4.10 ((u16)op.u.getdomaininfo.domain != domid) ) 4.11 { 4.12 PERROR("Could not get info on domain"); 4.13 goto error_out; 4.14 } 4.15 + 4.16 + if ( xc_domain_get_vcpu_context(xc_handle, domid, 0, ctxt) ) 4.17 + { 4.18 + PERROR("Could not get vcpu context"); 4.19 + goto error_out; 4.20 + } 4.21 + 4.22 if ( !(op.u.getdomaininfo.flags & DOMFLAGS_PAUSED) || 4.23 (ctxt->pt_base != 0) ) 4.24 {
5.1 --- a/tools/libxc/xc_linux_restore.c Wed May 11 14:15:56 2005 +0000 5.2 +++ b/tools/libxc/xc_linux_restore.c Wed May 11 15:05:07 2005 +0000 5.3 @@ -181,8 +181,6 @@ int xc_linux_restore(int xc_handle, XcIO 5.4 /* Get the domain's shared-info frame. */ 5.5 op.cmd = DOM0_GETDOMAININFO; 5.6 op.u.getdomaininfo.domain = (domid_t)dom; 5.7 - op.u.getdomaininfo.exec_domain = 0; 5.8 - op.u.getdomaininfo.ctxt = NULL; 5.9 if ( do_dom0_op(xc_handle, &op) < 0 ) 5.10 { 5.11 xcio_error(ioctxt, "Could not get information on new domain");
6.1 --- a/tools/libxc/xc_linux_save.c Wed May 11 14:15:56 2005 +0000 6.2 +++ b/tools/libxc/xc_linux_save.c Wed May 11 15:05:07 2005 +0000 6.3 @@ -324,7 +324,7 @@ static int analysis_phase( int xc_handle 6.4 6.5 6.6 int suspend_and_state(int xc_handle, XcIOContext *ioctxt, 6.7 - xc_domaininfo_t *info, 6.8 + xc_dominfo_t *info, 6.9 vcpu_guest_context_t *ctxt) 6.10 { 6.11 int i=0; 6.12 @@ -333,13 +333,18 @@ int suspend_and_state(int xc_handle, XcI 6.13 6.14 retry: 6.15 6.16 - if ( xc_domain_getfullinfo(xc_handle, ioctxt->domain, /* FIXME */ 0, 6.17 - info, ctxt) ) 6.18 + if ( xc_domain_getinfo(xc_handle, ioctxt->domain, 1, info) ) 6.19 { 6.20 xcio_error(ioctxt, "Could not get full domain info"); 6.21 return -1; 6.22 } 6.23 6.24 + if ( xc_domain_get_vcpu_context(xc_handle, ioctxt->domain, 0 /* XXX */, 6.25 + ctxt) ) 6.26 + { 6.27 + xcio_error(ioctxt, "Could not get vcpu context"); 6.28 + } 6.29 + 6.30 if ( (info->flags & 6.31 (DOMFLAGS_SHUTDOWN | (SHUTDOWN_suspend<<DOMFLAGS_SHUTDOWNSHIFT))) == 6.32 (DOMFLAGS_SHUTDOWN | (SHUTDOWN_suspend<<DOMFLAGS_SHUTDOWNSHIFT)) ) 6.33 @@ -374,7 +379,7 @@ retry: 6.34 6.35 int xc_linux_save(int xc_handle, XcIOContext *ioctxt) 6.36 { 6.37 - xc_domaininfo_t info; 6.38 + xc_dominfo_t info; 6.39 6.40 int rc = 1, i, j, k, last_iter, iter = 0; 6.41 unsigned long mfn; 6.42 @@ -444,13 +449,18 @@ int xc_linux_save(int xc_handle, XcIOCon 6.43 xcio_perror(ioctxt, "Unable to mlock ctxt"); 6.44 return 1; 6.45 } 6.46 - 6.47 - if ( xc_domain_getfullinfo( xc_handle, domid, /* FIXME */ 0, 6.48 - &info, &ctxt) ) 6.49 + 6.50 + if ( xc_domain_getinfo(xc_handle, domid, 1, &info) ) 6.51 { 6.52 xcio_error(ioctxt, "Could not get full domain info"); 6.53 goto out; 6.54 } 6.55 + if ( xc_domain_get_vcpu_context( xc_handle, domid, /* FIXME */ 0, 6.56 + &ctxt) ) 6.57 + { 6.58 + xcio_error(ioctxt, "Could not get vcpu context"); 6.59 + goto out; 6.60 + } 6.61 shared_info_frame = info.shared_info_frame; 6.62 6.63 /* A cheesy test to see whether the domain contains valid state. */ 6.64 @@ -459,7 +469,7 @@ int xc_linux_save(int xc_handle, XcIOCon 6.65 goto out; 6.66 } 6.67 6.68 - nr_pfns = info.max_pages; 6.69 + nr_pfns = info.nr_pages; 6.70 6.71 /* cheesy sanity check */ 6.72 if ( nr_pfns > 1024*1024 ){
7.1 --- a/tools/libxc/xc_plan9_build.c Wed May 11 14:15:56 2005 +0000 7.2 +++ b/tools/libxc/xc_plan9_build.c Wed May 11 15:05:07 2005 +0000 7.3 @@ -440,17 +440,21 @@ xc_plan9_build(int xc_handle, 7.4 7.5 op.cmd = DOM0_GETDOMAININFO; 7.6 op.u.getdomaininfo.domain = (domid_t) domid; 7.7 - op.u.getdomaininfo.exec_domain = 0; 7.8 - op.u.getdomaininfo.ctxt = ctxt; 7.9 if ((do_dom0_op(xc_handle, &op) < 0) || 7.10 ((u32) op.u.getdomaininfo.domain != domid)) { 7.11 PERROR("Could not get info on domain"); 7.12 goto error_out; 7.13 } 7.14 DPRINTF(("xc_get_tot_pages returns %ld pages\n", tot_pages)); 7.15 + 7.16 + if ( xc_domain_get_vcpu_context(xc_handle, domid, 0, ctxt) ) 7.17 + { 7.18 + PERROR("Could not get vcpu context"); 7.19 + goto error_out; 7.20 + } 7.21 7.22 if (!(op.u.getdomaininfo.flags & DOMFLAGS_PAUSED) 7.23 - || (op.u.getdomaininfo.ctxt->pt_base != 0)) { 7.24 + || (ctxt->pt_base != 0)) { 7.25 ERROR("Domain is already constructed"); 7.26 goto error_out; 7.27 }
8.1 --- a/tools/libxc/xc_private.c Wed May 11 14:15:56 2005 +0000 8.2 +++ b/tools/libxc/xc_private.c Wed May 11 15:05:07 2005 +0000 8.3 @@ -173,17 +173,16 @@ long long xc_domain_get_cpu_usage( int x 8.4 { 8.5 dom0_op_t op; 8.6 8.7 - op.cmd = DOM0_GETDOMAININFO; 8.8 - op.u.getdomaininfo.domain = (domid_t)domid; 8.9 - op.u.getdomaininfo.exec_domain = (u16)vcpu; 8.10 - op.u.getdomaininfo.ctxt = NULL; 8.11 - if ( (do_dom0_op(xc_handle, &op) < 0) || 8.12 - ((u16)op.u.getdomaininfo.domain != domid) ) 8.13 + op.cmd = DOM0_GETVCPUCONTEXT; 8.14 + op.u.getvcpucontext.domain = (domid_t)domid; 8.15 + op.u.getvcpucontext.exec_domain = (u16)vcpu; 8.16 + op.u.getvcpucontext.ctxt = NULL; 8.17 + if ( (do_dom0_op(xc_handle, &op) < 0) ) 8.18 { 8.19 PERROR("Could not get info on domain"); 8.20 return -1; 8.21 } 8.22 - return op.u.getdomaininfo.cpu_time; 8.23 + return op.u.getvcpucontext.cpu_time; 8.24 } 8.25 8.26 8.27 @@ -258,8 +257,6 @@ long xc_get_tot_pages(int xc_handle, u32 8.28 dom0_op_t op; 8.29 op.cmd = DOM0_GETDOMAININFO; 8.30 op.u.getdomaininfo.domain = (domid_t)domid; 8.31 - op.u.getdomaininfo.exec_domain = 0; 8.32 - op.u.getdomaininfo.ctxt = NULL; 8.33 return (do_dom0_op(xc_handle, &op) < 0) ? 8.34 -1 : op.u.getdomaininfo.tot_pages; 8.35 }
9.1 --- a/tools/libxc/xc_ptrace.c Wed May 11 14:15:56 2005 +0000 9.2 +++ b/tools/libxc/xc_ptrace.c Wed May 11 15:05:07 2005 +0000 9.3 @@ -71,7 +71,7 @@ struct gdb_regs { 9.4 #define FETCH_REGS(cpu) \ 9.5 if (!regs_valid[cpu]) \ 9.6 { \ 9.7 - int retval = xc_domain_getfullinfo(xc_handle, domid, cpu, NULL, &ctxt[cpu]); \ 9.8 + int retval = xc_domain_get_vcpu_context(xc_handle, domid, cpu, &ctxt[cpu]); \ 9.9 if (retval) \ 9.10 goto error_out; \ 9.11 cr3[cpu] = ctxt[cpu].pt_base; /* physical address */ \ 9.12 @@ -221,7 +221,6 @@ xc_waitdomain(int domain, int *status, i 9.13 { 9.14 dom0_op_t op; 9.15 int retval; 9.16 - vcpu_guest_context_t ctxt; 9.17 struct timespec ts; 9.18 ts.tv_sec = 0; 9.19 ts.tv_nsec = 10*1000*1000; 9.20 @@ -234,12 +233,10 @@ xc_waitdomain(int domain, int *status, i 9.21 } 9.22 op.cmd = DOM0_GETDOMAININFO; 9.23 op.u.getdomaininfo.domain = domain; 9.24 - op.u.getdomaininfo.exec_domain = 0; 9.25 - op.u.getdomaininfo.ctxt = &ctxt; 9.26 retry: 9.27 9.28 retval = do_dom0_op(xc_handle, &op); 9.29 - if (retval) { 9.30 + if (retval || op.u.getdomaininfo.domain != domain) { 9.31 printf("getdomaininfo failed\n"); 9.32 goto done; 9.33 } 9.34 @@ -325,10 +322,8 @@ xc_ptrace(enum __ptrace_request request, 9.35 case PTRACE_ATTACH: 9.36 op.cmd = DOM0_GETDOMAININFO; 9.37 op.u.getdomaininfo.domain = domid; 9.38 - op.u.getdomaininfo.exec_domain = 0; 9.39 - op.u.getdomaininfo.ctxt = NULL; 9.40 retval = do_dom0_op(xc_handle, &op); 9.41 - if (retval) { 9.42 + if (retval || op.u.getdomaininfo.domain != domid) { 9.43 perror("dom0 op failed"); 9.44 goto error_out; 9.45 }
10.1 --- a/tools/libxc/xc_vmx_build.c Wed May 11 14:15:56 2005 +0000 10.2 +++ b/tools/libxc/xc_vmx_build.c Wed May 11 15:05:07 2005 +0000 10.3 @@ -543,14 +543,19 @@ int xc_vmx_build(int xc_handle, 10.4 10.5 op.cmd = DOM0_GETDOMAININFO; 10.6 op.u.getdomaininfo.domain = (domid_t)domid; 10.7 - op.u.getdomaininfo.exec_domain = 0; 10.8 - op.u.getdomaininfo.ctxt = ctxt; 10.9 if ( (do_dom0_op(xc_handle, &op) < 0) || 10.10 ((u16)op.u.getdomaininfo.domain != domid) ) 10.11 { 10.12 PERROR("Could not get info on domain"); 10.13 goto error_out; 10.14 } 10.15 + 10.16 + if ( xc_domain_get_vcpu_context(xc_handle, domid, 0, ctxt) ) 10.17 + { 10.18 + PERROR("Could not get vcpu context"); 10.19 + goto error_out; 10.20 + } 10.21 + 10.22 if ( !(op.u.getdomaininfo.flags & DOMFLAGS_PAUSED) || 10.23 (ctxt->pt_base != 0) ) 10.24 {
11.1 --- a/xen/common/dom0_ops.c Wed May 11 14:15:56 2005 +0000 11.2 +++ b/xen/common/dom0_ops.c Wed May 11 15:05:07 2005 +0000 11.3 @@ -299,9 +299,16 @@ long do_dom0_op(dom0_op_t *u_dom0_op) 11.4 11.5 case DOM0_GETDOMAININFO: 11.6 { 11.7 - struct vcpu_guest_context *c; 11.8 - struct domain *d; 11.9 - struct exec_domain *ed; 11.10 + struct domain *d; 11.11 + struct exec_domain *ed; 11.12 + u64 cpu_time = 0; 11.13 + int vcpu_count = 0; 11.14 + u32 processors = 0; 11.15 + int flags = DOMFLAGS_PAUSED | DOMFLAGS_BLOCKED; 11.16 + 11.17 +#if MAX_VIRT_CPUS > 32 11.18 +#error "update processors field in GETDOMAININFO" 11.19 +#endif 11.20 11.21 read_lock(&domlist_lock); 11.22 11.23 @@ -322,13 +329,6 @@ long do_dom0_op(dom0_op_t *u_dom0_op) 11.24 11.25 op->u.getdomaininfo.domain = d->id; 11.26 11.27 - if ( (op->u.getdomaininfo.exec_domain >= MAX_VIRT_CPUS) || 11.28 - !d->exec_domain[op->u.getdomaininfo.exec_domain] ) 11.29 - { 11.30 - ret = -EINVAL; 11.31 - break; 11.32 - } 11.33 - 11.34 memset(&op->u.getdomaininfo.vcpu_to_cpu, -1, 11.35 sizeof(op->u.getdomaininfo.vcpu_to_cpu)); 11.36 memset(&op->u.getdomaininfo.cpumap, 0, 11.37 @@ -338,28 +338,86 @@ long do_dom0_op(dom0_op_t *u_dom0_op) 11.38 op->u.getdomaininfo.cpumap[ed->id] = ed->cpumap; 11.39 } 11.40 11.41 - ed = d->exec_domain[op->u.getdomaininfo.exec_domain]; 11.42 + /* 11.43 + * - domain is marked as paused or blocked only if all its vcpus 11.44 + * are paused or blocked 11.45 + * - domain is marked as running if any of its vcpus is running 11.46 + */ 11.47 + 11.48 + for_each_exec_domain(d, ed) 11.49 + { 11.50 + if (!((flags & DOMFLAGS_PAUSED) && test_bit(EDF_CTRLPAUSE, &ed->flags))) 11.51 + flags &= ~DOMFLAGS_PAUSED; 11.52 + if (!((flags & DOMFLAGS_BLOCKED) && test_bit(EDF_BLOCKED, &ed->flags))) 11.53 + flags &= ~DOMFLAGS_BLOCKED; 11.54 + flags |= (test_bit(EDF_RUNNING, &ed->flags) ? DOMFLAGS_RUNNING : 0); 11.55 + 11.56 + set_bit(ed->processor, &processors); 11.57 + if ( ed->cpu_time > cpu_time ) 11.58 + cpu_time += ed->cpu_time; 11.59 + vcpu_count++; 11.60 + } 11.61 + op->u.getdomaininfo.n_active_vcpus = vcpu_count; 11.62 + op->u.getdomaininfo.cpu_time = cpu_time; 11.63 11.64 op->u.getdomaininfo.flags = 11.65 (test_bit( DF_DYING, &d->flags) ? DOMFLAGS_DYING : 0) | 11.66 (test_bit( DF_CRASHED, &d->flags) ? DOMFLAGS_CRASHED : 0) | 11.67 (test_bit( DF_SHUTDOWN, &d->flags) ? DOMFLAGS_SHUTDOWN : 0) | 11.68 - (test_bit(EDF_CTRLPAUSE, &ed->flags) ? DOMFLAGS_PAUSED : 0) | 11.69 - (test_bit(EDF_BLOCKED, &ed->flags) ? DOMFLAGS_BLOCKED : 0) | 11.70 - (test_bit(EDF_RUNNING, &ed->flags) ? DOMFLAGS_RUNNING : 0); 11.71 + flags; 11.72 11.73 - op->u.getdomaininfo.flags |= ed->processor << DOMFLAGS_CPUSHIFT; 11.74 op->u.getdomaininfo.flags |= 11.75 d->shutdown_code << DOMFLAGS_SHUTDOWNSHIFT; 11.76 11.77 + op->u.getdomaininfo.processors = processors; 11.78 op->u.getdomaininfo.tot_pages = d->tot_pages; 11.79 op->u.getdomaininfo.max_pages = d->max_pages; 11.80 - op->u.getdomaininfo.cpu_time = ed->cpu_time; 11.81 op->u.getdomaininfo.n_vcpu = d->shared_info->n_vcpu; 11.82 op->u.getdomaininfo.shared_info_frame = 11.83 __pa(d->shared_info) >> PAGE_SHIFT; 11.84 11.85 - if ( op->u.getdomaininfo.ctxt != NULL ) 11.86 + if ( copy_to_user(u_dom0_op, op, sizeof(*op)) ) 11.87 + ret = -EINVAL; 11.88 + 11.89 + put_domain(d); 11.90 + } 11.91 + break; 11.92 + 11.93 + case DOM0_GETVCPUCONTEXT: 11.94 + { 11.95 + struct vcpu_guest_context *c; 11.96 + struct domain *d; 11.97 + struct exec_domain *ed; 11.98 + int active_index = 0; 11.99 + int exec_domain_index; 11.100 + 11.101 + exec_domain_index = op->u.getvcpucontext.exec_domain; 11.102 + d = find_domain_by_id(op->u.getvcpucontext.domain); 11.103 + 11.104 + if ( d == NULL ) 11.105 + { 11.106 + ret = -ESRCH; 11.107 + break; 11.108 + } 11.109 + 11.110 + if ( (exec_domain_index >= MAX_VIRT_CPUS) ) 11.111 + { 11.112 + ret = -EINVAL; 11.113 + break; 11.114 + } 11.115 + 11.116 + for_each_exec_domain(d, ed) 11.117 + { 11.118 + if ( exec_domain_index == active_index ) 11.119 + { 11.120 + op->u.getvcpucontext.exec_domain = ed->id; 11.121 + break; 11.122 + } 11.123 + active_index++; 11.124 + } 11.125 + op->u.getvcpucontext.cpu_time = ed->cpu_time; 11.126 + 11.127 + if ( op->u.getvcpucontext.ctxt != NULL ) 11.128 { 11.129 if ( (c = xmalloc(struct vcpu_guest_context)) == NULL ) 11.130 { 11.131 @@ -376,7 +434,7 @@ long do_dom0_op(dom0_op_t *u_dom0_op) 11.132 if ( ed != current ) 11.133 exec_domain_unpause(ed); 11.134 11.135 - if ( copy_to_user(op->u.getdomaininfo.ctxt, c, sizeof(*c)) ) 11.136 + if ( copy_to_user(op->u.getvcpucontext.ctxt, c, sizeof(*c)) ) 11.137 ret = -EINVAL; 11.138 11.139 xfree(c);
12.1 --- a/xen/include/public/dom0_ops.h Wed May 11 14:15:56 2005 +0000 12.2 +++ b/xen/include/public/dom0_ops.h Wed May 11 15:05:07 2005 +0000 12.3 @@ -70,7 +70,7 @@ typedef struct { 12.4 typedef struct { 12.5 /* IN variables. */ 12.6 domid_t domain; /* NB. IN/OUT variable. */ 12.7 - u16 exec_domain; 12.8 + u16 n_active_vcpus; /* # of vcpus currently active */ 12.9 /* OUT variables. */ 12.10 #define DOMFLAGS_DYING (1<<0) /* Domain is scheduled to die. */ 12.11 #define DOMFLAGS_CRASHED (1<<1) /* Crashed domain; frozen for postmortem. */ 12.12 @@ -83,7 +83,7 @@ typedef struct { 12.13 #define DOMFLAGS_SHUTDOWNMASK 255 /* DOMFLAGS_SHUTDOWN guest-supplied code. */ 12.14 #define DOMFLAGS_SHUTDOWNSHIFT 16 12.15 u32 flags; 12.16 - vcpu_guest_context_t *ctxt; /* NB. IN/OUT variable. */ 12.17 + u32 processors; 12.18 memory_t tot_pages; 12.19 memory_t max_pages; 12.20 memory_t shared_info_frame; /* MFN of shared_info struct */ 12.21 @@ -345,6 +345,15 @@ typedef struct { 12.22 u16 allow_access; /* allow or deny access to range? */ 12.23 } dom0_ioport_permission_t; 12.24 12.25 +#define DOM0_GETVCPUCONTEXT 37 12.26 +typedef struct { 12.27 + domid_t domain; /* domain to be affected */ 12.28 + u16 exec_domain; /* NB. IN: nth active cpu / OUT: actual cpu # */ 12.29 + vcpu_guest_context_t *ctxt; /* NB. IN/OUT variable. */ 12.30 + u64 cpu_time; 12.31 +} dom0_getvcpucontext_t; 12.32 + 12.33 + 12.34 typedef struct { 12.35 u32 cmd; 12.36 u32 interface_version; /* DOM0_INTERFACE_VERSION */ 12.37 @@ -376,6 +385,7 @@ typedef struct { 12.38 dom0_perfccontrol_t perfccontrol; 12.39 dom0_microcode_t microcode; 12.40 dom0_ioport_permission_t ioport_permission; 12.41 + dom0_getvcpucontext_t getvcpucontext; 12.42 } u; 12.43 } dom0_op_t; 12.44