123

Dependencies:   mbed

Fork of LG by igor Apu

DeviceUserPort.c

Committer:
Diletant
Date:
2016-06-05
Revision:
167:bedc0a9d559a
Parent:
161:efd949e8d536
Child:
177:672ef279c8e0

File content as of revision 167:bedc0a9d559a:

#include "Device.h"

extern Device device;
extern unsigned int SystemCoreClock1;

void InitUserPortDefaultSettings(void) {
  device.controller.uart[1].settings.baudRate = 38400;
}

void InitUserPortState(void) {
}

void DeviceStartUserPort(void)
{ 
  uint32_t Fdiv;
  uint32_t pclkdiv, pclk;

  LPC_PINCON->PINSEL4 &= ~0x0000000F;
  LPC_PINCON->PINSEL4 |= 0x0000000A;  //Enable RxD1 P2.1, TxD1 P2.0
    
  //By default, the PCLKSELx value is zero, thus, the PCLK for all the peripherals is 1/4 of the SystemFrequency.
  //Bit 8,9 are for UART1
  pclkdiv = (LPC_SC->PCLKSEL0 >> 8) & 0x03;
  switch ( pclkdiv ) {
      case 0x00:
      default:
        pclk = SystemCoreClock1/4;
        break;
      case 0x01:
        pclk = SystemCoreClock1;
        break; 
      case 0x02:
        pclk = SystemCoreClock1/2;
        break; 
      case 0x03:
        pclk = SystemCoreClock1/8;
        break;
  }
  
  device.controller.uart[1].state.LCR = 0x83;
  LPC_UART1->LCR = device.controller.uart[1].state.LCR;      //8 bits, no Parity, 1 Stop bit
  
  Fdiv = ( pclk / 16 ) / device.controller.uart[1].settings.baudRate;   /*baud rate */
  
  device.controller.uart[1].state.DLM = Fdiv / 256;
  LPC_UART1->DLM = device.controller.uart[1].state.DLM;
  
  device.controller.uart[1].state.DLL = Fdiv % 256;
  LPC_UART1->DLL = device.controller.uart[1].state.DLL;
  
  device.controller.uart[1].state.LCR = 0x03;
  LPC_UART1->LCR = device.controller.uart[1].state.LCR;      //DLAB = 0
  
  device.controller.uart[1].state.FCR = 0x03;
  LPC_UART1->FCR = device.controller.uart[1].state.FCR;      //Enable and reset TX and RX FIFO.

  //Uncomment to use interrupts
  //NVIC_EnableIRQ(UART1_IRQn);
  //LPC_UART1->IER = IER_RBR | IER_THRE | IER_RLS;  /* Enable UART1 interrupt */
}

void DeviceUserPortReceive(void){
  if (LPC_UART1->LSR & 0x01) {
    device.user.request.buffer.data[device.user.request.buffer.end] = LPC_UART1->RBR;
    device.user.request.buffer.end = (device.user.request.buffer.end + 1) % InputBufferSize;
    device.user.request.buffer.empty = 0;
    device.user.decoder.canceled = 0; //Clear decode canceled flag
  }
}

void DeviceUserPortTransmit(void){
  if (device.user.response.ready) {
    if ((device.user.response.type == RESPONSE_DELAYED) && (!device.user.response.triggered)) return;
    
    if (device.user.response.buffer.position < device.user.response.buffer.count) {
      if (LPC_UART1->LSR & 0x20) {
        LPC_UART1->THR = device.user.response.buffer.data[device.user.response.buffer.position];
        device.user.response.buffer.position++;
        if (device.user.response.buffer.position == device.user.response.buffer.count){
          device.user.response.ready = 0;
          if (device.user.response.type == RESPONSE_PERIODIC) {
            device.user.response.enabled = 1; //next response required
          }
          device.user.response.buffer.count = 0;
          device.user.response.buffer.position = 0;
        }
      }
    }
  }
}

//Not used
/*
#define IER_RBR     0x01
#define IER_THRE    0x02
#define IER_RLS     0x04

#define IIR_PEND    0x01
#define IIR_RLS     0x03
#define IIR_RDA     0x02
#define IIR_CTI     0x06
#define IIR_THRE    0x01

#define LSR_RDR     0x01
#define LSR_OE      0x02
#define LSR_PE      0x04
#define LSR_FE      0x08
#define LSR_BI      0x10
#define LSR_THRE    0x20
#define LSR_TEMT    0x40
#define LSR_RXFE    0x80

void UART1Send(void)
{
  uint8_t pos = 0;
  while (device.host.response.buffer.count != pos ) {
    //THRE status, contain valid data
    while ( !(device.host.port.TxEmpty & 0x01) ); 
    LPC_UART1->THR = device.host.response.buffer.data[pos];
    device.host.port.TxEmpty = 0; //not empty in the THR until it shifts out
    pos++;
  }
  device.host.response.buffer.count = 0;
}

//Not used 
__irq void UART1_IRQHandler (void)
{
  uint8_t IIRValue, LSRValue;
  uint8_t Dummy = Dummy;
    
  IIRValue = LPC_UART1->IIR;
    
  IIRValue >>= 1;            //skip pending bit in IIR
  IIRValue &= 0x07;          //check bit 1~3, interrupt identification
  if ( IIRValue == IIR_RLS ) // Receive Line Status
  {
    LSRValue = LPC_UART1->LSR;
    //Receive Line Status
    if ( LSRValue & (LSR_OE|LSR_PE|LSR_FE|LSR_RXFE|LSR_BI) )
    {
      //There are errors or break interrupt
      //Read LSR will clear the interrupt
      device.host.port.status = LSRValue;
      Dummy = LPC_UART1->RBR;//Dummy read on RX to clear interrupt, then bail out
      return;
    }
    if ( LSRValue & LSR_RDR )//Receive Data Ready
    {
      //If no error on RLS, normal ready, save into the data buffer.
      //Note: read RBR will clear the interrupt
      device.host.request.buffer.data[device.host.request.buffer.end] = LPC_UART1->RBR;
      device.host.request.buffer.end = (device.host.request.buffer.end + 1) % InputBufferSize;
    }
  }
  else if ( IIRValue == IIR_RDA )   //Receive Data Available
  {
    device.host.request.buffer.data[device.host.request.buffer.end] = LPC_UART1->RBR;
    device.host.request.buffer.end = (device.host.request.buffer.end + 1) % InputBufferSize;
  }
  else if ( IIRValue == IIR_CTI )   //Character timeout indicator
  {
    //Character Time-out indicator
    device.host.port.status |= 0x100; //Bit 9 as the CTI error
  }
  else if ( IIRValue == IIR_THRE )    //THRE, transmit holding register empty
  {
    //THRE interrupt
    LSRValue = LPC_UART1->LSR;        //Check status in the LSR to see if valid data in U0THR or not
    if ( LSRValue & LSR_THRE )
    {
      device.host.port.TxEmpty = 1;
    }
    else
    {
      device.host.port.TxEmpty = 0;
    }
  }
}*/