diff options
Diffstat (limited to 'include/asm-i386')
| -rw-r--r-- | include/asm-i386/acpi.h | 10 | ||||
| -rw-r--r-- | include/asm-i386/alternative.h | 129 | ||||
| -rw-r--r-- | include/asm-i386/arch_hooks.h | 3 | ||||
| -rw-r--r-- | include/asm-i386/atomic.h | 36 | ||||
| -rw-r--r-- | include/asm-i386/bitops.h | 7 | ||||
| -rw-r--r-- | include/asm-i386/cache.h | 2 | ||||
| -rw-r--r-- | include/asm-i386/cpufeature.h | 1 | ||||
| -rw-r--r-- | include/asm-i386/mach-default/do_timer.h | 2 | ||||
| -rw-r--r-- | include/asm-i386/mach-es7000/mach_mpparse.h | 10 | ||||
| -rw-r--r-- | include/asm-i386/mach-visws/do_timer.h | 2 | ||||
| -rw-r--r-- | include/asm-i386/mach-voyager/do_timer.h | 2 | ||||
| -rw-r--r-- | include/asm-i386/mpspec.h | 1 | ||||
| -rw-r--r-- | include/asm-i386/mtrr.h | 1 | ||||
| -rw-r--r-- | include/asm-i386/mutex.h | 6 | ||||
| -rw-r--r-- | include/asm-i386/pgtable-2level.h | 2 | ||||
| -rw-r--r-- | include/asm-i386/pgtable-3level.h | 2 | ||||
| -rw-r--r-- | include/asm-i386/pgtable.h | 5 | ||||
| -rw-r--r-- | include/asm-i386/rwlock.h | 56 | ||||
| -rw-r--r-- | include/asm-i386/semaphore.h | 8 | ||||
| -rw-r--r-- | include/asm-i386/spinlock.h | 34 | ||||
| -rw-r--r-- | include/asm-i386/system.h | 62 | ||||
| -rw-r--r-- | include/asm-i386/uaccess.h | 12 | ||||
| -rw-r--r-- | include/asm-i386/unistd.h | 36 |
23 files changed, 267 insertions, 162 deletions
diff --git a/include/asm-i386/acpi.h b/include/asm-i386/acpi.h index 55059abf9c95..20f523954218 100644 --- a/include/asm-i386/acpi.h +++ b/include/asm-i386/acpi.h | |||
| @@ -103,6 +103,12 @@ __acpi_release_global_lock (unsigned int *lock) | |||
| 103 | :"=r"(n_hi), "=r"(n_lo) \ | 103 | :"=r"(n_hi), "=r"(n_lo) \ |
| 104 | :"0"(n_hi), "1"(n_lo)) | 104 | :"0"(n_hi), "1"(n_lo)) |
| 105 | 105 | ||
| 106 | #ifdef CONFIG_X86_IO_APIC | ||
| 107 | extern void check_acpi_pci(void); | ||
| 108 | #else | ||
| 109 | static inline void check_acpi_pci(void) { } | ||
| 110 | #endif | ||
| 111 | |||
| 106 | #ifdef CONFIG_ACPI | 112 | #ifdef CONFIG_ACPI |
| 107 | extern int acpi_lapic; | 113 | extern int acpi_lapic; |
| 108 | extern int acpi_ioapic; | 114 | extern int acpi_ioapic; |
| @@ -128,8 +134,6 @@ extern int acpi_gsi_to_irq(u32 gsi, unsigned int *irq); | |||
| 128 | extern int skip_ioapic_setup; | 134 | extern int skip_ioapic_setup; |
| 129 | extern int acpi_skip_timer_override; | 135 | extern int acpi_skip_timer_override; |
| 130 | 136 | ||
| 131 | extern void check_acpi_pci(void); | ||
| 132 | |||
| 133 | static inline void disable_ioapic_setup(void) | 137 | static inline void disable_ioapic_setup(void) |
| 134 | { | 138 | { |
| 135 | skip_ioapic_setup = 1; | 139 | skip_ioapic_setup = 1; |
| @@ -142,8 +146,6 @@ static inline int ioapic_setup_disabled(void) | |||
| 142 | 146 | ||
| 143 | #else | 147 | #else |
| 144 | static inline void disable_ioapic_setup(void) { } | 148 | static inline void disable_ioapic_setup(void) { } |
| 145 | static inline void check_acpi_pci(void) { } | ||
| 146 | |||
| 147 | #endif | 149 | #endif |
| 148 | 150 | ||
| 149 | static inline void acpi_noirq_set(void) { acpi_noirq = 1; } | 151 | static inline void acpi_noirq_set(void) { acpi_noirq = 1; } |
diff --git a/include/asm-i386/alternative.h b/include/asm-i386/alternative.h new file mode 100644 index 000000000000..e201decea0c9 --- /dev/null +++ b/include/asm-i386/alternative.h | |||
| @@ -0,0 +1,129 @@ | |||
| 1 | #ifndef _I386_ALTERNATIVE_H | ||
| 2 | #define _I386_ALTERNATIVE_H | ||
| 3 | |||
| 4 | #ifdef __KERNEL__ | ||
| 5 | |||
| 6 | struct alt_instr { | ||
| 7 | u8 *instr; /* original instruction */ | ||
| 8 | u8 *replacement; | ||
| 9 | u8 cpuid; /* cpuid bit set for replacement */ | ||
| 10 | u8 instrlen; /* length of original instruction */ | ||
| 11 | u8 replacementlen; /* length of new instruction, <= instrlen */ | ||
| 12 | u8 pad; | ||
| 13 | }; | ||
| 14 | |||
| 15 | extern void apply_alternatives(struct alt_instr *start, struct alt_instr *end); | ||
| 16 | |||
| 17 | struct module; | ||
| 18 | extern void alternatives_smp_module_add(struct module *mod, char *name, | ||
| 19 | void *locks, void *locks_end, | ||
| 20 | void *text, void *text_end); | ||
| 21 | extern void alternatives_smp_module_del(struct module *mod); | ||
| 22 | extern void alternatives_smp_switch(int smp); | ||
| 23 | |||
| 24 | #endif | ||
| 25 | |||
| 26 | /* | ||
| 27 | * Alternative instructions for different CPU types or capabilities. | ||
| 28 | * | ||
| 29 | * This allows to use optimized instructions even on generic binary | ||
| 30 | * kernels. | ||
| 31 | * | ||
| 32 | * length of oldinstr must be longer or equal the length of newinstr | ||
| 33 | * It can be padded with nops as needed. | ||
| 34 | * | ||
| 35 | * For non barrier like inlines please define new variants | ||
| 36 | * without volatile and memory clobber. | ||
| 37 | */ | ||
| 38 | #define alternative(oldinstr, newinstr, feature) \ | ||
| 39 | asm volatile ("661:\n\t" oldinstr "\n662:\n" \ | ||
| 40 | ".section .altinstructions,\"a\"\n" \ | ||
| 41 | " .align 4\n" \ | ||
| 42 | " .long 661b\n" /* label */ \ | ||
| 43 | " .long 663f\n" /* new instruction */ \ | ||
| 44 | " .byte %c0\n" /* feature bit */ \ | ||
| 45 | " .byte 662b-661b\n" /* sourcelen */ \ | ||
| 46 | " .byte 664f-663f\n" /* replacementlen */ \ | ||
| 47 | ".previous\n" \ | ||
| 48 | ".section .altinstr_replacement,\"ax\"\n" \ | ||
| 49 | "663:\n\t" newinstr "\n664:\n" /* replacement */\ | ||
| 50 | ".previous" :: "i" (feature) : "memory") | ||
| 51 | |||
| 52 | /* | ||
| 53 | * Alternative inline assembly with input. | ||
| 54 | * | ||
| 55 | * Pecularities: | ||
| 56 | * No memory clobber here. | ||
| 57 | * Argument numbers start with 1. | ||
| 58 | * Best is to use constraints that are fixed size (like (%1) ... "r") | ||
| 59 | * If you use variable sized constraints like "m" or "g" in the | ||
| 60 | * replacement maake sure to pad to the worst case length. | ||
| 61 | */ | ||
| 62 | #define alternative_input(oldinstr, newinstr, feature, input...) \ | ||
| 63 | asm volatile ("661:\n\t" oldinstr "\n662:\n" \ | ||
| 64 | ".section .altinstructions,\"a\"\n" \ | ||
| 65 | " .align 4\n" \ | ||
| 66 | " .long 661b\n" /* label */ \ | ||
| 67 | " .long 663f\n" /* new instruction */ \ | ||
| 68 | " .byte %c0\n" /* feature bit */ \ | ||
| 69 | " .byte 662b-661b\n" /* sourcelen */ \ | ||
| 70 | " .byte 664f-663f\n" /* replacementlen */ \ | ||
| 71 | ".previous\n" \ | ||
| 72 | ".section .altinstr_replacement,\"ax\"\n" \ | ||
| 73 | "663:\n\t" newinstr "\n664:\n" /* replacement */\ | ||
| 74 | ".previous" :: "i" (feature), ##input) | ||
| 75 | |||
| 76 | /* | ||
| 77 | * Alternative inline assembly for SMP. | ||
| 78 | * | ||
| 79 | * alternative_smp() takes two versions (SMP first, UP second) and is | ||
| 80 | * for more complex stuff such as spinlocks. | ||
| 81 | * | ||
| 82 | * The LOCK_PREFIX macro defined here replaces the LOCK and | ||
| 83 | * LOCK_PREFIX macros used everywhere in the source tree. | ||
| 84 | * | ||
| 85 | * SMP alternatives use the same data structures as the other | ||
| 86 | * alternatives and the X86_FEATURE_UP flag to indicate the case of a | ||
| 87 | * UP system running a SMP kernel. The existing apply_alternatives() | ||
| 88 | * works fine for patching a SMP kernel for UP. | ||
| 89 | * | ||
| 90 | * The SMP alternative tables can be kept after boot and contain both | ||
| 91 | * UP and SMP versions of the instructions to allow switching back to | ||
| 92 | * SMP at runtime, when hotplugging in a new CPU, which is especially | ||
| 93 | * useful in virtualized environments. | ||
| 94 | * | ||
| 95 | * The very common lock prefix is handled as special case in a | ||
| 96 | * separate table which is a pure address list without replacement ptr | ||
| 97 | * and size information. That keeps the table sizes small. | ||
| 98 | */ | ||
| 99 | |||
| 100 | #ifdef CONFIG_SMP | ||
| 101 | #define alternative_smp(smpinstr, upinstr, args...) \ | ||
| 102 | asm volatile ("661:\n\t" smpinstr "\n662:\n" \ | ||
| 103 | ".section .smp_altinstructions,\"a\"\n" \ | ||
| 104 | " .align 4\n" \ | ||
| 105 | " .long 661b\n" /* label */ \ | ||
| 106 | " .long 663f\n" /* new instruction */ \ | ||
| 107 | " .byte 0x68\n" /* X86_FEATURE_UP */ \ | ||
| 108 | " .byte 662b-661b\n" /* sourcelen */ \ | ||
| 109 | " .byte 664f-663f\n" /* replacementlen */ \ | ||
| 110 | ".previous\n" \ | ||
| 111 | ".section .smp_altinstr_replacement,\"awx\"\n" \ | ||
| 112 | "663:\n\t" upinstr "\n" /* replacement */ \ | ||
| 113 | "664:\n\t.fill 662b-661b,1,0x42\n" /* space for original */ \ | ||
| 114 | ".previous" : args) | ||
| 115 | |||
| 116 | #define LOCK_PREFIX \ | ||
| 117 | ".section .smp_locks,\"a\"\n" \ | ||
| 118 | " .align 4\n" \ | ||
| 119 | " .long 661f\n" /* address */ \ | ||
| 120 | ".previous\n" \ | ||
| 121 | "661:\n\tlock; " | ||
| 122 | |||
| 123 | #else /* ! CONFIG_SMP */ | ||
| 124 | #define alternative_smp(smpinstr, upinstr, args...) \ | ||
| 125 | asm volatile (upinstr : args) | ||
| 126 | #define LOCK_PREFIX "" | ||
| 127 | #endif | ||
| 128 | |||
| 129 | #endif /* _I386_ALTERNATIVE_H */ | ||
diff --git a/include/asm-i386/arch_hooks.h b/include/asm-i386/arch_hooks.h index 28b96a6fb9fa..238cf4275b96 100644 --- a/include/asm-i386/arch_hooks.h +++ b/include/asm-i386/arch_hooks.h | |||
| @@ -24,4 +24,7 @@ extern void trap_init_hook(void); | |||
| 24 | extern void time_init_hook(void); | 24 | extern void time_init_hook(void); |
| 25 | extern void mca_nmi_hook(void); | 25 | extern void mca_nmi_hook(void); |
| 26 | 26 | ||
| 27 | extern int setup_early_printk(char *); | ||
| 28 | extern void early_printk(const char *fmt, ...) __attribute__((format(printf,1,2))); | ||
| 29 | |||
| 27 | #endif | 30 | #endif |
diff --git a/include/asm-i386/atomic.h b/include/asm-i386/atomic.h index de649d3aa2d4..22d80ece95cb 100644 --- a/include/asm-i386/atomic.h +++ b/include/asm-i386/atomic.h | |||
| @@ -10,12 +10,6 @@ | |||
| 10 | * resource counting etc.. | 10 | * resource counting etc.. |
| 11 | */ | 11 | */ |
| 12 | 12 | ||
| 13 | #ifdef CONFIG_SMP | ||
| 14 | #define LOCK "lock ; " | ||
| 15 | #else | ||
| 16 | #define LOCK "" | ||
| 17 | #endif | ||
| 18 | |||
| 19 | /* | 13 | /* |
| 20 | * Make sure gcc doesn't try to be clever and move things around | 14 | * Make sure gcc doesn't try to be clever and move things around |
| 21 | * on us. We need to use _exactly_ the address the user gave us, | 15 | * on us. We need to use _exactly_ the address the user gave us, |
| @@ -52,7 +46,7 @@ typedef struct { volatile int counter; } atomic_t; | |||
| 52 | static __inline__ void atomic_add(int i, atomic_t *v) | 46 | static __inline__ void atomic_add(int i, atomic_t *v) |
| 53 | { | 47 | { |
| 54 | __asm__ __volatile__( | 48 | __asm__ __volatile__( |
| 55 | LOCK "addl %1,%0" | 49 | LOCK_PREFIX "addl %1,%0" |
| 56 | :"=m" (v->counter) | 50 | :"=m" (v->counter) |
| 57 | :"ir" (i), "m" (v->counter)); | 51 | :"ir" (i), "m" (v->counter)); |
| 58 | } | 52 | } |
| @@ -67,7 +61,7 @@ static __inline__ void atomic_add(int i, atomic_t *v) | |||
| 67 | static __inline__ void atomic_sub(int i, atomic_t *v) | 61 | static __inline__ void atomic_sub(int i, atomic_t *v) |
| 68 | { | 62 | { |
| 69 | __asm__ __volatile__( | 63 | __asm__ __volatile__( |
| 70 | LOCK "subl %1,%0" | 64 | LOCK_PREFIX "subl %1,%0" |
| 71 | :"=m" (v->counter) | 65 | :"=m" (v->counter) |
| 72 | :"ir" (i), "m" (v->counter)); | 66 | :"ir" (i), "m" (v->counter)); |
| 73 | } | 67 | } |
| @@ -86,7 +80,7 @@ static __inline__ int atomic_sub_and_test(int i, atomic_t *v) | |||
| 86 | unsigned char c; | 80 | unsigned char c; |
| 87 | 81 | ||
| 88 | __asm__ __volatile__( | 82 | __asm__ __volatile__( |
| 89 | LOCK "subl %2,%0; sete %1" | 83 | LOCK_PREFIX "subl %2,%0; sete %1" |
| 90 | :"=m" (v->counter), "=qm" (c) | 84 | :"=m" (v->counter), "=qm" (c) |
| 91 | :"ir" (i), "m" (v->counter) : "memory"); | 85 | :"ir" (i), "m" (v->counter) : "memory"); |
| 92 | return c; | 86 | return c; |
| @@ -101,7 +95,7 @@ static __inline__ int atomic_sub_and_test(int i, atomic_t *v) | |||
| 101 | static __inline__ void atomic_inc(atomic_t *v) | 95 | static __inline__ void atomic_inc(atomic_t *v) |
| 102 | { | 96 | { |
| 103 | __asm__ __volatile__( | 97 | __asm__ __volatile__( |
| 104 | LOCK "incl %0" | 98 | LOCK_PREFIX "incl %0" |
| 105 | :"=m" (v->counter) | 99 | :"=m" (v->counter) |
| 106 | :"m" (v->counter)); | 100 | :"m" (v->counter)); |
| 107 | } | 101 | } |
| @@ -115,7 +109,7 @@ static __inline__ void atomic_inc(atomic_t *v) | |||
| 115 | static __inline__ void atomic_dec(atomic_t *v) | 109 | static __inline__ void atomic_dec(atomic_t *v) |
| 116 | { | 110 | { |
| 117 | __asm__ __volatile__( | 111 | __asm__ __volatile__( |
| 118 | LOCK "decl %0" | 112 | LOCK_PREFIX "decl %0" |
| 119 | :"=m" (v->counter) | 113 | :"=m" (v->counter) |
| 120 | :"m" (v->counter)); | 114 | :"m" (v->counter)); |
| 121 | } | 115 | } |
| @@ -133,7 +127,7 @@ static __inline__ int atomic_dec_and_test(atomic_t *v) | |||
| 133 | unsigned char c; | 127 | unsigned char c; |
| 134 | 128 | ||
| 135 | __asm__ __volatile__( | 129 | __asm__ __volatile__( |
| 136 | LOCK "decl %0; sete %1" | 130 | LOCK_PREFIX "decl %0; sete %1" |
| 137 | :"=m" (v->counter), "=qm" (c) | 131 | :"=m" (v->counter), "=qm" (c) |
| 138 | :"m" (v->counter) : "memory"); | 132 | :"m" (v->counter) : "memory"); |
| 139 | return c != 0; | 133 | return c != 0; |
| @@ -152,7 +146,7 @@ static __inline__ int atomic_inc_and_test(atomic_t *v) | |||
| 152 | unsigned char c; | 146 | unsigned char c; |
| 153 | 147 | ||
| 154 | __asm__ __volatile__( | 148 | __asm__ __volatile__( |
| 155 | LOCK "incl %0; sete %1" | 149 | LOCK_PREFIX "incl %0; sete %1" |
| 156 | :"=m" (v->counter), "=qm" (c) | 150 | :"=m" (v->counter), "=qm" (c) |
| 157 | :"m" (v->counter) : "memory"); | 151 | :"m" (v->counter) : "memory"); |
| 158 | return c != 0; | 152 | return c != 0; |
| @@ -172,7 +166,7 @@ static __inline__ int atomic_add_negative(int i, atomic_t *v) | |||
| 172 | unsigned char c; | 166 | unsigned char c; |
| 173 | 167 | ||
| 174 | __asm__ __volatile__( | 168 | __asm__ __volatile__( |
| 175 | LOCK "addl %2,%0; sets %1" | 169 | LOCK_PREFIX "addl %2,%0; sets %1" |
| 176 | :"=m" (v->counter), "=qm" (c) | 170 | :"=m" (v->counter), "=qm" (c) |
| 177 | :"ir" (i), "m" (v->counter) : "memory"); | 171 | :"ir" (i), "m" (v->counter) : "memory"); |
| 178 | return c; | 172 | return c; |
| @@ -195,7 +189,7 @@ static __inline__ int atomic_add_return(int i, atomic_t *v) | |||
| 195 | /* Modern 486+ processor */ | 189 | /* Modern 486+ processor */ |
| 196 | __i = i; | 190 | __i = i; |
| 197 | __asm__ __volatile__( | 191 | __asm__ __volatile__( |
| 198 | LOCK "xaddl %0, %1;" | 192 | LOCK_PREFIX "xaddl %0, %1;" |
| 199 | :"=r"(i) | 193 | :"=r"(i) |
| 200 | :"m"(v->counter), "0"(i)); | 194 | :"m"(v->counter), "0"(i)); |
| 201 | return i + __i; | 195 | return i + __i; |
| @@ -231,8 +225,14 @@ static __inline__ int atomic_sub_return(int i, atomic_t *v) | |||
| 231 | ({ \ | 225 | ({ \ |
| 232 | int c, old; \ | 226 | int c, old; \ |
| 233 | c = atomic_read(v); \ | 227 | c = atomic_read(v); \ |
| 234 | while (c != (u) && (old = atomic_cmpxchg((v), c, c + (a))) != c) \ | 228 | for (;;) { \ |
| 229 | if (unlikely(c == (u))) \ | ||
| 230 | break; \ | ||
| 231 | old = atomic_cmpxchg((v), c, c + (a)); \ | ||
| 232 | if (likely(old == c)) \ | ||
| 233 | break; \ | ||
| 235 | c = old; \ | 234 | c = old; \ |
| 235 | } \ | ||
| 236 | c != (u); \ | 236 | c != (u); \ |
| 237 | }) | 237 | }) |
| 238 | #define atomic_inc_not_zero(v) atomic_add_unless((v), 1, 0) | 238 | #define atomic_inc_not_zero(v) atomic_add_unless((v), 1, 0) |
| @@ -242,11 +242,11 @@ static __inline__ int atomic_sub_return(int i, atomic_t *v) | |||
| 242 | 242 | ||
| 243 | /* These are x86-specific, used by some header files */ | 243 | /* These are x86-specific, used by some header files */ |
| 244 | #define atomic_clear_mask(mask, addr) \ | 244 | #define atomic_clear_mask(mask, addr) \ |
| 245 | __asm__ __volatile__(LOCK "andl %0,%1" \ | 245 | __asm__ __volatile__(LOCK_PREFIX "andl %0,%1" \ |
| 246 | : : "r" (~(mask)),"m" (*addr) : "memory") | 246 | : : "r" (~(mask)),"m" (*addr) : "memory") |
| 247 | 247 | ||
| 248 | #define atomic_set_mask(mask, addr) \ | 248 | #define atomic_set_mask(mask, addr) \ |
| 249 | __asm__ __volatile__(LOCK "orl %0,%1" \ | 249 | __asm__ __volatile__(LOCK_PREFIX "orl %0,%1" \ |
| 250 | : : "r" (mask),"m" (*(addr)) : "memory") | 250 | : : "r" (mask),"m" (*(addr)) : "memory") |
| 251 | 251 | ||
| 252 | /* Atomic operations are already serializing on x86 */ | 252 | /* Atomic operations are already serializing on x86 */ |
diff --git a/include/asm-i386/bitops.h b/include/asm-i386/bitops.h index 88e6ca248cd7..7d20b95edb3b 100644 --- a/include/asm-i386/bitops.h +++ b/include/asm-i386/bitops.h | |||
| @@ -7,6 +7,7 @@ | |||
| 7 | 7 | ||
| 8 | #include <linux/config.h> | 8 | #include <linux/config.h> |
| 9 | #include <linux/compiler.h> | 9 | #include <linux/compiler.h> |
| 10 | #include <asm/alternative.h> | ||
| 10 | 11 | ||
| 11 | /* | 12 | /* |
| 12 | * These have to be done with inline assembly: that way the bit-setting | 13 | * These have to be done with inline assembly: that way the bit-setting |
| @@ -16,12 +17,6 @@ | |||
| 16 | * bit 0 is the LSB of addr; bit 32 is the LSB of (addr+1). | 17 | * bit 0 is the LSB of addr; bit 32 is the LSB of (addr+1). |
| 17 | */ | 18 | */ |
| 18 | 19 | ||
| 19 | #ifdef CONFIG_SMP | ||
| 20 | #define LOCK_PREFIX "lock ; " | ||
| 21 | #else | ||
| 22 | #define LOCK_PREFIX "" | ||
| 23 | #endif | ||
| 24 | |||
| 25 | #define ADDR (*(volatile long *) addr) | 20 | #define ADDR (*(volatile long *) addr) |
| 26 | 21 | ||
| 27 | /** | 22 | /** |
diff --git a/include/asm-i386/cache.h b/include/asm-i386/cache.h index 615911e5bd24..ca15c9c665cf 100644 --- a/include/asm-i386/cache.h +++ b/include/asm-i386/cache.h | |||
| @@ -10,4 +10,6 @@ | |||
| 10 | #define L1_CACHE_SHIFT (CONFIG_X86_L1_CACHE_SHIFT) | 10 | #define L1_CACHE_SHIFT (CONFIG_X86_L1_CACHE_SHIFT) |
| 11 | #define L1_CACHE_BYTES (1 << L1_CACHE_SHIFT) | 11 | #define L1_CACHE_BYTES (1 << L1_CACHE_SHIFT) |
| 12 | 12 | ||
| 13 | #define __read_mostly __attribute__((__section__(".data.read_mostly"))) | ||
| 14 | |||
| 13 | #endif | 15 | #endif |
diff --git a/include/asm-i386/cpufeature.h b/include/asm-i386/cpufeature.h index c4ec2a4d8fdf..5c0b5876b931 100644 --- a/include/asm-i386/cpufeature.h +++ b/include/asm-i386/cpufeature.h | |||
| @@ -70,6 +70,7 @@ | |||
| 70 | #define X86_FEATURE_P3 (3*32+ 6) /* P3 */ | 70 | #define X86_FEATURE_P3 (3*32+ 6) /* P3 */ |
| 71 | #define X86_FEATURE_P4 (3*32+ 7) /* P4 */ | 71 | #define X86_FEATURE_P4 (3*32+ 7) /* P4 */ |
| 72 | #define X86_FEATURE_CONSTANT_TSC (3*32+ 8) /* TSC ticks at a constant rate */ | 72 | #define X86_FEATURE_CONSTANT_TSC (3*32+ 8) /* TSC ticks at a constant rate */ |
| 73 | #define X86_FEATURE_UP (3*32+ 9) /* smp kernel running on up */ | ||
| 73 | 74 | ||
| 74 | /* Intel-defined CPU features, CPUID level 0x00000001 (ecx), word 4 */ | 75 | /* Intel-defined CPU features, CPUID level 0x00000001 (ecx), word 4 */ |
| 75 | #define X86_FEATURE_XMM3 (4*32+ 0) /* Streaming SIMD Extensions-3 */ | 76 | #define X86_FEATURE_XMM3 (4*32+ 0) /* Streaming SIMD Extensions-3 */ |
diff --git a/include/asm-i386/mach-default/do_timer.h b/include/asm-i386/mach-default/do_timer.h index 56211414fc95..6312c3e79814 100644 --- a/include/asm-i386/mach-default/do_timer.h +++ b/include/asm-i386/mach-default/do_timer.h | |||
| @@ -18,7 +18,7 @@ static inline void do_timer_interrupt_hook(struct pt_regs *regs) | |||
| 18 | { | 18 | { |
| 19 | do_timer(regs); | 19 | do_timer(regs); |
| 20 | #ifndef CONFIG_SMP | 20 | #ifndef CONFIG_SMP |
| 21 | update_process_times(user_mode(regs)); | 21 | update_process_times(user_mode_vm(regs)); |
| 22 | #endif | 22 | #endif |
| 23 | /* | 23 | /* |
| 24 | * In the SMP case we use the local APIC timer interrupt to do the | 24 | * In the SMP case we use the local APIC timer interrupt to do the |
diff --git a/include/asm-i386/mach-es7000/mach_mpparse.h b/include/asm-i386/mach-es7000/mach_mpparse.h index 4a0637a3e208..99f66be240be 100644 --- a/include/asm-i386/mach-es7000/mach_mpparse.h +++ b/include/asm-i386/mach-es7000/mach_mpparse.h | |||
| @@ -30,7 +30,8 @@ static inline int mps_oem_check(struct mp_config_table *mpc, char *oem, | |||
| 30 | return 0; | 30 | return 0; |
| 31 | } | 31 | } |
| 32 | 32 | ||
| 33 | static inline int es7000_check_dsdt() | 33 | #ifdef CONFIG_ACPI |
| 34 | static inline int es7000_check_dsdt(void) | ||
| 34 | { | 35 | { |
| 35 | struct acpi_table_header *header = NULL; | 36 | struct acpi_table_header *header = NULL; |
| 36 | if(!acpi_get_table_header_early(ACPI_DSDT, &header)) | 37 | if(!acpi_get_table_header_early(ACPI_DSDT, &header)) |
| @@ -54,6 +55,11 @@ static inline int acpi_madt_oem_check(char *oem_id, char *oem_table_id) | |||
| 54 | } | 55 | } |
| 55 | return 0; | 56 | return 0; |
| 56 | } | 57 | } |
| 57 | 58 | #else | |
| 59 | static inline int acpi_madt_oem_check(char *oem_id, char *oem_table_id) | ||
| 60 | { | ||
| 61 | return 0; | ||
| 62 | } | ||
| 63 | #endif | ||
| 58 | 64 | ||
| 59 | #endif /* __ASM_MACH_MPPARSE_H */ | 65 | #endif /* __ASM_MACH_MPPARSE_H */ |
diff --git a/include/asm-i386/mach-visws/do_timer.h b/include/asm-i386/mach-visws/do_timer.h index 92d638fc8b11..95568e6ca91c 100644 --- a/include/asm-i386/mach-visws/do_timer.h +++ b/include/asm-i386/mach-visws/do_timer.h | |||
| @@ -11,7 +11,7 @@ static inline void do_timer_interrupt_hook(struct pt_regs *regs) | |||
| 11 | 11 | ||
| 12 | do_timer(regs); | 12 | do_timer(regs); |
| 13 | #ifndef CONFIG_SMP | 13 | #ifndef CONFIG_SMP |
| 14 | update_process_times(user_mode(regs)); | 14 | update_process_times(user_mode_vm(regs)); |
| 15 | #endif | 15 | #endif |
| 16 | /* | 16 | /* |
| 17 | * In the SMP case we use the local APIC timer interrupt to do the | 17 | * In the SMP case we use the local APIC timer interrupt to do the |
diff --git a/include/asm-i386/mach-voyager/do_timer.h b/include/asm-i386/mach-voyager/do_timer.h index ae510e5d0d78..eaf518098981 100644 --- a/include/asm-i386/mach-voyager/do_timer.h +++ b/include/asm-i386/mach-voyager/do_timer.h | |||
| @@ -5,7 +5,7 @@ static inline void do_timer_interrupt_hook(struct pt_regs *regs) | |||
| 5 | { | 5 | { |
| 6 | do_timer(regs); | 6 | do_timer(regs); |
| 7 | #ifndef CONFIG_SMP | 7 | #ifndef CONFIG_SMP |
| 8 | update_process_times(user_mode(regs)); | 8 | update_process_times(user_mode_vm(regs)); |
| 9 | #endif | 9 | #endif |
| 10 | 10 | ||
| 11 | voyager_timer_interrupt(regs); | 11 | voyager_timer_interrupt(regs); |
diff --git a/include/asm-i386/mpspec.h b/include/asm-i386/mpspec.h index 64a0b8e6afeb..62113d3bfdc2 100644 --- a/include/asm-i386/mpspec.h +++ b/include/asm-i386/mpspec.h | |||
| @@ -22,7 +22,6 @@ extern int mp_bus_id_to_type [MAX_MP_BUSSES]; | |||
| 22 | extern int mp_irq_entries; | 22 | extern int mp_irq_entries; |
| 23 | extern struct mpc_config_intsrc mp_irqs [MAX_IRQ_SOURCES]; | 23 | extern struct mpc_config_intsrc mp_irqs [MAX_IRQ_SOURCES]; |
| 24 | extern int mpc_default_type; | 24 | extern int mpc_default_type; |
| 25 | extern int mp_bus_id_to_pci_bus [MAX_MP_BUSSES]; | ||
| 26 | extern unsigned long mp_lapic_addr; | 25 | extern unsigned long mp_lapic_addr; |
| 27 | extern int pic_mode; | 26 | extern int pic_mode; |
| 28 | extern int using_apic_timer; | 27 | extern int using_apic_timer; |
diff --git a/include/asm-i386/mtrr.h b/include/asm-i386/mtrr.h index 5b6ceda68c5f..64cf937c7e33 100644 --- a/include/asm-i386/mtrr.h +++ b/include/asm-i386/mtrr.h | |||
| @@ -25,6 +25,7 @@ | |||
| 25 | 25 | ||
| 26 | #include <linux/config.h> | 26 | #include <linux/config.h> |
| 27 | #include <linux/ioctl.h> | 27 | #include <linux/ioctl.h> |
| 28 | #include <linux/errno.h> | ||
| 28 | 29 | ||
| 29 | #define MTRR_IOCTL_BASE 'M' | 30 | #define MTRR_IOCTL_BASE 'M' |
| 30 | 31 | ||
diff --git a/include/asm-i386/mutex.h b/include/asm-i386/mutex.h index 9b2199e829f3..05a538531229 100644 --- a/include/asm-i386/mutex.h +++ b/include/asm-i386/mutex.h | |||
| @@ -9,6 +9,8 @@ | |||
| 9 | #ifndef _ASM_MUTEX_H | 9 | #ifndef _ASM_MUTEX_H |
| 10 | #define _ASM_MUTEX_H | 10 | #define _ASM_MUTEX_H |
| 11 | 11 | ||
| 12 | #include "asm/alternative.h" | ||
| 13 | |||
| 12 | /** | 14 | /** |
| 13 | * __mutex_fastpath_lock - try to take the lock by moving the count | 15 | * __mutex_fastpath_lock - try to take the lock by moving the count |
| 14 | * from 1 to a 0 value | 16 | * from 1 to a 0 value |
| @@ -27,7 +29,7 @@ do { \ | |||
| 27 | typecheck_fn(fastcall void (*)(atomic_t *), fail_fn); \ | 29 | typecheck_fn(fastcall void (*)(atomic_t *), fail_fn); \ |
| 28 | \ | 30 | \ |
| 29 | __asm__ __volatile__( \ | 31 | __asm__ __volatile__( \ |
| 30 | LOCK " decl (%%eax) \n" \ | 32 | LOCK_PREFIX " decl (%%eax) \n" \ |
| 31 | " js 2f \n" \ | 33 | " js 2f \n" \ |
| 32 | "1: \n" \ | 34 | "1: \n" \ |
| 33 | \ | 35 | \ |
| @@ -83,7 +85,7 @@ do { \ | |||
| 83 | typecheck_fn(fastcall void (*)(atomic_t *), fail_fn); \ | 85 | typecheck_fn(fastcall void (*)(atomic_t *), fail_fn); \ |
| 84 | \ | 86 | \ |
| 85 | __asm__ __volatile__( \ | 87 | __asm__ __volatile__( \ |
| 86 | LOCK " incl (%%eax) \n" \ | 88 | LOCK_PREFIX " incl (%%eax) \n" \ |
| 87 | " jle 2f \n" \ | 89 | " jle 2f \n" \ |
| 88 | "1: \n" \ | 90 | "1: \n" \ |
| 89 | \ | 91 | \ |
diff --git a/include/asm-i386/pgtable-2level.h b/include/asm-i386/pgtable-2level.h index 74ef721b534d..27bde973abc7 100644 --- a/include/asm-i386/pgtable-2level.h +++ b/include/asm-i386/pgtable-2level.h | |||
| @@ -61,4 +61,6 @@ static inline int pte_exec_kernel(pte_t pte) | |||
| 61 | #define __pte_to_swp_entry(pte) ((swp_entry_t) { (pte).pte_low }) | 61 | #define __pte_to_swp_entry(pte) ((swp_entry_t) { (pte).pte_low }) |
| 62 | #define __swp_entry_to_pte(x) ((pte_t) { (x).val }) | 62 | #define __swp_entry_to_pte(x) ((pte_t) { (x).val }) |
| 63 | 63 | ||
| 64 | void vmalloc_sync_all(void); | ||
| 65 | |||
| 64 | #endif /* _I386_PGTABLE_2LEVEL_H */ | 66 | #endif /* _I386_PGTABLE_2LEVEL_H */ |
diff --git a/include/asm-i386/pgtable-3level.h b/include/asm-i386/pgtable-3level.h index f1a8b454920a..36a5aa63cbbf 100644 --- a/include/asm-i386/pgtable-3level.h +++ b/include/asm-i386/pgtable-3level.h | |||
| @@ -152,4 +152,6 @@ static inline pmd_t pfn_pmd(unsigned long page_nr, pgprot_t pgprot) | |||
| 152 | 152 | ||
| 153 | #define __pmd_free_tlb(tlb, x) do { } while (0) | 153 | #define __pmd_free_tlb(tlb, x) do { } while (0) |
| 154 | 154 | ||
| 155 | #define vmalloc_sync_all() ((void)0) | ||
| 156 | |||
| 155 | #endif /* _I386_PGTABLE_3LEVEL_H */ | 157 | #endif /* _I386_PGTABLE_3LEVEL_H */ |
diff --git a/include/asm-i386/pgtable.h b/include/asm-i386/pgtable.h index 088a945bf26b..ee056c41a9fb 100644 --- a/include/asm-i386/pgtable.h +++ b/include/asm-i386/pgtable.h | |||
| @@ -219,13 +219,12 @@ extern unsigned long pg0[]; | |||
| 219 | * The following only work if pte_present() is true. | 219 | * The following only work if pte_present() is true. |
| 220 | * Undefined behaviour if not.. | 220 | * Undefined behaviour if not.. |
| 221 | */ | 221 | */ |
| 222 | #define __LARGE_PTE (_PAGE_PSE | _PAGE_PRESENT) | ||
| 223 | static inline int pte_user(pte_t pte) { return (pte).pte_low & _PAGE_USER; } | 222 | static inline int pte_user(pte_t pte) { return (pte).pte_low & _PAGE_USER; } |
| 224 | static inline int pte_read(pte_t pte) { return (pte).pte_low & _PAGE_USER; } | 223 | static inline int pte_read(pte_t pte) { return (pte).pte_low & _PAGE_USER; } |
| 225 | static inline int pte_dirty(pte_t pte) { return (pte).pte_low & _PAGE_DIRTY; } | 224 | static inline int pte_dirty(pte_t pte) { return (pte).pte_low & _PAGE_DIRTY; } |
| 226 | static inline int pte_young(pte_t pte) { return (pte).pte_low & _PAGE_ACCESSED; } | 225 | static inline int pte_young(pte_t pte) { return (pte).pte_low & _PAGE_ACCESSED; } |
| 227 | static inline int pte_write(pte_t pte) { return (pte).pte_low & _PAGE_RW; } | 226 | static inline int pte_write(pte_t pte) { return (pte).pte_low & _PAGE_RW; } |
| 228 | static inline int pte_huge(pte_t pte) { return ((pte).pte_low & __LARGE_PTE) == __LARGE_PTE; } | 227 | static inline int pte_huge(pte_t pte) { return (pte).pte_low & _PAGE_PSE; } |
| 229 | 228 | ||
| 230 | /* | 229 | /* |
| 231 | * The following only works if pte_present() is not true. | 230 | * The following only works if pte_present() is not true. |
| @@ -242,7 +241,7 @@ static inline pte_t pte_mkexec(pte_t pte) { (pte).pte_low |= _PAGE_USER; return | |||
| 242 | static inline pte_t pte_mkdirty(pte_t pte) { (pte).pte_low |= _PAGE_DIRTY; return pte; } | 241 | static inline pte_t pte_mkdirty(pte_t pte) { (pte).pte_low |= _PAGE_DIRTY; return pte; } |
| 243 | static inline pte_t pte_mkyoung(pte_t pte) { (pte).pte_low |= _PAGE_ACCESSED; return pte; } | 242 | static inline pte_t pte_mkyoung(pte_t pte) { (pte).pte_low |= _PAGE_ACCESSED; return pte; } |
| 244 | static inline pte_t pte_mkwrite(pte_t pte) { (pte).pte_low |= _PAGE_RW; return pte; } | 243 | static inline pte_t pte_mkwrite(pte_t pte) { (pte).pte_low |= _PAGE_RW; return pte; } |
| 245 | static inline pte_t pte_mkhuge(pte_t pte) { (pte).pte_low |= __LARGE_PTE; return pte; } | 244 | static inline pte_t pte_mkhuge(pte_t pte) { (pte).pte_low |= _PAGE_PSE; return pte; } |
| 246 | 245 | ||
| 247 | #ifdef CONFIG_X86_PAE | 246 | #ifdef CONFIG_X86_PAE |
| 248 | # include <asm/pgtable-3level.h> | 247 | # include <asm/pgtable-3level.h> |
diff --git a/include/asm-i386/rwlock.h b/include/asm-i386/rwlock.h index b57cc7afdf7e..94f00195d543 100644 --- a/include/asm-i386/rwlock.h +++ b/include/asm-i386/rwlock.h | |||
| @@ -21,21 +21,23 @@ | |||
| 21 | #define RW_LOCK_BIAS_STR "0x01000000" | 21 | #define RW_LOCK_BIAS_STR "0x01000000" |
| 22 | 22 | ||
| 23 | #define __build_read_lock_ptr(rw, helper) \ | 23 | #define __build_read_lock_ptr(rw, helper) \ |
| 24 | asm volatile(LOCK "subl $1,(%0)\n\t" \ | 24 | alternative_smp("lock; subl $1,(%0)\n\t" \ |
| 25 | "jns 1f\n" \ | 25 | "jns 1f\n" \ |
| 26 | "call " helper "\n\t" \ | 26 | "call " helper "\n\t" \ |
| 27 | "1:\n" \ | 27 | "1:\n", \ |
| 28 | ::"a" (rw) : "memory") | 28 | "subl $1,(%0)\n\t", \ |
| 29 | :"a" (rw) : "memory") | ||
| 29 | 30 | ||
| 30 | #define __build_read_lock_const(rw, helper) \ | 31 | #define __build_read_lock_const(rw, helper) \ |
| 31 | asm volatile(LOCK "subl $1,%0\n\t" \ | 32 | alternative_smp("lock; subl $1,%0\n\t" \ |
| 32 | "jns 1f\n" \ | 33 | "jns 1f\n" \ |
| 33 | "pushl %%eax\n\t" \ | 34 | "pushl %%eax\n\t" \ |
| 34 | "leal %0,%%eax\n\t" \ | 35 | "leal %0,%%eax\n\t" \ |
| 35 | "call " helper "\n\t" \ | 36 | "call " helper "\n\t" \ |
| 36 | "popl %%eax\n\t" \ | 37 | "popl %%eax\n\t" \ |
| 37 | "1:\n" \ | 38 | "1:\n", \ |
| 38 | :"=m" (*(volatile int *)rw) : : "memory") | 39 | "subl $1,%0\n\t", \ |
| 40 | "=m" (*(volatile int *)rw) : : "memory") | ||
| 39 | 41 | ||
| 40 | #define __build_read_lock(rw, helper) do { \ | 42 | #define __build_read_lock(rw, helper) do { \ |
| 41 | if (__builtin_constant_p(rw)) \ | 43 | if (__builtin_constant_p(rw)) \ |
| @@ -45,21 +47,23 @@ | |||
| 45 | } while (0) | 47 | } while (0) |
| 46 | 48 | ||
| 47 | #define __build_write_lock_ptr(rw, helper) \ | 49 | #define __build_write_lock_ptr(rw, helper) \ |
| 48 | asm volatile(LOCK "subl $" RW_LOCK_BIAS_STR ",(%0)\n\t" \ | 50 | alternative_smp("lock; subl $" RW_LOCK_BIAS_STR ",(%0)\n\t" \ |
| 49 | "jz 1f\n" \ | 51 | "jz 1f\n" \ |
| 50 | "call " helper "\n\t" \ | 52 | "call " helper "\n\t" \ |
| 51 | "1:\n" \ | 53 | "1:\n", \ |
| 52 | ::"a" (rw) : "memory") | 54 | "subl $" RW_LOCK_BIAS_STR ",(%0)\n\t", \ |
| 55 | :"a" (rw) : "memory") | ||
| 53 | 56 | ||
| 54 | #define __build_write_lock_const(rw, helper) \ | 57 | #define __build_write_lock_const(rw, helper) \ |
| 55 | asm volatile(LOCK "subl $" RW_LOCK_BIAS_STR ",%0\n\t" \ | 58 | alternative_smp("lock; subl $" RW_LOCK_BIAS_STR ",%0\n\t" \ |
| 56 | "jz 1f\n" \ | 59 | "jz 1f\n" \ |
| 57 | "pushl %%eax\n\t" \ | 60 | "pushl %%eax\n\t" \ |
| 58 | "leal %0,%%eax\n\t" \ | 61 | "leal %0,%%eax\n\t" \ |
| 59 | "call " helper "\n\t" \ | 62 | "call " helper "\n\t" \ |
| 60 | "popl %%eax\n\t" \ | 63 | "popl %%eax\n\t" \ |
| 61 | "1:\n" \ | 64 | "1:\n", \ |
| 62 | :"=m" (*(volatile int *)rw) : : "memory") | 65 | "subl $" RW_LOCK_BIAS_STR ",%0\n\t", \ |
| 66 | "=m" (*(volatile int *)rw) : : "memory") | ||
| 63 | 67 | ||
| 64 | #define __build_write_lock(rw, helper) do { \ | 68 | #define __build_write_lock(rw, helper) do { \ |
| 65 | if (__builtin_constant_p(rw)) \ | 69 | if (__builtin_constant_p(rw)) \ |
diff --git a/include/asm-i386/semaphore.h b/include/asm-i386/semaphore.h index 6a42b2142fd6..f7a0f310c524 100644 --- a/include/asm-i386/semaphore.h +++ b/include/asm-i386/semaphore.h | |||
| @@ -99,7 +99,7 @@ static inline void down(struct semaphore * sem) | |||
| 99 | might_sleep(); | 99 | might_sleep(); |
| 100 | __asm__ __volatile__( | 100 | __asm__ __volatile__( |
| 101 | "# atomic down operation\n\t" | 101 | "# atomic down operation\n\t" |
| 102 | LOCK "decl %0\n\t" /* --sem->count */ | 102 | LOCK_PREFIX "decl %0\n\t" /* --sem->count */ |
| 103 | "js 2f\n" | 103 | "js 2f\n" |
| 104 | "1:\n" | 104 | "1:\n" |
| 105 | LOCK_SECTION_START("") | 105 | LOCK_SECTION_START("") |
| @@ -123,7 +123,7 @@ static inline int down_interruptible(struct semaphore * sem) | |||
| 123 | might_sleep(); | 123 | might_sleep(); |
| 124 | __asm__ __volatile__( | 124 | __asm__ __volatile__( |
| 125 | "# atomic interruptible down operation\n\t" | 125 | "# atomic interruptible down operation\n\t" |
| 126 | LOCK "decl %1\n\t" /* --sem->count */ | 126 | LOCK_PREFIX "decl %1\n\t" /* --sem->count */ |
| 127 | "js 2f\n\t" | 127 | "js 2f\n\t" |
| 128 | "xorl %0,%0\n" | 128 | "xorl %0,%0\n" |
| 129 | "1:\n" | 129 | "1:\n" |
| @@ -148,7 +148,7 @@ static inline int down_trylock(struct semaphore * sem) | |||
| 148 | 148 | ||
| 149 | __asm__ __volatile__( | 149 | __asm__ __volatile__( |
| 150 | "# atomic interruptible down operation\n\t" | 150 | "# atomic interruptible down operation\n\t" |
| 151 | LOCK "decl %1\n\t" /* --sem->count */ | 151 | LOCK_PREFIX "decl %1\n\t" /* --sem->count */ |
| 152 | "js 2f\n\t" | 152 | "js 2f\n\t" |
| 153 | "xorl %0,%0\n" | 153 | "xorl %0,%0\n" |
| 154 | "1:\n" | 154 | "1:\n" |
| @@ -173,7 +173,7 @@ static inline void up(struct semaphore * sem) | |||
| 173 | { | 173 | { |
| 174 | __asm__ __volatile__( | 174 | __asm__ __volatile__( |
| 175 | "# atomic up operation\n\t" | 175 | "# atomic up operation\n\t" |
| 176 | LOCK "incl %0\n\t" /* ++sem->count */ | 176 | LOCK_PREFIX "incl %0\n\t" /* ++sem->count */ |
| 177 | "jle 2f\n" | 177 | "jle 2f\n" |
| 178 | "1:\n" | 178 | "1:\n" |
| 179 | LOCK_SECTION_START("") | 179 | LOCK_SECTION_START("") |
diff --git a/include/asm-i386/spinlock.h b/include/asm-i386/spinlock.h index 23604350cdf4..d76b7693cf1d 100644 --- a/include/asm-i386/spinlock.h +++ b/include/asm-i386/spinlock.h | |||
| @@ -35,31 +35,41 @@ | |||
| 35 | #define __raw_spin_lock_string_flags \ | 35 | #define __raw_spin_lock_string_flags \ |
| 36 | "\n1:\t" \ | 36 | "\n1:\t" \ |
| 37 | "lock ; decb %0\n\t" \ | 37 | "lock ; decb %0\n\t" \ |
| 38 | "jns 4f\n\t" \ | 38 | "jns 5f\n" \ |
| 39 | "2:\t" \ | 39 | "2:\t" \ |
| 40 | "testl $0x200, %1\n\t" \ | 40 | "testl $0x200, %1\n\t" \ |
| 41 | "jz 3f\n\t" \ | 41 | "jz 4f\n\t" \ |
| 42 | "sti\n\t" \ | 42 | "sti\n" \ |
| 43 | "3:\t" \ | 43 | "3:\t" \ |
| 44 | "rep;nop\n\t" \ | 44 | "rep;nop\n\t" \ |
| 45 | "cmpb $0, %0\n\t" \ | 45 | "cmpb $0, %0\n\t" \ |
| 46 | "jle 3b\n\t" \ | 46 | "jle 3b\n\t" \ |
| 47 | "cli\n\t" \ | 47 | "cli\n\t" \ |
| 48 | "jmp 1b\n" \ | 48 | "jmp 1b\n" \ |
| 49 | "4:\n\t" | 49 | "4:\t" \ |
| 50 | "rep;nop\n\t" \ | ||
| 51 | "cmpb $0, %0\n\t" \ | ||
| 52 | "jg 1b\n\t" \ | ||
| 53 | "jmp 4b\n" \ | ||
| 54 | "5:\n\t" | ||
| 55 | |||
| 56 | #define __raw_spin_lock_string_up \ | ||
| 57 | "\n\tdecb %0" | ||
| 50 | 58 | ||
| 51 | static inline void __raw_spin_lock(raw_spinlock_t *lock) | 59 | static inline void __raw_spin_lock(raw_spinlock_t *lock) |
| 52 | { | 60 | { |
| 53 | __asm__ __volatile__( | 61 | alternative_smp( |
| 54 | __raw_spin_lock_string | 62 | __raw_spin_lock_string, |
| 55 | :"=m" (lock->slock) : : "memory"); | 63 | __raw_spin_lock_string_up, |
| 64 | "=m" (lock->slock) : : "memory"); | ||
| 56 | } | 65 | } |
| 57 | 66 | ||
| 58 | static inline void __raw_spin_lock_flags(raw_spinlock_t *lock, unsigned long flags) | 67 | static inline void __raw_spin_lock_flags(raw_spinlock_t *lock, unsigned long flags) |
| 59 | { | 68 | { |
| 60 | __asm__ __volatile__( | 69 | alternative_smp( |
| 61 | __raw_spin_lock_string_flags | 70 | __raw_spin_lock_string_flags, |
| 62 | :"=m" (lock->slock) : "r" (flags) : "memory"); | 71 | __raw_spin_lock_string_up, |
| 72 | "=m" (lock->slock) : "r" (flags) : "memory"); | ||
| 63 | } | 73 | } |
| 64 | 74 | ||
| 65 | static inline int __raw_spin_trylock(raw_spinlock_t *lock) | 75 | static inline int __raw_spin_trylock(raw_spinlock_t *lock) |
| @@ -178,12 +188,12 @@ static inline int __raw_write_trylock(raw_rwlock_t *lock) | |||
| 178 | 188 | ||
| 179 | static inline void __raw_read_unlock(raw_rwlock_t *rw) | 189 | static inline void __raw_read_unlock(raw_rwlock_t *rw) |
| 180 | { | 190 | { |
| 181 | asm volatile("lock ; incl %0" :"=m" (rw->lock) : : "memory"); | 191 | asm volatile(LOCK_PREFIX "incl %0" :"=m" (rw->lock) : : "memory"); |
| 182 | } | 192 | } |
| 183 | 193 | ||
| 184 | static inline void __raw_write_unlock(raw_rwlock_t *rw) | 194 | static inline void __raw_write_unlock(raw_rwlock_t *rw) |
| 185 | { | 195 | { |
| 186 | asm volatile("lock ; addl $" RW_LOCK_BIAS_STR ", %0" | 196 | asm volatile(LOCK_PREFIX "addl $" RW_LOCK_BIAS_STR ", %0" |
| 187 | : "=m" (rw->lock) : : "memory"); | 197 | : "=m" (rw->lock) : : "memory"); |
| 188 | } | 198 | } |
| 189 | 199 | ||
diff --git a/include/asm-i386/system.h b/include/asm-i386/system.h index 399145a247f2..d0d8d7448d88 100644 --- a/include/asm-i386/system.h +++ b/include/asm-i386/system.h | |||
| @@ -352,67 +352,6 @@ static inline unsigned long long __cmpxchg64(volatile void *ptr, unsigned long l | |||
| 352 | 352 | ||
| 353 | #endif | 353 | #endif |
| 354 | 354 | ||
| 355 | #ifdef __KERNEL__ | ||
| 356 | struct alt_instr { | ||
| 357 | __u8 *instr; /* original instruction */ | ||
| 358 | __u8 *replacement; | ||
| 359 | __u8 cpuid; /* cpuid bit set for replacement */ | ||
| 360 | __u8 instrlen; /* length of original instruction */ | ||
| 361 | __u8 replacementlen; /* length of new instruction, <= instrlen */ | ||
| 362 | __u8 pad; | ||
| 363 | }; | ||
| 364 | #endif | ||
| 365 | |||
| 366 | /* | ||
| 367 | * Alternative instructions for different CPU types or capabilities. | ||
| 368 | * | ||
| 369 | * This allows to use optimized instructions even on generic binary | ||
| 370 | * kernels. | ||
| 371 | * | ||
| 372 | * length of oldinstr must be longer or equal the length of newinstr | ||
| 373 | * It can be padded with nops as needed. | ||
| 374 | * | ||
| 375 | * For non barrier like inlines please define new variants | ||
| 376 | * without volatile and memory clobber. | ||
| 377 | */ | ||
| 378 | #define alternative(oldinstr, newinstr, feature) \ | ||
| 379 | asm volatile ("661:\n\t" oldinstr "\n662:\n" \ | ||
| 380 | ".section .altinstructions,\"a\"\n" \ | ||
| 381 | " .align 4\n" \ | ||
| 382 | " .long 661b\n" /* label */ \ | ||
| 383 | " .long 663f\n" /* new instruction */ \ | ||
| 384 | " .byte %c0\n" /* feature bit */ \ | ||
| 385 | " .byte 662b-661b\n" /* sourcelen */ \ | ||
| 386 | " .byte 664f-663f\n" /* replacementlen */ \ | ||
| 387 | ".previous\n" \ | ||
| 388 | ".section .altinstr_replacement,\"ax\"\n" \ | ||
| 389 | "663:\n\t" newinstr "\n664:\n" /* replacement */ \ | ||
| 390 | ".previous" :: "i" (feature) : "memory") | ||
| 391 | |||
| 392 | /* | ||
| 393 | * Alternative inline assembly with input. | ||
| 394 | * | ||
| 395 | * Pecularities: | ||
| 396 | * No memory clobber here. | ||
| 397 | * Argument numbers start with 1. | ||
| 398 | * Best is to use constraints that are fixed size (like (%1) ... "r") | ||
| 399 | * If you use variable sized constraints like "m" or "g" in the | ||
| 400 | * replacement maake sure to pad to the worst case length. | ||
| 401 | */ | ||
| 402 | #define alternative_input(oldinstr, newinstr, feature, input...) \ | ||
| 403 | asm volatile ("661:\n\t" oldinstr "\n662:\n" \ | ||
| 404 | ".section .altinstructions,\"a\"\n" \ | ||
| 405 | " .align 4\n" \ | ||
| 406 | " .long 661b\n" /* label */ \ | ||
| 407 | " .long 663f\n" /* new instruction */ \ | ||
| 408 | " .byte %c0\n" /* feature bit */ \ | ||
| 409 | " .byte 662b-661b\n" /* sourcelen */ \ | ||
| 410 | " .byte 664f-663f\n" /* replacementlen */ \ | ||
| 411 | ".previous\n" \ | ||
| 412 | ".section .altinstr_replacement,\"ax\"\n" \ | ||
| 413 | "663:\n\t" newinstr "\n664:\n" /* replacement */ \ | ||
| 414 | ".previous" :: "i" (feature), ##input) | ||
| 415 | |||
| 416 | /* | 355 | /* |
| 417 | * Force strict CPU ordering. | 356 | * Force strict CPU ordering. |
| 418 | * And yes, this is required on UP too when we're talking | 357 | * And yes, this is required on UP too when we're talking |
| @@ -558,5 +497,6 @@ static inline void sched_cacheflush(void) | |||
| 558 | } | 497 | } |
| 559 | 498 | ||
| 560 | extern unsigned long arch_align_stack(unsigned long sp); | 499 | extern unsigned long arch_align_stack(unsigned long sp); |
| 500 | extern void free_init_pages(char *what, unsigned long begin, unsigned long end); | ||
| 561 | 501 | ||
| 562 | #endif | 502 | #endif |
diff --git a/include/asm-i386/uaccess.h b/include/asm-i386/uaccess.h index 3f1337c34208..371457b1ceb6 100644 --- a/include/asm-i386/uaccess.h +++ b/include/asm-i386/uaccess.h | |||
| @@ -197,13 +197,15 @@ extern void __put_user_8(void); | |||
| 197 | 197 | ||
| 198 | #define put_user(x,ptr) \ | 198 | #define put_user(x,ptr) \ |
| 199 | ({ int __ret_pu; \ | 199 | ({ int __ret_pu; \ |
| 200 | __typeof__(*(ptr)) __pu_val; \ | ||
| 200 | __chk_user_ptr(ptr); \ | 201 | __chk_user_ptr(ptr); \ |
| 202 | __pu_val = x; \ | ||
| 201 | switch(sizeof(*(ptr))) { \ | 203 | switch(sizeof(*(ptr))) { \ |
| 202 | case 1: __put_user_1(x, ptr); break; \ | 204 | case 1: __put_user_1(__pu_val, ptr); break; \ |
| 203 | case 2: __put_user_2(x, ptr); break; \ | 205 | case 2: __put_user_2(__pu_val, ptr); break; \ |
| 204 | case 4: __put_user_4(x, ptr); break; \ | 206 | case 4: __put_user_4(__pu_val, ptr); break; \ |
| 205 | case 8: __put_user_8(x, ptr); break; \ | 207 | case 8: __put_user_8(__pu_val, ptr); break; \ |
| 206 | default:__put_user_X(x, ptr); break; \ | 208 | default:__put_user_X(__pu_val, ptr); break; \ |
| 207 | } \ | 209 | } \ |
| 208 | __ret_pu; \ | 210 | __ret_pu; \ |
| 209 | }) | 211 | }) |
diff --git a/include/asm-i386/unistd.h b/include/asm-i386/unistd.h index dc81a55dd94d..d8afd0e3b81a 100644 --- a/include/asm-i386/unistd.h +++ b/include/asm-i386/unistd.h | |||
| @@ -347,9 +347,9 @@ __syscall_return(type,__res); \ | |||
| 347 | type name(type1 arg1) \ | 347 | type name(type1 arg1) \ |
| 348 | { \ | 348 | { \ |
| 349 | long __res; \ | 349 | long __res; \ |
| 350 | __asm__ volatile ("int $0x80" \ | 350 | __asm__ volatile ("push %%ebx ; movl %2,%%ebx ; int $0x80 ; pop %%ebx" \ |
| 351 | : "=a" (__res) \ | 351 | : "=a" (__res) \ |
| 352 | : "0" (__NR_##name),"b" ((long)(arg1)) : "memory"); \ | 352 | : "0" (__NR_##name),"ri" ((long)(arg1)) : "memory"); \ |
| 353 | __syscall_return(type,__res); \ | 353 | __syscall_return(type,__res); \ |
| 354 | } | 354 | } |
| 355 | 355 | ||
| @@ -357,9 +357,10 @@ __syscall_return(type,__res); \ | |||
| 357 | type name(type1 arg1,type2 arg2) \ | 357 | type name(type1 arg1,type2 arg2) \ |
| 358 | { \ | 358 | { \ |
| 359 | long __res; \ | 359 | long __res; \ |
| 360 | __asm__ volatile ("int $0x80" \ | 360 | __asm__ volatile ("push %%ebx ; movl %2,%%ebx ; int $0x80 ; pop %%ebx" \ |
| 361 | : "=a" (__res) \ | 361 | : "=a" (__res) \ |
| 362 | : "0" (__NR_##name),"b" ((long)(arg1)),"c" ((long)(arg2)) : "memory"); \ | 362 | : "0" (__NR_##name),"ri" ((long)(arg1)),"c" ((long)(arg2)) \ |
| 363 | : "memory"); \ | ||
| 363 | __syscall_return(type,__res); \ | 364 | __syscall_return(type,__res); \ |
| 364 | } | 365 | } |
| 365 | 366 | ||
| @@ -367,9 +368,9 @@ __syscall_return(type,__res); \ | |||
| 367 | type name(type1 arg1,type2 arg2,type3 arg3) \ | 368 | type name(type1 arg1,type2 arg2,type3 arg3) \ |
| 368 | { \ | 369 | { \ |
| 369 | long __res; \ | 370 | long __res; \ |
| 370 | __asm__ volatile ("int $0x80" \ | 371 | __asm__ volatile ("push %%ebx ; movl %2,%%ebx ; int $0x80 ; pop %%ebx" \ |
| 371 | : "=a" (__res) \ | 372 | : "=a" (__res) \ |
| 372 | : "0" (__NR_##name),"b" ((long)(arg1)),"c" ((long)(arg2)), \ | 373 | : "0" (__NR_##name),"ri" ((long)(arg1)),"c" ((long)(arg2)), \ |
| 373 | "d" ((long)(arg3)) : "memory"); \ | 374 | "d" ((long)(arg3)) : "memory"); \ |
| 374 | __syscall_return(type,__res); \ | 375 | __syscall_return(type,__res); \ |
| 375 | } | 376 | } |
| @@ -378,9 +379,9 @@ __syscall_return(type,__res); \ | |||
| 378 | type name (type1 arg1, type2 arg2, type3 arg3, type4 arg4) \ | 379 | type name (type1 arg1, type2 arg2, type3 arg3, type4 arg4) \ |
| 379 | { \ | 380 | { \ |
| 380 | long __res; \ | 381 | long __res; \ |
| 381 | __asm__ volatile ("int $0x80" \ | 382 | __asm__ volatile ("push %%ebx ; movl %2,%%ebx ; int $0x80 ; pop %%ebx" \ |
| 382 | : "=a" (__res) \ | 383 | : "=a" (__res) \ |
| 383 | : "0" (__NR_##name),"b" ((long)(arg1)),"c" ((long)(arg2)), \ | 384 | : "0" (__NR_##name),"ri" ((long)(arg1)),"c" ((long)(arg2)), \ |
| 384 | "d" ((long)(arg3)),"S" ((long)(arg4)) : "memory"); \ | 385 | "d" ((long)(arg3)),"S" ((long)(arg4)) : "memory"); \ |
| 385 | __syscall_return(type,__res); \ | 386 | __syscall_return(type,__res); \ |
| 386 | } | 387 | } |
| @@ -390,10 +391,12 @@ __syscall_return(type,__res); \ | |||
| 390 | type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5) \ | 391 | type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5) \ |
| 391 | { \ | 392 | { \ |
| 392 | long __res; \ | 393 | long __res; \ |
| 393 | __asm__ volatile ("int $0x80" \ | 394 | __asm__ volatile ("push %%ebx ; movl %2,%%ebx ; movl %1,%%eax ; " \ |
| 395 | "int $0x80 ; pop %%ebx" \ | ||
| 394 | : "=a" (__res) \ | 396 | : "=a" (__res) \ |
| 395 | : "0" (__NR_##name),"b" ((long)(arg1)),"c" ((long)(arg2)), \ | 397 | : "i" (__NR_##name),"ri" ((long)(arg1)),"c" ((long)(arg2)), \ |
| 396 | "d" ((long)(arg3)),"S" ((long)(arg4)),"D" ((long)(arg5)) : "memory"); \ | 398 | "d" ((long)(arg3)),"S" ((long)(arg4)),"D" ((long)(arg5)) \ |
| 399 | : "memory"); \ | ||
| 397 | __syscall_return(type,__res); \ | 400 | __syscall_return(type,__res); \ |
| 398 | } | 401 | } |
| 399 | 402 | ||
| @@ -402,11 +405,14 @@ __syscall_return(type,__res); \ | |||
| 402 | type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5,type6 arg6) \ | 405 | type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5,type6 arg6) \ |
| 403 | { \ | 406 | { \ |
| 404 | long __res; \ | 407 | long __res; \ |
| 405 | __asm__ volatile ("push %%ebp ; movl %%eax,%%ebp ; movl %1,%%eax ; int $0x80 ; pop %%ebp" \ | 408 | struct { long __a1; long __a6; } __s = { (long)arg1, (long)arg6 }; \ |
| 409 | __asm__ volatile ("push %%ebp ; push %%ebx ; movl 4(%2),%%ebp ; " \ | ||
| 410 | "movl 0(%2),%%ebx ; movl %1,%%eax ; int $0x80 ; " \ | ||
| 411 | "pop %%ebx ; pop %%ebp" \ | ||
| 406 | : "=a" (__res) \ | 412 | : "=a" (__res) \ |
| 407 | : "i" (__NR_##name),"b" ((long)(arg1)),"c" ((long)(arg2)), \ | 413 | : "i" (__NR_##name),"0" ((long)(&__s)),"c" ((long)(arg2)), \ |
| 408 | "d" ((long)(arg3)),"S" ((long)(arg4)),"D" ((long)(arg5)), \ | 414 | "d" ((long)(arg3)),"S" ((long)(arg4)),"D" ((long)(arg5)) \ |
| 409 | "0" ((long)(arg6)) : "memory"); \ | 415 | : "memory"); \ |
| 410 | __syscall_return(type,__res); \ | 416 | __syscall_return(type,__res); \ |
| 411 | } | 417 | } |
| 412 | 418 | ||
