As I mentioned in another comment, I'm not suggesting using m4 with/in-place of ansible -- rather as a compliment to the shell. I suppose one could use jinja2 stand-alone with the shell -- but then you get the python dependency etc... I meant that m4 might be a better fit to go along with bash/ksh.
Eg:
dpkg-query --show \
--showformat='${Package;6} ${Installed-Size;4}^L\n' \
m4 python2.7-minimal dash bash mksh ksh \|
sort -n -k2
dash 212
m4 382
mksh 878
ksh 3110
bash 3941
python 5456
(Not that you can avoid python-minmal on Debian - but in a chroot you might, etc).
As for can and cannot do, consider this "feature" of m4:
$ cat <<eof|m4 -Dme=you -Dpredictable=surprise
me=predictable
eof
you=surprise
Again, I'm not suggesting m4+dash is a great idea vs ansible -- just clarifying a couple of things...