Branch data Line data Source code
1 : : // SPDX-License-Identifier: GPL-2.0
2 : : #include <linux/export.h>
3 : : #include <linux/preempt.h>
4 : : #include <linux/smp.h>
5 : : #include <linux/completion.h>
6 : : #include <asm/msr.h>
7 : :
8 : 0 : static void __rdmsr_on_cpu(void *info)
9 : : {
10 : 0 : struct msr_info *rv = info;
11 : 0 : struct msr *reg;
12 : 0 : int this_cpu = raw_smp_processor_id();
13 : :
14 [ # # ]: 0 : if (rv->msrs)
15 : 0 : reg = per_cpu_ptr(rv->msrs, this_cpu);
16 : : else
17 : 0 : reg = &rv->reg;
18 : :
19 : 0 : rdmsr(rv->msr_no, reg->l, reg->h);
20 : 0 : }
21 : :
22 : 0 : static void __wrmsr_on_cpu(void *info)
23 : : {
24 : 0 : struct msr_info *rv = info;
25 : 0 : struct msr *reg;
26 : 0 : int this_cpu = raw_smp_processor_id();
27 : :
28 [ # # ]: 0 : if (rv->msrs)
29 : 0 : reg = per_cpu_ptr(rv->msrs, this_cpu);
30 : : else
31 : 0 : reg = &rv->reg;
32 : :
33 : 0 : wrmsr(rv->msr_no, reg->l, reg->h);
34 : 0 : }
35 : :
36 : 0 : int rdmsr_on_cpu(unsigned int cpu, u32 msr_no, u32 *l, u32 *h)
37 : : {
38 : 0 : int err;
39 : 0 : struct msr_info rv;
40 : :
41 : 0 : memset(&rv, 0, sizeof(rv));
42 : :
43 : 0 : rv.msr_no = msr_no;
44 : 0 : err = smp_call_function_single(cpu, __rdmsr_on_cpu, &rv, 1);
45 : 0 : *l = rv.reg.l;
46 : 0 : *h = rv.reg.h;
47 : :
48 : 0 : return err;
49 : : }
50 : : EXPORT_SYMBOL(rdmsr_on_cpu);
51 : :
52 : 0 : int rdmsrl_on_cpu(unsigned int cpu, u32 msr_no, u64 *q)
53 : : {
54 : 0 : int err;
55 : 0 : struct msr_info rv;
56 : :
57 : 0 : memset(&rv, 0, sizeof(rv));
58 : :
59 : 0 : rv.msr_no = msr_no;
60 : 0 : err = smp_call_function_single(cpu, __rdmsr_on_cpu, &rv, 1);
61 : 0 : *q = rv.reg.q;
62 : :
63 : 0 : return err;
64 : : }
65 : : EXPORT_SYMBOL(rdmsrl_on_cpu);
66 : :
67 : 0 : int wrmsr_on_cpu(unsigned int cpu, u32 msr_no, u32 l, u32 h)
68 : : {
69 : 0 : int err;
70 : 0 : struct msr_info rv;
71 : :
72 : 0 : memset(&rv, 0, sizeof(rv));
73 : :
74 : 0 : rv.msr_no = msr_no;
75 : 0 : rv.reg.l = l;
76 : 0 : rv.reg.h = h;
77 : 0 : err = smp_call_function_single(cpu, __wrmsr_on_cpu, &rv, 1);
78 : :
79 : 0 : return err;
80 : : }
81 : : EXPORT_SYMBOL(wrmsr_on_cpu);
82 : :
83 : 0 : int wrmsrl_on_cpu(unsigned int cpu, u32 msr_no, u64 q)
84 : : {
85 : 0 : int err;
86 : 0 : struct msr_info rv;
87 : :
88 : 0 : memset(&rv, 0, sizeof(rv));
89 : :
90 : 0 : rv.msr_no = msr_no;
91 : 0 : rv.reg.q = q;
92 : :
93 : 0 : err = smp_call_function_single(cpu, __wrmsr_on_cpu, &rv, 1);
94 : :
95 : 0 : return err;
96 : : }
97 : : EXPORT_SYMBOL(wrmsrl_on_cpu);
98 : :
99 : 0 : static void __rwmsr_on_cpus(const struct cpumask *mask, u32 msr_no,
100 : : struct msr *msrs,
101 : : void (*msr_func) (void *info))
102 : : {
103 : 0 : struct msr_info rv;
104 : 0 : int this_cpu;
105 : :
106 : 0 : memset(&rv, 0, sizeof(rv));
107 : :
108 : 0 : rv.msrs = msrs;
109 : 0 : rv.msr_no = msr_no;
110 : :
111 : 0 : this_cpu = get_cpu();
112 : :
113 [ # # ]: 0 : if (cpumask_test_cpu(this_cpu, mask))
114 : 0 : msr_func(&rv);
115 : :
116 : 0 : smp_call_function_many(mask, msr_func, &rv, 1);
117 : 0 : put_cpu();
118 : 0 : }
119 : :
120 : : /* rdmsr on a bunch of CPUs
121 : : *
122 : : * @mask: which CPUs
123 : : * @msr_no: which MSR
124 : : * @msrs: array of MSR values
125 : : *
126 : : */
127 : 0 : void rdmsr_on_cpus(const struct cpumask *mask, u32 msr_no, struct msr *msrs)
128 : : {
129 : 0 : __rwmsr_on_cpus(mask, msr_no, msrs, __rdmsr_on_cpu);
130 : 0 : }
131 : : EXPORT_SYMBOL(rdmsr_on_cpus);
132 : :
133 : : /*
134 : : * wrmsr on a bunch of CPUs
135 : : *
136 : : * @mask: which CPUs
137 : : * @msr_no: which MSR
138 : : * @msrs: array of MSR values
139 : : *
140 : : */
141 : 0 : void wrmsr_on_cpus(const struct cpumask *mask, u32 msr_no, struct msr *msrs)
142 : : {
143 : 0 : __rwmsr_on_cpus(mask, msr_no, msrs, __wrmsr_on_cpu);
144 : 0 : }
145 : : EXPORT_SYMBOL(wrmsr_on_cpus);
146 : :
147 : : struct msr_info_completion {
148 : : struct msr_info msr;
149 : : struct completion done;
150 : : };
151 : :
152 : : /* These "safe" variants are slower and should be used when the target MSR
153 : : may not actually exist. */
154 : 0 : static void __rdmsr_safe_on_cpu(void *info)
155 : : {
156 : 0 : struct msr_info_completion *rv = info;
157 : :
158 : 0 : rv->msr.err = rdmsr_safe(rv->msr.msr_no, &rv->msr.reg.l, &rv->msr.reg.h);
159 : 0 : complete(&rv->done);
160 : 0 : }
161 : :
162 : 0 : static void __wrmsr_safe_on_cpu(void *info)
163 : : {
164 : 0 : struct msr_info *rv = info;
165 : :
166 : 0 : rv->err = wrmsr_safe(rv->msr_no, rv->reg.l, rv->reg.h);
167 : 0 : }
168 : :
169 : 0 : int rdmsr_safe_on_cpu(unsigned int cpu, u32 msr_no, u32 *l, u32 *h)
170 : : {
171 : 0 : struct msr_info_completion rv;
172 : 0 : call_single_data_t csd = {
173 : : .func = __rdmsr_safe_on_cpu,
174 : : .info = &rv,
175 : : };
176 : 0 : int err;
177 : :
178 : 0 : memset(&rv, 0, sizeof(rv));
179 : 0 : init_completion(&rv.done);
180 : 0 : rv.msr.msr_no = msr_no;
181 : :
182 : 0 : err = smp_call_function_single_async(cpu, &csd);
183 [ # # ]: 0 : if (!err) {
184 : 0 : wait_for_completion(&rv.done);
185 : 0 : err = rv.msr.err;
186 : : }
187 : 0 : *l = rv.msr.reg.l;
188 : 0 : *h = rv.msr.reg.h;
189 : :
190 : 0 : return err;
191 : : }
192 : : EXPORT_SYMBOL(rdmsr_safe_on_cpu);
193 : :
194 : 0 : int wrmsr_safe_on_cpu(unsigned int cpu, u32 msr_no, u32 l, u32 h)
195 : : {
196 : 0 : int err;
197 : 0 : struct msr_info rv;
198 : :
199 : 0 : memset(&rv, 0, sizeof(rv));
200 : :
201 : 0 : rv.msr_no = msr_no;
202 : 0 : rv.reg.l = l;
203 : 0 : rv.reg.h = h;
204 : 0 : err = smp_call_function_single(cpu, __wrmsr_safe_on_cpu, &rv, 1);
205 : :
206 [ # # ]: 0 : return err ? err : rv.err;
207 : : }
208 : : EXPORT_SYMBOL(wrmsr_safe_on_cpu);
209 : :
210 : 0 : int wrmsrl_safe_on_cpu(unsigned int cpu, u32 msr_no, u64 q)
211 : : {
212 : 0 : int err;
213 : 0 : struct msr_info rv;
214 : :
215 : 0 : memset(&rv, 0, sizeof(rv));
216 : :
217 : 0 : rv.msr_no = msr_no;
218 : 0 : rv.reg.q = q;
219 : :
220 : 0 : err = smp_call_function_single(cpu, __wrmsr_safe_on_cpu, &rv, 1);
221 : :
222 [ # # ]: 0 : return err ? err : rv.err;
223 : : }
224 : : EXPORT_SYMBOL(wrmsrl_safe_on_cpu);
225 : :
226 : 0 : int rdmsrl_safe_on_cpu(unsigned int cpu, u32 msr_no, u64 *q)
227 : : {
228 : 0 : u32 low, high;
229 : 0 : int err;
230 : :
231 : 0 : err = rdmsr_safe_on_cpu(cpu, msr_no, &low, &high);
232 : 0 : *q = (u64)high << 32 | low;
233 : :
234 : 0 : return err;
235 : : }
236 : : EXPORT_SYMBOL(rdmsrl_safe_on_cpu);
237 : :
238 : : /*
239 : : * These variants are significantly slower, but allows control over
240 : : * the entire 32-bit GPR set.
241 : : */
242 : 0 : static void __rdmsr_safe_regs_on_cpu(void *info)
243 : : {
244 : 0 : struct msr_regs_info *rv = info;
245 : :
246 : 0 : rv->err = rdmsr_safe_regs(rv->regs);
247 : 0 : }
248 : :
249 : 0 : static void __wrmsr_safe_regs_on_cpu(void *info)
250 : : {
251 : 0 : struct msr_regs_info *rv = info;
252 : :
253 : 0 : rv->err = wrmsr_safe_regs(rv->regs);
254 : 0 : }
255 : :
256 : 0 : int rdmsr_safe_regs_on_cpu(unsigned int cpu, u32 *regs)
257 : : {
258 : 0 : int err;
259 : 0 : struct msr_regs_info rv;
260 : :
261 : 0 : rv.regs = regs;
262 : 0 : rv.err = -EIO;
263 : 0 : err = smp_call_function_single(cpu, __rdmsr_safe_regs_on_cpu, &rv, 1);
264 : :
265 [ # # ]: 0 : return err ? err : rv.err;
266 : : }
267 : : EXPORT_SYMBOL(rdmsr_safe_regs_on_cpu);
268 : :
269 : 0 : int wrmsr_safe_regs_on_cpu(unsigned int cpu, u32 *regs)
270 : : {
271 : 0 : int err;
272 : 0 : struct msr_regs_info rv;
273 : :
274 : 0 : rv.regs = regs;
275 : 0 : rv.err = -EIO;
276 : 0 : err = smp_call_function_single(cpu, __wrmsr_safe_regs_on_cpu, &rv, 1);
277 : :
278 [ # # ]: 0 : return err ? err : rv.err;
279 : : }
280 : : EXPORT_SYMBOL(wrmsr_safe_regs_on_cpu);
|