void EEPROM_Write(int addr,unsigned char* pdata,int len) { int i; unsigned long tmp; volatile unsigned char c1; volatile unsigned char c2; volatile unsigned char c3; volatile unsigned char* pd = pdata; c1 = 0x02; // Write command if (addr>0xFF) c1|=8; // address 9th bit c2 = addr; CS_ON(); PUT(0x06);//// Send WREN (Enable Write Operations) CS_OFF(); CS_ON(); while( SSIDataGetNonBlocking(SSI1_BASE, &tmp)) {} ; while(SSIBusy(SSI1_BASE)) {}; PUT(c1); PUT(c2); for(i=0;i<len;i++) { c3 = *(pd+i); PUT(c3); } CS_OFF(); DELAY(); }
/*! \brief ATA6870_SPI_COM() * * Sends complete commands to the ATA6870 * * \note nothing * * \param ucAdr2 - Adress of �C (required) * \param ucCommandCode1 - SPI Command Part 1 * \param ucCommandCode2 - SPI Command Part 2 * * \retval nothing */ void ATA6870_SPI_COM(uint8_t ucAdr2, uint8_t ucCommandCode1, uint8_t ucCommandCode2){ unsigned char ucAdr1 = 0x00; // Only two Chips adressed unsigned int j=0; switch(ucAdr2){ case 0x01: // IC1 Adressed case 0x02: // IC2 Adressed case 0x03: // Both IC Adressed default: break; } // SPI_Enable //CLEARBIT(NSS_PORTx, NSS); CS_ON(); // ********************************************* SPI_COM(ucAdr1); // SPI Command: Adr1 SPI_COM(ucAdr2); // SPI Command: Adr2 // ********************************************* SPI_COM(ucCommandCode1); // SPI Command: CODE2 switch(operation){ case 0x01: // Offset acq while(j<6){ Offset[(ucAdr2-1)][j] = SPI_COM(0x00); Offset[(ucAdr2-1)][j] <<= 8; Offset[(ucAdr2-1)][j++] |= SPI_COM(0x00); } operation=0x00; break; case 0x03: // Voltage acq while(j<6){ Acquisition[(ucAdr2-1)][j] = SPI_COM(0x00); Acquisition[(ucAdr2-1)][j] <<= 8; Acquisition[(ucAdr2-1)][j++] |= SPI_COM(0x00); } Tacquisition[ActiveTemp] = SPI_COM(0x00); //Temperature acquisition Tacquisition[ActiveTemp] <<= 8; Tacquisition[ActiveTemp] |= SPI_COM(0x00); operation=0x00; break; default: SPI_COM(ucCommandCode2); break; } _delay_ms(10); // SPI_Disable; //SETBIT(NSS_PORTx, NSS); CS_OFF(); }
static void rtc_clear_alarm_int(void) { CS_ON(); spi_transfer(RTC_CTRL_INT_FLAG | RTC_WRITE); spi_transfer(0); CS_OFF(); }
void EEPROM_Read(int addr,unsigned char* pdata,int len,unsigned char ischar) { int i=0; volatile unsigned long tmp=0; volatile unsigned char c1=0; volatile unsigned char c2=0; c1 = 0x03; // Read command if (addr>0xFF) c1|=8; // address 9th bit c2 = addr ; CS_ON(); while(SSIBusy(SSI1_BASE)) {}; PUT(c1); PUT(c2); while( SSIDataGetNonBlocking(SSI1_BASE,(unsigned long*) &tmp)) {} ; for(i=0;i<len;i++) { PUT(0x00);//// Send dummy Byte command while(SSIDataGetNonBlocking(SSI1_BASE, (unsigned long*) &tmp))// Fetch data from RX buffer { DELAY(); } if ((ischar) && (tmp==UNINITIALIZED)) tmp = ZERO; *(pdata+i) = tmp; } CS_OFF(); DELAY(); }
void init_command(unsigned int command_data, char display_num) { unsigned int i, j; command_data = command_data & 0xfff; command_data = command_data << 4; // Toggle CS1 CS_ON(display_num); DEBUG_DELAY CS_OFF(display_num); DEBUG_DELAY for (i = 0; i < 12; i++) { DEBUG_DELAY WR_OFF; j = command_data & 0x8000; command_data = command_data << 1; j = j >> 15; sendBit(j); DEBUG_DELAY WR_ON; } DEBUG_DELAY CS_ON(display_num); }
static int rtc_get_temperature(void) { CS_ON(); spi_transfer(RTC_TEMPERATURE | RTC_READ); uint8_t data = spi_transfer(0); CS_OFF(); return map(data, 0, 250, -60, 190); }
/******************************************************************************* *Настройка SPI-шины контроллера и включение ATA6870 ******************************************************************************/ void SPI_MasterInit(void){ /* configure pins used by SPI1 * 250kHz //FIXME in code * PA4 = PD_N Включение верхнего ATA6870 * PA5 = SCK * PA6 = MISO * PA7 = MOSI * CPOL = 1 * CPHA = 1 */ GPIO_InitTypeDef SPI_Pin_Init; //Настройка пинов SPI1. GPIO_InitTypeDef SPI_Pin_CS_Init; //CS. SPI_InitTypeDef SPI1_Init; //Настройка SPI1. RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); //Вкл. тактирование порта с пинами SPI1. RCC_APB2PeriphClockCmd(RCC_APB2Periph_SPI1, ENABLE); //Вкл. тактирования SPI1. SPI_Pin_Init.GPIO_Pin = GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7; SPI_Pin_Init.GPIO_Mode = GPIO_Mode_AF_PP; //Настраиваем PD_N, SPI1_SCK, SPI1_MOSI и SPI1_MOSI SPI_Pin_Init.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOA, &SPI_Pin_Init); //Настройка пина CS. SPI_Pin_CS_Init.GPIO_Mode = GPIO_Mode_Out_PP; SPI_Pin_CS_Init.GPIO_Pin = GPIO_Pin_4; SPI_Pin_CS_Init.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOA, &SPI_Pin_CS_Init); CS_OFF(); //CS=1. SPI1_Init.SPI_Direction = SPI_Direction_2Lines_FullDuplex; //Вход и выход. SPI1_Init.SPI_Mode = SPI_Mode_Master; //Мастер. SPI1_Init.SPI_DataSize = SPI_DataSize_8b; //Можно и 16! SPI1_Init.SPI_CPHA = SPI_CPHA_2Edge; //Со 2-го фронта. SPI1_Init.SPI_CPOL = SPI_CPOL_High; //В режиме ожидания SCK - 1. SPI1_Init.SPI_NSS = SPI_NSS_Soft; //Програмный NSS (в железе отключено). SPI1_Init.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_32; //Скорость. SPI1_Init.SPI_FirstBit = SPI_FirstBit_MSB; //Со старшего бита. SPI1_Init.SPI_CRCPolynomial = 7; //Фигня какая-то. SPI_Init(SPI1, &SPI1_Init); //SPI_I2S_ITConfig(SPI2, SPI_I2S_IT_RXNE, ENABLE); //Включаем прерывание SPI_Cmd(SPI1, ENABLE); //Запуск SPI1. // ATA6870 Enable PD_N_ON();//Activate ATA6870 // Поскольку сигнал NSS контролируется программно, установим его в единицу // Если сбросить его в ноль, то наш SPI модуль подумает, что // у нас мультимастерная топология и его лишили полномочий мастера. //SPI_NSSInternalSoftwareConfig(SPI1, SPI_NSSInternalSoft_Set); }
void senddata1(char display_num) { unsigned i; TP_ON; CS_ON(display_num); DEBUG_DELAY delayms(1); CS_OFF(display_num); DEBUG_DELAY delayms(1); WR_OFF; DEBUG_DELAY sendBit(1); DEBUG_DELAY WR_ON; DEBUG_DELAY WR_OFF; DEBUG_DELAY sendBit(0); DEBUG_DELAY WR_ON; DEBUG_DELAY WR_OFF; DEBUG_DELAY sendBit(1); DEBUG_DELAY WR_ON; DEBUG_DELAY temp1 = 0x80; MCU_Address_2416(0x00); for (row = 0; row < 3; row++) { for (i = 0; i < 8; i++) { MCU_Data_2416(Array1, display_num); if (temp1 == 0x00) temp1 = 0x80; } } delayms(1); DEBUG_DELAY CS_ON(display_num); DEBUG_DELAY TP_OFF; DEBUG_DELAY tmpBit = tmpBit ^ 1; }
//----------------------------------------------------------------- //RX void DMA2_Stream0_IRQHandler(void) { uint16_t temp; if (DMA_GetITStatus(DMA2_Stream0, DMA_IT_TCIF0) == SET) { DMA_ClearITPendingBit(DMA2_Stream0, DMA_IT_TCIF0); CS_OFF(); SPI_work = 0; buffer[0] = 0xAA; buffer[1] = 0xBB; temp = (((uint16_t)SPI_In[2])<<8)|((uint16_t)SPI_In[1]); if (temp >= 0x8000) { temp = temp - 0x8000; } else { temp = temp + 0x8000; } buffer[2] = (uint8_t)(temp>>8);//X buffer[3] = (uint8_t)temp; temp = (((uint16_t)SPI_In[4])<<8)|((uint16_t)SPI_In[3]);//Y if (temp >= 0x8000) { temp = temp - 0x8000; } else { temp = temp + 0x8000; } buffer[4] = (uint8_t)(temp>>8);//Y buffer[5] = (uint8_t)temp; temp = (((uint16_t)SPI_In[6])<<8)|((uint16_t)SPI_In[5]);//Z if (temp >= 0x8000) { temp = temp - 0x8000; } else { temp = temp + 0x8000; } buffer[6] = (uint8_t)(temp>>8);//Z buffer[7] = (uint8_t)temp; DMA_SetCurrDataCounter(DMA1_Stream6, 8); DMA_Cmd(DMA1_Stream6, ENABLE); }
static void rtc_get_datetime(TDateTime* dt) { CS_ON(); spi_transfer(RTC_CLOCK | RTC_READ); dt->second = spi_transfer(0); dt->minute = spi_transfer(0); dt->hour = spi_transfer(0); dt->day = spi_transfer(0); dt->weekday = spi_transfer(0); dt->month = spi_transfer(0); dt->year = spi_transfer(0); CS_OFF(); dt->second = bcd2bin(dt->second); dt->minute = bcd2bin(dt->minute); dt->hour = bcd2bin(dt->hour); dt->day = bcd2bin(dt->day); dt->weekday = bcd2bin(dt->weekday); dt->month = bcd2bin(dt->month); dt->year = bcd2bin(dt->year); }
static void rtc_set_alarm(TDateTime* dt) { TDateTime alarm_enabled = { 0 }; // mark alarm settings alarm_enabled.second = dt->second & RTC_AE_S; alarm_enabled.minute = dt->minute & RTC_AE_S; alarm_enabled.hour = dt->hour & RTC_AE_S; alarm_enabled.weekday = dt->weekday & RTC_AE_S; alarm_enabled.day = dt->day & RTC_AE_S; alarm_enabled.month = dt->month & RTC_AE_S; alarm_enabled.year = dt->year & RTC_AE_S; // clear alarm settings dt->second &= ~RTC_AE_S; dt->minute &= ~RTC_AE_S; dt->hour &= ~RTC_AE_S; dt->day &= ~RTC_AE_S; dt->month &= ~RTC_AE_S; dt->year &= ~RTC_AE_S; uint8_t seconds = bin2bcd(dt->second); uint8_t minutes = bin2bcd(dt->minute); uint8_t hours = bin2bcd(dt->hour); //uint8_t weekdays = bin2bcd(0); uint8_t days = bin2bcd(dt->day); uint8_t months = bin2bcd(dt->month); uint8_t years = bin2bcd(dt->year - 2000); CS_ON(); spi_transfer(RTC_ALARM | RTC_WRITE); spi_transfer(seconds | alarm_enabled.second); spi_transfer(minutes | alarm_enabled.minute); spi_transfer(hours | alarm_enabled.hour); spi_transfer(days | alarm_enabled.day); spi_transfer(0); spi_transfer(months | alarm_enabled.month); spi_transfer(years | alarm_enabled.year); CS_OFF(); }
static void rtc_set_datetime(TDateTime* dt) { uint8_t seconds = bin2bcd(dt->second); uint8_t minutes = bin2bcd(dt->minute); uint8_t hours = bin2bcd(dt->hour); //uint8_t weekdays = bin2bcd(0); uint8_t days = bin2bcd(dt->day); uint8_t months = bin2bcd(dt->month); uint8_t years = bin2bcd(dt->year); CS_ON(); spi_transfer(RTC_CLOCK | RTC_WRITE); spi_transfer(seconds); spi_transfer(minutes); spi_transfer(hours); spi_transfer(days); spi_transfer(0); spi_transfer(months); spi_transfer(years); CS_OFF(); }
static void rtc_debug(void) { uint8_t reg[26] = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x18, 0x19, 0x20, 0x30, 0x31, 0x32, 0x33 }; for (uint8_t i = 0; i < 26; i++) { CS_ON(); spi_transfer(reg[i] | RTC_READ); uint8_t d = spi_transfer(0); CS_OFF(); char buf[20] = { 0 }; sprintf(buf, "Reg 0x%02x: 0x%02x\r\n", reg[i], d); uart_putchars(buf, 20); _delay_ms(100); } }
int rtc_test(void) { uart_putchars("RTC Test\r\n", 10); DDRB = 0; // AVR-PIN Signal RTC-PIN // PB0 CS Chipselect 3 // PB3 MOSI Master Output 9 // PB4 MISO Master Input 5 // PB5 SCK Serial Clock 4 Set_bits(DDRB, (1 << PB0) | (1 << PB3) | (1 << PB5) | (1 << PB2)); CS_OFF(); SPCR = (1<<SPE) | (1 << MSTR) | (0 << SPI2X) | (0 << SPR1) | (0 << SPR0); // RTC Software Reset CS_ON(); spi_transfer(RTC_CTRL_RESET | RTC_WRITE); spi_transfer(RTC_RESET); CS_OFF(); //debug_rtc(); _delay_ms(100); // RTC Status CS_ON(); uint8_t ctrl_Status = spi_transfer(RTC_CTRL_STATUS); CS_OFF(); if(ctrl_Status & RTC_PON) { //clear POWER-ON bit ctrl_Status &= ~RTC_PON; CS_ON(); spi_transfer(RTC_CTRL_STATUS | RTC_WRITE); spi_transfer(ctrl_Status); CS_OFF(); } if(ctrl_Status & RTC_SR) { //clear SELF-RECOVERY bit ctrl_Status &= ~RTC_SR; CS_ON(); spi_transfer(RTC_CTRL_STATUS | RTC_WRITE); spi_transfer(ctrl_Status); CS_OFF(); } CS_ON(); spi_transfer(RTC_CTRL_INT_FLAG | RTC_WRITE); spi_transfer(0); CS_OFF(); CS_ON(); spi_transfer(RTC_CTRL_INT | RTC_WRITE); spi_transfer(1); CS_OFF(); CS_ON(); spi_transfer(RTC_EPROM_CTRL | RTC_WRITE); spi_transfer(RTC_THE); CS_OFF(); // set datetime now.year = 16; now.month = 5; now.day = 12; now.hour = 12; now.minute = 00; now.second = 00; rtc_set_datetime(&now); // set alarm TDateTime alarm = { 0 }; alarm.second = 5 | RTC_AE_S; //alarm.minute = 0 | RTC_AE_S; rtc_set_alarm(&alarm); rtc_debug(); uint8_t s = 0; for (;;) { rtc_get_datetime(&now); int temperature = rtc_get_temperature(); if(now.second != s) { s = now.second; char buf[50] = { 0 }; sprintf(buf, "%d.%d.%d - %d:%d:%d Temp:%d\r\n", now.day, now.month, now.year, now.hour, now.minute, now.second, temperature); uart_putchars(buf, 50); if(s == (alarm.second + 1)) { rtc_clear_alarm_int(); } } } }