link.c 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690
  1. // SPDX-License-Identifier: GPL-2.0+
  2. // Copyright 2017 IBM Corp.
  3. #include <linux/sched/mm.h>
  4. #include <linux/mutex.h>
  5. #include <linux/mm_types.h>
  6. #include <linux/mmu_context.h>
  7. #include <asm/copro.h>
  8. #include <asm/pnv-ocxl.h>
  9. #include <misc/ocxl.h>
  10. #include "ocxl_internal.h"
  11. #include "trace.h"
  12. #define SPA_PASID_BITS 15
  13. #define SPA_PASID_MAX ((1 << SPA_PASID_BITS) - 1)
  14. #define SPA_PE_MASK SPA_PASID_MAX
  15. #define SPA_SPA_SIZE_LOG 22 /* Each SPA is 4 Mb */
  16. #define SPA_CFG_SF (1ull << (63-0))
  17. #define SPA_CFG_TA (1ull << (63-1))
  18. #define SPA_CFG_HV (1ull << (63-3))
  19. #define SPA_CFG_UV (1ull << (63-4))
  20. #define SPA_CFG_XLAT_hpt (0ull << (63-6)) /* Hashed page table (HPT) mode */
  21. #define SPA_CFG_XLAT_roh (2ull << (63-6)) /* Radix on HPT mode */
  22. #define SPA_CFG_XLAT_ror (3ull << (63-6)) /* Radix on Radix mode */
  23. #define SPA_CFG_PR (1ull << (63-49))
  24. #define SPA_CFG_TC (1ull << (63-54))
  25. #define SPA_CFG_DR (1ull << (63-59))
  26. #define SPA_XSL_TF (1ull << (63-3)) /* Translation fault */
  27. #define SPA_XSL_S (1ull << (63-38)) /* Store operation */
  28. #define SPA_PE_VALID 0x80000000
  29. struct pe_data {
  30. struct mm_struct *mm;
  31. /* callback to trigger when a translation fault occurs */
  32. void (*xsl_err_cb)(void *data, u64 addr, u64 dsisr);
  33. /* opaque pointer to be passed to the above callback */
  34. void *xsl_err_data;
  35. struct rcu_head rcu;
  36. };
  37. struct spa {
  38. struct ocxl_process_element *spa_mem;
  39. int spa_order;
  40. struct mutex spa_lock;
  41. struct radix_tree_root pe_tree; /* Maps PE handles to pe_data */
  42. char *irq_name;
  43. int virq;
  44. void __iomem *reg_dsisr;
  45. void __iomem *reg_dar;
  46. void __iomem *reg_tfc;
  47. void __iomem *reg_pe_handle;
  48. /*
  49. * The following field are used by the memory fault
  50. * interrupt handler. We can only have one interrupt at a
  51. * time. The NPU won't raise another interrupt until the
  52. * previous one has been ack'd by writing to the TFC register
  53. */
  54. struct xsl_fault {
  55. struct work_struct fault_work;
  56. u64 pe;
  57. u64 dsisr;
  58. u64 dar;
  59. struct pe_data pe_data;
  60. } xsl_fault;
  61. };
  62. /*
  63. * A opencapi link can be used be by several PCI functions. We have
  64. * one link per device slot.
  65. *
  66. * A linked list of opencapi links should suffice, as there's a
  67. * limited number of opencapi slots on a system and lookup is only
  68. * done when the device is probed
  69. */
  70. struct link {
  71. struct list_head list;
  72. struct kref ref;
  73. int domain;
  74. int bus;
  75. int dev;
  76. atomic_t irq_available;
  77. struct spa *spa;
  78. void *platform_data;
  79. };
  80. static struct list_head links_list = LIST_HEAD_INIT(links_list);
  81. static DEFINE_MUTEX(links_list_lock);
  82. enum xsl_response {
  83. CONTINUE,
  84. ADDRESS_ERROR,
  85. RESTART,
  86. };
  87. static void read_irq(struct spa *spa, u64 *dsisr, u64 *dar, u64 *pe)
  88. {
  89. u64 reg;
  90. *dsisr = in_be64(spa->reg_dsisr);
  91. *dar = in_be64(spa->reg_dar);
  92. reg = in_be64(spa->reg_pe_handle);
  93. *pe = reg & SPA_PE_MASK;
  94. }
  95. static void ack_irq(struct spa *spa, enum xsl_response r)
  96. {
  97. u64 reg = 0;
  98. /* continue is not supported */
  99. if (r == RESTART)
  100. reg = PPC_BIT(31);
  101. else if (r == ADDRESS_ERROR)
  102. reg = PPC_BIT(30);
  103. else
  104. WARN(1, "Invalid irq response %d\n", r);
  105. if (reg) {
  106. trace_ocxl_fault_ack(spa->spa_mem, spa->xsl_fault.pe,
  107. spa->xsl_fault.dsisr, spa->xsl_fault.dar, reg);
  108. out_be64(spa->reg_tfc, reg);
  109. }
  110. }
  111. static void xsl_fault_handler_bh(struct work_struct *fault_work)
  112. {
  113. vm_fault_t flt = 0;
  114. unsigned long access, flags, inv_flags = 0;
  115. enum xsl_response r;
  116. struct xsl_fault *fault = container_of(fault_work, struct xsl_fault,
  117. fault_work);
  118. struct spa *spa = container_of(fault, struct spa, xsl_fault);
  119. int rc;
  120. /*
  121. * We must release a reference on mm_users whenever exiting this
  122. * function (taken in the memory fault interrupt handler)
  123. */
  124. rc = copro_handle_mm_fault(fault->pe_data.mm, fault->dar, fault->dsisr,
  125. &flt);
  126. if (rc) {
  127. pr_debug("copro_handle_mm_fault failed: %d\n", rc);
  128. if (fault->pe_data.xsl_err_cb) {
  129. fault->pe_data.xsl_err_cb(
  130. fault->pe_data.xsl_err_data,
  131. fault->dar, fault->dsisr);
  132. }
  133. r = ADDRESS_ERROR;
  134. goto ack;
  135. }
  136. if (!radix_enabled()) {
  137. /*
  138. * update_mmu_cache() will not have loaded the hash
  139. * since current->trap is not a 0x400 or 0x300, so
  140. * just call hash_page_mm() here.
  141. */
  142. access = _PAGE_PRESENT | _PAGE_READ;
  143. if (fault->dsisr & SPA_XSL_S)
  144. access |= _PAGE_WRITE;
  145. if (REGION_ID(fault->dar) != USER_REGION_ID)
  146. access |= _PAGE_PRIVILEGED;
  147. local_irq_save(flags);
  148. hash_page_mm(fault->pe_data.mm, fault->dar, access, 0x300,
  149. inv_flags);
  150. local_irq_restore(flags);
  151. }
  152. r = RESTART;
  153. ack:
  154. mmput(fault->pe_data.mm);
  155. ack_irq(spa, r);
  156. }
  157. static irqreturn_t xsl_fault_handler(int irq, void *data)
  158. {
  159. struct link *link = (struct link *) data;
  160. struct spa *spa = link->spa;
  161. u64 dsisr, dar, pe_handle;
  162. struct pe_data *pe_data;
  163. struct ocxl_process_element *pe;
  164. int lpid, pid, tid;
  165. bool schedule = false;
  166. read_irq(spa, &dsisr, &dar, &pe_handle);
  167. trace_ocxl_fault(spa->spa_mem, pe_handle, dsisr, dar, -1);
  168. WARN_ON(pe_handle > SPA_PE_MASK);
  169. pe = spa->spa_mem + pe_handle;
  170. lpid = be32_to_cpu(pe->lpid);
  171. pid = be32_to_cpu(pe->pid);
  172. tid = be32_to_cpu(pe->tid);
  173. /* We could be reading all null values here if the PE is being
  174. * removed while an interrupt kicks in. It's not supposed to
  175. * happen if the driver notified the AFU to terminate the
  176. * PASID, and the AFU waited for pending operations before
  177. * acknowledging. But even if it happens, we won't find a
  178. * memory context below and fail silently, so it should be ok.
  179. */
  180. if (!(dsisr & SPA_XSL_TF)) {
  181. WARN(1, "Invalid xsl interrupt fault register %#llx\n", dsisr);
  182. ack_irq(spa, ADDRESS_ERROR);
  183. return IRQ_HANDLED;
  184. }
  185. rcu_read_lock();
  186. pe_data = radix_tree_lookup(&spa->pe_tree, pe_handle);
  187. if (!pe_data) {
  188. /*
  189. * Could only happen if the driver didn't notify the
  190. * AFU about PASID termination before removing the PE,
  191. * or the AFU didn't wait for all memory access to
  192. * have completed.
  193. *
  194. * Either way, we fail early, but we shouldn't log an
  195. * error message, as it is a valid (if unexpected)
  196. * scenario
  197. */
  198. rcu_read_unlock();
  199. pr_debug("Unknown mm context for xsl interrupt\n");
  200. ack_irq(spa, ADDRESS_ERROR);
  201. return IRQ_HANDLED;
  202. }
  203. WARN_ON(pe_data->mm->context.id != pid);
  204. if (mmget_not_zero(pe_data->mm)) {
  205. spa->xsl_fault.pe = pe_handle;
  206. spa->xsl_fault.dar = dar;
  207. spa->xsl_fault.dsisr = dsisr;
  208. spa->xsl_fault.pe_data = *pe_data;
  209. schedule = true;
  210. /* mm_users count released by bottom half */
  211. }
  212. rcu_read_unlock();
  213. if (schedule)
  214. schedule_work(&spa->xsl_fault.fault_work);
  215. else
  216. ack_irq(spa, ADDRESS_ERROR);
  217. return IRQ_HANDLED;
  218. }
  219. static void unmap_irq_registers(struct spa *spa)
  220. {
  221. pnv_ocxl_unmap_xsl_regs(spa->reg_dsisr, spa->reg_dar, spa->reg_tfc,
  222. spa->reg_pe_handle);
  223. }
  224. static int map_irq_registers(struct pci_dev *dev, struct spa *spa)
  225. {
  226. return pnv_ocxl_map_xsl_regs(dev, &spa->reg_dsisr, &spa->reg_dar,
  227. &spa->reg_tfc, &spa->reg_pe_handle);
  228. }
  229. static int setup_xsl_irq(struct pci_dev *dev, struct link *link)
  230. {
  231. struct spa *spa = link->spa;
  232. int rc;
  233. int hwirq;
  234. rc = pnv_ocxl_get_xsl_irq(dev, &hwirq);
  235. if (rc)
  236. return rc;
  237. rc = map_irq_registers(dev, spa);
  238. if (rc)
  239. return rc;
  240. spa->irq_name = kasprintf(GFP_KERNEL, "ocxl-xsl-%x-%x-%x",
  241. link->domain, link->bus, link->dev);
  242. if (!spa->irq_name) {
  243. unmap_irq_registers(spa);
  244. dev_err(&dev->dev, "Can't allocate name for xsl interrupt\n");
  245. return -ENOMEM;
  246. }
  247. /*
  248. * At some point, we'll need to look into allowing a higher
  249. * number of interrupts. Could we have an IRQ domain per link?
  250. */
  251. spa->virq = irq_create_mapping(NULL, hwirq);
  252. if (!spa->virq) {
  253. kfree(spa->irq_name);
  254. unmap_irq_registers(spa);
  255. dev_err(&dev->dev,
  256. "irq_create_mapping failed for translation interrupt\n");
  257. return -EINVAL;
  258. }
  259. dev_dbg(&dev->dev, "hwirq %d mapped to virq %d\n", hwirq, spa->virq);
  260. rc = request_irq(spa->virq, xsl_fault_handler, 0, spa->irq_name,
  261. link);
  262. if (rc) {
  263. irq_dispose_mapping(spa->virq);
  264. kfree(spa->irq_name);
  265. unmap_irq_registers(spa);
  266. dev_err(&dev->dev,
  267. "request_irq failed for translation interrupt: %d\n",
  268. rc);
  269. return -EINVAL;
  270. }
  271. return 0;
  272. }
  273. static void release_xsl_irq(struct link *link)
  274. {
  275. struct spa *spa = link->spa;
  276. if (spa->virq) {
  277. free_irq(spa->virq, link);
  278. irq_dispose_mapping(spa->virq);
  279. }
  280. kfree(spa->irq_name);
  281. unmap_irq_registers(spa);
  282. }
  283. static int alloc_spa(struct pci_dev *dev, struct link *link)
  284. {
  285. struct spa *spa;
  286. spa = kzalloc(sizeof(struct spa), GFP_KERNEL);
  287. if (!spa)
  288. return -ENOMEM;
  289. mutex_init(&spa->spa_lock);
  290. INIT_RADIX_TREE(&spa->pe_tree, GFP_KERNEL);
  291. INIT_WORK(&spa->xsl_fault.fault_work, xsl_fault_handler_bh);
  292. spa->spa_order = SPA_SPA_SIZE_LOG - PAGE_SHIFT;
  293. spa->spa_mem = (struct ocxl_process_element *)
  294. __get_free_pages(GFP_KERNEL | __GFP_ZERO, spa->spa_order);
  295. if (!spa->spa_mem) {
  296. dev_err(&dev->dev, "Can't allocate Shared Process Area\n");
  297. kfree(spa);
  298. return -ENOMEM;
  299. }
  300. pr_debug("Allocated SPA for %x:%x:%x at %p\n", link->domain, link->bus,
  301. link->dev, spa->spa_mem);
  302. link->spa = spa;
  303. return 0;
  304. }
  305. static void free_spa(struct link *link)
  306. {
  307. struct spa *spa = link->spa;
  308. pr_debug("Freeing SPA for %x:%x:%x\n", link->domain, link->bus,
  309. link->dev);
  310. if (spa && spa->spa_mem) {
  311. free_pages((unsigned long) spa->spa_mem, spa->spa_order);
  312. kfree(spa);
  313. link->spa = NULL;
  314. }
  315. }
  316. static int alloc_link(struct pci_dev *dev, int PE_mask, struct link **out_link)
  317. {
  318. struct link *link;
  319. int rc;
  320. link = kzalloc(sizeof(struct link), GFP_KERNEL);
  321. if (!link)
  322. return -ENOMEM;
  323. kref_init(&link->ref);
  324. link->domain = pci_domain_nr(dev->bus);
  325. link->bus = dev->bus->number;
  326. link->dev = PCI_SLOT(dev->devfn);
  327. atomic_set(&link->irq_available, MAX_IRQ_PER_LINK);
  328. rc = alloc_spa(dev, link);
  329. if (rc)
  330. goto err_free;
  331. rc = setup_xsl_irq(dev, link);
  332. if (rc)
  333. goto err_spa;
  334. /* platform specific hook */
  335. rc = pnv_ocxl_spa_setup(dev, link->spa->spa_mem, PE_mask,
  336. &link->platform_data);
  337. if (rc)
  338. goto err_xsl_irq;
  339. *out_link = link;
  340. return 0;
  341. err_xsl_irq:
  342. release_xsl_irq(link);
  343. err_spa:
  344. free_spa(link);
  345. err_free:
  346. kfree(link);
  347. return rc;
  348. }
  349. static void free_link(struct link *link)
  350. {
  351. release_xsl_irq(link);
  352. free_spa(link);
  353. kfree(link);
  354. }
  355. int ocxl_link_setup(struct pci_dev *dev, int PE_mask, void **link_handle)
  356. {
  357. int rc = 0;
  358. struct link *link;
  359. mutex_lock(&links_list_lock);
  360. list_for_each_entry(link, &links_list, list) {
  361. /* The functions of a device all share the same link */
  362. if (link->domain == pci_domain_nr(dev->bus) &&
  363. link->bus == dev->bus->number &&
  364. link->dev == PCI_SLOT(dev->devfn)) {
  365. kref_get(&link->ref);
  366. *link_handle = link;
  367. goto unlock;
  368. }
  369. }
  370. rc = alloc_link(dev, PE_mask, &link);
  371. if (rc)
  372. goto unlock;
  373. list_add(&link->list, &links_list);
  374. *link_handle = link;
  375. unlock:
  376. mutex_unlock(&links_list_lock);
  377. return rc;
  378. }
  379. EXPORT_SYMBOL_GPL(ocxl_link_setup);
  380. static void release_xsl(struct kref *ref)
  381. {
  382. struct link *link = container_of(ref, struct link, ref);
  383. list_del(&link->list);
  384. /* call platform code before releasing data */
  385. pnv_ocxl_spa_release(link->platform_data);
  386. free_link(link);
  387. }
  388. void ocxl_link_release(struct pci_dev *dev, void *link_handle)
  389. {
  390. struct link *link = (struct link *) link_handle;
  391. mutex_lock(&links_list_lock);
  392. kref_put(&link->ref, release_xsl);
  393. mutex_unlock(&links_list_lock);
  394. }
  395. EXPORT_SYMBOL_GPL(ocxl_link_release);
  396. static u64 calculate_cfg_state(bool kernel)
  397. {
  398. u64 state;
  399. state = SPA_CFG_DR;
  400. if (mfspr(SPRN_LPCR) & LPCR_TC)
  401. state |= SPA_CFG_TC;
  402. if (radix_enabled())
  403. state |= SPA_CFG_XLAT_ror;
  404. else
  405. state |= SPA_CFG_XLAT_hpt;
  406. state |= SPA_CFG_HV;
  407. if (kernel) {
  408. if (mfmsr() & MSR_SF)
  409. state |= SPA_CFG_SF;
  410. } else {
  411. state |= SPA_CFG_PR;
  412. if (!test_tsk_thread_flag(current, TIF_32BIT))
  413. state |= SPA_CFG_SF;
  414. }
  415. return state;
  416. }
  417. int ocxl_link_add_pe(void *link_handle, int pasid, u32 pidr, u32 tidr,
  418. u64 amr, struct mm_struct *mm,
  419. void (*xsl_err_cb)(void *data, u64 addr, u64 dsisr),
  420. void *xsl_err_data)
  421. {
  422. struct link *link = (struct link *) link_handle;
  423. struct spa *spa = link->spa;
  424. struct ocxl_process_element *pe;
  425. int pe_handle, rc = 0;
  426. struct pe_data *pe_data;
  427. BUILD_BUG_ON(sizeof(struct ocxl_process_element) != 128);
  428. if (pasid > SPA_PASID_MAX)
  429. return -EINVAL;
  430. mutex_lock(&spa->spa_lock);
  431. pe_handle = pasid & SPA_PE_MASK;
  432. pe = spa->spa_mem + pe_handle;
  433. if (pe->software_state) {
  434. rc = -EBUSY;
  435. goto unlock;
  436. }
  437. pe_data = kmalloc(sizeof(*pe_data), GFP_KERNEL);
  438. if (!pe_data) {
  439. rc = -ENOMEM;
  440. goto unlock;
  441. }
  442. pe_data->mm = mm;
  443. pe_data->xsl_err_cb = xsl_err_cb;
  444. pe_data->xsl_err_data = xsl_err_data;
  445. memset(pe, 0, sizeof(struct ocxl_process_element));
  446. pe->config_state = cpu_to_be64(calculate_cfg_state(pidr == 0));
  447. pe->lpid = cpu_to_be32(mfspr(SPRN_LPID));
  448. pe->pid = cpu_to_be32(pidr);
  449. pe->tid = cpu_to_be32(tidr);
  450. pe->amr = cpu_to_be64(amr);
  451. pe->software_state = cpu_to_be32(SPA_PE_VALID);
  452. mm_context_add_copro(mm);
  453. /*
  454. * Barrier is to make sure PE is visible in the SPA before it
  455. * is used by the device. It also helps with the global TLBI
  456. * invalidation
  457. */
  458. mb();
  459. radix_tree_insert(&spa->pe_tree, pe_handle, pe_data);
  460. /*
  461. * The mm must stay valid for as long as the device uses it. We
  462. * lower the count when the context is removed from the SPA.
  463. *
  464. * We grab mm_count (and not mm_users), as we don't want to
  465. * end up in a circular dependency if a process mmaps its
  466. * mmio, therefore incrementing the file ref count when
  467. * calling mmap(), and forgets to unmap before exiting. In
  468. * that scenario, when the kernel handles the death of the
  469. * process, the file is not cleaned because unmap was not
  470. * called, and the mm wouldn't be freed because we would still
  471. * have a reference on mm_users. Incrementing mm_count solves
  472. * the problem.
  473. */
  474. mmgrab(mm);
  475. trace_ocxl_context_add(current->pid, spa->spa_mem, pasid, pidr, tidr);
  476. unlock:
  477. mutex_unlock(&spa->spa_lock);
  478. return rc;
  479. }
  480. EXPORT_SYMBOL_GPL(ocxl_link_add_pe);
  481. int ocxl_link_update_pe(void *link_handle, int pasid, __u16 tid)
  482. {
  483. struct link *link = (struct link *) link_handle;
  484. struct spa *spa = link->spa;
  485. struct ocxl_process_element *pe;
  486. int pe_handle, rc;
  487. if (pasid > SPA_PASID_MAX)
  488. return -EINVAL;
  489. pe_handle = pasid & SPA_PE_MASK;
  490. pe = spa->spa_mem + pe_handle;
  491. mutex_lock(&spa->spa_lock);
  492. pe->tid = cpu_to_be32(tid);
  493. /*
  494. * The barrier makes sure the PE is updated
  495. * before we clear the NPU context cache below, so that the
  496. * old PE cannot be reloaded erroneously.
  497. */
  498. mb();
  499. /*
  500. * hook to platform code
  501. * On powerpc, the entry needs to be cleared from the context
  502. * cache of the NPU.
  503. */
  504. rc = pnv_ocxl_spa_remove_pe_from_cache(link->platform_data, pe_handle);
  505. WARN_ON(rc);
  506. mutex_unlock(&spa->spa_lock);
  507. return rc;
  508. }
  509. int ocxl_link_remove_pe(void *link_handle, int pasid)
  510. {
  511. struct link *link = (struct link *) link_handle;
  512. struct spa *spa = link->spa;
  513. struct ocxl_process_element *pe;
  514. struct pe_data *pe_data;
  515. int pe_handle, rc;
  516. if (pasid > SPA_PASID_MAX)
  517. return -EINVAL;
  518. /*
  519. * About synchronization with our memory fault handler:
  520. *
  521. * Before removing the PE, the driver is supposed to have
  522. * notified the AFU, which should have cleaned up and make
  523. * sure the PASID is no longer in use, including pending
  524. * interrupts. However, there's no way to be sure...
  525. *
  526. * We clear the PE and remove the context from our radix
  527. * tree. From that point on, any new interrupt for that
  528. * context will fail silently, which is ok. As mentioned
  529. * above, that's not expected, but it could happen if the
  530. * driver or AFU didn't do the right thing.
  531. *
  532. * There could still be a bottom half running, but we don't
  533. * need to wait/flush, as it is managing a reference count on
  534. * the mm it reads from the radix tree.
  535. */
  536. pe_handle = pasid & SPA_PE_MASK;
  537. pe = spa->spa_mem + pe_handle;
  538. mutex_lock(&spa->spa_lock);
  539. if (!(be32_to_cpu(pe->software_state) & SPA_PE_VALID)) {
  540. rc = -EINVAL;
  541. goto unlock;
  542. }
  543. trace_ocxl_context_remove(current->pid, spa->spa_mem, pasid,
  544. be32_to_cpu(pe->pid), be32_to_cpu(pe->tid));
  545. memset(pe, 0, sizeof(struct ocxl_process_element));
  546. /*
  547. * The barrier makes sure the PE is removed from the SPA
  548. * before we clear the NPU context cache below, so that the
  549. * old PE cannot be reloaded erroneously.
  550. */
  551. mb();
  552. /*
  553. * hook to platform code
  554. * On powerpc, the entry needs to be cleared from the context
  555. * cache of the NPU.
  556. */
  557. rc = pnv_ocxl_spa_remove_pe_from_cache(link->platform_data, pe_handle);
  558. WARN_ON(rc);
  559. pe_data = radix_tree_delete(&spa->pe_tree, pe_handle);
  560. if (!pe_data) {
  561. WARN(1, "Couldn't find pe data when removing PE\n");
  562. } else {
  563. mm_context_remove_copro(pe_data->mm);
  564. mmdrop(pe_data->mm);
  565. kfree_rcu(pe_data, rcu);
  566. }
  567. unlock:
  568. mutex_unlock(&spa->spa_lock);
  569. return rc;
  570. }
  571. EXPORT_SYMBOL_GPL(ocxl_link_remove_pe);
  572. int ocxl_link_irq_alloc(void *link_handle, int *hw_irq, u64 *trigger_addr)
  573. {
  574. struct link *link = (struct link *) link_handle;
  575. int rc, irq;
  576. u64 addr;
  577. if (atomic_dec_if_positive(&link->irq_available) < 0)
  578. return -ENOSPC;
  579. rc = pnv_ocxl_alloc_xive_irq(&irq, &addr);
  580. if (rc) {
  581. atomic_inc(&link->irq_available);
  582. return rc;
  583. }
  584. *hw_irq = irq;
  585. *trigger_addr = addr;
  586. return 0;
  587. }
  588. EXPORT_SYMBOL_GPL(ocxl_link_irq_alloc);
  589. void ocxl_link_free_irq(void *link_handle, int hw_irq)
  590. {
  591. struct link *link = (struct link *) link_handle;
  592. pnv_ocxl_free_xive_irq(hw_irq);
  593. atomic_inc(&link->irq_available);
  594. }
  595. EXPORT_SYMBOL_GPL(ocxl_link_free_irq);