2024-08-24
| ||
12:08 | Merge [ee7ec33deb4d228f]: [fb2fa9b3f6] [21b0629c81]: ms-win: revert security patch to quote each %-c... check-in: 2cd781249b user: pooryorick tags: unchained, INCOMPATIBLE_LICENSE | |
2023-11-30
| ||
19:19 | • Closed ticket [21b0629c81]: 0-day vulnerability - insufficient escape by exec of batch-files for windows plus 6 other changes artifact: e3e71c4f57 user: oehhar | |
18:57 | Tickets [fb2fa9b3f6] [21b0629c81]: ms-win: revert security patch to quote each %-character seperatel... check-in: ee7ec33deb user: oehhar tags: core-8-6-branch | |
2023-11-16
| ||
16:27 | • Ticket [21b0629c81] 0-day vulnerability - insufficient escape by exec of batch-files for windows status still Open with 4 other changes artifact: b264ea45fc user: oehhar | |
16:04 | • Ticket [21b0629c81]: 3 changes artifact: 9f313465b7 user: sebres | |
15:17 | • Ticket [21b0629c81]: 4 changes artifact: 7ebcc8f520 user: oehhar | |
14:15 | • Ticket [21b0629c81]: 3 changes artifact: 934236ce4b user: sebres | |
2023-11-14
| ||
16:04 | • Ticket [21b0629c81]: 3 changes artifact: 8d99d3fd46 user: dkf | |
2023-11-10
| ||
11:12 | • Ticket [21b0629c81]: 4 changes artifact: b629a190ba user: oehhar | |
2023-11-03
| ||
11:35 | • Ticket [21b0629c81]: 4 changes artifact: 5b92321ad0 user: oehhar | |
11:30 | • Ticket [21b0629c81]: 4 changes artifact: 9bfcbeb6a2 user: oehhar | |
11:25 | Ticket [21b0629c] introduced additional exec quoting for Windows, but did not document it. Here is a... check-in: 7af4466e66 user: oehhar tags: bug-21b0629c-documentation | |
2023-10-27
| ||
10:46 | fixes percent-subst regression [fb2fa9b3f6] introduced by fixing of vulnerability [21b0629c81]; warn... check-in: ea3b6d6792 user: sebres tags: fix-fb2fa9b3f6--percent-subst-regr | |
08:33 | • Ticket [fb2fa9b3f6] exec broken for command having windows environment variables status still Open with 3 other changes artifact: 6be49fd251 user: sebres | |
2020-08-04
| ||
17:56 | • Ticket [344b1a0c0f] exec on Windows broken when '%' is used status still Open with 3 other changes artifact: db35f7bbc2 user: sebres | |
16:09 | • Closed ticket [efd15d181a]: problem with % in exec on windows plus 6 other changes artifact: 0cd4bc9531 user: sebres | |
2019-01-15
| ||
18:43 | • Ticket [344b1a0c0f] exec on Windows broken when '%' is used status still Open with 3 other changes artifact: fb1ca4ff9a user: sebres | |
2018-08-30
| ||
18:26 | • Open ticket [21b0629c81]: 0-day vulnerability - insufficient escape by exec of batch-files for windows plus 4 other changes artifact: cc35e8ac4d user: sebres | |
13:45 | • Closed ticket [21b0629c81]. artifact: 8e3b53ee69 user: sebres | |
2018-08-29
| ||
15:41 | merge 8.5 ([21b0629c81] 0-day vulnerability - insufficient escape by exec of batch-files for windows... check-in: 86e0fd3ecf user: sebres tags: core-8-6-branch | |
14:45 | closes [21b0629c81] 0-day vulnerability - insufficient escape by exec of batch-files for windows check-in: 99af12fd19 user: sebres tags: core-8-5-branch | |
2018-08-23
| ||
21:08 | • Ticket [21b0629c81] 0-day vulnerability - insufficient escape by exec of batch-files for windows status still Pending with 3 other changes artifact: a016935132 user: sebres | |
2018-08-21
| ||
19:04 | • Pending ticket [21b0629c81]. artifact: de74466f54 user: sebres | |
16:24 | • Open ticket [21b0629c81]. artifact: 7dec48d97f user: sebres | |
2018-08-20
| ||
19:59 | • Ticket [21b0629c81]: 3 changes artifact: 55b06569c7 user: sebres | |
18:08 | • Ticket [21b0629c81]: 3 changes artifact: 7ebe656be1 user: sebres | |
16:20 | • Pending ticket [21b0629c81]. artifact: b82e760bf4 user: sebres | |
14:35 | win: fixes [21b0629c81] - exec/open process pipe under windows (0-day vulnerability - insufficient e... check-in: cc1a3445f7 user: sebres tags: 0-day-21b0629c81 | |
2018-08-17
| ||
19:13 | • Ticket [21b0629c81] 0-day vulnerability - insufficient escape by exec of batch-files for windows status still Open with 4 other changes artifact: ba4545d022 user: sebres | |
14:23 | • Ticket [21b0629c81]: 3 changes artifact: b0654fef92 user: sebres | |
13:09 | • Ticket [21b0629c81]: 4 changes artifact: 471f3d796f user: sebres | |
13:09 | • New ticket [21b0629c81]. artifact: ba8f4fe0b6 user: sebres | |
Ticket UUID: | 21b0629c81fbe38ad153cd8fd899626200a66e15 | |||
Title: | 0-day vulnerability - insufficient escape by exec of batch-files for windows | |||
Type: | Bug | Version: | all (win) | |
Submitter: | sebres | Created on: | 2018-08-17 13:09:03 | |
Subsystem: | 16. Commands A-H | Assigned To: | sebres | |
Priority: | 9 Immediate | Severity: | Critical | |
Status: | Closed | Last Modified: | 2023-11-30 19:19:26 | |
Resolution: | Fixed | Closed By: | oehhar | |
Closed on: | 2023-11-30 19:19:26 | |||
Description: |
[UPDATED] Rather it is a matter the weird windows unescape behavior in case of command processor, For example python (for win):
See github.com/sebres/PoC/SB-0D-001-win-exec for more extensive PoC with additional info (and more lang's). Thanks to Peter (resuna) for link to discussion It looks like the arguments containing unpaired quote-chars somewhere will cause processing of the special meta-characters, so it should be extra escaped using tripple circumflex but only for unpaired quote-chars (by paired quotes it remains the meta-char as well as For more extensive PoC I wrote a small helper dumping arguments (here Instead of test-dump.exe one can use following code as And use following tcl-script ( set tn 0
foreach a {
{test"whoami} {test""whoami}
{test&whoami} {test|whoami}
{"test&whoami} {"test|whoami}
{test"&whoami} {test"|whoami}
{"test"&whoami} {"test"|whoami}
{""test"&whoami} {""test"|whoami}
{test&echo "} {test|echo "}
{"test&echo "} {"test|echo "}
{test"&echo "} {test"|echo "}
{"test"&echo "} {"test"|echo "}
{""test"&echo "} {""test"|echo "}
{test&echo ""} {test|echo ""}
{"test&echo ""} {"test|echo ""}
{test"&echo ""} {test"|echo ""}
{"test"&echo ""} {"test"|echo ""}
{""test"&echo ""} {""test"|echo ""}
{test>whoami} {test<whoami}
{"test>whoami} {"test<whoami}
{test">whoami} {test"<whoami}
{"test">whoami} {"test"<whoami}
{""test">whoami} {""test"<whoami}
{test(whoami)} {test(whoami)}
{test"(whoami)} {test"(whoami)}
{test^whoami} {test^^echo ^^^}
{test"^whoami} {test"^^echo ^^^}
} {
puts [string repeat - 20]
unset -nocomplain prevr
foreach cmd $testinv {
puts -nonewline [format "*%3d) `%s´" \
$tn [join [list test-dump[file extension [lindex $cmd 0]] $a] "´ `"]]
if {[catch {
set r [exec {*}$cmd $a]
} r]} {
set r "ERROR: $r"
}
if {![info exists prevr] || $prevr eq $r} {
puts ""
} else {
puts " -- *VULNERABLE*"
}
set prevr $r
puts [regsub -all -line {^} $r " "]
}
incr tn
}
The results:
--------------------
* 33) `test-dump.exe´ `test<whoami´
`test-dump.exe´ `test<whoami´
* 33) `test-dump.CMD´ `test<whoami´ -- *VULNERABLE*
`test-dump.exe´ `test´
--------------------
* 34) `test-dump.exe´ `"test>whoami´
`test-dump.exe´ `"test>whoami´
* 34) `test-dump.CMD´ `"test>whoami´
`test-dump.exe´ `"test>whoami´
--------------------
* 35) `test-dump.exe´ `"test<whoami´
`test-dump.exe´ `"test<whoami´
* 35) `test-dump.CMD´ `"test<whoami´
`test-dump.exe´ `"test<whoami´
--------------------
* 36) `test-dump.exe´ `test">whoami´
`test-dump.exe´ `test">whoami´
* 36) `test-dump.CMD´ `test">whoami´
`test-dump.exe´ `test">whoami´
--------------------
* 37) `test-dump.exe´ `test"<whoami´
`test-dump.exe´ `test"<whoami´
* 37) `test-dump.CMD´ `test"<whoami´
`test-dump.exe´ `test"<whoami´
--------------------
* 38) `test-dump.exe´ `"test">whoami´
`test-dump.exe´ `"test">whoami´
* 38) `test-dump.CMD´ `"test">whoami´ -- *VULNERABLE*
--------------------
* 39) `test-dump.exe´ `"test"<whoami´
`test-dump.exe´ `"test"<whoami´
* 39) `test-dump.CMD´ `"test"<whoami´ -- *VULNERABLE*
`test-dump.exe´ `"test"´
--------------------
* 40) `test-dump.exe´ `""test">whoami´
`test-dump.exe´ `""test">whoami´
* 40) `test-dump.CMD´ `""test">whoami´
`test-dump.exe´ `""test">whoami´
--------------------
* 41) `test-dump.exe´ `""test"<whoami´
`test-dump.exe´ `""test"<whoami´
* 41) `test-dump.CMD´ `""test"<whoami´
`test-dump.exe´ `""test"<whoami´
--------------------
* 42) `test-dump.exe´ `test(whoami)´
`test-dump.exe´ `test(whoami)´
* 42) `test-dump.CMD´ `test(whoami)´
`test-dump.exe´ `test(whoami)´
--------------------
* 43) `test-dump.exe´ `test(whoami)´
`test-dump.exe´ `test(whoami)´
* 43) `test-dump.CMD´ `test(whoami)´
`test-dump.exe´ `test(whoami)´
--------------------
* 44) `test-dump.exe´ `test"(whoami)´
`test-dump.exe´ `test"(whoami)´
* 44) `test-dump.CMD´ `test"(whoami)´
`test-dump.exe´ `test"(whoami)´
--------------------
* 45) `test-dump.exe´ `test"(whoami)´
`test-dump.exe´ `test"(whoami)´
* 45) `test-dump.CMD´ `test"(whoami)´
`test-dump.exe´ `test"(whoami)´
--------------------
* 46) `test-dump.exe´ `test^whoami´
`test-dump.exe´ `test^whoami´
* 46) `test-dump.CMD´ `test^whoami´ -- *VULNERABLE*
`test-dump.exe´ `testwhoami´
--------------------
* 47) `test-dump.exe´ `test^^echo ^^^´
`test-dump.exe´ `test^^echo ^^^´
* 47) `test-dump.CMD´ `test^^echo ^^^´
`test-dump.exe´ `test^^echo ^^^´
--------------------
* 48) `test-dump.exe´ `test"^whoami´
`test-dump.exe´ `test"^whoami´
* 48) `test-dump.CMD´ `test"^whoami´
`test-dump.exe´ `test"^whoami´
--------------------
* 49) `test-dump.exe´ `test"^^echo ^^^´
`test-dump.exe´ `test"^^echo ^^^´
* 49) `test-dump.CMD´ `test"^^echo ^^^´ -- *VULNERABLE*
`test-dump.exe´ `test"echo ´
The major injury is happened by pre-processing of the arguments with special meta-chars (so depends on quotes-count or position), but some tests show that Tcl seems to have here additionally insufficient escaping by some special characters (at least looks like vulnerable arguments-handling, also by execution of some tests without unpaired quotes (after escape). Fixed in branch 0-day-21b0629c81. | |||
User Comments: |
oehhar added on 2023-11-30 19:19:26:
Branch [fix-fb2fa9b3f6--percent-subst-regr] was merged with commit [ee7ec33deb]. Only the "%env%" part of ticket [ea3b6d6792] is reverted. The requirement was ticket [fb2fa9b3f6]. Open work for a general multi-mode exec is pending. Thanks to Sergey ! Harald oehhar added on 2023-11-16 16:27:56: Sergey, yes, I also think, we should only revert the special treatment of "%" by individual quoting. The rest of the patch improves anyway already present quoting rules and fixes issues with them (double quoting). Please just go on and merge it to 8.6. Thank you and take care, Harald sebres added on 2023-11-16 16:04:07: I meant only revert the special %-escape (so basically merge branch "fix-fb2fa9b3f6--percent-subst-regr"). Because the rest of [21b0629c81] is fully justified in my opinion, as well as more or less backwards compatible (unless one doesn't try to simulate special "raw" invocation by inject into old escape handling in order to get some special command line). But sure, I can do that, once I'd get the fossil to hand. Regarding the documentation, one'd then only need to meant that %-chars are not (yet) specially escaped, so by execution of comspec/batch/cmd windows would replace oehhar added on 2023-11-16 15:17:57: Dear Sergey, if you are the opinion, that this should be reverted, it would be great to do that soon. I think, this would be a good thing, as the usability for me is higher, than the vulnerability protection. Could you just act and do the changes? I may assist and adapt the documentation. Thank you for your constant effort, great ! Take care, Harald sebres added on 2023-11-16 14:15:48: Well, conditionally true... Even main of many script langs are implemented not very compliant to "default" parameters parsing - see the table in spoiler. But there is Although the more or less correct handling of comspec (cmd/bat/etc) is hard job, and one can't really do that fully correctly - therefore there is a new branch fix-fb2fa9b3f6--percent-subst-regr, reverting parts of this fix, handling the percent char and so restore the backwards compatibility calling comspec with More or less with a future This fix implements correct escape for dkf added on 2023-11-14 16:04:35: Ultimately, there isn't that much we can do because Windows itself is not consistent. When dealing with the Windows command line, parsing of that command line is done by the receiving program (usually by it's runtime bootstrap code) and that's inconsistent because there are multiple different runtimes in use out there. It's especially bad when dealing with the Tcl has historically taken the view of trying to make things work well with the MSVC runtime (by far the most common) and for the rest... well, you can write stuff into a batch script (with as much safe control as you like) and run that. It's an impossible situation; direct use of the Windows command line to run programs with untrusted arguments is simply not secure. Note that All IIRC. I've not made much use of this knowledge for over a decade (other than to always give oehhar added on 2023-11-10 11:12:02: Documentation of the current state added in core-8-6-branch and up: [71dd06e857] To control the quoting of exec is a purpose of a TIP which may come up soon. Thanks, Sergey, for the help on the documentation, Harald oehhar added on 2023-11-03 11:35:00: Also, recent discussion on this topic may be found in ticket [fb2fa9b3f6]. Take care, Harald oehhar added on 2023-11-03 11:30:32: Thanks, great ! Proposed documentation for the introduced quoting in commit [7af4466e66] for review. Review welcome ! Harald sebres added on 2018-08-30 18:26:26:
So although now it is anyway better as it previously was, the story continues -
the handling round about percent character is a bit complex:
Thanks to Eryk Sun (@eryksun) noticed this by the fix for python. So there are three possible scenarios:
So I'm by 2 at the moment, WiP. sebres added on 2018-08-30 13:45:55: closed within merge [99af12fd19] and the following, for >= 8.5 sebres added on 2018-08-21 19:04:39: Grrr... amend in [ae46c72447] should fix it now (+ extends test-cases). Further tests are welcome. sebres added on 2018-08-21 16:24:32:
Never ending story: found new cases that are still uncovered by current fix: WiP. sebres added on 2018-08-20 18:08:01:
Although this fixed the issue, at the same time it is a bit incompatible if wanted "raw" (not escaped) arguments, Search for exec in own (as well as many open source) projects, shows me almost never the usage of "raw" arguments as expected case. In contrary, many invocation's of Therefore (and because this fixed a grave 0-day vulnerability), the default escape should take place as it is implemented in 0-day-21b0629c81. But perhaps, just to provide the developer a possibility to invoke sebres added on 2018-08-20 16:20:31:
Fixed in branch 0-day-21b0629c81 (for 8.5). sebres added on 2018-08-17 19:13:18:
Updated with many other test-cases (with better readability as single-line, etc.).
|