Integrating LVGL with makefile without STM32IDE

Description

Hi everyone!

I’m new to LVGL, and I’m trying to get a 10-inch display up with THREAD X (which I cannot select within the OS part in lvgl_config.h) and running. Instead of using STM32CubeIDE (which I’m not a fan of), I prefer working with Visual Studio Code (VSC) and Makefile for my projects.

I noticed there are a lot of .c files to include for LVGL. From the documentation, I learned that the lvgl.mk file can automatically find and include all the necessary .c files from the lvgl folder.

I followed the steps in the LVGL documentation and added the following to my Makefile:

LVGL_DIR_NAME ?= lvgl     #The name of the lvgl folder (change this if you have renamed it)
LVGL_DIR ?= ${shell pwd}  #The path where the lvgl folder is
include $(LVGL_DIR)/$(LVGL_DIR_NAME)/lvgl.mk

However, I’ve made some modifications based on my folder structure. Here’s what I changed it to:

LVGL_DIR = LVGL/lvgl
include $(LVGL_DIR)/lvgl.mk

This is my current folder structure:

  • Core/Src

  • LVGL/
    - lvlg (folder with src and lvgl.mk)
    -lv_config.h

  • makefile (main makefile of my application)

When I try to compile, the compiler throws errors, saying it can’t find references to functions like lv_tick_set_cb or lv_init. I’m fairly certain the issue is that my main Makefile isn’t correctly referencing the lvgl.mk file.

To troubleshoot, I even tried adjusting the LVGL path in lvgl.mk like this:

LVGL_PATH = LVGL/lvgl

What MCU/Processor/Board and compiler are you using?

I’m using GCC with an STM32H747xx.

What do you want to achieve?

I want to configure LVGL correctly and have it compile successfully—all without using STM32CubeIDE.

What have you tried so far?

  • Added all the configuration files.
  • Included the relevant lines for LVGL in my main Makefile.
  • Wrote some test C code to see if everything compiles.

Code to reproduce

Here you can find my makefile:

##########################################################################################################################
# File automatically-generated by tool: [projectgenerator] version: [4.5.0-RC5] date: [Tue Jan 28 19:19:26 CET 2025]
##########################################################################################################################

# ------------------------------------------------
# Generic Makefile (based on gcc)
#
# ChangeLog :
#	2017-02-10 - Several enhancements + project update mode
#   2015-07-22 - first version
# ------------------------------------------------

######################################
# target
######################################
TARGET = STM32RIVERDI_LVGL_CM7


######################################
# building variables
######################################
# debug build?
DEBUG = 1
# optimization
OPT = -Og


#######################################
# paths
#######################################
# Build path
BUILD_DIR = build

LVGL_DIR = LVGL/lvgl



######################################
# source
######################################
# C sources
C_SOURCES =  \
CM7/Core/Src/main.c \
CM7/Core/Src/gpio.c \
CM7/Core/Src/app_threadx.c \
CM7/Core/Src/dma2d.c \
CM7/Core/Src/fmc.c \
CM7/Core/Src/i2c.c \
CM7/Core/Src/jpeg.c \
CM7/Core/Src/ltdc.c \
CM7/Core/Src/mdma.c \
CM7/Core/Src/quadspi.c \
CM7/Core/Src/tim.c \
CM7/Core/Src/stm32h7xx_it.c \
CM7/Core/Src/stm32h7xx_hal_msp.c \
CM7/Core/Src/stm32h7xx_hal_timebase_tim.c \
CM7/AZURE_RTOS/App/app_azure_rtos.c \
Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_tim.c \
Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_tim_ex.c \
Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_cortex.c \
Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_dma2d.c \
...
...

# ASM sources
ASM_SOURCES =  \
makefiles/CM7/startup_stm32h747xx_CM7.s

# ASM sources
ASMM_SOURCES =  \
CM7/Core/Src/tx_initialize_low_level.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_context_restore.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_context_save.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_interrupt_control.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_interrupt_disable.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_interrupt_restore.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_schedule.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_stack_build.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_thread_system_return.S \
Middlewares/ST/threadx/ports/cortex_m7/gnu/src/tx_timer_interrupt.S


#######################################
# binaries
#######################################

include $(LVGL_DIR)/lvgl.mk
PREFIX = arm-none-eabi-
# The gcc compiler bin path can be either defined in make command via GCC_PATH variable (> make GCC_PATH=xxx)
# either it can be added to the PATH environment variable.
ifdef GCC_PATH
CC = $(GCC_PATH)/$(PREFIX)gcc
AS = $(GCC_PATH)/$(PREFIX)gcc -x assembler-with-cpp
CP = $(GCC_PATH)/$(PREFIX)objcopy
SZ = $(GCC_PATH)/$(PREFIX)size
else
CC = $(PREFIX)gcc
AS = $(PREFIX)gcc -x assembler-with-cpp
CP = $(PREFIX)objcopy
SZ = $(PREFIX)size
endif
HEX = $(CP) -O ihex
BIN = $(CP) -O binary -S
 
#######################################
# CFLAGS
#######################################
# cpu
CPU = -mcpu=cortex-m7

# fpu
FPU = -mfpu=fpv5-d16

# float-abi
FLOAT-ABI = -mfloat-abi=hard

# mcu
MCU = $(CPU) -mthumb $(FPU) $(FLOAT-ABI)

# macros for gcc
# AS defines
AS_DEFS = 

# C defines
C_DEFS =  \
-DCORE_CM7 \
-DUSE_HAL_DRIVER \
-DSTM32H747xx \
-DUSE_PWR_LDO_SUPPLY \
-DTX_INCLUDE_USER_DEFINE_FILE \



# AS includes
AS_INCLUDES = 

# C includes
C_INCLUDES =  \
-ICM7/Core/Inc \
-ICM7/AZURE_RTOS/App \
-ILVGL/lvgl \
-IMiddlewares/ST/threadx/common/inc/ \
-IMiddlewares/ST/threadx/ports/cortex_m7/gnu/inc/ \
-IDrivers/STM32H7xx_HAL_Driver/Inc \
-IDrivers/STM32H7xx_HAL_Driver/Inc/Legacy \
-IUtilities/JPEG \
-IDrivers/CMSIS/Device/ST/STM32H7xx/Include \
-IDrivers/CMSIS/Include


# compile gcc flags
ASFLAGS = $(MCU) $(AS_DEFS) $(AS_INCLUDES) $(OPT) -Wall -fdata-sections -ffunction-sections

CFLAGS += $(MCU) $(C_DEFS) $(C_INCLUDES) $(OPT) -Wall -fdata-sections -ffunction-sections

ifeq ($(DEBUG), 1)
CFLAGS += -g -gdwarf-2
endif


# Generate dependency information
CFLAGS += -MMD -MP -MF"$(@:%.o=%.d)"


#######################################
# LDFLAGS
#######################################
# link script
LDSCRIPT = makefiles/CM7/stm32h747xx_flash_CM7.ld

# libraries
LIBS = -lc -lm -lnosys 
LIBDIR = 
LDFLAGS = $(MCU) -specs=nano.specs -T$(LDSCRIPT) $(LIBDIR) $(LIBS) -Wl,-Map=$(BUILD_DIR)/$(TARGET).map,--cref -Wl,--gc-sections

# default action: build all
all: $(BUILD_DIR)/$(TARGET).elf $(BUILD_DIR)/$(TARGET).hex $(BUILD_DIR)/$(TARGET).bin


#######################################
# build the application
#######################################
# list of objects
OBJECTS = $(addprefix $(BUILD_DIR)/,$(notdir $(C_SOURCES:.c=.o)))
vpath %.c $(sort $(dir $(C_SOURCES)))
# list of ASM program objects
OBJECTS += $(addprefix $(BUILD_DIR)/,$(notdir $(ASM_SOURCES:.s=.o)))
vpath %.s $(sort $(dir $(ASM_SOURCES)))
OBJECTS += $(addprefix $(BUILD_DIR)/,$(notdir $(ASMM_SOURCES:.S=.o)))
vpath %.S $(sort $(dir $(ASMM_SOURCES)))

$(BUILD_DIR)/%.o: %.c Makefile | $(BUILD_DIR) 
	$(CC) -c $(CFLAGS) -Wa,-a,-ad,-alms=$(BUILD_DIR)/$(notdir $(<:.c=.lst)) $< -o $@

$(BUILD_DIR)/%.o: %.s Makefile | $(BUILD_DIR)
	$(AS) -c $(CFLAGS) $< -o $@
$(BUILD_DIR)/%.o: %.S Makefile | $(BUILD_DIR)
	$(AS) -c $(CFLAGS) $< -o $@

$(BUILD_DIR)/$(TARGET).elf: $(OBJECTS) Makefile
	$(CC) $(OBJECTS) $(LDFLAGS) -o $@
	$(SZ) $@

$(BUILD_DIR)/%.hex: $(BUILD_DIR)/%.elf | $(BUILD_DIR)
	$(HEX) $< $@
	
$(BUILD_DIR)/%.bin: $(BUILD_DIR)/%.elf | $(BUILD_DIR)
	$(BIN) $< $@	
	
$(BUILD_DIR):
	mkdir $@		

#######################################
# clean up
#######################################
clean:
	-rm -fR $(BUILD_DIR)
  
#######################################
# dependencies
#######################################
-include $(wildcard $(BUILD_DIR)/*.d)


# *** EOF ***

Hello,
Trying to get SVG running on my stm32U5,
using VSCode.

Here are my (two) (windows) makefiles I have in the root of my project. I had to add txt for importing into this message.

They can be improved to use shared flags, include the Makefile instead of calling one from the other, etc…

Makefile.lvgl.txt (14.9 KB)
Makefile.txt (10.3 KB)
make_build_debug.bat.txt (212 Bytes)

And my VSCode workspace files:

tasks.json.txt (544 Bytes)
settings.json.txt (913 Bytes)

Hi,
i have already found a solution for this error.

I had to integrate this lines of code to my main makefile:

LVGL_SRCS := $(shell find $(LVGL_PATH)/src -type f -name '*.c')

LVGL_SRCS += $(shell find $(LVGL_PATH)/demos -type f -name '*.c')

LVGL_SRCS += $(shell find $(LVGL_PATH)/examples -type f -name '*.c')

where

LVGL_PATH = LVGL/lvgl

and my project folder is distributed as:

ProjectRoot/
├── Core/
│ ├── Src/
│ ├── Inc
├── LVGL/
│ ├── lvgl/ # Contains all LVGL source files
│ ├── lv_conf.h # LVGL configuration file
├── Middlewares/ # Other middleware files
├── makefiles/
├── …

and lastly:

# Add LVGL sources to global C source list
C_SOURCES += $(LVGL_SRCS)

# Include LVGL headers in compilation
CFLAGS += -I$(LVGL_PATH)/src
CXXFLAGS += -I$(LVGL_PATH)/src

Include all the Src and Inc files from LVGL to the compiler list