static int octeon_i2c_probe(struct platform_device *pdev) { int irq, result = 0; struct octeon_i2c *i2c; struct resource *res_mem; /* All adaptors have an irq. */ irq = platform_get_irq(pdev, 0); if (irq < 0) return irq; i2c = devm_kzalloc(&pdev->dev, sizeof(*i2c), GFP_KERNEL); if (!i2c) { dev_err(&pdev->dev, "kzalloc failed\n"); result = -ENOMEM; goto out; } i2c->dev = &pdev->dev; res_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (res_mem == NULL) { dev_err(i2c->dev, "found no memory resource\n"); result = -ENXIO; goto out; } i2c->twsi_phys = res_mem->start; i2c->regsize = resource_size(res_mem); /* * "clock-rate" is a legacy binding, the official binding is * "clock-frequency". Try the official one first and then * fall back if it doesn't exist. */ if (of_property_read_u32(pdev->dev.of_node, "clock-frequency", &i2c->twsi_freq) && of_property_read_u32(pdev->dev.of_node, "clock-rate", &i2c->twsi_freq)) { dev_err(i2c->dev, "no I2C 'clock-rate' or 'clock-frequency' property\n"); result = -ENXIO; goto out; } i2c->sys_freq = octeon_get_io_clock_rate(); if (!devm_request_mem_region(&pdev->dev, i2c->twsi_phys, i2c->regsize, res_mem->name)) { dev_err(i2c->dev, "request_mem_region failed\n"); goto out; } i2c->twsi_base = devm_ioremap(&pdev->dev, i2c->twsi_phys, i2c->regsize); init_waitqueue_head(&i2c->queue); i2c->irq = irq; result = devm_request_irq(&pdev->dev, i2c->irq, octeon_i2c_isr, 0, DRV_NAME, i2c); if (result < 0) { dev_err(i2c->dev, "failed to attach interrupt\n"); goto out; } result = octeon_i2c_initlowlevel(i2c); if (result) { dev_err(i2c->dev, "init low level failed\n"); goto out; } result = octeon_i2c_setclock(i2c); if (result) { dev_err(i2c->dev, "clock init failed\n"); goto out; } i2c->adap = octeon_i2c_ops; i2c->adap.dev.parent = &pdev->dev; i2c->adap.dev.of_node = pdev->dev.of_node; i2c_set_adapdata(&i2c->adap, i2c); platform_set_drvdata(pdev, i2c); result = i2c_add_adapter(&i2c->adap); if (result < 0) { dev_err(i2c->dev, "failed to add adapter\n"); goto fail_add; } dev_info(i2c->dev, "version %s\n", DRV_VERSION); of_i2c_register_devices(&i2c->adap); return 0; fail_add: platform_set_drvdata(pdev, NULL); out: return result; };
static int __devinit octeon_i2c_probe(struct platform_device *pdev) { int irq, result = 0; struct octeon_i2c *i2c; struct octeon_i2c_data *i2c_data; struct resource *res_mem; /* All adaptors have an irq. */ irq = platform_get_irq(pdev, 0); if (irq < 0) return irq; i2c = kzalloc(sizeof(*i2c), GFP_KERNEL); if (!i2c) { dev_err(&pdev->dev, "kzalloc failed\n"); result = -ENOMEM; goto out; } i2c->dev = &pdev->dev; i2c_data = pdev->dev.platform_data; res_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (res_mem == NULL) { dev_err(i2c->dev, "found no memory resource\n"); result = -ENXIO; goto fail_region; } if (i2c_data == NULL) { dev_err(i2c->dev, "no I2C frequency data\n"); result = -ENXIO; goto fail_region; } i2c->twsi_phys = res_mem->start; i2c->regsize = resource_size(res_mem); i2c->twsi_freq = i2c_data->i2c_freq; i2c->sys_freq = i2c_data->sys_freq; if (!request_mem_region(i2c->twsi_phys, i2c->regsize, res_mem->name)) { dev_err(i2c->dev, "request_mem_region failed\n"); goto fail_region; } i2c->twsi_base = ioremap(i2c->twsi_phys, i2c->regsize); init_waitqueue_head(&i2c->queue); i2c->irq = irq; result = request_irq(i2c->irq, octeon_i2c_isr, 0, DRV_NAME, i2c); if (result < 0) { dev_err(i2c->dev, "failed to attach interrupt\n"); goto fail_irq; } result = octeon_i2c_initlowlevel(i2c); if (result) { dev_err(i2c->dev, "init low level failed\n"); goto fail_add; } result = octeon_i2c_setclock(i2c); if (result) { dev_err(i2c->dev, "clock init failed\n"); goto fail_add; } i2c->adap = octeon_i2c_ops; i2c->adap.dev.parent = &pdev->dev; i2c->adap.nr = pdev->id >= 0 ? pdev->id : 0; i2c_set_adapdata(&i2c->adap, i2c); platform_set_drvdata(pdev, i2c); result = i2c_add_numbered_adapter(&i2c->adap); if (result < 0) { dev_err(i2c->dev, "failed to add adapter\n"); goto fail_add; } dev_info(i2c->dev, "version %s\n", DRV_VERSION); return result; fail_add: platform_set_drvdata(pdev, NULL); free_irq(i2c->irq, i2c); fail_irq: iounmap(i2c->twsi_base); release_mem_region(i2c->twsi_phys, i2c->regsize); fail_region: kfree(i2c); out: return result; };