реклама на сайте
подробности

 
 
 
Reply to this topicStart new topic
> SC16IS740 I2C to UART, interfacing with ARM
buletz
сообщение Mar 19 2008, 15:31
Сообщение #1


Участник
*

Группа: Свой
Сообщений: 52
Регистрация: 4-07-06
Из: Moscow
Пользователь №: 18 554



Имею ARM7 контроллер (LPC2138) и хочу от него передавать данные на RS232 через следующую цепочку:
ARM I2C -> SC16IS740 (i2c->uart) -> ADM3202 (uart->rs232) -> RS232 (COM порт) PC

Нужны исходники (на СИ) для передачи данных используя I2c через микруху SC16IS740. Может кто-нибудь помочь ?

на сайте производителя (nxp.com) нашел только вариант для SPI. sad.gif

Сообщение отредактировал buletz - Mar 19 2008, 15:31
Go to the top of the page
 
+Quote Post
buletz
сообщение Mar 21 2008, 14:22
Сообщение #2


Участник
*

Группа: Свой
Сообщений: 52
Регистрация: 4-07-06
Из: Moscow
Пользователь №: 18 554



Очень плотно искал готовые исходники под SC16IS740 (он же 750, он же 760) для связи с ARM7 под i2c, но нашел только SPI.
В итоге пришлось разбираться самому, за два дня я эту связь победил.

Основная проблема была в том, чтобы заметить что адреса регистра передаются на микруху SC16.. со сдвигом влево на 3 бита. Очень уж это неявно указано в документации было.

Может кому пригодится, выкладываю исходники.

Примеч.: написано под IAR компил., реализация без прерываний.


файл -------------------------i2c.h ------------------------------------

Код
typedef struct {
    uchar err;
    uchar tmp;
    }  Ti2c;


#define THR             0x00        // transmit FIFO, write only
#define RHR            0x00        // receive FIFO, read oly
#define IER            0x01        // interrup enable reg., R/W
#define FCR            0x02        // FIFO control, write only
#define IIR            0x02        // interrupt status, read only
#define LCR            0x03        // line control, R/W
#define MCR            0x04        // modem control, R/W
#define LSR            0x05        // Line status, R/W
#define MSR            0x06        // Modem status, R/W
#define SPR            0x07        // scratch pad, R/W
#define TXFIFO        0x08        // TX FIFO, R
#define RXFIFO        0x09        // RX FIFO, R


/* special registers, LCR.7 must be set to 1 to R/W to these registers */
#define DLL            0x00        // baud rate divisor, low R/W
#define DLH            0x01        // baud rate divisor, hi R/W
#define EFR            0x02        // enhanced register, R/W
#define XON1        0x04        // flow control
#define XON2        0x05        // flow control
#define XOFF1        0x06        // flow control
#define XOFF2        0x07        // flow control
  

#define I20CONSET_I2EN        0x00000040  /* I2C Control Set Register */
#define I20CONSET_AA        0x00000004
#define I20CONSET_SI        0x00000008
#define I20CONSET_STO        0x00000010
#define I20CONSET_STA        0x00000020

#define I20CONCLR_AAC        0x00000004  /* I2C Control clear Register */
#define I20CONCLR_SIC        0x00000008
#define I20CONCLR_STAC        0x00000020
#define I20CONCLR_I2ENC        0x00000040

#define SC16_ADR        0x9A
#define RD_BIT            0x01
#define WR_BIT            0x00

#define SC16_RESET_ON  IO0CLR= 1<<21             // ~sc16_rst висит на ноге P0.21  (ACTIVE LOW)
#define SC16_RESET_OFF IO0SET= 1<<21


void i2c_init();
void i2c_isr ();
uchar sc16_wr (uchar adr, uchar value);
uchar sc16_rd (uchar adr);


файл ----------------------------- i2c.c --------------------------------------------------


Код
uchar sc16_wr (uchar adr, uchar value)   //   ЗАПИСЬ БАЙТА В РЕГИСТР
// возвращает 1 если удачно передано
//            0 если неудачно
{
I20CONCLR = I20CONCLR_STAC |  I20CONCLR_SIC | I20CONCLR_AAC; // clear all bits, кроме I2EN


I20CONSET = I20CONSET_STA; // set START

while (I20STAT != 0x08); // ждем

I20DAT = SC16_ADR | WR_BIT;  // адрес микрухи
I20CONCLR = I20CONCLR_SIC;  // передача байта
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0x18)  { i2c_error (); return 0; }

I20DAT = adr<<3;  // адрес регистра
I20CONCLR = I20CONCLR_STAC; // clear START
I20CONCLR = I20CONCLR_SIC;  // передача байта
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0x28)  { i2c_error (); return 0; }

I20DAT = value;  // значение регистра
I20CONCLR = I20CONCLR_SIC;  // передача байта
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0x28)  { i2c_error (); return 0; }

I20CONSET = I20CONSET_STO;  // после данных сразу передаем STOP
I20CONCLR = I20CONCLR_SIC;  // передача байта
//while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0xF8)  { i2c_error (); return 0; }

return 1;
}



// ------------------------------------------------------------------------------------
uchar sc16_rd (uchar adr)       //           ЧТЕНИЕ байта по I2c
// возвращает 1 если удачно передано
//            0 если неудачно
{
uchar tmp;
I20CONCLR = I20CONCLR_STAC |  I20CONCLR_SIC | I20CONCLR_AAC; // clear all bits, кроме I2EN

I20CONSET = I20CONSET_STA; // set START
while (I20STAT != 0x08); // ждем

I20DAT = SC16_ADR | WR_BIT;  // адрес микрухи
I20CONCLR = I20CONCLR_SIC;  // передача байта
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0x18)  { i2c_error (); return 0; }

I20DAT = adr<<3;  // адрес регистра
I20CONCLR = I20CONCLR_STAC; // clear START
I20CONCLR = I20CONCLR_SIC;  // передача байта
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0x28)  { i2c_error (); return 0; }

I20CONSET = I20CONSET_STA; // repeated START
I20CONCLR = I20CONCLR_SIC;  // передача байта

while (I20STAT != 0x10); // ждем

I20DAT = SC16_ADR | RD_BIT;  // адрес микрухи
I20CONCLR = I20CONCLR_SIC;  // передача байта
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1

if (I20STAT != 0x40)  { i2c_error (); return 0; }

I20CONCLR = I20CONCLR_STAC | I20CONCLR_AAC; // clear START;   про AA написано для наглядности, хотя он итак 0
I20CONCLR = I20CONCLR_SIC;  // поехали на чтение
while ((I20CONSET & I20CONSET_SI) ==0); // ждем пока SI не установится в 1
if (I20STAT != 0x58)  { i2c_error (); return 0; }

tmp = I20DAT;

I20CONSET = I20CONSET_STO;
I20CONCLR = I20CONCLR_SIC;  // поехали

return tmp;
}



void i2c_init()
{
SC16_RESET_ON;
SC16_RESET_OFF;

// перед тем как юзать микруху SC16 по I2c необходимо выждать минимум 3 us.
uint i=0; while (i<65000) { i2c.tmp+= IO0PIN; i++; }  // <<<<<< типа ПАУЗА

//PINSEL0 |= 0x50; // P0.3 = SDA, P0.2 = SCL

// Initialize I2C0
I20CONCLR = 0xFF;
I20CONSET = 0x40; // Master mode configuration, I2EN bit set

// частота CLK для I2c
I20SCLH = 0xFF; // I2c_FREQ = FPCLK / ( SCLH + SCLL),  так что частоту считайте сами под свой кристалл
I20SCLL = 0xFF; //    



}


Сообщение отредактировал buletz - Mar 21 2008, 14:25
Go to the top of the page
 
+Quote Post

Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 21st July 2025 - 09:20
Рейтинг@Mail.ru


Страница сгенерированна за 0.01368 секунд с 7
ELECTRONIX ©2004-2016