#    rpmmacro.at: test rpm macros
#
AT_BANNER([RPM macros])

# ------------------------------
AT_SETUP([simple rpm --eval])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --define "this that" --eval '%{this}' --eval '%not_defined' --eval '%{not_defined}' --eval '%{}'
],
[0],
[that
%not_defined
%{not_defined}
%{}
])
AT_CLEANUP

# ------------------------------
AT_SETUP([invalid rpm --eval])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --eval '%define _ that'
],
[1],
[],
[error: Macro %_ has illegal name (%define)
])
AT_CLEANUP

# ------------------------------
AT_SETUP([invalid rpm --define])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --define "_ that"
runroot rpm --define "undefine that"
],
[1],
[],
[error: Macro %_ has illegal name (%define)
error: Macro %undefine is a built-in (%define)
])
AT_CLEANUP

AT_SETUP([rpm --undefine])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --define "this that" --eval '1. %{this}' --undefine 'this' --eval '2. %{this'}
runroot rpm --eval '1. %{this}' --define "this that" --eval '2. %{this}' --undefine 'this' --eval '3. %{this'}
],
[0],
[1. that
2. %{this}
1. %{this}
2. that
3. %{this}
])
AT_CLEANUP

AT_SETUP([simple true conditional rpm --eval])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --define "this that" --eval '%{?this}'
],
[0],
[that
])
AT_CLEANUP

AT_SETUP([simple false conditional rpm --eval])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --define "this that" --eval '%{?that}'
],
[0],
[
])
AT_CLEANUP

AT_SETUP([nested macro in name])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --define "this that" --define "that_that foo" --eval '%{expand:%{%{this}_that}}'
],
[0],
[foo
])
AT_CLEANUP

AT_SETUP([parametrized macro 1])
AT_KEYWORDS([macros])
AT_CHECK([
RPMDB_INIT
cat << EOF > ${RPMTEST}/mtest
%bar() bar
%foo()\\
%bar\\
foo 1\\
%{bar}\\
foo 2\\
%bar x\\
foo 3\\
%{bar x}\\
foo 4\\
%bar \\
foo 5
EOF

runroot rpm --eval '%{load:mtest}%{foo}'
],
[0],
[
bar
foo 1
bar
foo 2
bar
foo 3
bar
foo 4
bar
foo 5
],
[])
AT_CLEANUP

AT_SETUP([parametrized macro 2])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define '%bar() "Bar %#: %{?1} %{?2}"' \
    --define '%foo() "Foo %#: %{?1} %{?2}" %bar a' \
    --eval '%foo 1 2'
],
[0],
["Foo 2: 1 2" "Bar 1: a "
])
AT_CLEANUP

AT_SETUP([parametrized macro 3])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define '%foo() 1:%1 2:%2' \
    --eval '%foo %nil bar'
],
[0],
[1:bar 2:%2
])
AT_CLEANUP

AT_SETUP([parametrized macro 4])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define '%bar yyy' \
    --define '%foo() %1' \
    --eval '%foo %bar' \
    --eval '%foo %%bar'
],
[0],
[yyy
%bar
])
AT_CLEANUP

AT_SETUP([parametrized macro 5])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define '%foo() %#:%{?1:"%1"}%{?2: "%2"}' \
    --define 'bar zzz' \
    --eval '%foo 1' \
    --eval '%foo   2  ' \
    --eval '%foo 1 2' \
    --eval '%foo %{nil}' \
    --eval '%foo %{nil} xx' \
    --eval '%foo %{bar} xx' \
    --eval '%foo %{quote:   2 3  5} %{quote:%{nil}}' \
    --eval '%foo x%{quote:y}z 123' \
    --eval '%foo x%{quote:%{nil}}z' \
    --eval '%foo 1 \
bar' \
    --eval '%foo 1 \' \
],
[0],
[1:"1"
1:"2"
2:"1" "2"
0:
1:"xx"
2:"zzz" "xx"
2:"   2 3  5" ""
2:"xyz" "123"
1:"xz"
2:"1" "\"bar
2:"1" "\"
])
AT_CLEANUP

AT_SETUP([uncompress macro 1])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define "__gzip /my/bin/gzip" \
    --eval "%{uncompress:/data/SOURCES/hello-2.0.tar.gz}"
],
[0],
[/my/bin/gzip -dc /data/SOURCES/hello-2.0.tar.gz
])
AT_CLEANUP

AT_SETUP([uncompress macro 2])
AT_KEYWORDS([macros])
AT_CHECK([
RPMDB_INIT
echo xxxxxxxxxxxxxxxxxxxxxxxxx > ${RPMTEST}/tmp/"some%%ath"
runroot rpm \
    --eval "%{uncompress:/tmp/some%%%%ath}"
],
[0],
[/usr/bin/cat /tmp/some%%ath
])

AT_CLEANUP
AT_SETUP([basename macro])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval "%{basename:/data/SOURCES/hello-2.0.tar.gz}"
],
[0],
[hello-2.0.tar.gz
])
AT_CLEANUP

AT_SETUP([shrink macro])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval "%{shrink:  h e  l   lo  }"
],
[0],
[h e l lo
])
AT_CLEANUP

AT_SETUP([suffix macro])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval "%{suffix:/data/SOURCES/hello-2.0.tar.gz}"
],
[0],
[gz
])
AT_CLEANUP

AT_SETUP([url2path macro])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval "%{url2path:http://hello.org/releases/hello-2.0.tar.gz}"
],
[0],
[/releases/hello-2.0.tar.gz
])
AT_CLEANUP

AT_SETUP([macrobody macro])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define "somedir %{_exec_prefix}/%{_lib}" \
    --eval "%{macrobody:somedir}"
runroot rpm \
    --define "something somedir" \
    --define "somedir %{_exec_prefix}/%{_lib}" \
    --eval "%{macrobody:%{something}}"
],
[0],
[%{_exec_prefix}/%{_lib}
%{_exec_prefix}/%{_lib}
])
AT_CLEANUP

AT_SETUP([builtin macro arguments])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --eval "%{dirname}"
runroot rpm --eval "%{dirname:}"
runroot rpm --eval "%{dirname:dir}"
runroot rpm --define '%xxx /hello/%%%%/world' --eval '%{dirname:%xxx}'
runroot rpm --eval "%{uncompress}"
runroot rpm --eval "%{uncompress:}"
runroot rpm --eval "%{getncpus:}"
runroot rpm --eval "%{getncpus:5}"
runroot rpm --eval "%{define:}"
runroot rpm --eval "%{dump:foo}"
],
[1],
[
dir
/hello/%%

],
[error: %dirname: argument expected
error: %uncompress: argument expected
error: %getncpus: unexpected argument
error: %getncpus: unexpected argument
error: %define: unexpected argument
error: %dump: unexpected argument
])
AT_CLEANUP

AT_SETUP([expr macro 1])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define "aaa 5" \
    --define "bbb 0" \
    --eval '%{expr:4*1024}' \
    --eval '%{expr:5 < 1}' \
    --eval '%{expr:(4 + 5) * 2 == 18}' \
    --eval '%{expr:%{aaa} || %{bbb}}' \
    --eval '%{expr:%{aaa} && %{bbb}}' \
    --eval '%{expr:! ""}' \
    --eval '%{expr:! "foo"}' \
    --eval '%{expr: 0 || 3}' \
    --eval '%{expr: 2 || 3}' \
    --eval '%{expr: "" || "foo"}' \
    --eval '%{expr: "bar" || "foo"}' \
    --eval '%{expr: 0 && 3}' \
    --eval '%{expr: 2 && 3}' \
    --eval '%{expr: "" && "foo"}' \
    --eval '%{expr: "bar" && "foo"}'
],
[0],
[4096
0
1
5
0
1
0
3
2
foo
bar
0
3

foo
],
[])
AT_CLEANUP

AT_SETUP([expr macro 2])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --eval '%{expr:"a"*1}'
runroot rpm --eval '%{expr:(5+1)*4)}'
runroot rpm --eval '%{expr:"a"=!"b"}'
runroot rpm --eval '%{expr:4+}'
runroot rpm --eval '%{expr:bare}'
runroot rpm --eval '%{expr:1/0}'
runroot rpm --eval '%{expr:0 < 1 ? 2 : 1*"a"}'
runroot rpm --eval '%{expr:0 < 1 ? 1*"a" : 2}'
runroot rpm --eval '%{expr:0 < 1 ? 2 : "a"}'
runroot rpm --eval '%{expr:0 < 1 ? "a" : 2}'
],
[1],
[],
[error: types must match: "a"*1
error: syntax error in expression: (5+1)*4)
error:                                    ^
error: syntax error while parsing ==: "a"=!"b"
error:                                    ^
error: unexpected end of expression: 4+
error:                                ^
error: bare words are no longer supported, please use "...": bare
error:                                                       ^
error: division by zero: 1/0
error:                    ^
error: types must match: 0 < 1 ? 2 : 1*"a"
error: types must match: 0 < 1 ? 1*"a" : 2
error: types must match: 0 < 1 ? 2 : "a"
error: types must match: 0 < 1 ? "a" : 2
])
AT_CLEANUP

AT_SETUP([ternary expressions])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval '%{expr: 0 ? 2 : 3}' \
    --eval '%{expr: 1 ? 2 : 3}' \
    --eval '%{expr: 0 ? 0 ? 3 : 4 : 0 ? 6 : 7}' \
    --eval '%{expr: 0 ? 0 ? 3 : 4 : 5 ? 6 : 7}' \
    --eval '%{expr: 0 ? 2 ? 3 : 4 : 0 ? 6 : 7}' \
    --eval '%{expr: 0 ? 2 ? 3 : 4 : 5 ? 6 : 7}' \
    --eval '%{expr: 1 ? 0 ? 3 : 4 : 0 ? 6 : 7}' \
    --eval '%{expr: 1 ? 0 ? 3 : 4 : 5 ? 6 : 7}' \
    --eval '%{expr: 1 ? 2 ? 3 : 4 : 0 ? 6 : 7}' \
    --eval '%{expr: 1 ? 2 ? 3 : 4 : 5 ? 6 : 7}' \
],
[0],
[3
2
7
6
7
6
4
4
3
3
],
[])
AT_CLEANUP

AT_SETUP([short circuiting])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval '%{expr: 0 && 1 / 0}' \
    --eval '%{expr: 1 || 1 / 0}' \
    --eval '%{expr: 1 ? 2 : 1 / 0}' \
],
[0],
[0
1
2
],
[])
AT_CLEANUP

AT_SETUP([shell expansion])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --eval "%(echo foo)"
],
[0],
[foo
])
AT_CLEANUP

AT_SETUP([expression expansion 1])
AT_KEYWORDS([macros])
AT_CHECK([[
runroot rpm \
    --define "aaa 5" \
    --define "bbb 0" \
    --eval '%[4*1024]' \
    --eval '%[5 < 1]' \
    --eval '%[%aaa]' \
    --eval '%[%{aaa}]' \
    --eval '%["%{aaa}"]' \
    --eval '%[%{?ccc}]' \
    --eval '%[v"1:2.3-4"]' \
]],
[0],
[4096
0
5
5
5
0
1:2.3-4
],
[])
AT_CLEANUP

AT_SETUP([expression expansion 2])
AT_KEYWORDS([macros])
AT_CHECK([[
runroot rpm --define "aaa hello" --eval '%[%aaa]'
runroot rpm --eval '%[%{foo]'
runroot rpm --eval '%[v""]'
runroot rpm --eval '%[v"1" + v"2"]'
runroot rpm --eval '%[v"1" / v"2"]'
]],
[1],
[],
[error: macro expansion returned a bare word, please use "...": %aaa
error:                                                         ^
error: expanded string: hello
error: Unterminated {: {foo 
error: invalid version: v""
error:                    ^
error: + and - not supported for versions: v"1" + v"2"
error:                                          ^
error: * and / not supported for versions: v"1" / v"2"
error:                                          ^
])
AT_CLEANUP

AT_SETUP([expression version comparison])
AT_KEYWORDS([macros])
AT_CHECK([[
runroot rpm \
    --eval '%[v"1.0" == v"1.0"]' \
    --eval '%[v"1.0~rc" < v"1.0"]' \
    --eval '%[v"1.0~rc" > v"1.0"]' \
    --eval '%[v"1.0-rc" > v"1.0"]' \
]],
[0],
[1
1
0
1
],
[])
AT_CLEANUP

AT_SETUP([simple lua --eval])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
runroot rpm --eval '%{lua:print(5*5)}'
],
[0],
[25
])
AT_CLEANUP

AT_SETUP([lua rpm extensions 1])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
runroot rpm --eval '%{lua: rpm.define("foo bar") print(rpm.expand("%{foo}"))}'
],
[0],
[bar
])
AT_CLEANUP

AT_SETUP([lua rpm extensions 2])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
runroot rpm --eval '%{lua: print(rpm.vercmp("1.0", "2.0"))}'
],
[0],
[-1
])

AT_CLEANUP
AT_SETUP([lua posix extensions])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
runroot rpm \
  --eval '%{lua: posix.putenv("LUATEST=ok") print(posix.getenv("LUATEST"))}'
],
[0],
[ok
])
AT_CLEANUP

AT_SETUP([lua script exit behavior])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
runroot rpm \
  --eval '%{lua: os.exit()}))}'
],
[1],
[],
[error: lua script failed: [[string "<lua>"]]:1: exit not permitted in this context]
)
AT_CLEANUP

AT_SETUP([lua script redirect2null])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
runroot rpm \
  --eval '%{lua: posix.redirect2null()}))}'
],
[1],
[],
[error: lua script failed: [[string "<lua>"]]:1: redirect2null not permitted in this context]
)
AT_CLEANUP

AT_SETUP([lua library path])
AT_KEYWORDS([macros lua])
AT_CHECK([
AT_SKIP_IF([$LUA_DISABLED])
RPMDB_INIT
f=$(run rpm --eval "%{_rpmconfigdir}/lua/foo.lua")
echo "bar = 'graak'" > ${f}
runroot rpm \
  --eval '%{lua:require "foo"; print(bar)}'
rm -f ${f}
],
[0],
[graak
])
AT_CLEANUP

AT_SETUP([%define + %undefine in nested levels 1])
AT_KEYWORDS([macros define undefine])
AT_CHECK([
# basic %define in nested scoping level
runroot rpm \
    --define '%foo() %{expand:%define xxx 1} %{echo:%xxx} %{expand:%undefine xxx} %{echo:%xxx}' \
    --eval .'%foo'.
],
[0],
[1
%xxx
.   .
])
AT_CLEANUP

AT_SETUP([%define + %undefine in nested levels 2])
AT_KEYWORDS([macros define])
AT_CHECK([
# %define macro once in a nested scope
runroot rpm \
    --define '%foo() %{expand:%define xxx 1} %{echo:%xxx}' \
    --eval .'%foo'. \
    --eval '%xxx'
],
[0],
[1
. .
%xxx
])
AT_CLEANUP

AT_SETUP([%define + %undefine in nested levels 3])
AT_KEYWORDS([macros define])
AT_CHECK([
AT_XFAIL_IF([test $RPM_XFAIL -ne 0])
# %define macro twice in a nested scope
runroot rpm \
    --define '%foo() %{expand:%define xxx 1} %{echo:%xxx} %{expand: %define xxx 2} %{echo:%xxx}' \
    --eval .'%foo'. \
    --eval '%xxx'
],
[0],
[1
2
.    .
%xxx
])
AT_CLEANUP

AT_SETUP([%define + %undefine in nested levels 4])
AT_KEYWORDS([macros define global])
AT_CHECK([
AT_XFAIL_IF([test $RPM_XFAIL -ne 0])
# %define in a nested level covered by %global
runroot rpm \
    --define '%foo() %{expand:%define xxx 1} %{echo:%xxx} %{expand: %global xxx 2} %{echo:%xxx}' \
    --eval .'%foo'. \
    --eval '%xxx' \
    --eval .'%undefine xxx'. \
    --eval '%xxx'
],
[0],
[1
2
.    .
2
..
%xxx
])
AT_CLEANUP

AT_SETUP([%define in conditional macro])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
    --define 'dofoo() true'\
    --eval '.%{!?foo: %define foo bar}.'\
    --eval '%foo' \
    --eval '%dofoo'\
    --eval '%foo'
],
[0],
[. .
bar
true
bar
])
AT_CLEANUP

AT_SETUP([%verbose negative test])
AT_KEYWORDS([macros verbose])
AT_CHECK([
runroot rpm \
  --eval '%{verbose:%{echo:is verbose}}' \
  --eval '%{verbose:is verbose text}'\
  --eval '%{!verbose:%{echo:is not verbose}}'\
  --eval '%{!verbose:is not verbose text}'
],
[0],
[

is not verbose

is not verbose text
])
AT_CLEANUP

AT_SETUP([%verbose positive test])
AT_KEYWORDS([macros verbose])
AT_CHECK([
runroot rpm -v \
  --eval '%{!verbose:%{echo:is not verbose}}' \
  --eval '%{!verbose:is not verbose text}'\
  --eval '%{verbose:%{echo:is verbose}}'\
  --eval '%{verbose:is verbose text}'
],
[0],
[

is verbose

is verbose text
])
AT_CLEANUP

AT_SETUP([macro with a line starting by "{"])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm --macros "/data/macros.testfile" \
	--eval "%first" --eval "%second"],
[0],
[macro_1

macro_2
])
AT_CLEANUP

AT_SETUP([macro with %if-%endif])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpmspec -q --qf "%{summary}\n%{description}\n" /data/SPECS/iftest.spec
],
[0],
[macro 1
ccc0
ccc1
])
AT_CLEANUP

AT_SETUP([macro file errors])
AT_KEYWORDS([macros])
AT_CHECK([
cat << EOF > macros.bad
%_i foo

%multi \\
line\\
thing

%foo bar
%bad-name 123
EOF

run rpm --macros "macros.bad" --eval "%foo"
],
[0],
[bar
],
[error: macros.bad: line 1: Macro %_i has illegal name (%define)
warning: macros.bad: line 8: Macro %bad needs whitespace before body
])
AT_CLEANUP

AT_SETUP([macro comments])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
	--macros /data/macros.testfile \
	--eval "%{comment1}" \
	--eval "%{comment2}"
],
[0],
[
read
me

see
this
],
[])
AT_CLEANUP

AT_SETUP([macro comments 2])
AT_KEYWORDS([macros])
AT_CHECK([
runroot rpm \
	--macros /data/macros.testfile \
	--eval "%{comment3}"
],
[0],
[
read
' change this meaning
],
[])
AT_CLEANUP

