Skip to content

Add a page describing compatibility issues with native interoperability #4866

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: master
Choose a base branch
from

Conversation

SvyatoslavScherbina
Copy link
Contributor

@SvyatoslavScherbina SvyatoslavScherbina commented May 23, 2025

@SvyatoslavScherbina SvyatoslavScherbina requested a review from a team as a code owner May 23, 2025 11:53
@danil-pavlov danil-pavlov self-assigned this Jun 3, 2025
library directly.
Use another package name for the native library, similar to how described [here](#use-custom-package-name).

## Future evolution of interoperability
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Minor: not sure if such paragraph is needed. Beta status assumes that the feature will evolve.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't insist on having this. But I thought it might be nice to repeat.
We also kind of have certain breaking changes in mind already, that was one of the ideas behind this paragraph.

Maybe other reviewers would also have some input.

- The Kotlin API of the native library refers to a non-existent type
(example: [KT-71694](https://youtrack.jetbrains.com/issue/KT-71694)).
- The Kotlin API of the native library includes a type that belongs to a system library.
I.e., everything compiles well, but some system native type is added to your native library package.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we recommend always applying some filtering using modules or headerFilter in the .def file to mitigate this? This is not Xcode-only issue, right?

One other tool we could mention here is:

/path/to/konan/bin/klib dump-metadata/dump-metadata-signatures /path/to/cinterop.klib

which lets you easily see the API surface of your cinterop library (and whether something leaked by accident)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not Xcode-only issue, right?

No, this is Xcode-only.

Should we recommend always applying some filtering using modules or headerFilter in the .def file to mitigate this?

Not sure. Isn't it too much detail?
In particular, the CocoaPods plugin applies filtering by default.

One other tool we could mention here is:

Seems a bit too advanced and low-level for this document.

Copy link
Collaborator

@abdulowork abdulowork Jun 12, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Isn't it too much detail?

Maybe. I was reading this sentence

some system native type is added to your native library package.

and I (hope I) understand how this happens only because I have some experience with updating Xcode in K/N, so mentioning the klib tool and specific mitigations makes this information more tangible and actionable.

If we don't want to mention the klib tool, we could mention that when you encounter this issue, you will, for example, see these system APIs in the IDE completion for your cinterop library.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we don't want to mention the klib tool, we could mention that when you encounter this issue, you will, for example, see these system APIs in the IDE completion for your cinterop library.

I thought that was kind of implied by "some system native type is added to your native library package." 😅
I deliberately wanted to keep this document short and high-level. In particular, don't use the term "cinterop library", since it is an implementation detail.

I'm not sure how to describe the specific symptom while keeping things short and high-level.

What do you think of

The Kotlin API of the native library includes a type that belongs to a system library.
I.e., everything compiles well, but some system native type is added to your native library package. For example, this system type can be visible in autocompletion in the IDE when and where you don't expect it.

?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think of

LGTM, I think this is worth mentioning so that the reader has some way to explore whether this happened to their library

neither exclude it nor replace (substitute) it.

So, they won't be able to resolve potential clashes with other Kotlin libraries that include the same static library
or to adjust the version of the static library.
Copy link
Collaborator

@abdulowork abdulowork Jun 11, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think they could, but it would not be very convenient. If they had a collision:

-library cinterop-with-libFooV1-a.klib -library cinterop-with-libFooV2-a.klib

they could prepend

-library cinterop-override-with-libFooV3-a.klib

and the override will come first in the filelist. Would this solve the issue of adjusting the version / replacing the library?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would this solve the issue of adjusting the version / replacing the library?

Not sure. How?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How?

On symbol collision, the linker should use the first static library in the filelist, and I assume the filelist order of bundled static libraries is defined by -library order. So by ordering or placing your cinterop library with a particular version of a static library, you should be able to override the static library bundled in your dependency

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, I see.

I assume the filelist order of bundled static libraries is defined by -library order.

I think the compiler topologically sorts them at some point.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants