From 6a8379674c43103c008f841968b84287b8fdaf89 Mon Sep 17 00:00:00 2001 From: Michael Sevakis Date: Fri, 18 Jan 2008 13:12:33 +0000 Subject: Finally, out goes struct spinlock for anything but mutiprocessor targets where it becomes a reenterable corelock. git-svn-id: svn://svn.rockbox.org/rockbox/trunk@16105 a1c6a512-1295-4272-9138-f99709370657 --- firmware/drivers/ata.c | 60 +++++++++++++-------------- firmware/export/kernel.h | 15 +++---- firmware/kernel.c | 45 +++----------------- firmware/system.c | 2 +- firmware/target/arm/ipod/1g2g/adc-ipod-1g2g.c | 8 ++-- firmware/target/arm/sandisk/ata-c200_e200.c | 20 ++++----- firmware/target/arm/tms320dm320/spi-dm320.c | 8 ++-- uisimulator/sdl/kernel.c | 48 +-------------------- 8 files changed, 61 insertions(+), 145 deletions(-) diff --git a/firmware/drivers/ata.c b/firmware/drivers/ata.c index 1b917686c5..cacf4583ae 100644 --- a/firmware/drivers/ata.c +++ b/firmware/drivers/ata.c @@ -66,7 +66,7 @@ #define ATA_POWER_OFF_TIMEOUT 2*HZ #endif -static struct spinlock ata_spinlock NOCACHEBSS_ATTR; +static struct mutex ata_mtx NOCACHEBSS_ATTR; int ata_device; /* device 0 (master) or 1 (slave) */ int ata_spinup_time = 0; @@ -234,7 +234,7 @@ int ata_read_sectors(IF_MV2(int drive,) #ifdef HAVE_MULTIVOLUME (void)drive; /* unused for now */ #endif - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); #endif last_disk_activity = current_tick; @@ -246,14 +246,14 @@ int ata_read_sectors(IF_MV2(int drive,) spinup = true; if (poweroff) { if (ata_power_on()) { - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); ata_led(false); return -1; } } else { if (perform_soft_reset()) { - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); ata_led(false); return -1; } @@ -265,7 +265,7 @@ int ata_read_sectors(IF_MV2(int drive,) SET_REG(ATA_SELECT, ata_device); if (!wait_for_rdy()) { - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); ata_led(false); return -2; } @@ -376,7 +376,7 @@ int ata_read_sectors(IF_MV2(int drive,) ata_led(false); #ifndef MAX_PHYS_SECTOR_SIZE - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); #endif return ret; @@ -442,7 +442,7 @@ int ata_write_sectors(IF_MV2(int drive,) #ifdef HAVE_MULTIVOLUME (void)drive; /* unused for now */ #endif - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); #endif last_disk_activity = current_tick; @@ -454,14 +454,14 @@ int ata_write_sectors(IF_MV2(int drive,) spinup = true; if (poweroff) { if (ata_power_on()) { - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); ata_led(false); return -1; } } else { if (perform_soft_reset()) { - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); ata_led(false); return -1; } @@ -471,7 +471,7 @@ int ata_write_sectors(IF_MV2(int drive,) SET_REG(ATA_SELECT, ata_device); if (!wait_for_rdy()) { - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); ata_led(false); return -2; } @@ -534,7 +534,7 @@ int ata_write_sectors(IF_MV2(int drive,) ata_led(false); #ifndef MAX_PHYS_SECTOR_SIZE - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); #endif return ret; @@ -580,7 +580,7 @@ int ata_read_sectors(IF_MV2(int drive,) #ifdef HAVE_MULTIVOLUME (void)drive; /* unused for now */ #endif - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); offset = start & (phys_sector_mult - 1); @@ -630,7 +630,7 @@ int ata_read_sectors(IF_MV2(int drive,) } error: - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); return rc; } @@ -646,7 +646,7 @@ int ata_write_sectors(IF_MV2(int drive,) #ifdef HAVE_MULTIVOLUME (void)drive; /* unused for now */ #endif - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); offset = start & (phys_sector_mult - 1); @@ -707,7 +707,7 @@ int ata_write_sectors(IF_MV2(int drive,) } error: - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); return rc; } @@ -767,13 +767,13 @@ static int ata_perform_sleep(void) { int ret = 0; - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); SET_REG(ATA_SELECT, ata_device); if(!wait_for_rdy()) { DEBUGF("ata_perform_sleep() - not RDY\n"); - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); return -1; } @@ -786,7 +786,7 @@ static int ata_perform_sleep(void) } sleeping = true; - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); return ret; } @@ -797,7 +797,7 @@ void ata_sleep(void) void ata_sleepnow(void) { - if (!spinup && !sleeping && !ata_spinlock.locked && initialized) + if (!spinup && !sleeping && !ata_mtx.locked && initialized) { call_ata_idle_notifys(false); ata_perform_sleep(); @@ -819,7 +819,7 @@ static void ata_thread(void) while ( queue_empty( &ata_queue ) ) { if (!spinup && !sleeping) { - if (!ata_spinlock.locked) + if (!ata_mtx.locked) { if (!last_seen_mtx_unlock) last_seen_mtx_unlock = current_tick; @@ -844,9 +844,9 @@ static void ata_thread(void) if ( !spinup && sleeping && !poweroff && TIME_AFTER( current_tick, last_sleep + ATA_POWER_OFF_TIMEOUT )) { - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); ide_power_enable(false); - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); poweroff = true; } #endif @@ -858,11 +858,11 @@ static void ata_thread(void) #ifndef USB_NONE case SYS_USB_CONNECTED: if (poweroff) { - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); ata_led(true); ata_power_on(); ata_led(false); - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); } /* Tell the USB thread that we are safe */ @@ -936,11 +936,11 @@ int ata_soft_reset(void) { int ret; - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); ret = perform_soft_reset(); - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); return ret; } @@ -1132,11 +1132,11 @@ int ata_init(void) bool coldstart; if ( !initialized ) { - spinlock_init(&ata_spinlock IF_COP(, SPINLOCK_TASK_SWITCH)); + mutex_init(&ata_mtx); queue_init(&ata_queue, true); } - spinlock_lock(&ata_spinlock); + mutex_lock(&ata_mtx); /* must be called before ata_device_init() */ coldstart = ata_is_coldstart(); @@ -1150,7 +1150,7 @@ int ata_init(void) if ( !initialized ) { /* First call won't have multiple thread contention */ - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); if (!ide_powered()) /* somebody has switched it off */ { @@ -1223,7 +1223,7 @@ int ata_init(void) if (rc) rc = -70 + rc; - spinlock_unlock(&ata_spinlock); + mutex_unlock(&ata_mtx); return rc; } diff --git a/firmware/export/kernel.h b/firmware/export/kernel.h index 96a7752017..be5041f6c2 100644 --- a/firmware/export/kernel.h +++ b/firmware/export/kernel.h @@ -119,18 +119,14 @@ struct mutex unsigned char locked; /* locked semaphore */ }; +#if NUM_CORES > 1 struct spinlock { -#if NUM_CORES > 1 struct corelock cl; /* inter-core sync */ -#endif struct thread_entry *thread; /* lock owner */ int count; /* lock owner recursion count */ - unsigned char locked; /* is locked if nonzero */ -#if NUM_CORES > 1 - unsigned char task_switch; /* can task switch? */ -#endif }; +#endif #ifdef HAVE_SEMAPHORE_OBJECTS struct semaphore @@ -229,12 +225,11 @@ extern int queue_broadcast(long id, intptr_t data); extern void mutex_init(struct mutex *m); extern void mutex_lock(struct mutex *m); extern void mutex_unlock(struct mutex *m); -#define SPINLOCK_TASK_SWITCH 0x10 -#define SPINLOCK_NO_TASK_SWITCH 0x00 -extern void spinlock_init(struct spinlock *l IF_COP(, unsigned int flags)); +#if NUM_CORES > 1 +extern void spinlock_init(struct spinlock *l); extern void spinlock_lock(struct spinlock *l); extern void spinlock_unlock(struct spinlock *l); -extern int spinlock_lock_w_tmo(struct spinlock *l, int ticks); +#endif #ifdef HAVE_SEMAPHORE_OBJECTS extern void semaphore_init(struct semaphore *s, int max, int start); extern void semaphore_wait(struct semaphore *s); diff --git a/firmware/kernel.c b/firmware/kernel.c index 803c224640..204f3e8141 100644 --- a/firmware/kernel.c +++ b/firmware/kernel.c @@ -1127,15 +1127,12 @@ void mutex_unlock(struct mutex *m) /**************************************************************************** * Simpl-er mutex functions ;) ****************************************************************************/ -void spinlock_init(struct spinlock *l IF_COP(, unsigned int flags)) +#if NUM_CORES > 1 +void spinlock_init(struct spinlock *l) { - l->locked = 0; + corelock_init(&l->cl); l->thread = NULL; l->count = 0; -#if NUM_CORES > 1 - l->task_switch = flags & SPINLOCK_TASK_SWITCH; - corelock_init(&l->cl); -#endif } void spinlock_lock(struct spinlock *l) @@ -1148,24 +1145,7 @@ void spinlock_lock(struct spinlock *l) return; } -#if NUM_CORES > 1 - if (l->task_switch != 0) -#endif - { - /* Let other threads run until the lock is free */ - while(test_and_set(&l->locked, 1, &l->cl) != 0) - { - /* spin and switch until the lock is open... */ - switch_thread(NULL); - } - } -#if NUM_CORES > 1 - else - { - /* Use the corelock purely */ - corelock_lock(&l->cl); - } -#endif + corelock_lock(&l->cl); l->thread = thread; } @@ -1186,23 +1166,10 @@ void spinlock_unlock(struct spinlock *l) /* clear owner */ l->thread = NULL; -#if NUM_CORES > 1 - if (l->task_switch != 0) -#endif - { - /* release lock */ -#if CONFIG_CORELOCK == SW_CORELOCK - /* This must be done since our unlock could be missed by the - test_and_set and leave the object locked permanently */ - corelock_lock(&l->cl); -#endif - l->locked = 0; - } - -#if NUM_CORES > 1 + /* release lock */ corelock_unlock(&l->cl); -#endif } +#endif /* NUM_CORES > 1 */ /**************************************************************************** * Simple semaphore functions ;) diff --git a/firmware/system.c b/firmware/system.c index c186163cf6..2ba31f254f 100644 --- a/firmware/system.c +++ b/firmware/system.c @@ -39,7 +39,7 @@ static bool cpu_idle NOCACHEBSS_ATTR = false; struct spinlock boostctrl_spin NOCACHEBSS_ATTR; void cpu_boost_init(void) { - spinlock_init(&boostctrl_spin, SPINLOCK_NO_TASK_SWITCH); + spinlock_init(&boostctrl_spin); } #endif diff --git a/firmware/target/arm/ipod/1g2g/adc-ipod-1g2g.c b/firmware/target/arm/ipod/1g2g/adc-ipod-1g2g.c index 3a854afcdc..f80412023d 100644 --- a/firmware/target/arm/ipod/1g2g/adc-ipod-1g2g.c +++ b/firmware/target/arm/ipod/1g2g/adc-ipod-1g2g.c @@ -22,7 +22,7 @@ #include "hwcompat.h" #include "kernel.h" -static struct spinlock adc_spin NOCACHEBSS_ATTR; +static struct mutex adc_mtx NOCACHEBSS_ATTR; /* used in the 2nd gen ADC interrupt */ static unsigned int_data; @@ -33,7 +33,7 @@ unsigned short adc_scan(int channel) unsigned short data = 0; (void)channel; /* there is only one */ - spinlock_lock(&adc_spin); + mutex_lock(&adc_mtx); if ((IPOD_HW_REVISION >> 16) == 1) { @@ -69,7 +69,7 @@ unsigned short adc_scan(int channel) data = int_data & 0xff; } - spinlock_unlock(&adc_spin); + mutex_unlock(&adc_mtx); return data; } @@ -100,7 +100,7 @@ void ipod_2g_adc_int(void) void adc_init(void) { - spinlock_init(&adc_spin IF_COP(, SPINLOCK_TASK_SWITCH)); + mutex_init(&adc_mtx); GPIOB_ENABLE |= 0x1e; /* enable B1..B4 */ diff --git a/firmware/target/arm/sandisk/ata-c200_e200.c b/firmware/target/arm/sandisk/ata-c200_e200.c index ef2bad387b..9a5301884f 100644 --- a/firmware/target/arm/sandisk/ata-c200_e200.c +++ b/firmware/target/arm/sandisk/ata-c200_e200.c @@ -162,7 +162,7 @@ static struct sd_card_status sd_status[NUM_VOLUMES] = /* Shoot for around 75% usage */ static long sd_stack [(DEFAULT_STACK_SIZE*2 + 0x1c0)/sizeof(long)]; static const char sd_thread_name[] = "ata/sd"; -static struct spinlock sd_spin NOCACHEBSS_ATTR; +static struct mutex sd_mtx NOCACHEBSS_ATTR; static struct event_queue sd_queue; /* Posted when card plugged status has changed */ @@ -801,7 +801,7 @@ int ata_read_sectors(IF_MV2(int drive,) unsigned long start, int incount, /* TODO: Add DMA support. */ - spinlock_lock(&sd_spin); + mutex_lock(&sd_mtx); ata_led(true); @@ -888,7 +888,7 @@ ata_read_retry: while (1) { ata_led(false); - spinlock_unlock(&sd_spin); + mutex_unlock(&sd_mtx); return ret; @@ -916,7 +916,7 @@ int ata_write_sectors(IF_MV2(int drive,) unsigned long start, int count, const unsigned char *buf, *buf_end; int bank; - spinlock_lock(&sd_spin); + mutex_lock(&sd_mtx); ata_led(true); @@ -1016,7 +1016,7 @@ ata_write_retry: while (1) { ata_led(false); - spinlock_unlock(&sd_spin); + mutex_unlock(&sd_mtx); return ret; @@ -1050,7 +1050,7 @@ static void sd_thread(void) /* Lock to keep us from messing with this variable while an init may be in progress */ - spinlock_lock(&sd_spin); + mutex_lock(&sd_mtx); card_info[1].initialized = 0; sd_status[1].retry = 0; @@ -1073,7 +1073,7 @@ static void sd_thread(void) if (action != SDA_NONE) queue_broadcast(SYS_FS_CHANGED, 0); - spinlock_unlock(&sd_spin); + mutex_unlock(&sd_mtx); break; } /* SD_HOTSWAP */ #endif /* HAVE_HOTSWAP */ @@ -1150,9 +1150,9 @@ int ata_init(void) int ret = 0; if (!initialized) - spinlock_init(&sd_spin IF_COP(, SPINLOCK_TASK_SWITCH)); + mutex_init(&sd_mtx); - spinlock_lock(&sd_spin); + mutex_lock(&sd_mtx); ata_led(false); @@ -1215,7 +1215,7 @@ int ata_init(void) #endif } - spinlock_unlock(&sd_spin); + mutex_unlock(&sd_mtx); return ret; } diff --git a/firmware/target/arm/tms320dm320/spi-dm320.c b/firmware/target/arm/tms320dm320/spi-dm320.c index f3b41add54..d8f338f592 100644 --- a/firmware/target/arm/tms320dm320/spi-dm320.c +++ b/firmware/target/arm/tms320dm320/spi-dm320.c @@ -32,7 +32,7 @@ #define GIO_RTC_ENABLE (1<<12) #define GIO_BL_ENABLE (1<<13) -struct spinlock spi_lock; +struct mutex spi_mtx; struct SPI_info { volatile unsigned short *setreg; @@ -60,7 +60,7 @@ int spi_block_transfer(enum SPI_target target, const uint8_t *tx_bytes, unsigned int tx_size, uint8_t *rx_bytes, unsigned int rx_size) { - spinlock_lock(&spi_lock); + mutex_lock(&spi_mtx); /* Activate the slave select pin */ *spi_targets[target].setreg = spi_targets[target].bit; @@ -87,13 +87,13 @@ int spi_block_transfer(enum SPI_target target, *spi_targets[target].clrreg = spi_targets[target].bit; - spinlock_unlock(&spi_lock); + mutex_unlock(&spi_mtx); return 0; } void spi_init(void) { - spinlock_init(&spi_lock); + mutex_init(&spi_mtx); /* Set SCLK idle level = 0 */ IO_SERIAL0_MODE |= 1<<10; /* Enable TX */ diff --git a/uisimulator/sdl/kernel.c b/uisimulator/sdl/kernel.c index 7126b82072..17ca55a694 100644 --- a/uisimulator/sdl/kernel.c +++ b/uisimulator/sdl/kernel.c @@ -597,7 +597,7 @@ void mutex_unlock(struct mutex *m) /* unlocker not being the owner is an unlocking violation */ if(m->thread != thread_get_current()) { - fprintf(stderr, "spinlock_unlock->wrong thread"); + fprintf(stderr, "mutex_unlock->wrong thread"); exit(-1); } @@ -617,52 +617,6 @@ void mutex_unlock(struct mutex *m) } } -void spinlock_init(struct spinlock *l) -{ - l->locked = 0; - l->thread = NULL; - l->count = 0; -} - -void spinlock_lock(struct spinlock *l) -{ - struct thread_entry *const thread = thread_get_current(); - - if (l->thread == thread) - { - l->count++; - return; - } - - while(test_and_set(&l->locked, 1)) - { - switch_thread(NULL); - } - - l->thread = thread; -} - -void spinlock_unlock(struct spinlock *l) -{ - /* unlocker not being the owner is an unlocking violation */ - if(l->thread != thread_get_current()) - { - fprintf(stderr, "spinlock_unlock->wrong thread"); - exit(-1); - } - - if (l->count > 0) - { - /* this thread still owns lock */ - l->count--; - return; - } - - /* clear owner */ - l->thread = NULL; - l->locked = 0; -} - #ifdef HAVE_SEMAPHORE_OBJECTS void semaphore_init(struct semaphore *s, int max, int start) { -- cgit v1.2.3