/* Board support file for Samsung Tuna Board. * * Copyright (C) 2011 Google, Inc. * Copyright (C) 2010 Texas Instruments * * Based on mach-omap2/board-omap4panda.c * * This software is licensed under the terms of the GNU General Public * License version 2, as published by the Free Software Foundation, and * may be copied, distributed, and modified under those terms. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. */ #include #include #include #include #include #if defined(CONFIG_TWL6030_GPADC) #include #elif defined(CONFIG_TWL4030_MADC) #include #else /* CONFIG_TWL6030_MADC */ #include #endif #include #include "mux.h" #include "board-tuna.h" #define GPIO_EAR_MICBIAS_EN 49 #define GPIO_DET_35 0 #define GPIO_EAR_SEND_END 1 #define ADC_CHANNEL_JACK 2 static void sec_jack_set_micbias_state(bool on) { gpio_set_value(GPIO_EAR_MICBIAS_EN, on); } static struct sec_jack_zone sec_jack_zones[] = { { /* adc < 50, unstable zone, default to 3pole if it stays * in this range for a half second (20ms delays, 25 samples) */ .adc_high = 50, .delay_ms = 20, .check_count = 25, .jack_type = SEC_HEADSET_3POLE, }, { /* 50 < adc <= 490, unstable zone, default to 3pole if it stays * in this range for a second (10ms delays, 100 samples) */ .adc_high = 490, .delay_ms = 10, .check_count = 100, .jack_type = SEC_HEADSET_3POLE, }, { /* 490 < adc <= 900, unstable zone, default to 4pole if it * stays in this range for a second (10ms delays, 100 samples) */ .adc_high = 900, .delay_ms = 10, .check_count = 100, .jack_type = SEC_HEADSET_4POLE, }, { /* 900 < adc <= 1500, 4 pole zone, default to 4pole if it * stays in this range for 200ms (20ms delays, 10 samples) */ .adc_high = 1500, .delay_ms = 20, .check_count = 10, .jack_type = SEC_HEADSET_4POLE, }, { /* adc > 1500, unstable zone, default to 3pole if it stays * in this range for a second (10ms delays, 100 samples) */ .adc_high = 0x7fffffff, .delay_ms = 10, .check_count = 100, .jack_type = SEC_HEADSET_3POLE, }, }; /* To support 3-buttons earjack */ static struct sec_jack_buttons_zone sec_jack_buttons_zones[] = { { /* 0 <= adc <= 93, stable zone */ .code = KEY_MEDIA, .adc_low = 0, .adc_high = 93, }, { /* 94 <= adc <= 167, stable zone */ .code = KEY_PREVIOUSSONG, .adc_low = 94, .adc_high = 167, }, { /* 168 <= adc <= 370, stable zone */ .code = KEY_NEXTSONG, .adc_low = 168, .adc_high = 370, }, }; static int sec_jack_get_adc_value(void) { int value; #if defined(CONFIG_TWL6030_GPADC) value = twl6030_get_gpadc_conversion(ADC_CHANNEL_JACK); #elif defined(CONFIG_TWL4030_MADC) value = twl4030_get_madc_conversion(ADC_CHANNEL_JACK); #else /* CONFIG_TWL6030_MADC */ value = twl6030_get_madc_conversion(ADC_CHANNEL_JACK); #endif return (int)(1800*value) / 1024; } struct sec_jack_platform_data sec_jack_pdata = { .set_micbias_state = sec_jack_set_micbias_state, .get_adc_value = sec_jack_get_adc_value, .zones = sec_jack_zones, .num_zones = ARRAY_SIZE(sec_jack_zones), .buttons_zones = sec_jack_buttons_zones, .num_buttons_zones = ARRAY_SIZE(sec_jack_buttons_zones), .det_gpio = GPIO_DET_35, .send_end_gpio = GPIO_EAR_SEND_END, }; static struct platform_device sec_device_jack = { .name = "sec_jack", .id = 1, /* will be used also for gpio_event id */ .dev.platform_data = &sec_jack_pdata, }; void __init omap4_tuna_jack_init(void) { omap_mux_init_signal("sim_io.gpio_wk0", OMAP_PIN_INPUT); gpio_request(GPIO_DET_35, "det_35_en"); gpio_direction_input(GPIO_DET_35); omap_mux_init_signal("sim_clk.gpio_wk1", OMAP_PIN_INPUT); gpio_request(GPIO_EAR_SEND_END, "ear_send_end"); gpio_direction_input(GPIO_EAR_SEND_END); omap_mux_init_signal("gpmc_a25.gpio_49", OMAP_PIN_OUTPUT | OMAP_MUX_MODE3); gpio_request(GPIO_EAR_MICBIAS_EN, "ear_micbias_en"); gpio_direction_output(GPIO_EAR_MICBIAS_EN, 0); gpio_free(GPIO_DET_35); gpio_free(GPIO_EAR_SEND_END); platform_device_register(&sec_device_jack); }