diff options
Diffstat (limited to 'firmware/target')
-rw-r--r-- | firmware/target/arm/imx233/button-lradc-imx233.c | 73 | ||||
-rw-r--r-- | firmware/target/arm/imx233/button-lradc-imx233.h | 19 | ||||
-rw-r--r-- | firmware/target/arm/imx233/creative-zen/button-target.h | 11 | ||||
-rw-r--r-- | firmware/target/arm/imx233/lradc-imx233.h | 3 |
4 files changed, 93 insertions, 13 deletions
diff --git a/firmware/target/arm/imx233/button-lradc-imx233.c b/firmware/target/arm/imx233/button-lradc-imx233.c index 6bb7f9babe..141281041b 100644 --- a/firmware/target/arm/imx233/button-lradc-imx233.c +++ b/firmware/target/arm/imx233/button-lradc-imx233.c | |||
@@ -58,6 +58,10 @@ | |||
58 | /* delay's delay */ | 58 | /* delay's delay */ |
59 | #define DELAY (LRADC_DELAY_FREQ / RATE / SAMPLES) | 59 | #define DELAY (LRADC_DELAY_FREQ / RATE / SAMPLES) |
60 | 60 | ||
61 | #ifdef IMX233_BUTTON_LRADC_VDDIO | ||
62 | #define HAS_VDDIO | ||
63 | #endif | ||
64 | |||
61 | static int button_delay; | 65 | static int button_delay; |
62 | static int button_chan; | 66 | static int button_chan; |
63 | static int button_val[2]; | 67 | static int button_val[2]; |
@@ -65,9 +69,18 @@ static int button_idx; | |||
65 | static int button_mask; | 69 | static int button_mask; |
66 | static int table_size; | 70 | static int table_size; |
67 | static int raw_val; | 71 | static int raw_val; |
72 | #ifdef HAS_VDDIO | ||
73 | static int vddio_chan; | ||
74 | static int vddio_val; | ||
75 | #endif | ||
76 | static int delay_chan_mask; // trigger channel mask | ||
77 | static int irq_chan_mask; // triggered channel mask | ||
68 | 78 | ||
69 | static int button_find(int val) | 79 | static int button_find(int val) |
70 | { | 80 | { |
81 | #ifdef IMX233_BUTTON_LRADC_VDDIO | ||
82 | val = (val * IMX233_BUTTON_LRADC_VDDIO) / vddio_val; | ||
83 | #endif | ||
71 | // shortcuts | 84 | // shortcuts |
72 | struct imx233_button_lradc_mapping_t *table = imx233_button_lradc_mapping; | 85 | struct imx233_button_lradc_mapping_t *table = imx233_button_lradc_mapping; |
73 | /* FIXME use a dichotomy */ | 86 | /* FIXME use a dichotomy */ |
@@ -91,18 +104,35 @@ static int button_find(int val) | |||
91 | 104 | ||
92 | static void button_lradc_irq(int chan) | 105 | static void button_lradc_irq(int chan) |
93 | { | 106 | { |
94 | (void) chan; | 107 | /* read value, clear channel */ |
95 | /* read value, kick channel */ | 108 | #ifdef HAS_VDDIO |
96 | raw_val = imx233_lradc_read_channel(button_chan) / SAMPLES; | 109 | if(chan == vddio_chan) |
97 | imx233_lradc_clear_channel(button_chan); | 110 | { |
98 | imx233_lradc_setup_channel(button_chan, true, true, SAMPLES - 1, LRADC_SRC(CHAN)); | 111 | vddio_val = imx233_lradc_read_channel(vddio_chan) / SAMPLES; |
99 | imx233_lradc_setup_delay(button_delay, 1 << button_chan, 0, SAMPLES - 1, DELAY); | 112 | vddio_val *= 2; /* VDDIO channel has internal divider */ |
100 | imx233_lradc_kick_delay(button_delay); | 113 | imx233_lradc_clear_channel(vddio_chan); |
101 | /* compute mask, compare to previous one */ | 114 | imx233_lradc_setup_channel(vddio_chan, true, true, SAMPLES - 1, LRADC_SRC_VDDIO); |
102 | button_val[button_idx] = button_find(raw_val); | 115 | } |
103 | button_idx = 1 - button_idx; | 116 | #endif |
104 | if(button_val[0] == button_val[1]) | 117 | if(chan == button_chan) |
105 | button_mask = button_val[0]; | 118 | { |
119 | raw_val = imx233_lradc_read_channel(button_chan) / SAMPLES; | ||
120 | imx233_lradc_clear_channel(button_chan); | ||
121 | imx233_lradc_setup_channel(button_chan, true, true, SAMPLES - 1, LRADC_SRC(CHAN)); | ||
122 | } | ||
123 | /* record irq, trigger delay if all IRQs have been fired */ | ||
124 | irq_chan_mask |= 1 << chan; | ||
125 | if(irq_chan_mask == delay_chan_mask) | ||
126 | { | ||
127 | irq_chan_mask = 0; | ||
128 | imx233_lradc_setup_delay(button_delay, delay_chan_mask, 0, SAMPLES - 1, DELAY); | ||
129 | imx233_lradc_kick_delay(button_delay); | ||
130 | /* compute mask, compare to previous one */ | ||
131 | button_val[button_idx] = button_find(raw_val); | ||
132 | button_idx = 1 - button_idx; | ||
133 | if(button_val[0] == button_val[1]) | ||
134 | button_mask = button_val[0]; | ||
135 | } | ||
106 | } | 136 | } |
107 | 137 | ||
108 | void imx233_button_lradc_init(void) | 138 | void imx233_button_lradc_init(void) |
@@ -118,9 +148,19 @@ void imx233_button_lradc_init(void) | |||
118 | if(button_delay < 0) | 148 | if(button_delay < 0) |
119 | panicf("Cannot get delay for button-lradc"); | 149 | panicf("Cannot get delay for button-lradc"); |
120 | imx233_lradc_setup_channel(button_chan, true, true, SAMPLES - 1, LRADC_SRC(CHAN)); | 150 | imx233_lradc_setup_channel(button_chan, true, true, SAMPLES - 1, LRADC_SRC(CHAN)); |
121 | imx233_lradc_setup_delay(button_delay, 1 << button_chan, 0, SAMPLES - 1, DELAY); | ||
122 | imx233_lradc_enable_channel_irq(button_chan, true); | 151 | imx233_lradc_enable_channel_irq(button_chan, true); |
123 | imx233_lradc_set_channel_irq_callback(button_chan, button_lradc_irq); | 152 | imx233_lradc_set_channel_irq_callback(button_chan, button_lradc_irq); |
153 | delay_chan_mask = 1 << button_chan; | ||
154 | #ifdef HAS_VDDIO | ||
155 | vddio_chan = imx233_lradc_acquire_channel(LRADC_SRC_VDDIO, TIMEOUT_NOBLOCK); | ||
156 | if(vddio_chan < 0) | ||
157 | panicf("Cannot get vddio channel for button-lradc"); | ||
158 | imx233_lradc_setup_channel(vddio_chan, true, true, SAMPLES - 1, LRADC_SRC_VDDIO); | ||
159 | imx233_lradc_enable_channel_irq(vddio_chan, true); | ||
160 | imx233_lradc_set_channel_irq_callback(vddio_chan, button_lradc_irq); | ||
161 | delay_chan_mask |= 1 << vddio_chan; | ||
162 | #endif | ||
163 | imx233_lradc_setup_delay(button_delay, delay_chan_mask, 0, SAMPLES - 1, DELAY); | ||
124 | imx233_lradc_kick_delay(button_delay); | 164 | imx233_lradc_kick_delay(button_delay); |
125 | #if defined(HAS_BUTTON_HOLD) && IMX233_BUTTON_LRADC_HOLD_DET == BLH_GPIO | 165 | #if defined(HAS_BUTTON_HOLD) && IMX233_BUTTON_LRADC_HOLD_DET == BLH_GPIO |
126 | imx233_pinctrl_acquire(BLH_GPIO_BANK, BLH_GPIO_PIN, "button_lradc_hold"); | 166 | imx233_pinctrl_acquire(BLH_GPIO_BANK, BLH_GPIO_PIN, "button_lradc_hold"); |
@@ -164,3 +204,10 @@ int imx233_button_lradc_read_raw(void) | |||
164 | { | 204 | { |
165 | return raw_val; | 205 | return raw_val; |
166 | } | 206 | } |
207 | |||
208 | #ifdef HAS_VDDIO | ||
209 | int imx233_button_lradc_read_vddio(void) | ||
210 | { | ||
211 | return vddio_val; // the VDDIO channel has an internal divider | ||
212 | } | ||
213 | #endif | ||
diff --git a/firmware/target/arm/imx233/button-lradc-imx233.h b/firmware/target/arm/imx233/button-lradc-imx233.h index eac5517adf..d96823fcdc 100644 --- a/firmware/target/arm/imx233/button-lradc-imx233.h +++ b/firmware/target/arm/imx233/button-lradc-imx233.h | |||
@@ -30,7 +30,19 @@ | |||
30 | * - imx233_button_lradc_mapping: target-defined table of adc values and mapping | 30 | * - imx233_button_lradc_mapping: target-defined table of adc values and mapping |
31 | * - IMX233_BUTTON_LRADC_CHANNEL: lradc channel to use | 31 | * - IMX233_BUTTON_LRADC_CHANNEL: lradc channel to use |
32 | * - IMX233_BUTTON_LRADC_HOLD_DET: define hold detection method (ignored if !HAS_BUTTON_HOLD) | 32 | * - IMX233_BUTTON_LRADC_HOLD_DET: define hold detection method (ignored if !HAS_BUTTON_HOLD) |
33 | * - IMX233_BUTTON_LRADC_MODE: define the button lradc mode | ||
33 | * | 34 | * |
35 | * The LRADC code supports two modes of operations: VDDIO relative or absolute. | ||
36 | * In the (default) absolute value mode, the LRADC channel is sampled and its value | ||
37 | * is compared to the one in the imx233_button_lradc_mapping table. This is | ||
38 | * appropriate when the resistor ladder is derived from a fixed voltage. | ||
39 | * In the VDDIO relative mode, the values in imx233_button_lradc_mapping are | ||
40 | * the values for a specific value of VDDIO which is given by | ||
41 | * IMX233_BUTTON_LRADC_VDDIO. In this mode, the code will also sample VDDIO | ||
42 | * and do the following comparison: | ||
43 | * lradc_value <=? imx233_button_lradc_mapping[i] * vddio_ref / vddio_value | ||
44 | * where vddio_ref is IMX233_BUTTON_LRADC_VDDIO. | ||
45 | * | ||
34 | * The available values of IMX233_BUTTON_LRADC_HOLD are: | 46 | * The available values of IMX233_BUTTON_LRADC_HOLD are: |
35 | * - BLH_ADC: detect hold using adc | 47 | * - BLH_ADC: detect hold using adc |
36 | * - BLH_EXT: target button driver implements imx233_button_lradc_hold() using | 48 | * - BLH_EXT: target button driver implements imx233_button_lradc_hold() using |
@@ -40,6 +52,10 @@ | |||
40 | * + BLH_GPIO_PIN: pin in bank | 52 | * + BLH_GPIO_PIN: pin in bank |
41 | * + BLH_GPIO_INVERTED: define if inverted, default is active high | 53 | * + BLH_GPIO_INVERTED: define if inverted, default is active high |
42 | * + BLH_GPIO_PULLUP: define if pins needs pullup | 54 | * + BLH_GPIO_PULLUP: define if pins needs pullup |
55 | * | ||
56 | * WARNING | ||
57 | * There must always be entry in imx233_button_lradc_mapping whose value is the steady | ||
58 | * value of the channel when no button is pressed, and which maps to no button (.btn = 0) | ||
43 | */ | 59 | */ |
44 | 60 | ||
45 | /* hold detect method */ | 61 | /* hold detect method */ |
@@ -74,5 +90,8 @@ int imx233_button_lradc_read(int others); | |||
74 | bool imx233_button_lradc_hold(void); | 90 | bool imx233_button_lradc_hold(void); |
75 | #endif | 91 | #endif |
76 | int imx233_button_lradc_read_raw(void); // return raw adc value | 92 | int imx233_button_lradc_read_raw(void); // return raw adc value |
93 | #ifdef IMX233_BUTTON_LRADC_VDDIO | ||
94 | int imx233_button_lradc_read_vddio(void); | ||
95 | #endif | ||
77 | 96 | ||
78 | #endif /* __button_lradc_imx233__ */ | 97 | #endif /* __button_lradc_imx233__ */ |
diff --git a/firmware/target/arm/imx233/creative-zen/button-target.h b/firmware/target/arm/imx233/creative-zen/button-target.h index 65521d66e4..e9a3ac5ab7 100644 --- a/firmware/target/arm/imx233/creative-zen/button-target.h +++ b/firmware/target/arm/imx233/creative-zen/button-target.h | |||
@@ -25,11 +25,22 @@ | |||
25 | 25 | ||
26 | bool button_debug_screen(void); | 26 | bool button_debug_screen(void); |
27 | 27 | ||
28 | /* HOLD button */ | ||
28 | #if !defined(CREATIVE_ZENXFISTYLE) | 29 | #if !defined(CREATIVE_ZENXFISTYLE) |
29 | #define HAS_BUTTON_HOLD | 30 | #define HAS_BUTTON_HOLD |
30 | #define IMX233_BUTTON_LRADC_HOLD_DET BLH_ADC | 31 | #define IMX233_BUTTON_LRADC_HOLD_DET BLH_ADC |
31 | #endif | 32 | #endif |
32 | 33 | ||
34 | /* VDDIO value */ | ||
35 | #if defined(CREATIVE_ZENXFISTYLE) | ||
36 | #define IMX233_BUTTON_LRADC_VDDIO 3660 | ||
37 | #elif defined(CREATIVE_ZEN) | ||
38 | #define IMX233_BUTTON_LRADC_VDDIO 3480 | ||
39 | #elif defined(CREATIVE_ZENXFI) | ||
40 | #define IMX233_BUTTON_LRADC_VDDIO 3500 | ||
41 | #endif | ||
42 | |||
43 | /* LRADC channel */ | ||
33 | #if defined(CREATIVE_ZENXFISTYLE) | 44 | #if defined(CREATIVE_ZENXFISTYLE) |
34 | #define IMX233_BUTTON_LRADC_CHANNEL 2 | 45 | #define IMX233_BUTTON_LRADC_CHANNEL 2 |
35 | #else | 46 | #else |
diff --git a/firmware/target/arm/imx233/lradc-imx233.h b/firmware/target/arm/imx233/lradc-imx233.h index f274db3520..e7853b97a5 100644 --- a/firmware/target/arm/imx233/lradc-imx233.h +++ b/firmware/target/arm/imx233/lradc-imx233.h | |||
@@ -65,6 +65,9 @@ | |||
65 | /* frequency of the delay counter */ | 65 | /* frequency of the delay counter */ |
66 | #define LRADC_DELAY_FREQ 2000 | 66 | #define LRADC_DELAY_FREQ 2000 |
67 | 67 | ||
68 | /* maximum value of a sample (without accumulation), defines the precision */ | ||
69 | #define LRADC_MAX_VALUE 4096 | ||
70 | |||
68 | typedef void (*lradc_irq_fn_t)(int chan); | 71 | typedef void (*lradc_irq_fn_t)(int chan); |
69 | 72 | ||
70 | void imx233_lradc_init(void); | 73 | void imx233_lradc_init(void); |