FindIconv doesn't seem to behave correctly

Our project has our own FindIconv.cmake file as we’re using minimum version 3.10. I’m trying to upgrade to version 3.13 and in the process replace the FindIconv.cmake with the builtin FindIconv module. Our FindIconv.cmake looks like the following:

find_path(ICONV_INCLUDE_DIR NAMES iconv.h)
find_library(ICONV_LIBRARY NAMES iconv libiconv)
find_package_handle_standard_args(Iconv DEFAULT_MSG

add_library(iconv INTERFACE)
target_include_directories(iconv SYSTEM BEFORE INTERFACE ${ICONV_INCLUDE_DIR})
  target_link_libraries(iconv INTERFACE ${ICONV_LIBRARY})

However, when using the builtin module I get the following errors on freebsd:

ld: error: undefined symbol: libiconv_close
>>> referenced by bufwrite.c:1890 (/tmp/cirrus-ci-build/src/nvim/bufwrite.c:1890)
>>>               src/nvim/CMakeFiles/nvim.dir/bufwrite.c.o:(buf_write)
>>> referenced by fileio.c:760 (/tmp/cirrus-ci-build/src/nvim/fileio.c:760)
>>>               src/nvim/CMakeFiles/nvim.dir/fileio.c.o:(readfile)
>>> referenced by fileio.c:1037 (/tmp/cirrus-ci-build/src/nvim/fileio.c:1037)
>>>               src/nvim/CMakeFiles/nvim.dir/fileio.c.o:(readfile)
>>> referenced 3 more times

ld: error: undefined symbol: libiconv
>>> referenced by bufwrite.c:189 (/tmp/cirrus-ci-build/src/nvim/bufwrite.c:189)
>>>               src/nvim/CMakeFiles/nvim.dir/bufwrite.c.o:(buf_write_convert_with_iconv)
>>> referenced by bufwrite.c:201 (/tmp/cirrus-ci-build/src/nvim/bufwrite.c:201)
>>>               src/nvim/CMakeFiles/nvim.dir/bufwrite.c.o:(buf_write_convert_with_iconv)
>>> referenced by fileio.c:1115 (/tmp/cirrus-ci-build/src/nvim/fileio.c:1115)
>>>               src/nvim/CMakeFiles/nvim.dir/fileio.c.o:(readfile)
>>> referenced 2 more times

ld: error: undefined symbol: libiconv_open
>>> referenced by mbyte.c:2243 (/tmp/cirrus-ci-build/src/nvim/mbyte.c:2243)
>>>               src/nvim/CMakeFiles/nvim.dir/mbyte.c.o:(my_iconv_open)
cc: error: linker command failed with exit code 1 (use -v to see invocation)
ninja: build stopped: subcommand failed.

I am unsure why cmake tries to find libiconv instead of iconv, which is what I’d expect. Is there an idiomatic way to resolve this? For example, is there a way to make it not search for libiconv and just search for iconv instead?

The builtin module provides an Iconv::Iconv target that you probably would be better off using when porting. Other than that, CMake’s builtin one uses variables starting with Iconv_, not ICONV_.

I know, I am using the Iconv::Iconv target and Iconv_LIBRARIES. This shows up despite that.

PR: build: bump minimum cmake version to 3.13 by dundargoc · Pull Request #25638 · neovim/neovim · GitHub
CI results: Cirrus CI

I assume that one of the pre-built libraries wants a libiconv that is not built in the libc, so one that uses iconv symbols prefixed with lib…

Can you elaborate? What’s the correct solution to resolve this?

See e.g. iconv / libiconv 1.15 vs libc / libiconv_open | common/isc_file.cpp [CORE5989] · Issue #6239 · FirebirdSQL/firebird · GitHub

Just guessing here: you are using the wrong header file or FindIconv is not considering this.

Unsure what to do with the link, they use autotools and the PR comments are just botspam. Thanks I guess.