Commit | Line | Data |
---|---|---|
edeed305 AV |
1 | /* |
2 | * test_rodata.c: functional test for mark_rodata_ro function | |
3 | * | |
4 | * (C) Copyright 2008 Intel Corporation | |
5 | * Author: Arjan van de Ven <arjan@linux.intel.com> | |
6 | * | |
7 | * This program is free software; you can redistribute it and/or | |
8 | * modify it under the terms of the GNU General Public License | |
9 | * as published by the Free Software Foundation; version 2 | |
10 | * of the License. | |
11 | */ | |
12 | #include <linux/module.h> | |
7bfeab9a | 13 | #include <asm/cacheflush.h> |
edeed305 | 14 | #include <asm/sections.h> |
5d6f8d77 | 15 | #include <asm/asm.h> |
edeed305 AV |
16 | |
17 | int rodata_test(void) | |
18 | { | |
19 | unsigned long result; | |
20 | unsigned long start, end; | |
21 | ||
22 | /* test 1: read the value */ | |
23 | /* If this test fails, some previous testrun has clobbered the state */ | |
24 | if (!rodata_test_data) { | |
25 | printk(KERN_ERR "rodata_test: test 1 fails (start data)\n"); | |
26 | return -ENODEV; | |
27 | } | |
28 | ||
29 | /* test 2: write to the variable; this should fault */ | |
30 | /* | |
31 | * If this test fails, we managed to overwrite the data | |
32 | * | |
33 | * This is written in assembly to be able to catch the | |
34 | * exception that is supposed to happen in the correct | |
35 | * case | |
36 | */ | |
37 | ||
38 | result = 1; | |
39 | asm volatile( | |
40 | "0: mov %[zero],(%[rodata_test])\n" | |
41 | " mov %[zero], %[rslt]\n" | |
42 | "1:\n" | |
43 | ".section .fixup,\"ax\"\n" | |
44 | "2: jmp 1b\n" | |
45 | ".previous\n" | |
5d6f8d77 | 46 | _ASM_EXTABLE(0b,2b) |
edeed305 AV |
47 | : [rslt] "=r" (result) |
48 | : [rodata_test] "r" (&rodata_test_data), [zero] "r" (0UL) | |
49 | ); | |
50 | ||
51 | ||
52 | if (!result) { | |
53 | printk(KERN_ERR "rodata_test: test data was not read only\n"); | |
54 | return -ENODEV; | |
55 | } | |
56 | ||
57 | /* test 3: check the value hasn't changed */ | |
58 | /* If this test fails, we managed to overwrite the data */ | |
59 | if (!rodata_test_data) { | |
d939be3a | 60 | printk(KERN_ERR "rodata_test: Test 3 fails (end data)\n"); |
edeed305 AV |
61 | return -ENODEV; |
62 | } | |
63 | /* test 4: check if the rodata section is 4Kb aligned */ | |
64 | start = (unsigned long)__start_rodata; | |
65 | end = (unsigned long)__end_rodata; | |
66 | if (start & (PAGE_SIZE - 1)) { | |
67 | printk(KERN_ERR "rodata_test: .rodata is not 4k aligned\n"); | |
68 | return -ENODEV; | |
69 | } | |
70 | if (end & (PAGE_SIZE - 1)) { | |
71 | printk(KERN_ERR "rodata_test: .rodata end is not 4k aligned\n"); | |
72 | return -ENODEV; | |
73 | } | |
74 | ||
75 | return 0; | |
76 | } | |
77 | ||
78 | MODULE_LICENSE("GPL"); | |
9ccaf77c | 79 | MODULE_DESCRIPTION("Testcase for marking rodata as read-only"); |
edeed305 | 80 | MODULE_AUTHOR("Arjan van de Ven <arjan@linux.intel.com>"); |