1

I am trying to make a militaristic example of reading and executing C code within Kotlin-Native. I am following this article here. However, I'm receiving an "Unresolved Reference" error on the final step. Here are all the files/commands I'm using. My operating system is Windows.

testlib.h

#ifndef MY_TEST_LIB
#define MY_TEST_LIB

int getRandomNumber();

#endif

testlib.c

#include "testlib.h"

#include <stdio.h>
#include <stdlib.h>

int getRandomNumber() {
    return rand();
}

I've compiled these files into a static library named libtestlib.lib. My goal is to call getRandomNumber from within Kotlin Native.


Next I have these kotlin related files:

testlib.def

headers = testlib.h
headerFilter = ./*
compilerOpts = -L. -ltestlib -I.

CLibTest.kt

import testlib.*

fun main(args: Array<String>) {
    println(getRandomNumber())
}

Finally, I'm running these two commands. The first to make the klib:

cinterop -def testlib.def -o testlib


And then this last one to create the executable:

konanc CLibTest.kt -library testlib

Everything works great until this last command, where I receive the following error:

CLibTest.kt:4:10: error: unresolved reference: getRandomNumber println(getRandomNumber())


Could someone point out where I went wrong?

Griffort
  • 1,174
  • 1
  • 10
  • 26
  • Your function name may have been [decorated](https://en.wikipedia.org/wiki/Name_mangling#C). May be try with `_getRandomNumber()` – Mathieu Aug 28 '18 at 08:07
  • @purplepsycho Interesting. Unfortunately, that doesn't appear to be the solution. Still resulting in an identical error, only with `_getRandomNumber()` this time. >. – Griffort Aug 28 '18 at 08:16
  • Not an expert in this area, but what if in *testlib.h* file you declare the function: `__declspec(dllexport) int getRandomNumber();`? This is only to check if exporting is the real problem, then, if so, the export logic should look smth like https://stackoverflow.com/questions/30581837/linker-error-when-calling-a-c-function-from-c-code-in-different-vs2010-project/30583411#30583411, (or simpler: https://stackoverflow.com/questions/51507196/python-ctypes-to-return-an-array-of-function-pointers/51529527#51529527). – CristiFati Aug 28 '18 at 08:33
  • You can use the [`dumpbin`](https://msdn.microsoft.com/en-us/library/20y05bd5.aspx) tool to know how the name hase been mangled: `dumpbin /HEADERS testlib.lib` – Mathieu Aug 28 '18 at 08:35
  • @CristiFati Sorry, it did not make any difference. – Griffort Aug 28 '18 at 09:30
  • @purplepsycho I did so, but was unable to ascertain any information regarding mangling? – Griffort Aug 28 '18 at 09:30
  • Declare it extern "C". – rustyx Aug 28 '18 at 11:13
  • Btw, the issue is unrelated to the linker.The error message comes from Kotlin compiler (frontend) and means that the declaration wasn't found. While the linker would complain about missing definition. – Svyatoslav Scherbina Aug 29 '18 at 14:53

3 Answers3

2

Windows libraries must be created by msys2-mingw, not msvc.

Something like this (in mingw64 shell):

gcc -c testlib.c -o testlib.o && ar rc testlib.a testlib.o
1

headerFilter value in your testlib.def is incorrect. You can try to remove it.

The filter is applied to the value written under #include directive from headers and headers value elements from .def file. None of these strings have ./ prefix.

  • --I did so and received this error: `.../combined.o:(.text+0x1f0b5): undefined reference to 'getRandomNumber' clang++.exe: error: linker command failed with exit code 1`-- – Griffort Aug 29 '18 at 20:05
  • Nevermind, this combined with the embedding the static library into .klib resolved the issue! – Griffort Aug 29 '18 at 20:11
1

The answer is the combination of suggestions from Svyatoslav Scherbina and Mike Sinkovsky.

The "headerFilter" was incorrect and needed to be removed, and the static library needed to be embedded to the .klib. By setting testlib.def to be:

headers = testlib.h
compilerOpts = -I.
staticLibraries = libtestlib.lib
libraryPaths = .

The issue is resolved and the kotlin file complies/runs without issue!

Griffort
  • 1,174
  • 1
  • 10
  • 26