diff options
| author | Rafael J. Wysocki <rjw@sisk.pl> | 2011-12-21 03:51:23 -0500 |
|---|---|---|
| committer | Rafael J. Wysocki <rjw@sisk.pl> | 2011-12-21 03:51:23 -0500 |
| commit | dfa9d178cd28caf5d76bc4f37f4b3e7e8df8e697 (patch) | |
| tree | d97ca7790d8a622cba9fdd19832decdb0aa6418a /arch/arm/kernel | |
| parent | 3f19f08a7ec74cfc50fbad3c5e615760afbd23a0 (diff) | |
| parent | 7b4050381127ae11fcfc74a106d715a5fbbf888a (diff) | |
Merge branch 'devfreq-for-next' of git://git.infradead.org/users/kmpark/linux-samsung into pm-devfreq
* 'devfreq-for-next' of git://git.infradead.org/users/kmpark/linux-samsung: (765 commits)
PM/Devfreq: Add Exynos4-bus device DVFS driver for Exynos4210/4212/4412.
pci: Fix hotplug of Express Module with pci bridges
i2c-eg20t: correct the driver init order of pch_i2c_probe()
I2C: OMAP: fix FIFO usage for OMAP4
i2c-s3c2410: Fix return code of s3c24xx_i2c_parse_dt_gpio
i2c: i2c-s3c2410: Add a cpu_relax() to busy wait for bus idle
Linux 3.2-rc6
Revert "drm/i915: fix infinite recursion on unbind due to ilk vt-d w/a"
btrfs: lower the dirty balance poll interval
drm/i915/dp: Dither down to 6bpc if it makes the mode fit
drm/i915: enable semaphores on per-device defaults
drm/i915: don't set unpin_work if vblank_get fails
drm/i915: By default, enable RC6 on IVB and SNB when reasonable
iommu: Export intel_iommu_enabled to signal when iommu is in use
drm/i915/sdvo: Include LVDS panels for the IS_DIGITAL check
drm/i915: prevent division by zero when asking for chipset power
drm/i915: add PCH info to i915_capabilities
drm/i915: set the right SDVO transcoder for CPT
drm/i915: no-lvds quirk for ASUS AT5NM10T-I
sched: Fix select_idle_sibling() regression in selecting an idle SMT sibling
...
Diffstat (limited to 'arch/arm/kernel')
| -rw-r--r-- | arch/arm/kernel/entry-armv.S | 2 | ||||
| -rw-r--r-- | arch/arm/kernel/kprobes-arm.c | 4 | ||||
| -rw-r--r-- | arch/arm/kernel/kprobes-test-arm.c | 27 | ||||
| -rw-r--r-- | arch/arm/kernel/kprobes-test-thumb.c | 16 | ||||
| -rw-r--r-- | arch/arm/kernel/kprobes-test.h | 100 | ||||
| -rw-r--r-- | arch/arm/kernel/perf_event.c | 20 | ||||
| -rw-r--r-- | arch/arm/kernel/pmu.c | 1 | ||||
| -rw-r--r-- | arch/arm/kernel/process.c | 3 | ||||
| -rw-r--r-- | arch/arm/kernel/setup.c | 14 | ||||
| -rw-r--r-- | arch/arm/kernel/topology.c | 2 | ||||
| -rw-r--r-- | arch/arm/kernel/unwind.c | 129 |
11 files changed, 210 insertions, 108 deletions
diff --git a/arch/arm/kernel/entry-armv.S b/arch/arm/kernel/entry-armv.S index 9ad50c4208ae..b145f16c91bc 100644 --- a/arch/arm/kernel/entry-armv.S +++ b/arch/arm/kernel/entry-armv.S | |||
| @@ -497,7 +497,7 @@ ENDPROC(__und_usr) | |||
| 497 | .popsection | 497 | .popsection |
| 498 | .pushsection __ex_table,"a" | 498 | .pushsection __ex_table,"a" |
| 499 | .long 1b, 4b | 499 | .long 1b, 4b |
| 500 | #if __LINUX_ARM_ARCH__ >= 7 | 500 | #if CONFIG_ARM_THUMB && __LINUX_ARM_ARCH__ >= 6 && CONFIG_CPU_V7 |
| 501 | .long 2b, 4b | 501 | .long 2b, 4b |
| 502 | .long 3b, 4b | 502 | .long 3b, 4b |
| 503 | #endif | 503 | #endif |
diff --git a/arch/arm/kernel/kprobes-arm.c b/arch/arm/kernel/kprobes-arm.c index 9fe8910308af..8a30c89da70e 100644 --- a/arch/arm/kernel/kprobes-arm.c +++ b/arch/arm/kernel/kprobes-arm.c | |||
| @@ -519,10 +519,12 @@ static const union decode_item arm_cccc_0000_____1001_table[] = { | |||
| 519 | static const union decode_item arm_cccc_0001_____1001_table[] = { | 519 | static const union decode_item arm_cccc_0001_____1001_table[] = { |
| 520 | /* Synchronization primitives */ | 520 | /* Synchronization primitives */ |
| 521 | 521 | ||
| 522 | #if __LINUX_ARM_ARCH__ < 6 | ||
| 523 | /* Deprecated on ARMv6 and may be UNDEFINED on v7 */ | ||
| 522 | /* SMP/SWPB cccc 0001 0x00 xxxx xxxx xxxx 1001 xxxx */ | 524 | /* SMP/SWPB cccc 0001 0x00 xxxx xxxx xxxx 1001 xxxx */ |
| 523 | DECODE_EMULATEX (0x0fb000f0, 0x01000090, emulate_rd12rn16rm0_rwflags_nopc, | 525 | DECODE_EMULATEX (0x0fb000f0, 0x01000090, emulate_rd12rn16rm0_rwflags_nopc, |
| 524 | REGS(NOPC, NOPC, 0, 0, NOPC)), | 526 | REGS(NOPC, NOPC, 0, 0, NOPC)), |
| 525 | 527 | #endif | |
| 526 | /* LDREX/STREX{,D,B,H} cccc 0001 1xxx xxxx xxxx xxxx 1001 xxxx */ | 528 | /* LDREX/STREX{,D,B,H} cccc 0001 1xxx xxxx xxxx xxxx 1001 xxxx */ |
| 527 | /* And unallocated instructions... */ | 529 | /* And unallocated instructions... */ |
| 528 | DECODE_END | 530 | DECODE_END |
diff --git a/arch/arm/kernel/kprobes-test-arm.c b/arch/arm/kernel/kprobes-test-arm.c index fc82de8bdcce..ba32b393b3f0 100644 --- a/arch/arm/kernel/kprobes-test-arm.c +++ b/arch/arm/kernel/kprobes-test-arm.c | |||
| @@ -427,18 +427,25 @@ void kprobe_arm_test_cases(void) | |||
| 427 | 427 | ||
| 428 | TEST_GROUP("Synchronization primitives") | 428 | TEST_GROUP("Synchronization primitives") |
| 429 | 429 | ||
| 430 | /* | 430 | #if __LINUX_ARM_ARCH__ < 6 |
| 431 | * Use hard coded constants for SWP instructions to avoid warnings | 431 | TEST_RP("swp lr, r",7,VAL2,", [r",8,0,"]") |
| 432 | * about deprecated instructions. | 432 | TEST_R( "swpvs r0, r",1,VAL1,", [sp]") |
| 433 | */ | 433 | TEST_RP("swp sp, r",14,VAL2,", [r",12,13*4,"]") |
| 434 | TEST_RP( ".word 0xe108e097 @ swp lr, r",7,VAL2,", [r",8,0,"]") | 434 | #else |
| 435 | TEST_R( ".word 0x610d0091 @ swpvs r0, r",1,VAL1,", [sp]") | 435 | TEST_UNSUPPORTED(".word 0xe108e097 @ swp lr, r7, [r8]") |
| 436 | TEST_RP( ".word 0xe10cd09e @ swp sp, r",14,VAL2,", [r",12,13*4,"]") | 436 | TEST_UNSUPPORTED(".word 0x610d0091 @ swpvs r0, r1, [sp]") |
| 437 | TEST_UNSUPPORTED(".word 0xe10cd09e @ swp sp, r14 [r12]") | ||
| 438 | #endif | ||
| 437 | TEST_UNSUPPORTED(".word 0xe102f091 @ swp pc, r1, [r2]") | 439 | TEST_UNSUPPORTED(".word 0xe102f091 @ swp pc, r1, [r2]") |
| 438 | TEST_UNSUPPORTED(".word 0xe102009f @ swp r0, pc, [r2]") | 440 | TEST_UNSUPPORTED(".word 0xe102009f @ swp r0, pc, [r2]") |
| 439 | TEST_UNSUPPORTED(".word 0xe10f0091 @ swp r0, r1, [pc]") | 441 | TEST_UNSUPPORTED(".word 0xe10f0091 @ swp r0, r1, [pc]") |
| 440 | TEST_RP( ".word 0xe148e097 @ swpb lr, r",7,VAL2,", [r",8,0,"]") | 442 | #if __LINUX_ARM_ARCH__ < 6 |
| 441 | TEST_R( ".word 0x614d0091 @ swpvsb r0, r",1,VAL1,", [sp]") | 443 | TEST_RP("swpb lr, r",7,VAL2,", [r",8,0,"]") |
| 444 | TEST_R( "swpvsb r0, r",1,VAL1,", [sp]") | ||
| 445 | #else | ||
| 446 | TEST_UNSUPPORTED(".word 0xe148e097 @ swpb lr, r7, [r8]") | ||
| 447 | TEST_UNSUPPORTED(".word 0x614d0091 @ swpvsb r0, r1, [sp]") | ||
| 448 | #endif | ||
| 442 | TEST_UNSUPPORTED(".word 0xe142f091 @ swpb pc, r1, [r2]") | 449 | TEST_UNSUPPORTED(".word 0xe142f091 @ swpb pc, r1, [r2]") |
| 443 | 450 | ||
| 444 | TEST_UNSUPPORTED(".word 0xe1100090") /* Unallocated space */ | 451 | TEST_UNSUPPORTED(".word 0xe1100090") /* Unallocated space */ |
| @@ -550,7 +557,7 @@ void kprobe_arm_test_cases(void) | |||
| 550 | TEST_RPR( "strccd r",8, VAL2,", [r",13,0, ", r",12,48,"]") | 557 | TEST_RPR( "strccd r",8, VAL2,", [r",13,0, ", r",12,48,"]") |
| 551 | TEST_RPR( "strd r",4, VAL1,", [r",2, 24,", r",3, 48,"]!") | 558 | TEST_RPR( "strd r",4, VAL1,", [r",2, 24,", r",3, 48,"]!") |
| 552 | TEST_RPR( "strcsd r",12,VAL2,", [r",11,48,", -r",10,24,"]!") | 559 | TEST_RPR( "strcsd r",12,VAL2,", [r",11,48,", -r",10,24,"]!") |
| 553 | TEST_RPR( "strd r",2, VAL1,", [r",3, 24,"], r",4,48,"") | 560 | TEST_RPR( "strd r",2, VAL1,", [r",5, 24,"], r",4,48,"") |
| 554 | TEST_RPR( "strd r",10,VAL2,", [r",9, 48,"], -r",7,24,"") | 561 | TEST_RPR( "strd r",10,VAL2,", [r",9, 48,"], -r",7,24,"") |
| 555 | TEST_UNSUPPORTED(".word 0xe1afc0fa @ strd r12, [pc, r10]!") | 562 | TEST_UNSUPPORTED(".word 0xe1afc0fa @ strd r12, [pc, r10]!") |
| 556 | 563 | ||
diff --git a/arch/arm/kernel/kprobes-test-thumb.c b/arch/arm/kernel/kprobes-test-thumb.c index 5e726c31c45a..5d8b85792222 100644 --- a/arch/arm/kernel/kprobes-test-thumb.c +++ b/arch/arm/kernel/kprobes-test-thumb.c | |||
| @@ -222,8 +222,8 @@ void kprobe_thumb16_test_cases(void) | |||
| 222 | DONT_TEST_IN_ITBLOCK( | 222 | DONT_TEST_IN_ITBLOCK( |
| 223 | TEST_BF_R( "cbnz r",0,0, ", 2f") | 223 | TEST_BF_R( "cbnz r",0,0, ", 2f") |
| 224 | TEST_BF_R( "cbz r",2,-1,", 2f") | 224 | TEST_BF_R( "cbz r",2,-1,", 2f") |
| 225 | TEST_BF_RX( "cbnz r",4,1, ", 2f",0x20) | 225 | TEST_BF_RX( "cbnz r",4,1, ", 2f", SPACE_0x20) |
| 226 | TEST_BF_RX( "cbz r",7,0, ", 2f",0x40) | 226 | TEST_BF_RX( "cbz r",7,0, ", 2f", SPACE_0x40) |
| 227 | ) | 227 | ) |
| 228 | TEST_R("sxth r0, r",7, HH1,"") | 228 | TEST_R("sxth r0, r",7, HH1,"") |
| 229 | TEST_R("sxth r7, r",0, HH2,"") | 229 | TEST_R("sxth r7, r",0, HH2,"") |
| @@ -246,7 +246,7 @@ DONT_TEST_IN_ITBLOCK( | |||
| 246 | TESTCASE_START(code) \ | 246 | TESTCASE_START(code) \ |
| 247 | TEST_ARG_PTR(13, offset) \ | 247 | TEST_ARG_PTR(13, offset) \ |
| 248 | TEST_ARG_END("") \ | 248 | TEST_ARG_END("") \ |
| 249 | TEST_BRANCH_F(code,0) \ | 249 | TEST_BRANCH_F(code) \ |
| 250 | TESTCASE_END | 250 | TESTCASE_END |
| 251 | 251 | ||
| 252 | TEST("push {r0}") | 252 | TEST("push {r0}") |
| @@ -319,8 +319,8 @@ CONDITION_INSTRUCTIONS(8, | |||
| 319 | 319 | ||
| 320 | TEST_BF( "b 2f") | 320 | TEST_BF( "b 2f") |
| 321 | TEST_BB( "b 2b") | 321 | TEST_BB( "b 2b") |
| 322 | TEST_BF_X("b 2f", 0x400) | 322 | TEST_BF_X("b 2f", SPACE_0x400) |
| 323 | TEST_BB_X("b 2b", 0x400) | 323 | TEST_BB_X("b 2b", SPACE_0x400) |
| 324 | 324 | ||
| 325 | TEST_GROUP("Testing instructions in IT blocks") | 325 | TEST_GROUP("Testing instructions in IT blocks") |
| 326 | 326 | ||
| @@ -746,7 +746,7 @@ CONDITION_INSTRUCTIONS(22, | |||
| 746 | TEST_BB("bne.w 2b") | 746 | TEST_BB("bne.w 2b") |
| 747 | TEST_BF("bgt.w 2f") | 747 | TEST_BF("bgt.w 2f") |
| 748 | TEST_BB("blt.w 2b") | 748 | TEST_BB("blt.w 2b") |
| 749 | TEST_BF_X("bpl.w 2f",0x1000) | 749 | TEST_BF_X("bpl.w 2f", SPACE_0x1000) |
| 750 | ) | 750 | ) |
| 751 | 751 | ||
| 752 | TEST_UNSUPPORTED("msr cpsr, r0") | 752 | TEST_UNSUPPORTED("msr cpsr, r0") |
| @@ -786,11 +786,11 @@ CONDITION_INSTRUCTIONS(22, | |||
| 786 | 786 | ||
| 787 | TEST_BF( "b.w 2f") | 787 | TEST_BF( "b.w 2f") |
| 788 | TEST_BB( "b.w 2b") | 788 | TEST_BB( "b.w 2b") |
| 789 | TEST_BF_X("b.w 2f", 0x1000) | 789 | TEST_BF_X("b.w 2f", SPACE_0x1000) |
| 790 | 790 | ||
| 791 | TEST_BF( "bl.w 2f") | 791 | TEST_BF( "bl.w 2f") |
| 792 | TEST_BB( "bl.w 2b") | 792 | TEST_BB( "bl.w 2b") |
| 793 | TEST_BB_X("bl.w 2b", 0x1000) | 793 | TEST_BB_X("bl.w 2b", SPACE_0x1000) |
| 794 | 794 | ||
| 795 | TEST_X( "blx __dummy_arm_subroutine", | 795 | TEST_X( "blx __dummy_arm_subroutine", |
| 796 | ".arm \n\t" | 796 | ".arm \n\t" |
diff --git a/arch/arm/kernel/kprobes-test.h b/arch/arm/kernel/kprobes-test.h index 0dc5d77b9356..e28a869b1ae4 100644 --- a/arch/arm/kernel/kprobes-test.h +++ b/arch/arm/kernel/kprobes-test.h | |||
| @@ -149,23 +149,31 @@ struct test_arg_end { | |||
| 149 | "1: "instruction" \n\t" \ | 149 | "1: "instruction" \n\t" \ |
| 150 | " nop \n\t" | 150 | " nop \n\t" |
| 151 | 151 | ||
| 152 | #define TEST_BRANCH_F(instruction, xtra_dist) \ | 152 | #define TEST_BRANCH_F(instruction) \ |
| 153 | TEST_INSTRUCTION(instruction) \ | 153 | TEST_INSTRUCTION(instruction) \ |
| 154 | ".if "#xtra_dist" \n\t" \ | ||
| 155 | " b 99f \n\t" \ | 154 | " b 99f \n\t" \ |
| 156 | ".space "#xtra_dist" \n\t" \ | 155 | "2: nop \n\t" |
| 157 | ".endif \n\t" \ | 156 | |
| 157 | #define TEST_BRANCH_B(instruction) \ | ||
| 158 | " b 50f \n\t" \ | ||
| 159 | " b 99f \n\t" \ | ||
| 160 | "2: nop \n\t" \ | ||
| 161 | " b 99f \n\t" \ | ||
| 162 | TEST_INSTRUCTION(instruction) | ||
| 163 | |||
| 164 | #define TEST_BRANCH_FX(instruction, codex) \ | ||
| 165 | TEST_INSTRUCTION(instruction) \ | ||
| 166 | " b 99f \n\t" \ | ||
| 167 | codex" \n\t" \ | ||
| 158 | " b 99f \n\t" \ | 168 | " b 99f \n\t" \ |
| 159 | "2: nop \n\t" | 169 | "2: nop \n\t" |
| 160 | 170 | ||
| 161 | #define TEST_BRANCH_B(instruction, xtra_dist) \ | 171 | #define TEST_BRANCH_BX(instruction, codex) \ |
| 162 | " b 50f \n\t" \ | 172 | " b 50f \n\t" \ |
| 163 | " b 99f \n\t" \ | 173 | " b 99f \n\t" \ |
| 164 | "2: nop \n\t" \ | 174 | "2: nop \n\t" \ |
| 165 | " b 99f \n\t" \ | 175 | " b 99f \n\t" \ |
| 166 | ".if "#xtra_dist" \n\t" \ | 176 | codex" \n\t" \ |
| 167 | ".space "#xtra_dist" \n\t" \ | ||
| 168 | ".endif \n\t" \ | ||
| 169 | TEST_INSTRUCTION(instruction) | 177 | TEST_INSTRUCTION(instruction) |
| 170 | 178 | ||
| 171 | #define TESTCASE_END \ | 179 | #define TESTCASE_END \ |
| @@ -301,47 +309,60 @@ struct test_arg_end { | |||
| 301 | TESTCASE_START(code1 #reg1 code2) \ | 309 | TESTCASE_START(code1 #reg1 code2) \ |
| 302 | TEST_ARG_PTR(reg1, val1) \ | 310 | TEST_ARG_PTR(reg1, val1) \ |
| 303 | TEST_ARG_END("") \ | 311 | TEST_ARG_END("") \ |
| 304 | TEST_BRANCH_F(code1 #reg1 code2, 0) \ | 312 | TEST_BRANCH_F(code1 #reg1 code2) \ |
| 305 | TESTCASE_END | 313 | TESTCASE_END |
| 306 | 314 | ||
| 307 | #define TEST_BF_X(code, xtra_dist) \ | 315 | #define TEST_BF(code) \ |
| 308 | TESTCASE_START(code) \ | 316 | TESTCASE_START(code) \ |
| 309 | TEST_ARG_END("") \ | 317 | TEST_ARG_END("") \ |
| 310 | TEST_BRANCH_F(code, xtra_dist) \ | 318 | TEST_BRANCH_F(code) \ |
| 311 | TESTCASE_END | 319 | TESTCASE_END |
| 312 | 320 | ||
| 313 | #define TEST_BB_X(code, xtra_dist) \ | 321 | #define TEST_BB(code) \ |
| 314 | TESTCASE_START(code) \ | 322 | TESTCASE_START(code) \ |
| 315 | TEST_ARG_END("") \ | 323 | TEST_ARG_END("") \ |
| 316 | TEST_BRANCH_B(code, xtra_dist) \ | 324 | TEST_BRANCH_B(code) \ |
| 317 | TESTCASE_END | 325 | TESTCASE_END |
| 318 | 326 | ||
| 319 | #define TEST_BF_RX(code1, reg, val, code2, xtra_dist) \ | 327 | #define TEST_BF_R(code1, reg, val, code2) \ |
| 320 | TESTCASE_START(code1 #reg code2) \ | 328 | TESTCASE_START(code1 #reg code2) \ |
| 321 | TEST_ARG_REG(reg, val) \ | 329 | TEST_ARG_REG(reg, val) \ |
| 322 | TEST_ARG_END("") \ | 330 | TEST_ARG_END("") \ |
| 323 | TEST_BRANCH_F(code1 #reg code2, xtra_dist) \ | 331 | TEST_BRANCH_F(code1 #reg code2) \ |
| 324 | TESTCASE_END | 332 | TESTCASE_END |
| 325 | 333 | ||
| 326 | #define TEST_BB_RX(code1, reg, val, code2, xtra_dist) \ | 334 | #define TEST_BB_R(code1, reg, val, code2) \ |
| 327 | TESTCASE_START(code1 #reg code2) \ | 335 | TESTCASE_START(code1 #reg code2) \ |
| 328 | TEST_ARG_REG(reg, val) \ | 336 | TEST_ARG_REG(reg, val) \ |
| 329 | TEST_ARG_END("") \ | 337 | TEST_ARG_END("") \ |
| 330 | TEST_BRANCH_B(code1 #reg code2, xtra_dist) \ | 338 | TEST_BRANCH_B(code1 #reg code2) \ |
| 331 | TESTCASE_END | 339 | TESTCASE_END |
| 332 | 340 | ||
| 333 | #define TEST_BF(code) TEST_BF_X(code, 0) | ||
| 334 | #define TEST_BB(code) TEST_BB_X(code, 0) | ||
| 335 | |||
| 336 | #define TEST_BF_R(code1, reg, val, code2) TEST_BF_RX(code1, reg, val, code2, 0) | ||
| 337 | #define TEST_BB_R(code1, reg, val, code2) TEST_BB_RX(code1, reg, val, code2, 0) | ||
| 338 | |||
| 339 | #define TEST_BF_RR(code1, reg1, val1, code2, reg2, val2, code3) \ | 341 | #define TEST_BF_RR(code1, reg1, val1, code2, reg2, val2, code3) \ |
| 340 | TESTCASE_START(code1 #reg1 code2 #reg2 code3) \ | 342 | TESTCASE_START(code1 #reg1 code2 #reg2 code3) \ |
| 341 | TEST_ARG_REG(reg1, val1) \ | 343 | TEST_ARG_REG(reg1, val1) \ |
| 342 | TEST_ARG_REG(reg2, val2) \ | 344 | TEST_ARG_REG(reg2, val2) \ |
| 343 | TEST_ARG_END("") \ | 345 | TEST_ARG_END("") \ |
| 344 | TEST_BRANCH_F(code1 #reg1 code2 #reg2 code3, 0) \ | 346 | TEST_BRANCH_F(code1 #reg1 code2 #reg2 code3) \ |
| 347 | TESTCASE_END | ||
| 348 | |||
| 349 | #define TEST_BF_X(code, codex) \ | ||
| 350 | TESTCASE_START(code) \ | ||
| 351 | TEST_ARG_END("") \ | ||
| 352 | TEST_BRANCH_FX(code, codex) \ | ||
| 353 | TESTCASE_END | ||
| 354 | |||
| 355 | #define TEST_BB_X(code, codex) \ | ||
| 356 | TESTCASE_START(code) \ | ||
| 357 | TEST_ARG_END("") \ | ||
| 358 | TEST_BRANCH_BX(code, codex) \ | ||
| 359 | TESTCASE_END | ||
| 360 | |||
| 361 | #define TEST_BF_RX(code1, reg, val, code2, codex) \ | ||
| 362 | TESTCASE_START(code1 #reg code2) \ | ||
| 363 | TEST_ARG_REG(reg, val) \ | ||
| 364 | TEST_ARG_END("") \ | ||
| 365 | TEST_BRANCH_FX(code1 #reg code2, codex) \ | ||
| 345 | TESTCASE_END | 366 | TESTCASE_END |
| 346 | 367 | ||
| 347 | #define TEST_X(code, codex) \ | 368 | #define TEST_X(code, codex) \ |
| @@ -372,6 +393,25 @@ struct test_arg_end { | |||
| 372 | TESTCASE_END | 393 | TESTCASE_END |
| 373 | 394 | ||
| 374 | 395 | ||
| 396 | /* | ||
| 397 | * Macros for defining space directives spread over multiple lines. | ||
| 398 | * These are required so the compiler guesses better the length of inline asm | ||
| 399 | * code and will spill the literal pool early enough to avoid generating PC | ||
| 400 | * relative loads with out of range offsets. | ||
| 401 | */ | ||
| 402 | #define TWICE(x) x x | ||
| 403 | #define SPACE_0x8 TWICE(".space 4\n\t") | ||
| 404 | #define SPACE_0x10 TWICE(SPACE_0x8) | ||
| 405 | #define SPACE_0x20 TWICE(SPACE_0x10) | ||
| 406 | #define SPACE_0x40 TWICE(SPACE_0x20) | ||
| 407 | #define SPACE_0x80 TWICE(SPACE_0x40) | ||
| 408 | #define SPACE_0x100 TWICE(SPACE_0x80) | ||
| 409 | #define SPACE_0x200 TWICE(SPACE_0x100) | ||
| 410 | #define SPACE_0x400 TWICE(SPACE_0x200) | ||
| 411 | #define SPACE_0x800 TWICE(SPACE_0x400) | ||
| 412 | #define SPACE_0x1000 TWICE(SPACE_0x800) | ||
| 413 | |||
| 414 | |||
| 375 | /* Various values used in test cases... */ | 415 | /* Various values used in test cases... */ |
| 376 | #define N(val) (val ^ 0xffffffff) | 416 | #define N(val) (val ^ 0xffffffff) |
| 377 | #define VAL1 0x12345678 | 417 | #define VAL1 0x12345678 |
diff --git a/arch/arm/kernel/perf_event.c b/arch/arm/kernel/perf_event.c index 24e2347be6b1..88b0941ce51e 100644 --- a/arch/arm/kernel/perf_event.c +++ b/arch/arm/kernel/perf_event.c | |||
| @@ -343,19 +343,25 @@ validate_group(struct perf_event *event) | |||
| 343 | { | 343 | { |
| 344 | struct perf_event *sibling, *leader = event->group_leader; | 344 | struct perf_event *sibling, *leader = event->group_leader; |
| 345 | struct pmu_hw_events fake_pmu; | 345 | struct pmu_hw_events fake_pmu; |
| 346 | DECLARE_BITMAP(fake_used_mask, ARMPMU_MAX_HWEVENTS); | ||
| 346 | 347 | ||
| 347 | memset(&fake_pmu, 0, sizeof(fake_pmu)); | 348 | /* |
| 349 | * Initialise the fake PMU. We only need to populate the | ||
| 350 | * used_mask for the purposes of validation. | ||
| 351 | */ | ||
| 352 | memset(fake_used_mask, 0, sizeof(fake_used_mask)); | ||
| 353 | fake_pmu.used_mask = fake_used_mask; | ||
| 348 | 354 | ||
| 349 | if (!validate_event(&fake_pmu, leader)) | 355 | if (!validate_event(&fake_pmu, leader)) |
| 350 | return -ENOSPC; | 356 | return -EINVAL; |
| 351 | 357 | ||
| 352 | list_for_each_entry(sibling, &leader->sibling_list, group_entry) { | 358 | list_for_each_entry(sibling, &leader->sibling_list, group_entry) { |
| 353 | if (!validate_event(&fake_pmu, sibling)) | 359 | if (!validate_event(&fake_pmu, sibling)) |
| 354 | return -ENOSPC; | 360 | return -EINVAL; |
| 355 | } | 361 | } |
| 356 | 362 | ||
| 357 | if (!validate_event(&fake_pmu, event)) | 363 | if (!validate_event(&fake_pmu, event)) |
| 358 | return -ENOSPC; | 364 | return -EINVAL; |
| 359 | 365 | ||
| 360 | return 0; | 366 | return 0; |
| 361 | } | 367 | } |
| @@ -396,6 +402,9 @@ armpmu_reserve_hardware(struct arm_pmu *armpmu) | |||
| 396 | int i, err, irq, irqs; | 402 | int i, err, irq, irqs; |
| 397 | struct platform_device *pmu_device = armpmu->plat_device; | 403 | struct platform_device *pmu_device = armpmu->plat_device; |
| 398 | 404 | ||
| 405 | if (!pmu_device) | ||
| 406 | return -ENODEV; | ||
| 407 | |||
| 399 | err = reserve_pmu(armpmu->type); | 408 | err = reserve_pmu(armpmu->type); |
| 400 | if (err) { | 409 | if (err) { |
| 401 | pr_warning("unable to reserve pmu\n"); | 410 | pr_warning("unable to reserve pmu\n"); |
| @@ -631,6 +640,9 @@ static struct platform_device_id armpmu_plat_device_ids[] = { | |||
| 631 | 640 | ||
| 632 | static int __devinit armpmu_device_probe(struct platform_device *pdev) | 641 | static int __devinit armpmu_device_probe(struct platform_device *pdev) |
| 633 | { | 642 | { |
| 643 | if (!cpu_pmu) | ||
| 644 | return -ENODEV; | ||
| 645 | |||
| 634 | cpu_pmu->plat_device = pdev; | 646 | cpu_pmu->plat_device = pdev; |
| 635 | return 0; | 647 | return 0; |
| 636 | } | 648 | } |
diff --git a/arch/arm/kernel/pmu.c b/arch/arm/kernel/pmu.c index 2c3407ee8576..2334bf8a650a 100644 --- a/arch/arm/kernel/pmu.c +++ b/arch/arm/kernel/pmu.c | |||
| @@ -33,3 +33,4 @@ release_pmu(enum arm_pmu_type type) | |||
| 33 | { | 33 | { |
| 34 | clear_bit_unlock(type, pmu_lock); | 34 | clear_bit_unlock(type, pmu_lock); |
| 35 | } | 35 | } |
| 36 | EXPORT_SYMBOL_GPL(release_pmu); | ||
diff --git a/arch/arm/kernel/process.c b/arch/arm/kernel/process.c index 75316f0dd02a..3d0c6fb74ae4 100644 --- a/arch/arm/kernel/process.c +++ b/arch/arm/kernel/process.c | |||
| @@ -192,6 +192,9 @@ void cpu_idle(void) | |||
| 192 | #endif | 192 | #endif |
| 193 | 193 | ||
| 194 | local_irq_disable(); | 194 | local_irq_disable(); |
| 195 | #ifdef CONFIG_PL310_ERRATA_769419 | ||
| 196 | wmb(); | ||
| 197 | #endif | ||
| 195 | if (hlt_counter) { | 198 | if (hlt_counter) { |
| 196 | local_irq_enable(); | 199 | local_irq_enable(); |
| 197 | cpu_relax(); | 200 | cpu_relax(); |
diff --git a/arch/arm/kernel/setup.c b/arch/arm/kernel/setup.c index 3448a3f9cc8c..8fc2c8fcbdc6 100644 --- a/arch/arm/kernel/setup.c +++ b/arch/arm/kernel/setup.c | |||
| @@ -895,8 +895,6 @@ void __init setup_arch(char **cmdline_p) | |||
| 895 | { | 895 | { |
| 896 | struct machine_desc *mdesc; | 896 | struct machine_desc *mdesc; |
| 897 | 897 | ||
| 898 | unwind_init(); | ||
| 899 | |||
| 900 | setup_processor(); | 898 | setup_processor(); |
| 901 | mdesc = setup_machine_fdt(__atags_pointer); | 899 | mdesc = setup_machine_fdt(__atags_pointer); |
| 902 | if (!mdesc) | 900 | if (!mdesc) |
| @@ -904,6 +902,12 @@ void __init setup_arch(char **cmdline_p) | |||
| 904 | machine_desc = mdesc; | 902 | machine_desc = mdesc; |
| 905 | machine_name = mdesc->name; | 903 | machine_name = mdesc->name; |
| 906 | 904 | ||
| 905 | #ifdef CONFIG_ZONE_DMA | ||
| 906 | if (mdesc->dma_zone_size) { | ||
| 907 | extern unsigned long arm_dma_zone_size; | ||
| 908 | arm_dma_zone_size = mdesc->dma_zone_size; | ||
| 909 | } | ||
| 910 | #endif | ||
| 907 | if (mdesc->soft_reboot) | 911 | if (mdesc->soft_reboot) |
| 908 | reboot_setup("s"); | 912 | reboot_setup("s"); |
| 909 | 913 | ||
| @@ -934,12 +938,6 @@ void __init setup_arch(char **cmdline_p) | |||
| 934 | 938 | ||
| 935 | tcm_init(); | 939 | tcm_init(); |
| 936 | 940 | ||
| 937 | #ifdef CONFIG_ZONE_DMA | ||
| 938 | if (mdesc->dma_zone_size) { | ||
| 939 | extern unsigned long arm_dma_zone_size; | ||
| 940 | arm_dma_zone_size = mdesc->dma_zone_size; | ||
| 941 | } | ||
| 942 | #endif | ||
| 943 | #ifdef CONFIG_MULTI_IRQ_HANDLER | 941 | #ifdef CONFIG_MULTI_IRQ_HANDLER |
| 944 | handle_arch_irq = mdesc->handle_irq; | 942 | handle_arch_irq = mdesc->handle_irq; |
| 945 | #endif | 943 | #endif |
diff --git a/arch/arm/kernel/topology.c b/arch/arm/kernel/topology.c index 1040c00405d0..8200deaa14f6 100644 --- a/arch/arm/kernel/topology.c +++ b/arch/arm/kernel/topology.c | |||
| @@ -43,7 +43,7 @@ | |||
| 43 | 43 | ||
| 44 | struct cputopo_arm cpu_topology[NR_CPUS]; | 44 | struct cputopo_arm cpu_topology[NR_CPUS]; |
| 45 | 45 | ||
| 46 | const struct cpumask *cpu_coregroup_mask(unsigned int cpu) | 46 | const struct cpumask *cpu_coregroup_mask(int cpu) |
| 47 | { | 47 | { |
| 48 | return &cpu_topology[cpu].core_sibling; | 48 | return &cpu_topology[cpu].core_sibling; |
| 49 | } | 49 | } |
diff --git a/arch/arm/kernel/unwind.c b/arch/arm/kernel/unwind.c index e7e8365795c3..00df012c4678 100644 --- a/arch/arm/kernel/unwind.c +++ b/arch/arm/kernel/unwind.c | |||
| @@ -67,7 +67,7 @@ EXPORT_SYMBOL(__aeabi_unwind_cpp_pr2); | |||
| 67 | 67 | ||
| 68 | struct unwind_ctrl_block { | 68 | struct unwind_ctrl_block { |
| 69 | unsigned long vrs[16]; /* virtual register set */ | 69 | unsigned long vrs[16]; /* virtual register set */ |
| 70 | unsigned long *insn; /* pointer to the current instructions word */ | 70 | const unsigned long *insn; /* pointer to the current instructions word */ |
| 71 | int entries; /* number of entries left to interpret */ | 71 | int entries; /* number of entries left to interpret */ |
| 72 | int byte; /* current byte number in the instructions word */ | 72 | int byte; /* current byte number in the instructions word */ |
| 73 | }; | 73 | }; |
| @@ -83,8 +83,9 @@ enum regs { | |||
| 83 | PC = 15 | 83 | PC = 15 |
| 84 | }; | 84 | }; |
| 85 | 85 | ||
| 86 | extern struct unwind_idx __start_unwind_idx[]; | 86 | extern const struct unwind_idx __start_unwind_idx[]; |
| 87 | extern struct unwind_idx __stop_unwind_idx[]; | 87 | static const struct unwind_idx *__origin_unwind_idx; |
| 88 | extern const struct unwind_idx __stop_unwind_idx[]; | ||
| 88 | 89 | ||
| 89 | static DEFINE_SPINLOCK(unwind_lock); | 90 | static DEFINE_SPINLOCK(unwind_lock); |
| 90 | static LIST_HEAD(unwind_tables); | 91 | static LIST_HEAD(unwind_tables); |
| @@ -98,45 +99,99 @@ static LIST_HEAD(unwind_tables); | |||
| 98 | }) | 99 | }) |
| 99 | 100 | ||
| 100 | /* | 101 | /* |
| 101 | * Binary search in the unwind index. The entries entries are | 102 | * Binary search in the unwind index. The entries are |
| 102 | * guaranteed to be sorted in ascending order by the linker. | 103 | * guaranteed to be sorted in ascending order by the linker. |
| 104 | * | ||
| 105 | * start = first entry | ||
| 106 | * origin = first entry with positive offset (or stop if there is no such entry) | ||
| 107 | * stop - 1 = last entry | ||
| 103 | */ | 108 | */ |
| 104 | static struct unwind_idx *search_index(unsigned long addr, | 109 | static const struct unwind_idx *search_index(unsigned long addr, |
| 105 | struct unwind_idx *first, | 110 | const struct unwind_idx *start, |
| 106 | struct unwind_idx *last) | 111 | const struct unwind_idx *origin, |
| 112 | const struct unwind_idx *stop) | ||
| 107 | { | 113 | { |
| 108 | pr_debug("%s(%08lx, %p, %p)\n", __func__, addr, first, last); | 114 | unsigned long addr_prel31; |
| 115 | |||
| 116 | pr_debug("%s(%08lx, %p, %p, %p)\n", | ||
| 117 | __func__, addr, start, origin, stop); | ||
| 118 | |||
| 119 | /* | ||
| 120 | * only search in the section with the matching sign. This way the | ||
| 121 | * prel31 numbers can be compared as unsigned longs. | ||
| 122 | */ | ||
| 123 | if (addr < (unsigned long)start) | ||
| 124 | /* negative offsets: [start; origin) */ | ||
| 125 | stop = origin; | ||
| 126 | else | ||
| 127 | /* positive offsets: [origin; stop) */ | ||
| 128 | start = origin; | ||
| 129 | |||
| 130 | /* prel31 for address relavive to start */ | ||
| 131 | addr_prel31 = (addr - (unsigned long)start) & 0x7fffffff; | ||
| 109 | 132 | ||
| 110 | if (addr < first->addr) { | 133 | while (start < stop - 1) { |
| 134 | const struct unwind_idx *mid = start + ((stop - start) >> 1); | ||
| 135 | |||
| 136 | /* | ||
| 137 | * As addr_prel31 is relative to start an offset is needed to | ||
| 138 | * make it relative to mid. | ||
| 139 | */ | ||
| 140 | if (addr_prel31 - ((unsigned long)mid - (unsigned long)start) < | ||
| 141 | mid->addr_offset) | ||
| 142 | stop = mid; | ||
| 143 | else { | ||
| 144 | /* keep addr_prel31 relative to start */ | ||
| 145 | addr_prel31 -= ((unsigned long)mid - | ||
| 146 | (unsigned long)start); | ||
| 147 | start = mid; | ||
| 148 | } | ||
| 149 | } | ||
| 150 | |||
| 151 | if (likely(start->addr_offset <= addr_prel31)) | ||
| 152 | return start; | ||
| 153 | else { | ||
| 111 | pr_warning("unwind: Unknown symbol address %08lx\n", addr); | 154 | pr_warning("unwind: Unknown symbol address %08lx\n", addr); |
| 112 | return NULL; | 155 | return NULL; |
| 113 | } else if (addr >= last->addr) | 156 | } |
| 114 | return last; | 157 | } |
| 115 | 158 | ||
| 116 | while (first < last - 1) { | 159 | static const struct unwind_idx *unwind_find_origin( |
| 117 | struct unwind_idx *mid = first + ((last - first + 1) >> 1); | 160 | const struct unwind_idx *start, const struct unwind_idx *stop) |
| 161 | { | ||
| 162 | pr_debug("%s(%p, %p)\n", __func__, start, stop); | ||
| 163 | while (start < stop) { | ||
| 164 | const struct unwind_idx *mid = start + ((stop - start) >> 1); | ||
| 118 | 165 | ||
| 119 | if (addr < mid->addr) | 166 | if (mid->addr_offset >= 0x40000000) |
| 120 | last = mid; | 167 | /* negative offset */ |
| 168 | start = mid + 1; | ||
| 121 | else | 169 | else |
| 122 | first = mid; | 170 | /* positive offset */ |
| 171 | stop = mid; | ||
| 123 | } | 172 | } |
| 124 | 173 | pr_debug("%s -> %p\n", __func__, stop); | |
| 125 | return first; | 174 | return stop; |
| 126 | } | 175 | } |
| 127 | 176 | ||
| 128 | static struct unwind_idx *unwind_find_idx(unsigned long addr) | 177 | static const struct unwind_idx *unwind_find_idx(unsigned long addr) |
| 129 | { | 178 | { |
| 130 | struct unwind_idx *idx = NULL; | 179 | const struct unwind_idx *idx = NULL; |
| 131 | unsigned long flags; | 180 | unsigned long flags; |
| 132 | 181 | ||
| 133 | pr_debug("%s(%08lx)\n", __func__, addr); | 182 | pr_debug("%s(%08lx)\n", __func__, addr); |
| 134 | 183 | ||
| 135 | if (core_kernel_text(addr)) | 184 | if (core_kernel_text(addr)) { |
| 185 | if (unlikely(!__origin_unwind_idx)) | ||
| 186 | __origin_unwind_idx = | ||
| 187 | unwind_find_origin(__start_unwind_idx, | ||
| 188 | __stop_unwind_idx); | ||
| 189 | |||
| 136 | /* main unwind table */ | 190 | /* main unwind table */ |
| 137 | idx = search_index(addr, __start_unwind_idx, | 191 | idx = search_index(addr, __start_unwind_idx, |
| 138 | __stop_unwind_idx - 1); | 192 | __origin_unwind_idx, |
| 139 | else { | 193 | __stop_unwind_idx); |
| 194 | } else { | ||
| 140 | /* module unwind tables */ | 195 | /* module unwind tables */ |
| 141 | struct unwind_table *table; | 196 | struct unwind_table *table; |
| 142 | 197 | ||
| @@ -145,7 +200,8 @@ static struct unwind_idx *unwind_find_idx(unsigned long addr) | |||
| 145 | if (addr >= table->begin_addr && | 200 | if (addr >= table->begin_addr && |
| 146 | addr < table->end_addr) { | 201 | addr < table->end_addr) { |
| 147 | idx = search_index(addr, table->start, | 202 | idx = search_index(addr, table->start, |
| 148 | table->stop - 1); | 203 | table->origin, |
| 204 | table->stop); | ||
| 149 | /* Move-to-front to exploit common traces */ | 205 | /* Move-to-front to exploit common traces */ |
| 150 | list_move(&table->list, &unwind_tables); | 206 | list_move(&table->list, &unwind_tables); |
| 151 | break; | 207 | break; |
| @@ -274,7 +330,7 @@ static int unwind_exec_insn(struct unwind_ctrl_block *ctrl) | |||
| 274 | int unwind_frame(struct stackframe *frame) | 330 | int unwind_frame(struct stackframe *frame) |
| 275 | { | 331 | { |
| 276 | unsigned long high, low; | 332 | unsigned long high, low; |
| 277 | struct unwind_idx *idx; | 333 | const struct unwind_idx *idx; |
| 278 | struct unwind_ctrl_block ctrl; | 334 | struct unwind_ctrl_block ctrl; |
| 279 | 335 | ||
| 280 | /* only go to a higher address on the stack */ | 336 | /* only go to a higher address on the stack */ |
| @@ -399,7 +455,6 @@ struct unwind_table *unwind_table_add(unsigned long start, unsigned long size, | |||
| 399 | unsigned long text_size) | 455 | unsigned long text_size) |
| 400 | { | 456 | { |
| 401 | unsigned long flags; | 457 | unsigned long flags; |
| 402 | struct unwind_idx *idx; | ||
| 403 | struct unwind_table *tab = kmalloc(sizeof(*tab), GFP_KERNEL); | 458 | struct unwind_table *tab = kmalloc(sizeof(*tab), GFP_KERNEL); |
| 404 | 459 | ||
| 405 | pr_debug("%s(%08lx, %08lx, %08lx, %08lx)\n", __func__, start, size, | 460 | pr_debug("%s(%08lx, %08lx, %08lx, %08lx)\n", __func__, start, size, |
| @@ -408,15 +463,12 @@ struct unwind_table *unwind_table_add(unsigned long start, unsigned long size, | |||
| 408 | if (!tab) | 463 | if (!tab) |
| 409 | return tab; | 464 | return tab; |
| 410 | 465 | ||
| 411 | tab->start = (struct unwind_idx *)start; | 466 | tab->start = (const struct unwind_idx *)start; |
| 412 | tab->stop = (struct unwind_idx *)(start + size); | 467 | tab->stop = (const struct unwind_idx *)(start + size); |
| 468 | tab->origin = unwind_find_origin(tab->start, tab->stop); | ||
| 413 | tab->begin_addr = text_addr; | 469 | tab->begin_addr = text_addr; |
| 414 | tab->end_addr = text_addr + text_size; | 470 | tab->end_addr = text_addr + text_size; |
| 415 | 471 | ||
| 416 | /* Convert the symbol addresses to absolute values */ | ||
| 417 | for (idx = tab->start; idx < tab->stop; idx++) | ||
| 418 | idx->addr = prel31_to_addr(&idx->addr); | ||
| 419 | |||
| 420 | spin_lock_irqsave(&unwind_lock, flags); | 472 | spin_lock_irqsave(&unwind_lock, flags); |
| 421 | list_add_tail(&tab->list, &unwind_tables); | 473 | list_add_tail(&tab->list, &unwind_tables); |
| 422 | spin_unlock_irqrestore(&unwind_lock, flags); | 474 | spin_unlock_irqrestore(&unwind_lock, flags); |
| @@ -437,16 +489,3 @@ void unwind_table_del(struct unwind_table *tab) | |||
| 437 | 489 | ||
| 438 | kfree(tab); | 490 | kfree(tab); |
| 439 | } | 491 | } |
| 440 | |||
| 441 | int __init unwind_init(void) | ||
| 442 | { | ||
| 443 | struct unwind_idx *idx; | ||
| 444 | |||
| 445 | /* Convert the symbol addresses to absolute values */ | ||
| 446 | for (idx = __start_unwind_idx; idx < __stop_unwind_idx; idx++) | ||
| 447 | idx->addr = prel31_to_addr(&idx->addr); | ||
| 448 | |||
| 449 | pr_debug("unwind: ARM stack unwinding initialised\n"); | ||
| 450 | |||
| 451 | return 0; | ||
| 452 | } | ||
