From patchwork Fri Sep 5 21:23:21 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Simon Glass X-Patchwork-Id: 260 Return-Path: X-Original-To: u-boot-concept@u-boot.org Delivered-To: u-boot-concept@u-boot.org DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=u-boot.org; s=default; t=1757107438; bh=NfFvfaLqpS2xHnAxaAUDW61Qoz6npiPhV9f4Zx1jI7A=; h=From:To:Date:In-Reply-To:References:CC:Subject:List-Id: List-Archive:List-Help:List-Owner:List-Post:List-Subscribe: List-Unsubscribe:From; b=g/+M0lSJR8RG0Y8IdkuOowuRDSr2bSDXy0/UO8jf9P07AalkGLb3JZfKwzW+k+AC5 b0OAMAnzOgWFFeq+JGS5Vd6Wp5r4WYcHXZpPTDEte/I1oG+zAD3Tb9QmegTbob3iPg SQ7kDZ4HXqoTcZKZBfFYTjTc2upKFxUPMGxZfFLn/GO5HOD5xg6n6z1tfO8Ya7gmoq 4pYp5Wpla+AaMwvZpDDK/jGWlIXoUAbElVEDqO7TP1LKCYA+t/UnjCX1v03rU8RgiU WGdhdlDa8AoSvt11TODO047K770BFD97WoF8cL3a5613gayJB7/sB42xo/pYzWQvX6 g0y9CmQFib9yQ== Received: from localhost (localhost [127.0.0.1]) by mail.u-boot.org (Postfix) with ESMTP id 5AA4C679C1 for ; Fri, 5 Sep 2025 15:23:58 -0600 (MDT) X-Virus-Scanned: Debian amavis at Received: from mail.u-boot.org ([127.0.0.1]) by localhost (mail.u-boot.org [127.0.0.1]) (amavis, port 10024) with ESMTP id 50l_Z7PUinNH for ; Fri, 5 Sep 2025 15:23:58 -0600 (MDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=u-boot.org; s=default; t=1757107438; bh=NfFvfaLqpS2xHnAxaAUDW61Qoz6npiPhV9f4Zx1jI7A=; h=From:To:Date:In-Reply-To:References:CC:Subject:List-Id: List-Archive:List-Help:List-Owner:List-Post:List-Subscribe: List-Unsubscribe:From; b=g/+M0lSJR8RG0Y8IdkuOowuRDSr2bSDXy0/UO8jf9P07AalkGLb3JZfKwzW+k+AC5 b0OAMAnzOgWFFeq+JGS5Vd6Wp5r4WYcHXZpPTDEte/I1oG+zAD3Tb9QmegTbob3iPg SQ7kDZ4HXqoTcZKZBfFYTjTc2upKFxUPMGxZfFLn/GO5HOD5xg6n6z1tfO8Ya7gmoq 4pYp5Wpla+AaMwvZpDDK/jGWlIXoUAbElVEDqO7TP1LKCYA+t/UnjCX1v03rU8RgiU WGdhdlDa8AoSvt11TODO047K770BFD97WoF8cL3a5613gayJB7/sB42xo/pYzWQvX6 g0y9CmQFib9yQ== Received: from mail.u-boot.org (localhost [127.0.0.1]) by mail.u-boot.org (Postfix) with ESMTP id 46FC1679B5 for ; Fri, 5 Sep 2025 15:23:58 -0600 (MDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=u-boot.org; s=default; t=1757107437; bh=VVzFPP+F/z8dXNKYEqk29MHJxsunNz3xxIvOZPmnkjs=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=gnG4QooL6HGPqD20F+1cI83SluI6T9CBiyfUNqi2cWZ44kyUZ2Z3xD8yDX6vyn5Bv bZbnpqVRatEOFXrknaUfmrgfjRtQ0h74cFDlz1dy5pK2Jk/80wJJ2PUW2Xt66GUt3t z0bcENjgOWMxSaitgt29FMIDWXFF6IRBlPg572d324NwSD3f1Ko1x+w8mp3em3M/zv W5aaEH/XL5WpYpcS4GonhAgWVf/UdPzR/IWhL4Odrfv5sj2EHWp+LDGVouPJimg+Vy UZTGq02aTzT/CXE92pQa/E6Rtz/sySio4mDqBu4Ll+qUjTrukUTRGz2Ry9kF+2WIDS XcW23Ff43nyHg== Received: from localhost (localhost [127.0.0.1]) by mail.u-boot.org (Postfix) with ESMTP id 18A46678E7; Fri, 5 Sep 2025 15:23:57 -0600 (MDT) X-Virus-Scanned: Debian amavis at Received: from mail.u-boot.org ([127.0.0.1]) by localhost (mail.u-boot.org [127.0.0.1]) (amavis, port 10026) with ESMTP id OYHyeUmBZ9rX; Fri, 5 Sep 2025 15:23:57 -0600 (MDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=u-boot.org; s=default; t=1757107431; bh=54ct5QMplkUOElzyPFpml8vidTb6ZbDuxrHlfwFSHTo=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=u/qrflDTKioVkOiWsnbkONTrO+JgMColW7bEpiQCkEfSId9WuryuNkniWx1Vabd9t CB3ZKFARNCyq+UNk1nf6a69/BMvg4eos/FenirCGQ56GBrb0hEmdag7MMU6OTVDIsK kU1Qhm7eIwiQoUw4WA/AtZlXbYoYKjWmF+T582ZzqFjY+VNMrU4YIaszV2rT72dSoi vtSgMrVAs7Jqcfo+Yj9orknb5HY4Twa8CdYVi6qUT27PA9kpLLdFz3J5ph9eIVMx2C iAPf4VBuVVy4Evk6zMOVILTBsr+gtidTfmBTe/7mBrJy55sQbnUTWDwPdXAcbogCom SvKUNWWsWr1Zg== Received: from u-boot.org (unknown [73.34.74.121]) by mail.u-boot.org (Postfix) with ESMTPSA id 604B86799C; Fri, 5 Sep 2025 15:23:51 -0600 (MDT) From: Simon Glass To: U-Boot Concept Date: Fri, 5 Sep 2025 15:23:21 -0600 Message-ID: <20250905212330.354827-9-sjg@u-boot.org> X-Mailer: git-send-email 2.43.0 In-Reply-To: <20250905212330.354827-1-sjg@u-boot.org> References: <20250905212330.354827-1-sjg@u-boot.org> MIME-Version: 1.0 Message-ID-Hash: 4HLF2GDCRJNV242FGT3FYN2RJ3ACJO4K X-Message-ID-Hash: 4HLF2GDCRJNV242FGT3FYN2RJ3ACJO4K X-MailFrom: sjg@u-boot.org X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; loop; banned-address; emergency; member-moderation; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; digests; suspicious-header CC: Simon Glass X-Mailman-Version: 3.3.10 Precedence: list Subject: [Concept] [PATCH 08/10] ulib: Provide an example of how to build with ulib List-Id: Discussion and patches related to U-Boot Concept Archived-At: List-Archive: List-Help: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: From: Simon Glass Add an example Makefile which shows how to build against U-Boot from outside the U-Boot source tree. Signed-off-by: Simon Glass --- Makefile | 17 +++++++++ examples/ulib/Makefile | 73 +++++++++++++++++++++++++++++++++++++++ examples/ulib/README | 74 ++++++++++++++++++++++++++++++++++++++++ examples/ulib/demo.c | 61 +++++++++++++++++++++++++++++++++ examples/ulib/static.lds | 19 +++++++++++ 5 files changed, 244 insertions(+) create mode 100644 examples/ulib/Makefile create mode 100644 examples/ulib/README create mode 100644 examples/ulib/demo.c create mode 100644 examples/ulib/static.lds diff --git a/Makefile b/Makefile index 2e2f276eee6..8d082d1ae81 100644 --- a/Makefile +++ b/Makefile @@ -1048,6 +1048,9 @@ ifneq ($(cc-name),clang) ifeq ($(NO_LIBS),) INPUTS-$(CONFIG_ULIB) += libu-boot.so test/ulib/ulib_test INPUTS-$(CONFIG_ULIB) += libu-boot.a test/ulib/ulib_test_static +ifdef CONFIG_EXAMPLES +INPUTS-$(CONFIG_ULIB) += examples_ulib +endif endif endif endif @@ -1911,6 +1914,18 @@ test/ulib/ulib_test_static: test/ulib/ulib_test.o libu-boot.a \ $(LIB_STATIC_LDS) FORCE $(call if_changed,ulib_test_static) +PHONY += examples_ulib +examples_ulib: libu-boot.a libu-boot.so FORCE + $(Q)$(MAKE) -C $(srctree)/examples/ulib \ + UBOOT_BUILD=$(abspath $(obj)) \ + EXAMPLE_DIR=. \ + OUTDIR=$(abspath $(obj)/examples/ulib) \ + srctree="$(srctree)" \ + CC="$(CC)" \ + CFLAGS="$(CFLAGS)" \ + PLATFORM_LIBS="$(PLATFORM_LIBS)" \ + LIB_STATIC_LDS="$(LIB_STATIC_LDS)" + quiet_cmd_sym ?= SYM $@ cmd_sym ?= $(OBJDUMP) -t $< > $@ u-boot.sym: u-boot FORCE @@ -2339,6 +2354,8 @@ $(clean-dirs): clean: $(clean-dirs) $(call cmd,rmdirs) $(call cmd,rmfiles) + @$(MAKE) -C $(srctree)/examples/ulib clean \ + OUTDIR=$(abspath $(obj)/examples/ulib) @find $(if $(KBUILD_EXTMOD), $(KBUILD_EXTMOD), .) $(RCS_FIND_IGNORE) \ \( -name '*.[oas]' -o -name '*.ko' -o -name '.*.cmd' \ -o -name '*.ko.*' -o -name '*.su' -o -name '*.pyc' \ diff --git a/examples/ulib/Makefile b/examples/ulib/Makefile new file mode 100644 index 00000000000..da788e5792f --- /dev/null +++ b/examples/ulib/Makefile @@ -0,0 +1,73 @@ +# SPDX-License-Identifier: GPL-2.0+ +# +# Standalone Makefile for U-Boot library examples +# +# Copyright 2025 Canonical +# Written by Simon Glass + +# This Makefile can be used to build the examples. See doc/develop/ulib.rst +# +# Usage: cd examples/ulib; make UBOOT_BUILD=/tmp/b/sandbox/ srctree=../.. +# +# This Makefile is also called from the main U-Boot Makefile when CONFIG_ULIB +# and CONFIG_EXAMPLES are enabled. It receives these variables, many of which +# are needed to ensure that the output goes to the right place: +# +# UBOOT_BUILD - Build directory (e.g., /tmp/b/sandbox) +# EXAMPLE_DIR - Source tree path for these examples +# OUTDIR - Output directory for object files and executables +# srctree - U-Boot source tree +# +# Also these may be provided: +# CC - C compiler +# CFLAGS - C compiler flags +# SDL_CONFIG - Name of sdl2-config program +# PLATFORM_LIBS - Platform-specific libraries +# LIB_STATIC_LDS - Linker script for static library + +# For standalone builds, provide default values +EXAMPLE_DIR ?= . +OUTDIR ?= . +CC ?= gcc +SDL_CONFIG ?= sdl2-config +PLATFORM_LIBS ?= $(shell $(SDL_CONFIG) --libs) +LIB_STATIC_LDS ?= static.lds +# The main Makefile passes in Q=@ for quiet output +Q ?= + +DEMO_SRC := $(EXAMPLE_DIR)/demo.c +DEMO_BINS := $(OUTDIR)/demo $(OUTDIR)/demo_static + +# Default target builds both programs +all: $(DEMO_BINS) + @echo "Build complete: demo and demo_static in $(OUTDIR)" + +# Create the output directory if it doesn't exist +$(OUTDIR): + @mkdir -p $@ + +# The U-Boot library must be built before we can link against it. This is +# signalled by the presence of the $(UBOOT_BUILD)/examples/ulib directory. +# This is an order-only prerequisite, so it does not trigger a rebuild if the +# timestamp of the directory changes. +$(DEMO_BINS): | $(UBOOT_BUILD)/examples/ulib $(OUTDIR) + +# Build demo (dynamically linked with libu-boot.so) +$(OUTDIR)/demo: $(DEMO_SRC) + $(CC) $(CFLAGS) \ + -idirafter$(srctree)/include -o $@ $< \ + -L$(UBOOT_BUILD) -lu-boot \ + -Wl,-rpath,$(UBOOT_BUILD) + +# Build demo_static (statically linked with libu-boot.a) +$(OUTDIR)/demo_static: $(DEMO_SRC) + $(CC) $(CFLAGS) \ + -idirafter$(srctree)/include -o $@ $< \ + -Wl,-T,$(LIB_STATIC_LDS) \ + -Wl,--whole-archive $(UBOOT_BUILD)/libu-boot.a -Wl,--no-whole-archive \ + -lpthread -ldl $(PLATFORM_LIBS) -Wl,-z,noexecstack + +clean: + $(Q)rm -f $(DEMO_BINS) + +.PHONY: all clean diff --git a/examples/ulib/README b/examples/ulib/README new file mode 100644 index 00000000000..e6f48bf79cd --- /dev/null +++ b/examples/ulib/README @@ -0,0 +1,74 @@ +U-Boot Library Example +====================== + +This directory contains example programs showing how to use the U-Boot library +(libu-boot.so) in external C programs. + +Building U-Boot Library +----------------------- + +First, build U-Boot with library support: + + make O=/tmp/b/sandbox -j$(nproc) sandbox_defconfig all + +This creates: +- /tmp/b/sandbox/libu-boot.so (shared library) +- /tmp/b/sandbox/libu-boot.a (static library) + +Example Programs +---------------- + +The examples are built automatically as part of the U-Boot build. So far there +is only one. + +**demo.c** - Demonstrates using U-Boot library functions + +- Shows how to init the library with ulib_init() +- Uses U-Boot's OS functions (os_open(), os_fgets(), os_close()) +- Reads and displays system information +- Shows the U-Boot version + +Building Examples +----------------- + +The examples are built automatically when U-Boot has these options enabled:: + + CONFIG_ULIB=y + CONFIG_EXAMPLES=y + +To build manually: + + # From this directory examples/ulib + make UBOOT_BUILD=/tmp/b/sandbox/ srctree=../.. + +Running Examples +---------------- + + # Run the demo + LD_LIBRARY_PATH=/tmp/b/sandbox ./demo + + # Run the demo (static version) + ./demo_static + +Key Points +---------- + +- Avoid including U-Boot headers that conflict with system headers. This + Makefile gives priority to the system headers +- Use ulib_init() to init the library +- Use ulib_uninit() to clean up +- Set LD_LIBRARY_PATH when running dynamically linked programs + +Copying for External Use +------------------------- + +This directory can be copied elsewhere and used independently: + + cp -r examples/ulib ~/my-project/ + cd ~/my-project/ulib + make UBOOT_BUILD=/path/to/u-boot-build srctree=/path/to/u-boot-source + +License +------- + +All examples are licensed under GPL-2.0+ diff --git a/examples/ulib/demo.c b/examples/ulib/demo.c new file mode 100644 index 00000000000..4b12e91b17e --- /dev/null +++ b/examples/ulib/demo.c @@ -0,0 +1,61 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Demo program showing U-Boot library functionality + * + * This demonstrates using U-Boot library functions in sandbox like os_* + * from external programs. + * + * Copyright 2025 Canonical + * Written by Simon Glass + */ + +#include +#include +#include +#include + +#include +#include +#include + +int main(int argc, char *argv[]) +{ + int fd, lines = 0; + char line[256]; + + /* Init U-Boot library */ + if (ulib_init(argv[0]) < 0) { + fprintf(stderr, "Failed to initialize U-Boot library\n"); + return 1; + } + + printf("1U-Boot Library Demo\n"); + printf("================================\n"); + printf("U-Boot version: %s\n", version_string); + printf("\n"); + + /* Use U-Boot's os_open to open a file */ + fd = os_open("/proc/version", 0); + if (fd < 0) { + fprintf(stderr, "Failed to open /proc/version\n"); + ulib_uninit(); + return 1; + } + + printf("System version:\n"); + + /* Use U-Boot's os_fgets to read lines */ + while (os_fgets(line, sizeof(line), fd)) { + printf(" %s", line); + lines++; + } + + os_close(fd); + + printf("\nRead %d line(s) using U-Boot library functions.\n", lines); + + /* Clean up */ + ulib_uninit(); + + return 0; +} diff --git a/examples/ulib/static.lds b/examples/ulib/static.lds new file mode 100644 index 00000000000..c400fba4f2b --- /dev/null +++ b/examples/ulib/static.lds @@ -0,0 +1,19 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +/* + * Linker script for ulib_test_static binary + * + * This ensures proper alignment for linker-lists when linking with libu-boot.a + */ + +SECTIONS +{ + /* Ensure proper alignment for linker lists */ + . = ALIGN(32); + __u_boot_list : { + __u_boot_list_start = .; + KEEP(*(SORT(__u_boot_list*))); + __u_boot_list_end = .; + } +} + +INSERT AFTER .rodata;