5 #include <linux/kernel.h>
7 #include <linux/slab.h>
14 struct sparc64_msiq_cookie *msiq_cookie =
cookie;
16 unsigned long msiqid = msiq_cookie->msiqid;
17 const struct sparc64_msiq_ops *
ops;
18 unsigned long orig_head,
head;
23 err = ops->get_head(pbm, msiqid, &head);
31 err = ops->dequeue_msi(pbm, msiqid, &head, &msi);
35 irq = pbm->msi_irq_table[msi - pbm->msi_first];
45 if (
likely(head != orig_head)) {
46 err = ops->set_head(pbm, msiqid, head);
81 rotor = pbm->msiq_rotor;
82 ret = pbm->msiq_first + rotor;
84 if (++rotor >= pbm->msiq_num)
86 pbm->msiq_rotor = rotor;
88 spin_unlock_irqrestore(&rotor_lock, flags);
98 for (i = 0; i < pbm->msi_num; i++) {
100 return i + pbm->msi_first;
106 static void free_msi(
struct pci_pbm_info *pbm,
int msi_num)
108 msi_num -= pbm->msi_first;
121 static int sparc64_setup_msi_irq(
unsigned int *irq_p,
126 const struct sparc64_msiq_ops *ops = pbm->msi_ops;
139 err = alloc_msi(pbm);
145 msiqid = pick_msiq(pbm);
147 err = ops->msi_setup(pbm, msiqid, msi,
152 pbm->msi_irq_table[msi - pbm->msi_first] = *irq_p;
155 msg.address_hi = pbm->msi64_start >> 32;
156 msg.address_lo = pbm->msi64_start & 0xffffffff;
159 msg.address_lo = pbm->msi32_start;
180 static void sparc64_teardown_msi_irq(
unsigned int irq,
184 const struct sparc64_msiq_ops *ops = pbm->msi_ops;
185 unsigned int msi_num;
188 for (i = 0; i < pbm->msi_num; i++) {
189 if (pbm->msi_irq_table[i] == irq)
192 if (i >= pbm->msi_num) {
198 msi_num = pbm->msi_first +
i;
199 pbm->msi_irq_table[
i] = ~0
U;
201 err = ops->msi_teardown(pbm, msi_num);
204 "irq %u, gives error %d\n",
205 pbm->
name, msi_num, irq, err);
209 free_msi(pbm, msi_num);
217 unsigned long size, bits_per_ulong;
219 bits_per_ulong =
sizeof(
unsigned long) * 8;
220 size = (pbm->msi_num + (bits_per_ulong - 1)) & ~(bits_per_ulong - 1);
222 BUG_ON(size %
sizeof(
unsigned long));
225 if (!pbm->msi_bitmap)
233 kfree(pbm->msi_bitmap);
234 pbm->msi_bitmap =
NULL;
241 size = pbm->msiq_num *
sizeof(
struct sparc64_msiq_cookie);
242 pbm->msiq_irq_cookies = kzalloc(size,
GFP_KERNEL);
243 if (!pbm->msiq_irq_cookies)
246 for (i = 0; i < pbm->msiq_num; i++) {
247 struct sparc64_msiq_cookie *
p;
249 p = &pbm->msiq_irq_cookies[
i];
251 p->msiqid = pbm->msiq_first +
i;
254 size = pbm->msi_num *
sizeof(
unsigned int);
255 pbm->msi_irq_table = kzalloc(size,
GFP_KERNEL);
256 if (!pbm->msi_irq_table) {
257 kfree(pbm->msiq_irq_cookies);
258 pbm->msiq_irq_cookies =
NULL;
267 kfree(pbm->msiq_irq_cookies);
268 pbm->msiq_irq_cookies =
NULL;
270 kfree(pbm->msi_irq_table);
271 pbm->msi_irq_table =
NULL;
274 static int bringup_one_msi_queue(
struct pci_pbm_info *pbm,
275 const struct sparc64_msiq_ops *ops,
276 unsigned long msiqid,
277 unsigned long devino)
279 int irq = ops->msiq_build_irq(pbm, msiqid, devino);
290 irq_set_affinity(irq, &numa_mask);
294 &pbm->msiq_irq_cookies[msiqid - pbm->msiq_first]);
301 static int sparc64_bringup_msi_queues(
struct pci_pbm_info *pbm,
302 const struct sparc64_msiq_ops *ops)
306 for (i = 0; i < pbm->msiq_num; i++) {
307 unsigned long msiqid = i + pbm->msiq_first;
308 unsigned long devino = i + pbm->msiq_first_devino;
311 err = bringup_one_msi_queue(pbm, ops, msiqid, devino);
320 const struct sparc64_msiq_ops *ops)
326 if (!val || len != 4)
328 pbm->msiq_num = *
val;
330 const struct msiq_prop {
335 const struct msi_range_prop {
339 const struct addr_range_prop {
349 if (!val || len != 4)
352 pbm->msiq_ent_count = *
val;
355 "msi-eq-to-devino", &len);
358 "msi-eq-devino", &len);
359 if (!mqp || len !=
sizeof(
struct msiq_prop))
362 pbm->msiq_first = mqp->first_msiq;
363 pbm->msiq_first_devino = mqp->first_devino;
366 if (!val || len != 4)
371 if (!mrng || len !=
sizeof(
struct msi_range_prop))
373 pbm->msi_first = mrng->first_msi;
376 if (!val || len != 4)
378 pbm->msi_data_mask = *
val;
381 if (!val || len != 4)
383 pbm->msix_data_width = *
val;
387 if (!arng || len !=
sizeof(
struct addr_range_prop))
389 pbm->msi32_start = ((
u64)arng->msi32_high << 32) |
390 (
u64) arng->msi32_low;
391 pbm->msi64_start = ((
u64)arng->msi64_high << 32) |
392 (
u64) arng->msi64_low;
393 pbm->msi32_len = arng->msi32_len;
394 pbm->msi64_len = arng->msi64_len;
399 if (msi_table_alloc(pbm)) {
404 if (ops->msiq_alloc(pbm)) {
410 if (sparc64_bringup_msi_queues(pbm, ops)) {
420 pbm->msiq_first, pbm->msiq_num,
422 pbm->msiq_first_devino);
426 pbm->msi_first, pbm->msi_num, pbm->msi_data_mask,
427 pbm->msix_data_width);
429 "addr64[0x%llx:0x%x]\n",
431 pbm->msi32_start, pbm->msi32_len,
432 pbm->msi64_start, pbm->msi64_len);
435 __pa(pbm->msi_queues));
438 pbm->setup_msi_irq = sparc64_setup_msi_irq;
439 pbm->teardown_msi_irq = sparc64_teardown_msi_irq;