ia64/xen-unstable
changeset 3571:bc0fbb38cb25
bitkeeper revision 1.1159.1.540 (41f9f0eb0vCo2Pbn_siAkCKZ7XnejA)
Merge tempest.cl.cam.ac.uk:/auto/groups/xeno-xenod/BK/xeno.bk
into tempest.cl.cam.ac.uk:/local/scratch/smh22/xen-unstable.bk
Merge tempest.cl.cam.ac.uk:/auto/groups/xeno-xenod/BK/xeno.bk
into tempest.cl.cam.ac.uk:/local/scratch/smh22/xen-unstable.bk
line diff
1.1 --- a/.rootkeys Thu Jan 27 17:33:33 2005 +0000 1.2 +++ b/.rootkeys Fri Jan 28 07:59:39 2005 +0000 1.3 @@ -891,6 +891,7 @@ 3ddb79bccYVzXZJyVaxuv5T42Z1Fsw xen/arch/ 1.4 3ddb79bcOftONV9h4QCxXOfiT0h91w xen/arch/x86/traps.c 1.5 41c0c411tD3C7TpfDMiFTf7BaNd_Dg xen/arch/x86/vmx.c 1.6 41c0c411ODt8uEmV-yUxpQLpqimE5Q xen/arch/x86/vmx_io.c 1.7 +41f97ef5139vN42cOYHfX_Ac8WOOjA xen/arch/x86/vmx_platform.c 1.8 41c0c4128URE0dxcO15JME_MuKBPfg xen/arch/x86/vmx_vmcs.c 1.9 419cbedeQDg8IrO3izo3o5rQNlo0kQ xen/arch/x86/x86_32/asm-offsets.c 1.10 3e32af9aRnYGl4GMOaDKp7JdfhOGhg xen/arch/x86/x86_32/domain_page.c
2.1 --- a/Makefile Thu Jan 27 17:33:33 2005 +0000 2.2 +++ b/Makefile Fri Jan 28 07:59:39 2005 +0000 2.3 @@ -11,7 +11,7 @@ INSTALL_DIR := $(INSTALL) -d -m0755 2.4 INSTALL_DATA := $(INSTALL) -m0644 2.5 INSTALL_PROG := $(INSTALL) -m0755 2.6 2.7 -KERNELS ?= *2.6* 2.8 +KERNELS ?= linux-2.6-xen0 linux-2.6-xenU 2.9 # linux-2.4-xen0 linux-2.4-xenU netbsd-2.0-xenU 2.10 # You may use wildcards in the above e.g. KERNELS=*2.4* 2.11 2.12 @@ -30,20 +30,12 @@ endif 2.13 include buildconfigs/Rules.mk 2.14 2.15 .PHONY: all dist install xen tools kernels docs world clean mkpatches mrproper 2.16 -.PHONY: kbuild kdelete kclean install-tools install-xen install-docs 2.17 -.PHONY: install-kernels 2.18 +.PHONY: kbuild kdelete kclean 2.19 2.20 all: dist 2.21 2.22 -# install everything into the standard system directories 2.23 -# NB: install explicitly does not check that everything is up to date! 2.24 -install: DESTDIR= 2.25 -install: xen checked-tools kernels docs 2.26 - 2.27 -# Only check for install req'mts on 'make install', not on 'make dist'. 2.28 -checked-tools: 2.29 - $(MAKE) -C tools/check install 2.30 - $(MAKE) -C tools install 2.31 +# build and install everything into the standard system directories 2.32 +install: install-xen install-tools install-kernels install-docs 2.33 2.34 # build and install everything into local dist directory 2.35 dist: xen tools kernels docs 2.36 @@ -118,9 +110,17 @@ install-iptables: 2.37 tar -jxf iptables-1.2.11.tar.bz2 2.38 $(MAKE) -C iptables-1.2.11 PREFIX= KERNEL_DIR=../linux-$(LINUX_VER)-xen0 install 2.39 2.40 +install-%: DESTDIR= 2.41 +install-%: % 2.42 + @: # do nothing 2.43 + 2.44 help: 2.45 @echo 'Installation targets:' 2.46 @echo ' install - build and install everything' 2.47 + @echo ' install-xen - build and install the Xen hypervisor' 2.48 + @echo ' install-tools - build and install the control tools' 2.49 + @echo ' install-kernels - build and install guest kernels' 2.50 + @echo ' install-docs - build and install documentation' 2.51 @echo '' 2.52 @echo 'Building targets:' 2.53 @echo ' dist - build and install everything into local dist directory' 2.54 @@ -178,3 +178,4 @@ linux26: 2.55 2.56 netbsd20: 2.57 $(MAKE) netbsd-2.0-xenU-build 2.58 +
3.1 --- a/linux-2.6.10-xen-sparse/arch/xen/Kconfig Thu Jan 27 17:33:33 2005 +0000 3.2 +++ b/linux-2.6.10-xen-sparse/arch/xen/Kconfig Fri Jan 28 07:59:39 2005 +0000 3.3 @@ -26,7 +26,7 @@ menu "XEN" 3.4 config XEN_PRIVILEGED_GUEST 3.5 bool "Privileged Guest (domain 0)" 3.6 default n 3.7 - select XEN_PHYSDEV_ACCESS 3.8 + select XEN_PHYSDEV_ACCESS 3.9 help 3.10 Support for privileged operation (domain 0) 3.11 3.12 @@ -35,18 +35,18 @@ config XEN_PHYSDEV_ACCESS 3.13 default XEN_PRIVILEGED_GUEST 3.14 help 3.15 Assume access is available to physical hardware devices 3.16 - (e.g., hard drives, network cards). This allows you to configure 3.17 - such devices and also includes some low-level support that is 3.18 - otherwise not compiled into the kernel. 3.19 + (e.g., hard drives, network cards). This allows you to configure 3.20 + such devices and also includes some low-level support that is 3.21 + otherwise not compiled into the kernel. 3.22 3.23 config XEN_BLKDEV_BACKEND 3.24 - bool "Block-device backend driver" 3.25 - depends on XEN_PHYSDEV_ACCESS 3.26 - default y 3.27 - help 3.28 - The block-device backend driver allows the kernel to export its 3.29 - block devices to other guests via a high-performance shared-memory 3.30 - interface. 3.31 + bool "Block-device backend driver" 3.32 + depends on XEN_PHYSDEV_ACCESS 3.33 + default y 3.34 + help 3.35 + The block-device backend driver allows the kernel to export its 3.36 + block devices to other guests via a high-performance shared-memory 3.37 + interface. 3.38 3.39 config XEN_BLKDEV_TAP_BE 3.40 bool "Block Tap support for backend driver (DANGEROUS)" 3.41 @@ -62,87 +62,86 @@ config XEN_BLKDEV_TAP_BE 3.42 modified to use grant tables. 3.43 3.44 config XEN_NETDEV_BACKEND 3.45 - bool "Network-device backend driver" 3.46 - depends on XEN_PHYSDEV_ACCESS 3.47 - default y 3.48 - help 3.49 - The network-device backend driver allows the kernel to export its 3.50 - network devices to other guests via a high-performance shared-memory 3.51 - interface. 3.52 + bool "Network-device backend driver" 3.53 + depends on XEN_PHYSDEV_ACCESS 3.54 + default y 3.55 + help 3.56 + The network-device backend driver allows the kernel to export its 3.57 + network devices to other guests via a high-performance shared-memory 3.58 + interface. 3.59 3.60 config XEN_BLKDEV_FRONTEND 3.61 - bool "Block-device frontend driver" 3.62 - default y 3.63 - help 3.64 - The block-device frontend driver allows the kernel to access block 3.65 - devices mounted within another guest OS. Unless you are building a 3.66 - dedicated device-driver domain, or your master control domain 3.67 - (domain 0), then you almost certainly want to say Y here. 3.68 + bool "Block-device frontend driver" 3.69 + default y 3.70 + help 3.71 + The block-device frontend driver allows the kernel to access block 3.72 + devices mounted within another guest OS. Unless you are building a 3.73 + dedicated device-driver domain, or your master control domain 3.74 + (domain 0), then you almost certainly want to say Y here. 3.75 3.76 config XEN_NETDEV_FRONTEND 3.77 - bool "Network-device frontend driver" 3.78 - default y 3.79 - help 3.80 - The network-device frontend driver allows the kernel to access 3.81 - network interfaces within another guest OS. Unless you are building a 3.82 - dedicated device-driver domain, or your master control domain 3.83 - (domain 0), then you almost certainly want to say Y here. 3.84 + bool "Network-device frontend driver" 3.85 + default y 3.86 + help 3.87 + The network-device frontend driver allows the kernel to access 3.88 + network interfaces within another guest OS. Unless you are building a 3.89 + dedicated device-driver domain, or your master control domain 3.90 + (domain 0), then you almost certainly want to say Y here. 3.91 3.92 config XEN_NETDEV_FRONTEND_PIPELINED_TRANSMITTER 3.93 - bool "Pipelined transmitter (DANGEROUS)" 3.94 + bool "Pipelined transmitter (DANGEROUS)" 3.95 depends on XEN_NETDEV_FRONTEND 3.96 - default n 3.97 - help 3.98 - The driver will assume that the backend is pipelining packets for 3.99 - transmission: whenever packets are pending in the remote backend, 3.100 - the driver will not send asynchronous notifications when it queues 3.101 - additional packets for transmission. 3.102 - If the backend is a dumb domain, such as a transparent Ethernet 3.103 - bridge with no local IP interface, it is safe to say Y here to get 3.104 - slightly lower network overhead. 3.105 - If the backend has a local IP interface; or may be doing smart things 3.106 - like reassembling packets to perform firewall filtering; or if you 3.107 - are unsure; or if you experience network hangs when this option is 3.108 - enabled; then you must say N here. 3.109 + default n 3.110 + help 3.111 + The driver will assume that the backend is pipelining packets for 3.112 + transmission: whenever packets are pending in the remote backend, 3.113 + the driver will not send asynchronous notifications when it queues 3.114 + additional packets for transmission. 3.115 + If the backend is a dumb domain, such as a transparent Ethernet 3.116 + bridge with no local IP interface, it is safe to say Y here to get 3.117 + slightly lower network overhead. 3.118 + If the backend has a local IP interface; or may be doing smart things 3.119 + like reassembling packets to perform firewall filtering; or if you 3.120 + are unsure; or if you experience network hangs when this option is 3.121 + enabled; then you must say N here. 3.122 3.123 config XEN_BLKDEV_TAP 3.124 - bool "Block device tap driver" 3.125 - default n 3.126 - help 3.127 - This driver allows a VM to interact on block device channels 3.128 - to other VMs. Block messages may be passed through or redirected 3.129 - to a character device, allowing device prototyping in application 3.130 - space. Odds are that you want to say N here. 3.131 - 3.132 + bool "Block device tap driver" 3.133 + default n 3.134 + help 3.135 + This driver allows a VM to interact on block device channels 3.136 + to other VMs. Block messages may be passed through or redirected 3.137 + to a character device, allowing device prototyping in application 3.138 + space. Odds are that you want to say N here. 3.139 3.140 config XEN_WRITABLE_PAGETABLES 3.141 bool 3.142 default y 3.143 3.144 config XEN_SCRUB_PAGES 3.145 - bool "Scrub memory before freeing it to Xen" 3.146 - default y 3.147 - help 3.148 - Erase memory contents before freeing it back to Xen's global 3.149 - pool. This ensures that any secrets contained within that 3.150 - memory (e.g., private keys) cannot be found by other guests that 3.151 - may be running on the machine. Most people will want to say Y here. 3.152 - If security is not a concern then you may increase performance by 3.153 - saying N. 3.154 + bool "Scrub memory before freeing it to Xen" 3.155 + default y 3.156 + help 3.157 + Erase memory contents before freeing it back to Xen's global 3.158 + pool. This ensures that any secrets contained within that 3.159 + memory (e.g., private keys) cannot be found by other guests that 3.160 + may be running on the machine. Most people will want to say Y here. 3.161 + If security is not a concern then you may increase performance by 3.162 + saying N. 3.163 3.164 choice 3.165 - prompt "Processor Type" 3.166 - default X86 3.167 + prompt "Processor Type" 3.168 + default X86 3.169 3.170 config X86 3.171 - bool "X86" 3.172 - help 3.173 - Choose this option if your computer is a X86 architecture. 3.174 + bool "X86" 3.175 + help 3.176 + Choose this option if your computer is a X86 architecture. 3.177 3.178 config X86_64 3.179 - bool "X86_64" 3.180 - help 3.181 - Choose this option if your computer is a X86 architecture. 3.182 + bool "X86_64" 3.183 + help 3.184 + Choose this option if your computer is a X86 architecture. 3.185 3.186 endchoice 3.187
4.1 --- a/linux-2.6.10-xen-sparse/drivers/xen/netfront/netfront.c Thu Jan 27 17:33:33 2005 +0000 4.2 +++ b/linux-2.6.10-xen-sparse/drivers/xen/netfront/netfront.c Fri Jan 28 07:59:39 2005 +0000 4.3 @@ -1295,8 +1295,7 @@ static int __init netif_init(void) 4.4 { 4.5 int err = 0; 4.6 4.7 - if ( (xen_start_info.flags & SIF_INITDOMAIN) || 4.8 - (xen_start_info.flags & SIF_NET_BE_DOMAIN) ) 4.9 + if ( xen_start_info.flags & SIF_INITDOMAIN ) 4.10 return 0; 4.11 4.12 IPRINTK("Initialising virtual ethernet driver.\n");
5.1 --- a/tools/examples/Makefile Thu Jan 27 17:33:33 2005 +0000 5.2 +++ b/tools/examples/Makefile Fri Jan 28 07:59:39 2005 +0000 5.3 @@ -28,20 +28,23 @@ all: 5.4 install: all install-initd install-configs install-scripts 5.5 5.6 install-initd: 5.7 - $(INSTALL_DIR) $(DESTDIR)/etc/init.d 5.8 + [ -d $(DESTDIR)/etc/init.d ] || $(INSTALL_DIR) $(DESTDIR)/etc/init.d 5.9 $(INSTALL_PROG) $(XEND_INITD) $(DESTDIR)/etc/init.d 5.10 $(INSTALL_PROG) $(XENDOMAINS_INITD) $(DESTDIR)/etc/init.d 5.11 5.12 install-configs: 5.13 - $(INSTALL_DIR) $(DESTDIR)$(XEN_CONFIG_DIR) 5.14 - $(INSTALL_DIR) $(DESTDIR)$(XEN_CONFIG_DIR)/auto 5.15 + [ -d $(DESTDIR)$(XEN_CONFIG_DIR) ] || \ 5.16 + $(INSTALL_DIR) $(DESTDIR)$(XEN_CONFIG_DIR) 5.17 + [ -d $(DESTDIR)$(XEN_CONFIG_DIR)/auto ] || \ 5.18 + $(INSTALL_DIR) $(DESTDIR)$(XEN_CONFIG_DIR)/auto 5.19 for i in $(XEN_CONFIGS); \ 5.20 do [ -a $(DESTDIR)$(XEN_CONFIG_DIR)/$$i ] || \ 5.21 $(INSTALL_DATA) $$i $(DESTDIR)$(XEN_CONFIG_DIR); \ 5.22 done 5.23 5.24 install-scripts: 5.25 - $(INSTALL_DIR) $(DESTDIR)$(XEN_SCRIPT_DIR) 5.26 + [ -d $(DESTDIR)$(XEN_SCRIPT_DIR) ] || \ 5.27 + $(INSTALL_DIR) $(DESTDIR)$(XEN_SCRIPT_DIR) 5.28 for i in $(XEN_SCRIPTS); \ 5.29 do [ -a $(DESTDIR)$(XEN_SCRIPT_DIR)/$$i ] || \ 5.30 $(INSTALL_PROG) $$i $(DESTDIR)$(XEN_SCRIPT_DIR); \
6.1 --- a/tools/libxc/Makefile Thu Jan 27 17:33:33 2005 +0000 6.2 +++ b/tools/libxc/Makefile Fri Jan 28 07:59:39 2005 +0000 6.3 @@ -67,8 +67,8 @@ mk-symlinks: 6.4 ln -sf ../../$(LINUX_ROOT)/include/asm-xen/linux-public/*.h . ) 6.5 6.6 install: all 6.7 - $(INSTALL_DIR) $(DESTDIR)/usr/lib 6.8 - $(INSTALL_DIR) $(DESTDIR)/usr/include 6.9 + [ -d $(DESTDIR)/usr/lib ] || $(INSTALL_DIR) $(DESTDIR)/usr/lib 6.10 + [ -d $(DESTDIR)/usr/include ] || $(INSTALL_DIR) $(DESTDIR)/usr/include 6.11 $(INSTALL_PROG) $(LIB) $(DESTDIR)/usr/lib 6.12 ln -sf libxc.so.$(MAJOR).$(MINOR) $(DESTDIR)/usr/lib/libxc.so.$(MAJOR) 6.13 ln -sf libxc.so.$(MAJOR) $(DESTDIR)/usr/lib/libxc.so
7.1 --- a/tools/libxutil/Makefile Thu Jan 27 17:33:33 2005 +0000 7.2 +++ b/tools/libxutil/Makefile Fri Jan 28 07:59:39 2005 +0000 7.3 @@ -63,7 +63,7 @@ check-for-zlib: 7.4 fi 7.5 7.6 install: all 7.7 - $(INSTALL_DIR) -p $(DESTDIR)/usr/lib 7.8 + [ -d $(DESTDIR)/usr/lib ] || $(INSTALL_DIR) -p $(DESTDIR)/usr/lib 7.9 $(INSTALL_PROG) $(LIB) $(DESTDIR)/usr/lib 7.10 ln -sf $(LIB_NAME).so.$(MAJOR).$(MINOR) $(DESTDIR)/usr/lib/$(LIB_NAME).so.$(MAJOR) 7.11 ln -sf $(LIB_NAME).so.$(MAJOR) $(DESTDIR)/usr/lib/$(LIB_NAME).so
8.1 --- a/tools/misc/Makefile Thu Jan 27 17:33:33 2005 +0000 8.2 +++ b/tools/misc/Makefile Fri Jan 28 07:59:39 2005 +0000 8.3 @@ -23,8 +23,8 @@ all: $(TARGETS) 8.4 $(MAKE) -C miniterm 8.5 8.6 install: all 8.7 - $(INSTALL_DIR) $(DESTDIR)/usr/bin 8.8 - $(INSTALL_DIR) $(DESTDIR)/usr/sbin 8.9 + [ -d $(DESTDIR)/usr/bin ] || $(INSTALL_DIR) $(DESTDIR)/usr/bin 8.10 + [ -d $(DESTDIR)/usr/sbin ] || $(INSTALL_DIR) $(DESTDIR)/usr/sbin 8.11 $(INSTALL_PROG) $(INSTALL_BIN) $(DESTDIR)/usr/bin 8.12 $(INSTALL_PROG) $(INSTALL_SBIN) $(DESTDIR)/usr/sbin 8.13 # No sense in installing miniterm on the Xen box.
9.1 --- a/tools/misc/miniterm/Makefile Thu Jan 27 17:33:33 2005 +0000 9.2 +++ b/tools/misc/miniterm/Makefile Fri Jan 28 07:59:39 2005 +0000 9.3 @@ -9,7 +9,7 @@ TARGET = miniterm 9.4 all: $(TARGET) 9.5 9.6 install: all 9.7 - $(INSTALL_DIR) $(DESTDIR)/usr/bin 9.8 + [ -d $(DESTDIR)/usr/bin ] || $(INSTALL_DIR) $(DESTDIR)/usr/bin 9.9 $(INSTALL_PROG) $(TARGET) $(DESTDIR)/usr/bin 9.10 9.11 clean:
10.1 --- a/tools/python/xen/xend/XendDomainInfo.py Thu Jan 27 17:33:33 2005 +0000 10.2 +++ b/tools/python/xen/xend/XendDomainInfo.py Fri Jan 28 07:59:39 2005 +0000 10.3 @@ -457,9 +457,9 @@ class XendDomainInfo: 10.4 10.5 self.init_domain() 10.6 self.configure_console() 10.7 + self.configure_backends() 10.8 self.construct_image() 10.9 self.configure_restart() 10.10 - self.configure_backends() 10.11 deferred = self.configure() 10.12 def cberr(err): 10.13 self.destroy()
11.1 --- a/tools/python/xen/xend/server/netif.py Thu Jan 27 17:33:33 2005 +0000 11.2 +++ b/tools/python/xen/xend/server/netif.py Fri Jan 28 07:59:39 2005 +0000 11.3 @@ -140,7 +140,8 @@ class NetDev(controller.SplitDev): 11.4 self.ipaddr = self._get_config_ipaddr(config) or [] 11.5 11.6 try: 11.7 - self.backendDomain = int(sxp.child_value(config, 'backend', '0')) 11.8 + xd = get_component('xen.xend.XendDomain') 11.9 + self.backendDomain = int(xd.domain_lookup(sxp.child_value(config, 'backend', '0')).id) 11.10 except: 11.11 raise XendError('invalid backend domain') 11.12 11.13 @@ -161,7 +162,8 @@ class NetDev(controller.SplitDev): 11.14 bridge = sxp.child_value(config, 'bridge') 11.15 script = sxp.child_value(config, 'script') 11.16 ipaddr = self._get_config_ipaddr(config) 11.17 - backendDomain = sxp.child_value(config, 'backend', '0') 11.18 + xd = get_component('xen.xend.XendDomain') 11.19 + backendDomain = str(xd.domain_lookup(sxp.child_value(config, 'backend', '0')).id) 11.20 if (mac is not None) and (mac != self.mac): 11.21 raise XendError("cannot change mac") 11.22 if (backendDomain is not None) and (backendDomain != str(self.backendDomain)):
12.1 --- a/tools/sv/Makefile Thu Jan 27 17:33:33 2005 +0000 12.2 +++ b/tools/sv/Makefile Fri Jan 28 07:59:39 2005 +0000 12.3 @@ -17,15 +17,17 @@ IMAGES += next.png previous.png finish.p 12.4 12.5 install: 12.6 # copy XenSV Main.rpy file 12.7 - @$(INSTALL_DIR) $(DESTDIR)$(sv_insdir) 12.8 + @[ -d $(DESTDIR)$(sv_insdir) ] || $(INSTALL_DIR) $(DESTDIR)$(sv_insdir) 12.9 @$(INSTALL_DATA) Main.rpy $(DESTDIR)$(sv_insdir) 12.10 12.11 # copy XenSV images 12.12 - @$(INSTALL_DIR) $(DESTDIR)$(sv_insdir)/images 12.13 + @[ -d $(DESTDIR)$(sv_insdir)/images ] || \ 12.14 + $(INSTALL_DIR) $(DESTDIR)$(sv_insdir)/images 12.15 @(cd images && $(INSTALL_DATA) $(IMAGES) $(DESTDIR)$(sv_insdir)/images) 12.16 12.17 # copy XenSV stylesheet 12.18 - @$(INSTALL_DIR) $(DESTDIR)$(sv_insdir)/inc 12.19 + @[ -d $(DESTDIR)$(sv_insdir)/inc ] || \ 12.20 + $(INSTALL_DIR) $(DESTDIR)$(sv_insdir)/inc 12.21 @$(INSTALL_DATA) inc/style.css inc/script.js $(DESTDIR)$(sv_insdir)/inc 12.22 12.23 clean:
13.1 --- a/tools/xentrace/Makefile Thu Jan 27 17:33:33 2005 +0000 13.2 +++ b/tools/xentrace/Makefile Fri Jan 28 07:59:39 2005 +0000 13.3 @@ -24,9 +24,11 @@ MAN8 = $(wildcard *.8) 13.4 all: $(BIN) 13.5 13.6 install: all 13.7 - $(INSTALL_DIR) $(DESTDIR)/usr/bin 13.8 - $(INSTALL_DIR) $(DESTDIR)/usr/man/man1 13.9 - $(INSTALL_DIR) $(DESTDIR)/usr/man/man8 13.10 + [ -d $(DESTDIR)/usr/bin ] || $(INSTALL_DIR) $(DESTDIR)/usr/bin 13.11 + [ -d $(DESTDIR)/usr/man/man1 ] || \ 13.12 + $(INSTALL_DIR) $(DESTDIR)/usr/man/man1 13.13 + [ -d $(DESTDIR)/usr/man/man8 ] || \ 13.14 + $(INSTALL_DIR) $(DESTDIR)/usr/man/man8 13.15 $(INSTALL_PROG) $(BIN) $(SCRIPTS) $(DESTDIR)/usr/bin 13.16 $(INSTALL_DATA) $(MAN1) $(DESTDIR)/usr/man/man1 13.17 $(INSTALL_DATA) $(MAN8) $(DESTDIR)/usr/man/man8
14.1 --- a/tools/xfrd/Makefile Thu Jan 27 17:33:33 2005 +0000 14.2 +++ b/tools/xfrd/Makefile Fri Jan 28 07:59:39 2005 +0000 14.3 @@ -70,7 +70,8 @@ xfrd: $(XFRD_PROG_OBJ) 14.4 14.5 .PHONY: install 14.6 install: xfrd 14.7 - $(INSTALL_DIR) $(DESTDIR)$(XFRD_INSTALL_DIR) 14.8 + [ -d $(DESTDIR)$(XFRD_INSTALL_DIR) ] || \ 14.9 + $(INSTALL_DIR) $(DESTDIR)$(XFRD_INSTALL_DIR) 14.10 $(INSTALL_PROG) xfrd $(DESTDIR)$(XFRD_INSTALL_DIR) 14.11 14.12 .PHONY: libutil
15.1 --- a/xen/Makefile Thu Jan 27 17:33:33 2005 +0000 15.2 +++ b/xen/Makefile Fri Jan 28 07:59:39 2005 +0000 15.3 @@ -21,10 +21,11 @@ debug: 15.4 objdump -D -S $(TARGET)-syms > $(TARGET).s 15.5 15.6 install: $(TARGET).gz 15.7 - $(INSTALL_DIR) $(DESTDIR)/boot 15.8 + [ -d $(DESTDIR)/boot ] || $(INSTALL_DIR) $(DESTDIR)/boot 15.9 $(INSTALL_DATA) $(TARGET).gz $(DESTDIR)/boot 15.10 $(INSTALL_DATA) $(TARGET)-syms $(DESTDIR)/boot 15.11 - $(INSTALL_DIR) $(DESTDIR)/usr/include/xen/io 15.12 + [ -d $(DESTDIR)/usr/include/xen/io ] || \ 15.13 + $(INSTALL_DIR) $(DESTDIR)/usr/include/xen/io 15.14 $(INSTALL_DATA) include/public/*.h $(DESTDIR)/usr/include/xen 15.15 $(INSTALL_DATA) include/public/io/*.h $(DESTDIR)/usr/include/xen/io 15.16 $(INSTALL_DATA) include/public/COPYING $(DESTDIR)/usr/include/xen
16.1 --- a/xen/arch/x86/domain.c Thu Jan 27 17:33:33 2005 +0000 16.2 +++ b/xen/arch/x86/domain.c Fri Jan 28 07:59:39 2005 +0000 16.3 @@ -308,15 +308,21 @@ void arch_do_createdomain(struct exec_do 16.4 } 16.5 16.6 #ifdef CONFIG_VMX 16.7 -void arch_vmx_do_resume(struct exec_domain *d) 16.8 +void arch_vmx_do_resume(struct exec_domain *ed) 16.9 { 16.10 - vmx_do_resume(d); 16.11 + u64 vmcs_phys_ptr = (u64) virt_to_phys(ed->thread.arch_vmx.vmcs); 16.12 + 16.13 + load_vmcs(&ed->thread.arch_vmx, vmcs_phys_ptr); 16.14 + vmx_do_resume(ed); 16.15 reset_stack_and_jump(vmx_asm_do_resume); 16.16 } 16.17 16.18 -void arch_vmx_do_launch(struct exec_domain *d) 16.19 +void arch_vmx_do_launch(struct exec_domain *ed) 16.20 { 16.21 - vmx_do_launch(d); 16.22 + u64 vmcs_phys_ptr = (u64) virt_to_phys(ed->thread.arch_vmx.vmcs); 16.23 + 16.24 + load_vmcs(&ed->thread.arch_vmx, vmcs_phys_ptr); 16.25 + vmx_do_launch(ed); 16.26 reset_stack_and_jump(vmx_asm_do_launch); 16.27 } 16.28 16.29 @@ -332,14 +338,14 @@ static void monitor_mk_pagetable(struct 16.30 ASSERT( mpfn_info ); 16.31 16.32 mpfn = (unsigned long) (mpfn_info - frame_table); 16.33 - mpl2e = (l2_pgentry_t *) map_domain_mem(mpfn << PAGE_SHIFT); 16.34 + mpl2e = (l2_pgentry_t *) map_domain_mem(mpfn << L1_PAGETABLE_SHIFT); 16.35 memset(mpl2e, 0, PAGE_SIZE); 16.36 16.37 memcpy(&mpl2e[DOMAIN_ENTRIES_PER_L2_PAGETABLE], 16.38 &idle_pg_table[DOMAIN_ENTRIES_PER_L2_PAGETABLE], 16.39 HYPERVISOR_ENTRIES_PER_L2_PAGETABLE * sizeof(l2_pgentry_t)); 16.40 16.41 - m->monitor_table = mk_pagetable(mpfn << PAGE_SHIFT); 16.42 + m->monitor_table = mk_pagetable(mpfn << L1_PAGETABLE_SHIFT); 16.43 m->shadow_mode = SHM_full_32; 16.44 16.45 mpl2e[PERDOMAIN_VIRT_START >> L2_PAGETABLE_SHIFT] = 16.46 @@ -349,13 +355,42 @@ static void monitor_mk_pagetable(struct 16.47 unmap_domain_mem(mpl2e); 16.48 } 16.49 16.50 -static int vmx_final_setup_guestos(struct exec_domain *d, 16.51 +/* 16.52 + * Free the pages for monitor_table and guest_pl2e_cache 16.53 + */ 16.54 +static void monitor_rm_pagetable(struct exec_domain *ed) 16.55 +{ 16.56 + struct mm_struct *m = &ed->mm; 16.57 + l2_pgentry_t *mpl2e; 16.58 + unsigned long mpfn; 16.59 + 16.60 + ASSERT( m->monitor_table ); 16.61 + 16.62 + mpl2e = (l2_pgentry_t *) map_domain_mem(pagetable_val(m->monitor_table)); 16.63 + /* 16.64 + * First get the pfn for guest_pl2e_cache by looking at monitor_table 16.65 + */ 16.66 + mpfn = l2_pgentry_val(mpl2e[LINEAR_PT_VIRT_START >> L2_PAGETABLE_SHIFT]) 16.67 + >> PAGE_SHIFT; 16.68 + 16.69 + free_domheap_page(&frame_table[mpfn]); 16.70 + unmap_domain_mem(mpl2e); 16.71 + 16.72 + /* 16.73 + * Then free monitor_table. 16.74 + */ 16.75 + mpfn = (pagetable_val(m->monitor_table)) >> PAGE_SHIFT; 16.76 + free_domheap_page(&frame_table[mpfn]); 16.77 + 16.78 + m->monitor_table = mk_pagetable(0); 16.79 +} 16.80 + 16.81 +static int vmx_final_setup_guestos(struct exec_domain *ed, 16.82 full_execution_context_t *full_context) 16.83 { 16.84 int error; 16.85 execution_context_t *context; 16.86 struct vmcs_struct *vmcs; 16.87 - unsigned long guest_pa; 16.88 16.89 context = &full_context->cpu_ctxt; 16.90 16.91 @@ -367,33 +402,38 @@ static int vmx_final_setup_guestos(struc 16.92 return -ENOMEM; 16.93 } 16.94 16.95 - memset(&d->thread.arch_vmx, 0, sizeof (struct arch_vmx_struct)); 16.96 + memset(&ed->thread.arch_vmx, 0, sizeof (struct arch_vmx_struct)); 16.97 16.98 - d->thread.arch_vmx.vmcs = vmcs; 16.99 - error = construct_vmcs(&d->thread.arch_vmx, context, full_context, VMCS_USE_HOST_ENV); 16.100 + ed->thread.arch_vmx.vmcs = vmcs; 16.101 + error = construct_vmcs(&ed->thread.arch_vmx, context, full_context, VMCS_USE_HOST_ENV); 16.102 if (error < 0) { 16.103 printk("Failed to construct a new VMCS\n"); 16.104 goto out; 16.105 } 16.106 16.107 - monitor_mk_pagetable(d); 16.108 - guest_pa = pagetable_val(d->mm.pagetable); 16.109 - clear_bit(VMX_CPU_STATE_PG_ENABLED, &d->thread.arch_vmx.cpu_state); 16.110 + monitor_mk_pagetable(ed); 16.111 + ed->thread.schedule_tail = arch_vmx_do_launch; 16.112 + clear_bit(VMX_CPU_STATE_PG_ENABLED, &ed->thread.arch_vmx.cpu_state); 16.113 16.114 - d->thread.arch_vmx.vmx_platform.real_mode_data = 16.115 +#if defined (__i386) 16.116 + ed->thread.arch_vmx.vmx_platform.real_mode_data = 16.117 (unsigned long *) context->esi; 16.118 +#endif 16.119 16.120 - memset(&d->domain->shared_info->evtchn_mask[0], 0xff, 16.121 - sizeof(d->domain->shared_info->evtchn_mask)); 16.122 - clear_bit(IOPACKET_PORT, &d->domain->shared_info->evtchn_mask[0]); 16.123 - 16.124 - d->thread.schedule_tail = arch_vmx_do_launch; 16.125 + if (ed == ed->domain->exec_domain[0]) { 16.126 + /* 16.127 + * Required to do this once per domain 16.128 + */ 16.129 + memset(&ed->domain->shared_info->evtchn_mask[0], 0xff, 16.130 + sizeof(ed->domain->shared_info->evtchn_mask)); 16.131 + clear_bit(IOPACKET_PORT, &ed->domain->shared_info->evtchn_mask[0]); 16.132 + } 16.133 16.134 return 0; 16.135 16.136 out: 16.137 free_vmcs(vmcs); 16.138 - d->thread.arch_vmx.vmcs = 0; 16.139 + ed->thread.arch_vmx.vmcs = 0; 16.140 return error; 16.141 } 16.142 #endif 16.143 @@ -707,6 +747,35 @@ static void relinquish_list(struct domai 16.144 spin_unlock_recursive(&d->page_alloc_lock); 16.145 } 16.146 16.147 +static void vmx_domain_relinquish_memory(struct exec_domain *ed) 16.148 +{ 16.149 + struct domain *d = ed->domain; 16.150 + 16.151 + /* 16.152 + * Free VMCS 16.153 + */ 16.154 + ASSERT(ed->thread.arch_vmx.vmcs); 16.155 + free_vmcs(ed->thread.arch_vmx.vmcs); 16.156 + ed->thread.arch_vmx.vmcs = 0; 16.157 + 16.158 + monitor_rm_pagetable(ed); 16.159 + 16.160 + if (ed == d->exec_domain[0]) { 16.161 + int i; 16.162 + unsigned long pfn; 16.163 + 16.164 + for (i = 0; i < ENTRIES_PER_L1_PAGETABLE; i++) { 16.165 + unsigned long l1e; 16.166 + 16.167 + l1e = l1_pgentry_val(d->mm_perdomain_pt[i]); 16.168 + if (l1e & _PAGE_PRESENT) { 16.169 + pfn = l1e >> PAGE_SHIFT; 16.170 + free_domheap_page(&frame_table[pfn]); 16.171 + } 16.172 + } 16.173 + } 16.174 + 16.175 +} 16.176 16.177 void domain_relinquish_memory(struct domain *d) 16.178 { 16.179 @@ -725,6 +794,10 @@ void domain_relinquish_memory(struct dom 16.180 PAGE_SHIFT]); 16.181 } 16.182 16.183 + if (VMX_DOMAIN(d->exec_domain[0])) 16.184 + for_each_exec_domain(d, ed) 16.185 + vmx_domain_relinquish_memory(ed); 16.186 + 16.187 /* 16.188 * Relinquish GDT mappings. No need for explicit unmapping of the LDT as 16.189 * it automatically gets squashed when the guest's mappings go away.
17.1 --- a/xen/arch/x86/vmx.c Thu Jan 27 17:33:33 2005 +0000 17.2 +++ b/xen/arch/x86/vmx.c Fri Jan 28 07:59:39 2005 +0000 17.3 @@ -41,6 +41,11 @@ unsigned int opt_vmx_debug_level; 17.4 extern long evtchn_send(int lport); 17.5 extern long do_block(void); 17.6 17.7 +#define VECTOR_DB 1 17.8 +#define VECTOR_BP 3 17.9 +#define VECTOR_GP 13 17.10 +#define VECTOR_PG 14 17.11 + 17.12 int start_vmx() 17.13 { 17.14 struct vmcs_struct *vmcs; 17.15 @@ -102,7 +107,7 @@ static int vmx_do_page_fault(unsigned lo 17.16 { 17.17 unsigned long eip, pfn; 17.18 unsigned int index; 17.19 - unsigned long gpde = 0; 17.20 + unsigned long gpde = 0, gpte, gpa; 17.21 int result; 17.22 struct exec_domain *ed = current; 17.23 struct mm_struct *m = &ed->mm; 17.24 @@ -132,6 +137,15 @@ static int vmx_do_page_fault(unsigned lo 17.25 m->guest_pl2e_cache[index] = 17.26 mk_l2_pgentry((pfn << PAGE_SHIFT) | __PAGE_HYPERVISOR); 17.27 } 17.28 + 17.29 + if (unlikely(__get_user(gpte, (unsigned long *) 17.30 + &linear_pg_table[va >> PAGE_SHIFT]))) 17.31 + return 0; 17.32 + 17.33 + gpa = (gpte & PAGE_MASK) | (va & (PAGE_SIZE - 1)); 17.34 + 17.35 + if (mmio_space(gpa)) 17.36 + handle_mmio(va, gpte, gpa); 17.37 17.38 if ((result = shadow_fault(va, error_code))) 17.39 return result; 17.40 @@ -142,19 +156,26 @@ static int vmx_do_page_fault(unsigned lo 17.41 static void vmx_do_general_protection_fault(struct xen_regs *regs) 17.42 { 17.43 unsigned long eip, error_code; 17.44 + unsigned long intr_fields; 17.45 17.46 __vmread(GUEST_EIP, &eip); 17.47 __vmread(VM_EXIT_INTR_ERROR_CODE, &error_code); 17.48 17.49 - VMX_DBG_LOG(DBG_LEVEL_1, 17.50 + VMX_DBG_LOG(DBG_LEVEL_1, 17.51 "vmx_general_protection_fault: eip = %lx, erro_code = %lx\n", 17.52 eip, error_code); 17.53 17.54 - VMX_DBG_LOG(DBG_LEVEL_1, 17.55 + VMX_DBG_LOG(DBG_LEVEL_1, 17.56 "eax=%x, ebx=%x, ecx=%x, edx=%x, esi=%x, edi=%x\n", 17.57 regs->eax, regs->ebx, regs->ecx, regs->edx, regs->esi, regs->edi); 17.58 17.59 - __vmx_bug(regs); 17.60 + /* Reflect it back into the guest */ 17.61 + intr_fields = (INTR_INFO_VALID_MASK | 17.62 + INTR_TYPE_EXCEPTION | 17.63 + INTR_INFO_DELIEVER_CODE_MASK | 17.64 + VECTOR_GP); 17.65 + __vmwrite(VM_ENTRY_INTR_INFO_FIELD, intr_fields); 17.66 + __vmwrite(VM_ENTRY_EXCEPTION_ERROR_CODE, error_code); 17.67 } 17.68 17.69 static void vmx_vmexit_do_cpuid(unsigned long input, struct xen_regs *regs) 17.70 @@ -271,7 +292,7 @@ static inline void guest_pl2e_cache_inva 17.71 memset(m->guest_pl2e_cache, 0, PAGE_SIZE); 17.72 } 17.73 17.74 -static inline unsigned long gva_to_gpa(unsigned long gva) 17.75 +inline unsigned long gva_to_gpa(unsigned long gva) 17.76 { 17.77 unsigned long gpde, gpte, pfn, index; 17.78 struct exec_domain *d = current; 17.79 @@ -340,6 +361,10 @@ static void vmx_io_instruction(struct xe 17.80 p->size = (exit_qualification & 7) + 1; 17.81 17.82 if (test_bit(4, &exit_qualification)) { 17.83 + unsigned long eflags; 17.84 + 17.85 + __vmread(GUEST_EFLAGS, &eflags); 17.86 + p->df = (eflags & X86_EFLAGS_DF) ? 1 : 0; 17.87 p->pdata_valid = 1; 17.88 p->u.pdata = (void *) ((p->dir == IOREQ_WRITE) ? 17.89 regs->esi 17.90 @@ -725,11 +750,6 @@ asmlinkage void vmx_vmexit_handler(struc 17.91 switch (exit_reason) { 17.92 case EXIT_REASON_EXCEPTION_NMI: 17.93 { 17.94 -#define VECTOR_DB 1 17.95 -#define VECTOR_BP 3 17.96 -#define VECTOR_GP 13 17.97 -#define VECTOR_PG 14 17.98 - 17.99 /* 17.100 * We don't set the software-interrupt exiting (INT n). 17.101 * (1) We can get an exception (e.g. #PG) in the guest, or 17.102 @@ -773,6 +793,7 @@ asmlinkage void vmx_vmexit_handler(struc 17.103 __vmread(VM_EXIT_INTR_ERROR_CODE, &error_code); 17.104 VMX_DBG_LOG(DBG_LEVEL_VMMU, 17.105 "eax=%x, ebx=%x, ecx=%x, edx=%x, esi=%x, edi=%x\n", regs.eax, regs.ebx, regs.ecx, regs.edx, regs.esi, regs.edi); 17.106 + d->thread.arch_vmx.vmx_platform.mpci.inst_decoder_regs = ®s; 17.107 17.108 if (!(error = vmx_do_page_fault(va, error_code))) { 17.109 /*
18.1 --- a/xen/arch/x86/vmx_io.c Thu Jan 27 17:33:33 2005 +0000 18.2 +++ b/xen/arch/x86/vmx_io.c Fri Jan 28 07:59:39 2005 +0000 18.3 @@ -29,8 +29,143 @@ 18.4 #include <asm/vmx_vmcs.h> 18.5 #include <xen/event.h> 18.6 #include <public/io/ioreq.h> 18.7 +#include <asm/vmx_platform.h> 18.8 18.9 extern long do_block(); 18.10 + 18.11 +#if defined (__i386__) 18.12 +static void load_xen_regs(struct xen_regs *regs) 18.13 +{ 18.14 + /* 18.15 + * Write the guest register value into VMCS 18.16 + */ 18.17 + __vmwrite(GUEST_SS_SELECTOR, regs->ss); 18.18 + __vmwrite(GUEST_ESP, regs->esp); 18.19 + __vmwrite(GUEST_EFLAGS, regs->eflags); 18.20 + __vmwrite(GUEST_CS_SELECTOR, regs->cs); 18.21 + __vmwrite(GUEST_EIP, regs->eip); 18.22 +} 18.23 + 18.24 +static void set_reg_value (int size, int index, int seg, struct xen_regs *regs, long value) 18.25 +{ 18.26 + switch (size) { 18.27 + case BYTE: 18.28 + switch (index) { 18.29 + case 0: 18.30 + regs->eax &= 0xFFFFFF00; 18.31 + regs->eax |= (value & 0xFF); 18.32 + break; 18.33 + case 1: 18.34 + regs->ecx &= 0xFFFFFF00; 18.35 + regs->ecx |= (value & 0xFF); 18.36 + break; 18.37 + case 2: 18.38 + regs->edx &= 0xFFFFFF00; 18.39 + regs->edx |= (value & 0xFF); 18.40 + break; 18.41 + case 3: 18.42 + regs->ebx &= 0xFFFFFF00; 18.43 + regs->ebx |= (value & 0xFF); 18.44 + break; 18.45 + case 4: 18.46 + regs->eax &= 0xFFFF00FF; 18.47 + regs->eax |= ((value & 0xFF) << 8); 18.48 + break; 18.49 + case 5: 18.50 + regs->ecx &= 0xFFFF00FF; 18.51 + regs->ecx |= ((value & 0xFF) << 8); 18.52 + break; 18.53 + case 6: 18.54 + regs->edx &= 0xFFFF00FF; 18.55 + regs->edx |= ((value & 0xFF) << 8); 18.56 + break; 18.57 + case 7: 18.58 + regs->ebx &= 0xFFFF00FF; 18.59 + regs->ebx |= ((value & 0xFF) << 8); 18.60 + break; 18.61 + default: 18.62 + printk("size:%x, index:%x are invalid!\n", size, index); 18.63 + break; 18.64 + 18.65 + } 18.66 + break; 18.67 + case WORD: 18.68 + switch (index) { 18.69 + case 0: 18.70 + regs->eax &= 0xFFFF0000; 18.71 + regs->eax |= (value & 0xFFFF); 18.72 + break; 18.73 + case 1: 18.74 + regs->ecx &= 0xFFFF0000; 18.75 + regs->ecx |= (value & 0xFFFF); 18.76 + break; 18.77 + case 2: 18.78 + regs->edx &= 0xFFFF0000; 18.79 + regs->edx |= (value & 0xFFFF); 18.80 + break; 18.81 + case 3: 18.82 + regs->ebx &= 0xFFFF0000; 18.83 + regs->ebx |= (value & 0xFFFF); 18.84 + break; 18.85 + case 4: 18.86 + regs->esp &= 0xFFFF0000; 18.87 + regs->esp |= (value & 0xFFFF); 18.88 + break; 18.89 + 18.90 + case 5: 18.91 + regs->ebp &= 0xFFFF0000; 18.92 + regs->ebp |= (value & 0xFFFF); 18.93 + break; 18.94 + case 6: 18.95 + regs->esi &= 0xFFFF0000; 18.96 + regs->esi |= (value & 0xFFFF); 18.97 + break; 18.98 + case 7: 18.99 + regs->edi &= 0xFFFF0000; 18.100 + regs->edi |= (value & 0xFFFF); 18.101 + break; 18.102 + default: 18.103 + printk("size:%x, index:%x are invalid!\n", size, index); 18.104 + break; 18.105 + } 18.106 + break; 18.107 + case LONG: 18.108 + switch (index) { 18.109 + case 0: 18.110 + regs->eax = value; 18.111 + break; 18.112 + case 1: 18.113 + regs->ecx = value; 18.114 + break; 18.115 + case 2: 18.116 + regs->edx = value; 18.117 + break; 18.118 + case 3: 18.119 + regs->ebx = value; 18.120 + break; 18.121 + case 4: 18.122 + regs->esp = value; 18.123 + break; 18.124 + case 5: 18.125 + regs->ebp = value; 18.126 + break; 18.127 + case 6: 18.128 + regs->esi = value; 18.129 + break; 18.130 + case 7: 18.131 + regs->edi = value; 18.132 + break; 18.133 + default: 18.134 + printk("size:%x, index:%x are invalid!\n", size, index); 18.135 + break; 18.136 + } 18.137 + break; 18.138 + default: 18.139 + printk("size:%x, index:%x are invalid!\n", size, index); 18.140 + break; 18.141 + } 18.142 +} 18.143 +#endif 18.144 18.145 void vmx_io_assist(struct exec_domain *ed) 18.146 { 18.147 @@ -39,8 +174,12 @@ void vmx_io_assist(struct exec_domain *e 18.148 struct domain *d = ed->domain; 18.149 execution_context_t *ec = get_execution_context(); 18.150 unsigned long old_eax; 18.151 - unsigned long eflags; 18.152 - int dir; 18.153 + int sign; 18.154 + struct mi_per_cpu_info *mpci_p; 18.155 + struct xen_regs *inst_decoder_regs; 18.156 + 18.157 + mpci_p = &ed->thread.arch_vmx.vmx_platform.mpci; 18.158 + inst_decoder_regs = mpci_p->inst_decoder_regs; 18.159 18.160 /* clear the pending event */ 18.161 ed->vcpu_info->evtchn_upcall_pending = 0; 18.162 @@ -68,24 +207,39 @@ void vmx_io_assist(struct exec_domain *e 18.163 return; 18.164 } 18.165 18.166 - __vmread(GUEST_EFLAGS, &eflags); 18.167 - dir = (eflags & X86_EFLAGS_DF); 18.168 + sign = (p->df) ? -1 : 1; 18.169 + if (p->port_mm) { 18.170 + if (p->pdata_valid) { 18.171 + ec->esi += sign * p->count * p->size; 18.172 + ec->edi += sign * p->count * p->size; 18.173 + } else { 18.174 + if (p->dir == IOREQ_WRITE) { 18.175 + return; 18.176 + } 18.177 + int size = -1, index = -1; 18.178 + 18.179 + size = operand_size(ed->thread.arch_vmx.vmx_platform.mpci.mmio_target); 18.180 + index = operand_index(ed->thread.arch_vmx.vmx_platform.mpci.mmio_target); 18.181 + 18.182 + if (ed->thread.arch_vmx.vmx_platform.mpci.mmio_target & WZEROEXTEND) { 18.183 + p->u.data = p->u.data & 0xffff; 18.184 + } 18.185 + set_reg_value(size, index, 0, (struct xen_regs *)ec, p->u.data); 18.186 + 18.187 + } 18.188 + load_xen_regs((struct xen_regs *)ec); 18.189 + return; 18.190 + } 18.191 18.192 if (p->dir == IOREQ_WRITE) { 18.193 if (p->pdata_valid) { 18.194 - if (!dir) 18.195 - ec->esi += p->count * p->size; 18.196 - else 18.197 - ec->esi -= p->count * p->size; 18.198 + ec->esi += sign * p->count * p->size; 18.199 ec->ecx -= p->count; 18.200 } 18.201 return; 18.202 } else { 18.203 if (p->pdata_valid) { 18.204 - if (!dir) 18.205 - ec->edi += p->count * p->size; 18.206 - else 18.207 - ec->edi -= p->count * p->size; 18.208 + ec->edi += sign * p->count * p->size; 18.209 ec->ecx -= p->count; 18.210 return; 18.211 }
19.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 19.2 +++ b/xen/arch/x86/vmx_platform.c Fri Jan 28 07:59:39 2005 +0000 19.3 @@ -0,0 +1,554 @@ 19.4 +/* 19.5 + * vmx_platform.c: handling x86 platform related MMIO instructions 19.6 + * Copyright (c) 2004, Intel Corporation. 19.7 + * 19.8 + * This program is free software; you can redistribute it and/or modify it 19.9 + * under the terms and conditions of the GNU General Public License, 19.10 + * version 2, as published by the Free Software Foundation. 19.11 + * 19.12 + * This program is distributed in the hope it will be useful, but WITHOUT 19.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 19.14 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 19.15 + * more details. 19.16 + * 19.17 + * You should have received a copy of the GNU General Public License along with 19.18 + * this program; if not, write to the Free Software Foundation, Inc., 59 Temple 19.19 + * Place - Suite 330, Boston, MA 02111-1307 USA. 19.20 + * 19.21 + */ 19.22 + 19.23 +#include <xen/config.h> 19.24 +#include <xen/types.h> 19.25 +#include <xen/mm.h> 19.26 +#include <asm/shadow.h> 19.27 +#include <asm/domain_page.h> 19.28 +#include <asm/page.h> 19.29 +#include <xen/event.h> 19.30 +#include <xen/trace.h> 19.31 +#include <asm/vmx.h> 19.32 +#include <asm/vmx_platform.h> 19.33 +#include <public/io/ioreq.h> 19.34 + 19.35 +#include <xen/lib.h> 19.36 +#include <xen/sched.h> 19.37 +#include <asm/current.h> 19.38 + 19.39 +#define DECODE_success 1 19.40 +#define DECODE_failure 0 19.41 + 19.42 +#if defined (__x86_64__) 19.43 +static void store_xen_regs(struct xen_regs *regs) 19.44 +{ 19.45 + 19.46 +} 19.47 + 19.48 +static long get_reg_value(int size, int index, int seg, struct xen_regs *regs) 19.49 +{ 19.50 + return 0; 19.51 +} 19.52 +#elif defined (__i386__) 19.53 +static void store_xen_regs(struct xen_regs *regs) 19.54 +{ 19.55 + __vmread(GUEST_SS_SELECTOR, ®s->ss); 19.56 + __vmread(GUEST_ESP, ®s->esp); 19.57 + __vmread(GUEST_EFLAGS, ®s->eflags); 19.58 + __vmread(GUEST_CS_SELECTOR, ®s->cs); 19.59 + __vmread(GUEST_EIP, ®s->eip); 19.60 +} 19.61 + 19.62 +static long get_reg_value(int size, int index, int seg, struct xen_regs *regs) 19.63 +{ 19.64 + /* 19.65 + * Reference the db_reg[] table 19.66 + */ 19.67 + switch (size) { 19.68 + case BYTE: 19.69 + switch (index) { 19.70 + case 0: //%al 19.71 + return (char)(regs->eax & 0xFF); 19.72 + case 1: //%cl 19.73 + return (char)(regs->ecx & 0xFF); 19.74 + case 2: //%dl 19.75 + return (char)(regs->edx & 0xFF); 19.76 + case 3: //%bl 19.77 + return (char)(regs->ebx & 0xFF); 19.78 + case 4: //%ah 19.79 + return (char)((regs->eax & 0xFF00) >> 8); 19.80 + case 5: //%ch 19.81 + return (char)((regs->ecx & 0xFF00) >> 8); 19.82 + case 6: //%dh 19.83 + return (char)((regs->edx & 0xFF00) >> 8); 19.84 + case 7: //%bh 19.85 + return (char)((regs->ebx & 0xFF00) >> 8); 19.86 + default: 19.87 + printk("(get_reg_value)size case 0 error\n"); 19.88 + return -1; 19.89 + } 19.90 + case WORD: 19.91 + switch (index) { 19.92 + case 0: //%ax 19.93 + return (short)(regs->eax & 0xFFFF); 19.94 + case 1: //%cx 19.95 + return (short)(regs->ecx & 0xFFFF); 19.96 + case 2: //%dx 19.97 + return (short)(regs->edx & 0xFFFF); 19.98 + case 3: //%bx 19.99 + return (short)(regs->ebx & 0xFFFF); 19.100 + case 4: //%sp 19.101 + return (short)(regs->esp & 0xFFFF); 19.102 + break; 19.103 + case 5: //%bp 19.104 + return (short)(regs->ebp & 0xFFFF); 19.105 + case 6: //%si 19.106 + return (short)(regs->esi & 0xFFFF); 19.107 + case 7: //%di 19.108 + return (short)(regs->edi & 0xFFFF); 19.109 + default: 19.110 + printk("(get_reg_value)size case 1 error\n"); 19.111 + return -1; 19.112 + } 19.113 + case LONG: 19.114 + switch (index) { 19.115 + case 0: //%eax 19.116 + return regs->eax; 19.117 + case 1: //%ecx 19.118 + return regs->ecx; 19.119 + case 2: //%edx 19.120 + return regs->edx; 19.121 + 19.122 + case 3: //%ebx 19.123 + return regs->ebx; 19.124 + case 4: //%esp 19.125 + return regs->esp; 19.126 + case 5: //%ebp 19.127 + return regs->ebp; 19.128 + case 6: //%esi 19.129 + return regs->esi; 19.130 + case 7: //%edi 19.131 + return regs->edi; 19.132 + default: 19.133 + printk("(get_reg_value)size case 2 error\n"); 19.134 + return -1; 19.135 + } 19.136 + default: 19.137 + printk("(get_reg_value)size case error\n"); 19.138 + return -1; 19.139 + } 19.140 +} 19.141 +#endif 19.142 + 19.143 +static inline unsigned char *check_prefix(unsigned char *inst, struct instruction *thread_inst) 19.144 +{ 19.145 + while (1) { 19.146 + switch (*inst) { 19.147 + case 0xf3: //REPZ 19.148 + case 0xf2: //REPNZ 19.149 + case 0xf0: //LOCK 19.150 + case 0x2e: //CS 19.151 + case 0x36: //SS 19.152 + case 0x3e: //DS 19.153 + case 0x26: //ES 19.154 + case 0x64: //FS 19.155 + case 0x65: //GS 19.156 + break; 19.157 + case 0x66: //32bit->16bit 19.158 + thread_inst->op_size = WORD; 19.159 + break; 19.160 + case 0x67: 19.161 + break; 19.162 + default: 19.163 + return inst; 19.164 + } 19.165 + inst++; 19.166 + } 19.167 +} 19.168 + 19.169 +static inline unsigned long get_immediate(const unsigned char *inst, int op_size) 19.170 +{ 19.171 + int mod, reg, rm; 19.172 + unsigned long val = 0; 19.173 + int i; 19.174 + 19.175 + mod = (*inst >> 6) & 3; 19.176 + reg = (*inst >> 3) & 7; 19.177 + rm = *inst & 7; 19.178 + 19.179 + inst++; //skip ModR/M byte 19.180 + if (mod != 3 && rm == 4) { 19.181 + inst++; //skip SIB byte 19.182 + } 19.183 + 19.184 + switch(mod) { 19.185 + case 0: 19.186 + if (rm == 5) { 19.187 + inst = inst + 4; //disp32, skip 4 bytes 19.188 + } 19.189 + break; 19.190 + case 1: 19.191 + inst++; //disp8, skip 1 byte 19.192 + break; 19.193 + case 2: 19.194 + inst = inst + 4; //disp32, skip 4 bytes 19.195 + } 19.196 + for (i = 0; i < op_size; i++) { 19.197 + val |= (*inst++ & 0xff) << (8 * i); 19.198 + } 19.199 + 19.200 + return val; 19.201 +} 19.202 + 19.203 +static inline int get_index(const unsigned char *inst) 19.204 +{ 19.205 + int mod, reg, rm; 19.206 + 19.207 + mod = (*inst >> 6) & 3; 19.208 + reg = (*inst >> 3) & 7; 19.209 + rm = *inst & 7; 19.210 + 19.211 + //Only one operand in the instruction is register 19.212 + if (mod == 3) { 19.213 + return rm; 19.214 + } else { 19.215 + return reg; 19.216 + } 19.217 + return 0; 19.218 +} 19.219 + 19.220 +static int vmx_decode(const unsigned char *inst, struct instruction *thread_inst) 19.221 +{ 19.222 + int index; 19.223 + 19.224 + switch(*inst) { 19.225 + case 0x88: 19.226 + /* mov r8 to m8 */ 19.227 + thread_inst->op_size = BYTE; 19.228 + index = get_index((inst + 1)); 19.229 + thread_inst->operand[0] = mk_operand(BYTE, index, 0, REGISTER); 19.230 + break; 19.231 + case 0x89: 19.232 + /* mov r32/16 to m32/16 */ 19.233 + index = get_index((inst + 1)); 19.234 + if (thread_inst->op_size == WORD) { 19.235 + thread_inst->operand[0] = mk_operand(WORD, index, 0, REGISTER); 19.236 + } else { 19.237 + thread_inst->op_size = LONG; 19.238 + thread_inst->operand[0] = mk_operand(LONG, index, 0, REGISTER); 19.239 + } 19.240 + break; 19.241 + case 0x8a: 19.242 + /* mov m8 to r8 */ 19.243 + thread_inst->op_size = BYTE; 19.244 + index = get_index((inst + 1)); 19.245 + thread_inst->operand[1] = mk_operand(BYTE, index, 0, REGISTER); 19.246 + break; 19.247 + case 0x8b: 19.248 + /* mov r32/16 to m32/16 */ 19.249 + index = get_index((inst + 1)); 19.250 + if (thread_inst->op_size == WORD) { 19.251 + thread_inst->operand[1] = mk_operand(WORD, index, 0, REGISTER); 19.252 + } else { 19.253 + thread_inst->op_size = LONG; 19.254 + thread_inst->operand[1] = mk_operand(LONG, index, 0, REGISTER); 19.255 + } 19.256 + break; 19.257 + case 0x8c: 19.258 + case 0x8e: 19.259 + printk("%x, This opcode hasn't been handled yet!", *inst); 19.260 + return DECODE_failure; 19.261 + /* Not handle it yet. */ 19.262 + 19.263 + case 0xa0: 19.264 + /* mov byte to al */ 19.265 + thread_inst->op_size = BYTE; 19.266 + thread_inst->operand[1] = mk_operand(BYTE, 0, 0, REGISTER); 19.267 + break; 19.268 + case 0xa1: 19.269 + /* mov word/doubleword to ax/eax */ 19.270 + if (thread_inst->op_size == WORD) { 19.271 + thread_inst->operand[1] = mk_operand(WORD, 0, 0, REGISTER); 19.272 + } else { 19.273 + thread_inst->op_size = LONG; 19.274 + thread_inst->operand[1] = mk_operand(LONG, 0, 0, REGISTER); 19.275 + } 19.276 + break; 19.277 + case 0xa2: 19.278 + /* mov al to (seg:offset) */ 19.279 + thread_inst->op_size = BYTE; 19.280 + thread_inst->operand[0] = mk_operand(BYTE, 0, 0, REGISTER); 19.281 + break; 19.282 + case 0xa3: 19.283 + /* mov ax/eax to (seg:offset) */ 19.284 + if (thread_inst->op_size == WORD) { 19.285 + thread_inst->operand[0] = mk_operand(WORD, 0, 0, REGISTER); 19.286 + } else { 19.287 + thread_inst->op_size = LONG; 19.288 + thread_inst->operand[0] = mk_operand(LONG, 0, 0, REGISTER); 19.289 + } 19.290 + break; 19.291 + case 0xa4: 19.292 + /* movsb */ 19.293 + thread_inst->op_size = BYTE; 19.294 + strcpy(thread_inst->i_name, "movs"); 19.295 + 19.296 + return DECODE_success; 19.297 + case 0xa5: 19.298 + /* movsw/movsl */ 19.299 + if (thread_inst->op_size == WORD) { 19.300 + } else { 19.301 + thread_inst->op_size = LONG; 19.302 + } 19.303 + 19.304 + strcpy(thread_inst->i_name, "movs"); 19.305 + 19.306 + return DECODE_success; 19.307 + 19.308 + case 0xc6: 19.309 + /* mov imm8 to m8 */ 19.310 + thread_inst->op_size = BYTE; 19.311 + thread_inst->operand[0] = mk_operand(BYTE, 0, 0, IMMEDIATE); 19.312 + thread_inst->immediate = get_immediate((inst+1), thread_inst->op_size); 19.313 + break; 19.314 + case 0xc7: 19.315 + /* mov imm16/32 to m16/32 */ 19.316 + if (thread_inst->op_size == WORD) { 19.317 + thread_inst->operand[0] = mk_operand(WORD, 0, 0, IMMEDIATE); 19.318 + } else { 19.319 + thread_inst->op_size = LONG; 19.320 + thread_inst->operand[0] = mk_operand(LONG, 0, 0, IMMEDIATE); 19.321 + } 19.322 + thread_inst->immediate = get_immediate((inst+1), thread_inst->op_size); 19.323 + break; 19.324 + 19.325 + case 0x0f: 19.326 + break; 19.327 + default: 19.328 + printk("%x, This opcode hasn't been handled yet!", *inst); 19.329 + return DECODE_failure; 19.330 + } 19.331 + 19.332 + strcpy(thread_inst->i_name, "mov"); 19.333 + if (*inst != 0x0f) { 19.334 + return DECODE_success; 19.335 + } 19.336 + 19.337 + inst++; 19.338 + switch (*inst) { 19.339 + 19.340 + /* movz */ 19.341 + case 0xb7: 19.342 + index = get_index((inst + 1)); 19.343 + thread_inst->operand[1] = mk_operand(LONG, index, 0, REGISTER); 19.344 + strcpy(thread_inst->i_name, "movzw"); 19.345 + 19.346 + return DECODE_success; 19.347 + default: 19.348 + printk("0f %x, This opcode hasn't been handled yet!", *inst); 19.349 + return DECODE_failure; 19.350 + } 19.351 + 19.352 + /* will never reach here */ 19.353 + return DECODE_failure; 19.354 +} 19.355 + 19.356 +static int inst_copy_from_guest(char *buf, unsigned long guest_eip, int inst_len) 19.357 +{ 19.358 + unsigned long gpte; 19.359 + unsigned long mfn; 19.360 + unsigned long ma; 19.361 + unsigned char * inst_start; 19.362 + 19.363 + if (inst_len > MAX_INST_LEN || inst_len <= 0) { 19.364 + return 0; 19.365 + } 19.366 + 19.367 + if ((guest_eip & PAGE_MASK) == ((guest_eip + inst_len) & PAGE_MASK)) { 19.368 + if ( unlikely(__get_user(gpte, (unsigned long *) 19.369 + &linear_pg_table[guest_eip >> PAGE_SHIFT])) ) 19.370 + { 19.371 + printk("inst_copy_from_guest- EXIT: read gpte faulted" ); 19.372 + return 0; 19.373 + } 19.374 + mfn = phys_to_machine_mapping[gpte >> PAGE_SHIFT]; 19.375 + ma = (mfn << PAGE_SHIFT) | (guest_eip & (PAGE_SIZE - 1)); 19.376 + inst_start = (unsigned char *)map_domain_mem(ma); 19.377 + 19.378 + strncpy(buf, inst_start, inst_len); 19.379 + unmap_domain_mem(inst_start); 19.380 + } else { 19.381 + // Todo: In two page frames 19.382 + } 19.383 + 19.384 + return inst_len; 19.385 +} 19.386 + 19.387 +static void init_instruction(struct instruction *mmio_inst) 19.388 +{ 19.389 + memset(mmio_inst->i_name, '0', I_NAME_LEN); 19.390 + mmio_inst->op_size = 0; 19.391 + mmio_inst->offset = 0; 19.392 + mmio_inst->immediate = 0; 19.393 + mmio_inst->seg_sel = 0; 19.394 + mmio_inst->op_num = 0; 19.395 + 19.396 + mmio_inst->operand[0] = 0; 19.397 + mmio_inst->operand[1] = 0; 19.398 + mmio_inst->operand[2] = 0; 19.399 + 19.400 + mmio_inst->flags = 0; 19.401 +} 19.402 + 19.403 +static int read_from_mmio(struct instruction *inst_p) 19.404 +{ 19.405 + // Only for mov instruction now!!! 19.406 + if (inst_p->operand[1] & REGISTER) 19.407 + return 1; 19.408 + 19.409 + return 0; 19.410 +} 19.411 + 19.412 +// dir: 1 read from mmio 19.413 +// 0 write to mmio 19.414 +static void send_mmio_req(unsigned long gpa, 19.415 + struct instruction *inst_p, long value, int dir, int pvalid) 19.416 +{ 19.417 + struct exec_domain *d = current; 19.418 + vcpu_iodata_t *vio; 19.419 + ioreq_t *p; 19.420 + struct mi_per_cpu_info *mpci_p; 19.421 + struct xen_regs *inst_decoder_regs; 19.422 + extern inline unsigned long gva_to_gpa(unsigned long gva); 19.423 + extern long evtchn_send(int lport); 19.424 + extern long do_block(void); 19.425 + 19.426 + mpci_p = ¤t->thread.arch_vmx.vmx_platform.mpci; 19.427 + inst_decoder_regs = mpci_p->inst_decoder_regs; 19.428 + vio = (vcpu_iodata_t *) d->thread.arch_vmx.vmx_platform.shared_page_va; 19.429 + 19.430 + if (vio == NULL) { 19.431 + printk("bad shared page\n"); 19.432 + domain_crash(); 19.433 + } 19.434 + p = &vio->vp_ioreq; 19.435 + 19.436 + set_bit(ARCH_VMX_IO_WAIT, &d->thread.arch_vmx.flags); 19.437 + p->dir = dir; 19.438 + p->pdata_valid = pvalid; 19.439 + p->count = 1; 19.440 + 19.441 + p->port_mm = 1; 19.442 + p->size = inst_p->op_size; 19.443 + p->addr = gpa; 19.444 + p->u.data = value; 19.445 + 19.446 + // p->state = STATE_UPSTREAM_SENDING; 19.447 + p->state = STATE_IOREQ_READY; 19.448 + 19.449 + // Try to use ins/outs' framework 19.450 + if (pvalid) { 19.451 + // Handle "movs" 19.452 + p->u.pdata = (void *) ((p->dir == IOREQ_WRITE) ? 19.453 + inst_decoder_regs->esi 19.454 + : inst_decoder_regs->edi); 19.455 + p->u.pdata = (void *) gva_to_gpa(p->u.data); 19.456 + p->count = inst_decoder_regs->ecx; 19.457 + inst_decoder_regs->ecx = 0; 19.458 + p->df = (inst_decoder_regs->eflags & EF_DF) ? 1 : 0; 19.459 + } 19.460 + 19.461 + evtchn_send(IOPACKET_PORT); 19.462 + do_block(); 19.463 + 19.464 +} 19.465 + 19.466 +void handle_mmio(unsigned long va, unsigned long gpte, unsigned long gpa) 19.467 +{ 19.468 + unsigned long eip; 19.469 + unsigned long inst_len; 19.470 + struct mi_per_cpu_info *mpci_p; 19.471 + struct xen_regs *inst_decoder_regs; 19.472 + struct instruction mmio_inst; 19.473 + unsigned char inst[MAX_INST_LEN]; 19.474 + int ret; 19.475 + 19.476 + mpci_p = ¤t->thread.arch_vmx.vmx_platform.mpci; 19.477 + inst_decoder_regs = mpci_p->inst_decoder_regs; 19.478 + 19.479 + __vmread(GUEST_EIP, &eip); 19.480 + __vmread(INSTRUCTION_LEN, &inst_len); 19.481 + 19.482 + memset(inst, '0', MAX_INST_LEN); 19.483 + ret = inst_copy_from_guest(inst, eip, inst_len); 19.484 + if (ret != inst_len) { 19.485 + printk("handle_mmio - EXIT: get guest instruction fault\n"); 19.486 + domain_crash(); 19.487 + } 19.488 + 19.489 + init_instruction(&mmio_inst); 19.490 + 19.491 + if (vmx_decode(check_prefix(inst, &mmio_inst), &mmio_inst) == DECODE_failure) 19.492 + domain_crash(); 19.493 + 19.494 + __vmwrite(GUEST_EIP, eip + inst_len); 19.495 + store_xen_regs(inst_decoder_regs); 19.496 + 19.497 + // Only handle "mov" and "movs" instructions! 19.498 + if (!strncmp(mmio_inst.i_name, "movzw", 5)) { 19.499 + long value = 0; 19.500 + int index; 19.501 + 19.502 + if (read_from_mmio(&mmio_inst)) { 19.503 + // Send the request and waiting for return value. 19.504 + mpci_p->mmio_target = mmio_inst.operand[1] | WZEROEXTEND; 19.505 + mmio_inst.op_size = WORD; 19.506 + send_mmio_req(gpa, &mmio_inst, value, 1, 0); 19.507 + } else { 19.508 + // Write to MMIO 19.509 + if (mmio_inst.operand[0] & IMMEDIATE) { 19.510 + value = mmio_inst.immediate; 19.511 + } else if (mmio_inst.operand[0] & REGISTER) { 19.512 + index = operand_index(mmio_inst.operand[0]); 19.513 + value = get_reg_value(WORD, index, 0, inst_decoder_regs); 19.514 + } else { 19.515 + domain_crash(); 19.516 + } 19.517 + mmio_inst.op_size = WORD; 19.518 + send_mmio_req(gpa, &mmio_inst, value, 0, 0); 19.519 + return; 19.520 + } 19.521 + } 19.522 + 19.523 + if (!strncmp(mmio_inst.i_name, "movs", 4)) { 19.524 + int tmp_dir; 19.525 + 19.526 + tmp_dir = ((va == inst_decoder_regs->edi) ? IOREQ_WRITE : IOREQ_READ); 19.527 + send_mmio_req(gpa, &mmio_inst, 0, tmp_dir, 1); 19.528 + return; 19.529 + } 19.530 + 19.531 + if (!strncmp(mmio_inst.i_name, "mov", 3)) { 19.532 + long value = 0; 19.533 + int size, index; 19.534 + 19.535 + if (read_from_mmio(&mmio_inst)) { 19.536 + // Send the request and waiting for return value. 19.537 + mpci_p->mmio_target = mmio_inst.operand[1]; 19.538 + send_mmio_req(gpa, &mmio_inst, value, 1, 0); 19.539 + } else { 19.540 + // Write to MMIO 19.541 + if (mmio_inst.operand[0] & IMMEDIATE) { 19.542 + value = mmio_inst.immediate; 19.543 + } else if (mmio_inst.operand[0] & REGISTER) { 19.544 + size = operand_size(mmio_inst.operand[0]); 19.545 + index = operand_index(mmio_inst.operand[0]); 19.546 + value = get_reg_value(size, index, 0, inst_decoder_regs); 19.547 + } else { 19.548 + domain_crash(); 19.549 + } 19.550 + send_mmio_req(gpa, &mmio_inst, value, 0, 0); 19.551 + return; 19.552 + } 19.553 + domain_crash(); 19.554 + } 19.555 + domain_crash(); 19.556 +} 19.557 +
20.1 --- a/xen/include/asm-x86/shadow.h Thu Jan 27 17:33:33 2005 +0000 20.2 +++ b/xen/include/asm-x86/shadow.h Fri Jan 28 07:59:39 2005 +0000 20.3 @@ -305,10 +305,15 @@ static inline void l1pte_propagate_from_ 20.4 case SHM_full_32: 20.5 { 20.6 unsigned long host_pfn, host_gpte; 20.7 + spte = 0; 20.8 + 20.9 + if (mmio_space(gpte & 0xFFFFF000)) { 20.10 + *spte_p = spte; 20.11 + return; 20.12 + } 20.13 20.14 host_pfn = phys_to_machine_mapping[gpte >> PAGE_SHIFT]; 20.15 host_gpte = (host_pfn << PAGE_SHIFT) | (gpte & ~PAGE_MASK); 20.16 - spte = 0; 20.17 20.18 if ( (host_gpte & (_PAGE_PRESENT|_PAGE_ACCESSED) ) == 20.19 (_PAGE_PRESENT|_PAGE_ACCESSED) ) 20.20 @@ -697,7 +702,7 @@ static inline void __shadow_mk_pagetable 20.21 SH_VVLOG("__shadow_mk_pagetable(guest_gpfn=%08lx, gpfn=%08lx\n", 20.22 guest_gpfn, gpfn); 20.23 20.24 - spfn = __shadow_status(mm, gpfn) & PSH_pfn_mask; 20.25 + spfn = __shadow_status(mm, guest_gpfn) & PSH_pfn_mask; 20.26 if ( unlikely(spfn == 0) ) { 20.27 spfn = shadow_l2_table(mm, gpfn); 20.28 mm->shadow_table = mk_pagetable(spfn<<PAGE_SHIFT);
21.1 --- a/xen/include/asm-x86/vmx_platform.h Thu Jan 27 17:33:33 2005 +0000 21.2 +++ b/xen/include/asm-x86/vmx_platform.h Fri Jan 28 07:59:39 2005 +0000 21.3 @@ -19,6 +19,78 @@ 21.4 #ifndef __ASM_X86_VMX_PLATFORM_H__ 21.5 #define __ASM_X86_VMX_PLATFORM_H__ 21.6 21.7 -#include <asm/e820.h> /* from Linux */ 21.8 +#include <asm/e820.h> /* from Linux */ 21.9 + 21.10 +#define MAX_OPERAND_NUM 3 21.11 +#define I_NAME_LEN 16 21.12 + 21.13 +#define mk_operand(size, index, seg, flag) \ 21.14 + (((size) << 24) | ((index) << 16) | ((seg) << 8) | (flag)) 21.15 + 21.16 +#define operand_size(operand) \ 21.17 + ((operand >> 24) & 0xFF) 21.18 + 21.19 +#define operand_index(operand) \ 21.20 + ((operand >> 16) & 0xFF) 21.21 + //For instruction.operand[].size 21.22 +#define BYTE 1 21.23 +#define WORD 2 21.24 +#define LONG 4 21.25 +#define QUAD 8 21.26 + 21.27 + //For instruction.operand[].flag 21.28 +#define REGISTER 0x1 21.29 +#define MEMORY 0x2 21.30 +#define IMMEDIATE 0x4 21.31 +#define WZEROEXTEND 0x8 21.32 + 21.33 + //For instruction.flags 21.34 +#define REPZ 0x1 21.35 +#define REPNZ 0x2 21.36 + 21.37 +struct instruction { 21.38 + __s8 i_name[I_NAME_LEN]; //Instruction's name 21.39 + __s16 op_size; //The operand's bit size, e.g. 16-bit or 32-bit. 21.40 + 21.41 + __u64 offset; //The effective address 21.42 + //offset = Base + (Index * Scale) + Displacement 21.43 + 21.44 + __u64 immediate; 21.45 + 21.46 + __u16 seg_sel; //Segmentation selector 21.47 + 21.48 + __u32 operand[MAX_OPERAND_NUM]; //The order of operand is from AT&T Assembly 21.49 + __s16 op_num; //The operand numbers 21.50 + 21.51 + __u32 flags; // 21.52 +}; 21.53 + 21.54 +#define VGA_SPACE_START 0xA0000 21.55 +#define VGA_SPACE_END 0xC0000 21.56 +#define MAX_INST_LEN 32 21.57 + 21.58 +struct mi_per_cpu_info 21.59 +{ 21.60 + unsigned long mmio_target; 21.61 + struct xen_regs *inst_decoder_regs; 21.62 +}; 21.63 + 21.64 +struct virutal_platform_def { 21.65 + unsigned long *real_mode_data; /* E820, etc. */ 21.66 + unsigned long shared_page_va; 21.67 + struct mi_per_cpu_info mpci; /* MMIO */ 21.68 +}; 21.69 + 21.70 +extern int mmio_space(unsigned long); 21.71 +extern void handle_mmio(unsigned long, unsigned long, unsigned long); 21.72 +extern int vmx_setup_platform(struct exec_domain *, execution_context_t *); 21.73 + 21.74 +extern inline int mmio_space(unsigned long gpa) 21.75 +{ 21.76 + if (gpa >= VGA_SPACE_START && gpa < VGA_SPACE_END) { 21.77 + return 1; 21.78 + } 21.79 + return 0; 21.80 +} 21.81 21.82 #endif
22.1 --- a/xen/include/asm-x86/vmx_vmcs.h Thu Jan 27 17:33:33 2005 +0000 22.2 +++ b/xen/include/asm-x86/vmx_vmcs.h Fri Jan 28 07:59:39 2005 +0000 22.3 @@ -39,15 +39,7 @@ union vmcs_arbytes { 22.4 unsigned int bytes; 22.5 }; 22.6 22.7 -struct virutal_platform_def { 22.8 - unsigned long *real_mode_data; /* E820, etc. */ 22.9 - unsigned long shared_page_va; 22.10 -}; 22.11 - 22.12 -int vmx_setup_platform(struct exec_domain *, execution_context_t *); 22.13 - 22.14 #define VMX_CPU_STATE_PG_ENABLED 0 22.15 - 22.16 #define VMCS_SIZE 0x1000 22.17 22.18 struct vmcs_struct { 22.19 @@ -62,10 +54,6 @@ struct arch_vmx_struct { 22.20 unsigned long cpu_cr3; 22.21 unsigned long cpu_state; 22.22 struct virutal_platform_def vmx_platform; 22.23 -#if 0 22.24 - /* open */ 22.25 - unsigned long *page_list; /* page list for MMIO */ 22.26 -#endif 22.27 }; 22.28 22.29 #define vmx_schedule_tail(next) \
23.1 --- a/xen/include/public/io/ioreq.h Thu Jan 27 17:33:33 2005 +0000 23.2 +++ b/xen/include/public/io/ioreq.h Fri Jan 28 07:59:39 2005 +0000 23.3 @@ -41,10 +41,11 @@ typedef struct { 23.4 u64 data; /* data */ 23.5 void *pdata; /* pointer to data */ 23.6 } u; 23.7 - u8 state:5; 23.8 + u8 state:4; 23.9 u8 pdata_valid:1; /* if 1, use pdata above */ 23.10 u8 dir:1; /* 1=read, 0=write */ 23.11 u8 port_mm:1; /* 0=portio, 1=mmio */ 23.12 + u8 df:1; 23.13 } ioreq_t; 23.14 23.15 #define MAX_VECTOR 256