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

embedded c

Uploaded by

Athulya B.S
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
11 views

embedded c

Uploaded by

Athulya B.S
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 18

Structured Program Development in C

1. Definition of Structured Programming:


• Structured programming is a programming paradigm that emphasizes the
use of clear, logical structures to improve the clarity and efficiency of code.
It involves breaking down a program into smaller, manageable modules or
functions, each responsible for a specific task. This approach enhances
readability, maintainability, and reusability of code.
2. Importance of Structured Programming in C:
• Modularity: Programs are divided into functions, making it easier to
develop, test, and debug.
• Control Flow: Structured programming allows for precise control over the
flow of execution using control structures.
• Code Reusability: Functions can be reused in different parts of a program
or across different programs.
• Maintenance: Easier to update and maintain programs due to the clear
organization of code.
• Collaboration: Multiple developers can work on different modules
simultaneously.
3. Key Control Structures Used in Structured Programming:
• Control structures dictate the flow of execution in a program. The three
fundamental types are:
• Sequence Control Structure: Executes statements in a linear order.
• Example:
c
int a = 5;
int b = 10;
int sum = a + b; // Executes sequentially

• Selection Control Structure: Allows for decision-making based on


conditions.
• Example:
c
if (a > b) {
printf("A is greater");
} else {
printf("B is greater");
}

• Iteration Control Structure: Enables repeated execution of a block


of statements until a condition is met.
• Example:
c
for (int i = 0; i < 5; i++) {
printf("%d\n", i); // Prints numbers 0 to 4
}

4. Concept of Modularity in Structured Programming:


• Modularity refers to the practice of dividing a program into separate, self-
contained functions or modules. Each module performs a specific task and
can be developed independently.
• Benefits:
• Improved Readability: Code is easier to understand when
organized into functions.
• Easier Testing and Debugging: Individual modules can be tested
separately.
• Reusability: Functions can be reused across multiple programs or
projects.
• Simplified Maintenance: Changes can be made within individual
modules without affecting the entire program.
5. Process of Top-Down Design in Structured Program Development:
• Top-down design is an approach where the main problem is broken down
into smaller subproblems or tasks. This process involves:
• Identifying the main function or goal of the program.
• Breaking it down into smaller, manageable functions (subtasks).
• Further decomposing these subtasks until they are simple enough
to be implemented easily.
• This method promotes clarity and organization in program development.
6. Advantages and Disadvantages of Using Structured Programming:
• Advantages:
• Enhances code clarity and organization.
• Facilitates easier debugging and testing processes.
• Promotes code reusability and modular design.
• Supports teamwork by allowing multiple developers to work on
different modules simultaneously.
• Disadvantages:
• May introduce performance overhead due to function calls.
• Complexity can increase with too many interdependent modules,
making management difficult.
7. Example of a Simple Structured Program in C:
c
#include <stdio.h>

// Function declaration
int add(int x, int y);

// Main function
int main() {
int num1 = 10;
int num2 = 20;
int result;

result = add(num1, num2); // Function call


printf("The sum is: %d\n", result);
return 0;
}

// Function definition
int add(int x, int y) {
return x + y; // Returns the sum of x and y
}

• Components Explained:
• The program includes a header file for input/output operations
(#include <stdio.h>).
• The add function encapsulates the logic for adding two integers.
• The main function serves as the entry point where execution begins,
demonstrating modularity by calling the add function.

This structured approach ensures that programs are not only effective but also
maintainable and scalable, making structured programming an essential practice in C
programming.
Explain the working principle of a Digital to Analog Converter (DAC) and its importance in
embedded systems. How does the 8051 microcontroller interface with an external DAC to
generate an analog signal?

Working Principle of a Digital to Analog Converter (DAC)


A Digital to Analog Converter (DAC) is an electronic device that converts digital signals
(discrete binary values) into analog signals (continuous voltage or current). This
conversion is essential in various applications, particularly in embedded systems where
digital data needs to be transformed into a form that can interact with the analog world.
Below is a detailed explanation of the working principle of a DAC, its importance in
embedded systems, and how it interfaces with the 8051 microcontroller.

Block Diagram of DAC

Working Principle of DAC


1. Digital Input:
• The DAC receives a digital input signal, which consists of binary values (0s
and 1s). Each binary digit represents a specific voltage level based on its
weight in the binary number system.
2. Weighted Resistor Network:
• The most common method for DAC implementation is through a weighted
resistor network or an R-2R ladder network. In these configurations, each
bit of the digital input controls a switch that connects to a reference
voltage, creating an analog output proportional to the digital input.
• R-2R Ladder Network: This design uses only two resistor values (R and
2R) to simplify the circuit and maintain accuracy across multiple bits.
3. Summing Amplifier:
• The output from the weighted resistors is fed into a summing amplifier,
which combines these voltages into a single output voltage. The amplifier
ensures that the output signal has sufficient amplitude and drive
capability.
4. Analog Output:
• The final output from the summing amplifier is a continuous analog signal
that corresponds to the digital input value. This signal can be used for
various applications such as audio playback, control signals, or modulation
in communication systems.

Importance of DAC in Embedded Systems


1. Signal Generation:
• DACs are crucial for generating analog signals from digital data, allowing
microcontrollers to produce sound, control motors, and interface with
sensors.
2. Interfacing with Real World:
• Many real-world applications involve analog signals (e.g., audio signals,
temperature readings). DACs enable digital systems to interact with these
analog inputs effectively.
3. Precision Control:
• In applications such as robotics and automation, DACs provide precise
control over variables like speed and position through analog outputs.
4. Audio Applications:
• In audio systems, DACs convert digital audio files into analog signals that
can be amplified and played through speakers.
Interfacing the 8051 Microcontroller with an External DAC
To generate an analog signal using an external DAC with an 8051 microcontroller, follow
these steps:
1. Connection Setup:
• Connect the digital output pins of the 8051 microcontroller to the input
pins of the external DAC. Ensure that a proper reference voltage is
supplied to the DAC for accurate output generation.
2. Sending Data:
• Use one of the I/O ports on the 8051 microcontroller to send binary data
to the DAC. This data represents the desired analog output level.
3. Example Code:
Here’s an example embedded C program that sends data from the 8051
microcontroller to an external DAC:

4. Operation Explanation:
• In this example, Port 1 of the 8051 microcontroller is used to send an 8-bit
value (128) to the DAC.
• The program can be modified to change data_value based on inputs
from sensors or user commands, allowing dynamic control over the analog
output.
Determine the importance of resolution in a DAC when interfacing with the 8051 microcontroller.
How does the resolution of the DAC affect the accuracy and quality of the analog output signal?

Importance of Resolution in a DAC


1. Definition of Resolution:
• The resolution of a DAC indicates the number of discrete output levels it
can produce. It is determined by the number of bits in the digital input:
• Resolution=2n, where n is the number of bits.
• For example, an 8-bit DAC can produce 256 different output levels.
2. Impact on Accuracy:
• Finer Granularity: Higher resolution allows for smaller increments
between output levels, which means that the DAC can represent analog
values more precisely.
• Step Size Calculation: The step size (the smallest change in output
voltage) is given by:
Step Size=Vref / 2n
A smaller step size leads to smoother transitions and more accurate signal
representation.
3. Quality of Analog Output:
• Reduced Quantization Error: Higher resolution minimizes quantization
error, which is the difference between the actual analog value and the
value represented by the digital code. This results in less distortion in the
output signal.
• Smoother Waveforms: In applications like audio processing, higher
resolution results in smoother waveforms and better sound quality.
4. Quantization Distortion:
• As resolution increases, quantization distortion decreases. This is
particularly important for signals that require high fidelity, such as audio or
video signals.
5. Applications Requiring High Resolution:
• Applications such as audio playback, precision instrumentation, and
control systems benefit significantly from higher-resolution DACs because
they require accurate and smooth analog signals to function correctly.
Effects of Resolution on Accuracy and Quality
1. Signal-to-Noise Ratio (SNR):
• The SNR improves with increased resolution. The relationship can be
expressed as:
SNR=1.76 + 6.02n
Each additional bit increases SNR by approximately 6 dB, leading to clearer
signals with less noise interference.
2. Output Spectrum:
• Higher-resolution DACs exhibit lower spurious content in their output
spectrum, meaning fewer unwanted frequencies are present in the output
signal.
• This characteristic is crucial for applications where high-quality signal
reproduction is essential.

Interfacing with the 8051 Microcontroller


1. Connection Setup:
• Connect the digital output pins of the 8051 microcontroller to the input
pins of the external DAC (e.g., using Port 1). Ensure that a proper reference
voltage is supplied to the DAC for accurate output generation.
2. Example Code:
Below is an example embedded C program that demonstrates how to send
digital values from the 8051 microcontroller to a DAC:
}#include <reg51.h>

void main() {
unsigned char data_value;

// Initialize data value


data_value = 0x00; // Start from minimum output

while(1) {
// Send data to DAC connected at Port 1
P1 = data_value; // Output data_value to Port 1

// Increment data value for next iteration


data_value++;
if(data_value > 0xFF) {
data_value = 0x00; // Reset after reaching max
}

// Delay for a short period to observe changes in output


for(int i = 0; i < 1275; i++); // Simple delay loop
}
}

3. Operation Explanation:
• In this code, data_value starts at 0x00 (minimum output) and increments
until it wraps around after reaching 0xFF. Each value sent to Port 1
corresponds to a specific voltage level at the DAC's output.
• The higher the resolution of the DAC used, the finer the increments in
output voltage will be, leading to smoother analog signals.
Examine the role of the IE (Interrupt Enable) and IP (Interrupt Priority)
registers in managing interrupts in the 8051 microcontroller. Provide
examples of how they are configured for specific interrupts

Interrupts in the 8051 microcontroller are managed using IE (Interrupt Enable) and IP
(Interrupt Priority) registers. These registers control whether specific interrupts are enabled or
disabled and set their priority levels.

1. Interrupt Enable (IE) Register

The IE register is an 8-bit register that controls the enable/disable functionality of each interrupt
source in the 8051.

• Purpose: To enable or disable specific interrupts globally or individually.


• Structure: Each bit corresponds to an interrupt source or global interrupt enable.

IE Register Format

Bit Symbol Description


7 EA Global Enable/Disable (1: Enable, 0: Disable)
6 - Unused (Reserved, always 0)
5 ET2 Timer 2 Interrupt Enable
4 ES Serial Port Interrupt Enable
3 ET1 Timer 1 Interrupt Enable
2 EX1 External Interrupt 1 Enable
1 ET0 Timer 0 Interrupt Enable
0 EX0 External Interrupt 0 Enable

Working of IE Register

1. Global Enable (EA): If EA = 0, no interrupts will be recognized, regardless of other bits.


2. Individual Enable Bits: Specific interrupts can be enabled by setting the corresponding
bit to 1.
3. Reserved Bit: Bit 6 is unused and should always be set to 0.

2. Interrupt Priority (IP) Register

The IP register is another 8-bit register that determines the priority of interrupts when multiple
interrupts occur simultaneously.

• Purpose: To assign high or low priority to interrupts.


• Structure: Each bit corresponds to an interrupt source.
IP Register Format

Bit Symbol Description


7 - Unused (Reserved, always 0)
6 - Unused (Reserved, always 0)
5 PT2 Timer 2 Interrupt Priority
4 PS Serial Port Interrupt Priority
3 PT1 Timer 1 Interrupt Priority
2 PX1 External Interrupt 1 Priority
1 PT0 Timer 0 Interrupt Priority
0 PX0 External Interrupt 0 Priority

Working of IP Register

1. High Priority (1): If a bit is set to 1, the corresponding interrupt is assigned high priority.
2. Low Priority (0): If a bit is cleared (0), the interrupt is assigned low priority.
3. Simultaneous Requests: If two interrupts of the same priority occur, they are serviced
based on their natural order of priority (fixed sequence 0 to 5).

3. Interrupt Handling Workflow

1. An interrupt request is generated.


2. The IE register checks whether the interrupt is enabled (corresponding bit = 1 and EA =
1).
3. If enabled, the IP register determines whether the interrupt has high or low priority.
4. The 8051 microcontroller suspends the current program execution and services the
higher-priority interrupt.

4. Block Diagram

The interaction between the IE and IP registers and the interrupt control logic can be visualized
as: +-----------------+

|Interrupt Request|
+--------+--------+
|
v
+-------+ +---------------+ +----------------+
| IE |-------> | Interrupt |-------> | CPU Services |
| | | Enable Check | | Interrupt |
+-------+ +---------------+ +----------------+
^
|
+-------+ +---------------+
| IP |-------> | Priority |
| | | Determination |
+-------+ +---------------+

Example Code: Configuring and Using Interrupts in 8051

Scenario:

• Use External Interrupt 0 (EX0) to toggle an LED.


• Use Timer 1 Interrupt (ET1) to generate a 1-second delay.
• Assign high priority to EX0.

Code Example:

#include <reg51.h>
sbit LED = P1^0;

// Function Prototypes
void Timer1_ISR (void) interrupt 3;
void External0_ISR (void) interrupt 0;

// Main Function
void main(void) {
EA = 1;
EX0 = 1;
ET1 = 1;
PX0 = 1;
PT1 = 0;

// Timer 1 Configuration for 1-Second Delay


TMOD = 0x10;
TH1 = 0xFC;
TL1 = 0x66;
TR1 = 1;

while (1) {
// Main loop (LED toggling is handled by interrupts)
}
}
// Timer 1 Interrupt Service Routine
void Timer1_ISR (void) {
TR1 = 0;
TH1 = 0xFC;
TL1 = 0x66;
TR1 = 1;
LED = ~LED;
}

// External Interrupt 0 Service Routine


void External0_ISR (void) {
LED = 1; // Turn on LED when external interrupt occurs
}
Explanation

1. Global Configuration (Main Function)

• EA = 1: Enables all interrupts globally.


• EX0 = 1: Enables External Interrupt 0 (EX0).
• ET1 = 1: Enables Timer 1 Interrupt (ET1).
• PX0 = 1: Assigns high priority to EX0.
• PT1 = 0: Leaves Timer 1 Interrupt at low priority.

2. Timer 1 Configuration

• TMOD = 0x10: Sets Timer 1 in Mode 1 (16-bit timer mode).


• TH1 = 0xFC, TL1 = 0x66: Loads the timer registers for a 1-second delay (assuming a 12
MHz clock).
• TR1 = 1: Starts Timer 1.

3. Interrupt Service Routines (ISR)

• Timer1_ISR: Toggles the LED state every second by:


o Stopping Timer 1 (TR1 = 0).
o Reloading Timer 1 registers (TH1, TL1).
o Restarting Timer 1 (TR1 = 1).
o Toggling the LED (LED = ~LED).
• External0_ISR: Instantly turns the LED on when External Interrupt 0 is triggered.

4. Priority Management

• EX0 has high priority, ensuring immediate response to external events.


• ET1 has low priority, so it’s serviced only when no high-priority interrupt is active.

Real-Time Behavior

1. Timer-Based LED Blinking:


o The LED toggles every 1 second, controlled by the Timer 1 ISR.
2. Immediate Response to External Interrupt:
o When an external event occurs (e.g., a button press), External Interrupt 0
immediately turns the LED on, even if the timer interrupt is active.
Develop an embedded C program for restructuring the goat-
counting example
1. Modularizing the Code

• Purpose: Break the program into smaller sections (modules) for easier maintenance and
reusability.
• How: Use separate files for each task:
o Main.c: Main program loop.
o Switch.c: Code to handle the switch inputs and debouncing.
o Display.c: Code to show the count on a display.
o Main.h, Switch.h, Display.h: Header files for function prototypes and
definitions.

2. Main Program (Main.c)

• What it does: Initializes the switch and display, then counts the switch presses and
updates the display.
• Simple Example:

#include "Main.h"
#include "Switch.h"
#include "Display.h"

void main(void)
{
int count = 0;

SWITCH_Init(); // Initialize switch


DISPLAY_Init(); // Initialize display

while (1) {
if (SWITCH_IsPressed()) {
count++; // Increment count when switch is pressed
}
DISPLAY_ShowCount(count); // Display the count
}
}

3. Switch Handling (Switch.c)

• What it does: Waits for a button press and handles debouncing (prevents multiple counts
for one press).
• Simple Example:
#include "Switch.h"

void SWITCH_Init(void) {
// Configure switch pin
SwitchPin = 1; // Set as input
}

int SWITCH_IsPressed(void) {
if (SwitchPin == 0) { // If switch is pressed
DELAY(100); // Wait for debounce
return 1;
}
return 0;
}

4. Display Handling (Display.c)

• What it does: Shows the count on the display (could be LEDs or an LCD).
• Simple Example:

#include "Display.h"

void DISPLAY_Init(void) {
// Initialize the display (set pins, etc.)
}

void DISPLAY_ShowCount(int count) {


// Display the count value on the display
DisplayPort = count;
}

5. Key Points

• Modular Code: Split tasks (switch handling, display) into separate files.
• Simple Logic: In the Main.c, continuously check if the switch is pressed, update the
count, and show it on the display.
• Debouncing: Use a delay to prevent counting multiple presses from one button press.

This approach makes the program cleaner and easier to modify.


. Design and Develop an embedded C program for restructuring the
"Hello embedded world"?

1. Main.H (Header File)


#ifndef _MAIN_H
#define _MAIN_H
#include <reg52.h> // Microcontroller-specific header
#define OSC_FREQ 12000000UL // Oscillator frequency
#define OSC_PER_INST 12 // Oscillator cycles per instruction
typedef unsigned char tByte;
typedef unsigned int tWord;
typedef unsigned long tLong;
#endif

2. Port.H (LED Pin Definition)


#ifndef _PORT_H
#define _PORT_H
sbit LED_pin = P1^5; // Define LED pin
#endif

3. LED_Flash.H (LED Function Prototypes)


#ifndef _LED_FLASH_H
#define _LED_FLASH_H
void LED_FLASH_Init(void);
void LED_FLASH_Change_State(void);
#endif

4. LED_Flash.C (LED Control Functions)


#include "Main.H"
#include "Port.H"
#include "LED_Flash.H"
static bit LED_state_G;

void LED_FLASH_Init(void) {
LED_state_G = 0;
}

void LED_FLASH_Change_State(void) {
if (LED_state_G == 1) {
LED_state_G = 0;
LED_pin = 0; // LED OFF
} else {
LED_state_G = 1;
LED_pin = 1; // LED ON
}
}

5. Delay_Loop.H (Delay Function Prototype)


#ifndef _DELAY_LOOP_H
#define _DELAY_LOOP_H
void DELAY_LOOP_Wait(const tWord DELAY_MS);
#endif

6. Delay_Loop.C (Delay Function)


#include "Main.H"
#include "Port.H"
#include "Delay_Loop.H"

void DELAY_LOOP_Wait(const tWord DELAY_MS) {


tWord x, y;
for (x = 0; x <= DELAY_MS; x++) {
for (y = 0; y <= 120; y++);
}
}

7. Main.C (Main Program)


#include "Main.H"
#include "Port.H"
#include "Delay_Loop.H"
#include "LED_Flash.H"

void main(void) {
LED_FLASH_Init();
while(1) {
LED_FLASH_Change_State();
DELAY_LOOP_Wait(1000); // Delay for 1000 ms
}
}

• Modular Code Structure:

• The program is split into multiple files to make the code more organized and
maintainable.
• Each file has a specific responsibility: for example, one file handles the LED control,
another file handles delays, and one file contains the main program logic.

• Main.H:

• Microcontroller-specific settings like the oscillator frequency and cycles per instruction
are defined here.
• Type definitions are provided for easy use of data types (tByte, tWord, tLong).
• Port.H:

• This file contains the definition of the LED pin (LED_pin) and links it to the
microcontroller's hardware. It is simple and specific to the pin that controls the LED.

• LED_Flash.H & LED_Flash.C:

• The header (LED_Flash.H) contains function prototypes for initializing and changing
the LED state.
• The C file (LED_Flash.C) implements the functions:
o LED_FLASH_Init: Initializes the LED state.
o LED_FLASH_Change_State: Toggles the LED (ON/OFF).

• Delay_Loop.H & Delay_Loop.C:

• Delay_Loop.H declares the delay function, which provides a rough delay in


milliseconds.
• Delay_Loop.C defines the actual delay function using nested loops to introduce a time
delay.

• Main.C:

• The main program initializes the LED and then enters an infinite loop.
• Inside the loop, the LED state is toggled (ON/OFF), and a delay is introduced to make the
LED flash visible.

This structure separates the logic into modular files for readability and reusability.

You might also like