mirror of
https://github.com/Rockbox/rockbox.git
synced 2025-11-10 05:32:40 -05:00
rk27xx: Turn off i2c clock when not in use
Change-Id: Ifc6c25a53ace1a5f4d716a33d4979ea0a37fac98
This commit is contained in:
parent
16335da1cf
commit
ae27c331e1
1 changed files with 147 additions and 128 deletions
|
|
@ -40,7 +40,7 @@ static struct mutex i2c_mtx;
|
||||||
|
|
||||||
static bool i2c_write_byte(uint8_t data, bool start)
|
static bool i2c_write_byte(uint8_t data, bool start)
|
||||||
{
|
{
|
||||||
long timeout = current_tick + 50;
|
long timeout = current_tick + HZ/50;
|
||||||
|
|
||||||
/* START */
|
/* START */
|
||||||
I2C_CONR |= (1<<3) | (1<<2); /* master port enable, transmit bit */
|
I2C_CONR |= (1<<3) | (1<<2); /* master port enable, transmit bit */
|
||||||
|
|
@ -121,6 +121,8 @@ void i2c_init(void)
|
||||||
{
|
{
|
||||||
mutex_init(&i2c_mtx);
|
mutex_init(&i2c_mtx);
|
||||||
|
|
||||||
|
|
||||||
|
/* ungate i2c module clock */
|
||||||
SCU_CLKCFG &= ~(1<< 20);
|
SCU_CLKCFG &= ~(1<< 20);
|
||||||
|
|
||||||
I2C_OPR |= (1<<7); /* reset state machine */
|
I2C_OPR |= (1<<7); /* reset state machine */
|
||||||
|
|
@ -142,15 +144,23 @@ void i2c_init(void)
|
||||||
I2C_IER = 0x00;
|
I2C_IER = 0x00;
|
||||||
|
|
||||||
I2C_OPR |= (1<<6); /* enable i2c core */
|
I2C_OPR |= (1<<6); /* enable i2c core */
|
||||||
|
|
||||||
|
/* turn off i2c module clock until we need to comunicate */
|
||||||
|
SCU_CLKCFG |= (1<< 20);
|
||||||
}
|
}
|
||||||
|
|
||||||
int i2c_write(unsigned char slave, int address, int len,
|
int i2c_write(unsigned char slave, int address, int len,
|
||||||
const unsigned char *data)
|
const unsigned char *data)
|
||||||
{
|
{
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
mutex_lock(&i2c_mtx);
|
mutex_lock(&i2c_mtx);
|
||||||
|
|
||||||
i2c_iomux(slave);
|
i2c_iomux(slave);
|
||||||
|
|
||||||
|
/* ungate i2c clock */
|
||||||
|
SCU_CLKCFG &= ~(1<<20);
|
||||||
|
|
||||||
/* clear all flags */
|
/* clear all flags */
|
||||||
I2C_ISR = 0x00;
|
I2C_ISR = 0x00;
|
||||||
I2C_IER = 0x00;
|
I2C_IER = 0x00;
|
||||||
|
|
@ -158,16 +168,16 @@ int i2c_write(unsigned char slave, int address, int len,
|
||||||
/* START */
|
/* START */
|
||||||
if (! i2c_write_byte(slave & ~1, true))
|
if (! i2c_write_byte(slave & ~1, true))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 1;
|
||||||
return 1;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (address >= 0)
|
if (address >= 0)
|
||||||
{
|
{
|
||||||
if (! i2c_write_byte(address, false))
|
if (! i2c_write_byte(address, false))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 2;
|
||||||
return 2;
|
goto end;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -176,28 +186,35 @@ int i2c_write(unsigned char slave, int address, int len,
|
||||||
{
|
{
|
||||||
if (! i2c_write_byte(*data++, false))
|
if (! i2c_write_byte(*data++, false))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 4;
|
||||||
return 4;
|
goto end;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* STOP */
|
/* STOP */
|
||||||
if (! i2c_stop())
|
if (! i2c_stop())
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 5;
|
||||||
return 5;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
end:
|
||||||
mutex_unlock(&i2c_mtx);
|
mutex_unlock(&i2c_mtx);
|
||||||
return 0;
|
SCU_CLKCFG |= (1<<20);
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int i2c_read(unsigned char slave, int address, int len, unsigned char *data)
|
int i2c_read(unsigned char slave, int address, int len, unsigned char *data)
|
||||||
{
|
{
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
mutex_lock(&i2c_mtx);
|
mutex_lock(&i2c_mtx);
|
||||||
|
|
||||||
i2c_iomux(slave);
|
i2c_iomux(slave);
|
||||||
|
|
||||||
|
/* ungate i2c module clock */
|
||||||
|
SCU_CLKCFG &= ~(1<<20);
|
||||||
|
|
||||||
/* clear all flags */
|
/* clear all flags */
|
||||||
I2C_ISR = 0x00;
|
I2C_ISR = 0x00;
|
||||||
I2C_IER = 0x00;
|
I2C_IER = 0x00;
|
||||||
|
|
@ -207,23 +224,23 @@ int i2c_read(unsigned char slave, int address, int len, unsigned char *data)
|
||||||
/* START */
|
/* START */
|
||||||
if (! i2c_write_byte(slave & ~1, true))
|
if (! i2c_write_byte(slave & ~1, true))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 1;
|
||||||
return 1;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* write address */
|
/* write address */
|
||||||
if (! i2c_write_byte(address, false))
|
if (! i2c_write_byte(address, false))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 2;
|
||||||
return 2;
|
goto end;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* (repeated) START */
|
/* (repeated) START */
|
||||||
if (! i2c_write_byte(slave | 1, true))
|
if (! i2c_write_byte(slave | 1, true))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 3;
|
||||||
return 3;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
I2C_CONR &= ~(1<<3); /* clear transmit bit (switch to receive mode) */
|
I2C_CONR &= ~(1<<3); /* clear transmit bit (switch to receive mode) */
|
||||||
|
|
@ -232,8 +249,8 @@ int i2c_read(unsigned char slave, int address, int len, unsigned char *data)
|
||||||
{
|
{
|
||||||
if (! i2c_read_byte(data++))
|
if (! i2c_read_byte(data++))
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 4;
|
||||||
return 4;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (len == 1)
|
if (len == 1)
|
||||||
|
|
@ -247,10 +264,12 @@ int i2c_read(unsigned char slave, int address, int len, unsigned char *data)
|
||||||
/* STOP */
|
/* STOP */
|
||||||
if (! i2c_stop())
|
if (! i2c_stop())
|
||||||
{
|
{
|
||||||
mutex_unlock(&i2c_mtx);
|
ret = 5;
|
||||||
return 5;
|
goto end;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
end:
|
||||||
mutex_unlock(&i2c_mtx);
|
mutex_unlock(&i2c_mtx);
|
||||||
return 0;
|
SCU_CLKCFG |= (1<<20);
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue