diff options
Diffstat (limited to 'firmware/target/arm/tcc780x')
-rw-r--r-- | firmware/target/arm/tcc780x/sd-tcc780x.c | 129 |
1 files changed, 35 insertions, 94 deletions
diff --git a/firmware/target/arm/tcc780x/sd-tcc780x.c b/firmware/target/arm/tcc780x/sd-tcc780x.c index ba98539157..c80c3b746f 100644 --- a/firmware/target/arm/tcc780x/sd-tcc780x.c +++ b/firmware/target/arm/tcc780x/sd-tcc780x.c | |||
@@ -19,17 +19,13 @@ | |||
19 | * KIND, either express or implied. | 19 | * KIND, either express or implied. |
20 | * | 20 | * |
21 | ****************************************************************************/ | 21 | ****************************************************************************/ |
22 | #include "sd.h" | 22 | #include "config.h" |
23 | #include "system.h" | 23 | #include "system.h" |
24 | #include <string.h> | 24 | #include <string.h> |
25 | #include "gcc_extensions.h" | 25 | #include "gcc_extensions.h" |
26 | #include "sdmmc.h" | 26 | #include "sdmmc.h" |
27 | #include "storage.h" | 27 | #include "storage.h" |
28 | #include "led.h" | 28 | #include "led.h" |
29 | #include "thread.h" | ||
30 | #include "disk.h" | ||
31 | #include "ata_idle_notify.h" | ||
32 | #include "usb.h" | ||
33 | 29 | ||
34 | #if defined(HAVE_INTERNAL_SD) && defined(HAVE_HOTSWAP) | 30 | #if defined(HAVE_INTERNAL_SD) && defined(HAVE_HOTSWAP) |
35 | #define CARD_NUM_INTERNAL 0 | 31 | #define CARD_NUM_INTERNAL 0 |
@@ -55,9 +51,6 @@ | |||
55 | /* for compatibility */ | 51 | /* for compatibility */ |
56 | static long last_disk_activity = -1; | 52 | static long last_disk_activity = -1; |
57 | 53 | ||
58 | /** static, private data **/ | ||
59 | static bool initialized = false; | ||
60 | |||
61 | static long next_yield = 0; | 54 | static long next_yield = 0; |
62 | #define MIN_YIELD_PERIOD 1000 | 55 | #define MIN_YIELD_PERIOD 1000 |
63 | 56 | ||
@@ -80,14 +73,13 @@ static struct sd_card_status sd_status[NUM_DRIVES] = | |||
80 | #endif | 73 | #endif |
81 | }; | 74 | }; |
82 | 75 | ||
83 | /* Shoot for around 75% usage */ | ||
84 | static long sd_stack [(DEFAULT_STACK_SIZE*2 + 0x1c0)/sizeof(long)]; | ||
85 | static const char sd_thread_name[] = "sd"; | ||
86 | static struct mutex sd_mtx SHAREDBSS_ATTR; | 76 | static struct mutex sd_mtx SHAREDBSS_ATTR; |
87 | static struct event_queue sd_queue; | ||
88 | 77 | ||
78 | #ifdef CONFIG_STORAGE_MULTI | ||
89 | static int sd_first_drive = 0; | 79 | static int sd_first_drive = 0; |
90 | 80 | #else | |
81 | #define sd_first_drive 0 | ||
82 | #endif | ||
91 | 83 | ||
92 | static bool sd_poll_status(unsigned int trigger, long timeout) | 84 | static bool sd_poll_status(unsigned int trigger, long timeout) |
93 | { | 85 | { |
@@ -216,16 +208,13 @@ static inline bool card_detect_target(void) | |||
216 | 208 | ||
217 | static int sd1_oneshot_callback(struct timeout *tmo) | 209 | static int sd1_oneshot_callback(struct timeout *tmo) |
218 | { | 210 | { |
219 | (void)tmo; | ||
220 | |||
221 | /* This is called only if the state was stable for 300ms - check state | 211 | /* This is called only if the state was stable for 300ms - check state |
222 | * and post appropriate event. */ | 212 | * and post appropriate event. */ |
223 | if (card_detect_target()) | 213 | queue_broadcast(card_detect_target() ? SYS_HOTSWAP_INSERTED : |
224 | queue_broadcast(SYS_HOTSWAP_INSERTED, 0); | 214 | SYS_HOTSWAP_EXTRACTED, |
225 | else | 215 | sd_first_drive + CARD_NUM_SLOT); |
226 | queue_broadcast(SYS_HOTSWAP_EXTRACTED, 0); | ||
227 | |||
228 | return 0; | 216 | return 0; |
217 | (void)tmo; | ||
229 | } | 218 | } |
230 | 219 | ||
231 | void EXT0(void) | 220 | void EXT0(void) |
@@ -642,71 +631,6 @@ sd_write_error: | |||
642 | } | 631 | } |
643 | } | 632 | } |
644 | 633 | ||
645 | static void sd_thread(void) NORETURN_ATTR; | ||
646 | static void sd_thread(void) | ||
647 | { | ||
648 | struct queue_event ev; | ||
649 | bool idle_notified = false; | ||
650 | |||
651 | while (1) | ||
652 | { | ||
653 | queue_wait_w_tmo(&sd_queue, &ev, HZ); | ||
654 | |||
655 | switch ( ev.id ) | ||
656 | { | ||
657 | #ifdef HAVE_HOTSWAP | ||
658 | case SYS_HOTSWAP_INSERTED: | ||
659 | case SYS_HOTSWAP_EXTRACTED:; | ||
660 | int success = 1; | ||
661 | |||
662 | /* Release "by force" */ | ||
663 | disk_unmount(sd_first_drive + CARD_NUM_SLOT); | ||
664 | |||
665 | mutex_lock(&sd_mtx); /* lock-out card activity */ | ||
666 | |||
667 | /* Force card init for new card, re-init for re-inserted one or | ||
668 | * clear if the last attempt to init failed with an error. */ | ||
669 | card_info[CARD_NUM_SLOT].initialized = 0; | ||
670 | sd_status[CARD_NUM_SLOT].retry = 0; | ||
671 | |||
672 | mutex_unlock(&sd_mtx); | ||
673 | |||
674 | if (ev.id == SYS_HOTSWAP_INSERTED) | ||
675 | success = disk_mount(sd_first_drive + CARD_NUM_SLOT); | ||
676 | |||
677 | if (success) | ||
678 | queue_broadcast(SYS_FS_CHANGED, 0); | ||
679 | |||
680 | break; | ||
681 | #endif /* HAVE_HOTSWAP */ | ||
682 | |||
683 | case SYS_TIMEOUT: | ||
684 | if (TIME_BEFORE(current_tick, last_disk_activity+(3*HZ))) | ||
685 | { | ||
686 | idle_notified = false; | ||
687 | } | ||
688 | else | ||
689 | { | ||
690 | /* never let a timer wrap confuse us */ | ||
691 | next_yield = USEC_TIMER; | ||
692 | |||
693 | if (!idle_notified) | ||
694 | { | ||
695 | call_storage_idle_notifys(false); | ||
696 | idle_notified = true; | ||
697 | } | ||
698 | } | ||
699 | break; | ||
700 | |||
701 | case SYS_USB_CONNECTED: | ||
702 | usb_acknowledge(SYS_USB_CONNECTED_ACK); | ||
703 | /* Wait until the USB cable is extracted again */ | ||
704 | usb_wait_for_disconnect(&sd_queue); | ||
705 | break; | ||
706 | } | ||
707 | } | ||
708 | } | ||
709 | |||
710 | void sd_enable(bool on) | 634 | void sd_enable(bool on) |
711 | { | 635 | { |
712 | if(on) | 636 | if(on) |
@@ -725,6 +649,7 @@ void sd_enable(bool on) | |||
725 | 649 | ||
726 | int sd_init(void) | 650 | int sd_init(void) |
727 | { | 651 | { |
652 | static bool initialized = false; | ||
728 | int ret = 0; | 653 | int ret = 0; |
729 | 654 | ||
730 | if (!initialized) | 655 | if (!initialized) |
@@ -752,11 +677,6 @@ int sd_init(void) | |||
752 | /* Configure card power(?) GPIO as output */ | 677 | /* Configure card power(?) GPIO as output */ |
753 | GPIOC_DIR |= (1<<24); | 678 | GPIOC_DIR |= (1<<24); |
754 | 679 | ||
755 | queue_init(&sd_queue, true); | ||
756 | create_thread(sd_thread, sd_stack, sizeof(sd_stack), 0, | ||
757 | sd_thread_name IF_PRIO(, PRIORITY_USER_INTERFACE) | ||
758 | IF_COP(, CPU)); | ||
759 | |||
760 | sleep(HZ/10); | 680 | sleep(HZ/10); |
761 | 681 | ||
762 | #ifdef HAVE_HOTSWAP | 682 | #ifdef HAVE_HOTSWAP |
@@ -794,10 +714,6 @@ int sd_num_drives(int first_drive) | |||
794 | #endif | 714 | #endif |
795 | } | 715 | } |
796 | 716 | ||
797 | void sd_sleepnow(void) | ||
798 | { | ||
799 | } | ||
800 | |||
801 | bool sd_disk_is_active(void) | 717 | bool sd_disk_is_active(void) |
802 | { | 718 | { |
803 | return false; | 719 | return false; |
@@ -814,3 +730,28 @@ int sd_spinup_time(void) | |||
814 | } | 730 | } |
815 | 731 | ||
816 | #endif /* CONFIG_STORAGE_MULTI */ | 732 | #endif /* CONFIG_STORAGE_MULTI */ |
733 | |||
734 | int sd_event(long id, intptr_t data) | ||
735 | { | ||
736 | int rc = 0; | ||
737 | |||
738 | switch (id) | ||
739 | { | ||
740 | #ifdef HAVE_HOTSWAP | ||
741 | case SYS_HOTSWAP_INSERTED: | ||
742 | case SYS_HOTSWAP_EXTRACTED: | ||
743 | mutex_lock(&sd_mtx); | ||
744 | /* Force card init for new card, re-init for re-inserted one or | ||
745 | * clear if the last attempt to init failed with an error. */ | ||
746 | card_info[data].initialized = 0; | ||
747 | sd_status[data].retry = 0; | ||
748 | mutex_unlock(&sd_mtx); | ||
749 | break; | ||
750 | #endif /* HAVE_HOTSWAP */ | ||
751 | default: | ||
752 | rc = storage_event_default_handler(id, data, last_disk_activity, STORAGE_SD); | ||
753 | break; | ||
754 | } | ||
755 | |||
756 | return rc; | ||
757 | } | ||