Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Port to Zephyr OS #958

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from
Draft

Port to Zephyr OS #958

wants to merge 1 commit into from

Conversation

UncleGrumpy
Copy link
Collaborator

Setup a freestanding west application project for Zephyr SDK.

These changes are made under both the "Apache 2.0" and the "GNU Lesser General
Public License 2.1 or later" license terms (dual license).

SPDX-License-Identifier: Apache-2.0 OR LGPL-2.1-or-later

@UncleGrumpy UncleGrumpy mentioned this pull request Nov 22, 2023
src/platforms/generic_unix/main.c Outdated Show resolved Hide resolved
src/libAtomVM/nifs.c Outdated Show resolved Hide resolved
#
# SPDX-License-Identifier: Apache-2.0 OR LGPL-2.1-or-later
#

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Honestly I don't like copying and pasting code. I opened a discussion about this topic: zephyrproject-rtos/zephyr#65704

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I completely agree that duplication of the CMakeLists.txt is not an ideal situation. Hopefully a solution will arise from the issue you opened, and I will continue to study the Zephyr documentation and search for a better solution.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I also borrowed heavily from @adolfogc's comments in issue #802 (comment). I think we should give Adolfo E. García credit as well. I should probably reach out in a follow up to his post and ask for his explicit permission and see if he would like his name and contact info added to the copyright notice.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I’m wondering if we should be setting standard c11 globally in cmake for each port, so that setting it again in src/libAtomVM/CMakeLists.txt would not be necessary. That way we could avoid any conflicts with toolchain specific methods for setting C11 as the standard for the library.

Copy link

@adolfogc adolfogc Nov 25, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@bettio @UncleGrumpy I think the some of this could be moved into the original CMakeLists.txt residing under libAtomVM, coupled with the use of boolean flags set accordingly for the platform (for example, AVM_PLATFORM_ZEPHYR). The port could be structured like a Zephyr module, similarly to how QCPP does.

Copy link

@adolfogc adolfogc Nov 26, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Assuming libAtomVM is built as part of a Zephyr application, the variable could be set automatically like so:

if(Zephyr_FOUND)
    set(AVM_PORT_ZEPHYR ON)
endif()

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Some of the checks could be avoided also. See how some of the auxiliary CMake macros are defined: https://github.com/zephyrproject-rtos/zephyr/blob/zephyr-v3.5.0/cmake/modules/extensions.cmake

#
# This file is part of AtomVM.
#
# Copyright 2023 Winford (Uncle Grumpy) <winford@object.stream>
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This file looks based on prior work that has been done on src/libAtomVM/CMakeLists.txt, so we should include the original copyright notice too.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Right. I forgot to add that yet.

CONFIG_POSIX_SIGNAL=y
CONFIG_APP_LINK_WITH_POSIX_SUBSYS=y
CONFIG_FORTIFY_SOURCE_RUN_TIME=y
CONFIG_COMPILER_OPT="-std=c11"

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this line required, or is this also handled by CMake?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually that line does not work as intended. And any attempt in cmake to set C11 standard gas so far failed, I always get a flood of C99 warnings. If you have any suggestions I would really appreciate any input.

README.ZEPHYR.md Outdated

# AtomVM for Zephyr
This is an experimental port that will hopefully replace the current stm32 `libopencm3` based port, and should support many more boards.
Not all boards supported by Zephyr are capable of running AtomVM. The most likely excluding factor will be lack of flash storage space to accomodate both the VM and user BEAM applications. We will likely need a cusomized device tree to only define the boards that AtomVM can support. Currently a build can be attempeted for any board supported by the Zephyr SDK and the user will need to determing if the final build can fit onto the device and still have space left for a user application partition (on stm32 devices this is typically a 128K block size).

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cusomized -> customized
determing -> determine


target_link_libraries(app PRIVATE libAtomVM${PLATFORM_LIB_SUFFIX})

zephyr_cc_option("-std=c11")

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See related comment in prj.conf

# SPDX-License-Identifier: Apache-2.0 OR LGPL-2.1-or-later
#

CONFIG_KERNEL_BIN_NAME="AtomVM"

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure if this makes sense

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That changes the name of the final binary to AtomVM.elf rather than kernel.elf, it's purely cosmetic.


#include <zephyr/kernel.h>

// #include <libopencm3/cm3/nvic.h>

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should commented code of the libopencm3-based version remain?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not at all, I left some of that for reference while it's in draft, just so I could try to make sure this port starts on parity with the libopencm3 stm32 port. I have a lot of commented out code to remove still.

@bettio
Copy link
Collaborator

bettio commented Nov 25, 2023

avm_version.h PR (#959) has been merged, let's rebase this PR.

return UNDEFINED_ATOM;
}

// void sys_enable_flash_cache()
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's either cleanup code and remove commented out blocks, or remove them while adding a TODO.

UNUSED(glb);
}

// void sys_enable_core_periph_clocks()
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's either cleanup code and remove commented out blocks, or remove them while adding a TODO.

-->

# AtomVM for Zephyr
This is an experimental port that will hopefully replace the current stm32 `libopencm3` based port, and should support many more boards.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

stm32 -> STM32

@bettio
Copy link
Collaborator

bettio commented Nov 25, 2023

I'm adding a first list of goals, in order to keep this PR as focused as possible.

Zephyr port must not implement all the features and peripherals, but it should rather focus on general scaffolding and the basics.

  • Starting from first PR CI should be running also for Zephyr
  • native_sim must be supported (and it should be likely used on CI)
  • qemu x86 should be supported in order to avoid leaking ARM specific details into our Zephyr port

@UncleGrumpy
Copy link
Collaborator Author

These sound like a reasonable starting point for this port. I was definitely not planning on taking out of "draft" until the there is a CI workflow to test the port. I believe native_sim is already working, but I have not attempted a qemu build yet.

@UncleGrumpy
Copy link
Collaborator Author

UncleGrumpy commented Nov 25, 2023

After investigating a bit further native_sim will require a separate port from one intended to run on microcontrollers, the reason being that MCU must be able to load the application from a flash address. But creating a west project build structure for our current generic_unix port should be trivial, after we solve the standard c11 issue.

option(AVM_DISABLE_GPIO_NIFS "Disable GPIO nifs (input and output)" OFF)
option(AVM_DISABLE_GPIO_PORT_DRIVER "Disable GPIO 'port' driver (input, output, and interrupts)" OFF)

set(AVM_DISABLE_SMP ON FORCE)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the case of the Zephyr port, could testing for the CONFIG_SMP variable work? That variable is set in the Kconfig and made available in CMake.

See:

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. I was realizing today that making KConfig options to set these options would be preferable to passing extra -D options to west.

Copy link

@adolfogc adolfogc Nov 26, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think of structuring it as a Zephyr module, where the CMakeLists.txt could be something like:

cmake_minimum_required (VERSION 3.20)

if(Zephyr_FOUND)
    set(AVM_PORT_ZEPHYR ON)
endif()

# Options that make sense for this platform
cmake_dependent_option(AVM_USE_32BIT_FLOAT "Use 32 bit floats." ON "NOT CONFIG_64BIT" OFF)
option(AVM_VERBOSE_ABORT "Print module and line number on VM abort" OFF)
option(AVM_CREATE_STACKTRACES "Create stacktraces" ON)
cmake_dependent_option(AVM_NEWLIB_NANO "Use 'nano' newlib. Saves 46kB, no `long long` support" ON "CONFIG_HAS_NEWLIB_LIBC_NANO" OFF)
option(AVM_LOG_DISABLE "Disable log output" OFF)
option(AVM_ENABLE_LOG_COLOR "Use color log output" OFF)
option(AVM_ENABLE_LOG_LINES "Include source and line info for all enbled levels" OFF)
option(AVM_CONFIG_REBOOT_ON_NOT_OK "Reboot when application exits with non 'ok' return" OFF)
option(AVM_DISABLE_GPIO_NIFS "Disable GPIO nifs (input and output)" OFF)
option(AVM_DISABLE_GPIO_PORT_DRIVER "Disable GPIO 'port' driver (input, output, and interrupts)" OFF)

include_directories(src/libAtomVM)  # libAtomVM
include_directories(src/platforms/zephyr)  # AtomVM (Zephyr port)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The module would set the minimal Kconfig options for AtomVM:

menuconfig AVM
    bool "AVM"
    default n
    help
        Enables the AtomVM Module
    depends on FPU
    select APP_LINK_WITH_POSIX_SUBSYS
    select FORTIFY_SOURCE_RUN_TIME
    select POSIX_API
    select POSIX_CLOCK
    select POSIX_SIGNAL
    select REBOOT
    select REQUIRES_FLOAT_PRINTF
    select RUNTIME_ERROR_CHECKS
    select STACK_USAGE

if AVM

module = AVM
module-str = AtomVM

endif

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Instead of implementing main, the port could provide an implementation called avm_main which the Zephyr application could call from its own main implementation.

// #define ENABLE_TRACE
#include <trace.h>

#include "zephyros_sys.h"

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where is this file?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in AtomVM/src/platforms/zephyr/src/lib/

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is the file pending to be pushed?

Copy link
Collaborator Author

@UncleGrumpy UncleGrumpy Nov 27, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, it was... I just forgot to add it to the commit before pushing the changes. It's there now. Thanks for spotting that!

@adolfogc
Copy link

@bettio @UncleGrumpy would modifying src/libAtomVM/CMakeLists.txt like below be a good alternative to avoid code duplication?

cmake_minimum_required (VERSION 3.13)

project(libAtomVM C)

set(HEADER_FILES
    atom.h
    atomshashtable.h
    avmpack.h
    bif.h
    bitstring.h
    context.h
    debug.h
    defaultatoms.h
    dictionary.h
    erl_nif.h
    erl_nif_priv.h
    exportedfunction.h
    externalterm.h
    globalcontext.h
    iff.h
    interop.h
    list.h
    listeners.h
    mailbox.h
    memory.h
    module.h
    opcodes.h
    opcodesswitch.h
    overflow_helpers.h
    nifs.h
    platform_nifs.h
    port.h
    posix_nifs.h
    refc_binary.h
    resources.h
    scheduler.h
    smp.h
    synclist.h
    stacktrace.h
    sys.h
    term_typedef.h
    term.h
    timer_list.h
    trace.h
    utils.h
    valueshashtable.h
    ${CMAKE_CURRENT_BINARY_DIR}/avm_version.h
)

set(SOURCE_FILES
    atom.c
    atomshashtable.c
    avmpack.c
    bif.c
    bitstring.c
    context.c
    debug.c
    defaultatoms.c
    dictionary.c
    externalterm.c
    globalcontext.c
    iff.c
    interop.c
    mailbox.c
    memory.c
    module.c
    nifs.c
    port.c
    posix_nifs.c
    refc_binary.c
    resources.c
    scheduler.c
    stacktrace.c
    term.c
    timer_list.c
    valueshashtable.c
)

set(CMAKE_REQUIRED_FLAGS "${CMAKE_REQUIRED_FLAGS} -Werror=unknown-pragmas")

include(CheckCSourceCompiles)

check_c_source_compiles("
     #include <fenv.h>
     int main() {
         #pragma STDC FENV_ACCESS ON
        return 0;
     }
 " HAVE_PRAGMA_STDC_FENV_ACCESS FAIL_REGEX FENV_ACCESS)

 check_c_source_compiles("
 #include <stdatomic.h>
 int main() {
     _Static_assert(ATOMIC_POINTER_LOCK_FREE == 2, \"Expected ATOMIC_POINTER_LOCK_FREE to be equal to 2\");
 }
" ATOMIC_POINTER_LOCK_FREE_IS_TWO)

if(NOT AVM_PORT_ZEPHYR)
    add_library(libAtomVM ${SOURCE_FILES} ${HEADER_FILES})
    target_include_directories(libAtomVM PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
    target_link_libraries(libAtomVM PUBLIC m)
    target_compile_features(libAtomVM PUBLIC c_std_11)
    if (CMAKE_C_COMPILER_ID STREQUAL "GNU")
        target_compile_options(libAtomVM PUBLIC -Wall -pedantic -Wextra -ggdb -Werror=incompatible-pointer-types)
    elseif (CMAKE_C_COMPILER_ID MATCHES "Clang")
        target_compile_options(libAtomVM PUBLIC -Wall --extra-warnings -Werror=incompatible-pointer-types)
    endif()
else()
    zephyr_library_named(libAtomVM)
    zephyr_library_sources(${SOURCE_FILES} ${HEADER_FILES})
    zephyr_include_directories(${CMAKE_CURRENT_SOURCE_DIR})
    zephyr_library_compile_features(c_std_11)
endif()

# AtomVM options used in libAtomVM
if (ADVANCED_TRACING)
    if(NOT AVM_PORT_ZEPHYR)
        target_compile_definitions(libAtomVM PUBLIC ENABLE_ADVANCED_TRACE)
    else()
        zephyr_compile_definitions(ENABLE_ADVANCED_TRACE)
    endif()
endif()

if (HAVE_PRAGMA_STDC_FENV_ACCESS)
    if(NOT AVM_PORT_ZEPHYR)
        target_compile_definitions(libAtomVM PUBLIC HAVE_PRAGMA_STDC_FENV_ACCESS)
    else()
        zephyr_compile_definitions(HAVE_PRAGMA_STDC_FENV_ACCESS)
    endif()
endif()

if(${CMAKE_C_FLAGS} MATCHES -DAVM_NO_SMP)
    message("SMP is disabled by CFLAGS environment")
    set(AVM_DISABLE_SMP ON)
endif()

if(NOT AVM_PORT_ZEPHYR)
    if (AVM_DISABLE_SMP)
        target_compile_definitions(libAtomVM PUBLIC AVM_NO_SMP)
    else()
        include(CheckIncludeFile)
        CHECK_INCLUDE_FILE(stdatomic.h STDATOMIC_INCLUDE)
        if(HAVE_PLATFORM_SMP_H)
            target_compile_definitions(libAtomVM PUBLIC HAVE_PLATFORM_SMP_H)
        endif()
        if (NOT ATOMIC_POINTER_LOCK_FREE_IS_TWO AND NOT HAVE_PLATFORM_SMP_H)
            if (NOT STDATOMIC_INCLUDE)
                message(FATAL_ERROR "stdatomic.h cannot be found, you need to disable SMP on this platform or provide platform_smp.h and define HAVE_PLATFORM_SMP_H")
            else()
                message(FATAL_ERROR "Platform doesn't support atomic pointers, you need to disable SMP or provide platform_smp.h and define HAVE_PLATFORM_SMP_H")
            endif()
        endif()
    endif()
else()
    if(AVM_DISABLE_SMP)
        zephyr_compile_definitions(AVM_NO_SMP)
    else()
        if(CONFIG_SMP)
            zephyr_compile_definitions(HAVE_PLATFORM_SMP_H)
        endif()
    endif()
endif()

if (AVM_USE_32BIT_FLOAT)
    if(NOT AVM_PORT_ZEPHYR)
        target_compile_definitions(libAtomVM PUBLIC AVM_USE_SINGLE_PRECISION)
    else()
        zephyr_compile_definitions(AVM_USE_SINGLE_PRECISION)
    endif()
endif()

if (AVM_VERBOSE_ABORT)
    if(NOT AVM_PORT_ZEPHYR)
        target_compile_definitions(libAtomVM PUBLIC AVM_VERBOSE_ABORT)
    else()
        zephyr_compile_definitions(AVM_VERBOSE_ABORT)
    endif()
endif()

if(AVM_CREATE_STACKTRACES)
    if(NOT AVM_PORT_ZEPHYR)
        target_compile_definitions(libAtomVM PUBLIC AVM_CREATE_STACKTRACES)
    else()
        zephyr_compile_definitions(AVM_CREATE_STACKTRACES)
    endif()
endif()

include(DefineIfExists)
# HAVE_OPEN & HAVE_CLOSE are used in globalcontext.h
if(NOT AVM_PORT_ZEPHYR)
    define_if_function_exists(libAtomVM open "fcntl.h" PUBLIC HAVE_OPEN)
    define_if_function_exists(libAtomVM close "unistd.h" PUBLIC HAVE_CLOSE)
    define_if_function_exists(libAtomVM mkfifo "sys/stat.h" PRIVATE HAVE_MKFIFO)
    define_if_function_exists(libAtomVM unlink "unistd.h" PRIVATE HAVE_UNLINK)
    define_if_symbol_exists(libAtomVM O_CLOEXEC "fcntl.h" PRIVATE HAVE_O_CLOEXEC)
    define_if_symbol_exists(libAtomVM O_DIRECTORY "fcntl.h" PRIVATE HAVE_O_DIRECTORY)
    define_if_symbol_exists(libAtomVM O_DSYNC "fcntl.h" PRIVATE HAVE_O_DSYNC)
    define_if_symbol_exists(libAtomVM O_EXEC "fcntl.h" PRIVATE HAVE_O_EXEC)
    define_if_symbol_exists(libAtomVM O_NOFOLLOW "fcntl.h" PRIVATE HAVE_O_NOFOLLOW)
    define_if_symbol_exists(libAtomVM O_RSYNC "fcntl.h" PRIVATE HAVE_O_RSYNC)
    define_if_symbol_exists(libAtomVM O_SEARCH "fcntl.h" PRIVATE HAVE_O_SEARCH)
    define_if_symbol_exists(libAtomVM O_TTY_INIT "fcntl.h" PRIVATE HAVE_O_TTY_INIT)
    define_if_symbol_exists(libAtomVM clock_settime "time.h" PRIVATE HAVE_CLOCK_SETTIME)
    define_if_symbol_exists(libAtomVM settimeofday "sys/time.h" PRIVATE HAVE_SETTIMEOFDAY)
    define_if_symbol_exists(libAtomVM socket "sys/socket.h" PUBLIC HAVE_SOCKET)
    define_if_symbol_exists(libAtomVM select "sys/select.h" PUBLIC HAVE_SELECT)
else()
    define_if_function_exists(libAtomVM open "zephyr/posix/fcntl.h" PUBLIC HAVE_OPEN)
    define_if_function_exists(libAtomVM close "zephyr/posix/unistd.h" PUBLIC HAVE_CLOSE)
    define_if_function_exists(libAtomVM mkfifo "zephyr/posix/sys/stat.h" PRIVATE HAVE_MKFIFO)
    define_if_function_exists(libAtomVM unlink "zephyr/posix/unistd.h" PRIVATE HAVE_UNLINK)
    define_if_symbol_exists(libAtomVM O_CLOEXEC "zephyr/posix/fcntl.h" PRIVATE HAVE_O_CLOEXEC)
    define_if_symbol_exists(libAtomVM O_DIRECTORY "zephyr/posix/fcntl.h" PRIVATE HAVE_O_DIRECTORY)
    define_if_symbol_exists(libAtomVM O_DSYNC "zephyr/posix/fcntl.h" PRIVATE HAVE_O_DSYNC)
    define_if_symbol_exists(libAtomVM O_EXEC "zephyr/posix/fcntl.h" PRIVATE HAVE_O_EXEC)
    define_if_symbol_exists(libAtomVM O_NOFOLLOW "zephyr/posix/fcntl.h" PRIVATE HAVE_O_NOFOLLOW)
    define_if_symbol_exists(libAtomVM O_RSYNC "zephyr/posix/fcntl.h" PRIVATE HAVE_O_RSYNC)
    define_if_symbol_exists(libAtomVM O_SEARCH "zephyr/posix/fcntl.h" PRIVATE HAVE_O_SEARCH)
    define_if_symbol_exists(libAtomVM O_TTY_INIT "zephyr/posix/fcntl.h" PRIVATE HAVE_O_TTY_INIT)
    define_if_symbol_exists(libAtomVM clock_settime "zephyr/posix/time.h" PRIVATE HAVE_CLOCK_SETTIME)
    define_if_symbol_exists(libAtomVM settimeofday "zephyr/posix/sys/time.h" PRIVATE HAVE_SETTIMEOFDAY)
    define_if_symbol_exists(libAtomVM socket "zephyr/posix/sys/socket.h" PUBLIC HAVE_SOCKET)
    define_if_symbol_exists(libAtomVM select "zephyr/posix/sys/select.h" PUBLIC HAVE_SELECT)
endif()

# Automatically use zlib if present to load .beam files
if(NOT AVM_PORT_ZEPHYR)
    if (${CMAKE_SYSTEM_NAME} STREQUAL "Darwin" OR ${CMAKE_SYSTEM_NAME} STREQUAL "Linux" OR ${CMAKE_SYSTEM_NAME} STREQUAL "FreeBSD")
        find_package(ZLIB)
        if (ZLIB_FOUND)
            target_compile_definitions(libAtomVM PRIVATE WITH_ZLIB)
            target_link_libraries(libAtomVM PUBLIC ${ZLIB_LIBRARIES})
        endif(ZLIB_FOUND)
    endif()
endif()

function(gperf_generate input output)
    add_custom_command(
        OUTPUT ${output}
        COMMAND gperf -t ${input} > ${output}
        DEPENDS ${input}
        COMMENT "Hashing ${input}"
    )
endfunction()

gperf_generate(${CMAKE_CURRENT_SOURCE_DIR}/bifs.gperf bifs_hash.h)
gperf_generate(${CMAKE_CURRENT_SOURCE_DIR}/nifs.gperf nifs_hash.h)

add_custom_target(generated DEPENDS bifs_hash.h)
add_custom_target(generated-nifs-hash DEPENDS nifs_hash.h)

if(NOT AVM_PORT_ZEPHYR)
    add_dependencies(libAtomVM generated generated-nifs-hash)
else()
    zephyr_library_add_dependencies(generated generated-nifs-hash)
endif()

include(../../version.cmake)

if (ATOMVM_DEV)
    set(ATOMVM_GIT_REVISION "<unknown>")
    execute_process(
        COMMAND git rev-parse --short HEAD
        WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
        OUTPUT_VARIABLE ATOMVM_GIT_REVISION
        OUTPUT_STRIP_TRAILING_WHITESPACE
    )
    if (NOT ATOMVM_GIT_REVISION STREQUAL "")
        set(ATOMVM_VERSION "${ATOMVM_BASE_VERSION}+git.${ATOMVM_GIT_REVISION}")
    else()
        set(ATOMVM_VERSION ${ATOMVM_BASE_VERSION})
    endif()
else()
    set(ATOMVM_VERSION ${ATOMVM_BASE_VERSION})
endif()

# Add include to directory where avm_version.h is generated so targets linking
# libAtomVM can access it
if(NOT AVM_PORT_ZEPHYR)
    target_include_directories(libAtomVM PUBLIC ${CMAKE_CURRENT_BINARY_DIR})
else()
    zephyr_include_directories(${CMAKE_CURRENT_BINARY_DIR})
endif()
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/version.h.in ${CMAKE_CURRENT_BINARY_DIR}/avm_version.h)

if(NOT AVM_PORT_ZEPHYR)
    if (NOT ${CMAKE_SYSTEM_NAME} STREQUAL "Generic")
        target_link_libraries(libAtomVM PUBLIC libAtomVM${CMAKE_SYSTEM_NAME}-${CMAKE_SYSTEM_PROCESSOR})
    endif()
endif()

if (COVERAGE)
    include(CodeCoverage)
    append_coverage_compiler_flags_to_target(libAtomVM)
endif()

@UncleGrumpy
Copy link
Collaborator Author

That looks like it might be a better solution, except that using zephyr_library_compile_features to set C11 standard results in an error from, cmake:

Unknown CMake command "zephyr_library_compile_features"

I still have not found any way set the standard, including the recommended solution in their documentation setting:
set_property(GLOBAL PROPERTY CSTD c11)
or
set_property(GLOBAL PROPERTY CSTD iso9899:2011)
before find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) in CMakeLists.txt. Using either of these still results in warnings about features introduced in standard C and C99.

@adolfogc
Copy link

adolfogc commented Nov 26, 2023

@UncleGrumpy The target name remains the same, can you try this instead:

target_compile_features(libAtomVM PUBLIC c_std_11)

@UncleGrumpy
Copy link
Collaborator Author

Then we are back to the original problem encountered when including libAtomVM that @bettio opened a issue on here: zephyrproject-rtos/zephyr#65704

The error is:

CMake Error in /home/winford/zephyrproject/zephyr/CMakeLists.txt:
  No known features for C compiler

  "GNU"

  version 12.2.0.

Setup a freestanding `west` application project for `Zephyr SDK`.

Signed-off-by: Winford <winford@object.stream>
@@ -0,0 +1,174 @@
#
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Zephyr official answer: zephyrproject-rtos/zephyr#66683

Short version: we muse use ExternalProject_Add

@@ -0,0 +1,134 @@

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

extra new line here.

/*
* This file is part of AtomVM.
*
* Copyright 2023 Winford (Uncle Grumpy) <winford@object.stream>
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If this main.c is based on some other existing main.c, let's report original authors too.

// #define LOG_COLOR_BLUE "\033[0;34m"
// #define LOG_COLOR_PURPLE "\033[0;35m"
// #define LOG_COLOR_PINK "\033[1;35m"
// #define LOG_COLOR_CYAN "\033[0;36m"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

let's cleanup unused defines.

#if (CONFIG_FLASH_SIZE == 512)
#define AVM_APP_ADDRESS ((CONFIG_FLASH_BASE_ADDRESS) + 0x60000U)
#else
#define AVM_APP_ADDRESS ((CONFIG_FLASH_BASE_ADDRESS) + 0x80000U)
Copy link
Collaborator

@bettio bettio Dec 21, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where are 0x60000U and 0x80000U coming from?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants