Skip to content
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

Static libraries do not load dynamic functions and ignore initializer/finalizers #1200

Open
cbuttner opened this issue May 24, 2024 · 3 comments
Assignees
Labels
Bug Something isn't working Enhancement Request New feature or request Lower Priority This issue has lower priority for some reason Open Bug A bug which needs to be looked at
Milestone

Comments

@cbuttner
Copy link
Contributor

This happens on macOS.

Compile a C3 static library with

fn void test_c3() @export("test_c3") {
  Allocator allocator = allocator::heap();
  (void)allocator::new_array(allocator, int, 4);
}

Compile a C executable with

extern void test_c3();

int main(int argc, char** argv) {
  test_c3();
  return 0;
}

and link against the C3 library.
The program crashes, seemingly because the allocator interface is broken.

@lerno
Copy link
Collaborator

lerno commented May 25, 2024

For now -Wl,-all_load before linking the static library works.

@lerno lerno self-assigned this May 26, 2024
@lerno lerno added the Enhancement Request New feature or request label May 26, 2024
@lerno lerno added Bug Something isn't working and removed Enhancement Request New feature or request labels Jun 15, 2024
@lerno
Copy link
Collaborator

lerno commented Jun 15, 2024

If you do this with a C library, using the attribute((constructor)) I think you see the same thing (the constructor isn't called)

@lerno lerno added the Enhancement Request New feature or request label Jun 23, 2024
@lerno lerno added Open Bug A bug which needs to be looked at Lower Priority This issue has lower priority for some reason labels Aug 19, 2024
@lerno lerno added this to the 0.9 milestone Sep 14, 2024
@lerno lerno changed the title Interface crash with static library on macOS Static libraries do not load dynamic functions and ignore initializer/finalizers Sep 14, 2024
@lerno
Copy link
Collaborator

lerno commented Sep 14, 2024

The problem here is that if you include a static library, then unless the symbol can be traced it is deleted. While enforcing load works, this is not ideal.

We have the following situations:

  1. C3 static library with C main
  2. C3 static library x 2 with C main
  3. C3 static library with C3 main
  4. C3 static library x 2 with C3 main

On MacOS the constructors and destructors are placed in a special section. This will merge them. So this section is all that is needed to be retained in the 3/4 situation.

In 1/2 we also need to retain the loader of them.

On Linux/Wasm/Windows we rely on initializers. Here the problem is actually somewhat harder to fix.

For Objective-C, Clang requires a special -ObjC directive to make the methods in Objective-C classes be retained despite no direct dependency. This problem is similar to the same problem.

There are two ways to keep something from a static library:

  1. retrain a symbol that in turn links to it.
  2. take everything from the static lib

If we only dealt with a single static library, then we could create a $c3load function which would reference everything.

We would then use -symbol $c3load and it would be loaded.

However, if we have multiple static libraries this symbol would be overlapping. Can this be made to work? Or is a unique name needed, eg -symbol mylib$load?

Another alternative would be a linker script. This is a worse user experience I think, but if embedded in a linker, then perhaps it's possible.

Googling there seems to be no simple solution, but perhaps it's possible to do something clever.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Bug Something isn't working Enhancement Request New feature or request Lower Priority This issue has lower priority for some reason Open Bug A bug which needs to be looked at
Projects
None yet
Development

No branches or pull requests

2 participants