Hi KR,
I'm not expert on this issue, but I took a look and have an idea about this
issue (please take my advice with a grain of salt) :
Looking at arch/ I see only other 3 archs implement it:
$ git grep "void up_udelay"
arm/src/cxd56xx/cxd56_delay.c:void up_udelay(useconds_t microseconds)
risc-v/src/mpfs/mpfs_perf.c:void up_udelay(useconds_t microseconds)
risc-v/src/rv32m1/rv32m1_delay.c:void up_udelay(useconds_t microseconds)
So, chances are that none of these archs are in fact using these functions
(please double check, but I think they are facing the same issue as you).
Why? Because normally a weak function is not extracted from the .a lib
unless the linked can't find a definition to it.
And because it is already finding it at libsched.a (coming
from sched/clock/clock_delay.c) it will not try to extract another one from
libarch.a (even although your implementation doesn't have a week).
So, I think the proper solution should be creating
a CONFIG_ARCH_HAVE_UDELAY to be added to ARCHs that support it and
surround the up_udelay() at clock_delay.c with it.
#ifndef CONFIG_ARCH_HAVE_UDELAY
void weak_function up_udelay(useconds_t microseconds)
{
udelay_coarse(microseconds);
}
#endif
(same to mdelay and ndelay functions)
BR,
Alan
On Mon, Mar 2, 2026 at 1:00 PM <[email protected]> wrote:
> Hello,
>
> I would like to ask for help regarding the build process. It seems to be
> ignoring functions defined in a source code file for some reason and I
> can't figure it out.
>
> I am attempting to reimplement up_udelay for AVR, so I created file
> arch/avr/src/avrdx/avrdx_delay.c . To my understanding, since the
> function is defined as weak in sched/clock/clock_delay.c , the only
> thing needed is to define another function with the same name and it
> will override the weak one. I also added CHIP_CSRCS += avrdx_delay.c to
> arch/avr/src/avrdx/Make.defs . Tried to build everything, build
> succeeded but - looking at the disassembly - the original implementation
> was used.
>
> So then I started experimenting:
>
> 1. I tried if the source file avrdx_delay.c is actually being compiled
> by adding #error test . The compiler issued an error, as expected.
>
> 2. I tried to remove weak attribute from up_udelay in clock_delay.c to
> force "multiple definition" error in linking step to verify that my code
> is getting to the linker. No error though, build completed.
>
> 3. I also tried to force the same error with different function,
> randomly picked nxtask_start and added a dummy implementation of it to
> avrdx_delay.c. Still no error.
>
> 4. Still thinking there may be something wrong with the new file, I
> moved my implementation of nxtask_start to already existing and
> relatively well-tested arch/avr/src/avrdx/avrdx_serial.c . The build
> failed, multiple definition of `nxtask_init' (finally)
>
> 5. I then put my implementation of up_udelay to avrdx_serial.c (and
> removed nxtask_init from there.) The build succeeded and up_udelay used
> my implementation.
>
> 6. Now the really strange part (for me at least) - I added
> somerandomfunc() to avrdx_delay.c and called it from my application.
> Attempted to build and it failed because multiple definition of
> nxtask_init which was left there from previous experiments. To verify, I
> kept somerandomfunc in avrdx_delay.c but removed the call to it from my
> application. The build succeeded. I added the call to somerandomfunc
> back to the application, got build error again.
>
> So now I am at loss. From what I see, the linker is ignoring duplicate
> functions in an source code/object file unless the file also contains a
> function that is not a duplicate and that is actually called from
> somewhere.
>
> Could anyone shed some light on this? I am out of my league here
> unfortunately. Did some web search, found --whole-archive flag for the
> linker but experimenting with it led to nowhere (couldn't even make it
> to work, makes the build fail because linker then finds duplicates
> between libgcc and NuttX code and even within libgcc itself.)
>
> Tested with avr-gcc 14.2 and 5.4
>