convert from svn repository: remove tags directory
[lttv.git] / trunk / tests / kernel / test-cmpxchg-nolock2.c
1 /* test-cmpxchg-nolock.c
2 *
3 * Compare local cmpxchg with irq disable / enable.
4 */
5
6
7 #include <linux/jiffies.h>
8 #include <linux/compiler.h>
9 #include <linux/init.h>
10 #include <linux/module.h>
11 #include <linux/math64.h>
12 #include <asm/timex.h>
13 #include <asm/system.h>
14
15 #define NR_LOOPS 20000
16
17 int test_val;
18
19 static void do_testbaseline(void)
20 {
21 unsigned long flags;
22 unsigned int i;
23 cycles_t time1, time2, time;
24 u32 rem;
25
26 local_irq_save(flags);
27 preempt_disable();
28 time1 = get_cycles();
29 for (i = 0; i < NR_LOOPS; i++) {
30 asm volatile ("");
31 }
32 time2 = get_cycles();
33 local_irq_restore(flags);
34 preempt_enable();
35 time = time2 - time1;
36
37 printk(KERN_ALERT "test results: time for baseline\n");
38 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
39 printk(KERN_ALERT "total time: %llu\n", time);
40 time = div_u64_rem(time, NR_LOOPS, &rem);
41 printk(KERN_ALERT "-> baseline takes %llu cycles\n", time);
42 printk(KERN_ALERT "test end\n");
43 }
44
45 static void do_test_sync_cmpxchg(void)
46 {
47 int ret;
48 unsigned long flags;
49 unsigned int i;
50 cycles_t time1, time2, time;
51 u32 rem;
52
53 local_irq_save(flags);
54 preempt_disable();
55 time1 = get_cycles();
56 for (i = 0; i < NR_LOOPS; i++) {
57 #ifdef CONFIG_X86_32
58 ret = sync_cmpxchg(&test_val, 0, 0);
59 #else
60 ret = cmpxchg(&test_val, 0, 0);
61 #endif
62 }
63 time2 = get_cycles();
64 local_irq_restore(flags);
65 preempt_enable();
66 time = time2 - time1;
67
68 printk(KERN_ALERT "test results: time for locked cmpxchg\n");
69 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
70 printk(KERN_ALERT "total time: %llu\n", time);
71 time = div_u64_rem(time, NR_LOOPS, &rem);
72 printk(KERN_ALERT "-> locked cmpxchg takes %llu cycles\n", time);
73 printk(KERN_ALERT "test end\n");
74 }
75
76 static void do_test_cmpxchg(void)
77 {
78 int ret;
79 unsigned long flags;
80 unsigned int i;
81 cycles_t time1, time2, time;
82 u32 rem;
83
84 local_irq_save(flags);
85 preempt_disable();
86 time1 = get_cycles();
87 for (i = 0; i < NR_LOOPS; i++) {
88 ret = cmpxchg_local(&test_val, 0, 0);
89 }
90 time2 = get_cycles();
91 local_irq_restore(flags);
92 preempt_enable();
93 time = time2 - time1;
94
95 printk(KERN_ALERT "test results: time for non locked cmpxchg\n");
96 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
97 printk(KERN_ALERT "total time: %llu\n", time);
98 time = div_u64_rem(time, NR_LOOPS, &rem);
99 printk(KERN_ALERT "-> non locked cmpxchg takes %llu cycles\n", time);
100 printk(KERN_ALERT "test end\n");
101 }
102 static void do_test_sync_inc(void)
103 {
104 int ret;
105 unsigned long flags;
106 unsigned int i;
107 cycles_t time1, time2, time;
108 u32 rem;
109 atomic_t val;
110
111 local_irq_save(flags);
112 preempt_disable();
113 time1 = get_cycles();
114 for (i = 0; i < NR_LOOPS; i++) {
115 ret = atomic_add_return(10, &val);
116 }
117 time2 = get_cycles();
118 local_irq_restore(flags);
119 preempt_enable();
120 time = time2 - time1;
121
122 printk(KERN_ALERT "test results: time for locked add return\n");
123 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
124 printk(KERN_ALERT "total time: %llu\n", time);
125 time = div_u64_rem(time, NR_LOOPS, &rem);
126 printk(KERN_ALERT "-> locked add return takes %llu cycles\n", time);
127 printk(KERN_ALERT "test end\n");
128 }
129
130
131 static void do_test_inc(void)
132 {
133 int ret;
134 unsigned long flags;
135 unsigned int i;
136 cycles_t time1, time2, time;
137 u32 rem;
138 local_t loc_val;
139
140 local_irq_save(flags);
141 preempt_disable();
142 time1 = get_cycles();
143 for (i = 0; i < NR_LOOPS; i++) {
144 ret = local_add_return(10, &loc_val);
145 }
146 time2 = get_cycles();
147 local_irq_restore(flags);
148 preempt_enable();
149 time = time2 - time1;
150
151 printk(KERN_ALERT "test results: time for non locked add return\n");
152 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
153 printk(KERN_ALERT "total time: %llu\n", time);
154 time = div_u64_rem(time, NR_LOOPS, &rem);
155 printk(KERN_ALERT "-> non locked add return takes %llu cycles\n", time);
156 printk(KERN_ALERT "test end\n");
157 }
158
159
160
161 /*
162 * This test will have a higher standard deviation due to incoming interrupts.
163 */
164 static void do_test_enable_int(void)
165 {
166 unsigned long flags;
167 unsigned int i;
168 cycles_t time1, time2, time;
169 u32 rem;
170
171 local_irq_save(flags);
172 preempt_disable();
173 time1 = get_cycles();
174 for (i = 0; i < NR_LOOPS; i++) {
175 local_irq_restore(flags);
176 }
177 time2 = get_cycles();
178 local_irq_restore(flags);
179 preempt_enable();
180 time = time2 - time1;
181
182 printk(KERN_ALERT "test results: time for enabling interrupts (STI)\n");
183 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
184 printk(KERN_ALERT "total time: %llu\n", time);
185 time = div_u64_rem(time, NR_LOOPS, &rem);
186 printk(KERN_ALERT "-> enabling interrupts (STI) takes %llu cycles\n",
187 time);
188 printk(KERN_ALERT "test end\n");
189 }
190
191 static void do_test_disable_int(void)
192 {
193 unsigned long flags, flags2;
194 unsigned int i;
195 cycles_t time1, time2, time;
196 u32 rem;
197
198 local_irq_save(flags);
199 preempt_disable();
200 time1 = get_cycles();
201 for ( i = 0; i < NR_LOOPS; i++) {
202 local_irq_save(flags2);
203 }
204 time2 = get_cycles();
205 local_irq_restore(flags);
206 preempt_enable();
207 time = time2 - time1;
208
209 printk(KERN_ALERT "test results: time for disabling interrupts (CLI)\n");
210 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
211 printk(KERN_ALERT "total time: %llu\n", time);
212 time = div_u64_rem(time, NR_LOOPS, &rem);
213 printk(KERN_ALERT "-> disabling interrupts (CLI) takes %llu cycles\n",
214 time);
215 printk(KERN_ALERT "test end\n");
216 }
217
218 static void do_test_int(void)
219 {
220 unsigned long flags;
221 unsigned int i;
222 cycles_t time1, time2, time;
223 u32 rem;
224
225 local_irq_save(flags);
226 preempt_disable();
227 time1 = get_cycles();
228 for (i = 0; i < NR_LOOPS; i++) {
229 local_irq_restore(flags);
230 local_irq_save(flags);
231 }
232 time2 = get_cycles();
233 local_irq_restore(flags);
234 preempt_enable();
235 time = time2 - time1;
236
237 printk(KERN_ALERT "test results: time for disabling/enabling interrupts (STI/CLI)\n");
238 printk(KERN_ALERT "number of loops: %d\n", NR_LOOPS);
239 printk(KERN_ALERT "total time: %llu\n", time);
240 time = div_u64_rem(time, NR_LOOPS, &rem);
241 printk(KERN_ALERT "-> enabling/disabling interrupts (STI/CLI) takes %llu cycles\n",
242 time);
243 printk(KERN_ALERT "test end\n");
244 }
245
246
247
248 static int ltt_test_init(void)
249 {
250 printk(KERN_ALERT "test init\n");
251
252 do_testbaseline();
253 do_test_sync_cmpxchg();
254 do_test_cmpxchg();
255 do_test_sync_inc();
256 do_test_inc();
257 do_test_enable_int();
258 do_test_disable_int();
259 do_test_int();
260 return -EAGAIN; /* Fail will directly unload the module */
261 }
262
263 static void ltt_test_exit(void)
264 {
265 printk(KERN_ALERT "test exit\n");
266 }
267
268 module_init(ltt_test_init)
269 module_exit(ltt_test_exit)
270
271 MODULE_LICENSE("GPL");
272 MODULE_AUTHOR("Mathieu Desnoyers");
273 MODULE_DESCRIPTION("Cmpxchg vs int Test");
274
This page took 0.035345 seconds and 4 git commands to generate.