ia64/xen-unstable

view tools/xenstat/libxenstat/src/xen-interface.c @ 6552:a9873d384da4

Merge.
author adsharma@los-vmm.sc.intel.com
date Thu Aug 25 12:24:48 2005 -0700 (2005-08-25)
parents 112d44270733 fa0754a9f64f
children dfaf788ab18c
line source
1 /* xen-interface.c
2 *
3 * Copyright (C) International Business Machines Corp., 2005
4 * Authors: Josh Triplett <josht@us.ibm.com>
5 * Judy Fischbach <jfisch@us.ibm.com>
6 *
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
11 *
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
16 */
18 #include "xen-interface.h"
19 #include <fcntl.h>
20 #include <sys/ioctl.h>
21 #include <sys/mman.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <unistd.h>
26 #include "version.h"
27 #include "privcmd.h"
28 #include "xen.h"
30 struct xi_handle {
31 int fd;
32 };
34 /* Initialize for xen-interface. Returns a handle to be used with subsequent
35 * calls to the xen-interface functions or NULL if an error occurs. */
36 xi_handle *xi_init()
37 {
38 xi_handle *handle;
40 handle = (xi_handle *)calloc(1, sizeof(xi_handle));
41 if (handle == NULL)
42 return NULL;
44 handle->fd = open("/proc/xen/privcmd", O_RDWR);
45 if (handle->fd < 0) {
46 perror("Couldn't open /proc/xen/privcmd");
47 free(handle);
48 return NULL;
49 }
51 return handle;
52 }
54 /* Release the handle to libxc, free resources, etc. */
55 void xi_uninit(xi_handle *handle)
56 {
57 close (handle->fd);
58 free (handle);
59 }
61 /* Make simple xen version hypervisor calls */
62 static int xi_make_xen_version_hypercall(xi_handle *handle, long *vnum, xen_extraversion_t *ver)
63 {
64 privcmd_hypercall_t privcmd;
65 multicall_entry_t multicall[2];
66 int ret = 0;
68 /* set up for doing hypercall */
69 privcmd.op = __HYPERVISOR_multicall;
70 privcmd.arg[0] = (unsigned long)multicall;
71 privcmd.arg[1] = 2;
73 /* first one to get xen version number */
74 multicall[0].op = __HYPERVISOR_xen_version;
75 multicall[0].args[0] = (unsigned long)XENVER_version;
77 /* second to get xen version flag */
78 multicall[1].op = __HYPERVISOR_xen_version;
79 multicall[1].args[0] = (unsigned long)XENVER_extraversion;
80 multicall[1].args[1] = (unsigned long)ver;
82 if (mlock( &privcmd, sizeof(privcmd_hypercall_t)) < 0) {
83 perror("Failed to mlock privcmd structure");
84 return -1;
85 }
87 if (mlock( multicall, sizeof(multicall_entry_t)) < 0) {
88 perror("Failed to mlock multicall_entry structure");
89 munlock( &multicall, sizeof(multicall_entry_t));
90 return -1;
91 }
93 if (ioctl( handle->fd, IOCTL_PRIVCMD_HYPERCALL, &privcmd) < 0) {
94 perror("Hypercall failed");
95 ret = -1;
96 }
98 *vnum = multicall[0].result;
100 munlock( &privcmd, sizeof(privcmd_hypercall_t));
101 munlock( &multicall, sizeof(multicall_entry_t));
103 return ret;
104 }
106 /* Make Xen Dom0 op hypervisor call */
107 static int xi_make_dom0_op(xi_handle *handle, dom0_op_t *dom_op, int dom_opcode)
108 {
109 privcmd_hypercall_t privcmd;
110 int ret = 0;
112 /* set up for doing hypercall */
113 privcmd.op = __HYPERVISOR_dom0_op;
114 privcmd.arg[0] = (unsigned long)dom_op;
115 dom_op->cmd = dom_opcode;
116 dom_op->interface_version = DOM0_INTERFACE_VERSION;
118 if (mlock( &privcmd, sizeof(privcmd_hypercall_t)) < 0) {
119 perror("Failed to mlock privcmd structure");
120 return -1;
121 }
123 if (mlock( dom_op, sizeof(dom0_op_t)) < 0) {
124 perror("Failed to mlock dom0_op structure");
125 munlock( &privcmd, sizeof(privcmd_hypercall_t));
126 return -1;
127 }
129 if (ioctl( handle->fd, IOCTL_PRIVCMD_HYPERCALL, &privcmd) < 0) {
130 perror("Hypercall failed");
131 ret = -1;
132 }
134 munlock( &privcmd, sizeof(privcmd_hypercall_t));
135 munlock( dom_op, sizeof(dom0_op_t));
137 return ret;
138 }
140 /* Obtain domain data from dom0 */
141 int xi_get_physinfo(xi_handle *handle, dom0_physinfo_t *physinfo)
142 {
143 dom0_op_t op;
145 if (xi_make_dom0_op(handle, &op, DOM0_PHYSINFO) < 0) {
146 perror("DOM0_PHYSINFO Hypercall failed");
147 return -1;
148 }
150 *physinfo = op.u.physinfo;
151 return 0;
152 }
154 /* Obtain domain data from dom0 */
155 int xi_get_domaininfolist(xi_handle *handle, dom0_getdomaininfo_t *info,
156 unsigned int first_domain, unsigned int max_domains)
157 {
158 dom0_op_t op;
159 op.u.getdomaininfolist.first_domain = first_domain;
160 op.u.getdomaininfolist.max_domains = max_domains;
161 op.u.getdomaininfolist.buffer = info;
163 if (mlock( info, max_domains * sizeof(dom0_getdomaininfo_t)) < 0) {
164 perror("Failed to mlock domaininfo array");
165 return -1;
166 }
168 if (xi_make_dom0_op(handle, &op, DOM0_GETDOMAININFOLIST) < 0) {
169 perror("DOM0_GETDOMAININFOLIST Hypercall failed");
170 return -1;
171 }
173 return op.u.getdomaininfolist.num_domains;
174 }
176 /* Returns cpu usage data from dom0 */
177 long long xi_get_vcpu_usage(xi_handle *handle, unsigned int domain,
178 unsigned int vcpu)
179 {
180 dom0_op_t op;
181 op.u.getvcpucontext.domain = domain;
182 op.u.getvcpucontext.vcpu = vcpu;
183 op.u.getvcpucontext.ctxt = NULL;
185 if (xi_make_dom0_op(handle, &op, DOM0_GETVCPUCONTEXT) < 0) {
186 perror("DOM0_GETVCPUCONTEXT Hypercall failed");
187 return -1;
188 }
190 return op.u.getvcpucontext.cpu_time;
191 }
193 /* gets xen version information from hypervisor */
194 int xi_get_xen_version(xi_handle *handle, long *vnum, xen_extraversion_t *ver)
195 {
197 /* gets the XENVER_version and XENVER_extraversion */
198 if (xi_make_xen_version_hypercall( handle, vnum, ver) < 0) {;
199 perror("XEN VERSION Hypercall failed");
200 return -1;
201 }
203 return 0;
204 }