diff options
author | Cástor Muñoz <cmvidal@gmail.com> | 2015-12-17 00:22:41 +0100 |
---|---|---|
committer | Cástor Muñoz <cmvidal@gmail.com> | 2015-12-17 10:26:51 +0100 |
commit | 348bfc5c8f6633d40d3708e826aa7e9b0360729f (patch) | |
tree | 0202c2b9cbafd8ed322d8d4f18599c38609466e3 | |
parent | ead38dbc9df3f63bd4f870ff2365ba48876d5b46 (diff) | |
download | rockbox-348bfc5c8f6633d40d3708e826aa7e9b0360729f.tar.gz rockbox-348bfc5c8f6633d40d3708e826aa7e9b0360729f.zip |
iPod Classic: clickwheel fixes
Uses GPIO.E2 (Request To Send) to detect the holdswitch status,
it is a temporal workaround that seems to work on all models.
Holdswitch status must be detected to drive low GPIO.E2 (RTS)
and GPIO.E4 (Data Out) when the holdswitch is locked, otherwise
battery life decreases about 25%.
Holdswitch unlock action is detected by reading the HELLO message
that the external wheel controller sends when it is powered on,
this allows to quickly capture clickwheel activity after unlock.
GPIO.E2 is also used in case the HELLO message is missed because
the holdswitch was unlocked before Rockbox/bootloader starts.
These 2 lines (RTS and DOUT) can not be used to transmit messages
to the external clickwheel controller, not a problem, actually no
messages are sent while normal operation, only at initialization
stage.
Change-Id: I415fe54bfcbc2086d0f56d7affe6f789ce81a6db
-rw-r--r-- | firmware/target/arm/ipod/button-clickwheel.c | 33 |
1 files changed, 19 insertions, 14 deletions
diff --git a/firmware/target/arm/ipod/button-clickwheel.c b/firmware/target/arm/ipod/button-clickwheel.c index 3af50b5112..5f138aaf1b 100644 --- a/firmware/target/arm/ipod/button-clickwheel.c +++ b/firmware/target/arm/ipod/button-clickwheel.c | |||
@@ -271,6 +271,12 @@ static inline int ipod_4g_button_read(void) | |||
271 | semaphore_release(&button_init_wakeup); | 271 | semaphore_release(&button_init_wakeup); |
272 | } | 272 | } |
273 | #endif | 273 | #endif |
274 | #if CONFIG_CPU==S5L8702 | ||
275 | else if (status == 0xAAAAAAAA) | ||
276 | { | ||
277 | GPIOCMD = 0xe040f; /* DOUT = Output High */ | ||
278 | } | ||
279 | #endif | ||
274 | 280 | ||
275 | #ifdef CPU_PP | 281 | #ifdef CPU_PP |
276 | } | 282 | } |
@@ -362,9 +368,11 @@ static void s5l_clickwheel_init(void) | |||
362 | WHEEL04 |= 1; | 368 | WHEEL04 |= 1; |
363 | PDAT10 &= ~2; | 369 | PDAT10 &= ~2; |
364 | #elif CONFIG_CPU==S5L8702 | 370 | #elif CONFIG_CPU==S5L8702 |
365 | /* enable and init internal (s5l8702) wheel controller */ | 371 | PWRCON(1) &= ~(1 << 1); /* unmask clockgate */ |
366 | PWRCON(1) &= ~(1 << 1); | 372 | WHEEL00 = 0; /* stop s5l8702 controller */ |
367 | PCON(14) = (PCON(14) & ~0xffff0000) | 0x22220000; | 373 | PUNB(14) &= ~(1 << 2); /* disable pull-up for GPIO E2 */ |
374 | udelay(100); | ||
375 | PCON(14) = (PCON(14) & ~0x00ffff00) | 0x00222200; | ||
368 | WHEELINT = 7; | 376 | WHEELINT = 7; |
369 | WHEEL10 = 1; | 377 | WHEEL10 = 1; |
370 | WHEEL00 = 0x380000; | 378 | WHEEL00 = 0x380000; |
@@ -379,12 +387,15 @@ void button_init_device(void) | |||
379 | semaphore_init(&button_init_wakeup, 1, 0); | 387 | semaphore_init(&button_init_wakeup, 1, 0); |
380 | #if CONFIG_CPU==S5L8701 | 388 | #if CONFIG_CPU==S5L8701 |
381 | INTMSK |= (1<<26); | 389 | INTMSK |= (1<<26); |
382 | #elif CONFIG_CPU==S5L8702 | ||
383 | /* configure GPIO E2 as pull-up input */ | ||
384 | PUNB(14) |= (1 << 2); | ||
385 | #endif | 390 | #endif |
386 | s5l_clickwheel_init(); | 391 | s5l_clickwheel_init(); |
387 | semaphore_wait(&button_init_wakeup, HZ / 10); | 392 | semaphore_wait(&button_init_wakeup, HZ / 10); |
393 | #if CONFIG_CPU==S5L8702 | ||
394 | /* configure GPIO E2 as pull-up input */ | ||
395 | PUNB(14) |= (1 << 2); | ||
396 | udelay(100); | ||
397 | GPIOCMD = 0xe0200; | ||
398 | #endif | ||
388 | } | 399 | } |
389 | 400 | ||
390 | bool button_hold(void) | 401 | bool button_hold(void) |
@@ -439,13 +450,7 @@ int button_read_device(void) | |||
439 | WHEEL10 = 0; | 450 | WHEEL10 = 0; |
440 | PWRCONEXT |= 1; | 451 | PWRCONEXT |= 1; |
441 | #elif CONFIG_CPU==S5L8702 | 452 | #elif CONFIG_CPU==S5L8702 |
442 | /* disable external (CY8C21x34) wheel controller */ | 453 | GPIOCMD = 0xe040e; /* DOUT = Output Low */ |
443 | GPIOCMD = 0xe040e; | ||
444 | |||
445 | /* disable internal (s5l8702) wheel controller */ | ||
446 | WHEEL00 = 0; | ||
447 | WHEEL10 = 0; | ||
448 | PWRCON(1) |= (1 << 1); | ||
449 | #endif | 454 | #endif |
450 | } | 455 | } |
451 | else | 456 | else |
@@ -458,7 +463,7 @@ int button_read_device(void) | |||
458 | pmu_ldo_power_on(1); /* enable clickwheel power supply */ | 463 | pmu_ldo_power_on(1); /* enable clickwheel power supply */ |
459 | s5l_clickwheel_init(); | 464 | s5l_clickwheel_init(); |
460 | #elif CONFIG_CPU==S5L8702 | 465 | #elif CONFIG_CPU==S5L8702 |
461 | s5l_clickwheel_init(); | 466 | GPIOCMD = 0xe040f; /* DOUT = Output High */ |
462 | #endif | 467 | #endif |
463 | } | 468 | } |
464 | } | 469 | } |