Skip to content

cc_wrapper for all OSes - #1039

Merged
mergify[bot] merged 32 commits into
masterfrom
cc_wrapper_windows
Sep 10, 2019
Merged

cc_wrapper for all OSes#1039
mergify[bot] merged 32 commits into
masterfrom
cc_wrapper_windows

Conversation

@aherrmann

Copy link
Copy Markdown
Contributor

Introduces cc_wrapper for all operating systems.

  • Shortens library search paths to stay below maximum path length on Windows.
    GHC generates library search paths that contain redundant up-level references (..). This can exceed the maximum path length on Windows, which will cause linking failures.
  • Shortens rpaths and load commands on macOS.
    The rpaths and load commands generated by GHC and Bazel can quickly exceed the MACH-O header size limit on macOS. This wrapper shortens and combines rpaths and load commands to avoid exceeding that limit.
  • Finds .so files if only .dylib are searched on macOS.
    Bazel's cc_library will generate .so files for dynamic libraries even on macOS. GHC strictly expects .dylib files on macOS. This wrapper hooks into gcc's --print-file-name feature to work around this mismatch in file extension.
  • Removes the need to generate dynamic library symbolic links addressing symlink_dynamic_library takes an unreasonable amount of time #958.
  • The CC wrapper is also used for REPL and runghc targets so that these also don't require symlinks for dynamic libraries on macOS.
  • Uses a separate cc_wrapper written in bash on Windows.
    This works around py_binary executables can be very slow on Windows bazelbuild/bazel#8981, execution of py_binary targets is too slow on Windows to be practical for cc_wrapper. On Windows the cc_wrapper only needs to shorten library search paths and not worry about rpaths or dynamic library file extensions. This allows for a much simpler cc_wrapper.
  • Tested on https://github.com/digital-asset/daml on Linux, macOS, and Windows.

Second attempt at #1002, which failed due to py_binary being too slow on Windows, see bazelbuild/bazel#8981.

Closes #958

@aherrmann

Copy link
Copy Markdown
Contributor Author

Rebased on master to fix merge conflict.

@Profpatsch Profpatsch left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

wip review

Comment thread haskell/private/actions/link.bzl
Comment thread haskell/private/cc_wrapper.bzl

@Profpatsch Profpatsch left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

WIP review, part 2/

# current argument, the stream of up-coming arguments, and a
# reference to the list of arguments to forward. The handler must
# return True if it consumes the argument, and return False if
# another handler should consume the argument.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

This is beautifully bonkers, but I got no suggestions.

Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl Outdated

@Profpatsch Profpatsch left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

WIP review 3/

Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Comment thread haskell/private/cc_wrapper.py.tpl
Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Always pass locale_archive to run_ghc if provided.
- Shortens library search paths to stay below maximum path length on Windows.

    GHC generates library search paths that contain redundant up-level
    references (..). This can exceed the maximum path length on Windows, which
    will cause linking failures. This wrapper shortens library search paths to
    avoid that issue.

- Shortens rpaths and load commands on macOS.

    The rpaths and load commands generated by GHC and Bazel can quickly exceed
    the MACH-O header size limit on macOS. This wrapper shortens and combines
    rpaths and load commands to avoid exceeding that limit.

- Finds .so files if only .dylib are searched on macOS.

    Bazel's cc_library will generate .so files for dynamic libraries even on
    macOS. GHC strictly expects .dylib files on macOS. This wrapper hooks into
    gcc's --print-file-name feature to work around this mismatch in file
    extension.
Otherwise we would still require symbolic links for dynamic library
dependencies on macOS for REPL targets.
The python cc_wrapper is too slow on Windows. See
#1002

Rewriting it in C++ would be a lot of work as we cannot rely on C++17's
std::filesystem, yet. Including a C++ filesystem library would impose a
large dependency. Fortunately, the Windows cc_wrapper only needs to
shorten library paths, not handle dynamic libraries. It is easier to use
a dedicated bash cc_wrapper on Windows instead.
These libraries cause linking errors on Windows when linking pthreads.
Use nameref variables to return values from functions instead of echoing
strings. This allows to avoid command substitution, which would create a
subprocess for each function call, which is costly on Windows.
It's an internal attribute and should not be accessed directly, instead
clients should use `Args.linking`, `Args.compiling`, or
`Args.printing_file_name`.

https://github.com/tweag/rules_haskell/pull/1039/files#r318549754

@Profpatsch Profpatsch left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Review 4/4

Comment thread haskell/private/cc_wrapper.py.tpl Outdated
Comment thread haskell/private/cc_wrapper.bzl Outdated
Comment thread haskell/private/cc_wrapper.sh.tpl Outdated
Comment thread haskell/private/cc_wrapper.sh.tpl Outdated
Comment thread haskell/private/cc_wrapper.sh.tpl
Comment thread haskell/private/cc_wrapper.py.tpl

@Profpatsch Profpatsch left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

How to eat an elephant.

From my side this is good to go, but it could be good to have a second review, since it’s highly non-trivial code.

@aherrmann

Copy link
Copy Markdown
Contributor Author

The CI failure is a timeout. I'm testing locally if there's a performance regression. I also started a rerun. The reason for the timeout may not be that anything in particular got slower, but rather that everything had to be rebuilt.

Reduces the runtime of the cc_wrapper in nix-shell by 60% in case of
short overall cc_wrapper execution time.
aherrmann-da pushed a commit to digital-asset/daml that referenced this pull request Sep 6, 2019
Updates to latest rules_haskell master and adds the cc_wrapper PR as a
patch, see tweag/rules_haskell#1039.
aherrmann-da pushed a commit to digital-asset/daml that referenced this pull request Sep 6, 2019
Updates to latest rules_haskell master and adds the cc_wrapper PR as a
patch, see tweag/rules_haskell#1039.
Comment thread haskell/ghc_bindist.bzl
)

if os == "windows":
# These libraries cause linking errors on Windows when linking

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Is there an upstream ticket for this?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Not that I know. I'll try to come up with a good repro and open a ticket.

mergify Bot pushed a commit to digital-asset/daml that referenced this pull request Sep 9, 2019
* Fix bazel query deps(//...)

* Add rules_haskell cc_wrapper

Updates to latest rules_haskell master and adds the cc_wrapper PR as a
patch, see tweag/rules_haskell#1039.

* Shorten include dirs in cc-wrapper

When using `haskell_cabal_library` GHC constructs unnecessarily long
include directories which can quickly overflow the maximum command-line
length. This patch avoids the issue by normalizing include paths.

* glob --> breadth_first_walk
@aherrmann aherrmann added the merge-queue merge on green CI label Sep 10, 2019
@mergify
mergify Bot merged commit ce0a7f3 into master Sep 10, 2019
mergify Bot pushed a commit that referenced this pull request Sep 10, 2019
@aherrmann
aherrmann deleted the cc_wrapper_windows branch September 10, 2019 11:58
@mergify mergify Bot removed the merge-queue merge on green CI label Sep 10, 2019
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.

symlink_dynamic_library takes an unreasonable amount of time

3 participants