static int htc_headset_pmic_probe(struct platform_device *pdev) { int ret = 0; uint32_t vers = 0; struct htc_headset_pmic_platform_data *pdata = pdev->dev.platform_data; HS_LOG("++++++++++++++++++++"); hi = kzalloc(sizeof(struct htc_35mm_pmic_info), GFP_KERNEL); if (!hi) return -ENOMEM; hi->pdata.driver_flag = pdata->driver_flag; hi->pdata.hpin_gpio = pdata->hpin_gpio; hi->pdata.hpin_irq = pdata->hpin_irq; hi->pdata.key_gpio = pdata->key_gpio; hi->pdata.key_irq = pdata->key_irq; hi->pdata.key_enable_gpio = pdata->key_enable_gpio; hi->pdata.hs_controller = pdata->hs_controller; hi->pdata.hs_switch = pdata->hs_switch; hi->pdata.adc_mic = pdata->adc_mic; if (!hi->pdata.adc_mic) hi->pdata.adc_mic = HS_DEF_MIC_ADC_16_BIT_MIN; if (pdata->adc_mic_bias[0] && pdata->adc_mic_bias[1]) { memcpy(hi->pdata.adc_mic_bias, pdata->adc_mic_bias, sizeof(hi->pdata.adc_mic_bias)); hi->pdata.adc_mic = hi->pdata.adc_mic_bias[0]; } else { hi->pdata.adc_mic_bias[0] = hi->pdata.adc_mic; hi->pdata.adc_mic_bias[1] = HS_DEF_MIC_ADC_16_BIT_MAX; } if (pdata->adc_remote[5]) memcpy(hi->pdata.adc_remote, pdata->adc_remote, sizeof(hi->pdata.adc_remote)); if (pdata->adc_metrico[0] && pdata->adc_metrico[1]) memcpy(hi->pdata.adc_metrico, pdata->adc_metrico, sizeof(hi->pdata.adc_metrico)); hi->hpin_irq_type = IRQF_TRIGGER_LOW; hi->hpin_debounce = HS_JIFFIES_ZERO; hi->key_irq_type = IRQF_TRIGGER_LOW; wake_lock_init(&hi->hs_wake_lock, WAKE_LOCK_SUSPEND, DRIVER_NAME); detect_wq = create_workqueue("HS_PMIC_DETECT"); if (detect_wq == NULL) { ret = -ENOMEM; HS_ERR("Failed to create detect workqueue"); goto err_create_detect_work_queue; } button_wq = create_workqueue("HS_PMIC_BUTTON"); if (button_wq == NULL) { ret = -ENOMEM; HS_ERR("Failed to create button workqueue"); goto err_create_button_work_queue; } if (hi->pdata.hpin_gpio) { ret = hs_pmic_request_irq(hi->pdata.hpin_gpio, &hi->pdata.hpin_irq, detect_irq_handler, hi->hpin_irq_type, "HS_PMIC_DETECT", 1); if (ret < 0) { HS_ERR("Failed to request PMIC HPIN IRQ (0x%X)", ret); goto err_request_detect_irq; } } if (hi->pdata.key_gpio) { ret = hs_pmic_request_irq(hi->pdata.key_gpio, &hi->pdata.key_irq, button_irq_handler, hi->key_irq_type, "HS_PMIC_BUTTON", 1); if (ret < 0) { HS_ERR("Failed to request PMIC button IRQ (0x%X)", ret); goto err_request_button_irq; } } if (hi->pdata.driver_flag & DRIVER_HS_PMIC_RPC_KEY) { /* Register ADC RPC client */ endpoint_adc = msm_rpc_connect(HS_RPC_CLIENT_PROG, HS_RPC_CLIENT_VERS, 0); if (IS_ERR(endpoint_adc)) { hi->pdata.driver_flag &= ~DRIVER_HS_PMIC_RPC_KEY; HS_LOG("Failed to register ADC RPC client"); } else HS_LOG("Register ADC RPC client successfully"); } if (hi->pdata.driver_flag & DRIVER_HS_PMIC_DYNAMIC_THRESHOLD) { /* Register threshold RPC client */ vers = HS_PMIC_RPC_CLIENT_VERS_3_1; endpoint_current = msm_rpc_connect_compatible( HS_PMIC_RPC_CLIENT_PROG, vers, 0); if (!endpoint_current) { vers = HS_PMIC_RPC_CLIENT_VERS_2_1; endpoint_current = msm_rpc_connect( HS_PMIC_RPC_CLIENT_PROG, vers, 0); } if (!endpoint_current) { vers = HS_PMIC_RPC_CLIENT_VERS_1_1; endpoint_current = msm_rpc_connect( HS_PMIC_RPC_CLIENT_PROG, vers, 0); } if (!endpoint_current) { vers = HS_PMIC_RPC_CLIENT_VERS; endpoint_current = msm_rpc_connect( HS_PMIC_RPC_CLIENT_PROG, vers, 0); } if (IS_ERR(endpoint_current)) { hi->pdata.driver_flag &= ~DRIVER_HS_PMIC_DYNAMIC_THRESHOLD; HS_LOG("Failed to register threshold RPC client"); } else HS_LOG("Register threshold RPC client successfully" " (0x%X)", vers); } hs_pmic_register(); hs_notify_driver_ready(DRIVER_NAME); HS_LOG("--------------------"); return 0; err_request_button_irq: if (hi->pdata.hpin_gpio) { free_irq(hi->pdata.hpin_irq, 0); gpio_free(hi->pdata.hpin_gpio); } err_request_detect_irq: destroy_workqueue(button_wq); err_create_button_work_queue: destroy_workqueue(detect_wq); err_create_detect_work_queue: wake_lock_destroy(&hi->hs_wake_lock); kfree(hi); HS_ERR("Failed to register %s driver", DRIVER_NAME); return ret; }
static int htc_headset_pmic_probe(struct platform_device *pdev) { int ret = 0; uint32_t vers = 0; struct htc_headset_pmic_platform_data *pdata = pdev->dev.platform_data; HS_LOG("++++++++++++++++++++"); pmic_info = kzalloc(sizeof(struct htc_35mm_pmic_info), GFP_KERNEL); if (!pmic_info) return -ENOMEM; pmic_info->pdata.driver_flag = pdata->driver_flag; pmic_info->pdata.hpin_gpio = pdata->hpin_gpio; pmic_info->pdata.hpin_irq = pdata->hpin_irq; pmic_info->pdata.key_enable_gpio = pdata->key_enable_gpio; pmic_info->pdata.hs_controller = pdata->hs_controller; pmic_info->pdata.hs_switch = pdata->hs_switch; pmic_info->pdata.adc_mic = pdata->adc_mic; if (!pmic_info->pdata.adc_mic) pmic_info->pdata.adc_mic = HS_DEF_MIC_ADC_16_BIT; if (pdata->adc_remote[5]) memcpy(pmic_info->pdata.adc_remote, pdata->adc_remote, sizeof(pmic_info->pdata.adc_remote)); if (pdata->adc_metrico[0] && pdata->adc_metrico[1]) memcpy(pmic_info->pdata.adc_metrico, pdata->adc_metrico, sizeof(pmic_info->pdata.adc_metrico)); pmic_info->hpin_irq_type = IRQF_TRIGGER_LOW; pmic_info->hpin_debounce = HS_JIFFIES_INSERT; wake_lock_init(&pmic_info->hs_wake_lock, WAKE_LOCK_SUSPEND, DRIVER_NAME); detect_wq = create_workqueue("detection"); if (detect_wq == NULL) { ret = -ENOMEM; goto err_create_detect_work_queue; } if (pmic_info->pdata.hpin_irq) { ret = request_irq(pmic_info->pdata.hpin_irq, htc_35mm_pmic_irq, pmic_info->hpin_irq_type, "HS_PMIC_DETECT", NULL); if (ret < 0) { HS_LOG("Failed to request PMIC HPIN IRQ (0x%X)", ret); goto err_request_detect_irq; } ret = set_irq_wake(pmic_info->pdata.hpin_irq, 1); if (ret < 0) HS_LOG("Failed to set PMIC HPIN IRQ wake"); } if (pmic_info->pdata.driver_flag & DRIVER_HS_PMIC_RPC_KEY) { /* Register ADC RPC client */ endpoint_adc = msm_rpc_connect(HS_RPC_CLIENT_PROG, HS_RPC_CLIENT_VERS, 0); if (IS_ERR(endpoint_adc)) { pmic_info->pdata.driver_flag &= ~DRIVER_HS_PMIC_RPC_KEY; HS_LOG("Failed to register ADC RPC client"); } else HS_LOG("Register ADC RPC client successfully"); } if (pmic_info->pdata.driver_flag & DRIVER_HS_PMIC_DYNAMIC_THRESHOLD) { /* Register threshold RPC client */ vers = HS_PMIC_RPC_CLIENT_VERS_3_1; endpoint_current = msm_rpc_connect_compatible( HS_PMIC_RPC_CLIENT_PROG, vers, 0); if (!endpoint_current) { vers = HS_PMIC_RPC_CLIENT_VERS_2_1; endpoint_current = msm_rpc_connect( HS_PMIC_RPC_CLIENT_PROG, vers, 0); } if (!endpoint_current) { vers = HS_PMIC_RPC_CLIENT_VERS_1_1; endpoint_current = msm_rpc_connect( HS_PMIC_RPC_CLIENT_PROG, vers, 0); } if (!endpoint_current) { vers = HS_PMIC_RPC_CLIENT_VERS; endpoint_current = msm_rpc_connect( HS_PMIC_RPC_CLIENT_PROG, vers, 0); } if (IS_ERR(endpoint_current)) { pmic_info->pdata.driver_flag &= ~DRIVER_HS_PMIC_DYNAMIC_THRESHOLD; HS_LOG("Failed to register threshold RPC client"); } else HS_LOG("Register threshold RPC client successfully" " (0x%X)", vers); } hs_pmic_register(); hs_notify_driver_ready(DRIVER_NAME); HS_LOG("--------------------"); return 0; err_request_detect_irq: destroy_workqueue(detect_wq); err_create_detect_work_queue: wake_lock_destroy(&pmic_info->hs_wake_lock); kfree(pmic_info); HS_LOG("Failed to register %s driver", DRIVER_NAME); return ret; }