Hi Jeff
The Mask register (UART block + 0x14) is writable to set and clear the mask bits.
When this address is read it doesn't return the mask bits which have been set but instead returns the Status of the interrupt bits. This means that a read and write are at the same location but the actual register accessed is different. This means that instructions like x |= y or x &+ ~y; will not work correctly.
I don't know why you are seeing an initial interrupt. I didn't hav ethis effect. Below I have copied the initialisation routine which I use - you should get the idea and maybe see something which could help explain the difference.
Regards
Mark
==========================================================
// User configuration
QUEUE_HANDLE SerialPortID;
TTYTABLE tInterfaceParameters; // table for passing information to driver
tInterfaceParameters.ucChannel = 1; // use serial channel 1 on evaluation board / target
tInterfaceParameters.ucSpeed = temp_pars->temp_parameters.ucSerialSpeed; // baud rate
tInterfaceParameters.Rx_tx_sizes.RxQueueSize = RX_BUFFER_SIZE; // input buffer size
tInterfaceParameters.Rx_tx_sizes.TxQueueSize = TX_BUFFER_SIZE; // output buffer size
tInterfaceParameters.cTask_to_wake = OWN_TASK; // wake self when messages have been received
tInterfaceParameters.ucFlowHighWater = temp_pars->temp_parameters.ucFlowHigh;// set the flow control high and low water levels in %
tInterfaceParameters.ucFlowLowWater = temp_pars->temp_parameters.ucFlowLow;
tInterfaceParameters.usConfig = temp_pars->temp_parameters.usSerialMode;
SerialPortID = fnOpen( TYPE_TTY, FOR_I_O, &tInterfaceParameters ); // open or change the channel with defined configurations
... the following is called somewhere down the line
// configure the SCI hardware
//
void fnConfigSCI(unsigned char ucChannel, TTYTABLE *pars)
{
unsigned char *ucReg = fnSelectChannel(ucChannel); // set register pointer to corresponding block (command register)
unsigned short usSpeed;
unsigned char ucBits = UART_8_BIT;
switch (ucChannel) { // First configure the GPIO pins for UART use
case 0:
PUAPAR |= 0x05; // Set TX/RX on UA
IC_ICR_0_13 = (INTERRUPT_LEVEL_5 | INTERRUPT_PRIORITY_1); // define interrupts level and priority
IC_IMRL_0 &= ~(UART0_PIF_INT_L | MASK_ALL_INT); // unmask interrupt source
break;
case 1:
PUBPAR |= 0x05; // Set TX/RX on UB
IC_ICR_0_14 = (INTERRUPT_LEVEL_5 | INTERRUPT_PRIORITY_2); // define interrupts level and priority
IC_IMRL_0 &= ~(UART1_PIF_INT_L | MASK_ALL_INT); // unmask interrupt source
break;
case 2:
PUCPAR |= 0x03; // Set TX/RX on UB
IC_ICR_0_15 = (INTERRUPT_LEVEL_5 | INTERRUPT_PRIORITY_3); // define interrupts level and priority
IC_IMRL_0 &= ~(UART2_PIF_INT_L | MASK_ALL_INT); // unmask interrupt source
break;
default:
return; // Invalid UART channel
}
*ucReg = UART_RESET_RX; // reset rx and tx and ensure internal command pointer at start
*ucReg = UART_RESET_TX;
*ucReg = UART_RESET_CMD_PTR;
ucReg -= (UCR_0_OFFSET - USR_UCSR_0_OFFSET); // set to clock select register
*ucReg = (UART_RX_BUS_CLK | UART_TX_BUS_CLK); // Use internal bus clock
ucReg += (UBG1_0_OFFSET - USR_UCSR_0_OFFSET); // Move to BRG register
switch (pars->ucSpeed) {
case SERIAL_BAUD_300:
usSpeed = BUS_CLOCK/300/32; // set 300
break;
case SERIAL_BAUD_600:
usSpeed = BUS_CLOCK/600/32; // set 600
break;
case SERIAL_BAUD_1200:
usSpeed = BUS_CLOCK/1200/32; // set 1200
break;
case SERIAL_BAUD_2400:
usSpeed = BUS_CLOCK/2400/32; // set 2400
break;
case SERIAL_BAUD_4800:
usSpeed = BUS_CLOCK/4800/32; // set 4800
break;
case SERIAL_BAUD_9600:
usSpeed = BUS_CLOCK/9600/32; // set 9600
break;
case SERIAL_BAUD_14400:
usSpeed = BUS_CLOCK/14400/32; // set 14400
break;
default: // if not valid value set this one
case SERIAL_BAUD_19200:
usSpeed = BUS_CLOCK/19200/32; // set 19200
break;
case SERIAL_BAUD_38400:
usSpeed = BUS_CLOCK/38400/32; // set 38400
break;
case SERIAL_BAUD_57600:
usSpeed = BUS_CLOCK/57600/32; // set 57600
break;
case SERIAL_BAUD_115200:
usSpeed = BUS_CLOCK/115200/32; // set 115200
break;
case SERIAL_BAUD_230400:
usSpeed = BUS_CLOCK/230400/32; // set 230400
break;
}
*ucReg = (unsigned char)(usSpeed >> 8);
ucReg += (UBG2_0_OFFSET - UBG1_0_OFFSET);
*ucReg = (unsigned char)(usSpeed); // Baud rate set
ucReg -= (UBG2_0_OFFSET - UMR1_2_0_OFFSET); // set to Mode register
if (pars->usConfig & CHAR_7) {
ucBits = UART_7_BIT;
}
if (pars->usConfig & (RS232_ODD_PARITY | RS232_EVEN_PARITY)) {
if (pars->usConfig & RS232_ODD_PARITY) {
*ucReg = (UART_WITH_PARITY | ucBits | ODD_PARITY); // 7/8 bits - odd parity
}
else {
*ucReg = (UART_NO_PARITY | ucBits); // 7/8 bits - even parity
}
}
else {
*ucReg = (ucBits); // 7/8 bits - no parity
}
if (pars->usConfig & TWO_STOPS) { // The mode register 2 has been selected by previous write
*ucReg = UART_TWO_STOP;
}
else if (pars->usConfig & ONE_HALF_STOPS) {
*ucReg = UART_ONE_HALF_STOP;
}
else {
*ucReg = UART_ONE_STOP;
}
// Enable receiver (tx enabled when used)
ucReg = fnSelectChannel(ucChannel); // set register pointer to corresponding block (command register)
*ucReg = UART_RX_ENABLE; // enable RX interrupt and Rx
ucReg += (UIMR_UISR_0_OFFSET - UCR_0_OFFSET);
ucEnabledState[ucChannel] |= UART_RXRDY_MASK; // we must make a backup since the register can not be read
*ucReg = ucEnabledState[ucChannel];
}
=====================================================================