1*4882a593Smuzhiyun# This allows us to work with the newline character: 2*4882a593Smuzhiyundefine newline 3*4882a593Smuzhiyun 4*4882a593Smuzhiyun 5*4882a593Smuzhiyunendef 6*4882a593Smuzhiyunnewline := $(newline) 7*4882a593Smuzhiyun 8*4882a593Smuzhiyun# nl-escape 9*4882a593Smuzhiyun# 10*4882a593Smuzhiyun# Usage: escape = $(call nl-escape[,escape]) 11*4882a593Smuzhiyun# 12*4882a593Smuzhiyun# This is used as the common way to specify 13*4882a593Smuzhiyun# what should replace a newline when escaping 14*4882a593Smuzhiyun# newlines; the default is a bizarre string. 15*4882a593Smuzhiyun# 16*4882a593Smuzhiyunnl-escape = $(if $(1),$(1),m822df3020w6a44id34bt574ctac44eb9f4n) 17*4882a593Smuzhiyun 18*4882a593Smuzhiyun# escape-nl 19*4882a593Smuzhiyun# 20*4882a593Smuzhiyun# Usage: escaped-text = $(call escape-nl,text[,escape]) 21*4882a593Smuzhiyun# 22*4882a593Smuzhiyun# GNU make's $(shell ...) function converts to a 23*4882a593Smuzhiyun# single space each newline character in the output 24*4882a593Smuzhiyun# produced during the expansion; this may not be 25*4882a593Smuzhiyun# desirable. 26*4882a593Smuzhiyun# 27*4882a593Smuzhiyun# The only solution is to change each newline into 28*4882a593Smuzhiyun# something that won't be converted, so that the 29*4882a593Smuzhiyun# information can be recovered later with 30*4882a593Smuzhiyun# $(call unescape-nl...) 31*4882a593Smuzhiyun# 32*4882a593Smuzhiyunescape-nl = $(subst $(newline),$(call nl-escape,$(2)),$(1)) 33*4882a593Smuzhiyun 34*4882a593Smuzhiyun# unescape-nl 35*4882a593Smuzhiyun# 36*4882a593Smuzhiyun# Usage: text = $(call unescape-nl,escaped-text[,escape]) 37*4882a593Smuzhiyun# 38*4882a593Smuzhiyun# See escape-nl. 39*4882a593Smuzhiyun# 40*4882a593Smuzhiyununescape-nl = $(subst $(call nl-escape,$(2)),$(newline),$(1)) 41*4882a593Smuzhiyun 42*4882a593Smuzhiyun# shell-escape-nl 43*4882a593Smuzhiyun# 44*4882a593Smuzhiyun# Usage: $(shell some-command | $(call shell-escape-nl[,escape])) 45*4882a593Smuzhiyun# 46*4882a593Smuzhiyun# Use this to escape newlines from within a shell call; 47*4882a593Smuzhiyun# the default escape is a bizarre string. 48*4882a593Smuzhiyun# 49*4882a593Smuzhiyun# NOTE: The escape is used directly as a string constant 50*4882a593Smuzhiyun# in an `awk' program that is delimited by shell 51*4882a593Smuzhiyun# single-quotes, so be wary of the characters 52*4882a593Smuzhiyun# that are chosen. 53*4882a593Smuzhiyun# 54*4882a593Smuzhiyundefine shell-escape-nl 55*4882a593Smuzhiyunawk 'NR==1 {t=$$0} NR>1 {t=t "$(nl-escape)" $$0} END {printf t}' 56*4882a593Smuzhiyunendef 57*4882a593Smuzhiyun 58*4882a593Smuzhiyun# shell-unescape-nl 59*4882a593Smuzhiyun# 60*4882a593Smuzhiyun# Usage: $(shell some-command | $(call shell-unescape-nl[,escape])) 61*4882a593Smuzhiyun# 62*4882a593Smuzhiyun# Use this to unescape newlines from within a shell call; 63*4882a593Smuzhiyun# the default escape is a bizarre string. 64*4882a593Smuzhiyun# 65*4882a593Smuzhiyun# NOTE: The escape is used directly as an extended regular 66*4882a593Smuzhiyun# expression constant in an `awk' program that is 67*4882a593Smuzhiyun# delimited by shell single-quotes, so be wary 68*4882a593Smuzhiyun# of the characters that are chosen. 69*4882a593Smuzhiyun# 70*4882a593Smuzhiyun# (The bash shell has a bug where `{gsub(...),...}' is 71*4882a593Smuzhiyun# misinterpreted as a brace expansion; this can be 72*4882a593Smuzhiyun# overcome by putting a space between `{' and `gsub'). 73*4882a593Smuzhiyun# 74*4882a593Smuzhiyundefine shell-unescape-nl 75*4882a593Smuzhiyunawk 'NR==1 {t=$$0} NR>1 {t=t "\n" $$0} END { gsub(/$(nl-escape)/,"\n",t); printf t }' 76*4882a593Smuzhiyunendef 77*4882a593Smuzhiyun 78*4882a593Smuzhiyun# escape-for-shell-sq 79*4882a593Smuzhiyun# 80*4882a593Smuzhiyun# Usage: embeddable-text = $(call escape-for-shell-sq,text) 81*4882a593Smuzhiyun# 82*4882a593Smuzhiyun# This function produces text that is suitable for 83*4882a593Smuzhiyun# embedding in a shell string that is delimited by 84*4882a593Smuzhiyun# single-quotes. 85*4882a593Smuzhiyun# 86*4882a593Smuzhiyunescape-for-shell-sq = $(subst ','\'',$(1)) 87*4882a593Smuzhiyun 88*4882a593Smuzhiyun# shell-sq 89*4882a593Smuzhiyun# 90*4882a593Smuzhiyun# Usage: single-quoted-and-escaped-text = $(call shell-sq,text) 91*4882a593Smuzhiyun# 92*4882a593Smuzhiyunshell-sq = '$(escape-for-shell-sq)' 93*4882a593Smuzhiyun 94*4882a593Smuzhiyun# shell-wordify 95*4882a593Smuzhiyun# 96*4882a593Smuzhiyun# Usage: wordified-text = $(call shell-wordify,text) 97*4882a593Smuzhiyun# 98*4882a593Smuzhiyun# For instance: 99*4882a593Smuzhiyun# 100*4882a593Smuzhiyun# |define text 101*4882a593Smuzhiyun# |hello 102*4882a593Smuzhiyun# |world 103*4882a593Smuzhiyun# |endef 104*4882a593Smuzhiyun# | 105*4882a593Smuzhiyun# |target: 106*4882a593Smuzhiyun# | echo $(call shell-wordify,$(text)) 107*4882a593Smuzhiyun# 108*4882a593Smuzhiyun# At least GNU make gets confused by expanding a newline 109*4882a593Smuzhiyun# within the context of a command line of a makefile rule 110*4882a593Smuzhiyun# (this is in constrast to a `$(shell ...)' function call, 111*4882a593Smuzhiyun# which can handle it just fine). 112*4882a593Smuzhiyun# 113*4882a593Smuzhiyun# This function avoids the problem by producing a string 114*4882a593Smuzhiyun# that works as a shell word, regardless of whether or 115*4882a593Smuzhiyun# not it contains a newline. 116*4882a593Smuzhiyun# 117*4882a593Smuzhiyun# If the text to be wordified contains a newline, then 118*4882a593Smuzhiyun# an intrictate shell command substitution is constructed 119*4882a593Smuzhiyun# to render the text as a single line; when the shell 120*4882a593Smuzhiyun# processes the resulting escaped text, it transforms 121*4882a593Smuzhiyun# it into the original unescaped text. 122*4882a593Smuzhiyun# 123*4882a593Smuzhiyun# If the text does not contain a newline, then this function 124*4882a593Smuzhiyun# produces the same results as the `$(shell-sq)' function. 125*4882a593Smuzhiyun# 126*4882a593Smuzhiyunshell-wordify = $(if $(findstring $(newline),$(1)),$(_sw-esc-nl),$(shell-sq)) 127*4882a593Smuzhiyundefine _sw-esc-nl 128*4882a593Smuzhiyun"$$(echo $(call escape-nl,$(shell-sq),$(2)) | $(call shell-unescape-nl,$(2)))" 129*4882a593Smuzhiyunendef 130*4882a593Smuzhiyun 131*4882a593Smuzhiyun# is-absolute 132*4882a593Smuzhiyun# 133*4882a593Smuzhiyun# Usage: bool-value = $(call is-absolute,path) 134*4882a593Smuzhiyun# 135*4882a593Smuzhiyunis-absolute = $(shell echo $(shell-sq) | grep -q ^/ && echo y) 136*4882a593Smuzhiyun 137*4882a593Smuzhiyun# lookup 138*4882a593Smuzhiyun# 139*4882a593Smuzhiyun# Usage: absolute-executable-path-or-empty = $(call lookup,path) 140*4882a593Smuzhiyun# 141*4882a593Smuzhiyun# (It's necessary to use `sh -c' because GNU make messes up by 142*4882a593Smuzhiyun# trying too hard and getting things wrong). 143*4882a593Smuzhiyun# 144*4882a593Smuzhiyunlookup = $(call unescape-nl,$(shell sh -c $(_l-sh))) 145*4882a593Smuzhiyun_l-sh = $(call shell-sq,command -v $(shell-sq) | $(call shell-escape-nl,)) 146*4882a593Smuzhiyun 147*4882a593Smuzhiyun# is-executable 148*4882a593Smuzhiyun# 149*4882a593Smuzhiyun# Usage: bool-value = $(call is-executable,path) 150*4882a593Smuzhiyun# 151*4882a593Smuzhiyun# (It's necessary to use `sh -c' because GNU make messes up by 152*4882a593Smuzhiyun# trying too hard and getting things wrong). 153*4882a593Smuzhiyun# 154*4882a593Smuzhiyunis-executable = $(call _is-executable-helper,$(shell-sq)) 155*4882a593Smuzhiyun_is-executable-helper = $(shell sh -c $(_is-executable-sh)) 156*4882a593Smuzhiyun_is-executable-sh = $(call shell-sq,test -f $(1) -a -x $(1) && echo y) 157*4882a593Smuzhiyun 158*4882a593Smuzhiyun# get-executable 159*4882a593Smuzhiyun# 160*4882a593Smuzhiyun# Usage: absolute-executable-path-or-empty = $(call get-executable,path) 161*4882a593Smuzhiyun# 162*4882a593Smuzhiyun# The goal is to get an absolute path for an executable; 163*4882a593Smuzhiyun# the `command -v' is defined by POSIX, but it's not 164*4882a593Smuzhiyun# necessarily very portable, so it's only used if 165*4882a593Smuzhiyun# relative path resolution is requested, as determined 166*4882a593Smuzhiyun# by the presence of a leading `/'. 167*4882a593Smuzhiyun# 168*4882a593Smuzhiyunget-executable = $(if $(1),$(if $(is-absolute),$(_ge-abspath),$(lookup))) 169*4882a593Smuzhiyun_ge-abspath = $(if $(is-executable),$(1)) 170*4882a593Smuzhiyun 171*4882a593Smuzhiyun# get-supplied-or-default-executable 172*4882a593Smuzhiyun# 173*4882a593Smuzhiyun# Usage: absolute-executable-path-or-empty = $(call get-executable-or-default,variable,default) 174*4882a593Smuzhiyun# 175*4882a593Smuzhiyundefine get-executable-or-default 176*4882a593Smuzhiyun$(if $($(1)),$(call _ge_attempt,$($(1)),$(1)),$(call _ge_attempt,$(2))) 177*4882a593Smuzhiyunendef 178*4882a593Smuzhiyun_ge_attempt = $(if $(get-executable),$(get-executable),$(call _gea_err,$(2))) 179*4882a593Smuzhiyun_gea_err = $(if $(1),$(error Please set '$(1)' appropriately)) 180