Need Help? Contact us at:

Extreme Embedded Firmware Engineering Learning Path

3 courses | 44+ hours | Complete Source Code Included

         Your free gift is on its way to your inbox, but before you go 
check out this very special offer, just for you!

1. Embedded Build Systems with GNU Tools and Makefiles

Extreme Embedded Bare-Metal Development

        No  Integrated Developed Environment (IDE) used :
        just the command line, a text editor and makefiles.
        10+ hours of quality training | Complete source code included
Have you ever wondered what it is like to develop embedded firmware without using any IDE- just a simple text editor and the command line ?

Have you heard of build systems like Make, if so have you ever wondered how these tools can be applied to embedded firmware development to automate the build process? 

If you have no idea of what build systems like Make are, do you want to learn about them from scratch and apply them to your embedded firmware development ?

Preview #1
Lesson  : Writing the StartUp file(Pt.3)
In this lesson we complete the implementation of our startup.c file by writing the Reset_Handler()
Preview #2
Lesson :  Exploring the GNU Bin Tools- Analyzing Object files
In this lesson we shall see how to analyze an object file using the objdump tool the comes with our GNU Toolchain.
If any of this applies to you then keep reading this overview of our new course :

       Extreme Embedded Bare-Metal Development

The goal of this course is to teach you how to set up an embedded toolchain, set up a build system, and then navigate the reference manual and datasheet of the tools as well the target microcontroller to develop firmware for the target microcontroller without using any IDE (Integrated Development Environment), libraries or third party header files.

Exactly What You're Getting

This is dramatically different from any course you have ever taken because like many of my courses, this is more of a professional hands-on “field guide” to stm32 extreme bare metal firmware development. The reason why is because there’s no fluff or filler. It immediately gets down to the actual subject, showing you exactly what to do, how to do it, and why.

Plus, it’s easy.

And you’ll immediately “get” the entire mythology I personally use to build firmware for consumer devices in my professional life.

It's About MORE Than Just Getting the Code to Work
If at least one of the following applies to you then keep reading if not then simply skip this course:

" Escape From "

  • Using Integrated Development                                          Environments (IDE)
  • ​Copying/Pasting code you don’t understand
  • Using third party libraries and header files                like HAL, LL and StdPeiph
  • Experiencing bugs you don’t understand
  • ​Being afraid of technical documentations                  like the reference manual and datasheet of               the chip
  • ​Imposter syndrome

" Arrive At "

  • Using no IDEs- applying build systems like                 Make
  • Write your own Linker Script
  • ​Write your C Startup file​
  • ​Build every single line of code from scratch               by writing to the microcontroller’s memory               space directly.
  • Use No third party libraries or header files
  • Understand and write every single line of                   code yourself- no Copy/Paste
  • ​Use the debugger effectively to analyze                       and  resolve any bugs
  • ​Develop proficiency in your embedded                         development skills and confidently take                       the next steps
So like I said, there’s more than just getting each piece of code to work. 

Here’s an overview of what you’re getting...
Understanding the Build Process:
In order to be able to truly develop firmware from scratch we need to understand what goes on
at each and every stage as the .c and .h source files are being converted to .elf executables. We will analyze the Preprocessing Stage -> the Compiling Stage -> the Assembling Stage ->the Linking Stage  all the way to the Locator Stage.
Writing the Linker Script:
To be able to properly merge the various source files and place different sections of the source files into different memory regions of our target microcontroller we need to write our own linker script to tell the linker the different regions and sizes of memory available on our target microcontroller and also in which regions of memory we want to store specific sections of the source code.
Writing the C Startup file
The Reset_Handler is the first function to be executed when microcontroller comes out of reset. We will have to define this function in our C Startup file. We will also have to define the vector table in this same file.
Automating the Build Process with Make
A Build System is a piece of program that takes source code as input and produces a deployable software as output. Make is one of the popular Build Systems out there. We shall learn how to automate our build process with Make.
Analyzing the chip documentations:
Before developing the firmware for any chip you have to learn how to read the documentation provided by the chip manufacturer.
Defining address for the different peripheral:
All components on the microcontroller have an address range.To write to a component or read from a component you need to locate its address range in the documentation and properly define the addresses in your code.
Creating registers from the address:
The addresses in the address range of a component represent the registers of that component. To access these registers you have effectively typecast the addresses.
Understanding CMSIS:
Cortex-Microcontroller Interface Standard (CMSIS)CMSIS is a standard developed by Arm for all Cortex-Microcontrollers. This is the standard used in professional firmware development.
By the end of this course...

You Will Be Able To :

  • Build complete firmware without using an Integrated Development Environment (IDE)
  • ​Write your own Linker Script
  • Write your own C Startup file
  • ​Effectively apply GNU Bin Tools
  • ​Effectively apply Build Systems like Make to your Embedded Development
  • ​Effectively write your own Makefiles to automate the Build Process in your Embedded Projects
  • ​Build every single line of code from scratch by writing to the microcontroller’s memory space directly.
  • ​Use No third party libraries or header files
  • ​Develop proficiency in your embedded development skills and confidently take the next steps
  • ​Define addresses for the different peripherals
  • ​Analyze the chip documentation
  • ​Create registers from the addresses

Table of Contents

  • Development Environment
  • ​Ways of Firmware Development
  • ​Tools of the Trade
  • ​Overview of the Development Environment
  • ​Installing GCC for Arm
  • ​Setting Up OpenOCD
  • ​Constructing Peripheral Registers from Memory Addresses
  • ​Getting the best out of this course
  • ​Downloading our Integrated Development Environment (IDE) for Control Experiment
  • ​Installing an Integrated Development Environment (IDE) for Control Experiment
  • Getting the right Documentation for Bare-Metal Development
  • ​Programming : Locating the Ports and Pins of Components on the Nucleo board
  • ​Defining Addresses of Modules using information from the Documentation
  • ​Programming : Creating required Registers using Information from Documentation
  • ​Programming : Configuring Pins using the Registers we Created
  • ​Programming : Creating Registers from Structure Members
  • ​Understanding the Build Process and Exploring the GNU Toolchain
  • ​​Understanding the Build Process
  • ​Overview of Some GNU Bin Tools
  • ​Programming : Observing the Build Process from IDE Perspective
  • ​Compiling and Linking Existing Source files using the GNU Arm Toolchain
  • ​Programming : Exploring the GNU Bin Tools - The Compiler
  • ​Programming : Exploring the GNU Bin Tools - Adding Options for Arm Cortex
  • ​Programming : Exploring the GNU Bin Tools - Stopping After Compilation
  • ​Programming : Exploring the GNU Bin Tools - Analyzing Object files
  • ​Developing the Linker Script and Startup File
  • ​Understanding the Memory Model and Linker Script
  • ​Getting familiar with some Linker Commands
  • ​Analyzing the Linker Script Generated by CubeIDE
  • ​Understanding Linker Constants
  • ​Programming : Writing the Linker Script (Pt.1)- Memory Definition
  • ​Programming : Writing the StartUp file (Pt.1)- Creating the ISR Vector Section
  • ​Programming : Writing the StartUp file (Pt.2)- Populating the Vector Table
  • ​Programming : Verifying the Creation of the Custom Section
  • ​Understanding the load Memory of different Sections
  • ​Programming : Writing the Linker Script (Pt.2)- Merging Sections
  • ​Understanding Linker Symbols
  • ​The Location Counter
  • ​Example of a simple Linker Script
  • ​Programming : Writing the Linker Script (Pt.3)- Creating Symbols
  • ​Programming : Writing the Linker Script (Pt.4)- Testing the Linker Script
  • ​Programming : Writing the Linker Script (Pt.5)- Aligning Memory Sections
  • ​Programming : Writing the StartUp file (Pt.3)- Writing the Reset_Handler
  • ​Programming :Testing the Linker Script on the Target
  • ​Programming : Flashing the Target using GDB Client
  • The "Make" Build System
  • ​Introduction to Build Systems and Makefiles
  • ​Setting Up Make
  • ​Programming : Automating the Build Process using Make
  • ​Programming : Using Variables in Makefiles
  • ​Programming : Testing the Makefile
  • ​Integrating the Cortex-M Software Interface Standard (CMSIS)
  • ​Introduction to CMSIS and It's Components
  • ​Understanding the CMSIS Standard
  • ​Overview of ARM Cortex-M General Purpose Input/Output Module
  • ​More Techniques on Using Make
  • ​Programing : Integrating CMSIS into our Firmware
  • ​Programing : Creating Output Folders with Make
  • ​Programming : Generating Map files into Output Folders
  • ​Programming : Using Folder Variables and Input Folders
  • ​Programming : Building with Assembly Source files
  • ​Programming : Building with C++ Source files
  • ​Sending ADC Sensor Data using Semihosting
  • ​Introduction to Analog to Digital Conversion
  • ​Understanding ADC Independents Modes
  • ​Programming : Developing the ADC Single Conversion Driver
  • ​Programming : Developing the ADC Continuous Conversion Driver
  • ​Programming : Displaying Sensor Data with Semihosting (Pt.1)
  • ​Programming : Displaying Sensor Data with Semihosting (Pt.2)

Specially Designed For People Who Hate 

Listen. If you don’t like “Copy/Paste” you’re not alone. I can’t stand it either. I’d literally rather have a piece of code that I wrote from scratch that doesn’t work than someone else’s working code I copied and pasted.

And that’s why I’ve spent months designing and recording this course in which I show you how to locate every single register used and the meaning of every hexadecimal value written into the register. 
Although the course explains every single line of code .... you will also get

Access to the EmbeddedExpertIO Forum

where you can ask questions and discuss embedded systems topics.

2. Modern Bare-Metal Embedded C++ 
     From Ground Up                   

No  Libraries (IDE) used : Template Programming, Object Oriented Programming, Peripheral Driver Dev. etc.
  18+ hours of quality training | Complete source code included
      Practical programming course on embedded systems programming                                            using the C++ programming language
Key features of C++ such as template programming and object-oriented programming can greatly improve embedded software portability, in recent years this has made C++ very attractive to embedded developers.

 Goal of this course 
is to teach you how to navigate the microcontroller reference manual and datasheet to extract the right information to professionally build peripheral drivers and firmware. To achieve this goal, no libraries are used in this course, purely bare-metal Embedded-C++ and register manipulations.

By the end of this course you will be able write drivers for peripherals like ADC, UART, PWM, GPIO, TIMER,I2C, SPI, etc. You will also master the ARM architecture and how to build professional embedded firmware for ARM processors.

Furthermore, you will master C++ key features like Object-Oriented methods, Template Programming, and optimization.
Lesson : Creating a simple LED Class (PART I) 
By the end of this course...

You Will Be Able To :

  • Write Class Templates for accessing Microcontroller Registers
  • ​Write Object-Oriented Peripheral Drivers
  • Master Object-Oriented Techniques for Microcontrollers
  • ​Master C++ Templates for Microcontrollers
  • ​Write Universal Asynchronous Receiver-Transmitter (UART) drivers using bare-metal-C++
  • ​​Write Analog-to-Digital Converter (ADC) drivers using bare-metal Embedded-C++
  • ​Write General Purpose Timer (GPTM) drivers using bare-metal Embedded-C++
  • ​Write System Tick (SysTick) Timer drivers using bare-metal Embedded-C++
  • ​Write Serial Peripheral Interface (SPI) drivers using bare-metal Embedded-C++
  • ​Write Inter-Integrated Circuit (I2C) drivers using bare-metal Embedded-C++

Table of Contents

  • Getting Started with Embedded C++
  • ​Creating a simple LED Class (PART I)
  • ​Creating a simple LED Class (PART II)
  • ​C++ Essential Training for C Developers
  • ​Configuring our UART driver for displaying results (Part I)
  • ​Configuring our UART driver for displaying results (Part II)
  • ​Understanding Classes and Objects
  • ​Dynamic Allocation
  • ​Variable References
  • ​Understanding Function Templates
  • ​Using Default Arguments
  • ​Understanding Pass by Reference and Pass by Value
  • ​Understanding Pass by Address
  • ​Return by Address
  • ​Class Property Functions
  • ​Class Constructors
  • ​Understanding Scope Resolution
  • ​Understanding "this" Pointer
  • ​Differences between Class and Struct
  • ​The function "friend"
  • ​Class Inheritance
  • ​Understanding Access Specifiers
  • ​Class Pointers
  • ​Function Overriding
  • ​Virtual Functions
  • ​Polymorphism (Part I)
  • ​Polymorphism (Part II)
  • ​The class "friend"
  • ​Static Variables
  • ​Static Functions
  • ​Class Template
  • ​Understanding namespaces
  • ​Class destructors
  • ​Class virtual destructors
  • ​Microcontroller C++ Template Programming
  • ​​Introduction to Microcontroller Template Programming
  • ​Developing a Template for accessing Microcontroller Registers (Version 1)
  • ​Developing a Template for accessing Microcontroller Registers (Version 2)
  • ​​Register Bit-mapping (Part I)
  • ​​Register Bit-mapping (Part II)
  • ​​Applying Register Bit-mapping to Register Access Class Template
  • ​​Developing a Microcontroller Port Class Template

  • ​General Purpose Input/Output(GPIO) C++ Driver Development
  • ​Overview of ARM Cortex-M General Purpose Input/Output Module
  • ​Developing a GPIO Output Driver using information from the datasheet
  • ​Developing a GPIO Output Driver using the BSRR Register
  • ​Developing a GPIO Input Driver
  • ​Universal Asynchronous Receiver-Transmitter(UART) C++ Driver Development
  • ​Overview of the UART Protocol
  • ​Developing the UART Driver Using Information from the datasheet
  • ​Receiving Data with the UART
  • ​Two-way UART Communication
  • ​UART std::cout Retargeting
  • ​System Tick and General Purpose Timers C++ Driver Development
  • ​Overview of the System Tick Timer
  • ​Overview of General Purpose Timers
  • ​Developing the System Tick Timer Driver using information from the datasheet
  • ​Creating a Delay Function using the System Tick Timer
  • ​Analyzing General Purpose Timer registers
  • ​Developing the General Purpose Timer driver
  • ​Writing a driver for a different timer module
  • ​Developing the Timer Compare Mode Driver
  • ​Analog -to- Digital Converter (ADC) Driver Development
  • ​Introduction to Analog to Digital Conversion
  • ​Developing the ADC Driver
  • ​Inter-Integrated Circuit (I2C)
  • ​Introduction to I2C
  • ​Analyzing the DS1307 Realtime Clock
  • ​Creating I2C Registers
  • ​Writing the I2C Initialization function
  • ​Writing the I2C Read and Write Functions
  • ​Testing our I2C Driver
  • ​Serial Peripheral Interface (SPI)
  • ​Introduction to SPI
  • ​Creating SPI Registers
  • ​Writing a basic SPI Driver
  • ​Developing an SPI Library (PART I)
  • ​Developing an SPI Library (PART II)
  • ​Testing the SPI Library

3. Embedded Systems Design Patterns 
     From Ground Up                   

 Client-Server Design Pattern,Observer Pattern,Hardware Proxy Design Pattern etc.
  16+ hours of quality training | Complete source code included
This course teaches you how to... 
      Apply design patterns to embedded firmware development
Design patterns are reusable solutions to commonly occurring problems in software development. 

Design patterns allow us to think about solutions in a more abstract way and therefore identify and underscore the important properties of the solution. Also, design patterns allow us to reuse solutions that have been proven to be effective in other similar circumstances. 

 Goal of this course 
is to provide a set tools for firmware developers to deal with commonly recurring firmware design issues.
The course focuses on practical solutions by taking real-world problems and solving them using various design pattern solutions, examples such as data access in an ECG system using the Client-Server Design Pattern, IO device development using the Strategy Design Pattern, hardware portability using Hardware Proxy Design Pattern, Sensor Data Subscription and Notification Observer Design Pattern etc.
Lesson : Testing the Observer Pattern with Actual Sensors
By the end of this course...

You Will Be Able To :

  • Implement Client-Server Design Pattern for accessing data in an ECG system
  • ​Implement the Hardware Proxy Design Pattern to enable hardware portability
  • Implement Observer Design Pattern for Subscribing to Sensor Data
  • ​Master C++ Templates for Microcontrollers
  • ​Implement the STRATEGY Design Pattern in your firmware
  • ​Implement the STATE Design Pattern in your firmware
  • ​Implement the Hardware Adapter Design Pattern in your firmware
  • ​Master Embedded-C Bit manipulations

Table of Contents

  •  Getting Started - Th First Class ADT
  • ​Coding : Collecting Relevant Addresses from Datasheet
  • ​​Coding : Creating Registers from Addresses
  • ​​Coding : Implementing the Device Interface file
  • ​​Coding : Implementing Device Client APIs (PART I)
  • ​​Coding : Implementing Device Client APIs (PART II)
  • ​​Coding : Implementing Device Client APIs (PART III)
  • ​​Coding : Implementing Device Client APIs (PART IV)
  • ​Introduction to Design Pattern
  • ​What is a Design Pattern ?
  • ​​UnderStanding UML Notations
  • ​​Coding : Understanding Bit Masking
  • ​​Coding : Understanding Bit Fields
  • ​ ​The STATE Design Pattern
  • ​​Coding : Conditional Implementation of State Machines-Writing the Interface file
  • ​​Coding : Implementing the first Time Source
  • ​​Coding : Implementing the second Time Source
  • ​​Coding : Implementing the Watch Functions
  • ​​Coding : Testing our Implementation
  • ​​Coding : Table-based State Machine Implementation
  • ​​Coding : The STATE Pattern Implementation
  • ​The STRATEGY Design Pattern
  • ​Coding : The STRATEGY Design Pattern Implementation (PART I)
  • ​​Coding : The STRATEGY Design Pattern Implementation (PART II)
  • ​​Developing Peripheral Drivers for Sensor Data Collection
  • ​Coding : Developing a Driver for Collecting Digital Input Data
  • ​​Coding : Developing a Driver for Collecting Analog Input Data
  • Coding : Developing a Driver for Reading the Internal Temperature of the MCU
  • ​ ​The Hardware Proxy Design Pattern
  • ​Introduction to the Hardware Proxy Pattern
  • ​​Coding : Writing the Hardware Proxy Interface files
  • ​​Coding : Implementing the Hardware Proxy Functions
  • ​​Coding: Writing the data Encoding and Decoding functions
  • ​​Coding : Implementing more Hardware Proxy functions
  • ​​Coding : Testing the Hardware Proxy solution
  • ​The Hardware Adapter Design Pattern
  • ​​Introduction to the Hardware Adapter Pattern
  • ​​Writing the Hardware Adapter Interface files
  • ​​Coding: Implementing the Hardware Proxy functions
  • ​​Coding : Implementing the Trans-impedence Amplifier(TIA) Adapter functions
  • ​​Coding : Implementing the Light-to-frequency (LTF) Adapter functions
  • ​​Coding: Testing the Adapter with a Client
  • ​The Client-Server Design Pattern
  • ​Introduction to the Client-Server Pattern
  • ​​Coding : Writing the server interface file
  • ​​Coding : Writing the server functions
  • ​​Coding : Writing the HistogramDisplay client interface file
  • ​​Coding: Writing the ECG Module interface file
  • ​​Coding : Writing the ECG Module functions
  • ​​Coding : Writing the HistogramDisplay client functions
  • ​​Coding : Writing the interface file of the SystemManager
  • ​​Coding : Implementing the SystemManager functions
  • ​​Coding : Testing the System with a Single Client
  • ​​Coding : Writing the Interface file for the ArrythmiaDetector Client
  • ​​Coding : Implementing the ArrythmiaDetector Client functions
  • ​​Coding : Implementing the QRSDetector Client
  • ​​Coding : Integrating multiple clients into to the System
  • ​​Observer Design Pattern (Publisher-Subscriber Pattern )
  • ​Introduction to the Observer Pattern
  • ​​Coding : Writing the Interface file for the Server
  • ​​Coding : Implementing the Server functions
  • ​​Coding : Writing the Interface file of the Fertilizer Mixer Client
  • ​​Coding : Implementing the Fertilizer Mixer Client functions
  • ​​Coding : Implementing the Display Client
  • ​​Coding : Testing the Observer Pattern
  • ​​Coding : Testing the Observer Pattern with Actual Sensors
A little about me : Israel Ninsaw Gbati
Some of you may have taken some of my embedded systems courses from other online platforms. 
This is my private channel. 

I have been writing embedded firmware for years, I have built embedded devices like consumer products and robotic arms.
Till date I have 
trained over 75,000 students in embedded
 firmware development online till date
...including third year undergraduate university students in-person.

If you have taken any of my courses before you will know I start from the absolute basics, I do not assume that the student has any prior knowledge of the topic under discussion. You will also know that by the end of the course you understand the functions of every register used in developing the particular firmware or driver.

This method is the same for all of my published embedded systems courses. 


Sometimes I could get my firmware to work but I couldn’t understand a large portion of the code.

I didn’t know what some of the registers were doing. "Why do we write this hexadecimal number into that particular register ?" I would often ask.

Other times I could understand every line of code in the firmware but couldn’t get the firmware to work.

Because I wasn’t good enough, I couldn’t build exactly what I wanted if there were no already made drivers and libraries out there that I could use. Worst of all I couldn’t even get another microcontroller to work apart from the microcontroller used in class.
Long story short, I overcame all of this....
I devised a plan to master the fundamentals...
Quickly read the sections of interest in the datasheet...
Created my own firmware development checklist...
Created my own study guide...

I started creating courses to help other people like yourself master embedded systems development in the most efficient way possible, no waste of time, no frustrations. There is no need for you to go through the same roadblocks and frustrations I went through  some years ago.
Our courses have been reviewed by 1000+ students
Here are some of the reviews

 30 Day Money Back Guarantee

Now it's time for you also to benefit from the...

Modern Embedded-C 
From Ground Up

Here's a recap of


When You Purchase This AMAZING Offer!

  • 1. Extreme Embedded Bare-Metal Development  ($69.99 Value)
  • Duration: 10+ hours
  • Resources: Lifetime access to videos + Complete source code
  • ​2. Modern Bare-Metal Embedded-C++ From Ground Up ($59.99 Value)
  • Duration: 16+ hours
  • Resources: Lifetime access to videos + Complete source code
  • 3. Embedded Systems Design Patterns Ground Up ($59.99 Value)
  • Duration: 16+ hours
  • Resources: Lifetime access to videos + Complete source code
Total Value: $189.97
But today, you're getting all of this...
For Only $149.75

 30 Day Money Back Guarantee

Remember, I have no doubt you will love the training but should in case you are not completely satisfied you can request a refund within 30 days of purchase and you shall be fully refunded with no questions asked.

Sounds fair ?