0% found this document useful (0 votes)
34 views

Microcontroller Basics - A Comprehensive Guide For Beginners

MicrocontroLLers

Uploaded by

Piney Martin
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
34 views

Microcontroller Basics - A Comprehensive Guide For Beginners

MicrocontroLLers

Uploaded by

Piney Martin
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 53

Microcontroller Basics – A

Comprehensive Guide for


Beginners
By / / /

Sharing is Caring!

Do you think you can keep up with the innovations in


technology without using microcontrollers?

If your answer is a “BIG YES”, you are certainly going in the


wrong direction. Why?

Today, 17.6 billion devices around the world use


microcontrollers for consumer-targeted applications.

More importantly, this number is only going to increase


because of a rising trend in favor of microcontroller-based
IoT devices. Not Impressed? Let me put it in another
perspective.

A typical home in a developed country is likely to have 3


dozen microcontroller devices. Moreover, a mid-range
auto-mobile has about 30 microcontrollers.

Ranging from miniature devices (digital thermometers,


smartwatches, calculators, mobile phones, cameras) to
high-end consumer electronics (microwave ovens, washing
machines, televisions, refrigerators, vending machines), you
will almost always find a tiny microcontroller peeking at you
from the inside.

In 2019, the global microcontroller market size was valued at


$16.49 billion which is expected to hit $42.19 billion by
2027. Did that change your mind?

If no, my struggle will surely make you reconsider your


stance. Early on in my professional career, I tried to ignore
microcontrollers in about every aspect. Guess, what it got
me?

Three straight-off rejections during interviews for embedded


systems programmer. Another rejection for teaching
assistant position, where I was told “Your Electrical
Engineering is Weak!”. Well, you don’t want that? Or, do
you?

If you don’t want to end up like me, you need to start


learning about microcontrollers.

In this article, I will provide you with an ultimate Introduction


of Microcontroller Basics. This will help you get started with
microcontrollers right away.

Essentially, I will try to answer every question you may have


regarding the working of microcontrollers, such as:

What is a Microcontroller?
Components of Microcontroller
How Microcontroller Works?
Microcontroller Architecture
Microcontroller Peripherals
Difference between Microcontroller and Microprocessor
Microcontroller Applications

Disclaimer: I will be using exciting analogies and


interactive animations throughout the article, so you
won’t get bored. For those who think “Technology is
Boring Anyway”, try me and let me know of your
enjoyment score on a scale of 1-10.

Let’s get started then…

What is a Microcontroller
A “Microcontroller Unit” or “MCU” is an Integrated Circuit
(IC) that effectively controls electronic devices within a large
embedded system.

In simple terminology, a microcontroller takes input from a


user, processes the input signals, and then displays the
output as per the user demand.

A microcontroller is a combination of two words: “micro”


means small, and “controller” means an enhanced ability to
perform control functions.

This does not mean that you try to control your Spouse using
a microcontroller. Well, even if you do, don’t hold me
responsible for any repercussions.

Jokes apart, a microcontroller is a control device which


enables a friendly interaction between humans and
electronic devices.

You pour coffee ingredients in a coffee maker, and it helps


prepare a soothing coffee for you. With glucose meter, a
microcontroller helps analyse your blood glucose levels and
displays them on an LCD Display.

It helps thermostat in your Refrigerator to maintain a


freezing temperature. You can also set a timer on your
Washing Machines while doing your laundry. The
microcontroller also helps you capture, edit, and store
beautiful photos of your trips via Digital Cameras.

With microcontrollers, possibilities are endless. Most of the


time, you are using a microcontroller-driven device but you
are not fully aware of that. Now, how amazing is that!

Microcontroller Basics

Some of you may be thinking,” Why microcontrollers were


created when Personal Computers could have performed
such tasks with much better speed and accuracy?”

Your perspective is correct as far as the speed/accuracy


aspect is concerned. But look, here’s the thing…

You cannot deploy personal computers everywhere for


miniature tasks, simply because that would be too costly
and demand much greater space than a microcontroller
would, otherwise.

Your personal computer can run Word Editor, a Graphics


Design application, and a bunch of other resource-intensive
software, all at the same time.

But, why would you want to use such a powerful computer


only to detect your car and then open a simple garage door?
That would be a huge waste of computer resources, your
hard-earned money, and electrical power.

So, what’s the solution? Well, this is where Microcontrollers


say Hi to you!

Microcontrollers are highly application-oriented. You can


easily program a microcontroller to perform a dedicated task
for a specific application, that too at a reduced cost and
power requirements.

For a typical application, a personal computer would require


50 Watts. But a microcontroller can implement the same
task using merely 50 milliwatts. Does that ring any bells?

Moreover, a microcontroller can operate in extreme


conditions i.e., inside a hot car engine, in space satellites,
and chilly weather of Antarctica. Personal computers,
however, need to be ruggedized for such harsh
environments.

Microcontroller Components
Bus Bus
EEPROM/ DAC
Central Processing Unit (CPU)
FLASH
Arithmetic Logic Internal ADC
RAM Unit (ALU) Clock
Timers
External Crystal
Control Unit (CU) Registers
Oscillator (Clock) I/O Ports

Interrupt Controller EtherCAT

UART SPI I2C USB CAN

Schematic Diagram of Microcontroller Components (Copyrights: Embedded Robotics)

Until now, you must have understood the importance of


using a microcontroller within your next project. But we all
need to understand the technical aspects of anything we
intend to use, don’t we?

So, fasten your seatbelts now. I am going to dive into the


nitty-gritty details of the microcontroller.
Microcontroller Components
Until now, I hope that you have clearly understood ‘what is a
microcontroller’, and why do we even need microcontrollers
in the first place.

Now is the right time to tell you about the components which
combine to form a full-fledged microcontroller. And more
importantly, how microcontrollers process instructions given
by a human-user?

You cannot shout at the microcontrollers and say,” Fetch me


a glass of water”. Even your dog would not understand that
in true sense.

You need to talk to the microcontrollers in a language they


understand, THE BINARY LANGUAGE. Or more simply, the
language of ZEROs and ONEs.

In Binary language, one-bit can have two values (0 or 1). Two


bits can give you four values (0 to 3). Similarly, three bits can
take on eight values (0 to 7). Don’t you see a pattern
building up here?
Binary Decimal and Hexadecimal Representation for 1-4 Bits (Copyrights: Embedded
Robotics)

While binary instructions can help microcontrollers


understand the user-intentions, they still need some Data (in
binary form) to perform the desired operations.

The components of a microcontroller work in unison to


perform arithmetic (addition, subtraction, multiplication),
logical (OR, AND, XOR), shifting (left shift, right shift,
rotate), and move operations on Binary Data.

Let’s explore each of the individual microcontroller


components in great detail.

Memory

Once you have Instructions and Data, you need to store


them somewhere. Can you guess a place where you can
save them? Your cupboard maybe…

Don’t even think about that! Both the instructions and data
are in binary format, so you need a binary storage device.
In technical terms, such a device is called MEMORY.

The next question prevails, “How much data/instructions a


memory can store?”. Memory is divided into cells, and each
cell can store One Byte (8-bits). Moreover, the number of
Memory Address Lines depicts how much cells a memory
can have.

For example, a memory with one only address line can


address two cells (0,1) or store 2 bytes. Similarly, for two
address lines, there are 4 cells (0, 1, 2, 3) and storage of 4
bytes.

For three memory address lines, you can target 8 cells (0, 1,
2, 3, 4, 5, 6, 7) or store 8 bytes of data. If you are getting
along, you should be able to see another repetitive pattern.
Can you spot where have you seen such a pattern before?

Types of Memory

Three types of memories are commonly used in modern


microcontrollers. I am not going to discuss the old ones.
They are outdated anyway!
1. Random Access Memory (RAM)
2. Electrically Erasable Programmable Read-Only Memory
(EEPROM)
3. Flash Memory

Random Access Memory (RAM)

It is a volatile memory, which means it can only be accessed


when the system is powered-up. As the system power
shuts down, so do the contents inside the RAM.

It has a faster access time, but this is also expensive when


compared with the other ones. It is mainly used to store
temporary data, variables, and constants during the
execution of user instructions.

Due to the high cost and limited usage, the storage


capacity of RAM is less than EEPROM and Flash in most of
the modern-day microcontrollers.

Electrically Erasable Programmable Read-Only Memory


(EEPROM)

It is a non-volatile memory, which means that contents in


such a memory remain intact even when the power is
removed. You can program only one byte at a time in
EEPROM.

The main use of EEPROM in the microcontroller is to store


user instructions and data. The microcontroller then
accesses the instructions one-by-one and sequentially
executes them.

EEPROM needs to be programmed each time a user


changes the executable instructions. However, there is a
special circuitry needed for that.

Most of the manufacturers provide additional circuitry to


program EEPROM with the user instructions e.g., PICKIT3
Programmer for PIC Microcontrollers.

Flash Memory

Flash Memory is also non-volatile memory. Just like


EEPROM, it does not lose content when the power is
removed.

However, unlike EEPROM, it can only program a whole


sector or block of bytes. If you want to program a single
byte, you will have to program the whole memory sector.

Because of back and forth writing/erasing, flash memory


wears out more quickly than the EEPROM. That’s why Flash
memory is inexpensive as compared to EEPROM.

Some microcontroller manufacturers use either Flash or


EEPROM, while others use both to provide more flexibility to
the end-user.
Central Processing Unit (CPU)

CPU is a component of the microcontroller that fetches


instructions from the memory, decodes them, and then
executes them.

Whoa! Whoa! Stop! What is this Fetch, Decode, and


Execute? Are these the “Three Musketeers”?

Well, these are certainly not the musketeers. However, this is


what a CPU precisely does. I will explain the physical
interpretation of each term. But first, let me elaborate on the
major components which make up a CPU.

Control Unit (CU)

The main function of a control unit is to fetch and decode


the user instructions. The instructions are stored in
memory in the form of an ‘n-Bit’ stream. For an 8-bit
stream, 8 bits are stored in each cell of the memory.

For 16-bit instructions, two 8-bit streams are stored in the


consecutive cells of the memory.
8-Bit and 16-bit Instructions Stored in Memory (Copyrights: Embedded Robotics)

The first few bits depict the operation which is to be


performed i.e., addition, subtraction, multiplication, shifting,
rotation, and move, etc.

The remaining bits show the constants, or the memory


addresses for the data, or the memory store address.

Are you feeling overwhelmed? Yes? No? Please have some


faith in me.

I won’t leave you alone without providing a practical example


to easily understand all the concepts I have thrown at your
face.

I will use an instruction size of 8-bits. You need to


understand the concept, as it will remain the same for 16-bit
or even 32-bit instructions. Moreover, I will design my own
instruction set just for the sake of simplicity and obviously,
your understanding.

Here we go then!

Let’s suppose you want to design a microcontroller that can


perform four operations i.e., addition, subtraction, left shift,
and move.

Now you need a 2-bit opcode to define the four


instructions. Plus, each instruction needs two operands to
perform the desired operation.

Operands are the constants or the addresses of the


memory from where data is to be fetched. Each operand will
have a size of 3-bits in our case.

Now you can generalize the architecture of your 8-bit


instruction as:

Instruction: b7 b6 b5 b4 b3 b2 b1 b0

b2-b0: Source Operand

b5-b3: Destination Operand

b7-b6: Operation Code (or opcode)

Having defined the instruction architecture, you can define


custom instructions as:

00 – Add $a $b ($a = $a + $b): Add the value at memory


address ‘a’ and ‘b’. Store the result in memory address ‘a’

01 – Sub $a $b ($a = $a – $b): Subtract the value at


memory address ‘b’ from the value at memory address ‘a’.
Write the result in memory address ‘a’

10 – shl $a n ($a << n): Left-Shift the value at memory


address ‘a’ by n-bits. Write the result in memory address ‘a’

11 – mov $a $b ($a = $b): Copy the value located at


memory address ‘b’ to memory address ‘a’

Now I will explain some examples using the machine code


for our instructions set architecture. But, Wait…

Before I move forward, you have to promise me one thing.


You will not read the description of the machine codes
before you have tried hard enough to comprehend it
yourself. Promise? Ok, let’s dive in!

Question 1: What does the machine code ‘00011100’


means?

Answer 1: It means to add (remember the opcode ‘00’ for


add instruction) the numbers located at memory addresses
‘011’ and ‘100’. Later, the result should be stored in memory
address ‘011’

Easy-Peasy. Right? Let’s do another one…

Question 2: What does the machine code ‘01101001’


means?

Answer 2: It means to subtract (remember the opcode ‘01’


for sub instruction) the number located at memory
addresses ‘001’ from the number located at address ‘101’.
Later, the result should be stored in memory address ‘101’

I hope you are getting along! If not, you can throw in your
query in the comments section.

Time for the next one…

Question 3: What does the machine code ‘10111011’


means?

Answer 3: It means to left-shift (remember the opcode ‘10’


for shl instruction) the number located at memory addresses
‘111’ by 3 bits (‘011’). Later, the result should be stored in
memory address ‘111’

Now it’s your turn! Write the answer to the next question in
the comments:

Question 4: What does the machine code ‘11110111’ means?


Answer 4: I was not kidding. If you understand the concept,
please write the answer in the comments. Else, you can ask
me and I will personally reply to each and every one.

Whatever we have done in the last four examples is called


Decoding the Instructions.

Binary Instruction Decoding in a Microcontroller (Copyrights: Embedded Robotics)

Now, imagine the effort and amount of time you need to


decode 100,000 instructions like that? 5 hours? 10 hours?

Well, don’t get worried about that! You don’t need to do that,
as CPU has a dedicated Control Unit for this task.

But, Wait. If the Control unit can only fetch and decode the
instructions, who is going to perform the mathematical
operations? Is it again you who needs to get involved?
To get an answer, unlock the next sub-section. I am waiting
for you there…

Arithmetic Logic Unit (ALU)

The next component in the line of CPU operation is the


Arithmetic Logic Unit (ALU).

As the name implies, the basic task of an ALU is to perform


Arithmetic, Logic, Shifting, or other mathematical
operations as specified by the Instruction Set Architecture
of any microcontroller.

ALU precisely handles the “Instruction Execution”.

Control Unit fetches the instruction, decodes it, and then


sends appropriate commands to ALU about the desired
operation. ALU then executes the instruction, and stores the
result into memory.

So far, so good. I have discussed the CPU operation for a


single instruction. But what happens, when CPU has to deal
with a large number of instructions?

Instruction Pipelining

Instruction Pipelining is not a physical component in the


CPU. Rather, this is a concept to optimize the use of time
and the resources during Instruction Fetching, Decoding,
and Execution.

I have a question for you here. When the Control Unit is


fetching and decoding the instruction, what the ALU is doing
during that period? Also, when ALU is executing the
instruction, what the Control Unit is busy doing?

The answer to both of the questions is “NOTHING”. So, now


you have found the culprits who are using your time and
power but doing no useful work for almost half of the time.

What to do now? PIPELINE THEM! It means that the Control


Unit should fetch and start decoding the next instruction,
while ALU is busy executing the previous instruction.

By the time ALU executes the previous instruction, the


Control Unit should have decoded the next instruction. Now
control unit should pass this instruction over to ALU, and
fetch the next available instruction.

This cycle continues forever and reduces the instruction


execution time, a feature highly demanded by time-critical
applications.
Program Execution using Pipelined vs Non-Pipelined Architecture (Copyrights: Embedded
Robotics)

Stack

MCU Stack is a designated space in the memory used to


store the program status, as well as the return addresses
for Subroutine/Interrupt calls.

What is a Subroutine? It is a piece of code that is to be


executed by a program for a large number of times.

Rather than writing such code, again and again, it is written


for once and stored at a specific location in memory.
Whenever the program wants to use that code, it can go to
that specific location.

After executing the subroutine, the program jumps back to


the instruction which is sequentially next to the one that
called the subroutine.

What is an Interrupt? It is a diversion of the program from


normal execution flow due to external or internal
disturbances.

Each interrupt is satisfied using a specific Interrupt


Handler, which is again, a piece of code placed somewhere
into the memory.

Whenever an interrupt comes, the CPU disrupts the normal


program execution and starts executing the interrupt handler
to satisfy the interrupt requirements.

Once the interrupt handler terminates, CPU starts executing


the same instruction where it was interrupted.

For both the interrupt handler and the subroutine, the CPU
needs to go from the memory address of an instruction to
the memory address of the subroutine/interrupt handler.

But, how would a CPU know where to return once it has


entered the subroutine/interrupt handler? You need to store
the ‘Return Address’ somewhere in the memory. This is
where the mighty Stack comes in!

Stack works on a Last-In-First-Out (LIFO) scheme, which


means that the last pushed number will be the first one to
get popped out. Push means ‘Insert’. Pop means ‘Retrieve’.

Before starting the execution of any subroutine/interrupt


handler, CPU pushes the return address onto the stack.

Moreover, the last instruction in any subroutine/interrupt


handler pops the return address from the stack. This allows
the CPU to resume the normal program execution flow.

One critical point is that the CPU should push the return
address of the next instruction than the one, which is being
interrupted or calling the sub-routine. This will prevent an
infinite instruction execution loop.

You may be wondering “What is the need for a whole MCU


stack to store only the return address?”. Don’t Worry. You
will get the answer in the next sub-section.

Registers

Registers are temporary storage areas within a CPU. They


are used to store the information about the program flow,
program status, instruction results, and the hardware
configuration.

In most of the architectures, registers are merely 14-15 in


number. However, they are much faster to access than the
memory.
This is the single main reason why CPU prefers registers
over the memory for operations involving immediate data
access.

Microcontroller Registers with ARM Architecture (Copyrights: Embedded Robotics)

There are several types of registers which exist within a


CPU:

General Purpose Registers

These registers are used as source/destination operands


for arithmetic, logic, and shifting instructions

Stack Pointer

This register points to the section of the memory used for


the CPU hardware stack i.e., for subroutine/interrupt calls.
Stack Pointer always points to Top of the stack, which is also
the last pushed element onto the stack.

In a bottom-up stack (which increases in an upward


direction on element push), stack pointer gets incremented
first and then the element is pushed at the updated stack
pointer value.

For the pop operation, Top element is retrieved first and then
stack pointer gets decremented

Program Counter (PC)

This register stores the address of the next instruction,


which is to be executed by the CPU.

PC plays the most important rule during program execution


and guides the execution flow of the program.

During the normal program execution, PC gets incremented


to the address of the next instruction in a sequential manner.

For any subroutine/interrupt call, PC gets loaded with the


starting address of the subroutine/interrupt handler and
the return address for the next instruction is pushed onto the
stack.

While exiting out of the subroutine/interrupt handler, the last


instruction pops the return address from the stack into the
Program Counter. The CPU then starts executing the
instruction whose address gets loaded into PC.

Link Register (LR)

This register is not available in all of the microcontrollers.


However, its function is to store the return address of
subroutine/interrupt calls.

Remember! Earlier, CPU was saving the return address into a


stack. Now there is a register available for that.

But what happens when a subroutine is called within another


subroutine, or the same scenario occurs with an interrupt?

Now you also need to save your Link Register (LR) into the
stack, as LR will get updated with the new return address for
the nested subroutine/interrupt handler.

Once you get out of the nested subroutine, you need to pop
the value from stack into the LR. This will get you to the
starting point, the return address for the first sub-
routine/interrupt.

Special Function Registers

These registers are used for a specific configuration of the


hardware. More specifically, Status Flag Registers give
information about the hardware status.
For example, an interrupt status register sets a flag
whenever an interrupt occurs. This flag needs to be cleared
to be able to detect an interrupt from the same source again.

A zero-bit flag is set whenever a mathematical operation


result in a 0. This flag is used to compare the two operands
are equal or not.

The Carry-bit flag is set whenever the result of an operation


is larger than the allowed storage size.

For example, if you try to store a number greater than 255 in


an 8-bit storage area, the carry bit is set indicating that the
number is out-of-range.

Register Pushing onto Stack

Do you remember I promised you to answer one question in


this section? If no, I am repeating my question here:

“What is the need for a whole MCU stack to store only


the return address?”

After having learned about the registers, you are now well-
in-shape to understand this cheeky concept.

Stack does not only store the return address. It is also


needed to save Special Function Registers, Link Register,
and even general-purpose register at times.
Every sub-routine/interrupt handler tends to change the
Special Function Registers or flag status. Thus, it is
necessary to save the state of these registers into the stack
before entering the sub-routine/interrupt handler.

In the case of nested subroutines, Link Register gets


updated with the new value whenever a new sub-routine is
called. You need to store LR within the stack else you won’t
be able to return to the instruction which is called the first
instance of the sub-routine.

For the microcontroller architectures having no Link Register


(LR), the value of the Program Counter (PC) should be
stored in the stack whenever a subroutine or an interrupt
handler is invoked.

The general-purpose registers depict the status of a


program at any time. To preserve the status of the program
before any interrupt or subroutine, general-purpose registers
are pushed onto the stack and popped in reverse order
before the termination of interrupt handler or subroutine.

As Promised! Here is an interactive ANIMATION describing


the whole process:
Execution of a Program in Microcontroller with Nested Subroutines (Copyrights: Embedded
Robotics)

Clock
Before moving onto the clock signal, I want you to imagine a
scenario!

Let’s say you provided a bunch of instructions to CPU for


execution. You were happy and enthusiastic about that, but
then a strange thing happened!

CPU fetched instruction from memory and started executing


it. However, without executing the complete instruction, CPU
decided to fetch the next instruction. What will this
anomalous CPU behaviour leave you with?

A faulty or garbage result for the first instruction, which


tends to corrupt the whole program and ultimately the
complete embedded systems.

I am pretty sure; you wouldn’t want that! So, how you can
prevent this?

You need a Clock Signal which can synchronize each


activity of the CPU with a rising or falling edge.

Moreover, the frequency of the clock signal will specify the


execution period for each instruction. Higher the frequency,
lower the execution time.

And Boy oh Boy! Don’t we all want higher and higher


frequency…
I/O Ports

If you already know the data for your instruction, you can
feed that into the memory directly and you are good to go.

However, what will happen if you need to provide some


information about the environment during the program
execution?

Besides, what if you need to control some of the


environment variables or an external device?

The solution is simple. You need Input-Output ports in


microcontroller to read dynamic user-inputs, or to control
external devices.

For example, I/O Ports provide the user input data from
switches and keyboards to the CPU. Moreover, I/O Ports
output the desired information to the user by interfacing with
the LCD or LED display.

Each port in a microcontroller is programmable to be either


input/output. This provides a user with the flexibility to
program the I/O ports as per the application needs.

Bus

Now you have got all the components to execute your


instructions. All you need to do now is to connect all the
components using a Bus. This bus will establish a
communication link between different components.

There are three kinds of buses which are mostly used in


microcontrollers:

Instruction/Data Bus: This bus helps transfer


instructions/data back and forth into CPU and the memory

Address Bus: This bus specifies the address where the


desired instruction/data are located inside the memory

Control Bus: This bus specifies whether the


instructions/data are to be written or be fetched from the
memory

How Microcontroller Works


You are now aware of all the components which make up a
microcontroller, and their functions.

But how do all the components work in unison to execute


the instructions?

Or more simply, what happens when you have flashed your


code in the EEPROM and reset your microcontroller?

There are a series of steps that happen before even CPU


starts executing the first instruction of the user program.
Firstly, the microcontroller needs the know-how of the
address where the user instructions are stored within
EEPROM.

Luckily, there is a simple solution for that. On reset, the


microcontroller goes to a fixed memory location. This
memory location holds the actual address for the beginning
of the program code.

Compiler loads the Program Counter (PC) with the starting


address of the program code.

Control Unit (CU) fetches and decodes the instruction


pointed by the PC. ALU executes the instruction and stores
the result in the memory.

Meanwhile, PC gets updated with the address of the next-in-


line instruction. Control Unit then fetches the next
instruction, and the cycle goes on…

Repetitively, all the program instructions are fetched,


decoded, and executed as per the pipelined architecture.

Microcontroller Architecture
Most of the women believe that “All men are the same”. This
thinking, however, does not apply in the context of the
microcontrollers. Microcontrollers differ greatly based on
their architecture, which I am going to discuss further:
External Memory vs Embedded Memory

In the case of external memory microcontrollers, memory is


not interfaced within the microcontroller. Rather, the user
needs to connect an external memory to store
instructions/data.

For embedded memory microcontrollers, memory is


embedded inside the microcontroller.

If you are a beginner, embedded memory microcontrollers


are recommended since you will need a plug-and-play
approach to develop the desired application.

Instruction Set Architecture (ISA): RISC vs


CISC

RISC (Reduced Instruction Set Computer) has simplified


instructions, each of which takes one clock cycle to
execute. You need to write efficient software, as hardware in
RISC can only handle simple instructions.

CISC (Complex Instruction Set Architecture) has complex


instructions. Some of them may take one clock cycle, albeit
many will require multiple clock cycles. The hardware in
CISC is sophisticated enough to handle complex
instructions, so you won’t need to make any extra effort to
optimize your code.
Simply put, a CISC instruction may require multiple clock
cycles if executed on a RISC architecture. Besides, RISC
emphasizes software whereas CISC emphasizes
hardware.

Due to the execution of an instruction on each clock cycle,


RISC based microcontroller would also require more RAM as
compared to the CISC one.

Most of the modern-day microcontrollers employ RISC


Instruction Set Architecture. Besides, RISC has a successor
in RISC-V architecture, although it is not common in
commercial microcontrollers as of now.

Harvard vs Von. Neumann Architecture

In Harvard architecture, the microcontroller has separate


buses to access the instructions and data. Whereas, von
Neumann architecture has a common bus for both.

In simple terms, microcontrollers with Harvard architecture


can fetch data and instructions at the same time. However, in
von Neumann architecture, the microcontroller firstly fetches
instructions, and then the data.

This bottleneck in von Neumann architecture increases the


instruction execution time, and adversely affects the
overall system performance.
In Harvard architecture, memory address space is defined
for both the instructions and the data. So even if you have
some space available in the instruction region, you cannot
use that for the data and vice versa.

Difference between Harvard and Von Neumann Architecture (Copyrights: Embedded


Robotics)

Now, let’s evaluate the execution time of an ‘addition


operation’ for both the architectures.

In Harvard architecture, one clock cycle will be needed to


fetch both the instruction and data. The next clock cycle
would perform the addition operation. In the third clock
cycle, the data bus will store the result in memory whereas
the instruction bus will fetch the next instruction at the same
time.
In von Neumann architecture, two clock cycles will be used
to fetch the instruction and data. The third clock cycle will
see through the addition operation. The fourth clock cycle
will be used to store the data. Finally, the next instruction will
be fetched in the fifth clock cycle.

Now you can see for yourself, it took only three cycles in
Harvard architecture to execute an instruction and fetch
the next instruction. While von Neumann architecture took
five clock cycles for the same task.

Now imagine a scenario for tens of thousands of


instructions, and a cumulative delay caused by von
Neumann architecture.

That would be enough to convince you to adopt Harvard


Architecture, as most of the modern-day microcontroller
manufacturers already have.

Bit Configuration

As one shoe doesn’t fit all, so is the case with a


microcontroller for different applications. Microcontrollers
come in different bit configuration sizes i.e., 8-bit, 16-bit,
32-bit.

You may be wondering why so many configurations exist?


And why can’t we use a 32-bit microcontroller for all of the
applications? Let me explain this using a simple analogy.

Let’s say you are a team of 4 friends, and you all have
decided to visit Disney Land during summer vacations. You
have two choices for your ride: a car or an empty bus. Which
one would you pick?

I knew you would go for the bus. After all, you would be able
to sleep in the empty space. However, once you become
aware of the difference between the fare, you will certainly
prefer a car over an empty bus. I have excluded two kinds of
humans in my speculation: firstly BILLIONAIRES, and
secondly those with a fresh salary check!

The same concept applies to microcontrollers. If an 8-bit


microcontroller can fulfill the requirements of an
application, why would you want to use more costly and
more power-consuming 32-bit MCU? I mean, WHY?

And you won’t believe me, 90% of the applications can be


implemented with an 8-bit microcontroller. You will not need
16-bit or 32-bit MCU unless you intend to perform Digital
Signal Processing, Floating-Point Arithmetic, or other
resource-intensive tasks.

What is the physical, or technical interpretation of an n-bit


microcontroller?

An n-bit microcontroller simply means that the data bus is


‘n-bit’. This implies that we can store n-bits at a time in the
memory. Or, we can perform data manipulation up to a max
of n-bits during one clock cycle.

A 32-bit data manipulation will take 4 clock cycles on an 8-


bit microcontroller, whereas only 1 clock cycle on a 32-bit
microcontroller.

On the contrary, an 8-bit data manipulation will take one


clock cycle on either 8-bit/32-bit MCU. However, 32-bit
MCU will be more costly and consume more energy than the
8-bit counterpart.

Feeling confused? Let me elaborate with a practical


example…

Let’s suppose you need to add 100 and 150 on an 8-bit


microcontroller. How many clock cycles will be required?

Only one clock cycle, since 250 (100+150) is within the 8-


bit range (0…255).

However, if you want to add 200 and 250 using an 8-bit


MCU, you will require 2 clock cycles. The reason being 200
+ 250 = 450 is out-of-range for an 8-bit data (0-255) but
well within the range for 16-bit data (0-65535).

Now, tell me the number of clock cycles needed to add


‘60000’ and ‘10000’ in the comments…
Microcontroller Peripherals
Microcontrollers come with additional peripherals to develop
an interface with the external environment as well as to meet
the demands of the sophisticated applications.

These peripherals are add-on features for a microcontroller.


Some microcontrollers may have more of these features,
while others may have only two or three additional
peripherals.

It is you who is going to decide which features you need in a


microcontroller, considering the demands of the application
as well as the cost at which they are available.

Each peripheral of a microcontroller is sophisticated enough


to deserve a personal blog post. So, I am only going to
introduce each peripheral along with some of the possible
applications.

Timers/Counters:

As the name implies, this peripheral will induce the notion of


time within your system. A clock signal from an
external/internal crystal oscillator is used to ensure the
proper working of timers/counters.

Timers are used to introduce timer delays within your


program. For example, you can set a beep after every 1.5
seconds, or you can read the temperature sensor value after
every 5 minutes or so.

Counters are used to count external events. For example,


you may want to monitor how many times the user has
pressed a button in the last 5 seconds. You can also count
the number of bi-directional visitors passing through a
security gate within a window of 24 hours.

A most important feature of timers is the generation of Pulse


Width Modulation (PWM) signals. PWM signals are widely
used for motor control in robotic applications.

PWM is a square wave signal with a specified duty cycle and


frequency. The duty cycle means the ratio of signal ON-
Time to OFF-Time.

Duty Cycle = (ON Time/Off Time) * 100

Let’s suppose you have a PWM signal that is varying


between 0 and 5 volts. With a 20% Duty cycle, you will get 1
Volt. With 80% Duty Cycle, you will get 4 volts.
Pulse Width Modulation for different Duty Cycles (Copyrights: Embedded Robotics)

Thus, you can get different voltage at the output just by


varying the duty cycle of a PWM signal. Can you tell me how
much duty cycle you need to get 3 volts at the output? Over
to the comments section…

Communication Interfaces

Have you ever transferred any data from your mobile phone
to a desktop computer? Okay, so which communication
interface did you use?

Everybody knows it! USB or Universal Serial Bus. But do you


know that USB is not the only communication protocol?

Your desktop computer only has USB ports because it can


only interface with the USB hosts. However, the same is not
the case with a microcontroller.

The microcontroller needs to interface with all kinds of


devices, which have come to existence since the dark ages.
As the electronic devices are getting sophisticated with the
advent of technology, so are their communication interfaces.

The most important feature of a communication protocol is


its high speed and reliability during data transfer. Nobody
wants to lose their data. Right?

Many reliable and fast data communication protocols came


into existence. However, after recurring trials and testing,
there remain only a few which have won the trust of the
developers.

The most prominent of them are serial communication


protocols such as:

Universal Asynchronous Receiver Transmitter (UART)


Universal Synchronous Asynchronous Receiver
Transmitter (USART)
Serial Peripheral Interface (SPI)
Inter-Integrated Circuit (I2C)
Universal Serial Bus (USB)

Because of the never-ending demand for high speed and


reliable communication, we are inching towards Bus
Communication. There are two dominant protocols in this
domain:

Control Area Network (CAN) Bus


Ethernet for Control and Automation Technology
(EtherCAT)

Analog-to-Digital Converter (ADC)

All the sensors having either Serial or Bus Communication


Interface produce their output in a digital form. It means
that their output voltage is either at logic level ‘Low’ or logic
level ‘High’.

An output in such form is readily accepted by the


communication interfaces embedded within the
microcontroller.

However, there are some sensors whose output follows the


analog format. In other words, their output voltage varies
between the two levels.

Any such sensor could produce an output voltage of 1.3V, or


2.98V, or 4.78V. Such irregular output voltage is not
comprehended by the digital communication interfaces.

Ok. Fine. So, there must exist an analog communication


interface for analog data?

Believe me. That will be of no use because CPU also can’t


understand the analog voltage signals. What is the solution,
then?

An analog-to-digital converter is your best buddy for this


task. ADC takes analog inputs and converts them to digital
values. These digital values are then fed into CPU for further
processing.

If you have a 10-bit ADC, you will be able to convert analog


voltage (0-5 volts) to a digital value in the range of 0-1023.

A value of 0 volts will be equal to ‘0’, and a value of 5 volts


will be equal to ‘1023’ in the digital format. All the
intermediate values will have relative digital counterparts as
indicated by the formulae:

Digital Value = (Analog Voltage/5) * 1023

In a 16-bit ADC, you will be able to convert the analog


voltage into a digital range of 0-65535. So, you have more
precision and more control. In this case, formulae for digital
conversion will be:

Digital Value = (Analog Voltage/5) * 65535


Analog to Digital Converter (Image Source: DOEET)

Digital-to-Analog Converter (DAC)

Digital-to-Analog Converter (DAC) is a reciprocal of ADC.


DAC converts digital pulses into analog signals.

It finds applications for the devices which are controlled


using analog voltage.

As the microcontroller can only output digital values, you


need DAC to convert the digital values into analog voltage
signals.

For a 10-bit DAC, you can convert a digital value in the


range of 0-1023 to analog voltage signal from 0 – 5 volts.

The digital value of ‘0’ will correspond to 0 volts, and ‘1023’


will correspond to 5 volts as per the formulae:

Analog Voltage = (Digital Value/1023) * 5


For a 16-bit DAC, you can convert a high range of digital
values (0-65535) to an analog voltage in the range of 0-5
volts:

Analog Voltage = (Digital Value/65535) * 5

Digital to Analog Converter (Image Source: NUTAQ)

Interrupt Controllers

You may remember that we have already talked about


interrupt handlers in the context of MCU Stack. But what is
an interrupt controller?

You first need to be crystal clear about the interrupt handler.


Simply put, an Interrupt Handler is a piece of a program,
which is executed whenever an interrupt comes.

Interrupts caused by any external hardware are called


Hardware Interrupts. While interrupts happening internally
in the software are called Software Interrupts.

An example of a hardware interrupt is an interrupt due to


push button state change i.e., whenever a user presses a
push-button or releases it.

Software interrupt could be caused by an internal timer i.e.,


after each 1 sec, timer generates an interrupt.

There is also another type of interrupt called Exception.


Exceptions are the software interrupts caused by the
system-level programs rather than user-level programs.

Each peripheral in a microcontroller has its interrupt handler.


For example, Port A will have its interrupt handler. Timer0 will
have its interrupt handler. Timer1 will also have a unique
interrupt handler. I hope you are getting the point!

Whenever a software or hardware interrupt is caused by a


peripheral, the corresponding interrupt handler is executed.
You can write instructions in an interrupt handler, and your
instructions will execute whenever that same interrupt
handler is invoked.

Let’s say you want to toggle the output state of Port A after
each second. What will you do?

You will set a Timer0 to generate an interrupt after every


second. Then, you will go to the Timer0 Interrupt handler
and insert your application-specific instructions in that
handler i.e., toggle the state of Port A.

So far so good. But what role does Interrupt Controller play


in all this? Is Interrupt Controller just a fancy name for
‘Interrupt Handler’?

No, No! Wait, let me explain…

As there are a large number of interrupt handlers, they are


stored in NVIC (Nested Vectored Interrupt Controller). Now,
what the hell is this NVIC?

NVIC stores the starting address of each interrupt handler in


a vector-like format within the memory.

Whenever an interrupt occurs, THE “Interrupt Controller”


firstly detects the peripheral which has caused the interrupt.

In the second step, the interrupt controller fetches the


starting address of the corresponding interrupt handler from
the NVIC.

In the third step, the interrupt controller loads the Program


Counter (PC) with the address of the interrupt handler. CPU
then starts executing the interrupt handler, while the
Interrupt controller goes back to listen for more interrupts.

Nested Vector Interrupt Controller Mapping onto Interrupt Handlers (Copyrights:


Embedded Robotics)

Difference between Microcontroller and


Microprocessor
This is the topic that confuses almost 3/4th of the people,
who try to get their basics right about the microcontrollers.

Most of them get confused because they don’t understand


the microcontroller and its working principle. But you are not
like them!

You have now read almost 7000 words about the basics of
microcontroller, and understand microcontrollers from every
nook and angle. Understanding the difference between
microcontrollers and microprocessors is going to be a
piece of cake for you!

Do you remember all the components of a microcontroller


i.e., CPU, I/O Ports, Memory, Bus, and Clock? Also, do you
remember the additional peripherals that come embedded
into the microcontroller?

What if I remove all the components and peripherals from a


microcontroller except the CPU? What will you get then?

A Microprocessor!

How simple was that! I bet you did not have any problems
understanding that. People, however, make a mess of this
because they don’t comprehend microcontrollers in true
sense.

Simply put, a microprocessor is essentially a CPU with no


memory/peripherals attached. You need to interface the
memory as well as the other components/peripherals
externally.

With a microprocessor, you need to get some homework


done before you can even get the simplest of the
applications up and running.

On the contrary, a microcontroller is a ready-to-use unit. It


has all the memories, components, and peripherals
embedded inside a single chip. You only need to burn
EEPROM with the instructions and you are good to go!

But why do microprocessors even exist?

Although microcontrollers come with an embedded


memory inside, the memory is only enough to implement
low-profile applications.

What if you want to execute resource-intensive applications


such as Graphics, 3D Modelling, Android/IOS App
development? A more extreme case would be to run all such
applications at a single time.

Can a microcontroller perform such an intensive task?


Maybe, yes. However, due to the limited memory and CPU
computational power, it will take ages.

But we don’t want that? So, what is the solution?

Again. A Microprocessor!

A microprocessor essentially comes with high


computational power. Besides, you can interface large
memories with the microprocessor, making it an ideal
candidate for resource-intensive applications.

Another selling point of the microprocessor is its ability to


execute a myriad of resource-intensive applications at the
same time. This is the main reason why your desktop/laptop
computers come with a processor rather than a
microcontroller.

Microcontroller Applications
By now, you should have a fair idea of the applications which
can be implemented with the help of a microcontroller.

I have also mentioned many such applications within the


entire article. However, to give you an extra boost, I am
sharing some more:

Baby Monitors
Fire Detection
Internet of Things
Home Automation
Light Sensing
LED Control
Low-Cost Wearables
Medical Equipment
Sub-Marines
Ships
Aerospace System
and many more…

This list will never end, even If I continued to write for the
next three days.

I am calling it a day here. However, it’s time for you to take


some action!

Assignment: Think of 20 devices that you can develop with


the microcontrollers. Once you have done that, share them
with me via email. In return, I will share them on the social
media pages so that others can also benefit from your
knowledge. Awaiting your answers!

And, please. Don’t forget to share this amazing article with


your friends, colleagues, and even your stubborn Boss. You
may get a promotion for doing that!

Sharing is Caring!

You might also like