forked from ~ljy/RK356X_SDK_RELEASE

hc
2024-05-14 bedbef8ad3e75a304af6361af235302bcc61d06b
kernel/drivers/soc/fsl/qbman/qman_portal.c
....@@ -38,6 +38,7 @@
3838 #define CONFIG_FSL_DPA_PIRQ_FAST 1
3939
4040 static struct cpumask portal_cpus;
41
+static int __qman_portals_probed;
4142 /* protect qman global registers and global data shared among portals */
4243 static DEFINE_SPINLOCK(qman_lock);
4344
....@@ -195,8 +196,10 @@
195196 if (p) {
196197 pcfg = qman_get_qm_portal_config(p);
197198 if (pcfg) {
198
- irq_set_affinity(pcfg->irq, cpumask_of(0));
199
- qman_portal_update_sdest(pcfg, 0);
199
+ /* select any other online CPU */
200
+ cpu = cpumask_any_but(cpu_online_mask, cpu);
201
+ irq_set_affinity(pcfg->irq, cpumask_of(cpu));
202
+ qman_portal_update_sdest(pcfg, cpu);
200203 }
201204 }
202205 return 0;
....@@ -218,13 +221,19 @@
218221 return 0;
219222 }
220223
224
+int qman_portals_probed(void)
225
+{
226
+ return __qman_portals_probed;
227
+}
228
+EXPORT_SYMBOL_GPL(qman_portals_probed);
229
+
221230 static int qman_portal_probe(struct platform_device *pdev)
222231 {
223232 struct device *dev = &pdev->dev;
224233 struct device_node *node = dev->of_node;
225234 struct qm_portal_config *pcfg;
226235 struct resource *addr_phys[2];
227
- int irq, cpu, err;
236
+ int irq, cpu, err, i;
228237 u32 val;
229238
230239 err = qman_is_probed();
....@@ -236,8 +245,10 @@
236245 }
237246
238247 pcfg = devm_kmalloc(dev, sizeof(*pcfg), GFP_KERNEL);
239
- if (!pcfg)
248
+ if (!pcfg) {
249
+ __qman_portals_probed = -1;
240250 return -ENOMEM;
251
+ }
241252
242253 pcfg->dev = dev;
243254
....@@ -245,28 +256,27 @@
245256 DPAA_PORTAL_CE);
246257 if (!addr_phys[0]) {
247258 dev_err(dev, "Can't get %pOF property 'reg::CE'\n", node);
248
- return -ENXIO;
259
+ goto err_ioremap1;
249260 }
250261
251262 addr_phys[1] = platform_get_resource(pdev, IORESOURCE_MEM,
252263 DPAA_PORTAL_CI);
253264 if (!addr_phys[1]) {
254265 dev_err(dev, "Can't get %pOF property 'reg::CI'\n", node);
255
- return -ENXIO;
266
+ goto err_ioremap1;
256267 }
257268
258269 err = of_property_read_u32(node, "cell-index", &val);
259270 if (err) {
260271 dev_err(dev, "Can't get %pOF property 'cell-index'\n", node);
272
+ __qman_portals_probed = -1;
261273 return err;
262274 }
263275 pcfg->channel = val;
264276 pcfg->cpu = -1;
265277 irq = platform_get_irq(pdev, 0);
266
- if (irq <= 0) {
267
- dev_err(dev, "Can't get %pOF IRQ\n", node);
268
- return -ENXIO;
269
- }
278
+ if (irq <= 0)
279
+ goto err_ioremap1;
270280 pcfg->irq = irq;
271281
272282 pcfg->addr_virt_ce = memremap(addr_phys[0]->start,
....@@ -289,6 +299,7 @@
289299 spin_lock(&qman_lock);
290300 cpu = cpumask_next_zero(-1, &portal_cpus);
291301 if (cpu >= nr_cpu_ids) {
302
+ __qman_portals_probed = 1;
292303 /* unassigned portal, skip init */
293304 spin_unlock(&qman_lock);
294305 return 0;
....@@ -312,6 +323,22 @@
312323 if (!cpu_online(cpu))
313324 qman_offline_cpu(cpu);
314325
326
+ if (__qman_portals_probed == 1 && qman_requires_cleanup()) {
327
+ /*
328
+ * QMan wasn't reset prior to boot (Kexec for example)
329
+ * Empty all the frame queues so they are in reset state
330
+ */
331
+ for (i = 0; i < qm_get_fqid_maxcnt(); i++) {
332
+ err = qman_shutdown_fq(i);
333
+ if (err) {
334
+ dev_err(dev, "Failed to shutdown frame queue %d\n",
335
+ i);
336
+ goto err_portal_init;
337
+ }
338
+ }
339
+ qman_done_cleanup();
340
+ }
341
+
315342 return 0;
316343
317344 err_portal_init:
....@@ -319,6 +346,8 @@
319346 err_ioremap2:
320347 memunmap(pcfg->addr_virt_ce);
321348 err_ioremap1:
349
+ __qman_portals_probed = -1;
350
+
322351 return -ENXIO;
323352 }
324353