All, I'm a newbie to SDCC. So, I'm not sure if I'm asking for help in the
proper way. If I am, sorry.
Thanks for any suggestions you may have!!
I've been working on converting a simple C program and compiling it using
SDCC instead of Keil C. The program uses the AT89C51 watchdog timer, the
serial port, and blinks an LED. When compiled using Keil, the program
works perfectly. The program simply outputs 21 exes ('X') in response to
receiving a 'D' from a notebook PC. To compile the program using SDCC, I
first converted the AT89C51xDS header file from Atmel so that sfr and sbit
lines had the correct syntax. I also toggled the the LED bit using !
rather than ~. Finally, I used packihx to create the hex file.
The program responds to receiving a 'D' from the notebook PC, but it only
transmits 8 characters instead of 21.
Any suggestions? Thanks for your help in advance!!
With apologies for the clutter, I've attached the code below:
#define UART_TXD_DELAY_COUNT 10 // transmit delay cnt => 40*6/30MHz =
8mics/cnt for 115200 bps
#define UNIT_TIMER_RELOAD 0x06 //250 mac. cycles/super timer cnt or 50mics
res. at 30MHz
#define MAX_WAIT 4400 //4400*50mics=220ms conversion time at 30 mHz
#define LED0_PORT_BIT P2_0 // setup/power and while(1) loop cycle
flip-flop LED
#define WATCHDOG_ON // comment this line out to turn off watchdog timer
for debugging
#include "AT89C51xD2SDCC.h" // From Atmel: definition for the register
names of the AT89C51xD2 chips
unsigned long data g_ul_clock_count=0;
unsigned long data main_clock_count=0;
// Interrupt Vectors and Interrupt Support Functions
// timer 0 super clock count interrupt routine
void timer_0_interrupt(void) interrupt 1 using 3
{
TF0=0; // reset interrupt flag
if(!(~(((unsigned char data *)(&g_ul_clock_count))[3])))
if(!(~(((unsigned char data *)(&g_ul_clock_count))[2])))
if(!(~(((unsigned char data *)(&g_ul_clock_count))[1])))
if(!(~(((unsigned char data *)(&g_ul_clock_count))[0])))
g_ul_clock_count=0;
g_ul_clock_count++;
}
// UART Serial Port Interrupt 4 Function (input: RxD)(output: TxD)
// with SBUF (serial port) array output (256 bytes max) for interrupt 4
void UART_interrupt(void) interrupt 4 using 2
{
unsigned char UART_data=0;
unsigned char array_index=0;
unsigned long delay_index=0;
if(RI==1) // if reception occurs
{
RI=0; // clear reception flag for next reception
UART_data=SBUF; // read receive data
if(UART_data=='D')
{
for(array_index=0; array_index<=20; array_index++)
{
SBUF='X'; // send each byte to UART
delay_index=0;
while(delay_index<UART_TXD_DELAY_COUNT) delay_index++;
}
}
} else TI=0; // if emission occurs, clear emission flag for next emission
#ifdef WATCHDOG_ON
WDTRST=0x1E; // reset watchdog sequence
WDTRST=0xE1; // reset watchdog sequence
#endif
}
// Initialize relevant system devices and defaults
void setup_ThermoMIC(void)
{
// CPU Clock in X2 mode (peripherals are also at X2 or 6 clocks per mac.
cyc.)
CKCON0|=0x01;
// UART settings using the internal baud rate generator
PCON|=0x80; // SMOD1=1, selects double baud rate mode for UART in mode
1,2,3
SCON=0x50; // UART in mode 1 (8-bit), REN=1
BDRCON&=0xEC; // BRR=0, SRC=0
BDRCON|=0x0E; // TBCK=1, RBCK=1, SPD=1
BRL=0xF0; // 115200 bps at 30MHz in X2 mode
// Watchdog time-out setup
// For mode X1: 12 clock periods per machine cycle
// For mode X2: 6 clock periods per machine cycle
WDTPRG|=0x07; // (2^(14+0x07)-1) machine cycles [0x07=MAX] or 0.419s @
Fosc=30MHz & X2
// setup timer 0 in mode 2 with auto-reload & software gate
// to create a 100 microsec unit time count
TMOD&=0xF0; // timer 0 mode 2 with software gate
TMOD|=0x02; // GATE0=0, C/T0#=0, M10=1, M00=0
TH0=UNIT_TIMER_RELOAD; // reload value
TL0=UNIT_TIMER_RELOAD; // init value
IPL0|=0x02; // set timer 0 interrupt priority to 3 (highest)
IPH0|=0x02; // set timer 0 interrupt priority to 3 (highest)
// after setups are done then enable interrupts and start peripherals
ES=1; // enable UART serial port interrupt
ET0=1; // enable timer 0 interrupt
EA=1; // enable all interrupts (global mask)
TR0=1; // run timer 0
SPCON|=0x40; // run SPI
BDRCON|=0x10; // run internal baud rate generator
}
// watchdog restart sequence
void restart_watchdog(void)
{
#ifdef WATCHDOG_ON
WDTRST=0x1E;
WDTRST=0xE1;
#endif
}
// superclock count reset
void reset_superclock(void)
{
ET0=0; // disable timer 0 interrupt
g_ul_clock_count=0;
ET0=1; // enable timer 0 interrupt
}
// reset program clock count vars
void reset_clock_counts(void)
{
main_clock_count=0;
}
///////////////////////////////////////////////////////////////////////////////
// Main entry point of looping controller program
void main(void)
{
unsigned char indexer=0;
unsigned char check_flag=0;
// setup functions
setup_ThermoMIC();
reset_superclock();
restart_watchdog();
LED0_PORT_BIT=~1;
// primary loop
while(g_ul_clock_count<main_clock_count) { restart_watchdog(); } // wait
if early
main_clock_count=g_ul_clock_count+MAX_WAIT;
while(1)
{
LED0_PORT_BIT=!LED0_PORT_BIT;
if(g_ul_clock_count>0x7FFFFFFF)
{
reset_superclock();
reset_clock_counts();
}
while(g_ul_clock_count<main_clock_count) { restart_watchdog(); } // wait
if early
main_clock_count=g_ul_clock_count+MAX_WAIT;
}
}
Gary D. Sides, Ph.D.
Phone: 205-307-6695 Cell: 205-222-2757
[EMAIL PROTECTED]-------------------------------------------------------------------------
This SF.net email is sponsored by: Splunk Inc.
Still grepping through log files to find problems? Stop.
Now Search log events and configuration files using AJAX and a browser.
Download your FREE copy of Splunk now >> http://get.splunk.com/
_______________________________________________
Sdcc-user mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/sdcc-user