LPC2148 – Serial Communication Tutorial

Hi guys….. Today we are going to see LPC2148 Serial Communication Tutorial…UART (Universal Asynchronous Receiver Transmitter) are one of the basic interfaces which provide a cost effective simple and reliable communication between one controller to another controller or between a controller and PC.

Suggest To Read

If you are new to UART please go through our previous article about UART.

LPC2148 Serial Communication Tutorial

Coming to UART in LPC2148, the LPC214x series of MCUs have two UART blocks called UART0 and UART1. Each UART block is associated with two pins, one for transmission and the other for receiving.

In UART0 block, the TXD0 (Transmit) and RXD0 (Receive) pins in the device are P0.0 and P0.1 respectively. In case of UART1, the TXD1 and RXD1 pins are P0.8 and P0.9 respectively.

TX P0.0P0.8
RX P0.1P0.9

Both the UART modules are identical, except the UART1 block has an additional full modem interface. This includes all the pins for RS232 compatibility like flow control pins (CTS, RTS) etc. Both UART0 & UART1 blocks internally have a 16-byte FIFO (First In First Out) structure to hold the Rx and Tx data.  In this tutorial we will see only UART0. But If you understand the UART0 obviously you can play with UART1.

Registers Used For UART

This below table shows the registers used for UART.

UxTHRContains the data to be transmitted
UxRBRContains the recently received Data
UxLCR Controls the UART frame formatting(Number of Data Bits, Stop bits)
UxFDRControls the clock pre-scaler for the baud rate generation
UxDLL Least Significant Byte of the UART baud rate generator value
UxDLM Most Significant Byte of the UART baud rate generator value
UxLSR Provides status information on the UART0 TX and
RX blocks
UxFCRControls the operation of the UART0 Rx and TX FIFOs

Note: x-> 0/1 (UART0/UART1)

UxTHR (UART 0/1 Transmit  Holding Register)

The UxTHR is the top byte of the UART0/1 TX FIFO. The top byte is the newest character in the TX FIFO and can be written via the bus interface. The LSB represents the first bit to
The Divisor Latch Access Bit (DLAB) in UxLCR must be zero in order to access the
UxTHR. The UxTHR is always Write Only.

UxRBR (UART 0/1 Receiver Buffer Register)

The UxRBR is the top byte of the UART0/1 Rx FIFO. The top byte of the Rx FIFO contains the oldest character received and can be read via the bus interface. The LSB (bit 0) represents the “oldest” received data bit. If the character received is less than 8 bits, the unused MSBs are padded with zeroes.

The Divisor Latch Access Bit (DLAB) in UxLCR must be zero in order to access the
UxRBR. The UxRBR is always Read Only.

UxLCR (UART 0/1 Line Control Register)

The Line Control Register is used to set the format of the data which is transmitted or received. The value or settings in this register configure the UART0/1 block. As this is an 8-bit register. There are several parameters configured through this register such as word length, stop bit, parity enable, parity select, break control, divisor latch access bit. This register setting plays important role while initializing UART0/1 before using it.

UxFDR (Fractional Divider Register)

This register is used to set the prescale value for baud rate generation. The input clock is the peripheral clock and output is the desired clock defined by this register. This register actually holds to different 4-bit values (a divisor and a multiplier) for prescaling which are:

Important: If the fractional divider is active (DIVADDVAL > 0) and DLM = 0, the value of the DLL register must be 3 or greater

DIVADDVAL: This is the Prescale Divisor value. If this value is 0 then fractional baud rate generator have no effect on UART0/1 baud rate.

MULVAL: This defines Prescale Multiplier value. Even if fractional baud rate generator is not used the value in this register must be more than or equal to ‘1’.

UxDLL & UxDLM (UART 0/1 Divisor Latch registers)

These are standard UART0/1 baud rate generator divider registers. Each of this register holds 8-bit values. Together these registers form a 16-bit divisor value which will be used for baud rate generation. UxDLM holds the upper 8-bits and UxDLL holds the lower 8-bits and the formation is “[UxDLM:UxDLL]“. Since these form a divisor value and division by zero is invalid, the starting value for UxDLL is 0x01 (and not 0x00) i.e the starting value in combined formation is “[0x00:0x01]” i.e 0x0001. Please keep this in mind while doing baud-rate calculations. In order to access and use these registers properly, DLAB bit in UxLCR must be first set to 1.

UxLSR (UART 0/1 Line Status Register)

The Line Status Register gives us the information about the RX and TX blocks in UART0/1.

UxFCR (UART 0/1 FIFO Control Register)

The FIFO Control Register controls the operation of the RX and TX FIFOs in UART0/1.

Baud Rate Calculation

By using this below formula we will calculate the Baud Rate.

Example Calculation 1 (Baud Rate 9600 And PCLK = 60MHz)

First Assume U0DLM = 0 , DIVADDVAL = 0 & MULVAL = 1 with PCLK = 60 x 106 Hz

Substitute into that above formula.

U0DLL = 60000000/(16*9600)

U0DLL = 390.625 (~390)

Now the U0DLL value is greater than 255. So we cant store it into this U0DLL Register. Because it is 8-but register.

Now we will change our assumed values.

Now assume U0DLM =1

9600 = 60000000/(16*(256+U0DLL))

4096+16U0DLL = 60000000/9600

16U0DLL = 6250 - 4096

U0DLL = 2154/16

U0DLL = 134.625 (~135)

This U0DLL (135) gives 9591 Baud Rate. This is less than 9600. But we can take this value. Because less difference only.


PCLK = 60MHz

U0DLL = 135



U0DLM = 1

Baud Rate = 9600

Example Calculation 2 (Baud Rate 9600 And PCLK = 30MHz)

First Assume U0DLM = 0 , DIVADDVAL = 0 & MULVAL = 1 with PCLK = 30 x 106 Hz

U0DLL = 30000000/(16*9600)

U0DLL = 195.3125 (~195)

This U0DLL (195) gives 9615.38 Baud Rate. This is greater than 9600. But we can take this value. Because less difference only.

PCLK = 30MHz

U0DLL = 195



U0DLM = 0

Baud Rate = 9600

Note : 9600 is pretty famous Baud rate in embedded projects. Some of the standard Baud rates that can be used are : 2400 , 4800 , 7200 , 9600 , 14400 , 19200 , 28800 , 38400 , 57600 , 115200 , 230400 , etc..

Programming Explanation

Initializing UART

Below are the steps for configuring the UART0.

  1. .Configure the GPIO pin for UART0 function using PINSEL register.
  2. .Configure LCR for 8-data bits, 1 Stop bit, Disable Parity and Enable DLAB.
  3. .Update the DLM,DLL with the calculated values.
  4. .Finally clear DLAB to disable the access to DLM,DLL.

After this, the UART will be ready to Transmit/Receive Data at the specified baudrate.

Transmit (TX)

  1. Wait till the previous char is transmitted ie. till THRE becomes high in U0LSR Register.
  2. Load the new char to be transmitted into U0THR.

Receive (RX)

  1. Wait till the a char is received ie. till RDR becomes high in U0LSR.
  2. Copy the received data from receive buffer(RBR).

Code 1

This is like a echo program. Whatever typing it will resend via UART. Here PCLK = 60MHz, BaudRate=9600.

Code 2

This is also the same echo program. But Here PCLK = 30MHz, BaudRate=9600.

That is all guys…..You can also try this with UART1. If you have any doubt please let us know.

3 2 votes
Article Rating
Notify of

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Newest Most Voted
Inline Feedbacks
View all comments
Joshua Karumanchi
Joshua Karumanchi
March 23, 2018 2:07 PM

Excellent work. Excellent explanation, very easy to understand. Thank you.

Rahul Rajan
Rahul Rajan
April 28, 2018 4:28 AM

why u are putting pinsel as 0x05 in ur code

EmbeTronicx India
EmbeTronicx India
Reply to  Rahul Rajan
April 28, 2018 8:02 AM

We were using UART0. So we want that P0.0 and P0.1 to be act as Tx and Rx respectively. If we want to change its functionality, then we need to set the proper value to the PINSEL register. Please refer https://embetronicx.com/tutorials/microcontrollers/lpc2148/lpc2148-gpio-tutorial-led-interfacing/#PINSEL0.

Dayanand Killedar
Dayanand Killedar
April 4, 2019 12:39 PM

What will be the output for this. ? and how to check .?

EmbeTronicx India
EmbeTronicx India
Reply to  Dayanand Killedar
April 11, 2019 9:14 AM

Hi Dayanand Killedar,

This is echo program. When you type any letter in the keyboard, it will print those in the UART terminal.


Dayanand Killedar
Dayanand Killedar
Reply to  EmbeTronicx India
April 11, 2019 9:23 AM

Thank your for reply.. But still i am facing some issue. The issue is if i press the ‘d’ key it’s printing ‘f’ and several keys are behaving same.

Would love your thoughts, please comment.x
%d bloggers like this: