c3c icon indicating copy to clipboard operation
c3c copied to clipboard

undefined reference when attempting to create a c3i / c3l for a c3 static-lib

Open dazoe opened this issue 3 weeks ago • 2 comments

Not sure if this is truly a bug or maybe I'm doing it wrong. When creating a binding for a c3 static-lib I'm getting undefined reference linker error.

Steps to reproduce.

  1. create a static lib project
  2. change project type to 'static-lib'
  3. create a simple say_hello function.
fn void say_hello() @export {
	io::printn("Hello from mylib");
}
  1. build
  2. create a project
  3. c3c init myprog
  4. add "mylib" to "dependencies" in project.json
  5. create "mylib.c3l" directory in lib
  6. create "lib/mylib.c3l/manifest.json"
{
	"provides": "mylib",
	"sources" : [ "src/**" ],
	"targets" : {
		"linux-x64": {
			"linked-libraries": [ "mylib" ],
		}
	}
}
  1. create "lib/mylib.c3l/src/mylib.c3i"
module mylib;

extern fn void say_hello();
  1. copy mylib.a to "lib/mylib.c3l/linux-x64"
  2. use mylib::say_hello()
module myprog;
import mylib;

fn int main(String[] args)
{
	mylib::say_hello();
	return 0;
}
  1. build
[dave@inwin myprog]$ c3c build
/usr/bin/ld: build/obj/linux-x64/myprog.o: in function `myprog.main':
/home/dave/Projects/c3/myprog/src/main.c3:6:(.text+0x11): undefined reference to `say_hello'
collect2: error: ld returned 1 exit status
Failed to link executable 'build/myprog' using command 'cc -o build/myprog -rdynamic -pthread build/obj/linux-x64/std_collections_list.std.os.backtrace.Backtrace.o build/obj/linux-x64/libc.o build/obj/linux-x64/std.math.o build/obj/linux-x64/std.math.math_rt.o build/obj/linux-x64/std.os.posix.o build/obj/linux-x64/std.os.process.o build/obj/linux-x64/std.os.linux.o build/obj/linux-x64/std.os.backtrace.o build/obj/linux-x64/std.atomic.o build/obj/linux-x64/std.core.ascii.o build/obj/linux-x64/std.core.mem.o build/obj/linux-x64/std.core.types.o build/obj/linux-x64/std.core.dstring.o build/obj/linux-x64/std.core.builtin.o build/obj/linux-x64/std.core.string.o build/obj/linux-x64/std.core.string.conv.o build/obj/linux-x64/std.core.mem.allocator.o build/obj/linux-x64/std.io.os.o build/obj/linux-x64/std.io.file.o build/obj/linux-x64/std.io.o build/obj/linux-x64/myprog.o -Llib/mylib.c3l/linux-x64 -lmylib -ldl -lm'.

dazoe avatar Dec 01 '25 01:12 dazoe

The problem occurs when not using extern:

// mylib.c3i
module mylib;

fn void say_hello();

This tries to link with mylib.say_hello but I believe is instead meant to link with the @exported mylib__say_hello function. extern fn void say_hello() will correctly try to link with a C function named just say_hello.

Book-reader avatar Dec 01 '25 07:12 Book-reader

Use

// mylib.c3i
module mylib;

fn void say_hello() @export;

This should invoke the right mangling.

lerno avatar Dec 02 '25 16:12 lerno