Skip to content

4. Embedded programming

Core Focus Areas This Week

  1. Microcontroller Fundamentals
    • Harvard and Von Neumann architecture
    • Memory types (Registers, SRAM, Flash)
    • GPIO operations and peripheral interfaces
  2. Key Processors to Master
    • ATtiny412 (8-bit AVR) - Simple & cost-effective
    • RP2040 (ARM Cortex-M0+) - Advanced features & PIO
    • ESP32 (WiFi/Bluetooth capabilities)
  3. Essential Tools
    • Wokwi Simulator for virtual prototyping
    • Arduino IDE + megaTinyCore for ATtiny
    • Raspberry Pi Pico SDK for RP2040
Day To-Do Think
Day 1: Foundation Setup - [x] Study microcontroller basics (Harvard vs. Von Neumann).
- [x] Review ATtiny412 datasheet (Sections 2-6).
- [x] Install Arduino IDE + megaTinyCore.
- [x] Set up Wokwi Simulator.
- 🔍 What are the key differences between Harvard and Von Neumann architectures?
- 🔍 How does ATtiny412 manage memory and registers?
Day 2: GPIO Control - [x] Learn digital I/O operations (LED blinking, button reading).
- [x] Write & test simple GPIO code.
- [x] Simulate LED blink in Wokwi.
- 🔍 How does digitalWrite() affect the pin state?
- 🔍 Why use !digitalRead(3) to toggle the LED?
Day 3: Peripherals & Timers - [x] Study PWM, ADC, and timers in ATtiny412.
- [x] Implement PWM-based LED dimming.
- [x] Use AVR Insights to explore registers.
- 🔍 How does analogWrite() control LED brightness?
- 🔍 What role do timers play in PWM generation?
Day 4: Debugging & Simulation - [x] Learn serial debugging using Serial.print().
- [x] Simulate sensor interfaces (potentiometer + LED).
- [x] Test analog input reading (analogRead()).
- 🔍 Why is Serial.begin(9600) necessary?
- 🔍 How can serial output help debug the program?
Day 5: Final Project Alignment - [x] Identify all components for the final project.
- [x] Prototype one subsystem (LED pattern controller).
- 🔍 What features can enhance my project?
- 🔍 How should I structure my final code efficiently?
Day 6: Documentation & Testing - [x] Test programming workflows on physical boards.
- [x] Document findings & observations.
- 🔍 How do real-world results compare to simulations?
- 🔍 What challenges did I face during testing?
Day 7: Assignment Submission - [x] Compile documentation and test results.
- [x] Submit the project assignment.
- 🔍 How can I improve my approach for future projects?
- 🔍 What key lessons did I learn this week?

GROUP ASSIGNMENT

we learned about different architectures that are used in microcontrolers . we also looked into different sets of boards like esp 32 , rp2040 ,rasperry pi pico , rasberry pi 5 etc . We refgered data sheets of all these .

GROUP ASSIGNMENT

Rasberry pi pico

I am trying rasberry pi co for this week simulation using wokwi .

The Raspberry Pi Pico is a versatile microcontroller development board based on the RP2040 chip. It features a dual-core ARM Cortex-M0+ processor, 2MB of onboard flash memory, and extensive GPIO capabilities. Through hands-on experimentation, I explored its features including PWM control, analog inputs, and digital communications.

RP 2040

The RP2040 is a powerful dual-core ARM Cortex-M0+ microcontroller developed by Raspberry Pi. It features 264KB of SRAM, flexible clock frequencies up to 133 MHz, and programmable I/O (PIO) state machines that make it ideal for precise timing and custom protocols. I explored its capabilities through various projects using the Raspberry Pi Pico development board.

The below photo is a board of seeed studio using RP 2040

ARDUINO

Download https://www.arduino.cc/en/software Download from Above page and complete the installation.

LEARNINGS

Pull-up resistors:

  • Connect the pin to VCC (usually 3.3V for ESP32)

  • Ensure the pin reads HIGH when not actively driven LOW

  • Commonly used in ESP32, with internal pull-ups available

Pull-down resistors:

  • Connect the pin to ground (0V)

  • Ensure the pin reads LOW when not actively driven HIGH

  • Less common, but still used in certain applications

PIO PINS

PIO (Programmable Input/Output) pins are a specialized feature found in some microcontrollers, including the Raspberry Pi Pico. They offer several advantages over standard GPIO pins:

  • Independent data processing: PIO pins can handle data transmission and reception without using CPU resources4. This allows for more efficient use of the microcontroller’s processing power.

  • Customizable functionality: PIO pins can be programmed using a special assembly language to perform specific tasks4. This enables the creation of custom communication protocols or timing-sensitive operations.

  • Parallel processing: The Raspberry Pi Pico, for example, features 8 PIO state machines that can run simultaneously4. This allows for multiple independent I/O operations to occur in parallel.

  • Resource management: By offloading tasks to PIO pins, microcontrollers can better manage their limited processing power and memory4.

  • Continuous instruction execution: PIO pins are particularly useful for processes that require constant input or output, such as LED fading or precise timing control4.

  • Decoupling from CPU: PIO pins can execute instructions independently of the central CPU, allowing for more efficient multitasking4.

  • Flexible data handling: PIO pins use FIFO (First-In-First-Out) buffers for input and output, enabling efficient data transfer between the CPU and the PIO state machines4.

Then i aske what is DMA . here are my Results .

DIRECT MEMORY ACCESS (DMA)

Direct Memory Access (DMA) is a feature in computer systems that allows certain hardware subsystems to access main system memory independently of the central processing unit (CPU)13. Here are the key aspects of DMA:

  • Purpose: DMA enables data transfers directly between memory and peripherals, reducing CPU intervention and freeing up processing resources for other tasks1.

  • Performance improvement: By offloading data transfer tasks from the CPU to the DMA controller, system performance is enhanced, increasing overall throughput and efficiency3.

How it works:

  • A DMA controller manages the data transfer between memory and peripherals3.

  • The CPU initiates the transfer by setting up the DMA controller with source and destination addresses, transfer direction, and data block size1.

  • The DMA controller then handles the transfer independently, allowing the CPU to perform other operations3.

  • Applications: DMA is crucial for efficient data transfer with peripherals like disk drives, graphics cards, network cards, and audio devices13.

  • Transfer modes: DMA can operate in different modes, including burst mode, cycle-stealing mode, and transparent mode, each suited for specific system requirements3.

Advantages:

  • Reduces CPU overhead for data transfers3

  • Allows parallel processing of tasks1

  • Improves overall system efficiency13

WOKWI

Image 1 Image 2

Plus tab is used to add documents .

Play button is used to run the program .

Tried some simulations using wokwi software

LED Blinking

Controlling brightness using analog inputs.

void setup() { pinMode(3, OUTPUT); }  
void loop() { analogWrite(3, 128); } // 50% duty cycle  

Here i

LED Blinking

void setup() { pinMode(3, OUTPUT); }  
void loop() { digitalWrite(3, !digitalRead(3)); delay(500); }  

The setup() Function

The setup() function runs once when the Arduino board starts up or is reset1. It’s used to initialize variables, pin modes, start using libraries, etc. In this code:

pinMode(3, OUTPUT); configures pin 3 as an output pin, allowing it to control an LED or other device.

The loop() Function

The loop() function runs continuously after setup() completes, forming the main body of the program1. It allows your program to change and respond. In this code:

digitalWrite(3, !digitalRead(3)); toggles the state of pin 3:

digitalRead(3) reads the current state of pin 3

! inverts this state

digitalWrite(3, …) writes the inverted state back to pin 3

delay(500); pauses the program for 500 milliseconds (half a second)

I was not knowing what serial1begin stands for . so i asked perplexity and these are my results .

Serial1: This refers to one of the additional hardware serial ports available on certain Arduino boards, such as the Arduino Mega2. It’s separate from the default Serial port used for USB communication.

begin(): This function sets up the serial port for communication5.

115200: This is the baud rate, which determines the speed of data transmission in bits per second3. Both the sending and receiving devices must use the same baud rate for successful communication.

void setup() {

Serial1.begin(115200);

}

void loop() {
Serial1.println("Hello, Raspberry Pi Pico!");
delay(2000); 
Serial1.println("2 sec elapsed");
delay(1000); 
}

POTENTIOMETER + LED

const int potPin = A0;
const int ledPin = 9;

void setup() {
  Serial.begin(9600);
  pinMode(ledPin, OUTPUT);
}

void loop() {
  int potValue = analogRead(potPin);
  int ledBrightness = map(potValue, 0, 1023, 0, 255);
  analogWrite(ledPin, ledBrightness);

  Serial.print("Potentiometer value: ");
  Serial.print(potValue);
  Serial.print(" LED brightness: ");
  Serial.println(ledBrightness);

  delay(100);
}

Here map function is used to

The map() function takes the potValue and proportionally converts it from the 0-1023 range to the 0-255 range. For example:

If potValue is 0, ledBrightness will be 0

If potValue is 1023, ledBrightness will be 255

If potValue is 512 (halfway), ledBrightness will be 127

the working vidio is attached below

TWO LED RING WITH A SWITCH

I was going through wokwi prebuilt projects where i saw an led ring that is Run . First i used perplexity to understand the code and then i thought about adding an additional ring to the circuit . so i tried to do that. Below is the Image and code associated

from machine import Pin
from neopixel import NeoPixel
from time import sleep

rainbow = [
    (126, 1, 0), (114, 13, 0), (102, 25, 0), (90, 37, 0), (78, 49, 0), (66, 61, 0), (54, 73, 0), (42, 85, 0),
    (30, 97, 0), (18, 109, 0), (6, 121, 0), (0, 122, 5), (0, 110, 17), (0, 98, 29), (0, 86, 41), (0, 74, 53),
    (0, 62, 65), (0, 50, 77), (0, 38, 89), (0, 26, 101), (0, 14, 113), (0, 2, 125), (9, 0, 118), (21, 0, 106),
    (33, 0, 94), (45, 0, 82), (57, 0, 70), (69, 0, 58), (81, 0, 46), (93, 0, 34), (105, 0, 22), (117, 0, 10)
]

pixels = NeoPixel(Pin(15), 16)

while True:
    rainbow = rainbow[-1:] + rainbow[:-1]
    for i in range(16):
        pixels[i] = rainbow[i]
    pixels.write()
    sleep(1)  # You may want to change this back to 0.1 for smoother animation

How does the rainbow function work here ? (Prompt)

The line rainbow = rainbow[-1:] + rainbow[:-1] is a concise way to rotate the rainbow list by one position, moving the last element to the front. Let’s break it down:

rainbow[-1:] creates a new list containing only the last element of rainbow.

rainbow[:-1] creates a new list with all elements of rainbow except the last one.

from machine import Pin
from neopixel import NeoPixel
from time import sleep

# Define the rainbow color sequence
rainbow = [
    (126, 1, 0), (114, 13, 0), (102, 25, 0), (90, 37, 0), (78, 49, 0), (66, 61, 0), (54, 73, 0), (42, 85, 0),
    (30, 97, 0), (18, 109, 0), (6, 121, 0), (0, 122, 5), (0, 110, 17), (0, 98, 29), (0, 86, 41), (0, 74, 53),
    (0, 62, 65), (0, 50, 77), (0, 38, 89), (0, 26, 101), (0, 14, 113), (0, 2, 125), (9, 0, 118), (21, 0,106),
    (33 ,0 ,94),(45 ,0 ,82),(57 ,0 ,70),(69 ,0 ,58),(81 ,0 ,46),(93 ,0 ,34),(105 ,0 ,22),(117 ,0 ,10)
]

# Initialize NeoPixel and button

pixels = NeoPixel(Pin(15), total_leds :=16)
button = Pin(4, Pin.IN, Pin.PULL_UP) # Button connected to GPIO4 with an internal pull-up resistor

# Variables for animation state
animation_on = False

# Function to check button press

def check_button():
    global animation_on
    if not button.value(): # Button pressed
        sleep(0.2) # Debounce delay
        animation_on = not animation_on # Toggle animation state

while True:
    check_button() # Check if the button is pressed

    if animation_on:
        # Rotate rainbow colors and update LEDs
        rainbow = rainbow[-1:] + rainbow[:-1]
        for i in range(total_leds):
            pixels[i] = rainbow[i % len(rainbow)] # Wrap around if needed
        pixels.write()
        sleep(1) # Adjust delay for animation speed

Conclusion

I also explored basic microcontroller programming, implementing a simple LED blinking program to test the board’s functionality. This hands-on experience provided valuable insights into the entire PCB production workflow, from design to programming.

Overall, this week’s assignment deepened my understanding of electronics production processes and their integration with digital fabrication techniques. The skills acquired will be instrumental in future projects, particularly for my final quality inspection system.


Last update: February 19, 2025