tipushiba. megértéséhez szükséges az execv() syscall család ismerete.
az általad írt példában nagyjából ez történik:
(ha kieszképelted az értékadáskor az idézõjeleket, mert így syntax hibás)
execv('/bin/su', '-', 'zimbra', '-c', '"zmmailbox', '-z', ...)
másik esetben pedig: execv('/bin/sh', '-c', 'su - zimbra -c "zmmailbox -z ...')
tehát az $mktgz stringben átadott bash-es parancssorból a perl nem tudja kitalálni, melyik idézõjelet értetted literálisan és melyiket szántad a szóközökkel (IFS-sel) tagolt string egy paraméterként való értelmezésének kikényszerítéséhez.
Ugyanis az egész "zmmailbox -z -m $USER getRestURL '//?fmt=tgz'" rész a /bin/su 4. agrumentuma.
Viszont van egy másik eset is - talán a redir jel esetén -, amikor a perl elhárítja magáról a parancssor értelmezését, és átadja a $ENV{'SHELL'} -nek.
A >, <, | magic karakterek válthatják ki ezt az indulatot belõle. Mindjárt utánanézek.
Aztán lehet még hiba, a $valtozok behelyettesítése. A példádban már a perl behelyettesíti, de gondolom erre is számítasz, mivel a shellparancsban nem definiálsz valtozót. Viszont a $USER -bõl arra gondolok, hogy a USER environmentet akarod behelyettesíteni, emit perl-bõl $ENV{'USER'} -rel érsz el.
'//?fmt=tgz' -ben nincs bash számára magic karakter, ezért el lehet hagyni az aposztrófot, annyival is olvashatóbb és könnyebb eszképelni.
Beleirányítós kacsacsõr után egy token állhat, máskülönben a bash ambiguous redirect hibával tagadja meg a parancsot; ellenõrizd, hogy a $bckdir és $lines változók nem tartalmaznak space-t.
Mondanám, hogy open() vagy IPC::Open2::open2() -vel futtasd a parancsot, de az úgy lenne szép, ha elõtte $< állapotváltozó beállításával egybõl user-t valtanál (kivaltva ezzel az su -t), ahhoz viszont root-ként kéne futnia a perl scriptnek.
Aztán nem-e az van, hogy az su be akarja kérni a jelszót? És nem talál terminált, amire kiadja a noecho termio parancsot...