static int anx7808_i2c_probe(struct i2c_client *client, const struct i2c_device_id *id) { struct anx7808_data *anx7808; struct anx7808_platform_data *pdata; int ret = 0; int sbl_cable_type = 0; #ifdef SP_REGISTER_SET_TEST val_SP_TX_LT_CTRL_REG0 = 0x19; val_SP_TX_LT_CTRL_REG10 = 0x00; val_SP_TX_LT_CTRL_REG11 = 0x00; val_SP_TX_LT_CTRL_REG2 = 0x36; val_SP_TX_LT_CTRL_REG12 = 0x00; val_SP_TX_LT_CTRL_REG1 = 0x26; val_SP_TX_LT_CTRL_REG6 = 0x3c; val_SP_TX_LT_CTRL_REG16 = 0x18; val_SP_TX_LT_CTRL_REG5 = 0x28; val_SP_TX_LT_CTRL_REG8 = 0x2F; val_SP_TX_LT_CTRL_REG15 = 0x10; val_SP_TX_LT_CTRL_REG18 = 0x1F; #endif if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_I2C_BLOCK)) { pr_err("%s: i2c bus does not support the anx7808\n", __func__); ret = -ENODEV; goto exit; } anx7808 = kzalloc(sizeof(struct anx7808_data), GFP_KERNEL); if (!anx7808) { pr_err("%s: failed to allocate driver data\n", __func__); ret = -ENOMEM; goto exit; } if (client->dev.of_node) { pdata = devm_kzalloc(&client->dev, sizeof(struct anx7808_platform_data), GFP_KERNEL); if (!pdata) { pr_err("%s: Failed to allocate memory\n", __func__); return -ENOMEM; } client->dev.platform_data = pdata; /* device tree parsing function call */ ret = anx7808_parse_dt(&client->dev, pdata); if (ret != 0) /* if occurs error */ goto err0; anx7808->pdata = pdata; } else { anx7808->pdata = client->dev.platform_data; } /* to access global platform data */ g_pdata = anx7808->pdata; anx7808_client = client; mutex_init(&anx7808->lock); if (!anx7808->pdata) { ret = -EINVAL; goto err0; } ret = anx7808_init_gpio(anx7808); if (ret) { pr_err("%s: failed to initialize gpio\n", __func__); goto err0; } INIT_DELAYED_WORK(&anx7808->work, anx7808_work_func); INIT_DELAYED_WORK(&anx7808->dwc3_ref_clk_work, dwc3_ref_clk_work_func); anx7808->workqueue = create_singlethread_workqueue("anx7808_work"); if (anx7808->workqueue == NULL) { pr_err("%s: failed to create work queue\n", __func__); ret = -ENOMEM; goto err1; } anx7808->pdata->avdd_power(1); anx7808->pdata->dvdd_power(1); ret = anx7808_system_init(); if (ret) { pr_err("%s: failed to initialize anx7808\n", __func__); goto err2; } client->irq = gpio_to_irq(anx7808->pdata->gpio_cbl_det); if (client->irq < 0) { pr_err("%s : failed to get gpio irq\n", __func__); goto err2; } wake_lock_init(&anx7808->slimport_lock, WAKE_LOCK_SUSPEND, "slimport_wake_lock"); sbl_cable_type = anx7808_get_sbl_cable_type(); if ((lge_get_laf_mode() != LGE_LAF_MODE_LAF) && (sbl_cable_type != CBL_910K)) { ret = request_threaded_irq(client->irq, NULL, anx7808_cbl_det_isr, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING | IRQF_ONESHOT, "anx7808", anx7808); if (ret < 0) { pr_err("%s : failed to request irq\n", __func__); goto err2; } ret = irq_set_irq_wake(client->irq, 1); if (ret < 0) { pr_err("%s : Request irq for cable detect", __func__); pr_err("interrupt wake set fail\n"); goto err3; } ret = enable_irq_wake(client->irq); if (ret < 0) { pr_err("%s : Enable irq for cable detect", __func__); pr_err("interrupt wake enable fail\n"); goto err3; } } else { pr_err("%s %s : %s, Disable cbl det irq!!\n", LOG_TAG, __func__, sbl_cable_type == CBL_910K ? "910K Cable Connected" : "Laf Mode"); } ret = create_sysfs_interfaces(&client->dev); if (ret < 0) { pr_err("%s : sysfs register failed", __func__); goto err3; } #ifdef CONFIG_SLIMPORT_DYNAMIC_HPD hdmi_slimport_ops = devm_kzalloc(&client->dev, sizeof(struct msm_hdmi_slimport_ops), GFP_KERNEL); if (!hdmi_slimport_ops) { pr_err("%s: alloc hdmi slimport ops failed\n", __func__); ret = -ENOMEM; goto err3; } if (anx7808->pdata->hdmi_pdev) { ret = msm_hdmi_register_slimport(anx7808->pdata->hdmi_pdev, hdmi_slimport_ops, anx7808); if (ret) { pr_err("%s: register with hdmi failed\n", __func__); ret = -EPROBE_DEFER; goto err3; } } #endif goto exit; err3: free_irq(client->irq, anx7808); err2: destroy_workqueue(anx7808->workqueue); err1: anx7808_free_gpio(anx7808); err0: anx7808_client = NULL; kfree(anx7808); exit: return ret; }
static int anx7808_i2c_probe(struct i2c_client *client, const struct i2c_device_id *id) { struct anx7808_data *anx7808; struct anx7808_platform_data *pdata; struct device_node *dev_node = client->dev.of_node; struct msm_hdmi_sp_ops *hdmi_sp_ops = NULL; int ret = 0; if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_I2C_BLOCK)) { pr_err("i2c bus does not support anx7808\n"); ret = -ENODEV; goto exit; } anx7808 = kzalloc(sizeof(struct anx7808_data), GFP_KERNEL); if (!anx7808) { pr_err("failed to allocate driver data\n"); ret = -ENOMEM; goto exit; } anx7808->client = client; i2c_set_clientdata(client, anx7808); if (dev_node) { ret = anx7808_parse_dt(dev_node, anx7808); if (ret) { pr_err("failed to parse dt\n"); goto err0; } } else { pdata = client->dev.platform_data; if (pdata == NULL) { pr_err("no platform data.\n"); goto err0; } anx7808->gpio_p_dwn = pdata->gpio_p_dwn; anx7808->gpio_reset = pdata->gpio_reset; anx7808->gpio_int = pdata->gpio_int; anx7808->gpio_cbl_det = pdata->gpio_cbl_det; anx7808->vdd10_name = pdata->vdd10_name; anx7808->vdd10_name = pdata->avdd33_name; } /* initialize hdmi_sp_ops */ hdmi_sp_ops = devm_kzalloc(&client->dev, sizeof(struct msm_hdmi_sp_ops), GFP_KERNEL); if (!hdmi_sp_ops) { pr_err("alloc hdmi sp ops failed\n"); goto err0; } if (anx7808->hdmi_pdev) { ret = msm_hdmi_register_sp(anx7808->hdmi_pdev, hdmi_sp_ops); if (ret) { pr_err("register with hdmi_failed\n"); goto err0; } } anx7808->hdmi_sp_ops = hdmi_sp_ops; the_chip = anx7808; mutex_init(&anx7808->lock); init_completion(&init_aux_ch_completion); ret = anx7808_init_gpio(anx7808); if (ret) { pr_err("failed to initialize gpio\n"); goto err0; } INIT_DELAYED_WORK(&anx7808->work, anx7808_work_func); anx7808->workqueue = create_singlethread_workqueue("anx7808_work"); if (!anx7808->workqueue) { pr_err("failed to create work queue\n"); ret = -ENOMEM; goto err1; } ret = anx7808_avdd_3p3_power(anx7808, true); if (ret) goto err2; ret = anx7808_vdd_1p0_power(anx7808, false); if (ret) goto err3; ret = anx7808_system_init(); if (ret) { pr_err("failed to initialize anx7808\n"); goto err4; } client->irq = gpio_to_irq(anx7808->gpio_cbl_det); if (client->irq < 0) { pr_err("failed to get gpio irq\n"); goto err4; } wake_lock_init(&anx7808->slimport_lock, WAKE_LOCK_SUSPEND, "slimport_wake_lock"); ret = request_threaded_irq(client->irq, NULL, anx7808_cbl_det_isr, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING | IRQF_ONESHOT, "anx7808", anx7808); if (ret < 0) { pr_err("failed to request irq\n"); goto err5; } disable_irq(client->irq); ret = enable_irq_wake(client->irq); if (ret < 0) { pr_err("interrupt wake enable fail\n"); goto err6; } anx7808_setup_video_mode_lut(); anx7808_get_usb_clk(client); return 0; err6: free_irq(client->irq, anx7808); err5: wake_lock_destroy(&anx7808->slimport_lock); err4: if (!anx7808->vdd_reg) regulator_put(anx7808->vdd_reg); err3: if (!anx7808->avdd_reg) regulator_put(anx7808->avdd_reg); err2: destroy_workqueue(anx7808->workqueue); err1: anx7808_free_gpio(anx7808); err0: the_chip = NULL; kfree(anx7808); exit: return ret; }