diff options
Diffstat (limited to 'arch')
83 files changed, 956 insertions, 782 deletions
diff --git a/arch/arm/kernel/sys_arm.c b/arch/arm/kernel/sys_arm.c index 9bd1870d980e..0128687ba0f7 100644 --- a/arch/arm/kernel/sys_arm.c +++ b/arch/arm/kernel/sys_arm.c | |||
@@ -34,23 +34,6 @@ extern unsigned long do_mremap(unsigned long addr, unsigned long old_len, | |||
34 | unsigned long new_len, unsigned long flags, | 34 | unsigned long new_len, unsigned long flags, |
35 | unsigned long new_addr); | 35 | unsigned long new_addr); |
36 | 36 | ||
37 | /* | ||
38 | * sys_pipe() is the normal C calling standard for creating | ||
39 | * a pipe. It's not the way unix traditionally does this, though. | ||
40 | */ | ||
41 | asmlinkage int sys_pipe(unsigned long __user *fildes) | ||
42 | { | ||
43 | int fd[2]; | ||
44 | int error; | ||
45 | |||
46 | error = do_pipe(fd); | ||
47 | if (!error) { | ||
48 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
49 | error = -EFAULT; | ||
50 | } | ||
51 | return error; | ||
52 | } | ||
53 | |||
54 | /* common code for old and new mmaps */ | 37 | /* common code for old and new mmaps */ |
55 | inline long do_mmap2( | 38 | inline long do_mmap2( |
56 | unsigned long addr, unsigned long len, | 39 | unsigned long addr, unsigned long len, |
diff --git a/arch/arm/mach-orion5x/addr-map.c b/arch/arm/mach-orion5x/addr-map.c index 9608503d67f5..e63fb05dc893 100644 --- a/arch/arm/mach-orion5x/addr-map.c +++ b/arch/arm/mach-orion5x/addr-map.c | |||
@@ -34,11 +34,7 @@ | |||
34 | * Non-CPU Masters address decoding -- | 34 | * Non-CPU Masters address decoding -- |
35 | * Unlike the CPU, we setup the access from Orion's master interfaces to DDR | 35 | * Unlike the CPU, we setup the access from Orion's master interfaces to DDR |
36 | * banks only (the typical use case). | 36 | * banks only (the typical use case). |
37 | * Setup access for each master to DDR is issued by common.c. | 37 | * Setup access for each master to DDR is issued by platform device setup. |
38 | * | ||
39 | * Note: although orion_setbits() and orion_clrbits() are not atomic | ||
40 | * no locking is necessary here since code in this file is only called | ||
41 | * at boot time when there is no concurrency issues. | ||
42 | */ | 38 | */ |
43 | 39 | ||
44 | /* | 40 | /* |
@@ -48,10 +44,6 @@ | |||
48 | #define TARGET_DEV_BUS 1 | 44 | #define TARGET_DEV_BUS 1 |
49 | #define TARGET_PCI 3 | 45 | #define TARGET_PCI 3 |
50 | #define TARGET_PCIE 4 | 46 | #define TARGET_PCIE 4 |
51 | #define ATTR_DDR_CS(n) (((n) ==0) ? 0xe : \ | ||
52 | ((n) == 1) ? 0xd : \ | ||
53 | ((n) == 2) ? 0xb : \ | ||
54 | ((n) == 3) ? 0x7 : 0xf) | ||
55 | #define ATTR_PCIE_MEM 0x59 | 47 | #define ATTR_PCIE_MEM 0x59 |
56 | #define ATTR_PCIE_IO 0x51 | 48 | #define ATTR_PCIE_IO 0x51 |
57 | #define ATTR_PCIE_WA 0x79 | 49 | #define ATTR_PCIE_WA 0x79 |
@@ -61,17 +53,12 @@ | |||
61 | #define ATTR_DEV_CS1 0x1d | 53 | #define ATTR_DEV_CS1 0x1d |
62 | #define ATTR_DEV_CS2 0x1b | 54 | #define ATTR_DEV_CS2 0x1b |
63 | #define ATTR_DEV_BOOT 0xf | 55 | #define ATTR_DEV_BOOT 0xf |
64 | #define WIN_EN 1 | ||
65 | 56 | ||
66 | /* | 57 | /* |
67 | * Helpers to get DDR bank info | 58 | * Helpers to get DDR bank info |
68 | */ | 59 | */ |
69 | #define DDR_BASE_CS(n) ORION5X_DDR_REG(0x1500 + ((n) * 8)) | 60 | #define DDR_BASE_CS(n) ORION5X_DDR_REG(0x1500 + ((n) << 3)) |
70 | #define DDR_SIZE_CS(n) ORION5X_DDR_REG(0x1504 + ((n) * 8)) | 61 | #define DDR_SIZE_CS(n) ORION5X_DDR_REG(0x1504 + ((n) << 3)) |
71 | #define DDR_MAX_CS 4 | ||
72 | #define DDR_REG_TO_SIZE(reg) (((reg) | 0xffffff) + 1) | ||
73 | #define DDR_REG_TO_BASE(reg) ((reg) & 0xff000000) | ||
74 | #define DDR_BANK_EN 1 | ||
75 | 62 | ||
76 | /* | 63 | /* |
77 | * CPU Address Decode Windows registers | 64 | * CPU Address Decode Windows registers |
@@ -81,17 +68,6 @@ | |||
81 | #define CPU_WIN_REMAP_LO(n) ORION5X_BRIDGE_REG(0x008 | ((n) << 4)) | 68 | #define CPU_WIN_REMAP_LO(n) ORION5X_BRIDGE_REG(0x008 | ((n) << 4)) |
82 | #define CPU_WIN_REMAP_HI(n) ORION5X_BRIDGE_REG(0x00c | ((n) << 4)) | 69 | #define CPU_WIN_REMAP_HI(n) ORION5X_BRIDGE_REG(0x00c | ((n) << 4)) |
83 | 70 | ||
84 | /* | ||
85 | * Gigabit Ethernet Address Decode Windows registers | ||
86 | */ | ||
87 | #define ETH_WIN_BASE(win) ORION5X_ETH_REG(0x200 + ((win) * 8)) | ||
88 | #define ETH_WIN_SIZE(win) ORION5X_ETH_REG(0x204 + ((win) * 8)) | ||
89 | #define ETH_WIN_REMAP(win) ORION5X_ETH_REG(0x280 + ((win) * 4)) | ||
90 | #define ETH_WIN_EN ORION5X_ETH_REG(0x290) | ||
91 | #define ETH_WIN_PROT ORION5X_ETH_REG(0x294) | ||
92 | #define ETH_MAX_WIN 6 | ||
93 | #define ETH_MAX_REMAP_WIN 4 | ||
94 | |||
95 | 71 | ||
96 | struct mbus_dram_target_info orion5x_mbus_dram_info; | 72 | struct mbus_dram_target_info orion5x_mbus_dram_info; |
97 | 73 | ||
@@ -202,39 +178,3 @@ void __init orion5x_setup_pcie_wa_win(u32 base, u32 size) | |||
202 | { | 178 | { |
203 | setup_cpu_win(7, base, size, TARGET_PCIE, ATTR_PCIE_WA, -1); | 179 | setup_cpu_win(7, base, size, TARGET_PCIE, ATTR_PCIE_WA, -1); |
204 | } | 180 | } |
205 | |||
206 | void __init orion5x_setup_eth_wins(void) | ||
207 | { | ||
208 | int i; | ||
209 | |||
210 | /* | ||
211 | * First, disable and clear windows | ||
212 | */ | ||
213 | for (i = 0; i < ETH_MAX_WIN; i++) { | ||
214 | orion5x_write(ETH_WIN_BASE(i), 0); | ||
215 | orion5x_write(ETH_WIN_SIZE(i), 0); | ||
216 | orion5x_setbits(ETH_WIN_EN, 1 << i); | ||
217 | orion5x_clrbits(ETH_WIN_PROT, 0x3 << (i * 2)); | ||
218 | if (i < ETH_MAX_REMAP_WIN) | ||
219 | orion5x_write(ETH_WIN_REMAP(i), 0); | ||
220 | } | ||
221 | |||
222 | /* | ||
223 | * Setup windows for DDR banks. | ||
224 | */ | ||
225 | for (i = 0; i < DDR_MAX_CS; i++) { | ||
226 | u32 base, size; | ||
227 | size = orion5x_read(DDR_SIZE_CS(i)); | ||
228 | base = orion5x_read(DDR_BASE_CS(i)); | ||
229 | if (size & DDR_BANK_EN) { | ||
230 | base = DDR_REG_TO_BASE(base); | ||
231 | size = DDR_REG_TO_SIZE(size); | ||
232 | orion5x_write(ETH_WIN_SIZE(i), (size-1) & 0xffff0000); | ||
233 | orion5x_write(ETH_WIN_BASE(i), (base & 0xffff0000) | | ||
234 | (ATTR_DDR_CS(i) << 8) | | ||
235 | TARGET_DDR); | ||
236 | orion5x_clrbits(ETH_WIN_EN, 1 << i); | ||
237 | orion5x_setbits(ETH_WIN_PROT, 0x3 << (i * 2)); | ||
238 | } | ||
239 | } | ||
240 | } | ||
diff --git a/arch/arm/mach-orion5x/common.c b/arch/arm/mach-orion5x/common.c index 968deb58be01..4f13fd037f04 100644 --- a/arch/arm/mach-orion5x/common.c +++ b/arch/arm/mach-orion5x/common.c | |||
@@ -190,6 +190,11 @@ static struct platform_device orion5x_ehci1 = { | |||
190 | * (The Orion and Discovery (MV643xx) families use the same Ethernet driver) | 190 | * (The Orion and Discovery (MV643xx) families use the same Ethernet driver) |
191 | ****************************************************************************/ | 191 | ****************************************************************************/ |
192 | 192 | ||
193 | struct mv643xx_eth_shared_platform_data orion5x_eth_shared_data = { | ||
194 | .dram = &orion5x_mbus_dram_info, | ||
195 | .t_clk = ORION5X_TCLK, | ||
196 | }; | ||
197 | |||
193 | static struct resource orion5x_eth_shared_resources[] = { | 198 | static struct resource orion5x_eth_shared_resources[] = { |
194 | { | 199 | { |
195 | .start = ORION5X_ETH_PHYS_BASE + 0x2000, | 200 | .start = ORION5X_ETH_PHYS_BASE + 0x2000, |
@@ -201,6 +206,9 @@ static struct resource orion5x_eth_shared_resources[] = { | |||
201 | static struct platform_device orion5x_eth_shared = { | 206 | static struct platform_device orion5x_eth_shared = { |
202 | .name = MV643XX_ETH_SHARED_NAME, | 207 | .name = MV643XX_ETH_SHARED_NAME, |
203 | .id = 0, | 208 | .id = 0, |
209 | .dev = { | ||
210 | .platform_data = &orion5x_eth_shared_data, | ||
211 | }, | ||
204 | .num_resources = 1, | 212 | .num_resources = 1, |
205 | .resource = orion5x_eth_shared_resources, | 213 | .resource = orion5x_eth_shared_resources, |
206 | }; | 214 | }; |
@@ -223,7 +231,9 @@ static struct platform_device orion5x_eth = { | |||
223 | 231 | ||
224 | void __init orion5x_eth_init(struct mv643xx_eth_platform_data *eth_data) | 232 | void __init orion5x_eth_init(struct mv643xx_eth_platform_data *eth_data) |
225 | { | 233 | { |
234 | eth_data->shared = &orion5x_eth_shared; | ||
226 | orion5x_eth.dev.platform_data = eth_data; | 235 | orion5x_eth.dev.platform_data = eth_data; |
236 | |||
227 | platform_device_register(&orion5x_eth_shared); | 237 | platform_device_register(&orion5x_eth_shared); |
228 | platform_device_register(&orion5x_eth); | 238 | platform_device_register(&orion5x_eth); |
229 | } | 239 | } |
@@ -360,7 +370,6 @@ void __init orion5x_init(void) | |||
360 | * Setup Orion address map | 370 | * Setup Orion address map |
361 | */ | 371 | */ |
362 | orion5x_setup_cpu_mbus_bridge(); | 372 | orion5x_setup_cpu_mbus_bridge(); |
363 | orion5x_setup_eth_wins(); | ||
364 | 373 | ||
365 | /* | 374 | /* |
366 | * Register devices. | 375 | * Register devices. |
diff --git a/arch/arm/mach-orion5x/common.h b/arch/arm/mach-orion5x/common.h index 14adf8d1a54a..bd0f05de6e18 100644 --- a/arch/arm/mach-orion5x/common.h +++ b/arch/arm/mach-orion5x/common.h | |||
@@ -22,7 +22,6 @@ void orion5x_setup_dev0_win(u32 base, u32 size); | |||
22 | void orion5x_setup_dev1_win(u32 base, u32 size); | 22 | void orion5x_setup_dev1_win(u32 base, u32 size); |
23 | void orion5x_setup_dev2_win(u32 base, u32 size); | 23 | void orion5x_setup_dev2_win(u32 base, u32 size); |
24 | void orion5x_setup_pcie_wa_win(u32 base, u32 size); | 24 | void orion5x_setup_pcie_wa_win(u32 base, u32 size); |
25 | void orion5x_setup_eth_wins(void); | ||
26 | 25 | ||
27 | /* | 26 | /* |
28 | * Shared code used internally by other Orion core functions. | 27 | * Shared code used internally by other Orion core functions. |
diff --git a/arch/avr32/kernel/sys_avr32.c b/arch/avr32/kernel/sys_avr32.c index 8deb6003ee62..8e8911e55c8f 100644 --- a/arch/avr32/kernel/sys_avr32.c +++ b/arch/avr32/kernel/sys_avr32.c | |||
@@ -14,19 +14,6 @@ | |||
14 | #include <asm/mman.h> | 14 | #include <asm/mman.h> |
15 | #include <asm/uaccess.h> | 15 | #include <asm/uaccess.h> |
16 | 16 | ||
17 | asmlinkage int sys_pipe(unsigned long __user *filedes) | ||
18 | { | ||
19 | int fd[2]; | ||
20 | int error; | ||
21 | |||
22 | error = do_pipe(fd); | ||
23 | if (!error) { | ||
24 | if (copy_to_user(filedes, fd, sizeof(fd))) | ||
25 | error = -EFAULT; | ||
26 | } | ||
27 | return error; | ||
28 | } | ||
29 | |||
30 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, | 17 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, |
31 | unsigned long prot, unsigned long flags, | 18 | unsigned long prot, unsigned long flags, |
32 | unsigned long fd, off_t offset) | 19 | unsigned long fd, off_t offset) |
diff --git a/arch/blackfin/kernel/sys_bfin.c b/arch/blackfin/kernel/sys_bfin.c index efb7b25a2633..fce49d7cf001 100644 --- a/arch/blackfin/kernel/sys_bfin.c +++ b/arch/blackfin/kernel/sys_bfin.c | |||
@@ -45,23 +45,6 @@ | |||
45 | #include <asm/cacheflush.h> | 45 | #include <asm/cacheflush.h> |
46 | #include <asm/dma.h> | 46 | #include <asm/dma.h> |
47 | 47 | ||
48 | /* | ||
49 | * sys_pipe() is the normal C calling standard for creating | ||
50 | * a pipe. It's not the way unix traditionally does this, though. | ||
51 | */ | ||
52 | asmlinkage int sys_pipe(unsigned long __user *fildes) | ||
53 | { | ||
54 | int fd[2]; | ||
55 | int error; | ||
56 | |||
57 | error = do_pipe(fd); | ||
58 | if (!error) { | ||
59 | if (copy_to_user(fildes, fd, 2 * sizeof(int))) | ||
60 | error = -EFAULT; | ||
61 | } | ||
62 | return error; | ||
63 | } | ||
64 | |||
65 | /* common code for old and new mmaps */ | 48 | /* common code for old and new mmaps */ |
66 | static inline long | 49 | static inline long |
67 | do_mmap2(unsigned long addr, unsigned long len, | 50 | do_mmap2(unsigned long addr, unsigned long len, |
diff --git a/arch/cris/kernel/sys_cris.c b/arch/cris/kernel/sys_cris.c index 8b9984197edc..d124066e1728 100644 --- a/arch/cris/kernel/sys_cris.c +++ b/arch/cris/kernel/sys_cris.c | |||
@@ -40,8 +40,11 @@ asmlinkage int sys_pipe(unsigned long __user * fildes) | |||
40 | error = do_pipe(fd); | 40 | error = do_pipe(fd); |
41 | unlock_kernel(); | 41 | unlock_kernel(); |
42 | if (!error) { | 42 | if (!error) { |
43 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | 43 | if (copy_to_user(fildes, fd, 2*sizeof(int))) { |
44 | sys_close(fd[0]); | ||
45 | sys_close(fd[1]); | ||
44 | error = -EFAULT; | 46 | error = -EFAULT; |
47 | } | ||
45 | } | 48 | } |
46 | return error; | 49 | return error; |
47 | } | 50 | } |
diff --git a/arch/frv/kernel/sys_frv.c b/arch/frv/kernel/sys_frv.c index 04c6b1677ccf..49b2cf2c38f3 100644 --- a/arch/frv/kernel/sys_frv.c +++ b/arch/frv/kernel/sys_frv.c | |||
@@ -28,23 +28,6 @@ | |||
28 | #include <asm/setup.h> | 28 | #include <asm/setup.h> |
29 | #include <asm/uaccess.h> | 29 | #include <asm/uaccess.h> |
30 | 30 | ||
31 | /* | ||
32 | * sys_pipe() is the normal C calling standard for creating | ||
33 | * a pipe. It's not the way unix traditionally does this, though. | ||
34 | */ | ||
35 | asmlinkage long sys_pipe(unsigned long __user * fildes) | ||
36 | { | ||
37 | int fd[2]; | ||
38 | int error; | ||
39 | |||
40 | error = do_pipe(fd); | ||
41 | if (!error) { | ||
42 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
43 | error = -EFAULT; | ||
44 | } | ||
45 | return error; | ||
46 | } | ||
47 | |||
48 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, | 31 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, |
49 | unsigned long prot, unsigned long flags, | 32 | unsigned long prot, unsigned long flags, |
50 | unsigned long fd, unsigned long pgoff) | 33 | unsigned long fd, unsigned long pgoff) |
diff --git a/arch/h8300/kernel/sys_h8300.c b/arch/h8300/kernel/sys_h8300.c index 00608be6d567..2745656dcc52 100644 --- a/arch/h8300/kernel/sys_h8300.c +++ b/arch/h8300/kernel/sys_h8300.c | |||
@@ -27,23 +27,6 @@ | |||
27 | #include <asm/traps.h> | 27 | #include <asm/traps.h> |
28 | #include <asm/unistd.h> | 28 | #include <asm/unistd.h> |
29 | 29 | ||
30 | /* | ||
31 | * sys_pipe() is the normal C calling standard for creating | ||
32 | * a pipe. It's not the way unix traditionally does this, though. | ||
33 | */ | ||
34 | asmlinkage int sys_pipe(unsigned long * fildes) | ||
35 | { | ||
36 | int fd[2]; | ||
37 | int error; | ||
38 | |||
39 | error = do_pipe(fd); | ||
40 | if (!error) { | ||
41 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
42 | error = -EFAULT; | ||
43 | } | ||
44 | return error; | ||
45 | } | ||
46 | |||
47 | /* common code for old and new mmaps */ | 30 | /* common code for old and new mmaps */ |
48 | static inline long do_mmap2( | 31 | static inline long do_mmap2( |
49 | unsigned long addr, unsigned long len, | 32 | unsigned long addr, unsigned long len, |
diff --git a/arch/m32r/kernel/sys_m32r.c b/arch/m32r/kernel/sys_m32r.c index 6d7a80fdad48..319c79720b8a 100644 --- a/arch/m32r/kernel/sys_m32r.c +++ b/arch/m32r/kernel/sys_m32r.c | |||
@@ -90,8 +90,11 @@ sys_pipe(unsigned long r0, unsigned long r1, unsigned long r2, | |||
90 | 90 | ||
91 | error = do_pipe(fd); | 91 | error = do_pipe(fd); |
92 | if (!error) { | 92 | if (!error) { |
93 | if (copy_to_user((void __user *)r0, fd, 2*sizeof(int))) | 93 | if (copy_to_user((void __user *)r0, fd, 2*sizeof(int))) { |
94 | sys_close(fd[0]); | ||
95 | sys_close(fd[1]); | ||
94 | error = -EFAULT; | 96 | error = -EFAULT; |
97 | } | ||
95 | } | 98 | } |
96 | return error; | 99 | return error; |
97 | } | 100 | } |
diff --git a/arch/m68k/kernel/sys_m68k.c b/arch/m68k/kernel/sys_m68k.c index e892f17ba3fa..7f54efaf60bb 100644 --- a/arch/m68k/kernel/sys_m68k.c +++ b/arch/m68k/kernel/sys_m68k.c | |||
@@ -30,23 +30,6 @@ | |||
30 | #include <asm/page.h> | 30 | #include <asm/page.h> |
31 | #include <asm/unistd.h> | 31 | #include <asm/unistd.h> |
32 | 32 | ||
33 | /* | ||
34 | * sys_pipe() is the normal C calling standard for creating | ||
35 | * a pipe. It's not the way unix traditionally does this, though. | ||
36 | */ | ||
37 | asmlinkage int sys_pipe(unsigned long __user * fildes) | ||
38 | { | ||
39 | int fd[2]; | ||
40 | int error; | ||
41 | |||
42 | error = do_pipe(fd); | ||
43 | if (!error) { | ||
44 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
45 | error = -EFAULT; | ||
46 | } | ||
47 | return error; | ||
48 | } | ||
49 | |||
50 | /* common code for old and new mmaps */ | 33 | /* common code for old and new mmaps */ |
51 | static inline long do_mmap2( | 34 | static inline long do_mmap2( |
52 | unsigned long addr, unsigned long len, | 35 | unsigned long addr, unsigned long len, |
diff --git a/arch/m68k/kernel/traps.c b/arch/m68k/kernel/traps.c index fd4858e2dd63..75b8340b254b 100644 --- a/arch/m68k/kernel/traps.c +++ b/arch/m68k/kernel/traps.c | |||
@@ -468,15 +468,26 @@ static inline void access_error040(struct frame *fp) | |||
468 | * (if do_page_fault didn't fix the mapping, | 468 | * (if do_page_fault didn't fix the mapping, |
469 | * the writeback won't do good) | 469 | * the writeback won't do good) |
470 | */ | 470 | */ |
471 | disable_wb: | ||
471 | #ifdef DEBUG | 472 | #ifdef DEBUG |
472 | printk(".. disabling wb2\n"); | 473 | printk(".. disabling wb2\n"); |
473 | #endif | 474 | #endif |
474 | if (fp->un.fmt7.wb2a == fp->un.fmt7.faddr) | 475 | if (fp->un.fmt7.wb2a == fp->un.fmt7.faddr) |
475 | fp->un.fmt7.wb2s &= ~WBV_040; | 476 | fp->un.fmt7.wb2s &= ~WBV_040; |
477 | if (fp->un.fmt7.wb3a == fp->un.fmt7.faddr) | ||
478 | fp->un.fmt7.wb3s &= ~WBV_040; | ||
476 | } | 479 | } |
477 | } else if (send_fault_sig(&fp->ptregs) > 0) { | 480 | } else { |
478 | printk("68040 access error, ssw=%x\n", ssw); | 481 | /* In case of a bus error we either kill the process or expect |
479 | trap_c(fp); | 482 | * the kernel to catch the fault, which then is also responsible |
483 | * for cleaning up the mess. | ||
484 | */ | ||
485 | current->thread.signo = SIGBUS; | ||
486 | current->thread.faddr = fp->un.fmt7.faddr; | ||
487 | if (send_fault_sig(&fp->ptregs) >= 0) | ||
488 | printk("68040 bus error (ssw=%x, faddr=%lx)\n", ssw, | ||
489 | fp->un.fmt7.faddr); | ||
490 | goto disable_wb; | ||
480 | } | 491 | } |
481 | 492 | ||
482 | do_040writebacks(fp); | 493 | do_040writebacks(fp); |
diff --git a/arch/m68k/mac/config.c b/arch/m68k/mac/config.c index 735a49b4b936..ad3e3bacae39 100644 --- a/arch/m68k/mac/config.c +++ b/arch/m68k/mac/config.c | |||
@@ -48,9 +48,6 @@ | |||
48 | struct mac_booter_data mac_bi_data; | 48 | struct mac_booter_data mac_bi_data; |
49 | int mac_bisize = sizeof mac_bi_data; | 49 | int mac_bisize = sizeof mac_bi_data; |
50 | 50 | ||
51 | struct mac_hw_present mac_hw_present; | ||
52 | EXPORT_SYMBOL(mac_hw_present); | ||
53 | |||
54 | /* New m68k bootinfo stuff and videobase */ | 51 | /* New m68k bootinfo stuff and videobase */ |
55 | 52 | ||
56 | extern int m68k_num_memory; | 53 | extern int m68k_num_memory; |
@@ -817,27 +814,6 @@ void __init mac_identify(void) | |||
817 | m68k_ramdisk.addr, m68k_ramdisk.size); | 814 | m68k_ramdisk.addr, m68k_ramdisk.size); |
818 | #endif | 815 | #endif |
819 | 816 | ||
820 | /* | ||
821 | * TODO: set the various fields in macintosh_config->hw_present here! | ||
822 | */ | ||
823 | switch (macintosh_config->scsi_type) { | ||
824 | case MAC_SCSI_OLD: | ||
825 | MACHW_SET(MAC_SCSI_80); | ||
826 | break; | ||
827 | case MAC_SCSI_QUADRA: | ||
828 | case MAC_SCSI_QUADRA2: | ||
829 | case MAC_SCSI_QUADRA3: | ||
830 | MACHW_SET(MAC_SCSI_96); | ||
831 | if ((macintosh_config->ident == MAC_MODEL_Q900) || | ||
832 | (macintosh_config->ident == MAC_MODEL_Q950)) | ||
833 | MACHW_SET(MAC_SCSI_96_2); | ||
834 | break; | ||
835 | default: | ||
836 | printk(KERN_WARNING "config.c: wtf: unknown scsi, using 53c80\n"); | ||
837 | MACHW_SET(MAC_SCSI_80); | ||
838 | break; | ||
839 | } | ||
840 | |||
841 | iop_init(); | 817 | iop_init(); |
842 | via_init(); | 818 | via_init(); |
843 | oss_init(); | 819 | oss_init(); |
diff --git a/arch/m68knommu/kernel/sys_m68k.c b/arch/m68knommu/kernel/sys_m68k.c index 65f7a95f056e..700281638629 100644 --- a/arch/m68knommu/kernel/sys_m68k.c +++ b/arch/m68knommu/kernel/sys_m68k.c | |||
@@ -28,23 +28,6 @@ | |||
28 | #include <asm/cacheflush.h> | 28 | #include <asm/cacheflush.h> |
29 | #include <asm/unistd.h> | 29 | #include <asm/unistd.h> |
30 | 30 | ||
31 | /* | ||
32 | * sys_pipe() is the normal C calling standard for creating | ||
33 | * a pipe. It's not the way unix traditionally does this, though. | ||
34 | */ | ||
35 | asmlinkage int sys_pipe(unsigned long * fildes) | ||
36 | { | ||
37 | int fd[2]; | ||
38 | int error; | ||
39 | |||
40 | error = do_pipe(fd); | ||
41 | if (!error) { | ||
42 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
43 | error = -EFAULT; | ||
44 | } | ||
45 | return error; | ||
46 | } | ||
47 | |||
48 | /* common code for old and new mmaps */ | 31 | /* common code for old and new mmaps */ |
49 | static inline long do_mmap2( | 32 | static inline long do_mmap2( |
50 | unsigned long addr, unsigned long len, | 33 | unsigned long addr, unsigned long len, |
diff --git a/arch/mn10300/kernel/sys_mn10300.c b/arch/mn10300/kernel/sys_mn10300.c index 5f17a1ebc825..bca5a84dc72c 100644 --- a/arch/mn10300/kernel/sys_mn10300.c +++ b/arch/mn10300/kernel/sys_mn10300.c | |||
@@ -29,23 +29,6 @@ | |||
29 | #define MIN_MAP_ADDR PAGE_SIZE /* minimum fixed mmap address */ | 29 | #define MIN_MAP_ADDR PAGE_SIZE /* minimum fixed mmap address */ |
30 | 30 | ||
31 | /* | 31 | /* |
32 | * sys_pipe() is the normal C calling standard for creating | ||
33 | * a pipe. It's not the way Unix traditionally does this, though. | ||
34 | */ | ||
35 | asmlinkage long sys_pipe(unsigned long __user *fildes) | ||
36 | { | ||
37 | int fd[2]; | ||
38 | int error; | ||
39 | |||
40 | error = do_pipe(fd); | ||
41 | if (!error) { | ||
42 | if (copy_to_user(fildes, fd, 2 * sizeof(int))) | ||
43 | error = -EFAULT; | ||
44 | } | ||
45 | return error; | ||
46 | } | ||
47 | |||
48 | /* | ||
49 | * memory mapping syscall | 32 | * memory mapping syscall |
50 | */ | 33 | */ |
51 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, | 34 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, |
diff --git a/arch/parisc/kernel/sys_parisc.c b/arch/parisc/kernel/sys_parisc.c index 4f589216b39e..71b31957c8f1 100644 --- a/arch/parisc/kernel/sys_parisc.c +++ b/arch/parisc/kernel/sys_parisc.c | |||
@@ -33,19 +33,6 @@ | |||
33 | #include <linux/utsname.h> | 33 | #include <linux/utsname.h> |
34 | #include <linux/personality.h> | 34 | #include <linux/personality.h> |
35 | 35 | ||
36 | int sys_pipe(int __user *fildes) | ||
37 | { | ||
38 | int fd[2]; | ||
39 | int error; | ||
40 | |||
41 | error = do_pipe(fd); | ||
42 | if (!error) { | ||
43 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
44 | error = -EFAULT; | ||
45 | } | ||
46 | return error; | ||
47 | } | ||
48 | |||
49 | static unsigned long get_unshared_area(unsigned long addr, unsigned long len) | 36 | static unsigned long get_unshared_area(unsigned long addr, unsigned long len) |
50 | { | 37 | { |
51 | struct vm_area_struct *vma; | 38 | struct vm_area_struct *vma; |
diff --git a/arch/powerpc/kernel/syscalls.c b/arch/powerpc/kernel/syscalls.c index e722a4eeb5d0..4fe69ca24481 100644 --- a/arch/powerpc/kernel/syscalls.c +++ b/arch/powerpc/kernel/syscalls.c | |||
@@ -136,23 +136,6 @@ int sys_ipc(uint call, int first, unsigned long second, long third, | |||
136 | return ret; | 136 | return ret; |
137 | } | 137 | } |
138 | 138 | ||
139 | /* | ||
140 | * sys_pipe() is the normal C calling standard for creating | ||
141 | * a pipe. It's not the way unix traditionally does this, though. | ||
142 | */ | ||
143 | int sys_pipe(int __user *fildes) | ||
144 | { | ||
145 | int fd[2]; | ||
146 | int error; | ||
147 | |||
148 | error = do_pipe(fd); | ||
149 | if (!error) { | ||
150 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
151 | error = -EFAULT; | ||
152 | } | ||
153 | return error; | ||
154 | } | ||
155 | |||
156 | static inline unsigned long do_mmap2(unsigned long addr, size_t len, | 139 | static inline unsigned long do_mmap2(unsigned long addr, size_t len, |
157 | unsigned long prot, unsigned long flags, | 140 | unsigned long prot, unsigned long flags, |
158 | unsigned long fd, unsigned long off, int shift) | 141 | unsigned long fd, unsigned long off, int shift) |
diff --git a/arch/powerpc/kvm/booke_guest.c b/arch/powerpc/kvm/booke_guest.c index 6d9884a6884a..712d89a28c46 100644 --- a/arch/powerpc/kvm/booke_guest.c +++ b/arch/powerpc/kvm/booke_guest.c | |||
@@ -49,6 +49,7 @@ struct kvm_stats_debugfs_item debugfs_entries[] = { | |||
49 | { "inst_emu", VCPU_STAT(emulated_inst_exits) }, | 49 | { "inst_emu", VCPU_STAT(emulated_inst_exits) }, |
50 | { "dec", VCPU_STAT(dec_exits) }, | 50 | { "dec", VCPU_STAT(dec_exits) }, |
51 | { "ext_intr", VCPU_STAT(ext_intr_exits) }, | 51 | { "ext_intr", VCPU_STAT(ext_intr_exits) }, |
52 | { "halt_wakeup", VCPU_STAT(halt_wakeup) }, | ||
52 | { NULL } | 53 | { NULL } |
53 | }; | 54 | }; |
54 | 55 | ||
@@ -338,6 +339,11 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, | |||
338 | } | 339 | } |
339 | break; | 340 | break; |
340 | 341 | ||
342 | case BOOKE_INTERRUPT_FP_UNAVAIL: | ||
343 | kvmppc_queue_exception(vcpu, exit_nr); | ||
344 | r = RESUME_GUEST; | ||
345 | break; | ||
346 | |||
341 | case BOOKE_INTERRUPT_DATA_STORAGE: | 347 | case BOOKE_INTERRUPT_DATA_STORAGE: |
342 | vcpu->arch.dear = vcpu->arch.fault_dear; | 348 | vcpu->arch.dear = vcpu->arch.fault_dear; |
343 | vcpu->arch.esr = vcpu->arch.fault_esr; | 349 | vcpu->arch.esr = vcpu->arch.fault_esr; |
diff --git a/arch/powerpc/kvm/powerpc.c b/arch/powerpc/kvm/powerpc.c index bad40bd2d3ac..777e0f34e0ea 100644 --- a/arch/powerpc/kvm/powerpc.c +++ b/arch/powerpc/kvm/powerpc.c | |||
@@ -36,13 +36,12 @@ gfn_t unalias_gfn(struct kvm *kvm, gfn_t gfn) | |||
36 | 36 | ||
37 | int kvm_cpu_has_interrupt(struct kvm_vcpu *v) | 37 | int kvm_cpu_has_interrupt(struct kvm_vcpu *v) |
38 | { | 38 | { |
39 | /* XXX implement me */ | 39 | return !!(v->arch.pending_exceptions); |
40 | return 0; | ||
41 | } | 40 | } |
42 | 41 | ||
43 | int kvm_arch_vcpu_runnable(struct kvm_vcpu *v) | 42 | int kvm_arch_vcpu_runnable(struct kvm_vcpu *v) |
44 | { | 43 | { |
45 | return 1; | 44 | return !(v->arch.msr & MSR_WE); |
46 | } | 45 | } |
47 | 46 | ||
48 | 47 | ||
@@ -214,6 +213,11 @@ static void kvmppc_decrementer_func(unsigned long data) | |||
214 | struct kvm_vcpu *vcpu = (struct kvm_vcpu *)data; | 213 | struct kvm_vcpu *vcpu = (struct kvm_vcpu *)data; |
215 | 214 | ||
216 | kvmppc_queue_exception(vcpu, BOOKE_INTERRUPT_DECREMENTER); | 215 | kvmppc_queue_exception(vcpu, BOOKE_INTERRUPT_DECREMENTER); |
216 | |||
217 | if (waitqueue_active(&vcpu->wq)) { | ||
218 | wake_up_interruptible(&vcpu->wq); | ||
219 | vcpu->stat.halt_wakeup++; | ||
220 | } | ||
217 | } | 221 | } |
218 | 222 | ||
219 | int kvm_arch_vcpu_init(struct kvm_vcpu *vcpu) | 223 | int kvm_arch_vcpu_init(struct kvm_vcpu *vcpu) |
@@ -339,6 +343,8 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu, struct kvm_run *run) | |||
339 | int r; | 343 | int r; |
340 | sigset_t sigsaved; | 344 | sigset_t sigsaved; |
341 | 345 | ||
346 | vcpu_load(vcpu); | ||
347 | |||
342 | if (vcpu->sigset_active) | 348 | if (vcpu->sigset_active) |
343 | sigprocmask(SIG_SETMASK, &vcpu->sigset, &sigsaved); | 349 | sigprocmask(SIG_SETMASK, &vcpu->sigset, &sigsaved); |
344 | 350 | ||
@@ -363,12 +369,20 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu, struct kvm_run *run) | |||
363 | if (vcpu->sigset_active) | 369 | if (vcpu->sigset_active) |
364 | sigprocmask(SIG_SETMASK, &sigsaved, NULL); | 370 | sigprocmask(SIG_SETMASK, &sigsaved, NULL); |
365 | 371 | ||
372 | vcpu_put(vcpu); | ||
373 | |||
366 | return r; | 374 | return r; |
367 | } | 375 | } |
368 | 376 | ||
369 | int kvm_vcpu_ioctl_interrupt(struct kvm_vcpu *vcpu, struct kvm_interrupt *irq) | 377 | int kvm_vcpu_ioctl_interrupt(struct kvm_vcpu *vcpu, struct kvm_interrupt *irq) |
370 | { | 378 | { |
371 | kvmppc_queue_exception(vcpu, BOOKE_INTERRUPT_EXTERNAL); | 379 | kvmppc_queue_exception(vcpu, BOOKE_INTERRUPT_EXTERNAL); |
380 | |||
381 | if (waitqueue_active(&vcpu->wq)) { | ||
382 | wake_up_interruptible(&vcpu->wq); | ||
383 | vcpu->stat.halt_wakeup++; | ||
384 | } | ||
385 | |||
372 | return 0; | 386 | return 0; |
373 | } | 387 | } |
374 | 388 | ||
diff --git a/arch/powerpc/lib/Makefile b/arch/powerpc/lib/Makefile index 4bb023f4c869..f1d2cdc5331b 100644 --- a/arch/powerpc/lib/Makefile +++ b/arch/powerpc/lib/Makefile | |||
@@ -23,3 +23,4 @@ obj-$(CONFIG_SMP) += locks.o | |||
23 | endif | 23 | endif |
24 | 24 | ||
25 | obj-$(CONFIG_PPC_LIB_RHEAP) += rheap.o | 25 | obj-$(CONFIG_PPC_LIB_RHEAP) += rheap.o |
26 | obj-$(CONFIG_HAS_IOMEM) += devres.o | ||
diff --git a/arch/powerpc/lib/devres.c b/arch/powerpc/lib/devres.c new file mode 100644 index 000000000000..292115d98ea9 --- /dev/null +++ b/arch/powerpc/lib/devres.c | |||
@@ -0,0 +1,42 @@ | |||
1 | /* | ||
2 | * Copyright (C) 2008 Freescale Semiconductor, Inc. | ||
3 | * | ||
4 | * This program is free software; you can redistribute it and/or | ||
5 | * modify it under the terms of the GNU General Public License | ||
6 | * as published by the Free Software Foundation; either version | ||
7 | * 2 of the License, or (at your option) any later version. | ||
8 | */ | ||
9 | |||
10 | #include <linux/device.h> /* devres_*(), devm_ioremap_release() */ | ||
11 | #include <linux/io.h> /* ioremap_flags() */ | ||
12 | #include <linux/module.h> /* EXPORT_SYMBOL() */ | ||
13 | |||
14 | /** | ||
15 | * devm_ioremap_prot - Managed ioremap_flags() | ||
16 | * @dev: Generic device to remap IO address for | ||
17 | * @offset: BUS offset to map | ||
18 | * @size: Size of map | ||
19 | * @flags: Page flags | ||
20 | * | ||
21 | * Managed ioremap_prot(). Map is automatically unmapped on driver | ||
22 | * detach. | ||
23 | */ | ||
24 | void __iomem *devm_ioremap_prot(struct device *dev, resource_size_t offset, | ||
25 | size_t size, unsigned long flags) | ||
26 | { | ||
27 | void __iomem **ptr, *addr; | ||
28 | |||
29 | ptr = devres_alloc(devm_ioremap_release, sizeof(*ptr), GFP_KERNEL); | ||
30 | if (!ptr) | ||
31 | return NULL; | ||
32 | |||
33 | addr = ioremap_flags(offset, size, flags); | ||
34 | if (addr) { | ||
35 | *ptr = addr; | ||
36 | devres_add(dev, ptr); | ||
37 | } else | ||
38 | devres_free(ptr); | ||
39 | |||
40 | return addr; | ||
41 | } | ||
42 | EXPORT_SYMBOL(devm_ioremap_prot); | ||
diff --git a/arch/powerpc/platforms/chrp/pegasos_eth.c b/arch/powerpc/platforms/chrp/pegasos_eth.c index 5bcc58d9a4dd..130ff72d99dd 100644 --- a/arch/powerpc/platforms/chrp/pegasos_eth.c +++ b/arch/powerpc/platforms/chrp/pegasos_eth.c | |||
@@ -58,7 +58,9 @@ static struct resource mv643xx_eth0_resources[] = { | |||
58 | 58 | ||
59 | 59 | ||
60 | static struct mv643xx_eth_platform_data eth0_pd = { | 60 | static struct mv643xx_eth_platform_data eth0_pd = { |
61 | .shared = &mv643xx_eth_shared_device, | ||
61 | .port_number = 0, | 62 | .port_number = 0, |
63 | |||
62 | .tx_sram_addr = PEGASOS2_SRAM_BASE_ETH0, | 64 | .tx_sram_addr = PEGASOS2_SRAM_BASE_ETH0, |
63 | .tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE, | 65 | .tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE, |
64 | .tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16, | 66 | .tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16, |
@@ -88,7 +90,9 @@ static struct resource mv643xx_eth1_resources[] = { | |||
88 | }; | 90 | }; |
89 | 91 | ||
90 | static struct mv643xx_eth_platform_data eth1_pd = { | 92 | static struct mv643xx_eth_platform_data eth1_pd = { |
93 | .shared = &mv643xx_eth_shared_device, | ||
91 | .port_number = 1, | 94 | .port_number = 1, |
95 | |||
92 | .tx_sram_addr = PEGASOS2_SRAM_BASE_ETH1, | 96 | .tx_sram_addr = PEGASOS2_SRAM_BASE_ETH1, |
93 | .tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE, | 97 | .tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE, |
94 | .tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16, | 98 | .tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16, |
diff --git a/arch/powerpc/platforms/pseries/scanlog.c b/arch/powerpc/platforms/pseries/scanlog.c index bec3803f0618..417eca79df69 100644 --- a/arch/powerpc/platforms/pseries/scanlog.c +++ b/arch/powerpc/platforms/pseries/scanlog.c | |||
@@ -55,11 +55,6 @@ static ssize_t scanlog_read(struct file *file, char __user *buf, | |||
55 | dp = PDE(inode); | 55 | dp = PDE(inode); |
56 | data = (unsigned int *)dp->data; | 56 | data = (unsigned int *)dp->data; |
57 | 57 | ||
58 | if (!data) { | ||
59 | printk(KERN_ERR "scanlog: read failed no data\n"); | ||
60 | return -EIO; | ||
61 | } | ||
62 | |||
63 | if (count > RTAS_DATA_BUF_SIZE) | 58 | if (count > RTAS_DATA_BUF_SIZE) |
64 | count = RTAS_DATA_BUF_SIZE; | 59 | count = RTAS_DATA_BUF_SIZE; |
65 | 60 | ||
@@ -146,11 +141,6 @@ static int scanlog_open(struct inode * inode, struct file * file) | |||
146 | struct proc_dir_entry *dp = PDE(inode); | 141 | struct proc_dir_entry *dp = PDE(inode); |
147 | unsigned int *data = (unsigned int *)dp->data; | 142 | unsigned int *data = (unsigned int *)dp->data; |
148 | 143 | ||
149 | if (!data) { | ||
150 | printk(KERN_ERR "scanlog: open failed no data\n"); | ||
151 | return -EIO; | ||
152 | } | ||
153 | |||
154 | if (data[0] != 0) { | 144 | if (data[0] != 0) { |
155 | /* This imperfect test stops a second copy of the | 145 | /* This imperfect test stops a second copy of the |
156 | * data (or a reset while data is being copied) | 146 | * data (or a reset while data is being copied) |
@@ -168,10 +158,6 @@ static int scanlog_release(struct inode * inode, struct file * file) | |||
168 | struct proc_dir_entry *dp = PDE(inode); | 158 | struct proc_dir_entry *dp = PDE(inode); |
169 | unsigned int *data = (unsigned int *)dp->data; | 159 | unsigned int *data = (unsigned int *)dp->data; |
170 | 160 | ||
171 | if (!data) { | ||
172 | printk(KERN_ERR "scanlog: release failed no data\n"); | ||
173 | return -EIO; | ||
174 | } | ||
175 | data[0] = 0; | 161 | data[0] = 0; |
176 | 162 | ||
177 | return 0; | 163 | return 0; |
@@ -200,12 +186,11 @@ static int __init scanlog_init(void) | |||
200 | if (!data) | 186 | if (!data) |
201 | goto err; | 187 | goto err; |
202 | 188 | ||
203 | ent = proc_create("ppc64/rtas/scan-log-dump", S_IRUSR, NULL, | 189 | ent = proc_create_data("ppc64/rtas/scan-log-dump", S_IRUSR, NULL, |
204 | &scanlog_fops); | 190 | &scanlog_fops, data); |
205 | if (!ent) | 191 | if (!ent) |
206 | goto err; | 192 | goto err; |
207 | 193 | ||
208 | ent->data = data; | ||
209 | proc_ppc64_scan_log_dump = ent; | 194 | proc_ppc64_scan_log_dump = ent; |
210 | 195 | ||
211 | return 0; | 196 | return 0; |
diff --git a/arch/powerpc/sysdev/mv64x60_dev.c b/arch/powerpc/sysdev/mv64x60_dev.c index 41af1223e2a0..a132e0de8ca5 100644 --- a/arch/powerpc/sysdev/mv64x60_dev.c +++ b/arch/powerpc/sysdev/mv64x60_dev.c | |||
@@ -239,6 +239,8 @@ static int __init mv64x60_eth_device_setup(struct device_node *np, int id, | |||
239 | 239 | ||
240 | memset(&pdata, 0, sizeof(pdata)); | 240 | memset(&pdata, 0, sizeof(pdata)); |
241 | 241 | ||
242 | pdata.shared = shared_pdev; | ||
243 | |||
242 | prop = of_get_property(np, "reg", NULL); | 244 | prop = of_get_property(np, "reg", NULL); |
243 | if (!prop) | 245 | if (!prop) |
244 | return -ENODEV; | 246 | return -ENODEV; |
diff --git a/arch/ppc/syslib/mv64x60.c b/arch/ppc/syslib/mv64x60.c index 90fe904d3614..418f3053de52 100644 --- a/arch/ppc/syslib/mv64x60.c +++ b/arch/ppc/syslib/mv64x60.c | |||
@@ -341,6 +341,7 @@ static struct resource mv64x60_eth0_resources[] = { | |||
341 | }; | 341 | }; |
342 | 342 | ||
343 | static struct mv643xx_eth_platform_data eth0_pd = { | 343 | static struct mv643xx_eth_platform_data eth0_pd = { |
344 | .shared = &mv64x60_eth_shared_device; | ||
344 | .port_number = 0, | 345 | .port_number = 0, |
345 | }; | 346 | }; |
346 | 347 | ||
@@ -366,6 +367,7 @@ static struct resource mv64x60_eth1_resources[] = { | |||
366 | }; | 367 | }; |
367 | 368 | ||
368 | static struct mv643xx_eth_platform_data eth1_pd = { | 369 | static struct mv643xx_eth_platform_data eth1_pd = { |
370 | .shared = &mv64x60_eth_shared_device; | ||
369 | .port_number = 1, | 371 | .port_number = 1, |
370 | }; | 372 | }; |
371 | 373 | ||
@@ -391,6 +393,7 @@ static struct resource mv64x60_eth2_resources[] = { | |||
391 | }; | 393 | }; |
392 | 394 | ||
393 | static struct mv643xx_eth_platform_data eth2_pd = { | 395 | static struct mv643xx_eth_platform_data eth2_pd = { |
396 | .shared = &mv64x60_eth_shared_device; | ||
394 | .port_number = 2, | 397 | .port_number = 2, |
395 | }; | 398 | }; |
396 | 399 | ||
diff --git a/arch/s390/Kconfig b/arch/s390/Kconfig index 29a7940f284f..1d035082e78e 100644 --- a/arch/s390/Kconfig +++ b/arch/s390/Kconfig | |||
@@ -430,6 +430,13 @@ config CMM_IUCV | |||
430 | Select this option to enable the special message interface to | 430 | Select this option to enable the special message interface to |
431 | the cooperative memory management. | 431 | the cooperative memory management. |
432 | 432 | ||
433 | config PAGE_STATES | ||
434 | bool "Unused page notification" | ||
435 | help | ||
436 | This enables the notification of unused pages to the | ||
437 | hypervisor. The ESSA instruction is used to do the states | ||
438 | changes between a page that has content and the unused state. | ||
439 | |||
433 | config VIRT_TIMER | 440 | config VIRT_TIMER |
434 | bool "Virtual CPU timer support" | 441 | bool "Virtual CPU timer support" |
435 | help | 442 | help |
diff --git a/arch/s390/kernel/compat_wrapper.S b/arch/s390/kernel/compat_wrapper.S index 743d54f0b8db..d003a6e16afb 100644 --- a/arch/s390/kernel/compat_wrapper.S +++ b/arch/s390/kernel/compat_wrapper.S | |||
@@ -121,7 +121,7 @@ sys32_ptrace_wrapper: | |||
121 | lgfr %r3,%r3 # long | 121 | lgfr %r3,%r3 # long |
122 | llgtr %r4,%r4 # long | 122 | llgtr %r4,%r4 # long |
123 | llgfr %r5,%r5 # long | 123 | llgfr %r5,%r5 # long |
124 | jg sys_ptrace # branch to system call | 124 | jg compat_sys_ptrace # branch to system call |
125 | 125 | ||
126 | .globl sys32_alarm_wrapper | 126 | .globl sys32_alarm_wrapper |
127 | sys32_alarm_wrapper: | 127 | sys32_alarm_wrapper: |
diff --git a/arch/s390/kernel/entry.S b/arch/s390/kernel/entry.S index bdbb3bcd78a5..708cf9cf9a35 100644 --- a/arch/s390/kernel/entry.S +++ b/arch/s390/kernel/entry.S | |||
@@ -279,8 +279,6 @@ sysc_do_restart: | |||
279 | st %r2,SP_R2(%r15) # store return value (change R2 on stack) | 279 | st %r2,SP_R2(%r15) # store return value (change R2 on stack) |
280 | 280 | ||
281 | sysc_return: | 281 | sysc_return: |
282 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
283 | bno BASED(sysc_restore) | ||
284 | tm __TI_flags+3(%r9),_TIF_WORK_SVC | 282 | tm __TI_flags+3(%r9),_TIF_WORK_SVC |
285 | bnz BASED(sysc_work) # there is work to do (signals etc.) | 283 | bnz BASED(sysc_work) # there is work to do (signals etc.) |
286 | sysc_restore: | 284 | sysc_restore: |
@@ -312,6 +310,8 @@ sysc_work_loop: | |||
312 | # One of the work bits is on. Find out which one. | 310 | # One of the work bits is on. Find out which one. |
313 | # | 311 | # |
314 | sysc_work: | 312 | sysc_work: |
313 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
314 | bno BASED(sysc_restore) | ||
315 | tm __TI_flags+3(%r9),_TIF_MCCK_PENDING | 315 | tm __TI_flags+3(%r9),_TIF_MCCK_PENDING |
316 | bo BASED(sysc_mcck_pending) | 316 | bo BASED(sysc_mcck_pending) |
317 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED | 317 | tm __TI_flags+3(%r9),_TIF_NEED_RESCHED |
@@ -602,12 +602,6 @@ io_no_vtime: | |||
602 | la %r2,SP_PTREGS(%r15) # address of register-save area | 602 | la %r2,SP_PTREGS(%r15) # address of register-save area |
603 | basr %r14,%r1 # branch to standard irq handler | 603 | basr %r14,%r1 # branch to standard irq handler |
604 | io_return: | 604 | io_return: |
605 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
606 | #ifdef CONFIG_PREEMPT | ||
607 | bno BASED(io_preempt) # no -> check for preemptive scheduling | ||
608 | #else | ||
609 | bno BASED(io_restore) # no-> skip resched & signal | ||
610 | #endif | ||
611 | tm __TI_flags+3(%r9),_TIF_WORK_INT | 605 | tm __TI_flags+3(%r9),_TIF_WORK_INT |
612 | bnz BASED(io_work) # there is work to do (signals etc.) | 606 | bnz BASED(io_work) # there is work to do (signals etc.) |
613 | io_restore: | 607 | io_restore: |
@@ -629,10 +623,18 @@ io_restore_trace_psw: | |||
629 | .long 0, io_restore_trace + 0x80000000 | 623 | .long 0, io_restore_trace + 0x80000000 |
630 | #endif | 624 | #endif |
631 | 625 | ||
632 | #ifdef CONFIG_PREEMPT | 626 | # |
633 | io_preempt: | 627 | # switch to kernel stack, then check the TIF bits |
628 | # | ||
629 | io_work: | ||
630 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
631 | #ifndef CONFIG_PREEMPT | ||
632 | bno BASED(io_restore) # no-> skip resched & signal | ||
633 | #else | ||
634 | bnz BASED(io_work_user) # no -> check for preemptive scheduling | ||
635 | # check for preemptive scheduling | ||
634 | icm %r0,15,__TI_precount(%r9) | 636 | icm %r0,15,__TI_precount(%r9) |
635 | bnz BASED(io_restore) | 637 | bnz BASED(io_restore) # preemption disabled |
636 | l %r1,SP_R15(%r15) | 638 | l %r1,SP_R15(%r15) |
637 | s %r1,BASED(.Lc_spsize) | 639 | s %r1,BASED(.Lc_spsize) |
638 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) | 640 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) |
@@ -646,10 +648,7 @@ io_resume_loop: | |||
646 | br %r1 # call schedule | 648 | br %r1 # call schedule |
647 | #endif | 649 | #endif |
648 | 650 | ||
649 | # | 651 | io_work_user: |
650 | # switch to kernel stack, then check the TIF bits | ||
651 | # | ||
652 | io_work: | ||
653 | l %r1,__LC_KERNEL_STACK | 652 | l %r1,__LC_KERNEL_STACK |
654 | s %r1,BASED(.Lc_spsize) | 653 | s %r1,BASED(.Lc_spsize) |
655 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) | 654 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) |
diff --git a/arch/s390/kernel/entry64.S b/arch/s390/kernel/entry64.S index 5a4a7bcd2bba..fee10177dbfc 100644 --- a/arch/s390/kernel/entry64.S +++ b/arch/s390/kernel/entry64.S | |||
@@ -271,8 +271,6 @@ sysc_noemu: | |||
271 | stg %r2,SP_R2(%r15) # store return value (change R2 on stack) | 271 | stg %r2,SP_R2(%r15) # store return value (change R2 on stack) |
272 | 272 | ||
273 | sysc_return: | 273 | sysc_return: |
274 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
275 | jno sysc_restore | ||
276 | tm __TI_flags+7(%r9),_TIF_WORK_SVC | 274 | tm __TI_flags+7(%r9),_TIF_WORK_SVC |
277 | jnz sysc_work # there is work to do (signals etc.) | 275 | jnz sysc_work # there is work to do (signals etc.) |
278 | sysc_restore: | 276 | sysc_restore: |
@@ -304,6 +302,8 @@ sysc_work_loop: | |||
304 | # One of the work bits is on. Find out which one. | 302 | # One of the work bits is on. Find out which one. |
305 | # | 303 | # |
306 | sysc_work: | 304 | sysc_work: |
305 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
306 | jno sysc_restore | ||
307 | tm __TI_flags+7(%r9),_TIF_MCCK_PENDING | 307 | tm __TI_flags+7(%r9),_TIF_MCCK_PENDING |
308 | jo sysc_mcck_pending | 308 | jo sysc_mcck_pending |
309 | tm __TI_flags+7(%r9),_TIF_NEED_RESCHED | 309 | tm __TI_flags+7(%r9),_TIF_NEED_RESCHED |
@@ -585,12 +585,6 @@ io_no_vtime: | |||
585 | la %r2,SP_PTREGS(%r15) # address of register-save area | 585 | la %r2,SP_PTREGS(%r15) # address of register-save area |
586 | brasl %r14,do_IRQ # call standard irq handler | 586 | brasl %r14,do_IRQ # call standard irq handler |
587 | io_return: | 587 | io_return: |
588 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
589 | #ifdef CONFIG_PREEMPT | ||
590 | jno io_preempt # no -> check for preemptive scheduling | ||
591 | #else | ||
592 | jno io_restore # no-> skip resched & signal | ||
593 | #endif | ||
594 | tm __TI_flags+7(%r9),_TIF_WORK_INT | 588 | tm __TI_flags+7(%r9),_TIF_WORK_INT |
595 | jnz io_work # there is work to do (signals etc.) | 589 | jnz io_work # there is work to do (signals etc.) |
596 | io_restore: | 590 | io_restore: |
@@ -612,10 +606,41 @@ io_restore_trace_psw: | |||
612 | .quad 0, io_restore_trace | 606 | .quad 0, io_restore_trace |
613 | #endif | 607 | #endif |
614 | 608 | ||
615 | #ifdef CONFIG_PREEMPT | 609 | # |
616 | io_preempt: | 610 | # There is work todo, we need to check if we return to userspace, then |
611 | # check, if we are in SIE, if yes leave it | ||
612 | # | ||
613 | io_work: | ||
614 | tm SP_PSW+1(%r15),0x01 # returning to user ? | ||
615 | #ifndef CONFIG_PREEMPT | ||
616 | #if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) | ||
617 | jnz io_work_user # yes -> no need to check for SIE | ||
618 | la %r1, BASED(sie_opcode) # we return to kernel here | ||
619 | lg %r2, SP_PSW+8(%r15) | ||
620 | clc 0(2,%r1), 0(%r2) # is current instruction = SIE? | ||
621 | jne io_restore # no-> return to kernel | ||
622 | lg %r1, SP_PSW+8(%r15) # yes-> add 4 bytes to leave SIE | ||
623 | aghi %r1, 4 | ||
624 | stg %r1, SP_PSW+8(%r15) | ||
625 | j io_restore # return to kernel | ||
626 | #else | ||
627 | jno io_restore # no-> skip resched & signal | ||
628 | #endif | ||
629 | #else | ||
630 | jnz io_work_user # yes -> do resched & signal | ||
631 | #if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) | ||
632 | la %r1, BASED(sie_opcode) | ||
633 | lg %r2, SP_PSW+8(%r15) | ||
634 | clc 0(2,%r1), 0(%r2) # is current instruction = SIE? | ||
635 | jne 0f # no -> leave PSW alone | ||
636 | lg %r1, SP_PSW+8(%r15) # yes-> add 4 bytes to leave SIE | ||
637 | aghi %r1, 4 | ||
638 | stg %r1, SP_PSW+8(%r15) | ||
639 | 0: | ||
640 | #endif | ||
641 | # check for preemptive scheduling | ||
617 | icm %r0,15,__TI_precount(%r9) | 642 | icm %r0,15,__TI_precount(%r9) |
618 | jnz io_restore | 643 | jnz io_restore # preemption is disabled |
619 | # switch to kernel stack | 644 | # switch to kernel stack |
620 | lg %r1,SP_R15(%r15) | 645 | lg %r1,SP_R15(%r15) |
621 | aghi %r1,-SP_SIZE | 646 | aghi %r1,-SP_SIZE |
@@ -629,10 +654,7 @@ io_resume_loop: | |||
629 | jg preempt_schedule_irq | 654 | jg preempt_schedule_irq |
630 | #endif | 655 | #endif |
631 | 656 | ||
632 | # | 657 | io_work_user: |
633 | # switch to kernel stack, then check TIF bits | ||
634 | # | ||
635 | io_work: | ||
636 | lg %r1,__LC_KERNEL_STACK | 658 | lg %r1,__LC_KERNEL_STACK |
637 | aghi %r1,-SP_SIZE | 659 | aghi %r1,-SP_SIZE |
638 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) | 660 | mvc SP_PTREGS(__PT_SIZE,%r1),SP_PTREGS(%r15) |
@@ -653,6 +675,11 @@ io_work_loop: | |||
653 | j io_restore | 675 | j io_restore |
654 | io_work_done: | 676 | io_work_done: |
655 | 677 | ||
678 | #if defined(CONFIG_KVM) || defined(CONFIG_KVM_MODULE) | ||
679 | sie_opcode: | ||
680 | .long 0xb2140000 | ||
681 | #endif | ||
682 | |||
656 | # | 683 | # |
657 | # _TIF_MCCK_PENDING is set, call handler | 684 | # _TIF_MCCK_PENDING is set, call handler |
658 | # | 685 | # |
diff --git a/arch/s390/kernel/ptrace.c b/arch/s390/kernel/ptrace.c index 7f4270163744..35827b9bd4d1 100644 --- a/arch/s390/kernel/ptrace.c +++ b/arch/s390/kernel/ptrace.c | |||
@@ -292,8 +292,7 @@ poke_user(struct task_struct *child, addr_t addr, addr_t data) | |||
292 | return 0; | 292 | return 0; |
293 | } | 293 | } |
294 | 294 | ||
295 | static int | 295 | long arch_ptrace(struct task_struct *child, long request, long addr, long data) |
296 | do_ptrace_normal(struct task_struct *child, long request, long addr, long data) | ||
297 | { | 296 | { |
298 | ptrace_area parea; | 297 | ptrace_area parea; |
299 | int copied, ret; | 298 | int copied, ret; |
@@ -529,35 +528,19 @@ poke_user_emu31(struct task_struct *child, addr_t addr, addr_t data) | |||
529 | return 0; | 528 | return 0; |
530 | } | 529 | } |
531 | 530 | ||
532 | static int | 531 | long compat_arch_ptrace(struct task_struct *child, compat_long_t request, |
533 | do_ptrace_emu31(struct task_struct *child, long request, long addr, long data) | 532 | compat_ulong_t caddr, compat_ulong_t cdata) |
534 | { | 533 | { |
535 | unsigned int tmp; /* 4 bytes !! */ | 534 | unsigned long addr = caddr; |
535 | unsigned long data = cdata; | ||
536 | ptrace_area_emu31 parea; | 536 | ptrace_area_emu31 parea; |
537 | int copied, ret; | 537 | int copied, ret; |
538 | 538 | ||
539 | switch (request) { | 539 | switch (request) { |
540 | case PTRACE_PEEKTEXT: | ||
541 | case PTRACE_PEEKDATA: | ||
542 | /* read word at location addr. */ | ||
543 | copied = access_process_vm(child, addr, &tmp, sizeof(tmp), 0); | ||
544 | if (copied != sizeof(tmp)) | ||
545 | return -EIO; | ||
546 | return put_user(tmp, (unsigned int __force __user *) data); | ||
547 | |||
548 | case PTRACE_PEEKUSR: | 540 | case PTRACE_PEEKUSR: |
549 | /* read the word at location addr in the USER area. */ | 541 | /* read the word at location addr in the USER area. */ |
550 | return peek_user_emu31(child, addr, data); | 542 | return peek_user_emu31(child, addr, data); |
551 | 543 | ||
552 | case PTRACE_POKETEXT: | ||
553 | case PTRACE_POKEDATA: | ||
554 | /* write the word at location addr. */ | ||
555 | tmp = data; | ||
556 | copied = access_process_vm(child, addr, &tmp, sizeof(tmp), 1); | ||
557 | if (copied != sizeof(tmp)) | ||
558 | return -EIO; | ||
559 | return 0; | ||
560 | |||
561 | case PTRACE_POKEUSR: | 544 | case PTRACE_POKEUSR: |
562 | /* write the word at location addr in the USER area */ | 545 | /* write the word at location addr in the USER area */ |
563 | return poke_user_emu31(child, addr, data); | 546 | return poke_user_emu31(child, addr, data); |
@@ -587,82 +570,11 @@ do_ptrace_emu31(struct task_struct *child, long request, long addr, long data) | |||
587 | copied += sizeof(unsigned int); | 570 | copied += sizeof(unsigned int); |
588 | } | 571 | } |
589 | return 0; | 572 | return 0; |
590 | case PTRACE_GETEVENTMSG: | ||
591 | return put_user((__u32) child->ptrace_message, | ||
592 | (unsigned int __force __user *) data); | ||
593 | case PTRACE_GETSIGINFO: | ||
594 | if (child->last_siginfo == NULL) | ||
595 | return -EINVAL; | ||
596 | return copy_siginfo_to_user32((compat_siginfo_t | ||
597 | __force __user *) data, | ||
598 | child->last_siginfo); | ||
599 | case PTRACE_SETSIGINFO: | ||
600 | if (child->last_siginfo == NULL) | ||
601 | return -EINVAL; | ||
602 | return copy_siginfo_from_user32(child->last_siginfo, | ||
603 | (compat_siginfo_t | ||
604 | __force __user *) data); | ||
605 | } | 573 | } |
606 | return ptrace_request(child, request, addr, data); | 574 | return compat_ptrace_request(child, request, addr, data); |
607 | } | 575 | } |
608 | #endif | 576 | #endif |
609 | 577 | ||
610 | long arch_ptrace(struct task_struct *child, long request, long addr, long data) | ||
611 | { | ||
612 | switch (request) { | ||
613 | case PTRACE_SYSCALL: | ||
614 | /* continue and stop at next (return from) syscall */ | ||
615 | case PTRACE_CONT: | ||
616 | /* restart after signal. */ | ||
617 | if (!valid_signal(data)) | ||
618 | return -EIO; | ||
619 | if (request == PTRACE_SYSCALL) | ||
620 | set_tsk_thread_flag(child, TIF_SYSCALL_TRACE); | ||
621 | else | ||
622 | clear_tsk_thread_flag(child, TIF_SYSCALL_TRACE); | ||
623 | child->exit_code = data; | ||
624 | /* make sure the single step bit is not set. */ | ||
625 | user_disable_single_step(child); | ||
626 | wake_up_process(child); | ||
627 | return 0; | ||
628 | |||
629 | case PTRACE_KILL: | ||
630 | /* | ||
631 | * make the child exit. Best I can do is send it a sigkill. | ||
632 | * perhaps it should be put in the status that it wants to | ||
633 | * exit. | ||
634 | */ | ||
635 | if (child->exit_state == EXIT_ZOMBIE) /* already dead */ | ||
636 | return 0; | ||
637 | child->exit_code = SIGKILL; | ||
638 | /* make sure the single step bit is not set. */ | ||
639 | user_disable_single_step(child); | ||
640 | wake_up_process(child); | ||
641 | return 0; | ||
642 | |||
643 | case PTRACE_SINGLESTEP: | ||
644 | /* set the trap flag. */ | ||
645 | if (!valid_signal(data)) | ||
646 | return -EIO; | ||
647 | clear_tsk_thread_flag(child, TIF_SYSCALL_TRACE); | ||
648 | child->exit_code = data; | ||
649 | user_enable_single_step(child); | ||
650 | /* give it a chance to run. */ | ||
651 | wake_up_process(child); | ||
652 | return 0; | ||
653 | |||
654 | /* Do requests that differ for 31/64 bit */ | ||
655 | default: | ||
656 | #ifdef CONFIG_COMPAT | ||
657 | if (test_thread_flag(TIF_31BIT)) | ||
658 | return do_ptrace_emu31(child, request, addr, data); | ||
659 | #endif | ||
660 | return do_ptrace_normal(child, request, addr, data); | ||
661 | } | ||
662 | /* Not reached. */ | ||
663 | return -EIO; | ||
664 | } | ||
665 | |||
666 | asmlinkage void | 578 | asmlinkage void |
667 | syscall_trace(struct pt_regs *regs, int entryexit) | 579 | syscall_trace(struct pt_regs *regs, int entryexit) |
668 | { | 580 | { |
diff --git a/arch/s390/kernel/sys_s390.c b/arch/s390/kernel/sys_s390.c index 988d0d64c2c8..5fdb799062b7 100644 --- a/arch/s390/kernel/sys_s390.c +++ b/arch/s390/kernel/sys_s390.c | |||
@@ -32,23 +32,6 @@ | |||
32 | #include <asm/uaccess.h> | 32 | #include <asm/uaccess.h> |
33 | #include "entry.h" | 33 | #include "entry.h" |
34 | 34 | ||
35 | /* | ||
36 | * sys_pipe() is the normal C calling standard for creating | ||
37 | * a pipe. It's not the way Unix traditionally does this, though. | ||
38 | */ | ||
39 | asmlinkage long sys_pipe(unsigned long __user *fildes) | ||
40 | { | ||
41 | int fd[2]; | ||
42 | int error; | ||
43 | |||
44 | error = do_pipe(fd); | ||
45 | if (!error) { | ||
46 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
47 | error = -EFAULT; | ||
48 | } | ||
49 | return error; | ||
50 | } | ||
51 | |||
52 | /* common code for old and new mmaps */ | 35 | /* common code for old and new mmaps */ |
53 | static inline long do_mmap2( | 36 | static inline long do_mmap2( |
54 | unsigned long addr, unsigned long len, | 37 | unsigned long addr, unsigned long len, |
diff --git a/arch/s390/kvm/Kconfig b/arch/s390/kvm/Kconfig index 1761b74d639b..e051cad1f1e0 100644 --- a/arch/s390/kvm/Kconfig +++ b/arch/s390/kvm/Kconfig | |||
@@ -22,7 +22,6 @@ config KVM | |||
22 | select PREEMPT_NOTIFIERS | 22 | select PREEMPT_NOTIFIERS |
23 | select ANON_INODES | 23 | select ANON_INODES |
24 | select S390_SWITCH_AMODE | 24 | select S390_SWITCH_AMODE |
25 | select PREEMPT | ||
26 | ---help--- | 25 | ---help--- |
27 | Support hosting paravirtualized guest machines using the SIE | 26 | Support hosting paravirtualized guest machines using the SIE |
28 | virtualization capability on the mainframe. This should work | 27 | virtualization capability on the mainframe. This should work |
diff --git a/arch/s390/kvm/intercept.c b/arch/s390/kvm/intercept.c index 349581a26103..47a0b642174c 100644 --- a/arch/s390/kvm/intercept.c +++ b/arch/s390/kvm/intercept.c | |||
@@ -105,6 +105,9 @@ static intercept_handler_t instruction_handlers[256] = { | |||
105 | static int handle_noop(struct kvm_vcpu *vcpu) | 105 | static int handle_noop(struct kvm_vcpu *vcpu) |
106 | { | 106 | { |
107 | switch (vcpu->arch.sie_block->icptcode) { | 107 | switch (vcpu->arch.sie_block->icptcode) { |
108 | case 0x0: | ||
109 | vcpu->stat.exit_null++; | ||
110 | break; | ||
108 | case 0x10: | 111 | case 0x10: |
109 | vcpu->stat.exit_external_request++; | 112 | vcpu->stat.exit_external_request++; |
110 | break; | 113 | break; |
diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c index 98d1e73e01f1..0ac36a649eba 100644 --- a/arch/s390/kvm/kvm-s390.c +++ b/arch/s390/kvm/kvm-s390.c | |||
@@ -31,6 +31,7 @@ | |||
31 | 31 | ||
32 | struct kvm_stats_debugfs_item debugfs_entries[] = { | 32 | struct kvm_stats_debugfs_item debugfs_entries[] = { |
33 | { "userspace_handled", VCPU_STAT(exit_userspace) }, | 33 | { "userspace_handled", VCPU_STAT(exit_userspace) }, |
34 | { "exit_null", VCPU_STAT(exit_null) }, | ||
34 | { "exit_validity", VCPU_STAT(exit_validity) }, | 35 | { "exit_validity", VCPU_STAT(exit_validity) }, |
35 | { "exit_stop_request", VCPU_STAT(exit_stop_request) }, | 36 | { "exit_stop_request", VCPU_STAT(exit_stop_request) }, |
36 | { "exit_external_request", VCPU_STAT(exit_external_request) }, | 37 | { "exit_external_request", VCPU_STAT(exit_external_request) }, |
@@ -221,10 +222,6 @@ void kvm_arch_vcpu_load(struct kvm_vcpu *vcpu, int cpu) | |||
221 | vcpu->arch.guest_fpregs.fpc &= FPC_VALID_MASK; | 222 | vcpu->arch.guest_fpregs.fpc &= FPC_VALID_MASK; |
222 | restore_fp_regs(&vcpu->arch.guest_fpregs); | 223 | restore_fp_regs(&vcpu->arch.guest_fpregs); |
223 | restore_access_regs(vcpu->arch.guest_acrs); | 224 | restore_access_regs(vcpu->arch.guest_acrs); |
224 | |||
225 | if (signal_pending(current)) | ||
226 | atomic_set_mask(CPUSTAT_STOP_INT, | ||
227 | &vcpu->arch.sie_block->cpuflags); | ||
228 | } | 225 | } |
229 | 226 | ||
230 | void kvm_arch_vcpu_put(struct kvm_vcpu *vcpu) | 227 | void kvm_arch_vcpu_put(struct kvm_vcpu *vcpu) |
diff --git a/arch/s390/mm/Makefile b/arch/s390/mm/Makefile index fb988a48a754..2a7458134544 100644 --- a/arch/s390/mm/Makefile +++ b/arch/s390/mm/Makefile | |||
@@ -5,3 +5,4 @@ | |||
5 | obj-y := init.o fault.o extmem.o mmap.o vmem.o pgtable.o | 5 | obj-y := init.o fault.o extmem.o mmap.o vmem.o pgtable.o |
6 | obj-$(CONFIG_CMM) += cmm.o | 6 | obj-$(CONFIG_CMM) += cmm.o |
7 | obj-$(CONFIG_HUGETLB_PAGE) += hugetlbpage.o | 7 | obj-$(CONFIG_HUGETLB_PAGE) += hugetlbpage.o |
8 | obj-$(CONFIG_PAGE_STATES) += page-states.o | ||
diff --git a/arch/s390/mm/init.c b/arch/s390/mm/init.c index fa31de6ae97a..29f3a63806b9 100644 --- a/arch/s390/mm/init.c +++ b/arch/s390/mm/init.c | |||
@@ -126,6 +126,9 @@ void __init mem_init(void) | |||
126 | /* clear the zero-page */ | 126 | /* clear the zero-page */ |
127 | memset(empty_zero_page, 0, PAGE_SIZE); | 127 | memset(empty_zero_page, 0, PAGE_SIZE); |
128 | 128 | ||
129 | /* Setup guest page hinting */ | ||
130 | cmma_init(); | ||
131 | |||
129 | /* this will put all low memory onto the freelists */ | 132 | /* this will put all low memory onto the freelists */ |
130 | totalram_pages += free_all_bootmem(); | 133 | totalram_pages += free_all_bootmem(); |
131 | 134 | ||
diff --git a/arch/s390/mm/page-states.c b/arch/s390/mm/page-states.c new file mode 100644 index 000000000000..fc0ad73ffd90 --- /dev/null +++ b/arch/s390/mm/page-states.c | |||
@@ -0,0 +1,79 @@ | |||
1 | /* | ||
2 | * arch/s390/mm/page-states.c | ||
3 | * | ||
4 | * Copyright IBM Corp. 2008 | ||
5 | * | ||
6 | * Guest page hinting for unused pages. | ||
7 | * | ||
8 | * Author(s): Martin Schwidefsky <schwidefsky@de.ibm.com> | ||
9 | */ | ||
10 | |||
11 | #include <linux/kernel.h> | ||
12 | #include <linux/errno.h> | ||
13 | #include <linux/types.h> | ||
14 | #include <linux/mm.h> | ||
15 | #include <linux/init.h> | ||
16 | |||
17 | #define ESSA_SET_STABLE 1 | ||
18 | #define ESSA_SET_UNUSED 2 | ||
19 | |||
20 | static int cmma_flag; | ||
21 | |||
22 | static int __init cmma(char *str) | ||
23 | { | ||
24 | char *parm; | ||
25 | parm = strstrip(str); | ||
26 | if (strcmp(parm, "yes") == 0 || strcmp(parm, "on") == 0) { | ||
27 | cmma_flag = 1; | ||
28 | return 1; | ||
29 | } | ||
30 | cmma_flag = 0; | ||
31 | if (strcmp(parm, "no") == 0 || strcmp(parm, "off") == 0) | ||
32 | return 1; | ||
33 | return 0; | ||
34 | } | ||
35 | |||
36 | __setup("cmma=", cmma); | ||
37 | |||
38 | void __init cmma_init(void) | ||
39 | { | ||
40 | register unsigned long tmp asm("0") = 0; | ||
41 | register int rc asm("1") = -EOPNOTSUPP; | ||
42 | |||
43 | if (!cmma_flag) | ||
44 | return; | ||
45 | asm volatile( | ||
46 | " .insn rrf,0xb9ab0000,%1,%1,0,0\n" | ||
47 | "0: la %0,0\n" | ||
48 | "1:\n" | ||
49 | EX_TABLE(0b,1b) | ||
50 | : "+&d" (rc), "+&d" (tmp)); | ||
51 | if (rc) | ||
52 | cmma_flag = 0; | ||
53 | } | ||
54 | |||
55 | void arch_free_page(struct page *page, int order) | ||
56 | { | ||
57 | int i, rc; | ||
58 | |||
59 | if (!cmma_flag) | ||
60 | return; | ||
61 | for (i = 0; i < (1 << order); i++) | ||
62 | asm volatile(".insn rrf,0xb9ab0000,%0,%1,%2,0" | ||
63 | : "=&d" (rc) | ||
64 | : "a" ((page_to_pfn(page) + i) << PAGE_SHIFT), | ||
65 | "i" (ESSA_SET_UNUSED)); | ||
66 | } | ||
67 | |||
68 | void arch_alloc_page(struct page *page, int order) | ||
69 | { | ||
70 | int i, rc; | ||
71 | |||
72 | if (!cmma_flag) | ||
73 | return; | ||
74 | for (i = 0; i < (1 << order); i++) | ||
75 | asm volatile(".insn rrf,0xb9ab0000,%0,%1,%2,0" | ||
76 | : "=&d" (rc) | ||
77 | : "a" ((page_to_pfn(page) + i) << PAGE_SHIFT), | ||
78 | "i" (ESSA_SET_STABLE)); | ||
79 | } | ||
diff --git a/arch/sh/kernel/sys_sh64.c b/arch/sh/kernel/sys_sh64.c index 578004d71e02..91fb8445a5a0 100644 --- a/arch/sh/kernel/sys_sh64.c +++ b/arch/sh/kernel/sys_sh64.c | |||
@@ -31,23 +31,6 @@ | |||
31 | #include <asm/unistd.h> | 31 | #include <asm/unistd.h> |
32 | 32 | ||
33 | /* | 33 | /* |
34 | * sys_pipe() is the normal C calling standard for creating | ||
35 | * a pipe. It's not the way Unix traditionally does this, though. | ||
36 | */ | ||
37 | asmlinkage int sys_pipe(unsigned long * fildes) | ||
38 | { | ||
39 | int fd[2]; | ||
40 | int error; | ||
41 | |||
42 | error = do_pipe(fd); | ||
43 | if (!error) { | ||
44 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
45 | error = -EFAULT; | ||
46 | } | ||
47 | return error; | ||
48 | } | ||
49 | |||
50 | /* | ||
51 | * Do a system call from kernel instead of calling sys_execve so we | 34 | * Do a system call from kernel instead of calling sys_execve so we |
52 | * end up with proper pt_regs. | 35 | * end up with proper pt_regs. |
53 | */ | 36 | */ |
diff --git a/arch/sparc/kernel/process.c b/arch/sparc/kernel/process.c index e7f35198ae34..36431f377dee 100644 --- a/arch/sparc/kernel/process.c +++ b/arch/sparc/kernel/process.c | |||
@@ -419,14 +419,26 @@ asmlinkage int sparc_do_fork(unsigned long clone_flags, | |||
419 | unsigned long stack_size) | 419 | unsigned long stack_size) |
420 | { | 420 | { |
421 | unsigned long parent_tid_ptr, child_tid_ptr; | 421 | unsigned long parent_tid_ptr, child_tid_ptr; |
422 | unsigned long orig_i1 = regs->u_regs[UREG_I1]; | ||
423 | long ret; | ||
422 | 424 | ||
423 | parent_tid_ptr = regs->u_regs[UREG_I2]; | 425 | parent_tid_ptr = regs->u_regs[UREG_I2]; |
424 | child_tid_ptr = regs->u_regs[UREG_I4]; | 426 | child_tid_ptr = regs->u_regs[UREG_I4]; |
425 | 427 | ||
426 | return do_fork(clone_flags, stack_start, | 428 | ret = do_fork(clone_flags, stack_start, |
427 | regs, stack_size, | 429 | regs, stack_size, |
428 | (int __user *) parent_tid_ptr, | 430 | (int __user *) parent_tid_ptr, |
429 | (int __user *) child_tid_ptr); | 431 | (int __user *) child_tid_ptr); |
432 | |||
433 | /* If we get an error and potentially restart the system | ||
434 | * call, we're screwed because copy_thread() clobbered | ||
435 | * the parent's %o1. So detect that case and restore it | ||
436 | * here. | ||
437 | */ | ||
438 | if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK) | ||
439 | regs->u_regs[UREG_I1] = orig_i1; | ||
440 | |||
441 | return ret; | ||
430 | } | 442 | } |
431 | 443 | ||
432 | /* Copy a Sparc thread. The fork() return value conventions | 444 | /* Copy a Sparc thread. The fork() return value conventions |
diff --git a/arch/sparc/kernel/signal.c b/arch/sparc/kernel/signal.c index 3c312290c3c2..368157926d24 100644 --- a/arch/sparc/kernel/signal.c +++ b/arch/sparc/kernel/signal.c | |||
@@ -245,15 +245,29 @@ static inline int invalid_frame_pointer(void __user *fp, int fplen) | |||
245 | 245 | ||
246 | static inline void __user *get_sigframe(struct sigaction *sa, struct pt_regs *regs, unsigned long framesize) | 246 | static inline void __user *get_sigframe(struct sigaction *sa, struct pt_regs *regs, unsigned long framesize) |
247 | { | 247 | { |
248 | unsigned long sp; | 248 | unsigned long sp = regs->u_regs[UREG_FP]; |
249 | 249 | ||
250 | sp = regs->u_regs[UREG_FP]; | 250 | /* |
251 | * If we are on the alternate signal stack and would overflow it, don't. | ||
252 | * Return an always-bogus address instead so we will die with SIGSEGV. | ||
253 | */ | ||
254 | if (on_sig_stack(sp) && !likely(on_sig_stack(sp - framesize))) | ||
255 | return (void __user *) -1L; | ||
251 | 256 | ||
252 | /* This is the X/Open sanctioned signal stack switching. */ | 257 | /* This is the X/Open sanctioned signal stack switching. */ |
253 | if (sa->sa_flags & SA_ONSTACK) { | 258 | if (sa->sa_flags & SA_ONSTACK) { |
254 | if (!on_sig_stack(sp) && !((current->sas_ss_sp + current->sas_ss_size) & 7)) | 259 | if (sas_ss_flags(sp) == 0) |
255 | sp = current->sas_ss_sp + current->sas_ss_size; | 260 | sp = current->sas_ss_sp + current->sas_ss_size; |
256 | } | 261 | } |
262 | |||
263 | /* Always align the stack frame. This handles two cases. First, | ||
264 | * sigaltstack need not be mindful of platform specific stack | ||
265 | * alignment. Second, if we took this signal because the stack | ||
266 | * is not aligned properly, we'd like to take the signal cleanly | ||
267 | * and report that. | ||
268 | */ | ||
269 | sp &= ~7UL; | ||
270 | |||
257 | return (void __user *)(sp - framesize); | 271 | return (void __user *)(sp - framesize); |
258 | } | 272 | } |
259 | 273 | ||
diff --git a/arch/sparc/kernel/sys_sparc.c b/arch/sparc/kernel/sys_sparc.c index f188b5dc9fd0..e995491c4436 100644 --- a/arch/sparc/kernel/sys_sparc.c +++ b/arch/sparc/kernel/sys_sparc.c | |||
@@ -223,8 +223,7 @@ int sparc_mmap_check(unsigned long addr, unsigned long len, unsigned long flags) | |||
223 | { | 223 | { |
224 | if (ARCH_SUN4C_SUN4 && | 224 | if (ARCH_SUN4C_SUN4 && |
225 | (len > 0x20000000 || | 225 | (len > 0x20000000 || |
226 | ((flags & MAP_FIXED) && | 226 | (addr < 0xe0000000 && addr + len > 0x20000000))) |
227 | addr < 0xe0000000 && addr + len > 0x20000000))) | ||
228 | return -EINVAL; | 227 | return -EINVAL; |
229 | 228 | ||
230 | /* See asm-sparc/uaccess.h */ | 229 | /* See asm-sparc/uaccess.h */ |
diff --git a/arch/sparc64/kernel/process.c b/arch/sparc64/kernel/process.c index 500ac6d483a0..4129c0449856 100644 --- a/arch/sparc64/kernel/process.c +++ b/arch/sparc64/kernel/process.c | |||
@@ -503,6 +503,8 @@ asmlinkage long sparc_do_fork(unsigned long clone_flags, | |||
503 | unsigned long stack_size) | 503 | unsigned long stack_size) |
504 | { | 504 | { |
505 | int __user *parent_tid_ptr, *child_tid_ptr; | 505 | int __user *parent_tid_ptr, *child_tid_ptr; |
506 | unsigned long orig_i1 = regs->u_regs[UREG_I1]; | ||
507 | long ret; | ||
506 | 508 | ||
507 | #ifdef CONFIG_COMPAT | 509 | #ifdef CONFIG_COMPAT |
508 | if (test_thread_flag(TIF_32BIT)) { | 510 | if (test_thread_flag(TIF_32BIT)) { |
@@ -515,9 +517,19 @@ asmlinkage long sparc_do_fork(unsigned long clone_flags, | |||
515 | child_tid_ptr = (int __user *) regs->u_regs[UREG_I4]; | 517 | child_tid_ptr = (int __user *) regs->u_regs[UREG_I4]; |
516 | } | 518 | } |
517 | 519 | ||
518 | return do_fork(clone_flags, stack_start, | 520 | ret = do_fork(clone_flags, stack_start, |
519 | regs, stack_size, | 521 | regs, stack_size, |
520 | parent_tid_ptr, child_tid_ptr); | 522 | parent_tid_ptr, child_tid_ptr); |
523 | |||
524 | /* If we get an error and potentially restart the system | ||
525 | * call, we're screwed because copy_thread() clobbered | ||
526 | * the parent's %o1. So detect that case and restore it | ||
527 | * here. | ||
528 | */ | ||
529 | if ((unsigned long)ret >= -ERESTART_RESTARTBLOCK) | ||
530 | regs->u_regs[UREG_I1] = orig_i1; | ||
531 | |||
532 | return ret; | ||
521 | } | 533 | } |
522 | 534 | ||
523 | /* Copy a Sparc thread. The fork() return value conventions | 535 | /* Copy a Sparc thread. The fork() return value conventions |
diff --git a/arch/sparc64/kernel/signal.c b/arch/sparc64/kernel/signal.c index 45d6bf632daa..07c0443ea3f5 100644 --- a/arch/sparc64/kernel/signal.c +++ b/arch/sparc64/kernel/signal.c | |||
@@ -376,16 +376,29 @@ save_fpu_state(struct pt_regs *regs, __siginfo_fpu_t __user *fpu) | |||
376 | 376 | ||
377 | static inline void __user *get_sigframe(struct k_sigaction *ka, struct pt_regs *regs, unsigned long framesize) | 377 | static inline void __user *get_sigframe(struct k_sigaction *ka, struct pt_regs *regs, unsigned long framesize) |
378 | { | 378 | { |
379 | unsigned long sp; | 379 | unsigned long sp = regs->u_regs[UREG_FP] + STACK_BIAS; |
380 | 380 | ||
381 | sp = regs->u_regs[UREG_FP] + STACK_BIAS; | 381 | /* |
382 | * If we are on the alternate signal stack and would overflow it, don't. | ||
383 | * Return an always-bogus address instead so we will die with SIGSEGV. | ||
384 | */ | ||
385 | if (on_sig_stack(sp) && !likely(on_sig_stack(sp - framesize))) | ||
386 | return (void __user *) -1L; | ||
382 | 387 | ||
383 | /* This is the X/Open sanctioned signal stack switching. */ | 388 | /* This is the X/Open sanctioned signal stack switching. */ |
384 | if (ka->sa.sa_flags & SA_ONSTACK) { | 389 | if (ka->sa.sa_flags & SA_ONSTACK) { |
385 | if (!on_sig_stack(sp) && | 390 | if (sas_ss_flags(sp) == 0) |
386 | !((current->sas_ss_sp + current->sas_ss_size) & 7)) | ||
387 | sp = current->sas_ss_sp + current->sas_ss_size; | 391 | sp = current->sas_ss_sp + current->sas_ss_size; |
388 | } | 392 | } |
393 | |||
394 | /* Always align the stack frame. This handles two cases. First, | ||
395 | * sigaltstack need not be mindful of platform specific stack | ||
396 | * alignment. Second, if we took this signal because the stack | ||
397 | * is not aligned properly, we'd like to take the signal cleanly | ||
398 | * and report that. | ||
399 | */ | ||
400 | sp &= ~7UL; | ||
401 | |||
389 | return (void __user *)(sp - framesize); | 402 | return (void __user *)(sp - framesize); |
390 | } | 403 | } |
391 | 404 | ||
diff --git a/arch/sparc64/kernel/signal32.c b/arch/sparc64/kernel/signal32.c index 9415d2c918c5..0f6b7b156efd 100644 --- a/arch/sparc64/kernel/signal32.c +++ b/arch/sparc64/kernel/signal32.c | |||
@@ -406,11 +406,27 @@ static void __user *get_sigframe(struct sigaction *sa, struct pt_regs *regs, uns | |||
406 | regs->u_regs[UREG_FP] &= 0x00000000ffffffffUL; | 406 | regs->u_regs[UREG_FP] &= 0x00000000ffffffffUL; |
407 | sp = regs->u_regs[UREG_FP]; | 407 | sp = regs->u_regs[UREG_FP]; |
408 | 408 | ||
409 | /* | ||
410 | * If we are on the alternate signal stack and would overflow it, don't. | ||
411 | * Return an always-bogus address instead so we will die with SIGSEGV. | ||
412 | */ | ||
413 | if (on_sig_stack(sp) && !likely(on_sig_stack(sp - framesize))) | ||
414 | return (void __user *) -1L; | ||
415 | |||
409 | /* This is the X/Open sanctioned signal stack switching. */ | 416 | /* This is the X/Open sanctioned signal stack switching. */ |
410 | if (sa->sa_flags & SA_ONSTACK) { | 417 | if (sa->sa_flags & SA_ONSTACK) { |
411 | if (!on_sig_stack(sp) && !((current->sas_ss_sp + current->sas_ss_size) & 7)) | 418 | if (sas_ss_flags(sp) == 0) |
412 | sp = current->sas_ss_sp + current->sas_ss_size; | 419 | sp = current->sas_ss_sp + current->sas_ss_size; |
413 | } | 420 | } |
421 | |||
422 | /* Always align the stack frame. This handles two cases. First, | ||
423 | * sigaltstack need not be mindful of platform specific stack | ||
424 | * alignment. Second, if we took this signal because the stack | ||
425 | * is not aligned properly, we'd like to take the signal cleanly | ||
426 | * and report that. | ||
427 | */ | ||
428 | sp &= ~7UL; | ||
429 | |||
414 | return (void __user *)(sp - framesize); | 430 | return (void __user *)(sp - framesize); |
415 | } | 431 | } |
416 | 432 | ||
diff --git a/arch/sparc64/kernel/smp.c b/arch/sparc64/kernel/smp.c index 3aba47624df4..0d6403a630ac 100644 --- a/arch/sparc64/kernel/smp.c +++ b/arch/sparc64/kernel/smp.c | |||
@@ -865,21 +865,14 @@ void smp_call_function_client(int irq, struct pt_regs *regs) | |||
865 | void *info = call_data->info; | 865 | void *info = call_data->info; |
866 | 866 | ||
867 | clear_softint(1 << irq); | 867 | clear_softint(1 << irq); |
868 | |||
869 | irq_enter(); | ||
870 | |||
871 | if (!call_data->wait) { | ||
872 | /* let initiator proceed after getting data */ | ||
873 | atomic_inc(&call_data->finished); | ||
874 | } | ||
875 | |||
876 | func(info); | ||
877 | |||
878 | irq_exit(); | ||
879 | |||
880 | if (call_data->wait) { | 868 | if (call_data->wait) { |
881 | /* let initiator proceed only after completion */ | 869 | /* let initiator proceed only after completion */ |
870 | func(info); | ||
882 | atomic_inc(&call_data->finished); | 871 | atomic_inc(&call_data->finished); |
872 | } else { | ||
873 | /* let initiator proceed after getting data */ | ||
874 | atomic_inc(&call_data->finished); | ||
875 | func(info); | ||
883 | } | 876 | } |
884 | } | 877 | } |
885 | 878 | ||
@@ -1041,9 +1034,7 @@ void smp_receive_signal(int cpu) | |||
1041 | 1034 | ||
1042 | void smp_receive_signal_client(int irq, struct pt_regs *regs) | 1035 | void smp_receive_signal_client(int irq, struct pt_regs *regs) |
1043 | { | 1036 | { |
1044 | irq_enter(); | ||
1045 | clear_softint(1 << irq); | 1037 | clear_softint(1 << irq); |
1046 | irq_exit(); | ||
1047 | } | 1038 | } |
1048 | 1039 | ||
1049 | void smp_new_mmu_context_version_client(int irq, struct pt_regs *regs) | 1040 | void smp_new_mmu_context_version_client(int irq, struct pt_regs *regs) |
@@ -1051,8 +1042,6 @@ void smp_new_mmu_context_version_client(int irq, struct pt_regs *regs) | |||
1051 | struct mm_struct *mm; | 1042 | struct mm_struct *mm; |
1052 | unsigned long flags; | 1043 | unsigned long flags; |
1053 | 1044 | ||
1054 | irq_enter(); | ||
1055 | |||
1056 | clear_softint(1 << irq); | 1045 | clear_softint(1 << irq); |
1057 | 1046 | ||
1058 | /* See if we need to allocate a new TLB context because | 1047 | /* See if we need to allocate a new TLB context because |
@@ -1072,8 +1061,6 @@ void smp_new_mmu_context_version_client(int irq, struct pt_regs *regs) | |||
1072 | load_secondary_context(mm); | 1061 | load_secondary_context(mm); |
1073 | __flush_tlb_mm(CTX_HWBITS(mm->context), | 1062 | __flush_tlb_mm(CTX_HWBITS(mm->context), |
1074 | SECONDARY_CONTEXT); | 1063 | SECONDARY_CONTEXT); |
1075 | |||
1076 | irq_exit(); | ||
1077 | } | 1064 | } |
1078 | 1065 | ||
1079 | void smp_new_mmu_context_version(void) | 1066 | void smp_new_mmu_context_version(void) |
@@ -1239,8 +1226,6 @@ void smp_penguin_jailcell(int irq, struct pt_regs *regs) | |||
1239 | { | 1226 | { |
1240 | clear_softint(1 << irq); | 1227 | clear_softint(1 << irq); |
1241 | 1228 | ||
1242 | irq_enter(); | ||
1243 | |||
1244 | preempt_disable(); | 1229 | preempt_disable(); |
1245 | 1230 | ||
1246 | __asm__ __volatile__("flushw"); | 1231 | __asm__ __volatile__("flushw"); |
@@ -1253,8 +1238,6 @@ void smp_penguin_jailcell(int irq, struct pt_regs *regs) | |||
1253 | prom_world(0); | 1238 | prom_world(0); |
1254 | 1239 | ||
1255 | preempt_enable(); | 1240 | preempt_enable(); |
1256 | |||
1257 | irq_exit(); | ||
1258 | } | 1241 | } |
1259 | 1242 | ||
1260 | /* /proc/profile writes can call this, don't __init it please. */ | 1243 | /* /proc/profile writes can call this, don't __init it please. */ |
diff --git a/arch/sparc64/kernel/sys_sparc.c b/arch/sparc64/kernel/sys_sparc.c index 8d4761f15fa9..0dbc941f130e 100644 --- a/arch/sparc64/kernel/sys_sparc.c +++ b/arch/sparc64/kernel/sys_sparc.c | |||
@@ -549,13 +549,13 @@ int sparc64_mmap_check(unsigned long addr, unsigned long len, | |||
549 | if (len >= STACK_TOP32) | 549 | if (len >= STACK_TOP32) |
550 | return -EINVAL; | 550 | return -EINVAL; |
551 | 551 | ||
552 | if ((flags & MAP_FIXED) && addr > STACK_TOP32 - len) | 552 | if (addr > STACK_TOP32 - len) |
553 | return -EINVAL; | 553 | return -EINVAL; |
554 | } else { | 554 | } else { |
555 | if (len >= VA_EXCLUDE_START) | 555 | if (len >= VA_EXCLUDE_START) |
556 | return -EINVAL; | 556 | return -EINVAL; |
557 | 557 | ||
558 | if ((flags & MAP_FIXED) && invalid_64bit_range(addr, len)) | 558 | if (invalid_64bit_range(addr, len)) |
559 | return -EINVAL; | 559 | return -EINVAL; |
560 | } | 560 | } |
561 | 561 | ||
diff --git a/arch/sparc64/kernel/sys_sparc32.c b/arch/sparc64/kernel/sys_sparc32.c index 161ce4710fe7..1aa4288125f2 100644 --- a/arch/sparc64/kernel/sys_sparc32.c +++ b/arch/sparc64/kernel/sys_sparc32.c | |||
@@ -236,13 +236,6 @@ asmlinkage long sys32_getegid16(void) | |||
236 | 236 | ||
237 | /* 32-bit timeval and related flotsam. */ | 237 | /* 32-bit timeval and related flotsam. */ |
238 | 238 | ||
239 | static long get_tv32(struct timeval *o, struct compat_timeval __user *i) | ||
240 | { | ||
241 | return (!access_ok(VERIFY_READ, i, sizeof(*i)) || | ||
242 | (__get_user(o->tv_sec, &i->tv_sec) | | ||
243 | __get_user(o->tv_usec, &i->tv_usec))); | ||
244 | } | ||
245 | |||
246 | static inline long put_tv32(struct compat_timeval __user *o, struct timeval *i) | 239 | static inline long put_tv32(struct compat_timeval __user *o, struct timeval *i) |
247 | { | 240 | { |
248 | return (!access_ok(VERIFY_WRITE, o, sizeof(*o)) || | 241 | return (!access_ok(VERIFY_WRITE, o, sizeof(*o)) || |
@@ -757,30 +750,6 @@ asmlinkage long sys32_settimeofday(struct compat_timeval __user *tv, | |||
757 | return do_sys_settimeofday(tv ? &kts : NULL, tz ? &ktz : NULL); | 750 | return do_sys_settimeofday(tv ? &kts : NULL, tz ? &ktz : NULL); |
758 | } | 751 | } |
759 | 752 | ||
760 | asmlinkage long sys32_utimes(char __user *filename, | ||
761 | struct compat_timeval __user *tvs) | ||
762 | { | ||
763 | struct timespec tv[2]; | ||
764 | |||
765 | if (tvs) { | ||
766 | struct timeval ktvs[2]; | ||
767 | if (get_tv32(&ktvs[0], tvs) || | ||
768 | get_tv32(&ktvs[1], 1+tvs)) | ||
769 | return -EFAULT; | ||
770 | |||
771 | if (ktvs[0].tv_usec < 0 || ktvs[0].tv_usec >= 1000000 || | ||
772 | ktvs[1].tv_usec < 0 || ktvs[1].tv_usec >= 1000000) | ||
773 | return -EINVAL; | ||
774 | |||
775 | tv[0].tv_sec = ktvs[0].tv_sec; | ||
776 | tv[0].tv_nsec = 1000 * ktvs[0].tv_usec; | ||
777 | tv[1].tv_sec = ktvs[1].tv_sec; | ||
778 | tv[1].tv_nsec = 1000 * ktvs[1].tv_usec; | ||
779 | } | ||
780 | |||
781 | return do_utimes(AT_FDCWD, filename, tvs ? tv : NULL, 0); | ||
782 | } | ||
783 | |||
784 | /* These are here just in case some old sparc32 binary calls it. */ | 753 | /* These are here just in case some old sparc32 binary calls it. */ |
785 | asmlinkage long sys32_pause(void) | 754 | asmlinkage long sys32_pause(void) |
786 | { | 755 | { |
diff --git a/arch/sparc64/kernel/systbls.S b/arch/sparc64/kernel/systbls.S index a4fef2ba1ae1..8b5282d433c4 100644 --- a/arch/sparc64/kernel/systbls.S +++ b/arch/sparc64/kernel/systbls.S | |||
@@ -45,7 +45,7 @@ sys_call_table32: | |||
45 | /*120*/ .word compat_sys_readv, compat_sys_writev, sys32_settimeofday, sys32_fchown16, sys_fchmod | 45 | /*120*/ .word compat_sys_readv, compat_sys_writev, sys32_settimeofday, sys32_fchown16, sys_fchmod |
46 | .word sys_nis_syscall, sys32_setreuid16, sys32_setregid16, sys_rename, sys_truncate | 46 | .word sys_nis_syscall, sys32_setreuid16, sys32_setregid16, sys_rename, sys_truncate |
47 | /*130*/ .word sys_ftruncate, sys_flock, compat_sys_lstat64, sys_nis_syscall, sys_nis_syscall | 47 | /*130*/ .word sys_ftruncate, sys_flock, compat_sys_lstat64, sys_nis_syscall, sys_nis_syscall |
48 | .word sys_nis_syscall, sys32_mkdir, sys_rmdir, sys32_utimes, compat_sys_stat64 | 48 | .word sys_nis_syscall, sys32_mkdir, sys_rmdir, compat_sys_utimes, compat_sys_stat64 |
49 | /*140*/ .word sys32_sendfile64, sys_nis_syscall, sys32_futex, sys_gettid, compat_sys_getrlimit | 49 | /*140*/ .word sys32_sendfile64, sys_nis_syscall, sys32_futex, sys_gettid, compat_sys_getrlimit |
50 | .word compat_sys_setrlimit, sys_pivot_root, sys32_prctl, sys_pciconfig_read, sys_pciconfig_write | 50 | .word compat_sys_setrlimit, sys_pivot_root, sys32_prctl, sys_pciconfig_read, sys_pciconfig_write |
51 | /*150*/ .word sys_nis_syscall, sys_inotify_init, sys_inotify_add_watch, sys_poll, sys_getdents64 | 51 | /*150*/ .word sys_nis_syscall, sys_inotify_init, sys_inotify_add_watch, sys_poll, sys_getdents64 |
diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 4cad0b32b0af..ec3e2c72302a 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c | |||
@@ -771,6 +771,9 @@ static void __init find_ramdisk(unsigned long phys_base) | |||
771 | initrd_end = ramdisk_image + sparc_ramdisk_size; | 771 | initrd_end = ramdisk_image + sparc_ramdisk_size; |
772 | 772 | ||
773 | lmb_reserve(initrd_start, initrd_end); | 773 | lmb_reserve(initrd_start, initrd_end); |
774 | |||
775 | initrd_start += PAGE_OFFSET; | ||
776 | initrd_end += PAGE_OFFSET; | ||
774 | } | 777 | } |
775 | #endif | 778 | #endif |
776 | } | 779 | } |
@@ -2362,16 +2365,3 @@ void __flush_tlb_all(void) | |||
2362 | __asm__ __volatile__("wrpr %0, 0, %%pstate" | 2365 | __asm__ __volatile__("wrpr %0, 0, %%pstate" |
2363 | : : "r" (pstate)); | 2366 | : : "r" (pstate)); |
2364 | } | 2367 | } |
2365 | |||
2366 | #ifdef CONFIG_MEMORY_HOTPLUG | ||
2367 | |||
2368 | void online_page(struct page *page) | ||
2369 | { | ||
2370 | ClearPageReserved(page); | ||
2371 | init_page_count(page); | ||
2372 | __free_page(page); | ||
2373 | totalram_pages++; | ||
2374 | num_physpages++; | ||
2375 | } | ||
2376 | |||
2377 | #endif /* CONFIG_MEMORY_HOTPLUG */ | ||
diff --git a/arch/um/drivers/line.c b/arch/um/drivers/line.c index 10b86e1cc659..5047490fc299 100644 --- a/arch/um/drivers/line.c +++ b/arch/um/drivers/line.c | |||
@@ -191,9 +191,9 @@ void line_flush_chars(struct tty_struct *tty) | |||
191 | line_flush_buffer(tty); | 191 | line_flush_buffer(tty); |
192 | } | 192 | } |
193 | 193 | ||
194 | void line_put_char(struct tty_struct *tty, unsigned char ch) | 194 | int line_put_char(struct tty_struct *tty, unsigned char ch) |
195 | { | 195 | { |
196 | line_write(tty, &ch, sizeof(ch)); | 196 | return line_write(tty, &ch, sizeof(ch)); |
197 | } | 197 | } |
198 | 198 | ||
199 | int line_write(struct tty_struct *tty, const unsigned char *buf, int len) | 199 | int line_write(struct tty_struct *tty, const unsigned char *buf, int len) |
diff --git a/arch/um/include/line.h b/arch/um/include/line.h index 1223f2c844b4..979b73e6352d 100644 --- a/arch/um/include/line.h +++ b/arch/um/include/line.h | |||
@@ -71,7 +71,7 @@ extern int line_setup(struct line *lines, unsigned int sizeof_lines, | |||
71 | char *init, char **error_out); | 71 | char *init, char **error_out); |
72 | extern int line_write(struct tty_struct *tty, const unsigned char *buf, | 72 | extern int line_write(struct tty_struct *tty, const unsigned char *buf, |
73 | int len); | 73 | int len); |
74 | extern void line_put_char(struct tty_struct *tty, unsigned char ch); | 74 | extern int line_put_char(struct tty_struct *tty, unsigned char ch); |
75 | extern void line_set_termios(struct tty_struct *tty, struct ktermios * old); | 75 | extern void line_set_termios(struct tty_struct *tty, struct ktermios * old); |
76 | extern int line_chars_in_buffer(struct tty_struct *tty); | 76 | extern int line_chars_in_buffer(struct tty_struct *tty); |
77 | extern void line_flush_buffer(struct tty_struct *tty); | 77 | extern void line_flush_buffer(struct tty_struct *tty); |
diff --git a/arch/um/kernel/syscall.c b/arch/um/kernel/syscall.c index 9cffc628a37e..128ee85bc8d9 100644 --- a/arch/um/kernel/syscall.c +++ b/arch/um/kernel/syscall.c | |||
@@ -73,23 +73,6 @@ long old_mmap(unsigned long addr, unsigned long len, | |||
73 | out: | 73 | out: |
74 | return err; | 74 | return err; |
75 | } | 75 | } |
76 | /* | ||
77 | * sys_pipe() is the normal C calling standard for creating | ||
78 | * a pipe. It's not the way unix traditionally does this, though. | ||
79 | */ | ||
80 | long sys_pipe(unsigned long __user * fildes) | ||
81 | { | ||
82 | int fd[2]; | ||
83 | long error; | ||
84 | |||
85 | error = do_pipe(fd); | ||
86 | if (!error) { | ||
87 | if (copy_to_user(fildes, fd, sizeof(fd))) | ||
88 | error = -EFAULT; | ||
89 | } | ||
90 | return error; | ||
91 | } | ||
92 | |||
93 | 76 | ||
94 | long sys_uname(struct old_utsname __user * name) | 77 | long sys_uname(struct old_utsname __user * name) |
95 | { | 78 | { |
diff --git a/arch/v850/kernel/syscalls.c b/arch/v850/kernel/syscalls.c index 003db9c8c44a..1a83daf8e24f 100644 --- a/arch/v850/kernel/syscalls.c +++ b/arch/v850/kernel/syscalls.c | |||
@@ -132,23 +132,6 @@ sys_ipc (uint call, int first, int second, int third, void *ptr, long fifth) | |||
132 | return ret; | 132 | return ret; |
133 | } | 133 | } |
134 | 134 | ||
135 | /* | ||
136 | * sys_pipe() is the normal C calling standard for creating | ||
137 | * a pipe. It's not the way unix traditionally does this, though. | ||
138 | */ | ||
139 | int sys_pipe (int *fildes) | ||
140 | { | ||
141 | int fd[2]; | ||
142 | int error; | ||
143 | |||
144 | error = do_pipe (fd); | ||
145 | if (!error) { | ||
146 | if (copy_to_user (fildes, fd, 2*sizeof (int))) | ||
147 | error = -EFAULT; | ||
148 | } | ||
149 | return error; | ||
150 | } | ||
151 | |||
152 | static inline unsigned long | 135 | static inline unsigned long |
153 | do_mmap2 (unsigned long addr, size_t len, | 136 | do_mmap2 (unsigned long addr, size_t len, |
154 | unsigned long prot, unsigned long flags, | 137 | unsigned long prot, unsigned long flags, |
diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig index c3f880902d66..bbcafaa160c0 100644 --- a/arch/x86/Kconfig +++ b/arch/x86/Kconfig | |||
@@ -18,6 +18,7 @@ config X86_64 | |||
18 | ### Arch settings | 18 | ### Arch settings |
19 | config X86 | 19 | config X86 |
20 | def_bool y | 20 | def_bool y |
21 | select HAVE_UNSTABLE_SCHED_CLOCK | ||
21 | select HAVE_IDE | 22 | select HAVE_IDE |
22 | select HAVE_OPROFILE | 23 | select HAVE_OPROFILE |
23 | select HAVE_KPROBES | 24 | select HAVE_KPROBES |
@@ -1661,6 +1662,7 @@ config GEODE_MFGPT_TIMER | |||
1661 | 1662 | ||
1662 | config OLPC | 1663 | config OLPC |
1663 | bool "One Laptop Per Child support" | 1664 | bool "One Laptop Per Child support" |
1665 | depends on MGEODE_LX | ||
1664 | default n | 1666 | default n |
1665 | help | 1667 | help |
1666 | Add support for detecting the unique features of the OLPC | 1668 | Add support for detecting the unique features of the OLPC |
diff --git a/arch/x86/boot/compressed/relocs.c b/arch/x86/boot/compressed/relocs.c index d01ea42187e6..edaadea90aaf 100644 --- a/arch/x86/boot/compressed/relocs.c +++ b/arch/x86/boot/compressed/relocs.c | |||
@@ -191,7 +191,7 @@ static void read_ehdr(FILE *fp) | |||
191 | die("Cannot read ELF header: %s\n", | 191 | die("Cannot read ELF header: %s\n", |
192 | strerror(errno)); | 192 | strerror(errno)); |
193 | } | 193 | } |
194 | if (memcmp(ehdr.e_ident, ELFMAG, 4) != 0) { | 194 | if (memcmp(ehdr.e_ident, ELFMAG, SELFMAG) != 0) { |
195 | die("No ELF magic\n"); | 195 | die("No ELF magic\n"); |
196 | } | 196 | } |
197 | if (ehdr.e_ident[EI_CLASS] != ELFCLASS32) { | 197 | if (ehdr.e_ident[EI_CLASS] != ELFCLASS32) { |
diff --git a/arch/x86/kernel/Makefile b/arch/x86/kernel/Makefile index bbdacb398d48..5e618c3b4720 100644 --- a/arch/x86/kernel/Makefile +++ b/arch/x86/kernel/Makefile | |||
@@ -83,9 +83,7 @@ obj-$(CONFIG_KVM_GUEST) += kvm.o | |||
83 | obj-$(CONFIG_KVM_CLOCK) += kvmclock.o | 83 | obj-$(CONFIG_KVM_CLOCK) += kvmclock.o |
84 | obj-$(CONFIG_PARAVIRT) += paravirt.o paravirt_patch_$(BITS).o | 84 | obj-$(CONFIG_PARAVIRT) += paravirt.o paravirt_patch_$(BITS).o |
85 | 85 | ||
86 | ifdef CONFIG_INPUT_PCSPKR | 86 | obj-$(CONFIG_PCSPKR_PLATFORM) += pcspeaker.o |
87 | obj-y += pcspeaker.o | ||
88 | endif | ||
89 | 87 | ||
90 | obj-$(CONFIG_SCx200) += scx200.o | 88 | obj-$(CONFIG_SCx200) += scx200.o |
91 | scx200-y += scx200_32.o | 89 | scx200-y += scx200_32.o |
diff --git a/arch/x86/kernel/acpi/Makefile b/arch/x86/kernel/acpi/Makefile index 7335959b6aff..fd5ca97a2ad5 100644 --- a/arch/x86/kernel/acpi/Makefile +++ b/arch/x86/kernel/acpi/Makefile | |||
@@ -10,5 +10,5 @@ endif | |||
10 | $(obj)/wakeup_rm.o: $(obj)/realmode/wakeup.bin | 10 | $(obj)/wakeup_rm.o: $(obj)/realmode/wakeup.bin |
11 | 11 | ||
12 | $(obj)/realmode/wakeup.bin: FORCE | 12 | $(obj)/realmode/wakeup.bin: FORCE |
13 | $(Q)$(MAKE) $(build)=$(obj)/realmode $@ | 13 | $(Q)$(MAKE) $(build)=$(obj)/realmode |
14 | 14 | ||
diff --git a/arch/x86/kernel/acpi/realmode/Makefile b/arch/x86/kernel/acpi/realmode/Makefile index 092900854acc..1c31cc0e9def 100644 --- a/arch/x86/kernel/acpi/realmode/Makefile +++ b/arch/x86/kernel/acpi/realmode/Makefile | |||
@@ -6,7 +6,8 @@ | |||
6 | # for more details. | 6 | # for more details. |
7 | # | 7 | # |
8 | 8 | ||
9 | targets := wakeup.bin wakeup.elf | 9 | always := wakeup.bin |
10 | targets := wakeup.elf wakeup.lds | ||
10 | 11 | ||
11 | wakeup-y += wakeup.o wakemain.o video-mode.o copy.o | 12 | wakeup-y += wakeup.o wakemain.o video-mode.o copy.o |
12 | 13 | ||
@@ -48,7 +49,7 @@ LDFLAGS_wakeup.elf := -T | |||
48 | 49 | ||
49 | CPPFLAGS_wakeup.lds += -P -C | 50 | CPPFLAGS_wakeup.lds += -P -C |
50 | 51 | ||
51 | $(obj)/wakeup.elf: $(src)/wakeup.lds $(WAKEUP_OBJS) FORCE | 52 | $(obj)/wakeup.elf: $(obj)/wakeup.lds $(WAKEUP_OBJS) FORCE |
52 | $(call if_changed,ld) | 53 | $(call if_changed,ld) |
53 | 54 | ||
54 | OBJCOPYFLAGS_wakeup.bin := -O binary | 55 | OBJCOPYFLAGS_wakeup.bin := -O binary |
diff --git a/arch/x86/kernel/kvmclock.c b/arch/x86/kernel/kvmclock.c index ddee04043aeb..4bc1be5d5472 100644 --- a/arch/x86/kernel/kvmclock.c +++ b/arch/x86/kernel/kvmclock.c | |||
@@ -133,6 +133,7 @@ static int kvm_register_clock(void) | |||
133 | return native_write_msr_safe(MSR_KVM_SYSTEM_TIME, low, high); | 133 | return native_write_msr_safe(MSR_KVM_SYSTEM_TIME, low, high); |
134 | } | 134 | } |
135 | 135 | ||
136 | #ifdef CONFIG_X86_LOCAL_APIC | ||
136 | static void kvm_setup_secondary_clock(void) | 137 | static void kvm_setup_secondary_clock(void) |
137 | { | 138 | { |
138 | /* | 139 | /* |
@@ -143,6 +144,7 @@ static void kvm_setup_secondary_clock(void) | |||
143 | /* ok, done with our trickery, call native */ | 144 | /* ok, done with our trickery, call native */ |
144 | setup_secondary_APIC_clock(); | 145 | setup_secondary_APIC_clock(); |
145 | } | 146 | } |
147 | #endif | ||
146 | 148 | ||
147 | /* | 149 | /* |
148 | * After the clock is registered, the host will keep writing to the | 150 | * After the clock is registered, the host will keep writing to the |
@@ -177,7 +179,9 @@ void __init kvmclock_init(void) | |||
177 | pv_time_ops.get_wallclock = kvm_get_wallclock; | 179 | pv_time_ops.get_wallclock = kvm_get_wallclock; |
178 | pv_time_ops.set_wallclock = kvm_set_wallclock; | 180 | pv_time_ops.set_wallclock = kvm_set_wallclock; |
179 | pv_time_ops.sched_clock = kvm_clock_read; | 181 | pv_time_ops.sched_clock = kvm_clock_read; |
182 | #ifdef CONFIG_X86_LOCAL_APIC | ||
180 | pv_apic_ops.setup_secondary_clock = kvm_setup_secondary_clock; | 183 | pv_apic_ops.setup_secondary_clock = kvm_setup_secondary_clock; |
184 | #endif | ||
181 | machine_ops.shutdown = kvm_shutdown; | 185 | machine_ops.shutdown = kvm_shutdown; |
182 | #ifdef CONFIG_KEXEC | 186 | #ifdef CONFIG_KEXEC |
183 | machine_ops.crash_shutdown = kvm_crash_shutdown; | 187 | machine_ops.crash_shutdown = kvm_crash_shutdown; |
diff --git a/arch/x86/kernel/mpparse.c b/arch/x86/kernel/mpparse.c index 3e2c54dc8b29..404683b94e79 100644 --- a/arch/x86/kernel/mpparse.c +++ b/arch/x86/kernel/mpparse.c | |||
@@ -794,6 +794,11 @@ void __init find_smp_config(void) | |||
794 | ACPI-based MP Configuration | 794 | ACPI-based MP Configuration |
795 | -------------------------------------------------------------------------- */ | 795 | -------------------------------------------------------------------------- */ |
796 | 796 | ||
797 | /* | ||
798 | * Keep this outside and initialized to 0, for !CONFIG_ACPI builds: | ||
799 | */ | ||
800 | int es7000_plat; | ||
801 | |||
797 | #ifdef CONFIG_ACPI | 802 | #ifdef CONFIG_ACPI |
798 | 803 | ||
799 | #ifdef CONFIG_X86_IO_APIC | 804 | #ifdef CONFIG_X86_IO_APIC |
@@ -909,8 +914,6 @@ void __init mp_override_legacy_irq(u8 bus_irq, u8 polarity, u8 trigger, u32 gsi) | |||
909 | MP_intsrc_info(&intsrc); | 914 | MP_intsrc_info(&intsrc); |
910 | } | 915 | } |
911 | 916 | ||
912 | int es7000_plat; | ||
913 | |||
914 | void __init mp_config_acpi_legacy_irqs(void) | 917 | void __init mp_config_acpi_legacy_irqs(void) |
915 | { | 918 | { |
916 | struct mpc_config_intsrc intsrc; | 919 | struct mpc_config_intsrc intsrc; |
diff --git a/arch/x86/kernel/reboot.c b/arch/x86/kernel/reboot.c index 07c6d42ab5ff..f6be7d5f82f8 100644 --- a/arch/x86/kernel/reboot.c +++ b/arch/x86/kernel/reboot.c | |||
@@ -149,7 +149,6 @@ static struct dmi_system_id __initdata reboot_dmi_table[] = { | |||
149 | .matches = { | 149 | .matches = { |
150 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), | 150 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), |
151 | DMI_MATCH(DMI_PRODUCT_NAME, "OptiPlex 745"), | 151 | DMI_MATCH(DMI_PRODUCT_NAME, "OptiPlex 745"), |
152 | DMI_MATCH(DMI_BOARD_NAME, "0WF810"), | ||
153 | }, | 152 | }, |
154 | }, | 153 | }, |
155 | { /* Handle problems with rebooting on Dell Optiplex 745's DFF*/ | 154 | { /* Handle problems with rebooting on Dell Optiplex 745's DFF*/ |
diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c index c0c68c18a788..cc6f5eb20b24 100644 --- a/arch/x86/kernel/setup.c +++ b/arch/x86/kernel/setup.c | |||
@@ -95,7 +95,7 @@ void __init setup_per_cpu_areas(void) | |||
95 | 95 | ||
96 | /* Copy section for each CPU (we discard the original) */ | 96 | /* Copy section for each CPU (we discard the original) */ |
97 | size = PERCPU_ENOUGH_ROOM; | 97 | size = PERCPU_ENOUGH_ROOM; |
98 | printk(KERN_INFO "PERCPU: Allocating %lu bytes of per cpu data\n", | 98 | printk(KERN_INFO "PERCPU: Allocating %zd bytes of per cpu data\n", |
99 | size); | 99 | size); |
100 | 100 | ||
101 | for_each_possible_cpu(i) { | 101 | for_each_possible_cpu(i) { |
diff --git a/arch/x86/kernel/smpboot.c b/arch/x86/kernel/smpboot.c index 84241a256dc8..6b087ab6cd8f 100644 --- a/arch/x86/kernel/smpboot.c +++ b/arch/x86/kernel/smpboot.c | |||
@@ -299,7 +299,7 @@ static void __cpuinit smp_callin(void) | |||
299 | /* | 299 | /* |
300 | * Activate a secondary processor. | 300 | * Activate a secondary processor. |
301 | */ | 301 | */ |
302 | void __cpuinit start_secondary(void *unused) | 302 | static void __cpuinit start_secondary(void *unused) |
303 | { | 303 | { |
304 | /* | 304 | /* |
305 | * Don't put *anything* before cpu_init(), SMP booting is too | 305 | * Don't put *anything* before cpu_init(), SMP booting is too |
@@ -1306,7 +1306,7 @@ static void remove_siblinginfo(int cpu) | |||
1306 | cpu_clear(cpu, cpu_sibling_setup_map); | 1306 | cpu_clear(cpu, cpu_sibling_setup_map); |
1307 | } | 1307 | } |
1308 | 1308 | ||
1309 | int additional_cpus __initdata = -1; | 1309 | static int additional_cpus __initdata = -1; |
1310 | 1310 | ||
1311 | static __init int setup_additional_cpus(char *s) | 1311 | static __init int setup_additional_cpus(char *s) |
1312 | { | 1312 | { |
diff --git a/arch/x86/kernel/sys_i386_32.c b/arch/x86/kernel/sys_i386_32.c index a86d26f036e1..d2ab52cc1d6b 100644 --- a/arch/x86/kernel/sys_i386_32.c +++ b/arch/x86/kernel/sys_i386_32.c | |||
@@ -22,23 +22,6 @@ | |||
22 | #include <asm/uaccess.h> | 22 | #include <asm/uaccess.h> |
23 | #include <asm/unistd.h> | 23 | #include <asm/unistd.h> |
24 | 24 | ||
25 | /* | ||
26 | * sys_pipe() is the normal C calling standard for creating | ||
27 | * a pipe. It's not the way Unix traditionally does this, though. | ||
28 | */ | ||
29 | asmlinkage int sys_pipe(unsigned long __user * fildes) | ||
30 | { | ||
31 | int fd[2]; | ||
32 | int error; | ||
33 | |||
34 | error = do_pipe(fd); | ||
35 | if (!error) { | ||
36 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
37 | error = -EFAULT; | ||
38 | } | ||
39 | return error; | ||
40 | } | ||
41 | |||
42 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, | 25 | asmlinkage long sys_mmap2(unsigned long addr, unsigned long len, |
43 | unsigned long prot, unsigned long flags, | 26 | unsigned long prot, unsigned long flags, |
44 | unsigned long fd, unsigned long pgoff) | 27 | unsigned long fd, unsigned long pgoff) |
diff --git a/arch/x86/kernel/sys_x86_64.c b/arch/x86/kernel/sys_x86_64.c index bd802a5e1aa3..3b360ef33817 100644 --- a/arch/x86/kernel/sys_x86_64.c +++ b/arch/x86/kernel/sys_x86_64.c | |||
@@ -17,23 +17,6 @@ | |||
17 | #include <asm/uaccess.h> | 17 | #include <asm/uaccess.h> |
18 | #include <asm/ia32.h> | 18 | #include <asm/ia32.h> |
19 | 19 | ||
20 | /* | ||
21 | * sys_pipe() is the normal C calling standard for creating | ||
22 | * a pipe. It's not the way Unix traditionally does this, though. | ||
23 | */ | ||
24 | asmlinkage long sys_pipe(int __user *fildes) | ||
25 | { | ||
26 | int fd[2]; | ||
27 | int error; | ||
28 | |||
29 | error = do_pipe(fd); | ||
30 | if (!error) { | ||
31 | if (copy_to_user(fildes, fd, 2*sizeof(int))) | ||
32 | error = -EFAULT; | ||
33 | } | ||
34 | return error; | ||
35 | } | ||
36 | |||
37 | asmlinkage long sys_mmap(unsigned long addr, unsigned long len, unsigned long prot, unsigned long flags, | 20 | asmlinkage long sys_mmap(unsigned long addr, unsigned long len, unsigned long prot, unsigned long flags, |
38 | unsigned long fd, unsigned long off) | 21 | unsigned long fd, unsigned long off) |
39 | { | 22 | { |
diff --git a/arch/x86/kvm/i8254.c b/arch/x86/kvm/i8254.c index 4c943eabacc3..3324d90038e4 100644 --- a/arch/x86/kvm/i8254.c +++ b/arch/x86/kvm/i8254.c | |||
@@ -288,6 +288,8 @@ static void pit_load_count(struct kvm *kvm, int channel, u32 val) | |||
288 | * mode 1 is one shot, mode 2 is period, otherwise del timer */ | 288 | * mode 1 is one shot, mode 2 is period, otherwise del timer */ |
289 | switch (ps->channels[0].mode) { | 289 | switch (ps->channels[0].mode) { |
290 | case 1: | 290 | case 1: |
291 | /* FIXME: enhance mode 4 precision */ | ||
292 | case 4: | ||
291 | create_pit_timer(&ps->pit_timer, val, 0); | 293 | create_pit_timer(&ps->pit_timer, val, 0); |
292 | break; | 294 | break; |
293 | case 2: | 295 | case 2: |
diff --git a/arch/x86/kvm/mmu.c b/arch/x86/kvm/mmu.c index 2ad6f5481671..36c5406b1813 100644 --- a/arch/x86/kvm/mmu.c +++ b/arch/x86/kvm/mmu.c | |||
@@ -79,36 +79,6 @@ static int dbg = 1; | |||
79 | } | 79 | } |
80 | #endif | 80 | #endif |
81 | 81 | ||
82 | #define PT64_PT_BITS 9 | ||
83 | #define PT64_ENT_PER_PAGE (1 << PT64_PT_BITS) | ||
84 | #define PT32_PT_BITS 10 | ||
85 | #define PT32_ENT_PER_PAGE (1 << PT32_PT_BITS) | ||
86 | |||
87 | #define PT_WRITABLE_SHIFT 1 | ||
88 | |||
89 | #define PT_PRESENT_MASK (1ULL << 0) | ||
90 | #define PT_WRITABLE_MASK (1ULL << PT_WRITABLE_SHIFT) | ||
91 | #define PT_USER_MASK (1ULL << 2) | ||
92 | #define PT_PWT_MASK (1ULL << 3) | ||
93 | #define PT_PCD_MASK (1ULL << 4) | ||
94 | #define PT_ACCESSED_MASK (1ULL << 5) | ||
95 | #define PT_DIRTY_MASK (1ULL << 6) | ||
96 | #define PT_PAGE_SIZE_MASK (1ULL << 7) | ||
97 | #define PT_PAT_MASK (1ULL << 7) | ||
98 | #define PT_GLOBAL_MASK (1ULL << 8) | ||
99 | #define PT64_NX_SHIFT 63 | ||
100 | #define PT64_NX_MASK (1ULL << PT64_NX_SHIFT) | ||
101 | |||
102 | #define PT_PAT_SHIFT 7 | ||
103 | #define PT_DIR_PAT_SHIFT 12 | ||
104 | #define PT_DIR_PAT_MASK (1ULL << PT_DIR_PAT_SHIFT) | ||
105 | |||
106 | #define PT32_DIR_PSE36_SIZE 4 | ||
107 | #define PT32_DIR_PSE36_SHIFT 13 | ||
108 | #define PT32_DIR_PSE36_MASK \ | ||
109 | (((1ULL << PT32_DIR_PSE36_SIZE) - 1) << PT32_DIR_PSE36_SHIFT) | ||
110 | |||
111 | |||
112 | #define PT_FIRST_AVAIL_BITS_SHIFT 9 | 82 | #define PT_FIRST_AVAIL_BITS_SHIFT 9 |
113 | #define PT64_SECOND_AVAIL_BITS_SHIFT 52 | 83 | #define PT64_SECOND_AVAIL_BITS_SHIFT 52 |
114 | 84 | ||
@@ -154,10 +124,6 @@ static int dbg = 1; | |||
154 | #define PFERR_USER_MASK (1U << 2) | 124 | #define PFERR_USER_MASK (1U << 2) |
155 | #define PFERR_FETCH_MASK (1U << 4) | 125 | #define PFERR_FETCH_MASK (1U << 4) |
156 | 126 | ||
157 | #define PT64_ROOT_LEVEL 4 | ||
158 | #define PT32_ROOT_LEVEL 2 | ||
159 | #define PT32E_ROOT_LEVEL 3 | ||
160 | |||
161 | #define PT_DIRECTORY_LEVEL 2 | 127 | #define PT_DIRECTORY_LEVEL 2 |
162 | #define PT_PAGE_TABLE_LEVEL 1 | 128 | #define PT_PAGE_TABLE_LEVEL 1 |
163 | 129 | ||
@@ -186,6 +152,12 @@ static struct kmem_cache *mmu_page_header_cache; | |||
186 | 152 | ||
187 | static u64 __read_mostly shadow_trap_nonpresent_pte; | 153 | static u64 __read_mostly shadow_trap_nonpresent_pte; |
188 | static u64 __read_mostly shadow_notrap_nonpresent_pte; | 154 | static u64 __read_mostly shadow_notrap_nonpresent_pte; |
155 | static u64 __read_mostly shadow_base_present_pte; | ||
156 | static u64 __read_mostly shadow_nx_mask; | ||
157 | static u64 __read_mostly shadow_x_mask; /* mutual exclusive with nx_mask */ | ||
158 | static u64 __read_mostly shadow_user_mask; | ||
159 | static u64 __read_mostly shadow_accessed_mask; | ||
160 | static u64 __read_mostly shadow_dirty_mask; | ||
189 | 161 | ||
190 | void kvm_mmu_set_nonpresent_ptes(u64 trap_pte, u64 notrap_pte) | 162 | void kvm_mmu_set_nonpresent_ptes(u64 trap_pte, u64 notrap_pte) |
191 | { | 163 | { |
@@ -194,6 +166,23 @@ void kvm_mmu_set_nonpresent_ptes(u64 trap_pte, u64 notrap_pte) | |||
194 | } | 166 | } |
195 | EXPORT_SYMBOL_GPL(kvm_mmu_set_nonpresent_ptes); | 167 | EXPORT_SYMBOL_GPL(kvm_mmu_set_nonpresent_ptes); |
196 | 168 | ||
169 | void kvm_mmu_set_base_ptes(u64 base_pte) | ||
170 | { | ||
171 | shadow_base_present_pte = base_pte; | ||
172 | } | ||
173 | EXPORT_SYMBOL_GPL(kvm_mmu_set_base_ptes); | ||
174 | |||
175 | void kvm_mmu_set_mask_ptes(u64 user_mask, u64 accessed_mask, | ||
176 | u64 dirty_mask, u64 nx_mask, u64 x_mask) | ||
177 | { | ||
178 | shadow_user_mask = user_mask; | ||
179 | shadow_accessed_mask = accessed_mask; | ||
180 | shadow_dirty_mask = dirty_mask; | ||
181 | shadow_nx_mask = nx_mask; | ||
182 | shadow_x_mask = x_mask; | ||
183 | } | ||
184 | EXPORT_SYMBOL_GPL(kvm_mmu_set_mask_ptes); | ||
185 | |||
197 | static int is_write_protection(struct kvm_vcpu *vcpu) | 186 | static int is_write_protection(struct kvm_vcpu *vcpu) |
198 | { | 187 | { |
199 | return vcpu->arch.cr0 & X86_CR0_WP; | 188 | return vcpu->arch.cr0 & X86_CR0_WP; |
@@ -232,7 +221,7 @@ static int is_writeble_pte(unsigned long pte) | |||
232 | 221 | ||
233 | static int is_dirty_pte(unsigned long pte) | 222 | static int is_dirty_pte(unsigned long pte) |
234 | { | 223 | { |
235 | return pte & PT_DIRTY_MASK; | 224 | return pte & shadow_dirty_mask; |
236 | } | 225 | } |
237 | 226 | ||
238 | static int is_rmap_pte(u64 pte) | 227 | static int is_rmap_pte(u64 pte) |
@@ -387,7 +376,6 @@ static void account_shadowed(struct kvm *kvm, gfn_t gfn) | |||
387 | 376 | ||
388 | write_count = slot_largepage_idx(gfn, gfn_to_memslot(kvm, gfn)); | 377 | write_count = slot_largepage_idx(gfn, gfn_to_memslot(kvm, gfn)); |
389 | *write_count += 1; | 378 | *write_count += 1; |
390 | WARN_ON(*write_count > KVM_PAGES_PER_HPAGE); | ||
391 | } | 379 | } |
392 | 380 | ||
393 | static void unaccount_shadowed(struct kvm *kvm, gfn_t gfn) | 381 | static void unaccount_shadowed(struct kvm *kvm, gfn_t gfn) |
@@ -547,7 +535,7 @@ static void rmap_remove(struct kvm *kvm, u64 *spte) | |||
547 | return; | 535 | return; |
548 | sp = page_header(__pa(spte)); | 536 | sp = page_header(__pa(spte)); |
549 | pfn = spte_to_pfn(*spte); | 537 | pfn = spte_to_pfn(*spte); |
550 | if (*spte & PT_ACCESSED_MASK) | 538 | if (*spte & shadow_accessed_mask) |
551 | kvm_set_pfn_accessed(pfn); | 539 | kvm_set_pfn_accessed(pfn); |
552 | if (is_writeble_pte(*spte)) | 540 | if (is_writeble_pte(*spte)) |
553 | kvm_release_pfn_dirty(pfn); | 541 | kvm_release_pfn_dirty(pfn); |
@@ -1073,17 +1061,17 @@ static void mmu_set_spte(struct kvm_vcpu *vcpu, u64 *shadow_pte, | |||
1073 | * whether the guest actually used the pte (in order to detect | 1061 | * whether the guest actually used the pte (in order to detect |
1074 | * demand paging). | 1062 | * demand paging). |
1075 | */ | 1063 | */ |
1076 | spte = PT_PRESENT_MASK | PT_DIRTY_MASK; | 1064 | spte = shadow_base_present_pte | shadow_dirty_mask; |
1077 | if (!speculative) | 1065 | if (!speculative) |
1078 | pte_access |= PT_ACCESSED_MASK; | 1066 | pte_access |= PT_ACCESSED_MASK; |
1079 | if (!dirty) | 1067 | if (!dirty) |
1080 | pte_access &= ~ACC_WRITE_MASK; | 1068 | pte_access &= ~ACC_WRITE_MASK; |
1081 | if (!(pte_access & ACC_EXEC_MASK)) | 1069 | if (pte_access & ACC_EXEC_MASK) |
1082 | spte |= PT64_NX_MASK; | 1070 | spte |= shadow_x_mask; |
1083 | 1071 | else | |
1084 | spte |= PT_PRESENT_MASK; | 1072 | spte |= shadow_nx_mask; |
1085 | if (pte_access & ACC_USER_MASK) | 1073 | if (pte_access & ACC_USER_MASK) |
1086 | spte |= PT_USER_MASK; | 1074 | spte |= shadow_user_mask; |
1087 | if (largepage) | 1075 | if (largepage) |
1088 | spte |= PT_PAGE_SIZE_MASK; | 1076 | spte |= PT_PAGE_SIZE_MASK; |
1089 | 1077 | ||
@@ -1188,8 +1176,9 @@ static int __direct_map(struct kvm_vcpu *vcpu, gpa_t v, int write, | |||
1188 | return -ENOMEM; | 1176 | return -ENOMEM; |
1189 | } | 1177 | } |
1190 | 1178 | ||
1191 | table[index] = __pa(new_table->spt) | PT_PRESENT_MASK | 1179 | table[index] = __pa(new_table->spt) |
1192 | | PT_WRITABLE_MASK | PT_USER_MASK; | 1180 | | PT_PRESENT_MASK | PT_WRITABLE_MASK |
1181 | | shadow_user_mask | shadow_x_mask; | ||
1193 | } | 1182 | } |
1194 | table_addr = table[index] & PT64_BASE_ADDR_MASK; | 1183 | table_addr = table[index] & PT64_BASE_ADDR_MASK; |
1195 | } | 1184 | } |
@@ -1244,7 +1233,6 @@ static void mmu_free_roots(struct kvm_vcpu *vcpu) | |||
1244 | if (!VALID_PAGE(vcpu->arch.mmu.root_hpa)) | 1233 | if (!VALID_PAGE(vcpu->arch.mmu.root_hpa)) |
1245 | return; | 1234 | return; |
1246 | spin_lock(&vcpu->kvm->mmu_lock); | 1235 | spin_lock(&vcpu->kvm->mmu_lock); |
1247 | #ifdef CONFIG_X86_64 | ||
1248 | if (vcpu->arch.mmu.shadow_root_level == PT64_ROOT_LEVEL) { | 1236 | if (vcpu->arch.mmu.shadow_root_level == PT64_ROOT_LEVEL) { |
1249 | hpa_t root = vcpu->arch.mmu.root_hpa; | 1237 | hpa_t root = vcpu->arch.mmu.root_hpa; |
1250 | 1238 | ||
@@ -1256,7 +1244,6 @@ static void mmu_free_roots(struct kvm_vcpu *vcpu) | |||
1256 | spin_unlock(&vcpu->kvm->mmu_lock); | 1244 | spin_unlock(&vcpu->kvm->mmu_lock); |
1257 | return; | 1245 | return; |
1258 | } | 1246 | } |
1259 | #endif | ||
1260 | for (i = 0; i < 4; ++i) { | 1247 | for (i = 0; i < 4; ++i) { |
1261 | hpa_t root = vcpu->arch.mmu.pae_root[i]; | 1248 | hpa_t root = vcpu->arch.mmu.pae_root[i]; |
1262 | 1249 | ||
@@ -1282,7 +1269,6 @@ static void mmu_alloc_roots(struct kvm_vcpu *vcpu) | |||
1282 | 1269 | ||
1283 | root_gfn = vcpu->arch.cr3 >> PAGE_SHIFT; | 1270 | root_gfn = vcpu->arch.cr3 >> PAGE_SHIFT; |
1284 | 1271 | ||
1285 | #ifdef CONFIG_X86_64 | ||
1286 | if (vcpu->arch.mmu.shadow_root_level == PT64_ROOT_LEVEL) { | 1272 | if (vcpu->arch.mmu.shadow_root_level == PT64_ROOT_LEVEL) { |
1287 | hpa_t root = vcpu->arch.mmu.root_hpa; | 1273 | hpa_t root = vcpu->arch.mmu.root_hpa; |
1288 | 1274 | ||
@@ -1297,7 +1283,6 @@ static void mmu_alloc_roots(struct kvm_vcpu *vcpu) | |||
1297 | vcpu->arch.mmu.root_hpa = root; | 1283 | vcpu->arch.mmu.root_hpa = root; |
1298 | return; | 1284 | return; |
1299 | } | 1285 | } |
1300 | #endif | ||
1301 | metaphysical = !is_paging(vcpu); | 1286 | metaphysical = !is_paging(vcpu); |
1302 | if (tdp_enabled) | 1287 | if (tdp_enabled) |
1303 | metaphysical = 1; | 1288 | metaphysical = 1; |
@@ -1377,7 +1362,7 @@ static int tdp_page_fault(struct kvm_vcpu *vcpu, gva_t gpa, | |||
1377 | spin_lock(&vcpu->kvm->mmu_lock); | 1362 | spin_lock(&vcpu->kvm->mmu_lock); |
1378 | kvm_mmu_free_some_pages(vcpu); | 1363 | kvm_mmu_free_some_pages(vcpu); |
1379 | r = __direct_map(vcpu, gpa, error_code & PFERR_WRITE_MASK, | 1364 | r = __direct_map(vcpu, gpa, error_code & PFERR_WRITE_MASK, |
1380 | largepage, gfn, pfn, TDP_ROOT_LEVEL); | 1365 | largepage, gfn, pfn, kvm_x86_ops->get_tdp_level()); |
1381 | spin_unlock(&vcpu->kvm->mmu_lock); | 1366 | spin_unlock(&vcpu->kvm->mmu_lock); |
1382 | 1367 | ||
1383 | return r; | 1368 | return r; |
@@ -1484,7 +1469,7 @@ static int init_kvm_tdp_mmu(struct kvm_vcpu *vcpu) | |||
1484 | context->page_fault = tdp_page_fault; | 1469 | context->page_fault = tdp_page_fault; |
1485 | context->free = nonpaging_free; | 1470 | context->free = nonpaging_free; |
1486 | context->prefetch_page = nonpaging_prefetch_page; | 1471 | context->prefetch_page = nonpaging_prefetch_page; |
1487 | context->shadow_root_level = TDP_ROOT_LEVEL; | 1472 | context->shadow_root_level = kvm_x86_ops->get_tdp_level(); |
1488 | context->root_hpa = INVALID_PAGE; | 1473 | context->root_hpa = INVALID_PAGE; |
1489 | 1474 | ||
1490 | if (!is_paging(vcpu)) { | 1475 | if (!is_paging(vcpu)) { |
@@ -1633,7 +1618,7 @@ static bool last_updated_pte_accessed(struct kvm_vcpu *vcpu) | |||
1633 | { | 1618 | { |
1634 | u64 *spte = vcpu->arch.last_pte_updated; | 1619 | u64 *spte = vcpu->arch.last_pte_updated; |
1635 | 1620 | ||
1636 | return !!(spte && (*spte & PT_ACCESSED_MASK)); | 1621 | return !!(spte && (*spte & shadow_accessed_mask)); |
1637 | } | 1622 | } |
1638 | 1623 | ||
1639 | static void mmu_guess_page_from_pte_write(struct kvm_vcpu *vcpu, gpa_t gpa, | 1624 | static void mmu_guess_page_from_pte_write(struct kvm_vcpu *vcpu, gpa_t gpa, |
diff --git a/arch/x86/kvm/mmu.h b/arch/x86/kvm/mmu.h index e64e9f56a65e..1730757bbc7a 100644 --- a/arch/x86/kvm/mmu.h +++ b/arch/x86/kvm/mmu.h | |||
@@ -3,11 +3,38 @@ | |||
3 | 3 | ||
4 | #include <linux/kvm_host.h> | 4 | #include <linux/kvm_host.h> |
5 | 5 | ||
6 | #ifdef CONFIG_X86_64 | 6 | #define PT64_PT_BITS 9 |
7 | #define TDP_ROOT_LEVEL PT64_ROOT_LEVEL | 7 | #define PT64_ENT_PER_PAGE (1 << PT64_PT_BITS) |
8 | #else | 8 | #define PT32_PT_BITS 10 |
9 | #define TDP_ROOT_LEVEL PT32E_ROOT_LEVEL | 9 | #define PT32_ENT_PER_PAGE (1 << PT32_PT_BITS) |
10 | #endif | 10 | |
11 | #define PT_WRITABLE_SHIFT 1 | ||
12 | |||
13 | #define PT_PRESENT_MASK (1ULL << 0) | ||
14 | #define PT_WRITABLE_MASK (1ULL << PT_WRITABLE_SHIFT) | ||
15 | #define PT_USER_MASK (1ULL << 2) | ||
16 | #define PT_PWT_MASK (1ULL << 3) | ||
17 | #define PT_PCD_MASK (1ULL << 4) | ||
18 | #define PT_ACCESSED_MASK (1ULL << 5) | ||
19 | #define PT_DIRTY_MASK (1ULL << 6) | ||
20 | #define PT_PAGE_SIZE_MASK (1ULL << 7) | ||
21 | #define PT_PAT_MASK (1ULL << 7) | ||
22 | #define PT_GLOBAL_MASK (1ULL << 8) | ||
23 | #define PT64_NX_SHIFT 63 | ||
24 | #define PT64_NX_MASK (1ULL << PT64_NX_SHIFT) | ||
25 | |||
26 | #define PT_PAT_SHIFT 7 | ||
27 | #define PT_DIR_PAT_SHIFT 12 | ||
28 | #define PT_DIR_PAT_MASK (1ULL << PT_DIR_PAT_SHIFT) | ||
29 | |||
30 | #define PT32_DIR_PSE36_SIZE 4 | ||
31 | #define PT32_DIR_PSE36_SHIFT 13 | ||
32 | #define PT32_DIR_PSE36_MASK \ | ||
33 | (((1ULL << PT32_DIR_PSE36_SIZE) - 1) << PT32_DIR_PSE36_SHIFT) | ||
34 | |||
35 | #define PT64_ROOT_LEVEL 4 | ||
36 | #define PT32_ROOT_LEVEL 2 | ||
37 | #define PT32E_ROOT_LEVEL 3 | ||
11 | 38 | ||
12 | static inline void kvm_mmu_free_some_pages(struct kvm_vcpu *vcpu) | 39 | static inline void kvm_mmu_free_some_pages(struct kvm_vcpu *vcpu) |
13 | { | 40 | { |
diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c index 89e0be2c10d0..ab22615eee89 100644 --- a/arch/x86/kvm/svm.c +++ b/arch/x86/kvm/svm.c | |||
@@ -1863,6 +1863,15 @@ static bool svm_cpu_has_accelerated_tpr(void) | |||
1863 | return false; | 1863 | return false; |
1864 | } | 1864 | } |
1865 | 1865 | ||
1866 | static int get_npt_level(void) | ||
1867 | { | ||
1868 | #ifdef CONFIG_X86_64 | ||
1869 | return PT64_ROOT_LEVEL; | ||
1870 | #else | ||
1871 | return PT32E_ROOT_LEVEL; | ||
1872 | #endif | ||
1873 | } | ||
1874 | |||
1866 | static struct kvm_x86_ops svm_x86_ops = { | 1875 | static struct kvm_x86_ops svm_x86_ops = { |
1867 | .cpu_has_kvm_support = has_svm, | 1876 | .cpu_has_kvm_support = has_svm, |
1868 | .disabled_by_bios = is_disabled, | 1877 | .disabled_by_bios = is_disabled, |
@@ -1920,6 +1929,7 @@ static struct kvm_x86_ops svm_x86_ops = { | |||
1920 | .inject_pending_vectors = do_interrupt_requests, | 1929 | .inject_pending_vectors = do_interrupt_requests, |
1921 | 1930 | ||
1922 | .set_tss_addr = svm_set_tss_addr, | 1931 | .set_tss_addr = svm_set_tss_addr, |
1932 | .get_tdp_level = get_npt_level, | ||
1923 | }; | 1933 | }; |
1924 | 1934 | ||
1925 | static int __init svm_init(void) | 1935 | static int __init svm_init(void) |
diff --git a/arch/x86/kvm/vmx.c b/arch/x86/kvm/vmx.c index 8e5d6645b90d..bfe4db11989c 100644 --- a/arch/x86/kvm/vmx.c +++ b/arch/x86/kvm/vmx.c | |||
@@ -42,6 +42,9 @@ module_param(enable_vpid, bool, 0); | |||
42 | static int flexpriority_enabled = 1; | 42 | static int flexpriority_enabled = 1; |
43 | module_param(flexpriority_enabled, bool, 0); | 43 | module_param(flexpriority_enabled, bool, 0); |
44 | 44 | ||
45 | static int enable_ept = 1; | ||
46 | module_param(enable_ept, bool, 0); | ||
47 | |||
45 | struct vmcs { | 48 | struct vmcs { |
46 | u32 revision_id; | 49 | u32 revision_id; |
47 | u32 abort; | 50 | u32 abort; |
@@ -84,7 +87,7 @@ static inline struct vcpu_vmx *to_vmx(struct kvm_vcpu *vcpu) | |||
84 | return container_of(vcpu, struct vcpu_vmx, vcpu); | 87 | return container_of(vcpu, struct vcpu_vmx, vcpu); |
85 | } | 88 | } |
86 | 89 | ||
87 | static int init_rmode_tss(struct kvm *kvm); | 90 | static int init_rmode(struct kvm *kvm); |
88 | 91 | ||
89 | static DEFINE_PER_CPU(struct vmcs *, vmxarea); | 92 | static DEFINE_PER_CPU(struct vmcs *, vmxarea); |
90 | static DEFINE_PER_CPU(struct vmcs *, current_vmcs); | 93 | static DEFINE_PER_CPU(struct vmcs *, current_vmcs); |
@@ -107,6 +110,11 @@ static struct vmcs_config { | |||
107 | u32 vmentry_ctrl; | 110 | u32 vmentry_ctrl; |
108 | } vmcs_config; | 111 | } vmcs_config; |
109 | 112 | ||
113 | struct vmx_capability { | ||
114 | u32 ept; | ||
115 | u32 vpid; | ||
116 | } vmx_capability; | ||
117 | |||
110 | #define VMX_SEGMENT_FIELD(seg) \ | 118 | #define VMX_SEGMENT_FIELD(seg) \ |
111 | [VCPU_SREG_##seg] = { \ | 119 | [VCPU_SREG_##seg] = { \ |
112 | .selector = GUEST_##seg##_SELECTOR, \ | 120 | .selector = GUEST_##seg##_SELECTOR, \ |
@@ -214,6 +222,32 @@ static inline bool cpu_has_vmx_virtualize_apic_accesses(void) | |||
214 | SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES); | 222 | SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES); |
215 | } | 223 | } |
216 | 224 | ||
225 | static inline int cpu_has_vmx_invept_individual_addr(void) | ||
226 | { | ||
227 | return (!!(vmx_capability.ept & VMX_EPT_EXTENT_INDIVIDUAL_BIT)); | ||
228 | } | ||
229 | |||
230 | static inline int cpu_has_vmx_invept_context(void) | ||
231 | { | ||
232 | return (!!(vmx_capability.ept & VMX_EPT_EXTENT_CONTEXT_BIT)); | ||
233 | } | ||
234 | |||
235 | static inline int cpu_has_vmx_invept_global(void) | ||
236 | { | ||
237 | return (!!(vmx_capability.ept & VMX_EPT_EXTENT_GLOBAL_BIT)); | ||
238 | } | ||
239 | |||
240 | static inline int cpu_has_vmx_ept(void) | ||
241 | { | ||
242 | return (vmcs_config.cpu_based_2nd_exec_ctrl & | ||
243 | SECONDARY_EXEC_ENABLE_EPT); | ||
244 | } | ||
245 | |||
246 | static inline int vm_need_ept(void) | ||
247 | { | ||
248 | return (cpu_has_vmx_ept() && enable_ept); | ||
249 | } | ||
250 | |||
217 | static inline int vm_need_virtualize_apic_accesses(struct kvm *kvm) | 251 | static inline int vm_need_virtualize_apic_accesses(struct kvm *kvm) |
218 | { | 252 | { |
219 | return ((cpu_has_vmx_virtualize_apic_accesses()) && | 253 | return ((cpu_has_vmx_virtualize_apic_accesses()) && |
@@ -250,6 +284,18 @@ static inline void __invvpid(int ext, u16 vpid, gva_t gva) | |||
250 | : : "a"(&operand), "c"(ext) : "cc", "memory"); | 284 | : : "a"(&operand), "c"(ext) : "cc", "memory"); |
251 | } | 285 | } |
252 | 286 | ||
287 | static inline void __invept(int ext, u64 eptp, gpa_t gpa) | ||
288 | { | ||
289 | struct { | ||
290 | u64 eptp, gpa; | ||
291 | } operand = {eptp, gpa}; | ||
292 | |||
293 | asm volatile (ASM_VMX_INVEPT | ||
294 | /* CF==1 or ZF==1 --> rc = -1 */ | ||
295 | "; ja 1f ; ud2 ; 1:\n" | ||
296 | : : "a" (&operand), "c" (ext) : "cc", "memory"); | ||
297 | } | ||
298 | |||
253 | static struct kvm_msr_entry *find_msr_entry(struct vcpu_vmx *vmx, u32 msr) | 299 | static struct kvm_msr_entry *find_msr_entry(struct vcpu_vmx *vmx, u32 msr) |
254 | { | 300 | { |
255 | int i; | 301 | int i; |
@@ -301,6 +347,33 @@ static inline void vpid_sync_vcpu_all(struct vcpu_vmx *vmx) | |||
301 | __invvpid(VMX_VPID_EXTENT_SINGLE_CONTEXT, vmx->vpid, 0); | 347 | __invvpid(VMX_VPID_EXTENT_SINGLE_CONTEXT, vmx->vpid, 0); |
302 | } | 348 | } |
303 | 349 | ||
350 | static inline void ept_sync_global(void) | ||
351 | { | ||
352 | if (cpu_has_vmx_invept_global()) | ||
353 | __invept(VMX_EPT_EXTENT_GLOBAL, 0, 0); | ||
354 | } | ||
355 | |||
356 | static inline void ept_sync_context(u64 eptp) | ||
357 | { | ||
358 | if (vm_need_ept()) { | ||
359 | if (cpu_has_vmx_invept_context()) | ||
360 | __invept(VMX_EPT_EXTENT_CONTEXT, eptp, 0); | ||
361 | else | ||
362 | ept_sync_global(); | ||
363 | } | ||
364 | } | ||
365 | |||
366 | static inline void ept_sync_individual_addr(u64 eptp, gpa_t gpa) | ||
367 | { | ||
368 | if (vm_need_ept()) { | ||
369 | if (cpu_has_vmx_invept_individual_addr()) | ||
370 | __invept(VMX_EPT_EXTENT_INDIVIDUAL_ADDR, | ||
371 | eptp, gpa); | ||
372 | else | ||
373 | ept_sync_context(eptp); | ||
374 | } | ||
375 | } | ||
376 | |||
304 | static unsigned long vmcs_readl(unsigned long field) | 377 | static unsigned long vmcs_readl(unsigned long field) |
305 | { | 378 | { |
306 | unsigned long value; | 379 | unsigned long value; |
@@ -388,6 +461,8 @@ static void update_exception_bitmap(struct kvm_vcpu *vcpu) | |||
388 | eb |= 1u << 1; | 461 | eb |= 1u << 1; |
389 | if (vcpu->arch.rmode.active) | 462 | if (vcpu->arch.rmode.active) |
390 | eb = ~0; | 463 | eb = ~0; |
464 | if (vm_need_ept()) | ||
465 | eb &= ~(1u << PF_VECTOR); /* bypass_guest_pf = 0 */ | ||
391 | vmcs_write32(EXCEPTION_BITMAP, eb); | 466 | vmcs_write32(EXCEPTION_BITMAP, eb); |
392 | } | 467 | } |
393 | 468 | ||
@@ -985,7 +1060,7 @@ static __init int adjust_vmx_controls(u32 ctl_min, u32 ctl_opt, | |||
985 | static __init int setup_vmcs_config(struct vmcs_config *vmcs_conf) | 1060 | static __init int setup_vmcs_config(struct vmcs_config *vmcs_conf) |
986 | { | 1061 | { |
987 | u32 vmx_msr_low, vmx_msr_high; | 1062 | u32 vmx_msr_low, vmx_msr_high; |
988 | u32 min, opt; | 1063 | u32 min, opt, min2, opt2; |
989 | u32 _pin_based_exec_control = 0; | 1064 | u32 _pin_based_exec_control = 0; |
990 | u32 _cpu_based_exec_control = 0; | 1065 | u32 _cpu_based_exec_control = 0; |
991 | u32 _cpu_based_2nd_exec_control = 0; | 1066 | u32 _cpu_based_2nd_exec_control = 0; |
@@ -1003,6 +1078,8 @@ static __init int setup_vmcs_config(struct vmcs_config *vmcs_conf) | |||
1003 | CPU_BASED_CR8_LOAD_EXITING | | 1078 | CPU_BASED_CR8_LOAD_EXITING | |
1004 | CPU_BASED_CR8_STORE_EXITING | | 1079 | CPU_BASED_CR8_STORE_EXITING | |
1005 | #endif | 1080 | #endif |
1081 | CPU_BASED_CR3_LOAD_EXITING | | ||
1082 | CPU_BASED_CR3_STORE_EXITING | | ||
1006 | CPU_BASED_USE_IO_BITMAPS | | 1083 | CPU_BASED_USE_IO_BITMAPS | |
1007 | CPU_BASED_MOV_DR_EXITING | | 1084 | CPU_BASED_MOV_DR_EXITING | |
1008 | CPU_BASED_USE_TSC_OFFSETING; | 1085 | CPU_BASED_USE_TSC_OFFSETING; |
@@ -1018,11 +1095,13 @@ static __init int setup_vmcs_config(struct vmcs_config *vmcs_conf) | |||
1018 | ~CPU_BASED_CR8_STORE_EXITING; | 1095 | ~CPU_BASED_CR8_STORE_EXITING; |
1019 | #endif | 1096 | #endif |
1020 | if (_cpu_based_exec_control & CPU_BASED_ACTIVATE_SECONDARY_CONTROLS) { | 1097 | if (_cpu_based_exec_control & CPU_BASED_ACTIVATE_SECONDARY_CONTROLS) { |
1021 | min = 0; | 1098 | min2 = 0; |
1022 | opt = SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES | | 1099 | opt2 = SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES | |
1023 | SECONDARY_EXEC_WBINVD_EXITING | | 1100 | SECONDARY_EXEC_WBINVD_EXITING | |
1024 | SECONDARY_EXEC_ENABLE_VPID; | 1101 | SECONDARY_EXEC_ENABLE_VPID | |
1025 | if (adjust_vmx_controls(min, opt, MSR_IA32_VMX_PROCBASED_CTLS2, | 1102 | SECONDARY_EXEC_ENABLE_EPT; |
1103 | if (adjust_vmx_controls(min2, opt2, | ||
1104 | MSR_IA32_VMX_PROCBASED_CTLS2, | ||
1026 | &_cpu_based_2nd_exec_control) < 0) | 1105 | &_cpu_based_2nd_exec_control) < 0) |
1027 | return -EIO; | 1106 | return -EIO; |
1028 | } | 1107 | } |
@@ -1031,6 +1110,16 @@ static __init int setup_vmcs_config(struct vmcs_config *vmcs_conf) | |||
1031 | SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES)) | 1110 | SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES)) |
1032 | _cpu_based_exec_control &= ~CPU_BASED_TPR_SHADOW; | 1111 | _cpu_based_exec_control &= ~CPU_BASED_TPR_SHADOW; |
1033 | #endif | 1112 | #endif |
1113 | if (_cpu_based_2nd_exec_control & SECONDARY_EXEC_ENABLE_EPT) { | ||
1114 | /* CR3 accesses don't need to cause VM Exits when EPT enabled */ | ||
1115 | min &= ~(CPU_BASED_CR3_LOAD_EXITING | | ||
1116 | CPU_BASED_CR3_STORE_EXITING); | ||
1117 | if (adjust_vmx_controls(min, opt, MSR_IA32_VMX_PROCBASED_CTLS, | ||
1118 | &_cpu_based_exec_control) < 0) | ||
1119 | return -EIO; | ||
1120 | rdmsr(MSR_IA32_VMX_EPT_VPID_CAP, | ||
1121 | vmx_capability.ept, vmx_capability.vpid); | ||
1122 | } | ||
1034 | 1123 | ||
1035 | min = 0; | 1124 | min = 0; |
1036 | #ifdef CONFIG_X86_64 | 1125 | #ifdef CONFIG_X86_64 |
@@ -1256,7 +1345,7 @@ static void enter_rmode(struct kvm_vcpu *vcpu) | |||
1256 | fix_rmode_seg(VCPU_SREG_FS, &vcpu->arch.rmode.fs); | 1345 | fix_rmode_seg(VCPU_SREG_FS, &vcpu->arch.rmode.fs); |
1257 | 1346 | ||
1258 | kvm_mmu_reset_context(vcpu); | 1347 | kvm_mmu_reset_context(vcpu); |
1259 | init_rmode_tss(vcpu->kvm); | 1348 | init_rmode(vcpu->kvm); |
1260 | } | 1349 | } |
1261 | 1350 | ||
1262 | #ifdef CONFIG_X86_64 | 1351 | #ifdef CONFIG_X86_64 |
@@ -1304,8 +1393,64 @@ static void vmx_decache_cr4_guest_bits(struct kvm_vcpu *vcpu) | |||
1304 | vcpu->arch.cr4 |= vmcs_readl(GUEST_CR4) & ~KVM_GUEST_CR4_MASK; | 1393 | vcpu->arch.cr4 |= vmcs_readl(GUEST_CR4) & ~KVM_GUEST_CR4_MASK; |
1305 | } | 1394 | } |
1306 | 1395 | ||
1396 | static void ept_load_pdptrs(struct kvm_vcpu *vcpu) | ||
1397 | { | ||
1398 | if (is_paging(vcpu) && is_pae(vcpu) && !is_long_mode(vcpu)) { | ||
1399 | if (!load_pdptrs(vcpu, vcpu->arch.cr3)) { | ||
1400 | printk(KERN_ERR "EPT: Fail to load pdptrs!\n"); | ||
1401 | return; | ||
1402 | } | ||
1403 | vmcs_write64(GUEST_PDPTR0, vcpu->arch.pdptrs[0]); | ||
1404 | vmcs_write64(GUEST_PDPTR1, vcpu->arch.pdptrs[1]); | ||
1405 | vmcs_write64(GUEST_PDPTR2, vcpu->arch.pdptrs[2]); | ||
1406 | vmcs_write64(GUEST_PDPTR3, vcpu->arch.pdptrs[3]); | ||
1407 | } | ||
1408 | } | ||
1409 | |||
1410 | static void vmx_set_cr4(struct kvm_vcpu *vcpu, unsigned long cr4); | ||
1411 | |||
1412 | static void ept_update_paging_mode_cr0(unsigned long *hw_cr0, | ||
1413 | unsigned long cr0, | ||
1414 | struct kvm_vcpu *vcpu) | ||
1415 | { | ||
1416 | if (!(cr0 & X86_CR0_PG)) { | ||
1417 | /* From paging/starting to nonpaging */ | ||
1418 | vmcs_write32(CPU_BASED_VM_EXEC_CONTROL, | ||
1419 | vmcs_config.cpu_based_exec_ctrl | | ||
1420 | (CPU_BASED_CR3_LOAD_EXITING | | ||
1421 | CPU_BASED_CR3_STORE_EXITING)); | ||
1422 | vcpu->arch.cr0 = cr0; | ||
1423 | vmx_set_cr4(vcpu, vcpu->arch.cr4); | ||
1424 | *hw_cr0 |= X86_CR0_PE | X86_CR0_PG; | ||
1425 | *hw_cr0 &= ~X86_CR0_WP; | ||
1426 | } else if (!is_paging(vcpu)) { | ||
1427 | /* From nonpaging to paging */ | ||
1428 | vmcs_write32(CPU_BASED_VM_EXEC_CONTROL, | ||
1429 | vmcs_config.cpu_based_exec_ctrl & | ||
1430 | ~(CPU_BASED_CR3_LOAD_EXITING | | ||
1431 | CPU_BASED_CR3_STORE_EXITING)); | ||
1432 | vcpu->arch.cr0 = cr0; | ||
1433 | vmx_set_cr4(vcpu, vcpu->arch.cr4); | ||
1434 | if (!(vcpu->arch.cr0 & X86_CR0_WP)) | ||
1435 | *hw_cr0 &= ~X86_CR0_WP; | ||
1436 | } | ||
1437 | } | ||
1438 | |||
1439 | static void ept_update_paging_mode_cr4(unsigned long *hw_cr4, | ||
1440 | struct kvm_vcpu *vcpu) | ||
1441 | { | ||
1442 | if (!is_paging(vcpu)) { | ||
1443 | *hw_cr4 &= ~X86_CR4_PAE; | ||
1444 | *hw_cr4 |= X86_CR4_PSE; | ||
1445 | } else if (!(vcpu->arch.cr4 & X86_CR4_PAE)) | ||
1446 | *hw_cr4 &= ~X86_CR4_PAE; | ||
1447 | } | ||
1448 | |||
1307 | static void vmx_set_cr0(struct kvm_vcpu *vcpu, unsigned long cr0) | 1449 | static void vmx_set_cr0(struct kvm_vcpu *vcpu, unsigned long cr0) |
1308 | { | 1450 | { |
1451 | unsigned long hw_cr0 = (cr0 & ~KVM_GUEST_CR0_MASK) | | ||
1452 | KVM_VM_CR0_ALWAYS_ON; | ||
1453 | |||
1309 | vmx_fpu_deactivate(vcpu); | 1454 | vmx_fpu_deactivate(vcpu); |
1310 | 1455 | ||
1311 | if (vcpu->arch.rmode.active && (cr0 & X86_CR0_PE)) | 1456 | if (vcpu->arch.rmode.active && (cr0 & X86_CR0_PE)) |
@@ -1323,29 +1468,61 @@ static void vmx_set_cr0(struct kvm_vcpu *vcpu, unsigned long cr0) | |||
1323 | } | 1468 | } |
1324 | #endif | 1469 | #endif |
1325 | 1470 | ||
1471 | if (vm_need_ept()) | ||
1472 | ept_update_paging_mode_cr0(&hw_cr0, cr0, vcpu); | ||
1473 | |||
1326 | vmcs_writel(CR0_READ_SHADOW, cr0); | 1474 | vmcs_writel(CR0_READ_SHADOW, cr0); |
1327 | vmcs_writel(GUEST_CR0, | 1475 | vmcs_writel(GUEST_CR0, hw_cr0); |
1328 | (cr0 & ~KVM_GUEST_CR0_MASK) | KVM_VM_CR0_ALWAYS_ON); | ||
1329 | vcpu->arch.cr0 = cr0; | 1476 | vcpu->arch.cr0 = cr0; |
1330 | 1477 | ||
1331 | if (!(cr0 & X86_CR0_TS) || !(cr0 & X86_CR0_PE)) | 1478 | if (!(cr0 & X86_CR0_TS) || !(cr0 & X86_CR0_PE)) |
1332 | vmx_fpu_activate(vcpu); | 1479 | vmx_fpu_activate(vcpu); |
1333 | } | 1480 | } |
1334 | 1481 | ||
1482 | static u64 construct_eptp(unsigned long root_hpa) | ||
1483 | { | ||
1484 | u64 eptp; | ||
1485 | |||
1486 | /* TODO write the value reading from MSR */ | ||
1487 | eptp = VMX_EPT_DEFAULT_MT | | ||
1488 | VMX_EPT_DEFAULT_GAW << VMX_EPT_GAW_EPTP_SHIFT; | ||
1489 | eptp |= (root_hpa & PAGE_MASK); | ||
1490 | |||
1491 | return eptp; | ||
1492 | } | ||
1493 | |||
1335 | static void vmx_set_cr3(struct kvm_vcpu *vcpu, unsigned long cr3) | 1494 | static void vmx_set_cr3(struct kvm_vcpu *vcpu, unsigned long cr3) |
1336 | { | 1495 | { |
1496 | unsigned long guest_cr3; | ||
1497 | u64 eptp; | ||
1498 | |||
1499 | guest_cr3 = cr3; | ||
1500 | if (vm_need_ept()) { | ||
1501 | eptp = construct_eptp(cr3); | ||
1502 | vmcs_write64(EPT_POINTER, eptp); | ||
1503 | ept_sync_context(eptp); | ||
1504 | ept_load_pdptrs(vcpu); | ||
1505 | guest_cr3 = is_paging(vcpu) ? vcpu->arch.cr3 : | ||
1506 | VMX_EPT_IDENTITY_PAGETABLE_ADDR; | ||
1507 | } | ||
1508 | |||
1337 | vmx_flush_tlb(vcpu); | 1509 | vmx_flush_tlb(vcpu); |
1338 | vmcs_writel(GUEST_CR3, cr3); | 1510 | vmcs_writel(GUEST_CR3, guest_cr3); |
1339 | if (vcpu->arch.cr0 & X86_CR0_PE) | 1511 | if (vcpu->arch.cr0 & X86_CR0_PE) |
1340 | vmx_fpu_deactivate(vcpu); | 1512 | vmx_fpu_deactivate(vcpu); |
1341 | } | 1513 | } |
1342 | 1514 | ||
1343 | static void vmx_set_cr4(struct kvm_vcpu *vcpu, unsigned long cr4) | 1515 | static void vmx_set_cr4(struct kvm_vcpu *vcpu, unsigned long cr4) |
1344 | { | 1516 | { |
1345 | vmcs_writel(CR4_READ_SHADOW, cr4); | 1517 | unsigned long hw_cr4 = cr4 | (vcpu->arch.rmode.active ? |
1346 | vmcs_writel(GUEST_CR4, cr4 | (vcpu->arch.rmode.active ? | 1518 | KVM_RMODE_VM_CR4_ALWAYS_ON : KVM_PMODE_VM_CR4_ALWAYS_ON); |
1347 | KVM_RMODE_VM_CR4_ALWAYS_ON : KVM_PMODE_VM_CR4_ALWAYS_ON)); | 1519 | |
1348 | vcpu->arch.cr4 = cr4; | 1520 | vcpu->arch.cr4 = cr4; |
1521 | if (vm_need_ept()) | ||
1522 | ept_update_paging_mode_cr4(&hw_cr4, vcpu); | ||
1523 | |||
1524 | vmcs_writel(CR4_READ_SHADOW, cr4); | ||
1525 | vmcs_writel(GUEST_CR4, hw_cr4); | ||
1349 | } | 1526 | } |
1350 | 1527 | ||
1351 | static void vmx_set_efer(struct kvm_vcpu *vcpu, u64 efer) | 1528 | static void vmx_set_efer(struct kvm_vcpu *vcpu, u64 efer) |
@@ -1530,6 +1707,41 @@ out: | |||
1530 | return ret; | 1707 | return ret; |
1531 | } | 1708 | } |
1532 | 1709 | ||
1710 | static int init_rmode_identity_map(struct kvm *kvm) | ||
1711 | { | ||
1712 | int i, r, ret; | ||
1713 | pfn_t identity_map_pfn; | ||
1714 | u32 tmp; | ||
1715 | |||
1716 | if (!vm_need_ept()) | ||
1717 | return 1; | ||
1718 | if (unlikely(!kvm->arch.ept_identity_pagetable)) { | ||
1719 | printk(KERN_ERR "EPT: identity-mapping pagetable " | ||
1720 | "haven't been allocated!\n"); | ||
1721 | return 0; | ||
1722 | } | ||
1723 | if (likely(kvm->arch.ept_identity_pagetable_done)) | ||
1724 | return 1; | ||
1725 | ret = 0; | ||
1726 | identity_map_pfn = VMX_EPT_IDENTITY_PAGETABLE_ADDR >> PAGE_SHIFT; | ||
1727 | r = kvm_clear_guest_page(kvm, identity_map_pfn, 0, PAGE_SIZE); | ||
1728 | if (r < 0) | ||
1729 | goto out; | ||
1730 | /* Set up identity-mapping pagetable for EPT in real mode */ | ||
1731 | for (i = 0; i < PT32_ENT_PER_PAGE; i++) { | ||
1732 | tmp = (i << 22) + (_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | | ||
1733 | _PAGE_ACCESSED | _PAGE_DIRTY | _PAGE_PSE); | ||
1734 | r = kvm_write_guest_page(kvm, identity_map_pfn, | ||
1735 | &tmp, i * sizeof(tmp), sizeof(tmp)); | ||
1736 | if (r < 0) | ||
1737 | goto out; | ||
1738 | } | ||
1739 | kvm->arch.ept_identity_pagetable_done = true; | ||
1740 | ret = 1; | ||
1741 | out: | ||
1742 | return ret; | ||
1743 | } | ||
1744 | |||
1533 | static void seg_setup(int seg) | 1745 | static void seg_setup(int seg) |
1534 | { | 1746 | { |
1535 | struct kvm_vmx_segment_field *sf = &kvm_vmx_segment_fields[seg]; | 1747 | struct kvm_vmx_segment_field *sf = &kvm_vmx_segment_fields[seg]; |
@@ -1564,6 +1776,31 @@ out: | |||
1564 | return r; | 1776 | return r; |
1565 | } | 1777 | } |
1566 | 1778 | ||
1779 | static int alloc_identity_pagetable(struct kvm *kvm) | ||
1780 | { | ||
1781 | struct kvm_userspace_memory_region kvm_userspace_mem; | ||
1782 | int r = 0; | ||
1783 | |||
1784 | down_write(&kvm->slots_lock); | ||
1785 | if (kvm->arch.ept_identity_pagetable) | ||
1786 | goto out; | ||
1787 | kvm_userspace_mem.slot = IDENTITY_PAGETABLE_PRIVATE_MEMSLOT; | ||
1788 | kvm_userspace_mem.flags = 0; | ||
1789 | kvm_userspace_mem.guest_phys_addr = VMX_EPT_IDENTITY_PAGETABLE_ADDR; | ||
1790 | kvm_userspace_mem.memory_size = PAGE_SIZE; | ||
1791 | r = __kvm_set_memory_region(kvm, &kvm_userspace_mem, 0); | ||
1792 | if (r) | ||
1793 | goto out; | ||
1794 | |||
1795 | down_read(¤t->mm->mmap_sem); | ||
1796 | kvm->arch.ept_identity_pagetable = gfn_to_page(kvm, | ||
1797 | VMX_EPT_IDENTITY_PAGETABLE_ADDR >> PAGE_SHIFT); | ||
1798 | up_read(¤t->mm->mmap_sem); | ||
1799 | out: | ||
1800 | up_write(&kvm->slots_lock); | ||
1801 | return r; | ||
1802 | } | ||
1803 | |||
1567 | static void allocate_vpid(struct vcpu_vmx *vmx) | 1804 | static void allocate_vpid(struct vcpu_vmx *vmx) |
1568 | { | 1805 | { |
1569 | int vpid; | 1806 | int vpid; |
@@ -1638,6 +1875,9 @@ static int vmx_vcpu_setup(struct vcpu_vmx *vmx) | |||
1638 | CPU_BASED_CR8_LOAD_EXITING; | 1875 | CPU_BASED_CR8_LOAD_EXITING; |
1639 | #endif | 1876 | #endif |
1640 | } | 1877 | } |
1878 | if (!vm_need_ept()) | ||
1879 | exec_control |= CPU_BASED_CR3_STORE_EXITING | | ||
1880 | CPU_BASED_CR3_LOAD_EXITING; | ||
1641 | vmcs_write32(CPU_BASED_VM_EXEC_CONTROL, exec_control); | 1881 | vmcs_write32(CPU_BASED_VM_EXEC_CONTROL, exec_control); |
1642 | 1882 | ||
1643 | if (cpu_has_secondary_exec_ctrls()) { | 1883 | if (cpu_has_secondary_exec_ctrls()) { |
@@ -1647,6 +1887,8 @@ static int vmx_vcpu_setup(struct vcpu_vmx *vmx) | |||
1647 | ~SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES; | 1887 | ~SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES; |
1648 | if (vmx->vpid == 0) | 1888 | if (vmx->vpid == 0) |
1649 | exec_control &= ~SECONDARY_EXEC_ENABLE_VPID; | 1889 | exec_control &= ~SECONDARY_EXEC_ENABLE_VPID; |
1890 | if (!vm_need_ept()) | ||
1891 | exec_control &= ~SECONDARY_EXEC_ENABLE_EPT; | ||
1650 | vmcs_write32(SECONDARY_VM_EXEC_CONTROL, exec_control); | 1892 | vmcs_write32(SECONDARY_VM_EXEC_CONTROL, exec_control); |
1651 | } | 1893 | } |
1652 | 1894 | ||
@@ -1722,6 +1964,15 @@ static int vmx_vcpu_setup(struct vcpu_vmx *vmx) | |||
1722 | return 0; | 1964 | return 0; |
1723 | } | 1965 | } |
1724 | 1966 | ||
1967 | static int init_rmode(struct kvm *kvm) | ||
1968 | { | ||
1969 | if (!init_rmode_tss(kvm)) | ||
1970 | return 0; | ||
1971 | if (!init_rmode_identity_map(kvm)) | ||
1972 | return 0; | ||
1973 | return 1; | ||
1974 | } | ||
1975 | |||
1725 | static int vmx_vcpu_reset(struct kvm_vcpu *vcpu) | 1976 | static int vmx_vcpu_reset(struct kvm_vcpu *vcpu) |
1726 | { | 1977 | { |
1727 | struct vcpu_vmx *vmx = to_vmx(vcpu); | 1978 | struct vcpu_vmx *vmx = to_vmx(vcpu); |
@@ -1729,7 +1980,7 @@ static int vmx_vcpu_reset(struct kvm_vcpu *vcpu) | |||
1729 | int ret; | 1980 | int ret; |
1730 | 1981 | ||
1731 | down_read(&vcpu->kvm->slots_lock); | 1982 | down_read(&vcpu->kvm->slots_lock); |
1732 | if (!init_rmode_tss(vmx->vcpu.kvm)) { | 1983 | if (!init_rmode(vmx->vcpu.kvm)) { |
1733 | ret = -ENOMEM; | 1984 | ret = -ENOMEM; |
1734 | goto out; | 1985 | goto out; |
1735 | } | 1986 | } |
@@ -1994,6 +2245,9 @@ static int handle_exception(struct kvm_vcpu *vcpu, struct kvm_run *kvm_run) | |||
1994 | if (intr_info & INTR_INFO_DELIVER_CODE_MASK) | 2245 | if (intr_info & INTR_INFO_DELIVER_CODE_MASK) |
1995 | error_code = vmcs_read32(VM_EXIT_INTR_ERROR_CODE); | 2246 | error_code = vmcs_read32(VM_EXIT_INTR_ERROR_CODE); |
1996 | if (is_page_fault(intr_info)) { | 2247 | if (is_page_fault(intr_info)) { |
2248 | /* EPT won't cause page fault directly */ | ||
2249 | if (vm_need_ept()) | ||
2250 | BUG(); | ||
1997 | cr2 = vmcs_readl(EXIT_QUALIFICATION); | 2251 | cr2 = vmcs_readl(EXIT_QUALIFICATION); |
1998 | KVMTRACE_3D(PAGE_FAULT, vcpu, error_code, (u32)cr2, | 2252 | KVMTRACE_3D(PAGE_FAULT, vcpu, error_code, (u32)cr2, |
1999 | (u32)((u64)cr2 >> 32), handler); | 2253 | (u32)((u64)cr2 >> 32), handler); |
@@ -2323,6 +2577,64 @@ static int handle_task_switch(struct kvm_vcpu *vcpu, struct kvm_run *kvm_run) | |||
2323 | return kvm_task_switch(vcpu, tss_selector, reason); | 2577 | return kvm_task_switch(vcpu, tss_selector, reason); |
2324 | } | 2578 | } |
2325 | 2579 | ||
2580 | static int handle_ept_violation(struct kvm_vcpu *vcpu, struct kvm_run *kvm_run) | ||
2581 | { | ||
2582 | u64 exit_qualification; | ||
2583 | enum emulation_result er; | ||
2584 | gpa_t gpa; | ||
2585 | unsigned long hva; | ||
2586 | int gla_validity; | ||
2587 | int r; | ||
2588 | |||
2589 | exit_qualification = vmcs_read64(EXIT_QUALIFICATION); | ||
2590 | |||
2591 | if (exit_qualification & (1 << 6)) { | ||
2592 | printk(KERN_ERR "EPT: GPA exceeds GAW!\n"); | ||
2593 | return -ENOTSUPP; | ||
2594 | } | ||
2595 | |||
2596 | gla_validity = (exit_qualification >> 7) & 0x3; | ||
2597 | if (gla_validity != 0x3 && gla_validity != 0x1 && gla_validity != 0) { | ||
2598 | printk(KERN_ERR "EPT: Handling EPT violation failed!\n"); | ||
2599 | printk(KERN_ERR "EPT: GPA: 0x%lx, GVA: 0x%lx\n", | ||
2600 | (long unsigned int)vmcs_read64(GUEST_PHYSICAL_ADDRESS), | ||
2601 | (long unsigned int)vmcs_read64(GUEST_LINEAR_ADDRESS)); | ||
2602 | printk(KERN_ERR "EPT: Exit qualification is 0x%lx\n", | ||
2603 | (long unsigned int)exit_qualification); | ||
2604 | kvm_run->exit_reason = KVM_EXIT_UNKNOWN; | ||
2605 | kvm_run->hw.hardware_exit_reason = 0; | ||
2606 | return -ENOTSUPP; | ||
2607 | } | ||
2608 | |||
2609 | gpa = vmcs_read64(GUEST_PHYSICAL_ADDRESS); | ||
2610 | hva = gfn_to_hva(vcpu->kvm, gpa >> PAGE_SHIFT); | ||
2611 | if (!kvm_is_error_hva(hva)) { | ||
2612 | r = kvm_mmu_page_fault(vcpu, gpa & PAGE_MASK, 0); | ||
2613 | if (r < 0) { | ||
2614 | printk(KERN_ERR "EPT: Not enough memory!\n"); | ||
2615 | return -ENOMEM; | ||
2616 | } | ||
2617 | return 1; | ||
2618 | } else { | ||
2619 | /* must be MMIO */ | ||
2620 | er = emulate_instruction(vcpu, kvm_run, 0, 0, 0); | ||
2621 | |||
2622 | if (er == EMULATE_FAIL) { | ||
2623 | printk(KERN_ERR | ||
2624 | "EPT: Fail to handle EPT violation vmexit!er is %d\n", | ||
2625 | er); | ||
2626 | printk(KERN_ERR "EPT: GPA: 0x%lx, GVA: 0x%lx\n", | ||
2627 | (long unsigned int)vmcs_read64(GUEST_PHYSICAL_ADDRESS), | ||
2628 | (long unsigned int)vmcs_read64(GUEST_LINEAR_ADDRESS)); | ||
2629 | printk(KERN_ERR "EPT: Exit qualification is 0x%lx\n", | ||
2630 | (long unsigned int)exit_qualification); | ||
2631 | return -ENOTSUPP; | ||
2632 | } else if (er == EMULATE_DO_MMIO) | ||
2633 | return 0; | ||
2634 | } | ||
2635 | return 1; | ||
2636 | } | ||
2637 | |||
2326 | /* | 2638 | /* |
2327 | * The exit handlers return 1 if the exit was handled fully and guest execution | 2639 | * The exit handlers return 1 if the exit was handled fully and guest execution |
2328 | * may resume. Otherwise they set the kvm_run parameter to indicate what needs | 2640 | * may resume. Otherwise they set the kvm_run parameter to indicate what needs |
@@ -2346,6 +2658,7 @@ static int (*kvm_vmx_exit_handlers[])(struct kvm_vcpu *vcpu, | |||
2346 | [EXIT_REASON_APIC_ACCESS] = handle_apic_access, | 2658 | [EXIT_REASON_APIC_ACCESS] = handle_apic_access, |
2347 | [EXIT_REASON_WBINVD] = handle_wbinvd, | 2659 | [EXIT_REASON_WBINVD] = handle_wbinvd, |
2348 | [EXIT_REASON_TASK_SWITCH] = handle_task_switch, | 2660 | [EXIT_REASON_TASK_SWITCH] = handle_task_switch, |
2661 | [EXIT_REASON_EPT_VIOLATION] = handle_ept_violation, | ||
2349 | }; | 2662 | }; |
2350 | 2663 | ||
2351 | static const int kvm_vmx_max_exit_handlers = | 2664 | static const int kvm_vmx_max_exit_handlers = |
@@ -2364,6 +2677,13 @@ static int kvm_handle_exit(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu) | |||
2364 | KVMTRACE_3D(VMEXIT, vcpu, exit_reason, (u32)vmcs_readl(GUEST_RIP), | 2677 | KVMTRACE_3D(VMEXIT, vcpu, exit_reason, (u32)vmcs_readl(GUEST_RIP), |
2365 | (u32)((u64)vmcs_readl(GUEST_RIP) >> 32), entryexit); | 2678 | (u32)((u64)vmcs_readl(GUEST_RIP) >> 32), entryexit); |
2366 | 2679 | ||
2680 | /* Access CR3 don't cause VMExit in paging mode, so we need | ||
2681 | * to sync with guest real CR3. */ | ||
2682 | if (vm_need_ept() && is_paging(vcpu)) { | ||
2683 | vcpu->arch.cr3 = vmcs_readl(GUEST_CR3); | ||
2684 | ept_load_pdptrs(vcpu); | ||
2685 | } | ||
2686 | |||
2367 | if (unlikely(vmx->fail)) { | 2687 | if (unlikely(vmx->fail)) { |
2368 | kvm_run->exit_reason = KVM_EXIT_FAIL_ENTRY; | 2688 | kvm_run->exit_reason = KVM_EXIT_FAIL_ENTRY; |
2369 | kvm_run->fail_entry.hardware_entry_failure_reason | 2689 | kvm_run->fail_entry.hardware_entry_failure_reason |
@@ -2372,7 +2692,8 @@ static int kvm_handle_exit(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu) | |||
2372 | } | 2692 | } |
2373 | 2693 | ||
2374 | if ((vectoring_info & VECTORING_INFO_VALID_MASK) && | 2694 | if ((vectoring_info & VECTORING_INFO_VALID_MASK) && |
2375 | exit_reason != EXIT_REASON_EXCEPTION_NMI) | 2695 | (exit_reason != EXIT_REASON_EXCEPTION_NMI && |
2696 | exit_reason != EXIT_REASON_EPT_VIOLATION)) | ||
2376 | printk(KERN_WARNING "%s: unexpected, valid vectoring info and " | 2697 | printk(KERN_WARNING "%s: unexpected, valid vectoring info and " |
2377 | "exit reason is 0x%x\n", __func__, exit_reason); | 2698 | "exit reason is 0x%x\n", __func__, exit_reason); |
2378 | if (exit_reason < kvm_vmx_max_exit_handlers | 2699 | if (exit_reason < kvm_vmx_max_exit_handlers |
@@ -2674,6 +2995,15 @@ static struct kvm_vcpu *vmx_create_vcpu(struct kvm *kvm, unsigned int id) | |||
2674 | return ERR_PTR(-ENOMEM); | 2995 | return ERR_PTR(-ENOMEM); |
2675 | 2996 | ||
2676 | allocate_vpid(vmx); | 2997 | allocate_vpid(vmx); |
2998 | if (id == 0 && vm_need_ept()) { | ||
2999 | kvm_mmu_set_base_ptes(VMX_EPT_READABLE_MASK | | ||
3000 | VMX_EPT_WRITABLE_MASK | | ||
3001 | VMX_EPT_DEFAULT_MT << VMX_EPT_MT_EPTE_SHIFT); | ||
3002 | kvm_mmu_set_mask_ptes(0ull, VMX_EPT_FAKE_ACCESSED_MASK, | ||
3003 | VMX_EPT_FAKE_DIRTY_MASK, 0ull, | ||
3004 | VMX_EPT_EXECUTABLE_MASK); | ||
3005 | kvm_enable_tdp(); | ||
3006 | } | ||
2677 | 3007 | ||
2678 | err = kvm_vcpu_init(&vmx->vcpu, kvm, id); | 3008 | err = kvm_vcpu_init(&vmx->vcpu, kvm, id); |
2679 | if (err) | 3009 | if (err) |
@@ -2706,6 +3036,10 @@ static struct kvm_vcpu *vmx_create_vcpu(struct kvm *kvm, unsigned int id) | |||
2706 | if (alloc_apic_access_page(kvm) != 0) | 3036 | if (alloc_apic_access_page(kvm) != 0) |
2707 | goto free_vmcs; | 3037 | goto free_vmcs; |
2708 | 3038 | ||
3039 | if (vm_need_ept()) | ||
3040 | if (alloc_identity_pagetable(kvm) != 0) | ||
3041 | goto free_vmcs; | ||
3042 | |||
2709 | return &vmx->vcpu; | 3043 | return &vmx->vcpu; |
2710 | 3044 | ||
2711 | free_vmcs: | 3045 | free_vmcs: |
@@ -2735,6 +3069,11 @@ static void __init vmx_check_processor_compat(void *rtn) | |||
2735 | } | 3069 | } |
2736 | } | 3070 | } |
2737 | 3071 | ||
3072 | static int get_ept_level(void) | ||
3073 | { | ||
3074 | return VMX_EPT_DEFAULT_GAW + 1; | ||
3075 | } | ||
3076 | |||
2738 | static struct kvm_x86_ops vmx_x86_ops = { | 3077 | static struct kvm_x86_ops vmx_x86_ops = { |
2739 | .cpu_has_kvm_support = cpu_has_kvm_support, | 3078 | .cpu_has_kvm_support = cpu_has_kvm_support, |
2740 | .disabled_by_bios = vmx_disabled_by_bios, | 3079 | .disabled_by_bios = vmx_disabled_by_bios, |
@@ -2791,6 +3130,7 @@ static struct kvm_x86_ops vmx_x86_ops = { | |||
2791 | .inject_pending_vectors = do_interrupt_requests, | 3130 | .inject_pending_vectors = do_interrupt_requests, |
2792 | 3131 | ||
2793 | .set_tss_addr = vmx_set_tss_addr, | 3132 | .set_tss_addr = vmx_set_tss_addr, |
3133 | .get_tdp_level = get_ept_level, | ||
2794 | }; | 3134 | }; |
2795 | 3135 | ||
2796 | static int __init vmx_init(void) | 3136 | static int __init vmx_init(void) |
@@ -2843,9 +3183,14 @@ static int __init vmx_init(void) | |||
2843 | vmx_disable_intercept_for_msr(vmx_msr_bitmap, MSR_IA32_SYSENTER_ESP); | 3183 | vmx_disable_intercept_for_msr(vmx_msr_bitmap, MSR_IA32_SYSENTER_ESP); |
2844 | vmx_disable_intercept_for_msr(vmx_msr_bitmap, MSR_IA32_SYSENTER_EIP); | 3184 | vmx_disable_intercept_for_msr(vmx_msr_bitmap, MSR_IA32_SYSENTER_EIP); |
2845 | 3185 | ||
3186 | if (cpu_has_vmx_ept()) | ||
3187 | bypass_guest_pf = 0; | ||
3188 | |||
2846 | if (bypass_guest_pf) | 3189 | if (bypass_guest_pf) |
2847 | kvm_mmu_set_nonpresent_ptes(~0xffeull, 0ull); | 3190 | kvm_mmu_set_nonpresent_ptes(~0xffeull, 0ull); |
2848 | 3191 | ||
3192 | ept_sync_global(); | ||
3193 | |||
2849 | return 0; | 3194 | return 0; |
2850 | 3195 | ||
2851 | out2: | 3196 | out2: |
diff --git a/arch/x86/kvm/vmx.h b/arch/x86/kvm/vmx.h index 5dff4606b988..79d94c610dfe 100644 --- a/arch/x86/kvm/vmx.h +++ b/arch/x86/kvm/vmx.h | |||
@@ -35,6 +35,8 @@ | |||
35 | #define CPU_BASED_MWAIT_EXITING 0x00000400 | 35 | #define CPU_BASED_MWAIT_EXITING 0x00000400 |
36 | #define CPU_BASED_RDPMC_EXITING 0x00000800 | 36 | #define CPU_BASED_RDPMC_EXITING 0x00000800 |
37 | #define CPU_BASED_RDTSC_EXITING 0x00001000 | 37 | #define CPU_BASED_RDTSC_EXITING 0x00001000 |
38 | #define CPU_BASED_CR3_LOAD_EXITING 0x00008000 | ||
39 | #define CPU_BASED_CR3_STORE_EXITING 0x00010000 | ||
38 | #define CPU_BASED_CR8_LOAD_EXITING 0x00080000 | 40 | #define CPU_BASED_CR8_LOAD_EXITING 0x00080000 |
39 | #define CPU_BASED_CR8_STORE_EXITING 0x00100000 | 41 | #define CPU_BASED_CR8_STORE_EXITING 0x00100000 |
40 | #define CPU_BASED_TPR_SHADOW 0x00200000 | 42 | #define CPU_BASED_TPR_SHADOW 0x00200000 |
@@ -49,6 +51,7 @@ | |||
49 | * Definitions of Secondary Processor-Based VM-Execution Controls. | 51 | * Definitions of Secondary Processor-Based VM-Execution Controls. |
50 | */ | 52 | */ |
51 | #define SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES 0x00000001 | 53 | #define SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES 0x00000001 |
54 | #define SECONDARY_EXEC_ENABLE_EPT 0x00000002 | ||
52 | #define SECONDARY_EXEC_ENABLE_VPID 0x00000020 | 55 | #define SECONDARY_EXEC_ENABLE_VPID 0x00000020 |
53 | #define SECONDARY_EXEC_WBINVD_EXITING 0x00000040 | 56 | #define SECONDARY_EXEC_WBINVD_EXITING 0x00000040 |
54 | 57 | ||
@@ -100,10 +103,22 @@ enum vmcs_field { | |||
100 | VIRTUAL_APIC_PAGE_ADDR_HIGH = 0x00002013, | 103 | VIRTUAL_APIC_PAGE_ADDR_HIGH = 0x00002013, |
101 | APIC_ACCESS_ADDR = 0x00002014, | 104 | APIC_ACCESS_ADDR = 0x00002014, |
102 | APIC_ACCESS_ADDR_HIGH = 0x00002015, | 105 | APIC_ACCESS_ADDR_HIGH = 0x00002015, |
106 | EPT_POINTER = 0x0000201a, | ||
107 | EPT_POINTER_HIGH = 0x0000201b, | ||
108 | GUEST_PHYSICAL_ADDRESS = 0x00002400, | ||
109 | GUEST_PHYSICAL_ADDRESS_HIGH = 0x00002401, | ||
103 | VMCS_LINK_POINTER = 0x00002800, | 110 | VMCS_LINK_POINTER = 0x00002800, |
104 | VMCS_LINK_POINTER_HIGH = 0x00002801, | 111 | VMCS_LINK_POINTER_HIGH = 0x00002801, |
105 | GUEST_IA32_DEBUGCTL = 0x00002802, | 112 | GUEST_IA32_DEBUGCTL = 0x00002802, |
106 | GUEST_IA32_DEBUGCTL_HIGH = 0x00002803, | 113 | GUEST_IA32_DEBUGCTL_HIGH = 0x00002803, |
114 | GUEST_PDPTR0 = 0x0000280a, | ||
115 | GUEST_PDPTR0_HIGH = 0x0000280b, | ||
116 | GUEST_PDPTR1 = 0x0000280c, | ||
117 | GUEST_PDPTR1_HIGH = 0x0000280d, | ||
118 | GUEST_PDPTR2 = 0x0000280e, | ||
119 | GUEST_PDPTR2_HIGH = 0x0000280f, | ||
120 | GUEST_PDPTR3 = 0x00002810, | ||
121 | GUEST_PDPTR3_HIGH = 0x00002811, | ||
107 | PIN_BASED_VM_EXEC_CONTROL = 0x00004000, | 122 | PIN_BASED_VM_EXEC_CONTROL = 0x00004000, |
108 | CPU_BASED_VM_EXEC_CONTROL = 0x00004002, | 123 | CPU_BASED_VM_EXEC_CONTROL = 0x00004002, |
109 | EXCEPTION_BITMAP = 0x00004004, | 124 | EXCEPTION_BITMAP = 0x00004004, |
@@ -226,6 +241,8 @@ enum vmcs_field { | |||
226 | #define EXIT_REASON_MWAIT_INSTRUCTION 36 | 241 | #define EXIT_REASON_MWAIT_INSTRUCTION 36 |
227 | #define EXIT_REASON_TPR_BELOW_THRESHOLD 43 | 242 | #define EXIT_REASON_TPR_BELOW_THRESHOLD 43 |
228 | #define EXIT_REASON_APIC_ACCESS 44 | 243 | #define EXIT_REASON_APIC_ACCESS 44 |
244 | #define EXIT_REASON_EPT_VIOLATION 48 | ||
245 | #define EXIT_REASON_EPT_MISCONFIG 49 | ||
229 | #define EXIT_REASON_WBINVD 54 | 246 | #define EXIT_REASON_WBINVD 54 |
230 | 247 | ||
231 | /* | 248 | /* |
@@ -316,15 +333,36 @@ enum vmcs_field { | |||
316 | #define MSR_IA32_VMX_CR4_FIXED1 0x489 | 333 | #define MSR_IA32_VMX_CR4_FIXED1 0x489 |
317 | #define MSR_IA32_VMX_VMCS_ENUM 0x48a | 334 | #define MSR_IA32_VMX_VMCS_ENUM 0x48a |
318 | #define MSR_IA32_VMX_PROCBASED_CTLS2 0x48b | 335 | #define MSR_IA32_VMX_PROCBASED_CTLS2 0x48b |
336 | #define MSR_IA32_VMX_EPT_VPID_CAP 0x48c | ||
319 | 337 | ||
320 | #define MSR_IA32_FEATURE_CONTROL 0x3a | 338 | #define MSR_IA32_FEATURE_CONTROL 0x3a |
321 | #define MSR_IA32_FEATURE_CONTROL_LOCKED 0x1 | 339 | #define MSR_IA32_FEATURE_CONTROL_LOCKED 0x1 |
322 | #define MSR_IA32_FEATURE_CONTROL_VMXON_ENABLED 0x4 | 340 | #define MSR_IA32_FEATURE_CONTROL_VMXON_ENABLED 0x4 |
323 | 341 | ||
324 | #define APIC_ACCESS_PAGE_PRIVATE_MEMSLOT 9 | 342 | #define APIC_ACCESS_PAGE_PRIVATE_MEMSLOT 9 |
343 | #define IDENTITY_PAGETABLE_PRIVATE_MEMSLOT 10 | ||
325 | 344 | ||
326 | #define VMX_NR_VPIDS (1 << 16) | 345 | #define VMX_NR_VPIDS (1 << 16) |
327 | #define VMX_VPID_EXTENT_SINGLE_CONTEXT 1 | 346 | #define VMX_VPID_EXTENT_SINGLE_CONTEXT 1 |
328 | #define VMX_VPID_EXTENT_ALL_CONTEXT 2 | 347 | #define VMX_VPID_EXTENT_ALL_CONTEXT 2 |
329 | 348 | ||
349 | #define VMX_EPT_EXTENT_INDIVIDUAL_ADDR 0 | ||
350 | #define VMX_EPT_EXTENT_CONTEXT 1 | ||
351 | #define VMX_EPT_EXTENT_GLOBAL 2 | ||
352 | #define VMX_EPT_EXTENT_INDIVIDUAL_BIT (1ull << 24) | ||
353 | #define VMX_EPT_EXTENT_CONTEXT_BIT (1ull << 25) | ||
354 | #define VMX_EPT_EXTENT_GLOBAL_BIT (1ull << 26) | ||
355 | #define VMX_EPT_DEFAULT_GAW 3 | ||
356 | #define VMX_EPT_MAX_GAW 0x4 | ||
357 | #define VMX_EPT_MT_EPTE_SHIFT 3 | ||
358 | #define VMX_EPT_GAW_EPTP_SHIFT 3 | ||
359 | #define VMX_EPT_DEFAULT_MT 0x6ull | ||
360 | #define VMX_EPT_READABLE_MASK 0x1ull | ||
361 | #define VMX_EPT_WRITABLE_MASK 0x2ull | ||
362 | #define VMX_EPT_EXECUTABLE_MASK 0x4ull | ||
363 | #define VMX_EPT_FAKE_ACCESSED_MASK (1ull << 62) | ||
364 | #define VMX_EPT_FAKE_DIRTY_MASK (1ull << 63) | ||
365 | |||
366 | #define VMX_EPT_IDENTITY_PAGETABLE_ADDR 0xfffbc000ul | ||
367 | |||
330 | #endif | 368 | #endif |
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index 0ce556372a4d..21338bdb28ff 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c | |||
@@ -2417,6 +2417,9 @@ int kvm_arch_init(void *opaque) | |||
2417 | 2417 | ||
2418 | kvm_x86_ops = ops; | 2418 | kvm_x86_ops = ops; |
2419 | kvm_mmu_set_nonpresent_ptes(0ull, 0ull); | 2419 | kvm_mmu_set_nonpresent_ptes(0ull, 0ull); |
2420 | kvm_mmu_set_base_ptes(PT_PRESENT_MASK); | ||
2421 | kvm_mmu_set_mask_ptes(PT_USER_MASK, PT_ACCESSED_MASK, | ||
2422 | PT_DIRTY_MASK, PT64_NX_MASK, 0); | ||
2420 | return 0; | 2423 | return 0; |
2421 | 2424 | ||
2422 | out: | 2425 | out: |
@@ -3019,6 +3022,8 @@ int kvm_arch_vcpu_ioctl_set_regs(struct kvm_vcpu *vcpu, struct kvm_regs *regs) | |||
3019 | 3022 | ||
3020 | kvm_x86_ops->decache_regs(vcpu); | 3023 | kvm_x86_ops->decache_regs(vcpu); |
3021 | 3024 | ||
3025 | vcpu->arch.exception.pending = false; | ||
3026 | |||
3022 | vcpu_put(vcpu); | 3027 | vcpu_put(vcpu); |
3023 | 3028 | ||
3024 | return 0; | 3029 | return 0; |
@@ -3481,7 +3486,7 @@ int kvm_task_switch(struct kvm_vcpu *vcpu, u16 tss_selector, int reason) | |||
3481 | } | 3486 | } |
3482 | 3487 | ||
3483 | if (reason == TASK_SWITCH_IRET || reason == TASK_SWITCH_JMP) { | 3488 | if (reason == TASK_SWITCH_IRET || reason == TASK_SWITCH_JMP) { |
3484 | cseg_desc.type &= ~(1 << 8); //clear the B flag | 3489 | cseg_desc.type &= ~(1 << 1); //clear the B flag |
3485 | save_guest_segment_descriptor(vcpu, tr_seg.selector, | 3490 | save_guest_segment_descriptor(vcpu, tr_seg.selector, |
3486 | &cseg_desc); | 3491 | &cseg_desc); |
3487 | } | 3492 | } |
@@ -3507,7 +3512,7 @@ int kvm_task_switch(struct kvm_vcpu *vcpu, u16 tss_selector, int reason) | |||
3507 | } | 3512 | } |
3508 | 3513 | ||
3509 | if (reason != TASK_SWITCH_IRET) { | 3514 | if (reason != TASK_SWITCH_IRET) { |
3510 | nseg_desc.type |= (1 << 8); | 3515 | nseg_desc.type |= (1 << 1); |
3511 | save_guest_segment_descriptor(vcpu, tss_selector, | 3516 | save_guest_segment_descriptor(vcpu, tss_selector, |
3512 | &nseg_desc); | 3517 | &nseg_desc); |
3513 | } | 3518 | } |
@@ -3698,10 +3703,19 @@ void fx_init(struct kvm_vcpu *vcpu) | |||
3698 | { | 3703 | { |
3699 | unsigned after_mxcsr_mask; | 3704 | unsigned after_mxcsr_mask; |
3700 | 3705 | ||
3706 | /* | ||
3707 | * Touch the fpu the first time in non atomic context as if | ||
3708 | * this is the first fpu instruction the exception handler | ||
3709 | * will fire before the instruction returns and it'll have to | ||
3710 | * allocate ram with GFP_KERNEL. | ||
3711 | */ | ||
3712 | if (!used_math()) | ||
3713 | fx_save(&vcpu->arch.host_fx_image); | ||
3714 | |||
3701 | /* Initialize guest FPU by resetting ours and saving into guest's */ | 3715 | /* Initialize guest FPU by resetting ours and saving into guest's */ |
3702 | preempt_disable(); | 3716 | preempt_disable(); |
3703 | fx_save(&vcpu->arch.host_fx_image); | 3717 | fx_save(&vcpu->arch.host_fx_image); |
3704 | fpu_init(); | 3718 | fx_finit(); |
3705 | fx_save(&vcpu->arch.guest_fx_image); | 3719 | fx_save(&vcpu->arch.guest_fx_image); |
3706 | fx_restore(&vcpu->arch.host_fx_image); | 3720 | fx_restore(&vcpu->arch.host_fx_image); |
3707 | preempt_enable(); | 3721 | preempt_enable(); |
@@ -3906,6 +3920,8 @@ void kvm_arch_destroy_vm(struct kvm *kvm) | |||
3906 | kvm_free_physmem(kvm); | 3920 | kvm_free_physmem(kvm); |
3907 | if (kvm->arch.apic_access_page) | 3921 | if (kvm->arch.apic_access_page) |
3908 | put_page(kvm->arch.apic_access_page); | 3922 | put_page(kvm->arch.apic_access_page); |
3923 | if (kvm->arch.ept_identity_pagetable) | ||
3924 | put_page(kvm->arch.ept_identity_pagetable); | ||
3909 | kfree(kvm); | 3925 | kfree(kvm); |
3910 | } | 3926 | } |
3911 | 3927 | ||
diff --git a/arch/x86/kvm/x86_emulate.c b/arch/x86/kvm/x86_emulate.c index 2ca08386f993..f2a696d6a243 100644 --- a/arch/x86/kvm/x86_emulate.c +++ b/arch/x86/kvm/x86_emulate.c | |||
@@ -1761,6 +1761,7 @@ twobyte_insn: | |||
1761 | case 6: /* lmsw */ | 1761 | case 6: /* lmsw */ |
1762 | realmode_lmsw(ctxt->vcpu, (u16)c->src.val, | 1762 | realmode_lmsw(ctxt->vcpu, (u16)c->src.val, |
1763 | &ctxt->eflags); | 1763 | &ctxt->eflags); |
1764 | c->dst.type = OP_NONE; | ||
1764 | break; | 1765 | break; |
1765 | case 7: /* invlpg*/ | 1766 | case 7: /* invlpg*/ |
1766 | emulate_invlpg(ctxt->vcpu, memop); | 1767 | emulate_invlpg(ctxt->vcpu, memop); |
diff --git a/arch/x86/mm/discontig_32.c b/arch/x86/mm/discontig_32.c index 18378850e25a..914ccf983687 100644 --- a/arch/x86/mm/discontig_32.c +++ b/arch/x86/mm/discontig_32.c | |||
@@ -476,29 +476,3 @@ int memory_add_physaddr_to_nid(u64 addr) | |||
476 | 476 | ||
477 | EXPORT_SYMBOL_GPL(memory_add_physaddr_to_nid); | 477 | EXPORT_SYMBOL_GPL(memory_add_physaddr_to_nid); |
478 | #endif | 478 | #endif |
479 | |||
480 | #ifndef CONFIG_HAVE_ARCH_PARSE_SRAT | ||
481 | /* | ||
482 | * XXX FIXME: Make SLIT table parsing available to 32-bit NUMA | ||
483 | * | ||
484 | * These stub functions are needed to compile 32-bit NUMA when SRAT is | ||
485 | * not set. There are functions in srat_64.c for parsing this table | ||
486 | * and it may be possible to make them common functions. | ||
487 | */ | ||
488 | void acpi_numa_slit_init (struct acpi_table_slit *slit) | ||
489 | { | ||
490 | printk(KERN_INFO "ACPI: No support for parsing SLIT table\n"); | ||
491 | } | ||
492 | |||
493 | void acpi_numa_processor_affinity_init (struct acpi_srat_cpu_affinity *pa) | ||
494 | { | ||
495 | } | ||
496 | |||
497 | void acpi_numa_memory_affinity_init (struct acpi_srat_mem_affinity *ma) | ||
498 | { | ||
499 | } | ||
500 | |||
501 | void acpi_numa_arch_fixup(void) | ||
502 | { | ||
503 | } | ||
504 | #endif /* CONFIG_HAVE_ARCH_PARSE_SRAT */ | ||
diff --git a/arch/x86/mm/pgtable_32.c b/arch/x86/mm/pgtable_32.c index 9ee007be9142..369cf065b6a4 100644 --- a/arch/x86/mm/pgtable_32.c +++ b/arch/x86/mm/pgtable_32.c | |||
@@ -172,10 +172,3 @@ void reserve_top_address(unsigned long reserve) | |||
172 | __FIXADDR_TOP = -reserve - PAGE_SIZE; | 172 | __FIXADDR_TOP = -reserve - PAGE_SIZE; |
173 | __VMALLOC_RESERVE += reserve; | 173 | __VMALLOC_RESERVE += reserve; |
174 | } | 174 | } |
175 | |||
176 | int pmd_bad(pmd_t pmd) | ||
177 | { | ||
178 | WARN_ON_ONCE(pmd_bad_v1(pmd) != pmd_bad_v2(pmd)); | ||
179 | |||
180 | return pmd_bad_v1(pmd); | ||
181 | } | ||
diff --git a/arch/x86/pci/Makefile_32 b/arch/x86/pci/Makefile_32 index 7fa519868d70..89ec35d00efd 100644 --- a/arch/x86/pci/Makefile_32 +++ b/arch/x86/pci/Makefile_32 | |||
@@ -6,11 +6,19 @@ obj-$(CONFIG_PCI_DIRECT) += direct.o | |||
6 | obj-$(CONFIG_PCI_OLPC) += olpc.o | 6 | obj-$(CONFIG_PCI_OLPC) += olpc.o |
7 | 7 | ||
8 | pci-y := fixup.o | 8 | pci-y := fixup.o |
9 | |||
10 | # Do not change the ordering here. There is a nasty init function | ||
11 | # ordering dependency which breaks when you move acpi.o below | ||
12 | # legacy/irq.o | ||
9 | pci-$(CONFIG_ACPI) += acpi.o | 13 | pci-$(CONFIG_ACPI) += acpi.o |
10 | pci-y += legacy.o irq.o | 14 | pci-y += legacy.o irq.o |
11 | 15 | ||
12 | pci-$(CONFIG_X86_VISWS) += visws.o fixup.o | 16 | # Careful: VISWS and NUMAQ overrule the pci-y above. The colons are |
13 | pci-$(CONFIG_X86_NUMAQ) += numa.o irq.o | 17 | # therefor correct. This needs a proper fix by distangling the code. |
18 | pci-$(CONFIG_X86_VISWS) := visws.o fixup.o | ||
19 | pci-$(CONFIG_X86_NUMAQ) := numa.o irq.o | ||
20 | |||
21 | # Necessary for NUMAQ as well | ||
14 | pci-$(CONFIG_NUMA) += mp_bus_to_node.o | 22 | pci-$(CONFIG_NUMA) += mp_bus_to_node.o |
15 | 23 | ||
16 | obj-y += $(pci-y) common.o early.o | 24 | obj-y += $(pci-y) common.o early.o |
diff --git a/arch/x86/pci/acpi.c b/arch/x86/pci/acpi.c index 1a9c0c6a1a18..d95de2f199cd 100644 --- a/arch/x86/pci/acpi.c +++ b/arch/x86/pci/acpi.c | |||
@@ -6,45 +6,6 @@ | |||
6 | #include <asm/numa.h> | 6 | #include <asm/numa.h> |
7 | #include "pci.h" | 7 | #include "pci.h" |
8 | 8 | ||
9 | static int __devinit can_skip_ioresource_align(const struct dmi_system_id *d) | ||
10 | { | ||
11 | pci_probe |= PCI_CAN_SKIP_ISA_ALIGN; | ||
12 | printk(KERN_INFO "PCI: %s detected, can skip ISA alignment\n", d->ident); | ||
13 | return 0; | ||
14 | } | ||
15 | |||
16 | static struct dmi_system_id acpi_pciprobe_dmi_table[] __devinitdata = { | ||
17 | /* | ||
18 | * Systems where PCI IO resource ISA alignment can be skipped | ||
19 | * when the ISA enable bit in the bridge control is not set | ||
20 | */ | ||
21 | { | ||
22 | .callback = can_skip_ioresource_align, | ||
23 | .ident = "IBM System x3800", | ||
24 | .matches = { | ||
25 | DMI_MATCH(DMI_SYS_VENDOR, "IBM"), | ||
26 | DMI_MATCH(DMI_PRODUCT_NAME, "x3800"), | ||
27 | }, | ||
28 | }, | ||
29 | { | ||
30 | .callback = can_skip_ioresource_align, | ||
31 | .ident = "IBM System x3850", | ||
32 | .matches = { | ||
33 | DMI_MATCH(DMI_SYS_VENDOR, "IBM"), | ||
34 | DMI_MATCH(DMI_PRODUCT_NAME, "x3850"), | ||
35 | }, | ||
36 | }, | ||
37 | { | ||
38 | .callback = can_skip_ioresource_align, | ||
39 | .ident = "IBM System x3950", | ||
40 | .matches = { | ||
41 | DMI_MATCH(DMI_SYS_VENDOR, "IBM"), | ||
42 | DMI_MATCH(DMI_PRODUCT_NAME, "x3950"), | ||
43 | }, | ||
44 | }, | ||
45 | {} | ||
46 | }; | ||
47 | |||
48 | struct pci_root_info { | 9 | struct pci_root_info { |
49 | char *name; | 10 | char *name; |
50 | unsigned int res_num; | 11 | unsigned int res_num; |
@@ -196,8 +157,6 @@ struct pci_bus * __devinit pci_acpi_scan_root(struct acpi_device *device, int do | |||
196 | int pxm; | 157 | int pxm; |
197 | #endif | 158 | #endif |
198 | 159 | ||
199 | dmi_check_system(acpi_pciprobe_dmi_table); | ||
200 | |||
201 | if (domain && !pci_domains_supported) { | 160 | if (domain && !pci_domains_supported) { |
202 | printk(KERN_WARNING "PCI: Multiple domains not supported " | 161 | printk(KERN_WARNING "PCI: Multiple domains not supported " |
203 | "(dom %d, bus %d)\n", domain, busnum); | 162 | "(dom %d, bus %d)\n", domain, busnum); |
diff --git a/arch/x86/pci/common.c b/arch/x86/pci/common.c index 2a4d751818b7..8545c8a9d107 100644 --- a/arch/x86/pci/common.c +++ b/arch/x86/pci/common.c | |||
@@ -77,17 +77,48 @@ int pcibios_scanned; | |||
77 | */ | 77 | */ |
78 | DEFINE_SPINLOCK(pci_config_lock); | 78 | DEFINE_SPINLOCK(pci_config_lock); |
79 | 79 | ||
80 | static void __devinit pcibios_fixup_device_resources(struct pci_dev *dev) | 80 | static int __devinit can_skip_ioresource_align(const struct dmi_system_id *d) |
81 | { | 81 | { |
82 | struct resource *rom_r = &dev->resource[PCI_ROM_RESOURCE]; | 82 | pci_probe |= PCI_CAN_SKIP_ISA_ALIGN; |
83 | 83 | printk(KERN_INFO "PCI: %s detected, can skip ISA alignment\n", d->ident); | |
84 | if (rom_r->parent) | 84 | return 0; |
85 | return; | 85 | } |
86 | if (rom_r->start) | 86 | |
87 | /* we deal with BIOS assigned ROM later */ | 87 | static struct dmi_system_id can_skip_pciprobe_dmi_table[] __devinitdata = { |
88 | return; | 88 | /* |
89 | if (!(pci_probe & PCI_ASSIGN_ROMS)) | 89 | * Systems where PCI IO resource ISA alignment can be skipped |
90 | rom_r->start = rom_r->end = rom_r->flags = 0; | 90 | * when the ISA enable bit in the bridge control is not set |
91 | */ | ||
92 | { | ||
93 | .callback = can_skip_ioresource_align, | ||
94 | .ident = "IBM System x3800", | ||
95 | .matches = { | ||
96 | DMI_MATCH(DMI_SYS_VENDOR, "IBM"), | ||
97 | DMI_MATCH(DMI_PRODUCT_NAME, "x3800"), | ||
98 | }, | ||
99 | }, | ||
100 | { | ||
101 | .callback = can_skip_ioresource_align, | ||
102 | .ident = "IBM System x3850", | ||
103 | .matches = { | ||
104 | DMI_MATCH(DMI_SYS_VENDOR, "IBM"), | ||
105 | DMI_MATCH(DMI_PRODUCT_NAME, "x3850"), | ||
106 | }, | ||
107 | }, | ||
108 | { | ||
109 | .callback = can_skip_ioresource_align, | ||
110 | .ident = "IBM System x3950", | ||
111 | .matches = { | ||
112 | DMI_MATCH(DMI_SYS_VENDOR, "IBM"), | ||
113 | DMI_MATCH(DMI_PRODUCT_NAME, "x3950"), | ||
114 | }, | ||
115 | }, | ||
116 | {} | ||
117 | }; | ||
118 | |||
119 | void __init dmi_check_skip_isa_align(void) | ||
120 | { | ||
121 | dmi_check_system(can_skip_pciprobe_dmi_table); | ||
91 | } | 122 | } |
92 | 123 | ||
93 | /* | 124 | /* |
@@ -97,11 +128,7 @@ static void __devinit pcibios_fixup_device_resources(struct pci_dev *dev) | |||
97 | 128 | ||
98 | void __devinit pcibios_fixup_bus(struct pci_bus *b) | 129 | void __devinit pcibios_fixup_bus(struct pci_bus *b) |
99 | { | 130 | { |
100 | struct pci_dev *dev; | ||
101 | |||
102 | pci_read_bridge_bases(b); | 131 | pci_read_bridge_bases(b); |
103 | list_for_each_entry(dev, &b->devices, bus_list) | ||
104 | pcibios_fixup_device_resources(dev); | ||
105 | } | 132 | } |
106 | 133 | ||
107 | /* | 134 | /* |
@@ -318,13 +345,16 @@ static struct dmi_system_id __devinitdata pciprobe_dmi_table[] = { | |||
318 | {} | 345 | {} |
319 | }; | 346 | }; |
320 | 347 | ||
348 | void __init dmi_check_pciprobe(void) | ||
349 | { | ||
350 | dmi_check_system(pciprobe_dmi_table); | ||
351 | } | ||
352 | |||
321 | struct pci_bus * __devinit pcibios_scan_root(int busnum) | 353 | struct pci_bus * __devinit pcibios_scan_root(int busnum) |
322 | { | 354 | { |
323 | struct pci_bus *bus = NULL; | 355 | struct pci_bus *bus = NULL; |
324 | struct pci_sysdata *sd; | 356 | struct pci_sysdata *sd; |
325 | 357 | ||
326 | dmi_check_system(pciprobe_dmi_table); | ||
327 | |||
328 | while ((bus = pci_find_next_bus(bus)) != NULL) { | 358 | while ((bus = pci_find_next_bus(bus)) != NULL) { |
329 | if (bus->number == busnum) { | 359 | if (bus->number == busnum) { |
330 | /* Already scanned */ | 360 | /* Already scanned */ |
@@ -462,6 +492,9 @@ char * __devinit pcibios_setup(char *str) | |||
462 | } else if (!strcmp(str, "routeirq")) { | 492 | } else if (!strcmp(str, "routeirq")) { |
463 | pci_routeirq = 1; | 493 | pci_routeirq = 1; |
464 | return NULL; | 494 | return NULL; |
495 | } else if (!strcmp(str, "skip_isa_align")) { | ||
496 | pci_probe |= PCI_CAN_SKIP_ISA_ALIGN; | ||
497 | return NULL; | ||
465 | } | 498 | } |
466 | return str; | 499 | return str; |
467 | } | 500 | } |
@@ -489,7 +522,7 @@ void pcibios_disable_device (struct pci_dev *dev) | |||
489 | pcibios_disable_irq(dev); | 522 | pcibios_disable_irq(dev); |
490 | } | 523 | } |
491 | 524 | ||
492 | struct pci_bus *pci_scan_bus_on_node(int busno, struct pci_ops *ops, int node) | 525 | struct pci_bus * __devinit pci_scan_bus_on_node(int busno, struct pci_ops *ops, int node) |
493 | { | 526 | { |
494 | struct pci_bus *bus = NULL; | 527 | struct pci_bus *bus = NULL; |
495 | struct pci_sysdata *sd; | 528 | struct pci_sysdata *sd; |
@@ -512,7 +545,7 @@ struct pci_bus *pci_scan_bus_on_node(int busno, struct pci_ops *ops, int node) | |||
512 | return bus; | 545 | return bus; |
513 | } | 546 | } |
514 | 547 | ||
515 | struct pci_bus *pci_scan_bus_with_sysdata(int busno) | 548 | struct pci_bus * __devinit pci_scan_bus_with_sysdata(int busno) |
516 | { | 549 | { |
517 | return pci_scan_bus_on_node(busno, &pci_root_ops, -1); | 550 | return pci_scan_bus_on_node(busno, &pci_root_ops, -1); |
518 | } | 551 | } |
diff --git a/arch/x86/pci/fixup.c b/arch/x86/pci/fixup.c index b60b2abd480c..ff3a6a336342 100644 --- a/arch/x86/pci/fixup.c +++ b/arch/x86/pci/fixup.c | |||
@@ -502,7 +502,7 @@ DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_SIEMENS, 0x0015, | |||
502 | */ | 502 | */ |
503 | static void fam10h_pci_cfg_space_size(struct pci_dev *dev) | 503 | static void fam10h_pci_cfg_space_size(struct pci_dev *dev) |
504 | { | 504 | { |
505 | dev->cfg_size = pci_cfg_space_size_ext(dev, 0); | 505 | dev->cfg_size = pci_cfg_space_size_ext(dev); |
506 | } | 506 | } |
507 | 507 | ||
508 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AMD, 0x1200, fam10h_pci_cfg_space_size); | 508 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AMD, 0x1200, fam10h_pci_cfg_space_size); |
diff --git a/arch/x86/pci/init.c b/arch/x86/pci/init.c index dd30c6076b5d..e70b9c57b88e 100644 --- a/arch/x86/pci/init.c +++ b/arch/x86/pci/init.c | |||
@@ -33,6 +33,10 @@ static __init int pci_access_init(void) | |||
33 | printk(KERN_ERR | 33 | printk(KERN_ERR |
34 | "PCI: Fatal: No config space access function found\n"); | 34 | "PCI: Fatal: No config space access function found\n"); |
35 | 35 | ||
36 | dmi_check_pciprobe(); | ||
37 | |||
38 | dmi_check_skip_isa_align(); | ||
39 | |||
36 | return 0; | 40 | return 0; |
37 | } | 41 | } |
38 | arch_initcall(pci_access_init); | 42 | arch_initcall(pci_access_init); |
diff --git a/arch/x86/pci/pci.h b/arch/x86/pci/pci.h index c58805a92db5..f3972b12c60a 100644 --- a/arch/x86/pci/pci.h +++ b/arch/x86/pci/pci.h | |||
@@ -38,6 +38,9 @@ enum pci_bf_sort_state { | |||
38 | pci_dmi_bf, | 38 | pci_dmi_bf, |
39 | }; | 39 | }; |
40 | 40 | ||
41 | extern void __init dmi_check_pciprobe(void); | ||
42 | extern void __init dmi_check_skip_isa_align(void); | ||
43 | |||
41 | /* pci-i386.c */ | 44 | /* pci-i386.c */ |
42 | 45 | ||
43 | extern unsigned int pcibios_max_latency; | 46 | extern unsigned int pcibios_max_latency; |
diff --git a/arch/x86/vdso/vdso32-setup.c b/arch/x86/vdso/vdso32-setup.c index 4dceeb1fc5e0..cf058fecfcee 100644 --- a/arch/x86/vdso/vdso32-setup.c +++ b/arch/x86/vdso/vdso32-setup.c | |||
@@ -162,7 +162,7 @@ static __init void relocate_vdso(Elf32_Ehdr *ehdr) | |||
162 | Elf32_Shdr *shdr; | 162 | Elf32_Shdr *shdr; |
163 | int i; | 163 | int i; |
164 | 164 | ||
165 | BUG_ON(memcmp(ehdr->e_ident, ELFMAG, 4) != 0 || | 165 | BUG_ON(memcmp(ehdr->e_ident, ELFMAG, SELFMAG) != 0 || |
166 | !elf_check_arch_ia32(ehdr) || | 166 | !elf_check_arch_ia32(ehdr) || |
167 | ehdr->e_type != ET_DYN); | 167 | ehdr->e_type != ET_DYN); |
168 | 168 | ||
diff --git a/arch/x86/video/fbdev.c b/arch/x86/video/fbdev.c index 4db42bff8c60..69527688f794 100644 --- a/arch/x86/video/fbdev.c +++ b/arch/x86/video/fbdev.c | |||
@@ -1,5 +1,4 @@ | |||
1 | /* | 1 | /* |
2 | * | ||
3 | * Copyright (C) 2007 Antonino Daplas <adaplas@gmail.com> | 2 | * Copyright (C) 2007 Antonino Daplas <adaplas@gmail.com> |
4 | * | 3 | * |
5 | * This file is subject to the terms and conditions of the GNU General Public | 4 | * This file is subject to the terms and conditions of the GNU General Public |
@@ -29,3 +28,4 @@ int fb_is_primary_device(struct fb_info *info) | |||
29 | return retval; | 28 | return retval; |
30 | } | 29 | } |
31 | EXPORT_SYMBOL(fb_is_primary_device); | 30 | EXPORT_SYMBOL(fb_is_primary_device); |
31 | MODULE_LICENSE("GPL"); | ||