git-gui: handle the encoding of Git's output correctly
authorKarsten Blees <blees@dcon.de>
Thu, 26 Feb 2015 09:19:45 +0000 (17:19 +0800)
committerPat Thoyts <patthoyts@users.sourceforge.net>
Thu, 6 Oct 2016 08:23:21 +0000 (09:23 +0100)
If we use 'eval exec $opt $cmdp $args' to execute git command,
tcl engine will convert the output of the git comand with the rule
system default code page to unicode.

But cp936 -> unicode conversion implicitly done by exec is not reversible.
So we have to use git_read instead.

Bug report and an original reproducer by Cloud Chou:
https://github.com/msysgit/git/issues/302

Cloud Chou find the reason of the bug.

Thanks-to: Johannes Schindelin <johannes.schindelin@gmx.de>
Thanks-to: Pat Thoyts <patthoyts@users.sourceforge.net>
Reported-by: Cloud Chou <515312382@qq.com>
Original-test-by: Cloud Chou <515312382@qq.com>
Signed-off-by: Karsten Blees <blees@dcon.de>
Signed-off-by: Cloud Chou <515312382@qq.com>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Pat Thoyts <patthoyts@users.sourceforge.net>
git-gui.sh
index 1f5acc3c75cfae7a5354467c8060fe3d2f3ea7e5..5bc21b878d413e27de8e3d54e66a138ff41c7daa 100755 (executable)
@@ -534,31 +534,10 @@ proc _lappend_nice {cmd_var} {
 }
 
 proc git {args} {
-       set opt [list]
-
-       while {1} {
-               switch -- [lindex $args 0] {
-               --nice {
-                       _lappend_nice opt
-               }
-
-               default {
-                       break
-               }
-
-               }
-
-               set args [lrange $args 1 end]
-       }
-
-       set cmdp [_git_cmd [lindex $args 0]]
-       set args [lrange $args 1 end]
-
-       _trace_exec [concat $opt $cmdp $args]
-       set result [eval exec $opt $cmdp $args]
-       if {[encoding system] != "utf-8"} {
-               set result [encoding convertfrom utf-8 [encoding convertto $result]]
-       }
+       set fd [eval [list git_read] $args]
+       fconfigure $fd -translation binary -encoding utf-8
+       set result [string trimright [read $fd] "\n"]
+       close $fd
        if {$::_trace} {
                puts stderr "< $result"
        }