So, I finally did the exim4 upgrade that brought tainting and has now broken my mailman config.
I understand why tainting and the basics, but in the case of the mailman transport I wrote 20+ years ago, it is safe and I'd like to untaint local_part. Note that require_files encsures that local_part can't be random crap or the filematch would fail and the transport would never be called. Still, I tried to untaint with address_data and pass it to transport, but it's still tainted I lost 6H on this upgrade today and I'm now down until I downgrade exim and pin it back to an old version I'll never upgrade again. Before I go there, is there a fix to 22:29:56 1895290 ** [email protected] F=<[email protected]> R=mm21_main_director T=mm21_transport: Tainted arg 2 for mm21_transport transport command: 'testlist' ? What I have is: .ifdef MAILMAN_HOME # We want this router first in case we have a list named something like # mailman-owner mm21_main_director: debug_print = "R: mm21_main_director for $local_part@$domain" driver = accept # Explicitly untaint by capturing the validated local_part address_data = ${sg{${lc:$local_part}}{^([a-zA-Z0-9_.-]+)\$}{\$1}} # Condition to validate $local_part against safe characters and untaint it # We'll allow listname+foo addressing, but not for other admin addresses local_part_suffix = +* local_part_suffix_optional require_files = MAILMAN_HOME/lists/${lc::$local_part}/config.pck transport = mm21_transport mm21_director: debug_print = "R: mm21_director for $local_part@$domain" driver = accept # Explicitly untaint by capturing the validated local_part address_data = ${sg{${lc:$local_part}}{^([a-zA-Z0-9_.-]+)\$}{\$1}} require_files = MAILMAN_HOME/lists/${lc::$local_part}/config.pck address_data = ${sg{${lc:$local_part}}{^([a-zA-Z0-9_.-]+)\$}{\$1}} transport = mm21_transport .endif mm21_transport: debug_print = "T: mm21_transport for $local_part@$domain" driver = pipe # In case you wonder, substr_2 removes the leading '-' # and the regex removes optional +foo=hostname that can be after -bounce # (if you use VERP) -- Marc command = MAILMAN_WRAP "${if def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\\\\+.*}{}}}}{post}}" ${lc:$address_data} current_directory = MAILMAN_HOME home_directory = MAILMAN_HOME user = MAILMAN_UID group = MAILMAN_GID .endif 22:29:56 1895292 T: mm21_transport for [email protected] 22:29:56 1895292 mm21_transport transport entered 22:29:56 1895292 try option commsnd 22:29:56 1895292 direct command: 22:29:56 1895292 argv[0] = '/var/local/mailman/mail/mailman' 22:29:56 1895292 argv[1] = '${if def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}}' 22:29:56 1895292 argv[2] = '${lc:$address_data}' 22:29:56 1895292 arg 0 22:29:56 1895292 arg 1 22:29:56 1895292 ╭considering: ${if░def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ├──condition: def:local_part_suffix 22:29:56 1895292 ├─────result: false 22:29:56 1895292 ╭───scanning: ${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╭───scanning: {${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ├───────text: { 22:29:56 1895292 ├───scanning: ${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎╭───scanning: ${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ╭───scanning: $local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ├──────value: 22:29:56 1895292 ╎ ├───scanning: }}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ├───expanded: $local_part_suffix 22:29:56 1895292 ╎ ├─────result: ◀skipped▶ 22:29:56 1895292 ╎ ╰───skipping: result is not used 22:29:56 1895292 ╎├───scanning: }{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎├───expanded: ${lc:$local_part_suffix} 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ╎╭───scanning: \\+.*}{}}}}{post}} 22:29:56 1895292 ╎├backslashed: '\\' 22:29:56 1895292 ╎├───scanning: +.*}{}}}}{post}} 22:29:56 1895292 ╎├───────text: +.* 22:29:56 1895292 ╎├───scanning: }{}}}}{post}} 22:29:56 1895292 ╎├───expanded: \\+.* 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ╎╭───scanning: }}}}{post}} 22:29:56 1895292 ╎├───expanded: 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ├───scanning: }}{post}} 22:29:56 1895292 ├───expanded: {${sg{${lc:$local_part_suffix}}{\\+.*}{}} 22:29:56 1895292 ├─────result: ◀skipped▶ 22:29:56 1895292 ╰───skipping: result is not used 22:29:56 1895292 ├───scanning: }{post}} 22:29:56 1895292 ├───expanded: ${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}} 22:29:56 1895292 ├─────result: ◀skipped▶ 22:29:56 1895292 ╰───skipping: result is not used 22:29:56 1895292 ╭considering: post}} 22:29:56 1895292 ├───────text: post 22:29:56 1895292 ├considering: }} 22:29:56 1895292 ├───expanded: post 22:29:56 1895292 ╰─────result: post 22:29:56 1895292 ├───expanded: ${if░def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╰─────result: post 22:29:56 1895292 arg 2 22:29:56 1895292 ╭considering: ${lc:$address_data} 22:29:56 1895292 ╭considering: $address_data} 22:29:56 1895292 ├──────value: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├considering: } 22:29:56 1895292 ├───expanded: $address_data 22:29:56 1895292 ╰─────result: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├─────op-res: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├───expanded: ${lc:$address_data} 22:29:56 1895292 ╰─────result: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 search_tidyup called 22:29:56 1895292 >>>>>>>>>>>>>>>> Exim pid=1895292 (delivery-local) terminating with rc=0 >>>>>>>>>>>>>>>> 22:29:56 1895290 mm21_transport transport returned FAIL for [email protected] 22:29:56 1895290 post-process [email protected] (2) 22:29:56 1895290 LOG: MAIN 22:29:56 1895290 ** [email protected] F=<[email protected]> R=mm21_main_director T=mm21_transport: Tainted arg 2 for mm21_transport transport command: 'testlist' 22:29:56 1895292 T: mm21_transport for [email protected] 22:29:56 1895292 mm21_transport transport entered 22:29:56 1895292 try option commsnd 22:29:56 1895292 direct command: 22:29:56 1895292 argv[0] = '/var/local/mailman/mail/mailman' 22:29:56 1895292 argv[1] = '${if def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}}' 22:29:56 1895292 argv[2] = '${lc:$address_data}' 22:29:56 1895292 arg 0 22:29:56 1895292 arg 1 22:29:56 1895292 ╭considering: ${if░def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ├──condition: def:local_part_suffix 22:29:56 1895292 ├─────result: false 22:29:56 1895292 ╭───scanning: ${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╭───scanning: {${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ├───────text: { 22:29:56 1895292 ├───scanning: ${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎╭───scanning: ${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ╭───scanning: $local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ├──────value: 22:29:56 1895292 ╎ ├───scanning: }}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ├───expanded: $local_part_suffix 22:29:56 1895292 ╎ ├─────result: ◀skipped▶ 22:29:56 1895292 ╎ ╰───skipping: result is not used 22:29:56 1895292 ╎├───scanning: }{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎├───expanded: ${lc:$local_part_suffix} 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ╎╭───scanning: \\+.*}{}}}}{post}} 22:29:56 1895292 ╎├backslashed: '\\' 22:29:56 1895292 ╎├───scanning: +.*}{}}}}{post}} 22:29:56 1895292 ╎├───────text: +.* 22:29:56 1895292 ╎├───scanning: }{}}}}{post}} 22:29:56 1895292 ╎├───expanded: \\+.* 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ╎╭───scanning: }}}}{post}} 22:29:56 1895292 ╎├───expanded: 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ├───scanning: }}{post}} 22:29:56 1895292 ├───expanded: {${sg{${lc:$local_part_suffix}}{\\+.*}{}} 22:29:56 1895292 ├─────result: ◀skipped▶ 22:29:56 1895292 ╰───skipping: result is not used 22:29:56 1895292 ├───scanning: }{post}} 22:29:56 1895292 ├───expanded: ${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}} 22:29:56 1895292 ├─────result: ◀skipped▶ 22:29:56 1895292 ╰───skipping: result is not used 22:29:56 1895292 ╭considering: post}} 22:29:56 1895292 ├───────text: post 22:29:56 1895292 ├considering: }} 22:29:56 1895292 ├───expanded: post 22:29:56 1895292 ╰─────result: post 22:29:56 1895292 ├───expanded: ${if░def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╰─────result: post 22:29:56 1895292 arg 2 22:29:56 1895292 ╭considering: ${lc:$address_data} 22:29:56 1895292 ╭considering: $address_data} 22:29:56 1895292 ├──────value: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├considering: } 22:29:56 1895292 ├───expanded: $address_data 22:29:56 1895292 ╰─────result: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├─────op-res: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├───expanded: ${lc:$address_data} 22:29:56 1895292 ╰─────result: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 search_tidyup called 22:29:56 1895292 >>>>>>>>>>>>>>>> Exim pid=1895292 (delivery-local) terminating with rc=0 >>>>>>>>>>>>>>>> 22:29:56 1895290 mm21_transport transport returned FAIL for [email protected] 22:29:56 1895290 post-process [email protected] (2) 22:29:56 1895290 LOG: MAIN 22:29:56 1895290 ** [email protected] F=<[email protected]> R=mm21_main_director T=mm21_transport: Tainted arg 2 for mm21_transport transport command: 'testlist' 22:29:56 1895292 T: mm21_transport for [email protected] 22:29:56 1895292 mm21_transport transport entered 22:29:56 1895292 try option commsnd 22:29:56 1895292 direct command: 22:29:56 1895292 argv[0] = '/var/local/mailman/mail/mailman' 22:29:56 1895292 argv[1] = '${if def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}}' 22:29:56 1895292 argv[2] = '${lc:$address_data}' 22:29:56 1895292 arg 0 22:29:56 1895292 arg 1 22:29:56 1895292 ╭considering: ${if░def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ├──condition: def:local_part_suffix 22:29:56 1895292 ├─────result: false 22:29:56 1895292 ╭───scanning: ${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╭───scanning: {${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ├───────text: { 22:29:56 1895292 ├───scanning: ${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎╭───scanning: ${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ╭───scanning: $local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ├──────value: 22:29:56 1895292 ╎ ├───scanning: }}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎ ├───expanded: $local_part_suffix 22:29:56 1895292 ╎ ├─────result: ◀skipped▶ 22:29:56 1895292 ╎ ╰───skipping: result is not used 22:29:56 1895292 ╎├───scanning: }{\\+.*}{}}}}{post}} 22:29:56 1895292 ╎├───expanded: ${lc:$local_part_suffix} 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ╎╭───scanning: \\+.*}{}}}}{post}} 22:29:56 1895292 ╎├backslashed: '\\' 22:29:56 1895292 ╎├───scanning: +.*}{}}}}{post}} 22:29:56 1895292 ╎├───────text: +.* 22:29:56 1895292 ╎├───scanning: }{}}}}{post}} 22:29:56 1895292 ╎├───expanded: \\+.* 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ╎╭───scanning: }}}}{post}} 22:29:56 1895292 ╎├───expanded: 22:29:56 1895292 ╎├─────result: ◀skipped▶ 22:29:56 1895292 ╎╰───skipping: result is not used 22:29:56 1895292 ├───scanning: }}{post}} 22:29:56 1895292 ├───expanded: {${sg{${lc:$local_part_suffix}}{\\+.*}{}} 22:29:56 1895292 ├─────result: ◀skipped▶ 22:29:56 1895292 ╰───skipping: result is not used 22:29:56 1895292 ├───scanning: }{post}} 22:29:56 1895292 ├───expanded: ${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}} 22:29:56 1895292 ├─────result: ◀skipped▶ 22:29:56 1895292 ╰───skipping: result is not used 22:29:56 1895292 ╭considering: post}} 22:29:56 1895292 ├───────text: post 22:29:56 1895292 ├considering: }} 22:29:56 1895292 ├───expanded: post 22:29:56 1895292 ╰─────result: post 22:29:56 1895292 ├───expanded: ${if░def:local_part_suffix{${substr_2:{${sg{${lc:$local_part_suffix}}{\\+.*}{}}}}{post}} 22:29:56 1895292 ╰─────result: post 22:29:56 1895292 arg 2 22:29:56 1895292 ╭considering: ${lc:$address_data} 22:29:56 1895292 ╭considering: $address_data} 22:29:56 1895292 ├──────value: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├considering: } 22:29:56 1895292 ├───expanded: $address_data 22:29:56 1895292 ╰─────result: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├─────op-res: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 ├───expanded: ${lc:$address_data} 22:29:56 1895292 ╰─────result: testlist 22:29:56 1895292 ╰──(tainted) 22:29:56 1895292 search_tidyup called 22:29:56 1895292 >>>>>>>>>>>>>>>> Exim pid=1895292 (delivery-local) terminating with rc=0 >>>>>>>>>>>>>>>> 22:29:56 1895290 mm21_transport transport returned FAIL for [email protected] 22:29:56 1895290 post-process [email protected] (2) 22:29:56 1895290 LOG: MAIN 22:29:56 1895290 ** [email protected] F=<[email protected]> R=mm21_main_director T=mm21_transport: Tainted arg 2 for mm21_transport transport command: 'testlist' Thanks Marc -- "A mouse is a device used to point at the xterm you want to type in" - A.S.R. Home page: http://marc.merlins.org/ | PGP 7F55D5F27AAF9D08 -- ## subscription configuration (requires account): ## https://lists.exim.org/mailman3/postorius/lists/exim-users.lists.exim.org/ ## unsubscribe (doesn't require an account): ## [email protected] ## Exim details at http://www.exim.org/ ## Please use the Wiki with this list - http://wiki.exim.org/
