static ssize_t select_jack_store(struct device *dev, struct device_attribute *attr, const char *buf, size_t size) { struct sec_jack_info *hi = dev_get_drvdata(dev); struct sec_jack_platform_data *pdata = hi->pdata; int value = 0; sscanf(buf, "%d", &value); pr_err("%s: User selection : 0X%x", __func__, value); if (value == SEC_HEADSET_4POLE) { pdata->set_micbias_state(true); msleep(100); } sec_jack_set_type(hi, value); return size; }
static void determine_jack_type(struct sec_jack_info *hi) { struct sec_jack_zone *zones = hi->pdata->zones; struct sec_jack_platform_data *pd = hi->pdata; int size = hi->pdata->num_zones; int count[MAX_ZONE_LIMIT] = {0}; int adc; int i; struct adc_queue *adc_q = init_adc_queue(); #if defined (CONFIG_MACH_MELIUS_CHN_CTC) if (nv_hw_revision > 7 || nv_hw_revision < 2) zones = pd->zones_rev08; #elif defined (CONFIG_MACH_SERRANO_ATT) || defined(CONFIG_MACH_SERRANO_VZW) || defined(CONFIG_MACH_SERRANO_USC) || defined(CONFIG_MACH_SERRANO_LRA) if (system_rev > 2) zones = pd->zones_rev03; #endif while (pd->get_det_jack_state()) { #ifdef CONFIG_SAMSUNG_JACK_ADC_SCALE3 adc = pd->get_ear_adc_value(); #else adc = pd->get_adc_value(); #endif if (adc < 0) break; add_adc_queue(adc_q, adc); /* determine the type of headset based on the * adc value. An adc value can fall in various * ranges or zones. Within some ranges, the type * can be returned immediately. Within others, the * value is considered unstable and we need to sample * a few more types (up to the limit determined by * the range) before we return the type for that range. */ for (i = 0; i < size; i++) { if (adc <= zones[i].adc_high) { if (++count[i] > zones[i].check_count) { print_adc_queue(adc_q); pr_debug(MODULE_NAME "determine_jack_type %d, %d, %d\n", zones[i].adc_high, count[i], zones[i].check_count); #if defined(CONFIG_SAMSUNG_JACK_GNDLDET) /* G plus L Detection */ if (!hi->pdata->get_gnd_jack_state()) { pr_err("%s : err 2nd det jack state\n", __func__); handle_jack_not_inserted(hi); recheck_jack = false; return; } #else if (recheck_jack == true && i == 3) { pr_err(MODULE_NAME "something wrong connectoin!\n"); handle_jack_not_inserted(hi); recheck_jack = false; return; } #endif sec_jack_set_type(hi, zones[i].jack_type); /* mic_bias remains enabled * in race condition. */ if (hi->cur_jack_type != SEC_HEADSET_4POLE) { pd->set_micbias_state(false); pr_info(MODULE_NAME "forced mic_bias disable\n"); } recheck_jack = false; return; } #if defined CONFIG_MACH_GOLDEN msleep(zones[i].delay_ms); #else usleep_range(zones[i].delay_ms*1000, zones[i].delay_ms*1000); #endif break; } } } /* jack removed before detection complete */ recheck_jack = false; pr_err("%s : err det jack state\n", __func__); print_adc_queue(adc_q); handle_jack_not_inserted(hi); }
static void determine_jack_type(struct sec_jack_info *hi) { struct sec_jack_zone *zones = hi->pdata->zones; int size = hi->pdata->num_zones; int count[MAX_ZONE_LIMIT] = {0}; int adc; int i; while (hi->pdata->get_det_jack_state()) { adc = hi->pdata->get_adc_value(); pr_info(MODULE_NAME "determine_jack_type adc = %d\n", adc); /* determine the type of headset based on the * adc value. An adc value can fall in various * ranges or zones. Within some ranges, the type * can be returned immediately. Within others, the * value is considered unstable and we need to sample * a few more types (up to the limit determined by * the range) before we return the type for that range. */ for (i = 0; i < size; i++) { if (adc <= zones[i].adc_high) { if (++count[i] > zones[i].check_count) { pr_debug(MODULE_NAME "determine_jack_type %d, %d, %d\n", zones[i].adc_high, count[i], zones[i].check_count); #ifndef CONFIG_MACH_JAGUAR if (recheck_jack == true && i == 3) { #else if (recheck_jack == true && i == 5) { #endif pr_err(MODULE_NAME "something wrong connectoin!\n"); handle_jack_not_inserted(hi); recheck_jack = false; return; } sec_jack_set_type(hi, zones[i].jack_type); /* mic_bias remains enabled * in race condition. */ if (hi->cur_jack_type != SEC_HEADSET_4POLE) { hi->pdata->set_micbias_state(false); pr_info(MODULE_NAME "forced mic_bias disable\n"); } recheck_jack = false; return; } msleep(zones[i].delay_ms); break; } } } /* jack removed before detection complete */ recheck_jack = false; handle_jack_not_inserted(hi); } #ifdef SUPPORT_PBA static ssize_t key_state_onoff_show(struct device *dev, struct device_attribute *attr, char *buf) { struct sec_jack_info *hi = dev_get_drvdata(dev); #ifdef CONFIG_MACH_JAGUAR struct sec_jack_platform_data *pdata = hi->pdata; #endif int value = 0; #ifdef CONFIG_MACH_JAGUAR int send_key_state = 0; #endif #ifndef CONFIG_MACH_JAGUAR if (hi->send_key_pressed != true) value = 0; else value = 1; #else send_key_state = pdata->get_send_key_state(); pr_info(MODULE_NAME "%s : cur_jack_type=%d, send_key_state=%d.\n", __func__, hi->cur_jack_type, send_key_state); if ((hi->cur_jack_type != SEC_HEADSET_4POLE) || (send_key_state != true)) value = 0; else value = 1; #endif return sprintf(buf, "%d\n", value); } static DEVICE_ATTR(key_state, 0664 , key_state_onoff_show, NULL); static ssize_t earjack_state_onoff_show(struct device *dev, struct device_attribute *attr, char *buf) { struct sec_jack_info *hi = dev_get_drvdata(dev); int value = 0; if (hi->cur_jack_type == SEC_HEADSET_4POLE) value = 1; else value = 0; return sprintf(buf, "%d\n", value); } static DEVICE_ATTR(state, 0664 , earjack_state_onoff_show, NULL); static ssize_t select_jack_show(struct device *dev, struct device_attribute *attr, char *buf) { pr_info("%s : operate nothing\n", __func__); return 0; }
static void handle_jack_not_inserted(struct sec_jack_info *hi) { pr_info("%s\n", __func__); sec_jack_set_type(hi, SEC_JACK_NO_DEVICE); hi->pdata->set_micbias_state(false); }
static void handle_jack_not_inserted(struct sec_jack_info *hi) { pr_info(MODULE_NAME "Jack not inserted properly\n"); sec_jack_set_type(hi, SEC_JACK_NO_DEVICE); hi->pdata->set_micbias_state(false); }