1*4882a593Smuzhiyun#!/usr/bin/env bash 2*4882a593Smuzhiyun 3*4882a593Smuzhiyun# Try to hardlink a file into a directory, fallback to copy on failure. 4*4882a593Smuzhiyun# 5*4882a593Smuzhiyun# Hardlink-or-copy the source file in the first argument into the 6*4882a593Smuzhiyun# destination directory in the second argument, using the basename in 7*4882a593Smuzhiyun# the third argument as basename for the destination file. If the third 8*4882a593Smuzhiyun# argument is missing, use the basename of the source file as basename 9*4882a593Smuzhiyun# for the destination file. 10*4882a593Smuzhiyun# 11*4882a593Smuzhiyun# In either case, remove the destination prior to doing the 12*4882a593Smuzhiyun# hardlink-or-copy. 13*4882a593Smuzhiyun# 14*4882a593Smuzhiyun# Note that this is NOT an atomic operation. 15*4882a593Smuzhiyun 16*4882a593Smuzhiyunset -e 17*4882a593Smuzhiyun 18*4882a593Smuzhiyunmain() { 19*4882a593Smuzhiyun local src_file="${1}" 20*4882a593Smuzhiyun local dst_dir="${2}" 21*4882a593Smuzhiyun local dst_file="${3}" 22*4882a593Smuzhiyun 23*4882a593Smuzhiyun if [ -n "${dst_file}" ]; then 24*4882a593Smuzhiyun dst_file="${dst_dir}/${dst_file}" 25*4882a593Smuzhiyun else 26*4882a593Smuzhiyun dst_file="${dst_dir}/${src_file##*/}" 27*4882a593Smuzhiyun fi 28*4882a593Smuzhiyun 29*4882a593Smuzhiyun mkdir -p "${dst_dir}" 30*4882a593Smuzhiyun rm -f "${dst_file}" 31*4882a593Smuzhiyun ln -f "${src_file}" "${dst_file}" 2>/dev/null \ 32*4882a593Smuzhiyun || cp -f "${src_file}" "${dst_file}" 33*4882a593Smuzhiyun} 34*4882a593Smuzhiyun 35*4882a593Smuzhiyunmain "${@}" 36