int transmitByte(uint8_t data) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = data; /* send data */ return 0; }
void uart_putchar(char c) { loop_until_bit_is_set(UCSR0A, UDRE0); /* Wait until data register empty. */ UDR0 = c; }
//Usage: uart_putchar('R'); //Purpose: Sends character c through the UART //Inputs: char c->Character to be transmitted //Outputs: None static int uart_putchar(char c, FILE *stream) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = c; return 0; }
unsigned char uart_getchar(void) { loop_until_bit_is_set(UCSRA, RXC); return UDR; }
void USART0_putc (char c) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = c; }
void configureAndTest(void) { struct TestData testData; char btName[20]; // Configure Bluetooth module SET_LED_STAT; // USART setup at 9600 baud (default in Bluetooth module) UBRR0 = 77; // = [F_CPU / (16*baud)] - 1 (9600 bps @ 12MHz) UCSR0B = B(TXEN0); // Enable TX and keep default 8n1 serial data format sei(); // To enable UDRE interrupt to send UART data btStatMode = true; _delay_ms(1000); // Bluetooth module startup delay sendProgmemStr(cmdName); _delay_ms(1000); // Bluetooth module delay between commands sendProgmemStr(cmdBaud); CLR_LED_STAT; // give time for the LDRs on test system to stabilize _delay_ms(1000); // Bluetooth module delay between commands cli(); // System test (with test system) // ADC setup ADCSRA = B(ADEN) | B(ADPS2) | B(ADPS1); // Enable ADC with 1/64 prescaler - fAD = 12e6/64 = 187.5 kHz @ 12MHz (must be < 200 kHz) // SPI module setup to communicate with test system SPCR = B(SPE) | B(MSTR) | B(SPR0); // Enable SPI master mode, SCK freq = fosc/8 = 1.5 MHz @ 12 MHz (must be < 12 MHz / 4) SPSR = B(SPI2X); testData.inputs0 = ISSET_I2 | ISSET_INT; // should be low testData.inputs1 = ISSET_I1; // should be high (button not pressed) CLR_SS; // set /SS output low // initiate communication with test system SPDR = 0x34; loop_until_bit_is_set(SPSR, SPIF); testData.init = SPDR; // Rest values // voltage levels //_delay_us(10); // give time to test system set I2 testData.vBat = sampleADC(BITPOS_ABAT); // this will also give time to test system set I2 sampleADC(0x0E); // pre-select bandgap voltage reference to allow it to stabilize testData.inputs1 |= ISSET_I2; // should be high testData.dv1_1 = recvSPI(); // 1.1 V internal reference on test system (powered by DVcc) testData.av1_1 = sampleADC(0x0E); // 1.1 V internal reference; also give time to test system set /INT //_delay_us(10); // give time to test system set /INT testData.inputs1 |= ISSET_INT; // should be high testData.vRef = recvSPI(); testData.emgRef_2 = recvSPI(); testData.ecgRef_2 = recvSPI(); testData.eegRef_2 = recvSPI(); // outputs testData.ldrSta00 = recvSPI(); testData.ldrBat00 = recvSPI(); testData.ldrLedOff = recvSPI(); testData.pwmOff = recvSPI(); // inputs testData.edaShort = sampleADC(BITPOS_A3); // EDA testData.accXoff = recvSPI(); testData.accYoff = recvSPI(); testData.accZoff = sampleADC(BITPOS_A5); // ACC testData.luxOff = sampleADC(BITPOS_A6); // LUX // Start PWM stimulus: Timer 0 setup for PWM output OCR0B = 0xC0; // set PWM duty cycle as 3/4 TCCR0A = B(COM0B1) | B(WGM01) | B(WGM00); // Non-inverting Fast PWM mode on OC0B TCCR0B = B(CS00); // Start timer with no prescaling // Status LED on SET_LED_STAT; _delay_ms(110); // give time to test system reply testData.ldrSta10 = recvSPI(); testData.ldrBat10 = recvSPI(); CLR_LED_STAT; // Battery LED on SET_LED_BAT; _delay_ms(110); // give time to test system reply testData.ldrSta01 = recvSPI(); testData.ldrBat01 = recvSPI(); CLR_LED_BAT; // O1 LED on SET_O1; _delay_ms(110); // give time to test system reply testData.ldrLedOn = recvSPI(); CLR_O1; // Button pressed _delay_ms(110); // give time to test system press button testData.inputs0 |= ISSET_I1; // should be low (button pressed) // ACC ST on testData.accXon = recvSPI(); testData.accYon = recvSPI(); testData.accZon = sampleADC(BITPOS_A5); // ACC // LUX on //_delay_ms(100); // wait 100 ms for the LDRs to stabilize //testData.luxOn = sampleADC(BITPOS_A6); // LUX // PWM on (~400 ms have elapsed since start of PWM stimulus) //_delay_ms(10); // give time to test system reply testData.pwmOn = recvSPI(); OCR0B = 0; // EDA on //testData.edaOn = sampleADC(BITPOS_A3); // EDA ADCSRA = B(ADIF); // Disable ADC and clear pending interrupt flag SPCR = 0; // Disable SPI SET_SS; // set /SS output high // Send test data UBRR0 = 12; // = [F_CPU / (8*baud)] - 1 with U2X0 = 1 (115.2kbps @ 12MHz) UCSR0A = B(U2X0); UCSR0B = B(RXEN0) | B(TXEN0); // Enable RX and TX and keep default 8n1 serial data format loop_until_bit_is_set(UCSR0A, RXC0); // wait for incoming byte (and ignore it) for(byte i = 0; i < sizeof testData; i++) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = ((byte *)&testData)[i]; } // Receive Set Bluetooth name command do { loop_until_bit_is_set(UCSR0A, RXC0); // wait for incoming byte } while (UDR0 != 0x63); // loop until Set Bluetooth name command is received for(byte i = 0; i < sizeof btName; i++) { loop_until_bit_is_set(UCSR0A, RXC0); // wait for incoming byte btName[i] = UDR0; if (btName[i] == 0) break; } // send command reply loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = 0x36; // Change Bluetooth name // wait for Bluetooth connection drop while (ISSET_CTS) ; _delay_ms(100); // Add a delay between connection drop and command // send "AT+NAME" for(byte i = 0; i < 7; i++) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = pgm_read_byte(cmdName+i); } for(byte i = 0; i < sizeof btName; i++) { if (btName[i] == 0) break; loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = btName[i]; } _delay_ms(1000); // Bluetooth module delay between commands //UCSR0A = B(TXC0) | B(U2X0); // clear TXC0 //loop_until_bit_is_set(UCSR0A, TXC0); // wait for end of transmission UCSR0B = 0; // flush RX buffer }
/* * Receive a character from the UART Rx. * * This features a simple line-editor that allows to delete and * re-edit the characters entered, until either CR or NL is entered. * Printable characters entered will be echoed using uart_putchar(). * * Editing characters: * * . \b (BS) or \177 (DEL) delete the previous character * . ^u kills the entire input buffer * . ^w deletes the previous word * . ^r sends a CR, and then reprints the buffer * . \t will be replaced by a single space * * All other control characters will be ignored. * * The internal line buffer is RX_BUFSIZE (80) characters long, which * includes the terminating \n (but no terminating \0). If the buffer * is full (i. e., at RX_BUFSIZE-1 characters in order to keep space for * the trailing \n), any further input attempts will send a \a to * uart_putchar() (BEL character), although line editing is still * allowed. * * Input errors while talking to the UART will cause an immediate * return of -1 (error indication). Notably, this will be caused by a * framing error (e. g. serial line "break" condition), by an input * overrun, and by a parity error (if parity was enabled and automatic * parity recognition is supported by hardware). * * Successive calls to uart_getchar() will be satisfied from the * internal buffer until that buffer is emptied again. */ int uart_getchar(FILE *stream) { uint8_t c; char *cp, *cp2; static char b[RX_BUFSIZE]; static char *rxp; if (rxp == 0) for (cp = b;;) { loop_until_bit_is_set(UCSRA, RXC); if (UCSRA & _BV(FE)) return _FDEV_EOF; if (UCSRA & _BV(DOR)) return _FDEV_ERR; c = UDR; /* behaviour similar to Unix stty ICRNL */ if (c == '\r') c = '\n'; if (c == '\n') { *cp = c; uart_putchar(c, stream); rxp = b; break; } else if (c == '\t') c = ' '; if ((c >= (uint8_t)' ' && c <= (uint8_t)'\x7e') || c >= (uint8_t)'\xa0') { if (cp == b + RX_BUFSIZE - 1) uart_putchar('\a', stream); else { *cp++ = c; uart_putchar(c, stream); } continue; } switch (c) { case 'c' & 0x1f: return -1; case '\b': case '\x7f': if (cp > b) { uart_putchar('\b', stream); uart_putchar(' ', stream); uart_putchar('\b', stream); cp--; } break; case 'r' & 0x1f: uart_putchar('\r', stream); for (cp2 = b; cp2 < cp; cp2++) uart_putchar(*cp2, stream); break; case 'u' & 0x1f: while (cp > b) { uart_putchar('\b', stream); uart_putchar(' ', stream); uart_putchar('\b', stream); cp--; } break; case 'w' & 0x1f: while (cp > b && cp[-1] != ' ') { uart_putchar('\b', stream); uart_putchar(' ', stream); uart_putchar('\b', stream); cp--; } break; } } c = *rxp++; if (c == '\n') rxp = 0; return c; }
/* waits for transmitter to not be busy then tx a byte */ void serTx(unsigned char data) { loop_until_bit_is_set(UCSRA, UDRE); // wait while previous tx is finished UDR = data; // tx }
void JETI_put_stop (void) { loop_until_bit_is_set(UCSR0A, UDRE0); UCSR0B &= ~(1 << TXB80); UDR0 = 0xFF; }
u16 REMOTE_get(void) { u08 i, tmp = 0; u08 time; u08 T2,T4; union u16convert code; loop_until_bit_is_set (PIN(REMOTE_PORT), REMOTE_BIT); // skip leading signal TCCR0 = (4); //update every 32us TCNT0 = 1; while (bit_is_set(PIN(REMOTE_PORT), REMOTE_BIT)) { T2 = TCNT0; if (T2 >= 140) // max wait time was 100 return 0; } // measure time T TCNT0 = 1; loop_until_bit_is_set(PIN(REMOTE_PORT), REMOTE_BIT); T2 = TCNT0; // T is normally around 0E-10 hex = 15 -> 480 uS T2 = T2 * 2; // max time is 4T T4 = T2 * 2; for (i = 0; i < 32; i++) { TCNT0 = 1; while(1) { time = TCNT0; if (time > T4) return 0; // measure time on the lo flank if (bit_is_clear(PIN(REMOTE_PORT), REMOTE_BIT)) { tmp <<= 1; if (time >= T2) tmp += 1; break; } } // save command data as we go if( i == 15) code.bytes.high = tmp; if( i == 31) code.bytes.low = tmp; // syncronize - wait for next hi flank loop_until_bit_is_set(PIN(REMOTE_PORT), REMOTE_BIT); } return code.value; }
int main (void) { // disable unused functions for powersaving PRR = (1<<PRUSI) | (1<<PRUSART); DDRA = 0xff; change_clock_prescale( 0x01 ); // full speed 4MHz led_init_port(); // brownout @1.8V if device is started with insuficcient bats. if ( mcusr_mirror == (1<<BORF) ) { blink_red_powersave(); sleep_powerdown(); } uint8_t i=0; // selected pattern; uint8_t pwrhyst = 0; // switch on stepup, change frequency after short delay POWER_DDR |= (1<<POWER_PIN); POWER_PORT |= (1<<POWER_PIN); // bat comparator ACSR = (1<<ACBG); DIDR |= (1<<AIN1D); // init pwm counter led_init_timer(); key_init_timer_port(); // alive signal pled_on( (1<<PLED_RED) | (1<<PLED_GREEN) ); led_set_mode_r( 0x11, 0x11, 0 ); _delay_ms(50); led_set_mode_r( 0x00, 0x00, 0 ); _delay_ms(500); pled_off( (1<<PLED_RED) ); // check initial bat state for undervolt if ( (ACSR & (1<<ACO)) ) pwrhyst = 0xFF; sei(); for(;;) { for(uint8_t r=0; r< (*light_patterns[i]).rotate; r++) { // if there is a change to measure with leds off, then here // => check bat voltage if ( ACSR & (1<<ACO) ) { if ( pwrhyst == 0x0f ) { pled_on( 1<<PLED_RED); pled_off(1<<PLED_GREEN); } else { pwrhyst++; } } else { if ( pwrhyst == 0x00 ) { pled_on(1<<PLED_GREEN); pled_off( 1<<PLED_RED); } else { pwrhyst--; } } for(uint8_t p=0; p<(*light_patterns[i]).nr_elements; p++) { if ( key_press & ALL_KEYS ) { pwrhyst = 0; led_set_mode_r(0x00,0x00,0); if( get_key_short( 1<<KEY0 )) { r = 0; p = 0; i++; if ( i >= sizeof(light_patterns)/sizeof(light_patterns[0]) ) i = 0; } if( get_key_long( 1<<KEY0 )) { pled_off( (1<<PLED_RED) | (1<<PLED_GREEN) ); // wait for key release (with pullup=>1) loop_until_bit_is_set( KEY_PIN, KEY0 ); sleep_powerdown(); } } else { led_set_mode_r( (*light_patterns[i]->lp_elements)[p]->l12, (*light_patterns[i]->lp_elements)[p]->l34, r); key_wait_times_5ms( (*light_patterns[i]->lp_elements)[p]->duration ); } } } } }
/** * @brief Recieves one byte of data from the serial port (i.e. from the PC). * * @return byteReceived Character that was received on the USART. * */ unsigned char getCharDebug(void){ loop_until_bit_is_set(UCSR1A, RXC1); // wait until data is received char c = UDR1; // read char from serial return c; }
/** * @brief Sends one byte to the USART1 Tx pin (Transmits one byte). * * @param byteToSend The byte that is to be transmitted through USART1. * */ void putCharDebug(char byteToSend){ loop_until_bit_is_set(UCSR1A, UDRE1); // wait... UDR1 = byteToSend; // write char to PC }
uint8_t receiveByte() { loop_until_bit_is_set(UCSR0A, RXC0); /* Wait for incoming data */ return UDR0; /* return register value */ }
unsigned char SPI::xmit(unsigned char data) { SPDR = data; loop_until_bit_is_set(SPSR, SPIF); return SPDR; }
/* Send 1 byte data */ void tx_1byte_USART( unsigned char data ) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = data; }
void SPI_tradeByte(uint8_t byte) { SPDR = byte; /* SPI starts sending immediately */ loop_until_bit_is_set(SPSR, SPIF); /* wait until done */ /* SPDR now contains the received byte */ }
static void ADC_WaitConversionComplete() { loop_until_bit_is_set(ADCSRA,ADIF); }
int usart_getchar(FILE *stream) { loop_until_bit_is_set(UCSR0A, RXC0); return UDR0; }
void i2cWaitForComplete(void) { loop_until_bit_is_set(TWCR, TWINT); }
void uart_putchar(unsigned char c) { loop_until_bit_is_set(UCSRA, UDRE); UDR = c; //loop_until_bit_is_set(UCSRA, TXC); }
static int cput(char c, FILE *f) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = c; return 0; }
void send_char(uint8_t c) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = c; }
static int cget(FILE *f) { loop_until_bit_is_set(UCSR0A, RXC0); return UDR0; }
//============================================================================// // I2C START // //==========================================================================// void I2c_start(void) { //se habilita el two ,la condicion de estar y la int de transmicion completa TWCR=_BV(TWINT)|_BV(TWSTA)|_BV(TWEN); loop_until_bit_is_set(TWCR,TWINT); }
/* Simple and braindead, just like the AVR's SPI unit */ static uint8_t spi_exchange_byte(uint8_t output) { SPDR = output; loop_until_bit_is_set(SPSR, SPIF); return SPDR; }
char uart_getchar(void) { loop_until_bit_is_set(UCSR0A, RXC0); /* Wait until data exists. */ return UDR0; }
unsigned char UARTreceive(){ loop_until_bit_is_set(UCSR0A, RXC0); return UDR0; }
void uart_putchar(char c, FILE *stream) { loop_until_bit_is_set(UCSR0A, UDRE0); UDR0 = c; }
void USART_putc (char c) { loop_until_bit_is_set(UCSRA, UDRE); UDR = c; }