static int highbank_l2_err_remove(struct platform_device *pdev)
{
	struct edac_device_ctl_info *dci = platform_get_drvdata(pdev);

	edac_device_del_device(&pdev->dev);
	edac_device_free_ctl_info(dci);
	return 0;
}
static int octeon_l2c_remove(struct platform_device *pdev)
{
	struct edac_device_ctl_info *l2c = platform_get_drvdata(pdev);

	edac_device_del_device(&pdev->dev);
	edac_device_free_ctl_info(l2c);

	return 0;
}
Esempio n. 3
0
static int qcom_llcc_edac_remove(struct platform_device *pdev)
{
	struct edac_device_ctl_info *edev_ctl = dev_get_drvdata(&pdev->dev);

	edac_device_del_device(edev_ctl->dev);
	edac_device_free_ctl_info(edev_ctl);

	return 0;
}
Esempio n. 4
0
static int qcom_llcc_edac_probe(struct platform_device *pdev)
{
	struct llcc_drv_data *llcc_driv_data = pdev->dev.platform_data;
	struct edac_device_ctl_info *edev_ctl;
	struct device *dev = &pdev->dev;
	int ecc_irq;
	int rc;

	rc = qcom_llcc_core_setup(llcc_driv_data->bcast_regmap);
	if (rc)
		return rc;

	/* Allocate edac control info */
	edev_ctl = edac_device_alloc_ctl_info(0, "qcom-llcc", 1, "bank",
					      llcc_driv_data->num_banks, 1,
					      NULL, 0,
					      edac_device_alloc_index());

	if (!edev_ctl)
		return -ENOMEM;

	edev_ctl->dev = dev;
	edev_ctl->mod_name = dev_name(dev);
	edev_ctl->dev_name = dev_name(dev);
	edev_ctl->ctl_name = "llcc";
	edev_ctl->panic_on_ue = LLCC_ERP_PANIC_ON_UE;
	edev_ctl->pvt_info = llcc_driv_data;

	rc = edac_device_add_device(edev_ctl);
	if (rc)
		goto out_mem;

	platform_set_drvdata(pdev, edev_ctl);

	/* Request for ecc irq */
	ecc_irq = llcc_driv_data->ecc_irq;
	if (ecc_irq < 0) {
		rc = -ENODEV;
		goto out_dev;
	}
	rc = devm_request_irq(dev, ecc_irq, llcc_ecc_irq_handler,
			      IRQF_TRIGGER_HIGH, "llcc_ecc", edev_ctl);
	if (rc)
		goto out_dev;

	return rc;

out_dev:
	edac_device_del_device(edev_ctl->dev);
out_mem:
	edac_device_free_ctl_info(edev_ctl);

	return rc;
}
Esempio n. 5
0
/**
 * zynqmp_ocm_edac_remove - Unbind driver from controller
 * @pdev:	Pointer to the platform_device struct
 *
 * Return: Unconditionally 0
 */
static int zynqmp_ocm_edac_remove(struct platform_device *pdev)
{
	struct edac_device_ctl_info *dci = platform_get_drvdata(pdev);
	struct zynqmp_ocm_edac_priv *priv = dci->pvt_info;

	writel(OCM_CEUE_MASK, priv->baseaddr + OCM_IDS_OFST);
	edac_device_del_device(&pdev->dev);
	edac_device_free_ctl_info(dci);

	return 0;
}
Esempio n. 6
0
static int mpc85xx_l2_err_remove(struct of_device *op)
{
	struct edac_device_ctl_info *edac_dev = dev_get_drvdata(&op->dev);
	struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;

	debugf0("%s()\n", __func__);

	if (edac_op_state == EDAC_OPSTATE_INT) {
		out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINTEN, 0);
		irq_dispose_mapping(pdata->irq);
	}

	out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDIS, orig_l2_err_disable);
	edac_device_del_device(&op->dev);
	edac_device_free_ctl_info(edac_dev);
	return 0;
}
Esempio n. 7
0
/**
 * pl310_edac_l2_remove - Unbind driver from controller
 * @pdev:	Pointer to the platform_device struct
 *
 * This routine unbinds the EDAC device controller instance associated
 * with the specified arm,pl310-cache controller described by the
 * OpenFirmware device tree node passed as a parameter.
 *
 * Return: Always returns 0
 */
static int pl310_edac_l2_remove(struct platform_device *pdev)
{
	struct edac_device_ctl_info *dci = platform_get_drvdata(pdev);
	struct pl310_edac_l2_priv *priv = dci->pvt_info;
	u32 regval;

	if (edac_op_state != EDAC_OPSTATE_POLL) {
		regval = readl(priv->base+L2X0_INTR_MASK);
		regval &= ~(L2X0_INTR_PARRD_MASK | L2X0_INTR_PARRT_MASK);
		writel(regval, priv->base+L2X0_INTR_MASK);
	}

	edac_device_del_device(&pdev->dev);
	edac_device_free_ctl_info(dci);

	return 0;
}
Esempio n. 8
0
static void amd8111_dev_remove(struct pci_dev *dev)
{
	struct amd8111_dev_info *dev_info;

	for (dev_info = amd8111_devices; dev_info->err_dev; dev_info++)
		if (dev_info->dev->device == dev->device)
			break;

	if (!dev_info->err_dev)	/* should never happen */
		return;

	if (dev_info->edac_dev) {
		edac_device_del_device(dev_info->edac_dev->dev);
		edac_device_free_ctl_info(dev_info->edac_dev);
	}

	if (dev_info->exit)
		dev_info->exit(dev_info);

	pci_dev_put(dev_info->dev);
}
Esempio n. 9
0
static int __devinit mpc85xx_l2_err_probe(struct of_device *op,
					  const struct of_device_id *match)
{
	struct edac_device_ctl_info *edac_dev;
	struct mpc85xx_l2_pdata *pdata;
	struct resource r;
	int res;

	if (!devres_open_group(&op->dev, mpc85xx_l2_err_probe, GFP_KERNEL))
		return -ENOMEM;

	edac_dev = edac_device_alloc_ctl_info(sizeof(*pdata),
					      "cpu", 1, "L", 1, 2, NULL, 0,
					      edac_dev_idx);
	if (!edac_dev) {
		devres_release_group(&op->dev, mpc85xx_l2_err_probe);
		return -ENOMEM;
	}

	pdata = edac_dev->pvt_info;
	pdata->name = "mpc85xx_l2_err";
	pdata->irq = NO_IRQ;
	edac_dev->dev = &op->dev;
	dev_set_drvdata(edac_dev->dev, edac_dev);
	edac_dev->ctl_name = pdata->name;
	edac_dev->dev_name = pdata->name;

	res = of_address_to_resource(op->node, 0, &r);
	if (res) {
		printk(KERN_ERR "%s: Unable to get resource for "
		       "L2 err regs\n", __func__);
		goto err;
	}

	/* we only need the error registers */
	r.start += 0xe00;

	if (!devm_request_mem_region(&op->dev, r.start,
				     r.end - r.start + 1, pdata->name)) {
		printk(KERN_ERR "%s: Error while requesting mem region\n",
		       __func__);
		res = -EBUSY;
		goto err;
	}

	pdata->l2_vbase = devm_ioremap(&op->dev, r.start, r.end - r.start + 1);
	if (!pdata->l2_vbase) {
		printk(KERN_ERR "%s: Unable to setup L2 err regs\n", __func__);
		res = -ENOMEM;
		goto err;
	}

	out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDET, ~0);

	orig_l2_err_disable = in_be32(pdata->l2_vbase + MPC85XX_L2_ERRDIS);

	/* clear the err_dis */
	out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDIS, 0);

	edac_dev->mod_name = EDAC_MOD_STR;

	if (edac_op_state == EDAC_OPSTATE_POLL)
		edac_dev->edac_check = mpc85xx_l2_check;

	mpc85xx_set_l2_sysfs_attributes(edac_dev);

	pdata->edac_idx = edac_dev_idx++;

	if (edac_device_add_device(edac_dev) > 0) {
		debugf3("%s(): failed edac_device_add_device()\n", __func__);
		goto err;
	}

	if (edac_op_state == EDAC_OPSTATE_INT) {
		pdata->irq = irq_of_parse_and_map(op->node, 0);
		res = devm_request_irq(&op->dev, pdata->irq,
				       mpc85xx_l2_isr, IRQF_DISABLED,
				       "[EDAC] L2 err", edac_dev);
		if (res < 0) {
			printk(KERN_ERR
			       "%s: Unable to requiest irq %d for "
			       "MPC85xx L2 err\n", __func__, pdata->irq);
			irq_dispose_mapping(pdata->irq);
			res = -ENODEV;
			goto err2;
		}

		printk(KERN_INFO EDAC_MOD_STR " acquired irq %d for L2 Err\n",
		       pdata->irq);

		edac_dev->op_state = OP_RUNNING_INTERRUPT;

		out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINTEN, L2_EIE_MASK);
	}

	devres_remove_group(&op->dev, mpc85xx_l2_err_probe);

	debugf3("%s(): success\n", __func__);
	printk(KERN_INFO EDAC_MOD_STR " L2 err registered\n");

	return 0;

err2:
	edac_device_del_device(&op->dev);
err:
	devres_release_group(&op->dev, mpc85xx_l2_err_probe);
	edac_device_free_ctl_info(edac_dev);
	return res;
}
static int highbank_l2_err_probe(struct platform_device *pdev)
{
	const struct of_device_id *id;
	struct edac_device_ctl_info *dci;
	struct hb_l2_drvdata *drvdata;
	struct resource *r;
	int res = 0;

	dci = edac_device_alloc_ctl_info(sizeof(*drvdata), "cpu",
		1, "L", 1, 2, NULL, 0, 0);
	if (!dci)
		return -ENOMEM;

	drvdata = dci->pvt_info;
	dci->dev = &pdev->dev;
	platform_set_drvdata(pdev, dci);

	if (!devres_open_group(&pdev->dev, NULL, GFP_KERNEL))
		return -ENOMEM;

	r = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	if (!r) {
		dev_err(&pdev->dev, "Unable to get mem resource\n");
		res = -ENODEV;
		goto err;
	}

	if (!devm_request_mem_region(&pdev->dev, r->start,
				     resource_size(r), dev_name(&pdev->dev))) {
		dev_err(&pdev->dev, "Error while requesting mem region\n");
		res = -EBUSY;
		goto err;
	}

	drvdata->base = devm_ioremap(&pdev->dev, r->start, resource_size(r));
	if (!drvdata->base) {
		dev_err(&pdev->dev, "Unable to map regs\n");
		res = -ENOMEM;
		goto err;
	}

	id = of_match_device(hb_l2_err_of_match, &pdev->dev);
	dci->mod_name = pdev->dev.driver->name;
	dci->ctl_name = id ? id->compatible : "unknown";
	dci->dev_name = dev_name(&pdev->dev);

	if (edac_device_add_device(dci))
		goto err;

	drvdata->db_irq = platform_get_irq(pdev, 0);
	res = devm_request_irq(&pdev->dev, drvdata->db_irq,
			       highbank_l2_err_handler,
			       0, dev_name(&pdev->dev), dci);
	if (res < 0)
		goto err2;

	drvdata->sb_irq = platform_get_irq(pdev, 1);
	res = devm_request_irq(&pdev->dev, drvdata->sb_irq,
			       highbank_l2_err_handler,
			       0, dev_name(&pdev->dev), dci);
	if (res < 0)
		goto err2;

	devres_close_group(&pdev->dev, NULL);
	return 0;
err2:
	edac_device_del_device(&pdev->dev);
err:
	devres_release_group(&pdev->dev, NULL);
	edac_device_free_ctl_info(dci);
	return res;
}
Esempio n. 11
0
/**
 * pl310_edac_l2_probe - Check controller and bind driver
 * @pdev:	Pointer to the platform_device struct
 *
 * This routine probes a specific arm,pl310-cache instance for binding
 * with the driver.
 *
 * Return: 0 if the controller instance was successfully bound to the
 * driver; otherwise, < 0 on error.
 */
static int pl310_edac_l2_probe(struct platform_device *pdev)
{
	struct edac_device_ctl_info *dci;
	struct pl310_edac_l2_priv *priv;
	int rc;
	struct resource *res;
	void __iomem *baseaddr;
	u32 regval;

	/* Get the data from the platform device */
	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	baseaddr = devm_ioremap_resource(&pdev->dev, res);
	if (IS_ERR(baseaddr))
		return PTR_ERR(baseaddr);

	/* Check for the ecc enable status */
	if (pl310_edac_l2_get_paritystate(baseaddr) == false) {
		dev_err(&pdev->dev, "parity check not enabled\n");
		return -ENXIO;
	}

	dci = edac_device_alloc_ctl_info(sizeof(*priv), "l2cache",
					 1, "L", 1, 1, NULL, 0,
					 edac_device_alloc_index());
	if (IS_ERR(dci))
		return PTR_ERR(dci);

	priv = dci->pvt_info;
	priv->base = baseaddr;
	dci->dev = &pdev->dev;
	dci->mod_name = "pl310_edac_l2";
	dci->ctl_name = "pl310_l2_controller";
	dci->dev_name = dev_name(&pdev->dev);

	priv->irq = platform_get_irq(pdev, 0);
	rc = devm_request_irq(&pdev->dev, priv->irq,
				pl310_edac_l2_int_handler,
				0, dev_name(&pdev->dev), (void *)dci);
	if (rc < 0) {
		dci->edac_check = pl310_edac_l2_poll_handler;
		edac_op_state = EDAC_OPSTATE_POLL;
	}

	rc = edac_device_add_device(dci);
	if (rc) {
		dev_err(&pdev->dev, "failed to register with EDAC core\n");
		goto del_edac_device;
	}

	if (edac_op_state != EDAC_OPSTATE_POLL) {
		regval = readl(priv->base+L2X0_INTR_MASK);
		regval |= (L2X0_INTR_PARRD_MASK | L2X0_INTR_PARRT_MASK);
		writel(regval, priv->base+L2X0_INTR_MASK);
	}

	return rc;

del_edac_device:
	edac_device_del_device(&pdev->dev);
	edac_device_free_ctl_info(dci);

	return rc;
}
Esempio n. 12
0
/**
 * zynqmp_ocm_edac_probe - Check controller and bind driver
 * @pdev:	Pointer to the platform_device struct
 *
 * Probes a specific controller instance for binding with the driver.
 *
 * Return: 0 if the controller instance was successfully bound to the
 * driver; otherwise, < 0 on error.
 */
static int zynqmp_ocm_edac_probe(struct platform_device *pdev)
{
	struct edac_device_ctl_info *dci;
	struct zynqmp_ocm_edac_priv *priv;
	int irq, status;
	struct resource *res;
	void __iomem *baseaddr;

	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	baseaddr = devm_ioremap_resource(&pdev->dev, res);
	if (IS_ERR(baseaddr))
		return PTR_ERR(baseaddr);

	if (!zynqmp_ocm_edac_get_eccstate(baseaddr)) {
		edac_printk(KERN_INFO, EDAC_DEVICE,
				"ECC not enabled - Disabling EDAC driver\n");
		return -ENXIO;
	}

	dci = edac_device_alloc_ctl_info(sizeof(*priv), ZYNQMP_OCM_EDAC_STRING,
			1, ZYNQMP_OCM_EDAC_STRING, 1, 0, NULL, 0, 0);
	if (!dci) {
		edac_printk(KERN_ERR, EDAC_DEVICE,
				"Unable to allocate EDAC device\n");
		return -ENOMEM;
	}

	priv = dci->pvt_info;
	platform_set_drvdata(pdev, dci);
	dci->dev = &pdev->dev;
	priv->baseaddr = baseaddr;
	dci->mod_name = pdev->dev.driver->name;
	dci->ctl_name = ZYNQMP_OCM_EDAC_STRING;
	dci->dev_name = dev_name(&pdev->dev);

	zynqmp_set_ocm_edac_sysfs_attributes(dci);
	if (edac_device_add_device(dci))
		goto free_dev_ctl;

	irq = platform_get_irq(pdev, 0);
	if (irq < 0) {
		edac_printk(KERN_ERR, EDAC_DEVICE,
				"No irq %d in DT\n", irq);
		return irq;
	}

	status = devm_request_irq(&pdev->dev, irq,
		zynqmp_ocm_edac_intr_handler,
		0, dev_name(&pdev->dev), dci);
	if (status < 0) {
		edac_printk(KERN_ERR, EDAC_DEVICE, "Failed to request Irq\n");
		goto free_edac_dev;
	}

	writel(OCM_CEUE_MASK, priv->baseaddr + OCM_IEN_OFST);

	return 0;

free_edac_dev:
	edac_device_del_device(&pdev->dev);
free_dev_ctl:
	edac_device_free_ctl_info(dci);

	return -1;
}