0

I'm new to cmake/make so I'm trying to do a simple compilation with include and lib directories as well as a library to link to the main file.

My directory structure looks like this

PROJECTDIRECTORY/
 main.c
 CMAKELISTS.txt
 include/
   add.h
 lib/
   add.a
 build/

My main.c contains

#include <add.h>

int main(void)
{
    add(5,10);
    return 0;
}

My add.h contains

int add(int x,int y);

And my add.a is a static library which I compiled from add.c which contains the implementation.

Finally in my CMakeLists.txt I have

cmake_minimum_required (VERSION 3.6)
project(addproject)

add_executable(addproject main.c)

include_directories(include)

link_directories(lib)

target_link_libraries(addproject add.a)

Then when I run cmake . , it generates the makefile correctly.

But when I run make, I receive a linker error

Scanning dependencies of target addproject
[ 50%] Building C object CMakeFiles/addproject.dir/main.c.o
[100%] Linking C executable addproject
ld: library not found for -ladd
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[2]: *** [addproject] Error 1
make[1]: *** [CMakeFiles/addproject.dir/all] Error 2
make: *** [all] Error 2

Stating it can't find library for add? Even though I set library_directories in cmake.. Can someone help me fix this error?

Thanks!

Kayla
  • 223
  • 2
  • 14
  • Where is `add.c`? You shouldn't be linking to library _files_, but rather to library _targets_, especially if you created them yourself. – Alex Reinking Mar 14 '21 at 18:16
  • @AlexReinking Well I was testing with a library file. So add.c isn't there because I've already compiled add.a into add.c and I wanted to see if I could link it with cmake.. – Kayla Mar 14 '21 at 18:45
  • then the answer to your question is here: https://stackoverflow.com/a/41909627/2137996 – Alex Reinking Mar 14 '21 at 18:47
  • Thank you that does answer my question! – Kayla Mar 14 '21 at 18:55

1 Answers1

0

Since you compiled add.c into add.a yourself, you should just do everything with targets in CMake. You don't say where add.c is, but I'm going to assume it's in lib. Here's what you should write:

cmake_minimum_required(VERSION 3.19)
project(addproject)

add_library(add lib/add.c)
target_include_directories(add PUBLIC include)

add_executable(addproject main.c)
target_link_libraries(addproject PRIVATE add)

Now that CMake manages both parts of the build, it will derive correct compiler flags for addproject when linking to add. Note that "PUBLIC" properties propagate to their linkees. So because addproject links to add, it will receive the include directories for add.

In new CMake code, never use directory functions like include_directories and link_directories. They're the decade-old way of doing things. They're brittle, error-prone, and have weird behaviors you don't want me to explain. Use the target_* functions.

Alex Reinking
  • 16,724
  • 5
  • 52
  • 86
  • i guess you should type add.c instead of acc.c – kzlca Mar 14 '21 at 18:32
  • Yup. Fat-fingered it. – Alex Reinking Mar 14 '21 at 18:34
  • Thank you for that answer. That's fine I was doing it with add.c is there any way I can link with add.a instead of telling it to compile add.c into add.a then linking? – Kayla Mar 14 '21 at 18:47
  • I would like you to keep this answer in case anyone comes across it and wants to do it with source files instead of already compiled library files. Thank you! – Kayla Mar 14 '21 at 19:41