| #!/bin/bash | 
 | # | 
 | # Copyright 2015 The Bazel Authors. All rights reserved. | 
 | # | 
 | # Licensed under the Apache License, Version 2.0 (the "License"); | 
 | # you may not use this file except in compliance with the License. | 
 | # You may obtain a copy of the License at | 
 | # | 
 | #    http://www.apache.org/licenses/LICENSE-2.0 | 
 | # | 
 | # Unless required by applicable law or agreed to in writing, software | 
 | # distributed under the License is distributed on an "AS IS" BASIS, | 
 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 
 | # See the License for the specific language governing permissions and | 
 | # limitations under the License. | 
 | # | 
 | # OS X relpath is not really working. This is a wrapper script around gcc | 
 | # to simulate relpath behavior. | 
 | # | 
 | # This wrapper uses install_name_tool to replace all paths in the binary | 
 | # (bazel-out/.../path/to/original/library.so) by the paths relative to | 
 | # the binary. It parses the command line to behave as rpath is supposed | 
 | # to work. | 
 | # | 
 | # See https://blogs.oracle.com/dipol/entry/dynamic_libraries_rpath_and_mac | 
 | # on how to set those paths for Mach-O binaries. | 
 | # | 
 | set -eu | 
 |  | 
 | GCC=/usr/bin/gcc | 
 | INSTALL_NAME_TOOL="/usr/bin/install_name_tool" | 
 |  | 
 | LIBS= | 
 | LIB_DIRS= | 
 | RPATH= | 
 | OUTPUT= | 
 | # let parse the option list | 
 | for i in "$@"; do | 
 |     if [[ "${OUTPUT}" = "1" ]]; then | 
 |         OUTPUT=$i | 
 |     elif [[ "$i" =~ ^-l(.*)$ ]]; then | 
 |         # lib | 
 |         LIBS="${BASH_REMATCH[1]} $LIBS" | 
 |     elif [[ "$i" =~ ^-L(.*)$ ]]; then | 
 |         # lib | 
 |         LIB_DIRS="${BASH_REMATCH[1]} $LIB_DIRS" | 
 |     elif [[ "$i" =~ ^-Wl,-rpath,\$ORIGIN/(.*)$ ]]; then | 
 |         # rpath | 
 |         RPATH=${BASH_REMATCH[1]} | 
 |     elif [[ "$i" = "-o" ]]; then | 
 |         # output is coming | 
 |         OUTPUT=1 | 
 |     fi | 
 | done | 
 |  | 
 | # Call gcc | 
 | ${GCC} "$@" | 
 |  | 
 | function get_library_path() { | 
 |     for libdir in ${LIB_DIRS}; do | 
 |         if [ -f ${libdir}/lib$1.so ]; then | 
 |             echo "${libdir}/lib$1.so" | 
 |         fi | 
 |     done | 
 | } | 
 |  | 
 | # A convenient method to return the actual path even for non symlinks | 
 | # and multi-level symlinks. | 
 | function get_realpath() { | 
 |     local previous="$1" | 
 |     local next=$(readlink "${previous}") | 
 |     while [ -n "${next}" ]; do | 
 |         previous="${next}" | 
 |         next=$(readlink "${previous}") | 
 |     done | 
 |     echo "${previous}" | 
 | } | 
 |  | 
 | # Get the path of a lib inside a tool | 
 | function get_otool_path() { | 
 |     # the lib path is the path of the original lib relative to the workspace | 
 |     get_realpath $1 | sed 's|^.*/bazel-out/|bazel-out/|' | 
 | } | 
 |  | 
 | # Do replacements in the output | 
 | if [ -n "${RPATH}" ]; then | 
 |     for lib in ${LIBS}; do | 
 |         libpath=$(get_library_path ${lib}) | 
 |         if [ -n "${libpath}" ]; then | 
 |             ${INSTALL_NAME_TOOL} -change $(get_otool_path "${libpath}") "@loader_path/${RPATH}/lib${lib}.so" "${OUTPUT}" | 
 |         fi | 
 |     done | 
 | fi | 
 |  |