From: chris v. <chr...@go...> - 2009-03-30 08:34:36
|
Hi, chew jin ling schrieb: > can anyone help me in this adc to RS232? i 'm weak at write a program > in microcontroller. > Anyone have done it be4? > i need it urgently > you need to be a litte more specific: - what CPU, crystal speed and baudrate do you want/have ? - how often should a value be sent, and which channel (or channels) do you need ? - do you want your values to be transmitted in ASCII (readable with a terminal) or plain binary values ? basically, all you need is in the modularEEG basic firmware. I attached a little ATmega8-firmware that transmits the value of ADC channel 0 one time per second in a human-readable form to the UART. (you need an rs232 converter or/and a UART/RS232 to USB solution to attach this to a PC). select other channels using ADMUX, and change the speed by changing the prescaler (ADCSRA) or (cnt==28) in the timer ISR. regards, chris. /* Send_ADC.c Usage of the Analog Digital Converter This program sends ADC values of channel 0 at a slow sampling rate (1 Hz) over the UART. Following interrupt service routines are used: Timer0_OVF_vect : initiates the AD-conversion at the sampling rate ADC_vect : reads in a sample value from the ADC channel 0 and initiales UART Transmission UART_UDRE_vect : sends the data over UART 115200 baud, 8N1 is the transmission setting for the USART Use a terminal program on the PC to verifiy program operation. The crystal frequency (XTAL) is 7372800 Hz */ #include <avr/io.h> #include <avr/interrupt.h> #include <inttypes.h> #define F_CPU 7372800 // our crystal frequency unsigned char TXBuf[6]; // Buffers for sending ADC-values over UART void inttostring (unsigned int value, unsigned char * str) { int i; for (i=3;i>=0;i--) // value has max. 10 bits, will fit into four decimal digits { str[i] = '0' + value % 10; // extract ones (modulo 10) value=value / 10; // shift to right } str[4]='\r';str[5]='\n'; str[6]=0; // add newline and string termination } ISR(TIMER0_OVF_vect) // Sampling timer (timer 0) interrupt servie routine { // TCNT0= RELOAD; // we do not reload the timer counter: // timer interrupt is generated after 256 counter cycles static unsigned int cnt=0; cnt++; if (cnt==28) // this slows down the sampling rate { // to F_CPU / 1024 / 256 / 28 = 1 Hz cnt=0; PORTD ^= (1<<5); // toggle led on the Eval board UCSRB &= ~(1<<UDRIE); // Ensure UART IRQ's are disabled. ADMUX=0; // Select ADC channel 0 ADCSRA |= (1<<ADIF); // Reset any pending ADC interrupts ADCSRA |= (1<<ADSC); // Start the ADC } } ISR(ADC_vect) // AD-conversion-complete interrupt service routine { unsigned char low,high; unsigned int value; PORTD ^= (1<<6); // toggle Led2 on the eval board low = ADCL; // read ADC value (low byte first !) high = ADCH; // read ADC value high byte value = (high<<8) + low; // calculate integer value inttostring(value, TXBuf); // transform into ASCII-string and store into transmit buffer // Hand over to ISR USART_UDRE by starting // the UART transfer and enabling UDR IRQ's. UDR= TXBuf[0]; // TXBuf[0]; UCSRB |= (1<<UDRIE); // enable USART Transmission Register empty interrupts } ISR (USART_UDRE_vect) // UART Data Transmission Register empty interrupt service routine { static int pos=1; if (TXBuf[pos]) UDR = TXBuf[pos++]; // Send next byte else { pos=1; UCSRB &= ~(1<<UDRIE); } // Disable SIG_UART_DATA interrupts. } void init_uart (unsigned long baudrate) { unsigned int ubrr = (F_CPU/16/baudrate)-1; UBRRH = (unsigned char)(ubrr>>8); // Set baud rate by filling high and UBRRL = (unsigned char)(ubrr&0xff); // low byte of the Baud Rate Register UCSRB = ( 1<<TXEN | 1<<RXEN ); // Enable receiver and transmitter UCSRC = ( 1<<URSEL | 1<<UCSZ1 | 1<<UCSZ0 ); // select character size, stop and parity bits: 8N1 } int main( void ) { init_uart ( 115200 ); // Initialize the UART for 115200, 8N1 DDRD = (1<<5) | (1<<6); // led1 ánd led2 on PD5 and PD6: output PORTD |= (1<<5); // switch on led1 TXBuf[4]='\r';TXBuf[5]='\n'; TXBuf[6]=0; // prepare transmit buffer //Initialize the ADC // Timings for sampling of one 10-bit AD-value: // prescaler = 64 (ADPS2 = 1, ADPS1 = 1, ADPS0 = 0) // ADCYCLE = XTAL / prescaler = 115200Hz or 8.68 us/cycle // 14 (single conversion) cycles = 121.5 us (8230 samples/sec) // 26 (1st conversion) cycles = 225.69 us ADCSRA = (1<<ADPS2) | (1<<ADPS1); // Prescaler = 64, free running mode = off, interrupts off. ADCSRA |= (1<<ADIF); // Reset any pending ADC interrupts ADCSRA |= (1<<ADEN); // Enable the ADC ADCSRA |= (1<<ADIE); // Enable ADC interrupts. // The first conversion will start after ADSC is set in the timer interrupt //Initialize timer 0 TCNT0 = 0; // Clear the Timer 0 Counter TCCR0 = 5; // Set the prescaler to Frequency = clk / 1024 TIMSK = (1<<TOIE0); // Enable the interrupts. sei(); // enable global interrupts while (1) ; // wait for interrupts, this is an event-driven program, } > ------------------------------------------------------------------------ > > ------------------------------------------------------------------------------ > > ------------------------------------------------------------------------ > > _______________________________________________ > Openeeg-list mailing list > Ope...@li... > https://lists.sourceforge.net/lists/listinfo/openeeg-list > Go to the above address to change your > subscription options, e.g unsubscribe. > |