Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
Comment: | Merge from trunk |
---|---|
Downloads: | Tarball | ZIP archive |
Timelines: | family | ancestors | descendants | both | thread |
Files: | files | file ages | folders |
SHA1: |
d1d44e3aedd340c84b95f711eb1d4408 |
User & Date: | peter 2016-08-03 17:45:11.795 |
Context
2016-08-06
| ||
18:59 | Handle vfs in threads Leaf check-in: a36a8fc470 user: peter tags: thread | |
2016-08-03
| ||
17:45 | Merge from trunk check-in: d1d44e3aed user: peter tags: thread | |
17:44 | Added ability to transfer mounts to another thread. check-in: e650f1067c user: peter tags: thread | |
2016-07-29
| ||
22:03 | Include plugin options in plugin dialog. check-in: c9e28d0c53 user: peter tags: trunk | |
Changes
Changes to Changes.
1 2 3 4 5 6 7 | 2016-07-01 When displaying a patch, detect chunks marked with ##. E.g. svn diff lists changed properties like that. 2016-06-10 Reorganised code for option descriptions. | > > > > > > > > > > | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | 2016-07-29 Include plugin command line options in command line help. Include plugin options in plugin dialog. 2016-07-29 Corrected right side numbering when parsing patch. [288be8f321] 2016-07-06 Support negative revisions with GIT. Added log view for GIT. 2016-07-01 When displaying a patch, detect chunks marked with ##. E.g. svn diff lists changed properties like that. 2016-06-10 Reorganised code for option descriptions. |
︙ | ︙ |
Changes to htdocs/changes.wiki.
1 2 3 4 | <title>Changes</title> Upcoming changes (not yet released): | > | > | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | <title>Changes</title> Upcoming changes (not yet released): * Corrected right side numbering when parsing patch. * Word parse now consistently uses non-space as word char. * New [./table.wiki | table] view, activated by -table, when comparing tables. * Mercurial support for Directory Diff, Commit, Revert and Log. * GIT support for negative revisions and log view. * Printed PDF is now compressed. * Printed PDF from patch view adds page break between files. * Plugins can define command line options they accept. * Plugins can read ::argv to know the given command line. * New plugin for binary files * New plugin for CSV files * Added option -sep, to set a separator that makes input be interpreted |
︙ | ︙ | |||
22 23 24 25 26 27 28 | Changes in v2.7 (2015-03-09): * Directory Diff support for GIT, Fossil and Subversion. Directly browse and compare two revisions. * Plugins in Directory Diff. * Added option -printFont to select font for PDF generation. Default font changed to a True Type font. | | | 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | Changes in v2.7 (2015-03-09): * Directory Diff support for GIT, Fossil and Subversion. Directly browse and compare two revisions. * Plugins in Directory Diff. * Added option -printFont to select font for PDF generation. Default font changed to a True Type font. Use "-printFont Courier" to fall back on PDF built-in. * Mac supported Changes in v2.6.7 (2014-11-13): * Fixed Directory Diff that stopped working in 2.6.6 Changes in v2.6.6 (2014-10-27): |
︙ | ︙ | |||
67 68 69 70 71 72 73 | * Support negative revisions with Fossil. * Added -nocdiff command line flag for debug. * Fixed a bug where alignment was not properly shown in output. * Fixed out-of-stack crash. Changes in v2.6.1 (2011-11-01): | | | | 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 | * Support negative revisions with Fossil. * Added -nocdiff command line flag for debug. * Fixed a bug where alignment was not properly shown in output. * Fixed out-of-stack crash. Changes in v2.6.1 (2011-11-01): * Eskil [http://eskil.tcl.tk|re-hosted] and changed to use [http://www.fossil-scm.org|Fossil]. * Fixed directory diff appearance on Windows. * Fixed bug where copy button in directory diff picked the wrong file. * Fixed bug where plugins were not found in VFS. Changes in v2.6 (2011-10-30): * Support commit in Git and Fossil. * Support commit, list of files and revisions with -review. * Added Paste Patch command. * New -pluginlist option. New GUI for plugin selection. * Added three-way merge. * Auto-detect line endings in ancestor file to select merge output. * Fully rewritten directory diff with new design. * Set alignment with drag & drop. Changes in v2.5 (2011-04-01): * Requires Tcl 8.5. * Plugins: Added dump, better documentation. |
︙ | ︙ | |||
124 125 126 127 128 129 130 | * Added experimental -nonewline command option. * Added -close command option. * Added experimental PDF print. * Added dirdiff preferences and filters. * Smarter save in merge. FR 2957 * Added commit button for CVS. FR 2780 | | | 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 | * Added experimental -nonewline command option. * Added -close command option. * Added experimental PDF print. * Added dirdiff preferences and filters. * Smarter save in merge. FR 2957 * Added commit button for CVS. FR 2780 * Bug fixes include: Kits are mounted read-only, fixed dir diff window menu, improved patch file parsing. Changes in v2.1 (2006-06-02): * Added -preprocess command line option. * Added -foreach command line option. * Added -context command line option. |
︙ | ︙ | |||
167 168 169 170 171 172 173 | * Added context options for "Diffs only" mode. * Rewrote how "Separate Diff" and "Align" works. The latter now only happens after a "Redo Diff". * Added scroll map and some more context menu options in Directory Diff. Changes in v2.0.2 (2004-05-03): * Fixed a bug in ClearCase support. | | | 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 | * Added context options for "Diffs only" mode. * Rewrote how "Separate Diff" and "Align" works. The latter now only happens after a "Redo Diff". * Added scroll map and some more context menu options in Directory Diff. Changes in v2.0.2 (2004-05-03): * Fixed a bug in ClearCase support. * Improved enscript usage in print command. * Added "mark file" in dirdiff context menu. Changes in v2.0.1 (2004-02-10): * Added preference for width and height. * Added Tools menu to directory diff window. * Made it simpler to save a conflict in the same file. First public release v2.0 (2004-01-30): |
Changes to htdocs/plugins.wiki.
︙ | ︙ | |||
20 21 22 23 24 25 26 27 28 29 30 31 32 33 | * -plugin plugin : Use plugin * -plugininfo info : Pass info to plugin (plugin specific) * -plugindump plugin : Dump plugin source to stdout * -pluginlist : List known plugins * -pluginallow : Allow full access privilege for a plugin. A plugin may further define command line options that it accepts. <h1>General Format</h1> A plugin is a Tcl script file that must start with the verbatim sequence "##Eskil Plugin :". A plugin is sourced and used in its own safe interpreter and thus have free access to its own global space. Hookup points are defined by declaring specifically named procedures as specified | > > | 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | * -plugin plugin : Use plugin * -plugininfo info : Pass info to plugin (plugin specific) * -plugindump plugin : Dump plugin source to stdout * -pluginlist : List known plugins * -pluginallow : Allow full access privilege for a plugin. A plugin may further define command line options that it accepts. A way to see the plugin's options is to do: <pre>eskil -plugin <plg> -help</pre> <h1>General Format</h1> A plugin is a Tcl script file that must start with the verbatim sequence "##Eskil Plugin :". A plugin is sourced and used in its own safe interpreter and thus have free access to its own global space. Hookup points are defined by declaring specifically named procedures as specified |
︙ | ︙ | |||
51 52 53 54 55 56 57 | <h2>Additional options</h2> A plugin can declare command line options that should be accepted by Eskil. They will be passed on to the plugin through the ::argv list. If the initial "##Eskil" line is followed by comments formatted as below, it adds options. Any empty line will end parsing for such lines. A line like "## Option -<option>" declares an option that takes a value and | | | > > | | | 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 | <h2>Additional options</h2> A plugin can declare command line options that should be accepted by Eskil. They will be passed on to the plugin through the ::argv list. If the initial "##Eskil" line is followed by comments formatted as below, it adds options. Any empty line will end parsing for such lines. A line like "## Option -<option>" declares an option that takes a value and a line like "## Flag -<option>" declares an option without value. The rest of the line after the option name is functionally ignored and can be used for comments. It is included in command line help, so the rest should preferably be formatted as " : Explanation" if used. <h1>File plugin</h1> To process the files being compared, the following procedure should be defined in the plugin file: <pre>proc PreProcess {side chi cho} {...}</pre> The arguments given to PreProcess are: * side : left or right, indicating which file is being handled * chi : An input channel for reading the original file * cho : An output channel for writing the processed file A plugin may give a result that has a line-by-line correspondence to the original, in which case the preprocessed data is used for comparing while the original is used for displaying. The PreProcess procedure should return 0 to signify this case. If the PreProcess procedure returns 1, the processed data is used also for displaying. If Eskil is run with Tcl 8.6 or newer, PreProcess is run as a coroutine and may yield. The left and right side will then be called alternately until they return. This allows a plugin to take both sides into account for decisions if needed. <h1>Directory plugin</h1> To be used for file comparison in a directory diff, the following procedure |
︙ | ︙ |
Changes to htdocs/revision.wiki.
1 2 3 4 | <title>Revision Control Support</title> <h1>Introduction</h1> | | | 1 2 3 4 5 6 7 8 9 10 11 12 | <title>Revision Control Support</title> <h1>Introduction</h1> Eskil can compare versions in many revision control systems. Currently RCS, CVS, Git, Fossil, Mercurial, Bazaar, Subversion, Perforce and ClearCase are supported (some features are not implemented for all systems). If you specify only one file on the command line to Eskil, it will automatically detect if the file is under revision control and enter revision control mode. By default the local file is compared against the latest checked in version. |
︙ | ︙ | |||
102 103 104 105 106 107 108 | <pre>git config --global diff.tool eskil</pre> <pre>git config --global difftool.eskil.cmd 'eskil $LOCAL $REMOTE'</pre> <h2>Fossil</h2> For Fossil -r <rev> is passed to finfo, as in "fossil finfo -p <file> -r <rev>". | | | 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 | <pre>git config --global diff.tool eskil</pre> <pre>git config --global difftool.eskil.cmd 'eskil $LOCAL $REMOTE'</pre> <h2>Fossil</h2> For Fossil -r <rev> is passed to finfo, as in "fossil finfo -p <file> -r <rev>". Additionally, if a revision is zero or a negative integer, the log is searched backwards for earlier versions. E.g. -1 gives the second to last version. The search follows the current branch from the current version. To use Eskil for conflict resolution these settings can be used. <pre>fossil settings gmerge-command 'eskil -fine -a "%baseline" "%merge" "%original" -o "%output"' -global</pre> |
︙ | ︙ |
Changes to htdocs/table.wiki.
1 2 3 4 5 6 7 8 9 10 | <title>Table diff</title> <h1>Table diff</h1> Eskil can compare tables in comma/tab separated text files and display them like a table. <verbatim> eskil -table apa1.csv apa2.csv </verbatim> | | | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | <title>Table diff</title> <h1>Table diff</h1> Eskil can compare tables in comma/tab separated text files and display them like a table. <verbatim> eskil -table apa1.csv apa2.csv </verbatim> Eskil will try to auto-detect the separator but you can also give it using -sep. Example for tab separation: <verbatim> eskil -table -sep '\t' apa1.csv apa2.csv </verbatim> Eskil has a built in plugin, csv, than can preprocess table files. This example clears the "Short" and "Long" columns before comparison: |
︙ | ︙ |
Changes to plugins/backslash.tcl.
1 | ##Eskil Plugin : Compare with backslash-newline removed | | > > > | < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | ##Eskil Plugin : Compare with backslash-newline removed # # This plugin replaces any backslash-newline with space, thus # ignoring restructured lines. # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { set trim 0 while {[gets $chi line] >= 0} { |
︙ | ︙ |
Changes to plugins/binary.tcl.
1 2 | ##Eskil Plugin : Compare binary files, in hex ## Option -binsep : A set of chars to be used as "newline" | | > > > > > | < < < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | ##Eskil Plugin : Compare binary files, in hex ## Option -binsep : A set of chars to be used as "newline" # # This plugin converts files to hex to be able to compare binary files. # A set of chars can be defined to be used as "newline". Default "0 10 13". # Example usage: # eskil -plugin binary -binsep "0 10 13 32" f1 f2 # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin may declare command line options that should be allowed through # to ::argv # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { set delimitL [list 0 10 13] if {[llength $::Info] > 0} { |
︙ | ︙ |
Changes to plugins/csv.tcl.
1 2 3 4 5 6 7 8 9 10 11 12 | ##Eskil Plugin : Compare comma separated value (CSV) files ## Option -csvignore : A list of columns to ignore ## Option -csvkey : A list of columns to sort on before comparison ## Flag -csvheader : First line is a header line defining names of columns # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin may declare command line options that should be allowed through # to ::argv | > > > > > < < < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | ##Eskil Plugin : Compare comma separated value (CSV) files ## Option -csvignore : A list of columns to ignore ## Option -csvkey : A list of columns to sort on before comparison ## Flag -csvheader : First line is a header line defining names of columns # # This plugin compares CSV files with some preprocessing available # Example usage: # eskil -plugin csv -csvignore "head3 head5" -csvkey head2 -sep , \ # examples/dir*/csv1.txt # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin may declare command line options that should be allowed through # to ::argv # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { # Look for parameters in command line set opts(-sep) "," |
︙ | ︙ |
Changes to plugins/grep.tcl.
1 2 | ##Eskil Plugin : Compare after filtering lines ## Option -grepre : Regexp to filter on | | > > > > | < < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | ##Eskil Plugin : Compare after filtering lines ## Option -grepre : Regexp to filter on # # This plugin only compares lines that match a regexp pattern. # Example usage: # eskil -plugin grep -grepre "<t>" f1 f2 # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin may declare command line options that should be allowed through # to ::argv # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { if {[catch {llength $::Info}]} { puts $cho "Grep plugin needs -plugininfo parameter to be a list" |
︙ | ︙ |
Changes to plugins/keyword.tcl.
1 | ##Eskil Plugin : Ignore $Keywords$ | | > > > | < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | ##Eskil Plugin : Ignore $Keywords$ # # This plugin ignores keywords like $Revision$, both in file diff # and in directory diff # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { while {1} { # Read data in large chunks for speed |
︙ | ︙ |
Changes to plugins/nocase.tcl.
1 | ##Eskil Plugin : Case insensitive matching | | > > > | < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | ##Eskil Plugin : Case insensitive matching # # This plugin implements case insensitive matching, similar to the # -nocase flag. # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { while {1} { # Read data in large chunks for speed |
︙ | ︙ |
Changes to plugins/pdf.tcl.
1 | ##Eskil Plugin : Compare text from PDF files. (needs pdftotext) | | < < < < > > > > | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | ##Eskil Plugin : Compare text from PDF files. (needs pdftotext) # # This plugin runs input through the external tool pdftotext. # Thus it must be run together with the -pluginallow flag. # Anything given in -plugininfo is passed as parameters to pdftotext. # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { if {[info commands exec] eq ""} { puts $cho "PDF plugin must be run with privilege to be able\ |
︙ | ︙ |
Changes to plugins/sort.tcl.
1 | ##Eskil Plugin : Compare files after sorting lines | | > > | < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | ##Eskil Plugin : Compare files after sorting lines # # This plugin compares files after sorting the lines in each side # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { set data [read $chi] set endingNewLine 0 |
︙ | ︙ |
Changes to plugins/swap.tcl.
1 | ##Eskil Plugin : Swap sides of contents | | > > > | < < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | ##Eskil Plugin : Swap sides of contents # # This plugin swaps data between files. A fairly useless thing. # This is to test and exemplify how to use yield in a plugin. # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { if {[info commands yield] eq ""} { puts $cho "Swap plugin must be run with Tcl 8.6 or newer" |
︙ | ︙ |
Changes to plugins/words.tcl.
1 | ##Eskil Plugin : Compare set of words | | > > | < < | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | ##Eskil Plugin : Compare set of words # # This plugin compares the set of words in files. # Example file for a plugin. # A plugin's first line must start exactly like this one. # The text after : is the summary you can get at the command line # A plugin must define this procedure to do the job. # side: left or right # chi: An input channel for reading the original file. # cho: An output channel for writing the processed file. proc PreProcess {side chi cho} { while {[gets $chi line] >= 0} { foreach word [regexp -all -inline {\w+} $line] { |
︙ | ︙ |
Changes to src/eskil.tcl.
︙ | ︙ | |||
1237 1238 1239 1240 1241 1242 1243 | # We are in a -u style diff if {$state eq "both"} { if {![regexp {^[\s+-]} $line]} continue set sig [string trim [string index $line 0]] set str [string range $line 1 end] if {$sig eq ""} { lappend leftLines [list $leftLine "" $str] | | | | 1237 1238 1239 1240 1241 1242 1243 1244 1245 1246 1247 1248 1249 1250 1251 1252 1253 1254 1255 1256 1257 1258 | # We are in a -u style diff if {$state eq "both"} { if {![regexp {^[\s+-]} $line]} continue set sig [string trim [string index $line 0]] set str [string range $line 1 end] if {$sig eq ""} { lappend leftLines [list $leftLine "" $str] lappend rightLines [list $rightLine "" $str] incr leftLine incr rightLine } elseif {$sig eq "-"} { lappend leftLines [list $leftLine "-" $str] incr leftLine } else { lappend rightLines [list $rightLine "+" $str] incr rightLine } continue } } if {$state != "none"} { displayOnePatch $top $leftLines $rightLines $leftLine $rightLine |
︙ | ︙ |
Changes to src/plugin.tcl.
︙ | ︙ | |||
26 27 28 29 30 31 32 | set dirs [list . ./plugins] lappend dirs [file join $::eskil(thisDir) .. ..] lappend dirs [file join $::eskil(thisDir) .. .. plugins] lappend dirs [file join $::eskil(thisDir) .. plugins] return $dirs } | | > | | | > > > > > > > > > > > > > > > > > > > | | > | 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 | set dirs [list . ./plugins] lappend dirs [file join $::eskil(thisDir) .. ..] lappend dirs [file join $::eskil(thisDir) .. .. plugins] lappend dirs [file join $::eskil(thisDir) .. plugins] return $dirs } # Locate plugin source and extract some info proc LocatePlugin {plugin} { set res [dict create name "" src "" opts ""] set fSrc "" set dirs [PluginSearchPath] foreach dir $dirs { set dir [file normalize $dir] set files {} lappend files [file join $dir $plugin] lappend files [file join $dir $plugin.tcl] foreach file $files { if {![file exists $file]} continue if {![file isfile $file]} continue if {![file readable $file]} continue set ch [open $file r] set data [read $ch 20] close $ch if {[string match "##Eskil Plugin*" $data]} { set fSrc $file break } } if {$fSrc ne ""} break } if {$fSrc ne ""} { dict set res name $plugin dict set res src $fSrc # Look for declarations of command line options set ch [open $fSrc r] while {[gets $ch line] >= 0} { # Only look until empty line if {[string trim $line] eq ""} break if {[regexp {^\#\# Option\s+(\S+)(.*)} $line -> name rest]} { # structure is name flag doc dict lappend res opts $name 0 [string trim $rest " :"] } if {[regexp {^\#\# Flag\s+(\S+)(.*)} $line -> name rest]} { dict lappend res opts $name 1 [string trim $rest " :"] } } close $ch } return $res } proc createPluginInterp {plugin info allow pinfoName} { upvar 1 $pinfoName pinfo set res [LocatePlugin $plugin] set src [dict get $res src] if {$src eq ""} { return "" } # Create interpreter and load source if {$allow} { |
︙ | ︙ | |||
94 95 96 97 98 99 100 | if {[$pi eval info proc FileCompare] ne ""} { dict set pinfo dir 1 } return $pi } | | | > | > > > > > > > > > | 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 | if {[$pi eval info proc FileCompare] ne ""} { dict set pinfo dir 1 } return $pi } proc printPlugin {plugin {short 0}} { set res [LocatePlugin $plugin] set src [dict get $res src] if {$src eq ""} { printPlugins return } set ch [open $src] set lines [split [read $ch] \n] foreach line $lines { set line [string trim $line] if {$short} { if {![string match "#*" $line]} { break } } puts $line } close $ch } proc listPlugins {} { set dirs [PluginSearchPath] set result {} |
︙ | ︙ | |||
170 171 172 173 174 175 176 | } } proc preparePlugin {top} { disallowEdit $top set allow [dict get $::eskil($top,pluginpinfo) allow] # Pass ::argv to plugin | > > > > | | 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 | } } proc preparePlugin {top} { disallowEdit $top set allow [dict get $::eskil($top,pluginpinfo) allow] # Pass ::argv to plugin set pArgv $::eskil(argv) if {[info exists ::eskil($top,pluginargv)]} { lappend pArgv {*}$::eskil($top,pluginargv) } $::eskil($top,plugin) eval [list set ::argv $pArgv] # Pass ::Pref to plugin $::eskil($top,plugin) eval [list array set ::Pref [array get ::Pref]] # Pass File info to plugin $::eskil($top,plugin) eval [list set ::File(left) $::eskil($top,leftFile)] $::eskil($top,plugin) eval [list set ::File(right) $::eskil($top,rightFile)] set out1 [tmpFile] |
︙ | ︙ | |||
285 286 287 288 289 290 291 292 293 294 295 296 297 298 | } if {![info exists ::eskil($top,pluginallow)]} { set ::eskil($top,pluginallow) 0 } set ::eskil($top,edit,pluginname) $::eskil($top,pluginname) set ::eskil($top,edit,plugininfo) $::eskil($top,plugininfo) set ::eskil($top,edit,pluginallow) $::eskil($top,pluginallow) set t 0 foreach {plugin info} $plugins { set descr [dict get $info descr] if {$dirdiff && ![dict get $info dir]} continue ttk::radiobutton $wt.rb$t -variable ::eskil($top,edit,pluginname) \ -value $plugin -text $plugin ttk::label $wt.l$t -text $descr -anchor w | > > > > | > > > | > > > > | | > > > > > > | | | < > > > | | > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > | > | > > > > > > > > > > > > > > > | > | 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 | } if {![info exists ::eskil($top,pluginallow)]} { set ::eskil($top,pluginallow) 0 } set ::eskil($top,edit,pluginname) $::eskil($top,pluginname) set ::eskil($top,edit,plugininfo) $::eskil($top,plugininfo) set ::eskil($top,edit,pluginallow) $::eskil($top,pluginallow) ttk::labelframe $wt.lfs -text "Select" grid columnconfigure $wt.lfs 1 -weight 1 set t 0 foreach {plugin info} $plugins { set descr [dict get $info descr] if {$dirdiff && ![dict get $info dir]} continue ttk::radiobutton $wt.rb$t -variable ::eskil($top,edit,pluginname) \ -value $plugin -text $plugin ttk::label $wt.l$t -text $descr -anchor w grid $wt.rb$t $wt.l$t -in $wt.lfs -sticky we -padx 3 -pady 3 incr t } ttk::radiobutton $wt.rb$t -variable ::eskil($top,edit,pluginname) \ -value "" -text "No Plugin" ttk::button $wt.bs -text "Show" \ -command "ShowPlugin $wt \$::eskil($top,edit,pluginname)" addBalloon $wt.bs "Show plugin source code." grid $wt.rb$t $wt.bs -in $wt.lfs -sticky we -padx 3 -pady 3 grid $wt.bs -sticky e ttk::labelframe $wt.lfgc -text "Generic Configuration" grid columnconfigure $wt.lfgc 1 -weight 1 ttk::label $wt.li -text "Info" -anchor w addBalloon $wt.li "Info passed to plugin. Plugin specific." ttk::entry $wt.ei -textvariable ::eskil($top,edit,plugininfo) grid $wt.li $wt.ei -in $wt.lfgc -sticky we -padx 3 -pady 3 ttk::checkbutton $wt.cb -text "Privilege" \ -variable ::eskil($top,edit,pluginallow) addBalloon $wt.cb "Run plugin with raised privileges" grid $wt.cb - -in $wt.lfgc -sticky w -padx 3 -pady 3 ttk::labelframe $wt.lfsc -text "Specific Configuration" set ::widgets($top,prefPluginsSpec) $wt.lfsc trace add variable ::eskil($top,edit,pluginname) write \ [list UpdateSpecificPluginConf $top] UpdateSpecificPluginConf $top ttk::frame $wt.fb -padding 3 ttk::button $wt.fb.b1 -text "Ok" \ -command [list EditPrefPluginsOk $top $wt 0] ttk::button $wt.fb.b2 -text "Apply" \ -command [list EditPrefPluginsOk $top $wt 1] ttk::button $wt.fb.b3 -text "Cancel" -command [list destroy $wt] set ::widgets($top,prefPluginsOk) $wt.fb.b1 grid $wt.fb.b1 x $wt.fb.b2 x $wt.fb.b3 -sticky we grid columnconfigure $wt.fb {0 2 4} -uniform a grid columnconfigure $wt.fb {1 3} -weight 1 grid $wt.lfs -sticky we -padx 3 -pady 3 grid $wt.lfgc -sticky we -padx 3 -pady 3 grid $wt.lfsc -sticky we -padx 3 -pady 3 grid $wt.fb -sticky we -padx 3 -pady 3 grid columnconfigure $wt 0 -weight 1 } proc UpdateSpecificPluginConf {top args} { set w $::widgets($top,prefPluginsSpec) # If the dialog is closed w might not exist if {![winfo exists $w]} return eval destroy [winfo children $w] set arg $::eskil($top,edit,pluginname) set pOpts {} if {$arg ne ""} { set res [LocatePlugin $arg] set pOpts [dict get $res opts] } # Look for declarations of command line options set n 0 set ::eskil($top,edit,opts) $pOpts foreach {name flag doc} $pOpts { ttk::label $w.l$n -text $name addBalloon $w.l$n $doc grid $w.l$n -sticky "w" -padx 3 -pady 3 if {$flag} { ttk::checkbutton $w.s$n -text "On" \ -variable ::eskil($top,edit,$name) grid $w.s$n -row $n -column 1 -sticky "w" -padx 3 -pady 3 } else { ttk::entry $w.s$n \ -textvariable ::eskil($top,edit,$name) grid $w.s$n -row $n -column 1 -sticky we -padx 3 -pady 3 } incr n } grid columnconfigure $w 1 -weight 1 if {$n == 0} { ttk::label $w.l -text "No specific configuration" grid $w.l -sticky "w" -padx 3 -pady 3 return } } proc EditPrefPluginsOk {top wt apply} { if {!$apply} { destroy $wt } set ::eskil($top,pluginname) $::eskil($top,edit,pluginname) set ::eskil($top,plugininfo) $::eskil($top,edit,plugininfo) set ::eskil($top,pluginallow) $::eskil($top,edit,pluginallow) if {$::eskil($top,pluginname) ne ""} { set pinterp [createPluginInterp $::eskil($top,pluginname) \ $::eskil($top,plugininfo) \ $::eskil($top,pluginallow) pinfo] } else { set pinterp "" set pinfo "" } set ::eskil($top,plugin) $pinterp set ::eskil($top,pluginpinfo) $pinfo set ::eskil($top,pluginargv) {} foreach {name flag doc} $::eskil($top,edit,opts) { if {$flag} { if {[info exists ::eskil($top,edit,$name)] && \ $::eskil($top,edit,$name)} { lappend ::eskil($top,pluginargv) $name } } else { if {[info exists ::eskil($top,edit,$name)] && \ $::eskil($top,edit,$name) ne ""} { lappend ::eskil($top,pluginargv) $name $::eskil($top,edit,$name) } } } } # Put Tcl code in a text widget, with some syntax highlighting proc TextViewTcl {t data} { $t tag configure comment -foreground "#b22222" foreach line [split $data \n] { if {[regexp {^\s*#} $line]} { $t insert end $line\n comment } elseif {[regexp {^(.*;\s*)(#.*)$} $line -> pre post]} { $t insert end $pre $t insert end $post\n comment } else { $t insert end $line\n } } } # Show plugin source proc ShowPlugin {parent plugin} { set res [LocatePlugin $plugin] set src [dict get $res src] if {$src eq ""} return set ch [open $src] set data [read $ch] close $ch set wt $parent.plugin if {[winfo exists $wt]} { wm deiconify $wt |
︙ | ︙ |
Changes to src/rev.tcl.
︙ | ︙ | |||
652 653 654 655 656 657 658 659 660 661 662 663 664 665 | if {[regexp {r(\d+)} $line -> rev]} { lappend revs $rev } } } return $revs } # Return revision list of a FOSSIL file proc eskil::rev::FOSSIL::GetRevList {filename} { # Keep on current branch set x [exec fossil branch list] if { ! [regexp -line {^\* (.*)$} $x -> branch]} { set branch "" | > > > > > > > > > > > > > > > > > > > > > > > > > > > > > | 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 | if {[regexp {r(\d+)} $line -> rev]} { lappend revs $rev } } } return $revs } # Return revision list of a GIT file proc eskil::rev::GIT::GetRevList {filename} { set old "" set cmd [list exec git log --first-parent --oneline -n 50] if {$filename eq ""} { # Nothing } else { set old [pwd] cd [file dirname $filename] lappend cmd [file nativename [file tail $filename]] } if {[catch {eval $cmd} res]} { # What to do here? set revs [list HEAD] } else { set lines [split $res \n] set revs {} foreach line $lines { if {[regexp {^(\w+)} $line -> rev]} { lappend revs $rev } } } if {$old ne ""} { cd $old } return $revs } # Return revision list of a FOSSIL file proc eskil::rev::FOSSIL::GetRevList {filename} { # Keep on current branch set x [exec fossil branch list] if { ! [regexp -line {^\* (.*)$} $x -> branch]} { set branch "" |
︙ | ︙ | |||
724 725 726 727 728 729 730 731 732 733 | # RCS does not support tree versions return {} } return $revs } # Figure out GIT revision from arguments proc eskil::rev::GIT::ParseRevs {filename revs} { set result "" foreach rev $revs { | > < | | | > > > | > | > > > | 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 | # RCS does not support tree versions return {} } return $revs } # Figure out GIT revision from arguments # The resulting rev should work with 'git show <rev>:filename' proc eskil::rev::GIT::ParseRevs {filename revs} { set result "" foreach rev $revs { # Special cases that shortcuts to GIT special names if {$rev eq "_" || $rev eq "0"} {set rev HEAD} if {[string is integer -strict $rev] && $rev < 0} { # A negative integer rev is a relative rev set revList [eskil::rev::GIT::GetRevList $filename] set rev [lindex $revList [- $rev]] if {$rev eq ""} { set rev [lindex $revs end] } } # Let anything else through lappend result $rev } return $result } # Figure out FOSSIL revision from arguments proc eskil::rev::FOSSIL::ParseRevs {filename revs} { set result "" |
︙ | ︙ | |||
1241 1242 1243 1244 1245 1246 1247 1248 1249 1250 1251 1252 1253 1254 | proc eskil::rev::SVN::viewLog {top filename revs} { set cmd [list exec svn log] if {[llength $revs] > 1} { lappend cmd -r [join $revs ":"] } else { lappend cmd -r HEAD:[lindex $revs 0] } lappend cmd $filename if {[catch {eval $cmd} result]} { #return } ViewLog $top $filename $result } | > > > > > > > > > > > > > > > | 1277 1278 1279 1280 1281 1282 1283 1284 1285 1286 1287 1288 1289 1290 1291 1292 1293 1294 1295 1296 1297 1298 1299 1300 1301 1302 1303 1304 1305 | proc eskil::rev::SVN::viewLog {top filename revs} { set cmd [list exec svn log] if {[llength $revs] > 1} { lappend cmd -r [join $revs ":"] } else { lappend cmd -r HEAD:[lindex $revs 0] } lappend cmd $filename if {[catch {eval $cmd} result]} { #return } ViewLog $top $filename $result } # View log between displayed versions proc eskil::rev::GIT::viewLog {top filename revs} { set cmd [list exec git log] if {[llength $revs] > 1} { lappend cmd [join $revs ".."] } else { lappend cmd [lindex $revs 0].. } lappend cmd $filename if {[catch {eval $cmd} result]} { #return } ViewLog $top $filename $result } |
︙ | ︙ |
Changes to src/startup.tcl.
︙ | ︙ | |||
377 378 379 380 381 382 383 384 385 386 387 388 389 390 | set chunk [string range $d 0 $ci-1] set d [string trim [string range $d $ci end]] } puts "$outName$chunk" set outName [format %*s $indent ""] } } } ##################################### # Option/flag handling helpers ##################################### # Validators proc optValidatePdfColor {opt arg} { | > > > > | 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 | set chunk [string range $d 0 $ci-1] set d [string trim [string range $d $ci end]] } puts "$outName$chunk" set outName [format %*s $indent ""] } } if {$::eskil(opts,src) ne ""} { puts "" printPlugin $::eskil(opts,src) 1 } } ##################################### # Option/flag handling helpers ##################################### # Validators proc optValidatePdfColor {opt arg} { |
︙ | ︙ | |||
423 424 425 426 427 428 429 | puts [join [lsort -dictionary [pdf4tcl::getPaperSizeList]] \n] exit } } proc optValidatePlugin {opt arg} { # We must start up completely to check a plugin Init | | > | < < | | > | | | < < > > > | | 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 | puts [join [lsort -dictionary [pdf4tcl::getPaperSizeList]] \n] exit } } proc optValidatePlugin {opt arg} { # We must start up completely to check a plugin Init set res [LocatePlugin $arg] set src [dict get $res src] if {$src eq ""} { puts "Bad plugin: $arg" printPlugins exit } # Look for declarations of command line options foreach {name flag doc} [dict get $res opts] { if {$flag} { addFlags $name } else { addOpt $name } docFlag $name "Plugin $arg : $doc" addSource $name $arg } } # Option database setup proc initOpts {} { set ::eskil(opts) {} set ::eskil(opts,info) {} set ::eskil(opts,src) "" set ::eskil(defoptinfo) { flag 0 given 0 multi 0 type "" validator "" filter "" sideeffect "" shortdescr "" longdescr "" source "" } } # Add a command line flag that do not take a value proc addFlags {args} { foreach name $args { dict set ::eskil(opts) $name 0 dict set ::eskil(opts,info) $name $::eskil(defoptinfo) dict set ::eskil(opts,info) $name flag 1 } } # Document a flag or option proc docFlag {name short {long {}}} { dict set ::eskil(opts,info) $name shortdescr $short dict set ::eskil(opts,info) $name longdescr $long } # Flag that affects Pref proc addPrefFlag {name elem {value 1}} { |
︙ | ︙ | |||
511 512 513 514 515 516 517 518 519 520 521 522 523 524 | proc addValidator {name cmd} { dict set ::eskil(opts,info) $name validator $cmd } # Add a filter command prefix to an Opt proc addFilter {name cmd} { dict set ::eskil(opts,info) $name filter $cmd } # Add a sideeffect to an Opt ##nagelfar syntax addSideEffect x c proc addSideEffect {name script} { dict set ::eskil(opts,info) $name sideeffect $script } # Add a command line option that takes a value and stores in local opts proc addOptsOpt {name elem {validator ""}} { | > > > > > | 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 | proc addValidator {name cmd} { dict set ::eskil(opts,info) $name validator $cmd } # Add a filter command prefix to an Opt proc addFilter {name cmd} { dict set ::eskil(opts,info) $name filter $cmd } # Add a source reference to an Opt proc addSource {name src} { set ::eskil(opts,src) $src dict set ::eskil(opts,info) $name source $src } # Add a sideeffect to an Opt ##nagelfar syntax addSideEffect x c proc addSideEffect {name script} { dict set ::eskil(opts,info) $name sideeffect $script } # Add a command line option that takes a value and stores in local opts proc addOptsOpt {name elem {validator ""}} { |
︙ | ︙ |
Changes to tests/blocks.test.
|
| < | | | 1 2 3 4 5 6 7 8 9 | #------------------------------------------------------------*- tcl -*- # Tests for comparing blocks. #---------------------------------------------------------------------- test blocks-1.1 { Change-block parsing } -body { set b1 [list "Apa 1" "Bepa 1" "Cepa 1"] set b2 [list "Apa 2" "Bepa 2" "Cepa 2"] |
︙ | ︙ |
Changes to tests/dir.test.
|
| < | < > | 1 2 3 4 5 6 7 8 9 | #------------------------------------------------------------*- tcl -*- # Tests for comparing directories. #---------------------------------------------------------------------- set ::Pref(dir,ignorekey) 0 set ::Pref(dir,comparelevel) 1 set ::eskil(.dirdiff,plugin) "" proc testCompareFiles {text1 text2 {sametime 0}} { |
︙ | ︙ |
Changes to tests/gui.test.
1 2 | #------------------------------------------------------------*- tcl -*- # Tests for GUI | < < | 1 2 3 4 5 6 7 8 9 | #------------------------------------------------------------*- tcl -*- # Tests for GUI #---------------------------------------------------------------------- lappend ::auto_path /home/peter/src/TkTest package require TkTest wm withdraw . proc XauthSecure {} { |
︙ | ︙ |
Changes to tests/patch.test.
|
| < | < > > > > > > > > | > > > > > | > | > > > | | > > > > > > > > > > > > > > > > > > | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 | #------------------------------------------------------------*- tcl -*- # Tests for patch file parsing functions #---------------------------------------------------------------------- # Overload exec during these tests set ::eskil(gurka,patchFile) "" set ::eskil(gurka,patchData) "" stub update args {} stub getFullPatch {top} { return $::testpatch } stub displayOnePatch {top leftLines rightLines leftLine rightLine} { # Line per patch lappend ::_patchfiles(pll) $leftLine lappend ::_patchfiles(prl) $rightLine # All lines foreach l $leftLines { lassign $l lline lmode lstr lappend ::_patchfiles(ll) $lline } foreach l $rightLines { lassign $l lline lmode lstr lappend ::_patchfiles(rl) $lline } } stub emptyLine {top n {highlight 1}} { incr ::_patchfiles(e) } stub insertLine {top n line text {tag {equal}} {linetag {}}} { } stub addChange {top n tag line1 n1 line2 n2} {} proc _PatchInit {} { set ::_patchfiles(e) 0 set ::_patchfiles(pll) {} set ::_patchfiles(prl) {} set ::_patchfiles(ll) {} set ::_patchfiles(rl) {} } test patch-1.1 { Xxx } -body { _PatchInit set ::testpatch [string trim { --- foo.txt 2016-07-10 21:53:36.671932638 -0700 +++ bar.txt 2016-07-10 21:53:54.739860205 -0700 @@ -1 +1,2 @@ +0 1 @@ -5 +8,9 @@ +0 1 }] displayPatch gurka concat $_patchfiles(ll) $_patchfiles(rl) } -result {1 5 1 2 8 9} test patch-1.2 { Xxx } -body { _PatchInit set ::testpatch { Index: vhdl/tb/tb_system.bhv =================================================================== --- vhdl/tb/tb_system.bhv (revision 320) +++ vhdl/tb/tb_system.bhv (working copy) |
︙ | ︙ | |||
129 130 131 132 133 134 135 | + variable TcDFHeader : out TcDFH_T); procedure TcAddrCalc(PresentAddr : in integer; AccWidth : in DynamicSize_T; } displayPatch gurka | | | 162 163 164 165 166 167 168 169 170 | + variable TcDFHeader : out TcDFH_T); procedure TcAddrCalc(PresentAddr : in integer; AccWidth : in DynamicSize_T; } displayPatch gurka set ::_patchfiles(e) } -result {6} |
Changes to tests/print.test.
|
| < | | | 1 2 3 4 5 6 7 8 9 | #------------------------------------------------------------*- tcl -*- # Tests for printing. #---------------------------------------------------------------------- test print-1.1 {Tab expansion} {FixTextBlock "a\fp\fa" 1.0} {apa} test print-1.2 {Tab expansion} {FixTextBlock "\tapa" 1.0} { apa} test print-1.3 {Tab expansion} {FixTextBlock "\tapa" 1.1} { apa} test print-1.4 {Tab expansion} {FixTextBlock "\tapa" 1.7} { apa} test print-1.5 {Tab expansion} {FixTextBlock "\tapa" 1.8} { apa} |
︙ | ︙ |
Changes to tests/procs.test.
|
| < | < > | 1 2 3 4 5 6 7 8 9 | #------------------------------------------------------------*- tcl -*- # Tests for comparing misc procedures. #---------------------------------------------------------------------- test procs-1.1 { Linit } -body { # Make sure argument ordering is same as lindex lindex [Linit x 3 4 5] 2 3 4 |
︙ | ︙ |
Changes to tests/rev.test.
|
| < | | | 1 2 3 4 5 6 7 8 9 | #------------------------------------------------------------*- tcl -*- # Tests for revision control functions #---------------------------------------------------------------------- # Overload exec during these tests stub exec {args} { set cmd [lindex $args 0] switch -- $cmd { cleartool { |
︙ | ︙ |