System.Data.SQLite

Check-in [e4d08f6098]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Update Eagle in externals to the beta 40 release.
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: e4d08f6098112d99051fd84c08e6f0671df63b87
User & Date: mistachkin 2017-09-29 16:59:36.446
Context
2017-10-04
19:52
Stop using ToString calls within the parameter binding subsystem that do not take into account the configured culture information. check-in: fb6160ee72 user: mistachkin tags: trunk
2017-09-29
16:59
Update Eagle in externals to the beta 40 release. check-in: e4d08f6098 user: mistachkin tags: trunk
2017-09-28
18:22
Update version history docs. check-in: 0cfbfac5f7 user: mistachkin tags: trunk
Changes
Unified Diff Ignore Whitespace Patch
Changes to Externals/Eagle/bin/Eagle.dll.

cannot compute difference between binary files

Changes to Externals/Eagle/bin/EagleShell.exe.

cannot compute difference between binary files

Changes to Externals/Eagle/bin/EagleShell.exe.config.
8
9
10
11
12
13
14









15
16
17
18
19
20
21
 * See the file "license.terms" for information on usage and redistribution of
 * this file, and for a DISCLAIMER OF ALL WARRANTIES.
 *
 * RCS: @(#) $Id: $
 *
-->
<configuration>









  <startup useLegacyV2RuntimeActivationPolicy="true">
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0" />

    <!--
    <supportedRuntime version="v2.0.50727" />
    <supportedRuntime version="v4.0.30319" />
    -->







>
>
>
>
>
>
>
>
>







8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
 * See the file "license.terms" for information on usage and redistribution of
 * this file, and for a DISCLAIMER OF ALL WARRANTIES.
 *
 * RCS: @(#) $Id: $
 *
-->
<configuration>
  <appSettings>
    <!--
    <add key="ArgumentCount" value="3" />
    <add key="Argument0String" value="-anyInitialize" />
    <add key="Argument1String" value="puts stdout app_settings1" />
    <add key="Argument2List" value="-anyInitialize {puts stdout app_settings2}" />
    -->
  </appSettings>

  <startup useLegacyV2RuntimeActivationPolicy="true">
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0" />

    <!--
    <supportedRuntime version="v2.0.50727" />
    <supportedRuntime version="v4.0.30319" />
    -->
Changes to Externals/Eagle/bin/EagleShell32.exe.

cannot compute difference between binary files

Changes to Externals/Eagle/bin/x64/Spilornis.dll.

cannot compute difference between binary files

Changes to Externals/Eagle/bin/x86/Spilornis.dll.

cannot compute difference between binary files

Changes to Externals/Eagle/lib/Eagle1.0/init.eagle.
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
    #
    # NOTE: Load the extra script library files that contain commonly used
    #       procedures that are shared between native Tcl and Eagle.
    #
    loadScripts [file dirname [info script]] [list \
        auxiliary.eagle database.eagle exec.eagle file1.eagle \
        file2.eagle file3.eagle info.eagle list.eagle \
        platform.eagle testlog.eagle]

    #
    # NOTE: Load the extra script library files that contain procedures that
    #       require a specific language (i.e. either native Tcl or Eagle).
    #
    if {[isEagle]} then {
      loadScripts [file dirname [info script]] [list \







|







117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
    #
    # NOTE: Load the extra script library files that contain commonly used
    #       procedures that are shared between native Tcl and Eagle.
    #
    loadScripts [file dirname [info script]] [list \
        auxiliary.eagle database.eagle exec.eagle file1.eagle \
        file2.eagle file3.eagle info.eagle list.eagle \
        pkgt.eagle platform.eagle testlog.eagle unzip.eagle]

    #
    # NOTE: Load the extra script library files that contain procedures that
    #       require a specific language (i.e. either native Tcl or Eagle).
    #
    if {[isEagle]} then {
      loadScripts [file dirname [info script]] [list \
347
348
349
350
351
352
353
354

355
356
357
358
359
360
361
          makeLogChannel readFile readSharedFile writeFile appendFile \
          appendLogFile appendSharedFile appendSharedLogFile \
          readAsciiFile writeAsciiFile readUnicodeFile \
          writeUnicodeFile getDirResultPath addToPath removeFromPath \
          execShell lshuffle ldifference filter map reduce \
          getLengthModifier debug findDirectories \
          findDirectoriesRecursive findFiles findFilesRecursive \
          exportAndImportPackageCommands] false false

    }

    ###########################################################################
    ############################## END Tcl ONLY ###############################
    ###########################################################################
  }








|
>







347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
          makeLogChannel readFile readSharedFile writeFile appendFile \
          appendLogFile appendSharedFile appendSharedLogFile \
          readAsciiFile writeAsciiFile readUnicodeFile \
          writeUnicodeFile getDirResultPath addToPath removeFromPath \
          execShell lshuffle ldifference filter map reduce \
          getLengthModifier debug findDirectories \
          findDirectoriesRecursive findFiles findFilesRecursive \
          exportAndImportPackageCommands setupUnzipVars \
          unzipMustBeInstalled extractZipArchive] false false
    }

    ###########################################################################
    ############################## END Tcl ONLY ###############################
    ###########################################################################
  }

Changes to Externals/Eagle/lib/Eagle1.0/pkgIndex.eagle.
49
50
51
52
53
54
55



56
57
58
59
60
61
62

package ifneeded Eagle.List 1.0 \
    [list sourceWithInfo [file join $dir list.eagle]]

package ifneeded Eagle.Object 1.0 \
    [list sourceWithInfo [file join $dir object.eagle]]




package ifneeded Eagle.Platform 1.0 \
    [list sourceWithInfo [file join $dir platform.eagle]]

package ifneeded Eagle.Process 1.0 \
    [list sourceWithInfo [file join $dir process.eagle]]

package ifneeded Eagle.Runtime.Option 1.0 \







>
>
>







49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65

package ifneeded Eagle.List 1.0 \
    [list sourceWithInfo [file join $dir list.eagle]]

package ifneeded Eagle.Object 1.0 \
    [list sourceWithInfo [file join $dir object.eagle]]

package ifneeded Eagle.Package.Toolset 1.0 \
    [list sourceWithInfo [file join $dir pkgt.eagle]]

package ifneeded Eagle.Platform 1.0 \
    [list sourceWithInfo [file join $dir platform.eagle]]

package ifneeded Eagle.Process 1.0 \
    [list sourceWithInfo [file join $dir process.eagle]]

package ifneeded Eagle.Runtime.Option 1.0 \
76
77
78
79
80
81
82



83
84

package ifneeded Eagle.Test.Log 1.0 \
    [list sourceWithInfo [file join $dir testlog.eagle]]

package ifneeded Eagle.Unknown.Object 1.0 \
    [list sourceWithInfo [file join $dir unkobj.eagle]]




package ifneeded Eagle.Update 1.0 \
    [list sourceWithInfo [file join $dir update.eagle]]







>
>
>


79
80
81
82
83
84
85
86
87
88
89
90

package ifneeded Eagle.Test.Log 1.0 \
    [list sourceWithInfo [file join $dir testlog.eagle]]

package ifneeded Eagle.Unknown.Object 1.0 \
    [list sourceWithInfo [file join $dir unkobj.eagle]]

package ifneeded Eagle.Unzip 1.0 \
    [list sourceWithInfo [file join $dir unzip.eagle]]

package ifneeded Eagle.Update 1.0 \
    [list sourceWithInfo [file join $dir update.eagle]]
Changes to Externals/Eagle/lib/Eagle1.0/pkgIndex.tcl.
49
50
51
52
53
54
55



56
57
58
59
60
61
62

package ifneeded Eagle.List 1.0 \
    [list source [file join $dir list.eagle]]

package ifneeded Eagle.Object 1.0 \
    [list source [file join $dir object.eagle]]




package ifneeded Eagle.Platform 1.0 \
    [list source [file join $dir platform.eagle]]

package ifneeded Eagle.Process 1.0 \
    [list source [file join $dir process.eagle]]

package ifneeded Eagle.Runtime.Option 1.0 \







>
>
>







49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65

package ifneeded Eagle.List 1.0 \
    [list source [file join $dir list.eagle]]

package ifneeded Eagle.Object 1.0 \
    [list source [file join $dir object.eagle]]

package ifneeded Eagle.Package.Toolset 1.0 \
    [list source [file join $dir pkgt.eagle]]

package ifneeded Eagle.Platform 1.0 \
    [list source [file join $dir platform.eagle]]

package ifneeded Eagle.Process 1.0 \
    [list source [file join $dir process.eagle]]

package ifneeded Eagle.Runtime.Option 1.0 \
76
77
78
79
80
81
82



83
84

package ifneeded Eagle.Test.Log 1.0 \
    [list source [file join $dir testlog.eagle]]

package ifneeded Eagle.Unknown.Object 1.0 \
    [list source [file join $dir unkobj.eagle]]




package ifneeded Eagle.Update 1.0 \
    [list source [file join $dir update.eagle]]







>
>
>


79
80
81
82
83
84
85
86
87
88
89
90

package ifneeded Eagle.Test.Log 1.0 \
    [list source [file join $dir testlog.eagle]]

package ifneeded Eagle.Unknown.Object 1.0 \
    [list source [file join $dir unkobj.eagle]]

package ifneeded Eagle.Unzip 1.0 \
    [list source [file join $dir unzip.eagle]]

package ifneeded Eagle.Update 1.0 \
    [list source [file join $dir update.eagle]]
Added Externals/Eagle/lib/Eagle1.0/pkgt.eagle.














































































































































































































































>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
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
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
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
###############################################################################
#
# pkgt.eagle --
#
# Extensible Adaptable Generalized Logic Engine (Eagle)
# Eagle Package Toolset Package File
#
# Copyright (c) 2007-2012 by Joe Mistachkin.  All rights reserved.
#
# See the file "license.terms" for information on usage and redistribution of
# this file, and for a DISCLAIMER OF ALL WARRANTIES.
#
# RCS: @(#) $Id: $
#
###############################################################################

#
# NOTE: Use our own namespace here because even though we do not directly
#       support namespaces ourselves, we do not want to pollute the global
#       namespace if this script actually ends up being evaluated in Tcl.
#
namespace eval ::Eagle {
  #
  # NOTE: This procedure sets up the default values for all configuration
  #       parameters used by this package.  If the force argument is non-zero,
  #       any existing values will be overwritten and set back to their
  #       default values.
  #
  proc setupPackageToolsetVars { force } {
    #
    # NOTE: Using the [getAuxiliaryBaseUri] procedure requires the update
    #       package.
    #
    # NOTE: The base URI used to build the URIs for the Package Client
    #       Toolset downloads.
    #
    variable baseUri; # DEFAULT: [getAuxiliaryBaseUri] -OR- https://urn.to/r

    if {$force || ![info exists baseUri]} then {
      if {[isEagle]} then {
        package require Eagle.Update
        set baseUri [getAuxiliaryBaseUri]
      } else {
        set baseUri https://urn.to/r
      }
    }

    #
    # NOTE: The URN, relative to the base URI, where the Package Client
    #       Toolset may be downloaded.
    #
    variable packageToolsetUrn; # DEFAULT: pkg_client_only

    if {$force || ![info exists packageToolsetUrn]} then {
      set packageToolsetUrn pkg_client_only
    }

    #
    # NOTE: The URI where the Package Client Toolset may be downloaded.
    #
    variable packageToolsetUri; # DEFAULT: ${baseUri}/${packageToolsetUrn}

    if {$force || ![info exists packageToolsetUri]} then {
      set packageToolsetUri {${baseUri}/${packageToolsetUrn}}
    }
  }

  #
  # NOTE: This procedure attempts to download and extract the Package Client
  #       Toolset.  The optional channel argument is the output channel where
  #       diagnostic information is sent.  The optional quiet argument should
  #       be non-zero to prevent diagnostic information from being emitted.
  #       This procedure may raise script errors.  The return value is the
  #       full path to the directory that should be added to the auto-path.
  #
  proc downloadAndExtractPackageClientToolset {
          {channel stdout} {quiet false} } {
    setupPackageToolsetVars false

    variable baseUri
    variable packageToolsetUri
    variable packageToolsetUrn

    package require Eagle.Test
    package require Eagle.Unzip

    set extractRootDirectory [getTemporaryPath]

    set directory [file join $extractRootDirectory [appendArgs \
        ea-pt-di- [pid] - [string trim [clock seconds] -]]]

    set uri [subst $packageToolsetUri]
    set fileName [getTemporaryFileName]

    if {[isEagle]} then {
      uri download $uri $fileName
    } else {
      package require Eagle.Tools.Common

      namespace import \
          ::Eagle::Tools::Common::getFileViaHttp \
          ::Eagle::Tools::Common::writeFile

      set data [getFileViaHttp $uri 20 $channel $quiet -binary true]

      writeFile $fileName $data
    }

    set extractDirectory [extractZipArchive $fileName $extractRootDirectory]
    return [file join $extractDirectory pkgr_an_d client 1.0 neutral]
  }

  #
  # NOTE: Provide the Eagle "package toolset" package to the interpreter.
  #
  package provide Eagle.Package.Toolset \
    [expr {[isEagle] ? [info engine PatchLevel] : "1.0"}]
}

Changes to Externals/Eagle/lib/Eagle1.0/test.eagle.
399
400
401
402
403
404
405

406
407
408
409
410
411
412
413
      # NOTE: Calculate how many whole seconds we need to spin for.
      #
      set seconds [expr {$milliseconds / 1000}]

      #
      # NOTE: Calculate the starting and ending values of [clock seconds].
      #

      set now [clock seconds]; set start $now; set stop [expr {$now + $seconds}]

      #
      # NOTE: Do nothing for X seconds (i.e. except call [clock seconds]).
      #
      while {$start <= $now && $now < $stop} {set now [clock seconds]}

      #







>
|







399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
      # NOTE: Calculate how many whole seconds we need to spin for.
      #
      set seconds [expr {$milliseconds / 1000}]

      #
      # NOTE: Calculate the starting and ending values of [clock seconds].
      #
      set now [clock seconds]
      set start $now; set stop [expr {$now + $seconds}]

      #
      # NOTE: Do nothing for X seconds (i.e. except call [clock seconds]).
      #
      while {$start <= $now && $now < $stop} {set now [clock seconds]}

      #
865
866
867
868
869
870
871






























872
873
874
875
876
877
878
      # NOTE: Tcl fallback, *assume* that we can use the
      #       directory where the executable is running for
      #       temporary storage.
      #
      return [file normalize [file dirname [info nameofexecutable]]]
    }
  }































  proc getFiles { directory pattern } {
    if {[isEagle]} then {
      set result [list]

      if {[file exists $directory] && [file isdirectory $directory]} then {
        foreach fileName [lsort -dictionary [file list $directory $pattern]] {







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
      # NOTE: Tcl fallback, *assume* that we can use the
      #       directory where the executable is running for
      #       temporary storage.
      #
      return [file normalize [file dirname [info nameofexecutable]]]
    }
  }

  proc getTemporaryFileName { {seconds 5} } {
    if {[isEagle]} then {
      return [file tempname]
    } else {
      set path [getTemporaryPath]

      set now [clock seconds]
      set start $now; set stop [expr {$now + $seconds}]

      while {$start <= $now && $now < $stop} {
        binary scan [binary format d* [expr {rand()}]] h* random

        set fileNameOnly [appendArgs \
            tmp [string index $random 0] [string index $random 1] \
            [string index $random end-1] [string index $random end] \
            .tmp]

        set fileName [file join $path $fileNameOnly]

        if {![file exists $fileName]} then {
          return $fileName
        }

        set now [clock seconds]
      }

      error "cannot generate temporary file name"
    }
  }

  proc getFiles { directory pattern } {
    if {[isEagle]} then {
      set result [list]

      if {[file exists $directory] && [file isdirectory $directory]} then {
        foreach fileName [lsort -dictionary [file list $directory $pattern]] {
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
            trimleft [pid] -] [string trimleft [info tid] -] [string \
            trimleft [clock now] -] [string trimleft [clock clicks] -] \
            [string trimleft [expr $expr] -]]]
      }
    } else {
      #
      # NOTE: Generate a random number using [expr] and then convert it
      #       to hexadecimal.
      #
      binary scan [binary format d* [expr {rand()}]] w* random

      #
      # NOTE: Convert the host name to a hexadecimal string and include
      #       it in the result in an attempt to make it more unique in
      #       both time and space.







|







983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
            trimleft [pid] -] [string trimleft [info tid] -] [string \
            trimleft [clock now] -] [string trimleft [clock clicks] -] \
            [string trimleft [expr $expr] -]]]
      }
    } else {
      #
      # NOTE: Generate a random number using [expr] and then convert it
      #       to a 64-bit integer.
      #
      binary scan [binary format d* [expr {rand()}]] w* random

      #
      # NOTE: Convert the host name to a hexadecimal string and include
      #       it in the result in an attempt to make it more unique in
      #       both time and space.
2378
2379
2380
2381
2382
2383
2384











2385
2386
2387
2388
2389
2390
2391
                }
              } else {
                if {$::tcltest::numTests(Failed) == 0} then {
                  incr ::tcltest::numTests(Total)
                  incr ::tcltest::numTests(Failed)
                }
              }











            }
          }

          #
          # NOTE: We evaluated another test file.
          #
          incr count







>
>
>
>
>
>
>
>
>
>
>







2409
2410
2411
2412
2413
2414
2415
2416
2417
2418
2419
2420
2421
2422
2423
2424
2425
2426
2427
2428
2429
2430
2431
2432
2433
                }
              } else {
                if {$::tcltest::numTests(Failed) == 0} then {
                  incr ::tcltest::numTests(Total)
                  incr ::tcltest::numTests(Failed)
                }
              }
            } else {
              #
              # NOTE: At this point, we know the test file had an error that
              #       probably caused it to skip a bunch of tests -AND- the
              #       option to stop-testing-on-error is not enabled.  That
              #       being said, we must not simply ignore the error.  The
              #       overall results of the test suite run must now reflect
              #       the failure.  Set a special variable for the epilogue
              #       to pick up on (later).
              #
              lappend ::test_suite_errors $error
            }
          }

          #
          # NOTE: We evaluated another test file.
          #
          incr count
Added Externals/Eagle/lib/Eagle1.0/unzip.eagle.




























































































































































































































































































































































































































































































>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
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
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
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
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
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
###############################################################################
#
# unzip.eagle --
#
# Extensible Adaptable Generalized Logic Engine (Eagle)
# Eagle Unzip Package File
#
# Copyright (c) 2007-2012 by Joe Mistachkin.  All rights reserved.
#
# See the file "license.terms" for information on usage and redistribution of
# this file, and for a DISCLAIMER OF ALL WARRANTIES.
#
# RCS: @(#) $Id: $
#
###############################################################################

#
# NOTE: Use our own namespace here because even though we do not directly
#       support namespaces ourselves, we do not want to pollute the global
#       namespace if this script actually ends up being evaluated in Tcl.
#
namespace eval ::Eagle {
  #
  # NOTE: This procedure sets up the default values for all configuration
  #       parameters used by this package.  If the force argument is non-zero,
  #       any existing values will be overwritten and set back to their
  #       default values.
  #
  proc setupUnzipVars { force } {
    #
    # NOTE: Using the [getAuxiliaryBaseUri] procedure requires the update
    #       package.
    #
    # NOTE: The base URI used to build the URIs for the unzip command line
    #       tool downloads.
    #
    variable baseUri; # DEFAULT: [getAuxiliaryBaseUri] -OR- https://urn.to/r

    if {$force || ![info exists baseUri]} then {
      if {[isEagle]} then {
        package require Eagle.Update
        set baseUri [getAuxiliaryBaseUri]
      } else {
        set baseUri https://urn.to/r
      }
    }

    #
    # NOTE: The URN, relative to the base URI, where the unzip command
    #       line tool may be downloaded.
    #
    variable unzipUrn; # DEFAULT: unzip

    if {$force || ![info exists unzipUrn]} then {
      set unzipUrn unzip
    }

    #
    # NOTE: The URI where the unzip command line tool may be downloaded.
    #
    variable unzipUri; # DEFAULT: ${baseUri}/${unzipUrn}

    if {$force || ![info exists unzipUri]} then {
      set unzipUri {${baseUri}/${unzipUrn}}
    }

    #
    # NOTE: The command to use when attempting to verify that UnZip is
    #       installed locally.
    #
    variable unzipInstalledCommand; # DEFAULT: unzip

    if {$force || ![info exists unzipInstalledCommand]} then {
      set unzipInstalledCommand unzip
    }

    #
    # NOTE: The regular expression pattern used when attempting to verify
    #       that UnZip is installed locally.
    #
    variable unzipInstalledPattern; # DEFAULT: ^UnZip ..., by Info-ZIP\.

    if {$force || ![info exists unzipInstalledPattern]} then {
      set unzipInstalledPattern \
          {^UnZip \d+\.\d+ of \d{1,2} \w+ \d{4}, by Info-ZIP\.}
    }

    #
    # NOTE: The command to use when attempting to unzip an archive.
    #
    variable unzipExtractCommand; # DEFAULT: unzip ...

    if {$force || ![info exists unzipExtractCommand]} then {
      set unzipExtractCommand {unzip {${fileName}} -d {${directory}}}
    }
  }

  #
  # NOTE: This procedure attempts to verify that an implementation of the
  #       unzip command line tool is installed locally.  There are no
  #       arguments.  Script errors are raised if any problems are found.
  #       The return value is undefined.
  #
  proc unzipMustBeInstalled {} {
    variable unzipInstalledCommand
    variable unzipInstalledPattern

    set message {
      Cannot use UnZip: it does not appear to be installed.

      UnZip may be downloaded from "https://www.info-zip.org/"
      and then installed by copying the (single) UnZip binary to
      a directory that lies somewhere along the executable search
      path.

      Alternatively, it may be possible to install UnZip via the
      package management subsystem included with your operating
      system.
    }

    if {[isEagle]} then {
      if {[catch {
        eval exec -success Success $unzipInstalledCommand
      } result]} then {
        error $message
      }
    } else {
      if {[catch {
        eval exec $unzipInstalledCommand
      } result]} then {
        error $message
      }
    }

    if {![info exists result] || \
        ![regexp -- $unzipInstalledPattern $result]} then {
      error "cannot use UnZip: unknown or unsupported version"
    }

    return ""
  }

  #
  # NOTE: This procedure attempts to use the unzip command line tool in order
  #       to extract a ZIP archive file.  The archiveFileName argument is the
  #       ZIP archive file to extract.  The extractRootDirectory argument is
  #       the location of a directory that should contain a new temporary
  #       extraction directory.  The actual temporary extraction directory is
  #       returned.
  #
  proc extractZipArchive { archiveFileName extractRootDirectory } {
    setupUnzipVars false

    variable baseUri
    variable unzipExtractCommand
    variable unzipUri
    variable unzipUrn
    variable unzipVersionCommand

    set fileName [file nativename $archiveFileName]

    set extractDirectory [file join $extractRootDirectory \
        [appendArgs ea-uz-xa- [pid] - [string trim [clock seconds] -]]]

    set directory [file nativename $extractDirectory]

    if {[isEagle]} then {
      #
      # HACK: On Windows only, when the unzip command line tool does
      #       not appear to be installed, attempt to download it to a
      #       temporary directory and use it from there.  In theory,
      #       if this procedure is called multiple times, this should
      #       only be necessary the first time.
      #
      if {[isWindows] && [catch {unzipMustBeInstalled}]} then {
        set uri [subst $unzipUri]
        set exeFileName [file tempname]

        uri download $uri $exeFileName

        #
        # NOTE: *SECURITY* The downloaded unzip command line tool must
        #       be signed; otherwise, it will be deleted and a script
        #       error will be raised.
        #
        if {[catch {library certificate $exeFileName}]} then {
          catch {file delete $exeFileName}
          error "cannot use UnZip: downloaded file was not properly signed"
        }

        #
        # NOTE: Create a brand new temporary directory, underneath the
        #       extraction root directory, that will be added to the
        #       executable search path and move the downloaded file to
        #       it.
        #
        set exeDirectory [file join $extractRootDirectory \
            [appendArgs ea-uz-xt- [pid] - [string trim [clock seconds] -]]]

        file mkdir $exeDirectory
        file copy $exeFileName [file join $exeDirectory unzip.exe]
        catch {file delete $exeFileName}

        addToPath $exeDirectory
      }

      unzipMustBeInstalled

      set fileName [appendArgs \" $fileName \"]
      set directory [appendArgs \" $directory \"]

      if {[catch {
        eval exec -success Success [subst $unzipExtractCommand]
      } error]} then {
        error [appendArgs \
            "could not extract archive \"" $fileName "\": " $error]
      }
    } else {
      unzipMustBeInstalled

      if {[catch {
        eval exec [subst $unzipExtractCommand]
      } error]} then {
        error [appendArgs \
            "could not extract archive \"" $fileName "\": " $error]
      }
    }

    return $extractDirectory
  }

  #
  # NOTE: Provide the Eagle "unzip" package to the interpreter.
  #
  package provide Eagle.Unzip \
    [expr {[isEagle] ? [info engine PatchLevel] : "1.0"}]
}

Changes to Externals/Eagle/lib/Eagle1.0/update.eagle.
374
375
376
377
378
379
380























381
382
383
384
385
386
387
  proc getDownloadBaseUri {} {
    #
    # NOTE: Just return the current base URI for downloads.
    #
    return [info engine DownloadBaseUri]; # NOTE: Current.
  }
























  #
  # NOTE: This procedure is used to check for new versions -OR- new update
  #       scripts for the runtime when a user executes the interactive
  #       "#check" command.  To disable this functionality, simply redefine
  #       this procedure to do nothing.
  #
  proc checkForUpdate {







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







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
  proc getDownloadBaseUri {} {
    #
    # NOTE: Just return the current base URI for downloads.
    #
    return [info engine DownloadBaseUri]; # NOTE: Current.
  }

  #
  # NOTE: This procedure returns the base URI that should be used to download
  #       available scripts, if a specific base URI is not specified via the
  #       manifest of available scripts.
  #
  proc getScriptBaseUri {} {
    #
    # NOTE: Just return the current base URI for scripts.
    #
    return [info engine ScriptBaseUri]; # NOTE: Current.
  }

  #
  # NOTE: This procedure returns the base URI that should be used to download
  #       auxiliary data.
  #
  proc getAuxiliaryBaseUri {} {
    #
    # NOTE: Just return the current base URI for auxiliary data.
    #
    return [info engine AuxiliaryBaseUri]; # NOTE: Current.
  }

  #
  # NOTE: This procedure is used to check for new versions -OR- new update
  #       scripts for the runtime when a user executes the interactive
  #       "#check" command.  To disable this functionality, simply redefine
  #       this procedure to do nothing.
  #
  proc checkForUpdate {
607
608
609
610
611
612
613
614



615









616
617
618
619
620
621
622
                ($checkScript && $match)} then {
              #
              # NOTE: Grab the base URI field (i.e. it may be a mirror
              #       site).
              #
              set baseUri [lindex $fields 6]

              if {$checkBuild && [string length $baseUri] == 0} then {



                set baseUri [getDownloadBaseUri]; # primary site.









              }

              #
              # NOTE: Grab the notes field (which may be empty).
              #
              set notes [lindex $fields 10]








|
>
>
>
|
>
>
>
>
>
>
>
>
>







630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
                ($checkScript && $match)} then {
              #
              # NOTE: Grab the base URI field (i.e. it may be a mirror
              #       site).
              #
              set baseUri [lindex $fields 6]

              if {$checkBuild} then {
                if {[string length $baseUri] > 0} then {
                  set buildUri $baseUri
                } else {
                  set buildUri [getDownloadBaseUri]; # primary site.
                }
              }

              if {$checkScript} then {
                if {[string length $baseUri] > 0} then {
                  set scriptUri $baseUri
                } else {
                  set scriptUri [getScriptBaseUri]; # primary site.
                }
              }

              #
              # NOTE: Grab the notes field (which may be empty).
              #
              set notes [lindex $fields 10]

667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
                      # NOTE: Ok, run the updater now and then exit.
                      #
                      runUpdateAndExit $automatic
                    }
                  }
                }

                return [list $text [list $baseUri $patchLevel] [list $notes]]
              }

              #
              # NOTE: The script patch level from the line matches the
              #       current engine patch level exactly, this script
              #       should be evaluated if it can be authenticated.
              #







|







702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
                      # NOTE: Ok, run the updater now and then exit.
                      #
                      runUpdateAndExit $automatic
                    }
                  }
                }

                return [list $text [list $buildUri $patchLevel] [list $notes]]
              }

              #
              # NOTE: The script patch level from the line matches the
              #       current engine patch level exactly, this script
              #       should be evaluated if it can be authenticated.
              #
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
                }

                #
                # NOTE: Next, verify the script has a valid base URI.
                #       For update scripts, this must be the location
                #       where the update script data can be downloaded.
                #
                if {[string length $baseUri] == 0} then {
                  if {!$quiet} then {
                    tqputs $channel [appendArgs \
                        "---- invalid baseUri value for update script " \
                        "line: " $line \"\n]
                  }
                  incr scriptCount(invalid); continue
                }







|







727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
                }

                #
                # NOTE: Next, verify the script has a valid base URI.
                #       For update scripts, this must be the location
                #       where the update script data can be downloaded.
                #
                if {[string length $scriptUri] == 0} then {
                  if {!$quiet} then {
                    tqputs $channel [appendArgs \
                        "---- invalid baseUri value for update script " \
                        "line: " $line \"\n]
                  }
                  incr scriptCount(invalid); continue
                }
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
785

                #
                # NOTE: Next, show the extra information associated with
                #       this update script, if any.
                #
                if {!$quiet} then {
                  tqputs $channel [appendArgs \
                      "---- fetching update script from \"" $baseUri \
                      "\" (" $dateTime ") with notes:\n"]

                  set trimNotes [string trim $notes]

                  tqputs $channel [appendArgs \
                      [expr {[string length $trimNotes] > 0 ? $trimNotes : \
                      "<none>"}] "\n---- end of update script notes\n"]
                }

                #
                # NOTE: Next, attempt to fetch the update script data.
                #
                set code [catch {getUpdateScriptData $baseUri} result]

                if {$code == 0} then {
                  #
                  # NOTE: Success, set the script data from the result.
                  #
                  set scriptData $result
                } else {







|












|







793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820

                #
                # NOTE: Next, show the extra information associated with
                #       this update script, if any.
                #
                if {!$quiet} then {
                  tqputs $channel [appendArgs \
                      "---- fetching update script from \"" $scriptUri \
                      "\" (" $dateTime ") with notes:\n"]

                  set trimNotes [string trim $notes]

                  tqputs $channel [appendArgs \
                      [expr {[string length $trimNotes] > 0 ? $trimNotes : \
                      "<none>"}] "\n---- end of update script notes\n"]
                }

                #
                # NOTE: Next, attempt to fetch the update script data.
                #
                set code [catch {getUpdateScriptData $scriptUri} result]

                if {$code == 0} then {
                  #
                  # NOTE: Success, set the script data from the result.
                  #
                  set scriptData $result
                } else {
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866

                #
                # NOTE: Finally, everything looks good.  Therefore, just
                #       evaluate the update script and print the result.
                #
                if {!$quiet} then {
                  tqputs $channel [appendArgs \
                      "---- evaluating update script from \"" $baseUri \
                      \"...\n]
                }

                #
                # NOTE: Reset the variables that will be used to contain
                #       the result of the update script.
                #
                set code 0; set result ""

                #
                # NOTE: Manually override file name to be returned by
                #       [info script] to refer back to the originally
                #       read script base URI.
                #
                set pushed false

                if {[llength [info commands object]] > 0} then {
                  object invoke -flags +NonPublic Interpreter.GetActive \
                      PushScriptLocation $baseUri true

                  set pushed true
                }

                try {
                  #
                  # NOTE: Evaluate the update script in the context of







|


















|







868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901

                #
                # NOTE: Finally, everything looks good.  Therefore, just
                #       evaluate the update script and print the result.
                #
                if {!$quiet} then {
                  tqputs $channel [appendArgs \
                      "---- evaluating update script from \"" $scriptUri \
                      \"...\n]
                }

                #
                # NOTE: Reset the variables that will be used to contain
                #       the result of the update script.
                #
                set code 0; set result ""

                #
                # NOTE: Manually override file name to be returned by
                #       [info script] to refer back to the originally
                #       read script base URI.
                #
                set pushed false

                if {[llength [info commands object]] > 0} then {
                  object invoke -flags +NonPublic Interpreter.GetActive \
                      PushScriptLocation $scriptUri true

                  set pushed true
                }

                try {
                  #
                  # NOTE: Evaluate the update script in the context of
Changes to Externals/Eagle/lib/Test1.0/constraints.eagle.
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
#       support namespaces ourselves, we do not want to pollute the global
#       namespace if this script actually ends up being evaluated in Tcl.
#
namespace eval ::Eagle {
  proc getKnownBuildTypes {} {
    return [list \
        NetFx20 NetFx35 NetFx40 NetFx45 NetFx451 NetFx452 \
        NetFx46 NetFx461 NetFx462 Bare LeanAndMean Database \
        MonoOnUnix Development]
  }

  proc getKnownCompileOptions {} {
    return [list \
        APPDOMAINS APPROVED_VERBS ARGUMENT_CACHE ARM ARM64 ASSEMBLY_RELEASE \
        ASSEMBLY_STRONG_NAME_TAG ASSEMBLY_TAG ASSEMBLY_TEXT ASSEMBLY_URI \
        BREAK_ON_EXITING BREAKPOINTS CACHE_ARGUMENT_TOSTRING \
        CACHE_ARGUMENTLIST_TOSTRING CACHE_DICTIONARY CACHE_RESULT_TOSTRING \
        CACHE_STATISTICS CACHE_STRINGLIST_TOSTRING CALLBACK_QUEUE CAS_POLICY \
        CERTIFICATE_PLUGIN CERTIFICATE_POLICY CERTIFICATE_RENEWAL \
        CODE_ANALYSIS COM_TYPE_CACHE CONSOLE DAEMON DATA DEAD_CODE DEBUG \
        DEBUGGER DEBUGGER_ARGUMENTS DEBUGGER_ENGINE DEBUGGER_EXECUTE \
        DEBUGGER_EXPRESSION DEBUGGER_VARIABLE DEBUG_TRACE DEBUG_WRITE DRAWING \
        DYNAMIC EAGLE EMBEDDED_LIBRARY EMBED_CERTIFICATE EXECUTE_CACHE \
        EXPRESSION_FLAGS FAST_ERRORCODE FAST_ERRORINFO FOR_TEST_USE_ONLY \
        HAVE_SIZEOF HISTORY IA64 INTERACTIVE_COMMANDS INTERNALS_VISIBLE_TO \
        ISOLATED_INTERPRETERS ISOLATED_PLUGINS LIBRARY LICENSING \
        LICENSE_MANAGER LIMITED_EDITION LIST_CACHE MONO MONO_BUILD MONO_HACKS \
        MONO_LEGACY NATIVE NATIVE_PACKAGE NATIVE_THREAD_ID NATIVE_UTILITY \
        NATIVE_UTILITY_BSTR NETWORK NET_20 NET_20_FAST_ENUM NET_20_ONLY \
        NET_20_SP1 NET_20_SP2 NET_30 NET_35 NET_40 NET_45 NET_451 NET_452 \
        NET_46 NET_461 NET_462 NON_WORKING_CODE NOTIFY NOTIFY_ACTIVE \
        NOTIFY_ARGUMENTS NOTIFY_EXCEPTION NOTIFY_EXECUTE NOTIFY_EXPRESSION \
        NOTIFY_GLOBAL NOTIFY_OBJECT OBSOLETE OBFUSCATION OFFICIAL PARSE_CACHE \
        PATCHLEVEL PLUGIN_COMMANDS POLICY_TRACE PREVIOUS_RESULT RANDOMIZE_ID \
        REMOTING SAMPLE SECURITY SERIALIZATION SHARED_ID_POOL SHELL SOURCE_ID \
        SOURCE_TIMESTAMP STATIC TCL TCL_KITS TCL_THREADED TCL_THREADS \
        TCL_UNICODE TCL_WRAPPER TEST TEST_PLUGIN THREADING THROW_ON_DISPOSED \

        TRACE TYPE_CACHE UNIX USE_APPDOMAIN_FOR_ID USE_NAMESPACES VERBOSE WEB \
        WINDOWS WINFORMS WIX_30 WIX_35 WIX_36 WIX_37 WIX_38 WIX_39 WIX_310 \
        X64 X86 XML]
  }

  proc getKnownMonoVersions { {force false} } {
    #
    # NOTE: This job of this procedure is to return the list of "known"
    #       versions of Mono supported by the test suite infrastructure.
    #







|
|













|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
>
|
|
<







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
#       support namespaces ourselves, we do not want to pollute the global
#       namespace if this script actually ends up being evaluated in Tcl.
#
namespace eval ::Eagle {
  proc getKnownBuildTypes {} {
    return [list \
        NetFx20 NetFx35 NetFx40 NetFx45 NetFx451 NetFx452 \
        NetFx46 NetFx461 NetFx462 NetFx47 Bare LeanAndMean \
        Database MonoOnUnix Development]
  }

  proc getKnownCompileOptions {} {
    return [list \
        APPDOMAINS APPROVED_VERBS ARGUMENT_CACHE ARM ARM64 ASSEMBLY_RELEASE \
        ASSEMBLY_STRONG_NAME_TAG ASSEMBLY_TAG ASSEMBLY_TEXT ASSEMBLY_URI \
        BREAK_ON_EXITING BREAKPOINTS CACHE_ARGUMENT_TOSTRING \
        CACHE_ARGUMENTLIST_TOSTRING CACHE_DICTIONARY CACHE_RESULT_TOSTRING \
        CACHE_STATISTICS CACHE_STRINGLIST_TOSTRING CALLBACK_QUEUE CAS_POLICY \
        CERTIFICATE_PLUGIN CERTIFICATE_POLICY CERTIFICATE_RENEWAL \
        CODE_ANALYSIS COM_TYPE_CACHE CONSOLE DAEMON DATA DEAD_CODE DEBUG \
        DEBUGGER DEBUGGER_ARGUMENTS DEBUGGER_ENGINE DEBUGGER_EXECUTE \
        DEBUGGER_EXPRESSION DEBUGGER_VARIABLE DEBUG_TRACE DEBUG_WRITE DRAWING \
        DYNAMIC EAGLE EMBEDDED_LIBRARY EMBED_CERTIFICATES ENTERPRISE_LOCKDOWN \
        EXECUTE_CACHE EXPRESSION_FLAGS FAST_ERRORCODE FAST_ERRORINFO \
        FOR_TEST_USE_ONLY HAVE_SIZEOF HISTORY IA64 INTERACTIVE_COMMANDS \
        INTERNALS_VISIBLE_TO ISOLATED_INTERPRETERS ISOLATED_PLUGINS LIBRARY \
        LICENSING LICENSE_MANAGER LIMITED_EDITION LIST_CACHE MONO MONO_BUILD \
        MONO_HACKS MONO_LEGACY NATIVE NATIVE_PACKAGE NATIVE_THREAD_ID \
        NATIVE_UTILITY NATIVE_UTILITY_BSTR NETWORK NET_20 NET_20_FAST_ENUM \
        NET_20_ONLY NET_20_SP1 NET_20_SP2 NET_30 NET_35 NET_40 NET_45 NET_451 \
        NET_452 NET_46 NET_461 NET_462 NET_47 NON_WORKING_CODE NOTIFY \
        NOTIFY_ACTIVE NOTIFY_ARGUMENTS NOTIFY_EXCEPTION NOTIFY_EXECUTE \
        NOTIFY_EXPRESSION NOTIFY_GLOBAL NOTIFY_OBJECT OBSOLETE OBFUSCATION \
        OFFICIAL PARSE_CACHE PATCHLEVEL PLUGIN_COMMANDS POLICY_TRACE \
        PREVIOUS_RESULT RANDOMIZE_ID REMOTING SAMPLE SECURITY SERIALIZATION \
        SHARED_ID_POOL SHELL SOURCE_ID SOURCE_TIMESTAMP STATIC TCL TCL_KITS \
        TCL_THREADED TCL_THREADS TCL_UNICODE TCL_WRAPPER TEST TEST_PLUGIN \
        THREADING THROW_ON_DISPOSED TRACE TYPE_CACHE UNIX \
        USE_APPDOMAIN_FOR_ID USE_NAMESPACES VERBOSE WEB WINDOWS WINFORMS \
        WIX_30 WIX_35 WIX_36 WIX_37 WIX_38 WIX_39 WIX_310 X64 X86 XML]

  }

  proc getKnownMonoVersions { {force false} } {
    #
    # NOTE: This job of this procedure is to return the list of "known"
    #       versions of Mono supported by the test suite infrastructure.
    #
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
    #       the Mono runtime is released.
    #
    if {$force || ![info exists ::no(monoVersions)]} then {
      return [list \
          [list 2 0] [list 2 2] [list 2 4] [list 2 6] [list 2 8] [list 2 10] \
          [list 2 11] [list 3 0] [list 3 1] [list 3 2] [list 3 4] [list 3 6] \
          [list 3 8] [list 3 10] [list 3 12] [list 4 0] [list 4 2] [list 4 4] \
          [list 4 6] [list 4 8] [list 5 0]]
    } else {
      return [list]
    }
  }

  proc addKnownMonoConstraints { generic } {
    #







|







74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
    #       the Mono runtime is released.
    #
    if {$force || ![info exists ::no(monoVersions)]} then {
      return [list \
          [list 2 0] [list 2 2] [list 2 4] [list 2 6] [list 2 8] [list 2 10] \
          [list 2 11] [list 3 0] [list 3 1] [list 3 2] [list 3 4] [list 3 6] \
          [list 3 8] [list 3 10] [list 3 12] [list 4 0] [list 4 2] [list 4 4] \
          [list 4 6] [list 4 8] [list 5 0] [list 5 2] [list 5 4]]
    } else {
      return [list]
    }
  }

  proc addKnownMonoConstraints { generic } {
    #
112
113
114
115
116
117
118































































119
120
121
122
123
124
125
      set constraints [list monoToDo monoBug monoCrash]

      foreach constraint $constraints {
        addConstraint $constraint
      }
    }
  }
































































  #
  # NOTE: This procedure was adapted from the one listed on the Tcl Wiki page
  #       at "https://wiki.tcl.tk/43".  It is only intended to be used on very
  #       small lists because of its heavy use of recursion and complexity on
  #       the order of O(N!).
  #







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







112
113
114
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
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
      set constraints [list monoToDo monoBug monoCrash]

      foreach constraint $constraints {
        addConstraint $constraint
      }
    }
  }

  proc getKnownTclVersions { {force false} } {
    #
    # NOTE: This job of this procedure is to return the list of "known"
    #       versions of Tcl/Tk supported by the test suite infrastructure.
    #
    if {$force || ![info exists ::no(tclVersions)]} then {
      return [list [list 8 4] [list 8 5] [list 8 6] [list 8 7]]
    } else {
      return [list]
    }
  }

  proc filterKnownVersions {
          versions {minimumVersion ""} {maximumVersion ""} } {
    if {[string length $minimumVersion] > 0} then {
      set dotMinimumVersion [getDottedVersion $minimumVersion]
    } else {
      set dotMinimumVersion ""
    }

    if {[string length $maximumVersion] > 0} then {
      set dotMaximumVersion [getDottedVersion $maximumVersion]
    } else {
      set dotMaximumVersion ""
    }

    set result [list]

    foreach version $versions {
      set dotVersion [getDottedVersion $version]

      if {[string length $dotMinimumVersion] > 0 && \
          $dotVersion < $dotMinimumVersion} then {
        continue
      }

      if {[string length $dotMaximumVersion] > 0 && \
          $dotVersion > $dotMaximumVersion} then {
        continue
      }

      lappend result $version
    }

    return $result
  }

  proc getDottedVersion { version } {
    return [join $version .]
  }

  proc getDotlessVersion { version } {
    if {[string first . $version] != -1} then {
      return [string map [list . ""] $version]
    } else {
      return [join $version ""]
    }
  }

  proc getMajorMinorVersion { version } {
    return [join [lrange [split $version .] 0 1] .]
  }

  #
  # NOTE: This procedure was adapted from the one listed on the Tcl Wiki page
  #       at "https://wiki.tcl.tk/43".  It is only intended to be used on very
  #       small lists because of its heavy use of recursion and complexity on
  #       the order of O(N!).
  #
161
162
163
164
165
166
167






168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187

188
189
190
191
192
193
194
    #       return true.
    #
    return [expr {
      [catch {interp readylimit {}} readylimit] || $readylimit == 0
    }]
  }







  proc canExecComSpec {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(comSpec)]} then {
      return false
    }

    if {[info exists ::no(canExecComSpec)]} then {
      return false
    }

    return true
  }

  #
  # NOTE: This procedure should return non-zero if the "whoami" command may
  #       be executed by the test suite infrastructure outside the context
  #       of any specific tests.

  #
  proc canExecWhoAmI {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(whoami)]} then {







>
>
>
>
>
>



















|
>







224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
    #       return true.
    #
    return [expr {
      [catch {interp readylimit {}} readylimit] || $readylimit == 0
    }]
  }

  #
  # NOTE: This procedure should return non-zero if the operating system
  #       shell may be executed by the test suite infrastructure outside
  #       the context of any specific tests.  The specific tests themselves
  #       must make use of their own constraints to prevent its execution.
  #
  proc canExecComSpec {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(comSpec)]} then {
      return false
    }

    if {[info exists ::no(canExecComSpec)]} then {
      return false
    }

    return true
  }

  #
  # NOTE: This procedure should return non-zero if the "whoami" command may
  #       be executed by the test suite infrastructure outside the context
  #       of any specific tests.  The specific tests themselves must make
  #       use of their own constraints to prevent its execution.
  #
  proc canExecWhoAmI {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(whoami)]} then {
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
    return true
  }

  #
  # NOTE: This procedure should return non-zero if the native Tcl shell may
  #       be executed by the test suite infrastructure outside the context
  #       of any specific tests.  The specific tests themselves must make
  #       use of their own constraints to prevent execution of the native
  #       Tcl shell.
  #
  proc canExecTclShell {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(tcl)]} then {







|
<







272
273
274
275
276
277
278
279

280
281
282
283
284
285
286
    return true
  }

  #
  # NOTE: This procedure should return non-zero if the native Tcl shell may
  #       be executed by the test suite infrastructure outside the context
  #       of any specific tests.  The specific tests themselves must make
  #       use of their own constraints to prevent its execution.

  #
  proc canExecTclShell {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(tcl)]} then {
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245






















246
247
248
249
250
251
252
    return true
  }

  #
  # NOTE: This procedure should return non-zero if Fossil may be executed by
  #       the test suite infrastructure outside the context of any specific
  #       tests.  The specific tests themselves must make use of their own
  #       constraints to prevent execution of Fossil.
  #
  proc canExecFossil {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(fossil)]} then {
      return false
    }

    if {[info exists ::no(canExecFossil)]} then {
      return false
    }























    return true
  }

  #
  # NOTE: This procedure should return non-zero if the test suite should be
  #       considered to be running on Mono.







|













>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
    return true
  }

  #
  # NOTE: This procedure should return non-zero if Fossil may be executed by
  #       the test suite infrastructure outside the context of any specific
  #       tests.  The specific tests themselves must make use of their own
  #       constraints to prevent its execution.
  #
  proc canExecFossil {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(fossil)]} then {
      return false
    }

    if {[info exists ::no(canExecFossil)]} then {
      return false
    }

    return true
  }

  #
  # NOTE: This procedure should return non-zero if the "vswhere" tool may be
  #       executed by the test suite infrastructure outside the context of
  #       any specific tests.  The specific tests themselves must make use
  #       of their own constraints to prevent its execution.
  #
  proc canExecVsWhere {} {
    if {[info exists ::no(exec)]} then {
      return false
    }

    if {[info exists ::no(vswhere)]} then {
      return false
    }

    if {[info exists ::no(canExecVsWhere)]} then {
      return false
    }

    return true
  }

  #
  # NOTE: This procedure should return non-zero if the test suite should be
  #       considered to be running on Mono.
401
402
403
404
405
406
407
408
409
410
411

412
413
414
415
416
417
418
      # TODO: If additional test suite files are added within the base
      #       package path, add them here as well.
      #
      foreach fileNameOnly [list \
          auxiliary.eagle compat.eagle csharp.eagle database.eagle \
          embed.eagle exec.eagle file1.eagle file2.eagle \
          file3.eagle info.eagle init.eagle list.eagle \
          object.eagle pkgIndex.eagle pkgIndex.tcl platform.eagle \
          process.eagle runopt.eagle safe.eagle shell.eagle \
          shim.eagle test.eagle testlog.eagle unkobj.eagle \
          update.eagle vendor.eagle word.tcl] {

        #
        # NOTE: First, check if the file resides in the Eagle-specific
        #       package sub-directory.  Failing that, fallback to using
        #       the base package path itself.
        #
        set fileName [file join \
            $::test_package_path Eagle1.0 $fileNameOnly]







|
|
|
|
>







492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
      # TODO: If additional test suite files are added within the base
      #       package path, add them here as well.
      #
      foreach fileNameOnly [list \
          auxiliary.eagle compat.eagle csharp.eagle database.eagle \
          embed.eagle exec.eagle file1.eagle file2.eagle \
          file3.eagle info.eagle init.eagle list.eagle \
          object.eagle pkgIndex.eagle pkgIndex.tcl pkgt.eagle \
          platform.eagle process.eagle runopt.eagle safe.eagle \
          shell.eagle shim.eagle test.eagle testlog.eagle \
          unkobj.eagle unzip.eagle update.eagle vendor.eagle \
          word.tcl] {
        #
        # NOTE: First, check if the file resides in the Eagle-specific
        #       package sub-directory.  Failing that, fallback to using
        #       the base package path itself.
        #
        set fileName [file join \
            $::test_package_path Eagle1.0 $fileNameOnly]
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
        #
        if {[file exists $fileName]} then {
          lappend fileNames $fileName
        }
      }

      #
      # TODO: If additional test suite files are added within the base
      #       package path, add them here as well.
      #
      foreach fileNameOnly [list \
          all.eagle constraints.eagle epilogue.eagle pkgIndex.eagle \
          pkgIndex.tcl prologue.eagle] {
        #
        # NOTE: First, check if the file resides in the Eagle-specific







|







519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
        #
        if {[file exists $fileName]} then {
          lappend fileNames $fileName
        }
      }

      #
      # TODO: If additional test suite files are added within the test
      #       package path, add them here as well.
      #
      foreach fileNameOnly [list \
          all.eagle constraints.eagle epilogue.eagle pkgIndex.eagle \
          pkgIndex.tcl prologue.eagle] {
        #
        # NOTE: First, check if the file resides in the Eagle-specific
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475

    #
    # NOTE: Check if the test package path is available.
    #
    if {[info exists ::test_path]} then {
      #
      # TODO: If additional test suite files are added within the test
      #       package path, add them here as well.
      #
      foreach fileNameOnly [list all.eagle epilogue.eagle prologue.eagle] {
        #
        # NOTE: Check if the file resides in the test package directory.
        #
        set fileName [file join $::test_path $fileNameOnly]








|







553
554
555
556
557
558
559
560
561
562
563
564
565
566
567

    #
    # NOTE: Check if the test package path is available.
    #
    if {[info exists ::test_path]} then {
      #
      # TODO: If additional test suite files are added within the test
      #       suite path, add them here as well.
      #
      foreach fileNameOnly [list all.eagle epilogue.eagle prologue.eagle] {
        #
        # NOTE: Check if the file resides in the test package directory.
        #
        set fileName [file join $::test_path $fileNameOnly]

977
978
979
980
981
982
983





























































































984
985
986
987
988
989
990
        #
        return
      }
    }

    tputs $channel no\n
  }






























































































  proc checkForEagle { channel } {
    tputs $channel "---- checking for Eagle... "

    if {[isEagle]} then {
      #
      # NOTE: We are running inside Eagle.







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
        #
        return
      }
    }

    tputs $channel no\n
  }

  proc checkForVisualStudioViaVsWhere { channel } {
    tputs $channel "---- checking for Visual Studio using \"vswhere\"... "

    #
    # NOTE: Initially, no versions of Visual Studio have been found.
    #
    set visualStudioVersions [list]

    #
    # NOTE: Use of the "vswhere" tool must be enabled for us to detect
    #       any instances of Visual Studio.
    #
    if {[canExecVsWhere]} then {
      #
      # NOTE: The versions of Visual Studio that we support detection
      #       of using the "vswhere" tool.
      #
      set versions [list [list 15.0 2017]]

      #
      # NOTE: Check each version and keep track of the ones we find.
      #
      foreach version $versions {
        #
        # NOTE: Attempt to fetch Visual Studio install directories
        #       value using the "vswhere" tool.
        #
        if {[canExecVsWhere] && [catch {
          exec -nocarriagereturns -- vswhere -products * \
              -version [lindex $version 0] -property installationPath
        } installationPaths] == 0} then {
          #
          # NOTE: Check each Visual Studio install directory, in the
          #       order they were returned, after splitting them into
          #       a proper Tcl list.
          #
          set installationPaths [split \
              [string trim $installationPaths] \n]

          foreach installationPath $installationPaths {
            #
            # NOTE: Remove the trailing backslash, if any.  Does the
            #       directory name look valid and does it actually
            #       exist?
            #
            set fileName [file join \
                [string trimright $installationPath \\] Common7 IDE \
                msenv.dll]

            if {[file isfile $fileName]} then {
              #
              # NOTE: Yes, it appears that it is available.
              #
              addConstraint [appendArgs \
                  visualStudio [lindex $version 1]]

              #
              # NOTE: Keep track of all the versions that we find.
              #
              lappend visualStudioVersions [lindex $version 1]

              #
              # NOTE: Save the directory for later usage by the test
              #       suite itself.
              #
              if {![info exists ::no(setVisualStudio)]} then {
                set ::test_visual_studio [file dirname $fileName]
              }

              #
              # HACK: Stop after we find the first instance of Visual
              #       Studio with the requested version.
              #
              break
            }
          }
        }
      }
    }

    if {[llength $visualStudioVersions] > 0} then {
      #
      # NOTE: Show where we found the latest version.
      #
      tputs $channel [appendArgs \
          "yes (" $visualStudioVersions ", \"" \
          [expr {[info exists ::test_visual_studio] ? \
              $::test_visual_studio : "<none>"}] "\")\n"]
    } else {
      tputs $channel no\n
    }
  }

  proc checkForEagle { channel } {
    tputs $channel "---- checking for Eagle... "

    if {[isEagle]} then {
      #
      # NOTE: We are running inside Eagle.
999
1000
1001
1002
1003
1004
1005


1006
1007
1008
1009
1010
1011
1012
1013
      addConstraint tclBug
      addConstraint tclCrash

      #
      # NOTE: Add the necessary constraints for each
      #       version of Tcl we know about.
      #


      foreach version [list 84 85 86] {
        addConstraint [appendArgs tclBug $version]
        addConstraint [appendArgs tclCrash $version]
      }

      tputs $channel yes\n
    } else {
      #







>
>
|







1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
      addConstraint tclBug
      addConstraint tclCrash

      #
      # NOTE: Add the necessary constraints for each
      #       version of Tcl we know about.
      #
      foreach tclVersion [getKnownTclVersions] {
        set version [getDotlessVersion $tclVersion]

        addConstraint [appendArgs tclBug $version]
        addConstraint [appendArgs tclCrash $version]
      }

      tputs $channel yes\n
    } else {
      #
1025
1026
1027
1028
1029
1030
1031


1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
        # NOTE: For each Tcl version we know about,
        #       check it against the currently running
        #       Tcl version.  If the two are not equal,
        #       add the test constraints that prevent
        #       skipping those tests that are buggy
        #       only for the particular version of Tcl.
        #


        foreach dotVersion [list 8.4 8.5 8.6] {
          if {$::tcl_version ne $dotVersion} then {
            set version [string map [list . ""] $dotVersion]

            addConstraint [appendArgs tclBug $version]
            addConstraint [appendArgs tclCrash $version]
          }
        }
      }








>
>
|

|







1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
        # NOTE: For each Tcl version we know about,
        #       check it against the currently running
        #       Tcl version.  If the two are not equal,
        #       add the test constraints that prevent
        #       skipping those tests that are buggy
        #       only for the particular version of Tcl.
        #
        foreach tclVersion [getKnownTclVersions] {
          set dotVersion [getDottedVersion $tclVersion]

          if {$::tcl_version ne $dotVersion} then {
            set version [getDotlessVersion $tclVersion]

            addConstraint [appendArgs tclBug $version]
            addConstraint [appendArgs tclCrash $version]
          }
        }
      }

1193
1194
1195
1196
1197
1198
1199
1200

1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222


1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238

1239
1240

1241
1242
1243
1244





1245
1246



1247
1248

1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262







1263









1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280

1281
1282
1283
1284
1285
1286
1287

  proc checkForTk { channel } {
    tputs $channel "---- checking for Tk... "

    #
    # HACK: For now, disable testing Tk 8.4/8.5 when running in Eagle.
    #
    if {![isEagle] || [haveConstraint tclLibrary86]} then {

      addConstraint tk

      tputs $channel yes\n
    } else {
      tputs $channel no\n
    }
  }

  proc checkForVersion { channel } {
    tputs $channel "---- checking for language version... "

    if {[info exists ::tcl_version]} then {
      #
      # TODO: Cleanup the semantics for adding test
      #       constraints here.
      #
      if {$::tcl_version eq "8.4"} then {
        #
        # NOTE: Baseline reported language and feature
        #       version.
        #
        addConstraint tcl84


        addConstraint tcl84Feature
        addConstraint tcl84OrLower
        addConstraint tcl84OrHigher
        addConstraint tcl85OrLower

        if {[isEagle]} then {
          #
          # NOTE: *EAGLE* We do want to include any
          #       tests that target "Tcl 8.5 or higher"
          #       features and/or "Tcl 8.6 or higher"
          #       features because they would not be in
          #       the test suite if we did not support
          #       that particular feature, regardless
          #       of the language version.
          #
          addConstraint tcl85Feature

          addConstraint tcl86Feature
        }

      } elseif {$::tcl_version eq "8.5"} then {
        #
        # NOTE: Baseline reported language and feature
        #       version.  Tcl 8.5 includes all the





        #       features from itself and Tcl 8.4.
        #



        addConstraint tcl84Feature
        addConstraint tcl84OrHigher

        addConstraint tcl85
        addConstraint tcl85Feature
        addConstraint tcl85OrLower
        addConstraint tcl85OrHigher

        if {[isEagle]} then {
          #
          # NOTE: *EAGLE* We do want to include any
          #       tests that target "Tcl 8.5 or higher"
          #       features and/or "Tcl 8.6 or higher"
          #       features because they would not be in
          #       the test suite if we did not support
          #       that particular feature, regardless
          #       of the language version.







          #









          addConstraint tcl86Feature
        }
      } elseif {$::tcl_version eq "8.6"} then {
        #
        # NOTE: Baseline reported language and feature
        #       version.  Tcl 8.6 includes all the
        #       features from itself Tcl 8.4, and Tcl
        #       8.5.
        #
        addConstraint tcl84Feature
        addConstraint tcl84OrHigher
        addConstraint tcl85Feature
        addConstraint tcl85OrHigher
        addConstraint tcl86
        addConstraint tcl86Feature
        addConstraint tcl86OrLower
        addConstraint tcl86OrHigher

      }

      tputs $channel [appendArgs $::tcl_version \n]
    } else {
      tputs $channel no\n
    }
  }







|
>













|
<

|
|
<
<
|
|
>
>
|
|
<
<
|
|
|
|
|
<
<
|
<
<
|
|
>
|

>
|
|
|
|
>
>
>
>
>
|

>
>
>
|
<
>
|
|
<
<

<

|
|
|
|
<
<
|
>
>
>
>
>
>
>
|
>
>
>
>
>
>
>
>
>
|
|
|
|
|
<
<
|
|
|
<
<
<
<
<
<
<
>







1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393
1394
1395
1396
1397
1398
1399
1400
1401
1402
1403
1404

1405
1406
1407


1408
1409
1410
1411
1412
1413


1414
1415
1416
1417
1418


1419


1420
1421
1422
1423
1424
1425
1426
1427
1428
1429
1430
1431
1432
1433
1434
1435
1436
1437
1438
1439
1440

1441
1442
1443


1444

1445
1446
1447
1448
1449


1450
1451
1452
1453
1454
1455
1456
1457
1458
1459
1460
1461
1462
1463
1464
1465
1466
1467
1468
1469
1470
1471
1472


1473
1474
1475







1476
1477
1478
1479
1480
1481
1482
1483

  proc checkForTk { channel } {
    tputs $channel "---- checking for Tk... "

    #
    # HACK: For now, disable testing Tk 8.4/8.5 when running in Eagle.
    #
    if {![isEagle] || [haveConstraint tclLibrary86] || \
        [haveConstraint tclLibrary87]} then {
      addConstraint tk

      tputs $channel yes\n
    } else {
      tputs $channel no\n
    }
  }

  proc checkForVersion { channel } {
    tputs $channel "---- checking for language version... "

    if {[info exists ::tcl_version]} then {
      #
      # NOTE: First, obtain the list of all "known" Tcl versions.

      #
      set tclVersions [getKnownTclVersions]



      #
      # NOTE: *EAGLE* We do want to include any tests that target
      #       "Tcl 8.X or higher" features because those tests
      #       would not be in the test suite if we did not support
      #       that particular feature, regardless of the language
      #       version.


      #
      if {[isEagle]} then {
        #
        # NOTE: Process each "known" Tcl version, adding each of
        #       the "feature" constraints (i.e. since this is an


        #       Eagle test suite infrastructure package).


        #
        foreach tclVersion(1) $tclVersions {
          set version(1) [getDotlessVersion $tclVersion(1)]
          addConstraint [appendArgs tcl $version(1) Feature]
        }
      }

      #
      # NOTE: Process each "known" Tcl version, checking for an
      #       exact match with the running Tcl version.  When an
      #       exact match is found, add appropriate constraints.
      #
      foreach tclVersion(1) $tclVersions {
        #
        # NOTE: Does the running Tcl version match this "known"
        #       Tcl version exactly?
        #
        if {$::tcl_version eq [getDottedVersion $tclVersion(1)]} then {
          #
          # NOTE: Yes, it does.  First, add the "exact" match
          #       constraint.  There can be only one of these.

          #
          addConstraint [appendArgs \
              tcl [getDotlessVersion $tclVersion(1)]]




          #
          # NOTE: Next, process each of the "known" Tcl versions
          #       less than or equal to the running Tcl version,
          #       while adding both the "feature" and "or higher"
          #       constraints.  There will always be at least one


          #       of these.
          #
          foreach tclVersion(2) [filterKnownVersions \
              $tclVersions "" $tclVersion(1)] {
            set version(2) [getDotlessVersion $tclVersion(2)]
            addConstraint [appendArgs tcl $version(2) Feature]
            addConstraint [appendArgs tcl $version(2) OrHigher]
          }

          #
          # NOTE: Finally, process each of the "known" Tcl versions
          #       greater than or equal to the running Tcl version,
          #       while adding the "or lower" constraints.  There
          #       will always be at least one of these.
          #
          foreach tclVersion(3) [filterKnownVersions \
              $tclVersions $tclVersion(1) ""] {
            set version(3) [getDotlessVersion $tclVersion(3)]
            addConstraint [appendArgs tcl $version(3) OrLower]
          }

          #
          # NOTE: There can be only one exact Tcl version match;


          #       therefore, we are done.
          #
          break







        }
      }

      tputs $channel [appendArgs $::tcl_version \n]
    } else {
      tputs $channel no\n
    }
  }
1799
1800
1801
1802
1803
1804
1805

























































1806
1807
1808
1809
1810
1811
1812
      addConstraint tip440

      tputs $channel [appendArgs "yes (" $engine ")\n"]
    } else {
      tputs $channel no\n
    }
  }


























































  proc checkForTiming {
          channel threshold {constraint ""} {tries 1} {delay 1000}
          {average false} {asynchronous false} } {
    tputs $channel [appendArgs \
        "---- checking for precision timing (threshold of " $threshold \
        " milliseconds" [expr {$average ? " average" : ""}] ", delay of " \







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







1995
1996
1997
1998
1999
2000
2001
2002
2003
2004
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
2025
2026
2027
2028
2029
2030
2031
2032
2033
2034
2035
2036
2037
2038
2039
2040
2041
2042
2043
2044
2045
2046
2047
2048
2049
2050
2051
2052
2053
2054
2055
2056
2057
2058
2059
2060
2061
2062
2063
2064
2065
      addConstraint tip440

      tputs $channel [appendArgs "yes (" $engine ")\n"]
    } else {
      tputs $channel no\n
    }
  }

  proc checkForTip461 { channel } {
    tputs $channel "---- checking for TIP #461... "

    #
    # NOTE: Is the interpreter TIP #461 ready?
    #
    if {[catch {
      set expr(ge) {int("abc" ge "abc")}
      set expr(gt) {int("abc" gt "abc")}
      set expr(le) {int("abc" le "abc")}
      set expr(lt) {int("abc" lt "abc")}

      list [expr $expr(ge)] [expr $expr(gt)] \
          [expr $expr(le)] [expr $expr(lt)]
    }] == 0} then {
      addConstraint tip461

      tputs $channel yes\n
    } else {
      tputs $channel no\n
    }
  }

  proc checkForTip463 { channel } {
    tputs $channel "---- checking for TIP #463... "

    #
    # NOTE: Is the interpreter TIP #463 ready?
    #
    if {[catch {
      regsub -command . . list
    }] == 0} then {
      addConstraint tip463

      tputs $channel yes\n
    } else {
      tputs $channel no\n
    }
  }

  proc checkForTip471 { channel } {
    tputs $channel "---- checking for TIP #471... "

    #
    # NOTE: Is the interpreter TIP #471 ready?
    #
    catch {info linkedname} error

    if {[string match {wrong # args: should be "*} $error]} then {
      addConstraint tip471

      tputs $channel yes\n
    } else {
      tputs $channel no\n
    }
  }

  proc checkForTiming {
          channel threshold {constraint ""} {tries 1} {delay 1000}
          {average false} {asynchronous false} } {
    tputs $channel [appendArgs \
        "---- checking for precision timing (threshold of " $threshold \
        " milliseconds" [expr {$average ? " average" : ""}] ", delay of " \
2675
2676
2677
2678
2679
2680
2681
2682
2683
2684
2685
2686
2687
2688
2689
2690
      tputs $channel "---- checking for image runtime version... "

      if {[info exists ::eagle_platform(imageRuntimeVersion)] && \
          [string length $::eagle_platform(imageRuntimeVersion)] > 0} then {
        #
        # NOTE: Get the major and minor portions of the version only.
        #
        set dotVersion [join [lrange [split \
            $::eagle_platform(imageRuntimeVersion) .] 0 1] .]

        #
        # NOTE: Now create a version string for use in the constraint name
        #       (remove the periods).
        #
        set version [string map [list v "" . ""] $dotVersion]








|
|







2928
2929
2930
2931
2932
2933
2934
2935
2936
2937
2938
2939
2940
2941
2942
2943
      tputs $channel "---- checking for image runtime version... "

      if {[info exists ::eagle_platform(imageRuntimeVersion)] && \
          [string length $::eagle_platform(imageRuntimeVersion)] > 0} then {
        #
        # NOTE: Get the major and minor portions of the version only.
        #
        set dotVersion [getMajorMinorVersion \
            $::eagle_platform(imageRuntimeVersion)]

        #
        # NOTE: Now create a version string for use in the constraint name
        #       (remove the periods).
        #
        set version [string map [list v "" . ""] $dotVersion]

2705
2706
2707
2708
2709
2710
2711
2712
2713
2714
2715
2716
2717
2718
2719
2720
2721
2722
2723
2724
2725
2726
2727
2728
2729
2730
2731
2732
2733
2734
2735






































































2736
2737
2738
2739
2740
2741
2742
2743
2744
2745
2746
2747
2748
2749
2750
2751
2752
      tputs $channel "---- checking for framework version... "

      if {[info exists ::eagle_platform(frameworkVersion)] && \
          [string length $::eagle_platform(frameworkVersion)] > 0} then {
        #
        # NOTE: Get the major and minor portions of the version only.
        #
        set dotVersion [join [lrange [split \
            $::eagle_platform(frameworkVersion) .] 0 1] .]

        #
        # NOTE: Now create a version string for use in the constraint name
        #       (remove the periods).
        #
        set version [string map [list . ""] $dotVersion]

        #
        # NOTE: If the framework version was found, add a test constraint
        #       for it now.
        #
        if {[string length $version] > 0} then {
          addConstraint [appendArgs framework $version]
        }

        tputs $channel [appendArgs \
            $::eagle_platform(frameworkVersion) " (" $dotVersion ")\n"]
      } else {
        tputs $channel no\n
      }
    }







































































    proc checkForRuntimeVersion { channel } {
      tputs $channel "---- checking for runtime version... "

      if {[info exists ::eagle_platform(runtimeVersion)] && \
          [string length $::eagle_platform(runtimeVersion)] > 0} then {
        #
        # NOTE: Get the major and minor portions of the version only.
        #
        set dotVersion [join [lrange [split \
            $::eagle_platform(runtimeVersion) .] 0 1] .]

        #
        # NOTE: Now create a version string for use in the constraint name
        #       (remove the periods).
        #
        set version [string map [list . ""] $dotVersion]








|
|





|
















>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>








|
|







2958
2959
2960
2961
2962
2963
2964
2965
2966
2967
2968
2969
2970
2971
2972
2973
2974
2975
2976
2977
2978
2979
2980
2981
2982
2983
2984
2985
2986
2987
2988
2989
2990
2991
2992
2993
2994
2995
2996
2997
2998
2999
3000
3001
3002
3003
3004
3005
3006
3007
3008
3009
3010
3011
3012
3013
3014
3015
3016
3017
3018
3019
3020
3021
3022
3023
3024
3025
3026
3027
3028
3029
3030
3031
3032
3033
3034
3035
3036
3037
3038
3039
3040
3041
3042
3043
3044
3045
3046
3047
3048
3049
3050
3051
3052
3053
3054
3055
3056
3057
3058
3059
3060
3061
3062
3063
3064
3065
3066
3067
3068
3069
3070
3071
3072
3073
3074
3075
      tputs $channel "---- checking for framework version... "

      if {[info exists ::eagle_platform(frameworkVersion)] && \
          [string length $::eagle_platform(frameworkVersion)] > 0} then {
        #
        # NOTE: Get the major and minor portions of the version only.
        #
        set dotVersion [getMajorMinorVersion \
            $::eagle_platform(frameworkVersion)]

        #
        # NOTE: Now create a version string for use in the constraint name
        #       (remove the periods).
        #
        set version [getDotlessVersion $dotVersion]

        #
        # NOTE: If the framework version was found, add a test constraint
        #       for it now.
        #
        if {[string length $version] > 0} then {
          addConstraint [appendArgs framework $version]
        }

        tputs $channel [appendArgs \
            $::eagle_platform(frameworkVersion) " (" $dotVersion ")\n"]
      } else {
        tputs $channel no\n
      }
    }

    proc checkForMatchingFrameworkVersion { channel } {
      tputs $channel "---- checking for matching framework version... "

      if {[info exists ::eagle_platform(frameworkVersion)] && \
          [string length $::eagle_platform(frameworkVersion)] > 0} then {
        if {[info exists ::eagle_platform(imageRuntimeVersion)] && \
            [string length $::eagle_platform(imageRuntimeVersion)] > 0} then {
          #
          # NOTE: Get the major and minor portions of the versions only.
          #
          set dotVersion(1) [getMajorMinorVersion \
              $::eagle_platform(frameworkVersion)]

          set dotVersion(2) [getMajorMinorVersion \
              $::eagle_platform(imageRuntimeVersion)]

          #
          # NOTE: Remove single leading "v" characters, if applicable.
          #
          if {[string index $dotVersion(1) 0] eq "v"} then {
            set dotVersion(1) [string range $dotVersion(1) 1 end]
          }

          if {[string index $dotVersion(2) 0] eq "v"} then {
            set dotVersion(2) [string range $dotVersion(2) 1 end]
          }

          #
          # NOTE: Now create a version string for use in the constraint
          #       name (remove the periods).
          #
          set version(1) [string map [list . ""] $dotVersion(1)]

          #
          # NOTE: Check for an exact match between the image runtime
          #       version and the framework version.
          #
          if {$dotVersion(1) eq $dotVersion(2)} then {
            #
            # NOTE: Yes, the image runtime version matches the framework.
            #
            addConstraint matchFramework
            addConstraint [appendArgs matchFramework $version(1)]

            addConstraint dotnetMatchFramework
            addConstraint [appendArgs dotnetMatchFramework $version(1)]

            addConstraint monoMatchFramework
            addConstraint [appendArgs monoMatchFramework $version(1)]

            tputs $channel yes\n
          } else {
            if {[isMono]} then {
              addConstraint dotnetMatchFramework
              addConstraint [appendArgs dotnetMatchFramework $version(1)]
            } else {
              addConstraint monoMatchFramework
              addConstraint [appendArgs monoMatchFramework $version(1)]
            }

            tputs $channel no\n
          }
        } else {
          tputs $channel "no, missing image runtime version\n"
        }
      } else {
        tputs $channel "no, missing framework version\n"
      }
    }

    proc checkForRuntimeVersion { channel } {
      tputs $channel "---- checking for runtime version... "

      if {[info exists ::eagle_platform(runtimeVersion)] && \
          [string length $::eagle_platform(runtimeVersion)] > 0} then {
        #
        # NOTE: Get the major and minor portions of the version only.
        #
        set dotVersion [getMajorMinorVersion \
            $::eagle_platform(runtimeVersion)]

        #
        # NOTE: Now create a version string for use in the constraint name
        #       (remove the periods).
        #
        set version [string map [list . ""] $dotVersion]

3316
3317
3318
3319
3320
3321
3322
3323
3324
3325
3326
3327
3328
3329
3330
3331
3332
3333
3334
3335
3336
3337
3338
3339
3340
3341
3342
3343
3344
3345
3346
3347

3348
3349
3350
3351
3352

3353




3354
3355
3356
3357
3358
3359
3360

      #
      # NOTE: Check for dynamically loadable Tcl libraries (for this
      #       architecture only).
      #
      if {[catch {tcl select -architecture} tcl] == 0} then {
        #
        # NOTE: Did we find one?  Attempt to grab the index
        #       of the version field from the list.
        #
        set index [lsearch -exact $tcl version]

        if {$index != -1} then {
          #
          # NOTE: The very next list index contains the value
          #       (i.e. like a Tcl 8.5+ dict).
          #
          set dotVersion [lindex $tcl [incr index]]

          #
          # NOTE: Do we know the version?
          #
          if {[string length $dotVersion] > 0 && \
              [regexp -- {^\d+\.\d+$} $dotVersion]} then {
            #
            # NOTE: Yes, some version of Tcl is available.
            #
            addConstraint tclLibrary

            #
            # NOTE: Is the version 8.x or higher?
            #

            if {$dotVersion >= 8.6} then {
              addConstraint tclLibrary86
            } elseif {$dotVersion >= 8.5} then {
              addConstraint tclLibrary85
            } elseif {$dotVersion >= 8.4} then {

              addConstraint tclLibrary84




            }

            tputs $channel [appendArgs $dotVersion \n]

            #
            # NOTE: We are done here, return now.
            #







|
|





|
|
















>
|
|
<
|
|
>
|
>
>
>
>







3639
3640
3641
3642
3643
3644
3645
3646
3647
3648
3649
3650
3651
3652
3653
3654
3655
3656
3657
3658
3659
3660
3661
3662
3663
3664
3665
3666
3667
3668
3669
3670
3671
3672
3673

3674
3675
3676
3677
3678
3679
3680
3681
3682
3683
3684
3685
3686
3687
3688

      #
      # NOTE: Check for dynamically loadable Tcl libraries (for this
      #       architecture only).
      #
      if {[catch {tcl select -architecture} tcl] == 0} then {
        #
        # NOTE: Found one?  Ok, attempt to grab the index of the version
        #       field from the list.
        #
        set index [lsearch -exact $tcl version]

        if {$index != -1} then {
          #
          # NOTE: The very next list index contains the value (i.e. like
          #       a Tcl 8.5+ dict).
          #
          set dotVersion [lindex $tcl [incr index]]

          #
          # NOTE: Do we know the version?
          #
          if {[string length $dotVersion] > 0 && \
              [regexp -- {^\d+\.\d+$} $dotVersion]} then {
            #
            # NOTE: Yes, some version of Tcl is available.
            #
            addConstraint tclLibrary

            #
            # NOTE: Is the version 8.x or higher?
            #
            foreach tclVersion [lreverse [getKnownTclVersions]] {
              if {$dotVersion >= [getDottedVersion $tclVersion]} then {
                addConstraint [appendArgs \

                    tclLibrary [getDotlessVersion $tclVersion]]

                #
                # NOTE: For now, there can be only one Tcl library match;
                #       therefore, we are done.
                #
                break
              }
            }

            tputs $channel [appendArgs $dotVersion \n]

            #
            # NOTE: We are done here, return now.
            #
3381
3382
3383
3384
3385
3386
3387
3388
3389
3390
3391
3392
3393
3394
3395
3396

3397
3398
3399

3400
3401

3402



3403
3404

3405
3406
3407
3408
3409
3410
3411
3412
3413
3414
3415
3416
3417
3418
3419
3420
3421

3422
3423
3424
3425

3426




3427
3428
3429
3430
3431
3432
3433
        addConstraint tclReadyOrLibrary

        #
        # NOTE: Ok, attempt to determine the loaded Tcl version.
        #
        if {[catch {
          tcl eval [tcl master] {info tclversion}
        } version] == 0 && [regexp -- {^\d+\.\d+$} $version]} then {
          addConstraint [appendArgs \
              tclReady [string map [list . ""] $version]]

          #
          # NOTE: The Tcl library is ready; however, we need to add the
          #       appropriate test constraint to indicate that a specific
          #       version of Tcl is "either ready or available".
          #

          if {[haveConstraint tclLibrary86] && $version >= 8.6} then {
            addConstraint tclReadyOrLibrary86
          } elseif {[haveConstraint tclLibrary85] && $version >= 8.5} then {

            addConstraint tclReadyOrLibrary85
          } elseif {[haveConstraint tclLibrary84] && $version >= 8.4} then {

            addConstraint tclReadyOrLibrary84



          }


          tputs $channel [appendArgs "yes (" $version ")\n"]
        } else {
          #
          # NOTE: The Tcl library is ready; however, we have no idea what
          #       version it actually is; therefore, skip adding the test
          #       constraint to indicate that a specific version of Tcl
          #       is "either ready or available".
          #
          tputs $channel yes\n
        }
      } else {
        #
        # NOTE: The Tcl library is not ready; however, we still need to add
        #       the appropriate test constraint to indicate that a specific
        #       version of Tcl is "either ready or available".
        #
        if {[haveConstraint tclLibrary86]} then {

          addConstraint tclReadyOrLibrary86
        } elseif {[haveConstraint tclLibrary85]} then {
          addConstraint tclReadyOrLibrary85
        } elseif {[haveConstraint tclLibrary84]} then {

          addConstraint tclReadyOrLibrary84




        }

        tputs $channel no\n
      }
    }

    proc checkForTclSelect { channel } {







|

|






>
|
|
|
>
|
|
>
|
>
>
>
|
|
>
|















|
>
|
|
|
|
>
|
>
>
>
>







3709
3710
3711
3712
3713
3714
3715
3716
3717
3718
3719
3720
3721
3722
3723
3724
3725
3726
3727
3728
3729
3730
3731
3732
3733
3734
3735
3736
3737
3738
3739
3740
3741
3742
3743
3744
3745
3746
3747
3748
3749
3750
3751
3752
3753
3754
3755
3756
3757
3758
3759
3760
3761
3762
3763
3764
3765
3766
3767
3768
3769
3770
3771
3772
3773
3774
        addConstraint tclReadyOrLibrary

        #
        # NOTE: Ok, attempt to determine the loaded Tcl version.
        #
        if {[catch {
          tcl eval [tcl master] {info tclversion}
        } dotVersion] == 0 && [regexp -- {^\d+\.\d+$} $dotVersion]} then {
          addConstraint [appendArgs \
              tclReady [getDotlessVersion $dotVersion]]

          #
          # NOTE: The Tcl library is ready; however, we need to add the
          #       appropriate test constraint to indicate that a specific
          #       version of Tcl is "either ready or available".
          #
          foreach tclVersion [lreverse [getKnownTclVersions]] {
            set version [getDotlessVersion $tclVersion]

            if {[haveConstraint [appendArgs tclLibrary $version]] && \
                $dotVersion >= [getDottedVersion $tclVersion]} then {
              addConstraint [appendArgs tclReadyOrLibrary $version]

              #
              # NOTE: For now, there can be only one Tcl library match;
              #       therefore, we are done.
              #
              break
            }
          }

          tputs $channel [appendArgs "yes (" $dotVersion ")\n"]
        } else {
          #
          # NOTE: The Tcl library is ready; however, we have no idea what
          #       version it actually is; therefore, skip adding the test
          #       constraint to indicate that a specific version of Tcl
          #       is "either ready or available".
          #
          tputs $channel yes\n
        }
      } else {
        #
        # NOTE: The Tcl library is not ready; however, we still need to add
        #       the appropriate test constraint to indicate that a specific
        #       version of Tcl is "either ready or available".
        #
        foreach tclVersion [lreverse [getKnownTclVersions]] {
          set version [getDotlessVersion $tclVersion]

          if {[haveConstraint [appendArgs tclLibrary $version]]} then {
            addConstraint [appendArgs tclReadyOrLibrary $version]

            #
            # NOTE: For now, there can be only one Tcl library match;
            #       therefore, we are done.
            #
            break
          }
        }

        tputs $channel no\n
      }
    }

    proc checkForTclSelect { channel } {
3740
3741
3742
3743
3744
3745
3746
3747
3748
3749
3750
3751
3752
3753
3754
        set name [lindex $::eagle_platform(nativeUtility) 0]

        if {[string length $name] > 0} then {
          set version [lindex $::eagle_platform(nativeUtility) 1]

          if {[string length $version] > 0} then {
            set nativeUtility [appendArgs \
                $name . [join [lrange [split $version .] 0 1] .]]
          } else {
            set nativeUtility $name
          }

          if {$nativeUtility ni "disabled unavailable"} then {
            addConstraint nativeUtility
          }







|







4081
4082
4083
4084
4085
4086
4087
4088
4089
4090
4091
4092
4093
4094
4095
        set name [lindex $::eagle_platform(nativeUtility) 0]

        if {[string length $name] > 0} then {
          set version [lindex $::eagle_platform(nativeUtility) 1]

          if {[string length $version] > 0} then {
            set nativeUtility [appendArgs \
                $name . [getMajorMinorVersion $version]]
          } else {
            set nativeUtility $name
          }

          if {$nativeUtility ni "disabled unavailable"} then {
            addConstraint nativeUtility
          }
3871
3872
3873
3874
3875
3876
3877

















3878
3879
3880
3881
3882
3883
3884
      }

      #
      # NOTE: We are not running on Windows 10, return the normal value.
      #
      return 394806
    }


















    proc checkForNetFx4x { channel } {
      tputs $channel "---- checking for .NET Framework 4.x... "

      #
      # NOTE: Platform must be Windows for this constraint to even be
      #       checked (i.e. we require the registry).







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







4212
4213
4214
4215
4216
4217
4218
4219
4220
4221
4222
4223
4224
4225
4226
4227
4228
4229
4230
4231
4232
4233
4234
4235
4236
4237
4238
4239
4240
4241
4242
      }

      #
      # NOTE: We are not running on Windows 10, return the normal value.
      #
      return 394806
    }

    proc getFrameworkSetup47Value {} {
      #
      # NOTE: Check if we are running on Windows 10 or later.
      #
      if {[isWindows] && $::tcl_platform(osVersion) >= 10.0} then {
        #
        # NOTE: We are running on Windows 10, return the special value.
        #
        return 460798
      }

      #
      # NOTE: We are not running on Windows 10, return the normal value.
      #
      return 460805
    }

    proc checkForNetFx4x { channel } {
      tputs $channel "---- checking for .NET Framework 4.x... "

      #
      # NOTE: Platform must be Windows for this constraint to even be
      #       checked (i.e. we require the registry).
3917
3918
3919
3920
3921
3922
3923
3924

3925
3926
3927
3928










3929
3930
3931
3932
3933
3934
3935
          #       is installed.  However, if the "release" value is also
          #       greater than or equal to 379893, then the .NET Framework
          #       4.5.2 is installed, which is an in-place upgrade to 4.5.1
          #       (and 4.5).  If the "release" value is also greater than or
          #       equal to 393297 (393295 on Windows 10), then the .NET
          #       Framework 4.6 is installed, which is an in-place upgrade
          #       to 4.5.x.  Similar handling is necessary for the .NET
          #       Framework 4.6.1 and 4.6.2.  For more information, see:

          #
          #       https://msdn.microsoft.com/en-us/library/hh925568.aspx
          #
          if {$release >= [getFrameworkSetup462Value]} then {










            addConstraint dotNet451OrHigher
            addConstraint dotNet452OrHigher
            addConstraint dotNet46OrHigher
            addConstraint dotNet461OrHigher
            addConstraint dotNet462
            addConstraint dotNet462OrHigher








|
>



|
>
>
>
>
>
>
>
>
>
>







4275
4276
4277
4278
4279
4280
4281
4282
4283
4284
4285
4286
4287
4288
4289
4290
4291
4292
4293
4294
4295
4296
4297
4298
4299
4300
4301
4302
4303
4304
          #       is installed.  However, if the "release" value is also
          #       greater than or equal to 379893, then the .NET Framework
          #       4.5.2 is installed, which is an in-place upgrade to 4.5.1
          #       (and 4.5).  If the "release" value is also greater than or
          #       equal to 393297 (393295 on Windows 10), then the .NET
          #       Framework 4.6 is installed, which is an in-place upgrade
          #       to 4.5.x.  Similar handling is necessary for the .NET
          #       Framework 4.6.1, 4.6.2, and 4.7.  For more information,
          #       see:
          #
          #       https://msdn.microsoft.com/en-us/library/hh925568.aspx
          #
          if {$release >= [getFrameworkSetup47Value]} then {
            addConstraint dotNet451OrHigher
            addConstraint dotNet452OrHigher
            addConstraint dotNet46OrHigher
            addConstraint dotNet461OrHigher
            addConstraint dotNet462OrHigher
            addConstraint dotNet47
            addConstraint dotNet47OrHigher

            set version 4.7
          } elseif {$release >= [getFrameworkSetup462Value]} then {
            addConstraint dotNet451OrHigher
            addConstraint dotNet452OrHigher
            addConstraint dotNet46OrHigher
            addConstraint dotNet461OrHigher
            addConstraint dotNet462
            addConstraint dotNet462OrHigher

3977
3978
3979
3980
3981
3982
3983
3984
3985





3986
3987
3988
3989
3990
3991
3992
3993
3994
3995
3996
3997
3998
3999
4000
4001
4002
4003

4004
4005
4006
4007
4008
4009
4010
4011
4012
4013
4014
4015
4016
4017
4018

4019
4020
4021

4022





4023
4024
4025
4026
4027

4028
4029
4030
4031
4032
4033
4034
4035
4036
4037
4038
4039

4040
4041
4042
4043
4044
4045
4046
4047
4048
4049
4050

4051
4052
4053
4054
4055
4056
4057
4058
          return
        }
      }

      tputs $channel no\n
    }

    proc checkForVisualStudio { channel } {
      tputs $channel "---- checking for Visual Studio... "






      #
      # NOTE: Platform must be Windows for this constraint to even be
      #       checked (i.e. we require the registry).
      #
      set visualStudioVersions [list]

      if {[isWindows]} then {
        #
        # NOTE: Registry hive where Visual Studio install information is
        #       stored.  Make sure to look in the WoW64 registry because
        #       Visual Studio is currently always a 32-bit application.
        #
        set key [appendArgs HKEY_LOCAL_MACHINE\\ \
            [getSoftwareRegistryKey true] {\Microsoft\VisualStudio}]

        #
        # NOTE: The versions of Visual Studio that we support.

        #
        set versions [list [list 8.0 2005] [list 9.0 2008] \
            [list 10.0 2010] [list 11.0 2012] [list 12.0 2013] \
            [list 14.0 2015]]

        #
        # NOTE: Check each version and keep track of the ones we find.
        #
        foreach version $versions {
          #
          # NOTE: Attempt to fetch the Visual Studio install directory
          #       value from the registry, removing the trailing backslash,
          #       if any.  Does the directory name look valid and does it
          #       actually exist?
          #

          if {[catch {file normalize [file join [string trimright [object \
                  invoke Microsoft.Win32.Registry GetValue [appendArgs $key \\ \
                  [lindex $version 0]] InstallDir null] \\] msenv.dll]} \

                  fileName] == 0 && \





              [string length $fileName] > 0 && [file isfile $fileName]} then {
            #
            # NOTE: Yes, it appears that it is available.
            #
            addConstraint [appendArgs visualStudio [lindex $version 1]]


            #
            # NOTE: Keep track of all the versions that we find.
            #
            lappend visualStudioVersions [lindex $version 1]

            #
            # NOTE: Save the directory for later usage by
            #       the test itself.
            #
            if {![info exists ::no(setVisualStudio)]} then {
              set ::test_visual_studio [file dirname $fileName]

            }
          }
        }
      }

      if {[llength $visualStudioVersions] > 0} then {
        #
        # NOTE: Show where we found the latest version.
        #
        tputs $channel [appendArgs \
            "yes (" $visualStudioVersions ", \"" \

            $::test_visual_studio "\")\n"]
      } else {
        tputs $channel no\n
      }
    }

    proc checkForNativeDebugger { channel } {
      tputs $channel "---- checking for native debugger... "







|
|
>
>
>
>
>





<
<










|
>












<
|

>
|
|
|
>
|
>
>
>
>
>
|
|
|
|
|
>

|
|
|
|

|
|
|
|
|
|
>











>
|







4346
4347
4348
4349
4350
4351
4352
4353
4354
4355
4356
4357
4358
4359
4360
4361
4362
4363
4364


4365
4366
4367
4368
4369
4370
4371
4372
4373
4374
4375
4376
4377
4378
4379
4380
4381
4382
4383
4384
4385
4386
4387
4388

4389
4390
4391
4392
4393
4394
4395
4396
4397
4398
4399
4400
4401
4402
4403
4404
4405
4406
4407
4408
4409
4410
4411
4412
4413
4414
4415
4416
4417
4418
4419
4420
4421
4422
4423
4424
4425
4426
4427
4428
4429
4430
4431
4432
4433
4434
4435
4436
4437
4438
4439
4440
          return
        }
      }

      tputs $channel no\n
    }

    proc checkForVisualStudioViaRegistry { channel } {
      tputs $channel "---- checking for Visual Studio using registry... "

      #
      # NOTE: Initially, no versions of Visual Studio have been found.
      #
      set visualStudioVersions [list]

      #
      # NOTE: Platform must be Windows for this constraint to even be
      #       checked (i.e. we require the registry).
      #


      if {[isWindows]} then {
        #
        # NOTE: Registry hive where Visual Studio install information is
        #       stored.  Make sure to look in the WoW64 registry because
        #       Visual Studio is currently always a 32-bit application.
        #
        set key [appendArgs HKEY_LOCAL_MACHINE\\ \
            [getSoftwareRegistryKey true] {\Microsoft\VisualStudio}]

        #
        # NOTE: The versions of Visual Studio that we support detection
        #       of using the registry.
        #
        set versions [list [list 8.0 2005] [list 9.0 2008] \
            [list 10.0 2010] [list 11.0 2012] [list 12.0 2013] \
            [list 14.0 2015]]

        #
        # NOTE: Check each version and keep track of the ones we find.
        #
        foreach version $versions {
          #
          # NOTE: Attempt to fetch the Visual Studio install directory
          #       value from the registry, removing the trailing backslash,

          #       if any.
          #
          if {[catch {
            file normalize [file join [string trimright [object \
                invoke Microsoft.Win32.Registry GetValue [appendArgs \
                $key \\ [lindex $version 0]] InstallDir null] \\] \
                msenv.dll]
          } fileName] == 0} then {
            #
            # NOTE: Does the directory name look valid and does it
            #       actually exist?
            #
            if {[string length $fileName] > 0 && \
                [file isfile $fileName]} then {
              #
              # NOTE: Yes, it appears that it is available.
              #
              addConstraint [appendArgs \
                  visualStudio [lindex $version 1]]

              #
              # NOTE: Keep track of all the versions that we find.
              #
              lappend visualStudioVersions [lindex $version 1]

              #
              # NOTE: Save the directory for later usage by the test
              #       suite itself.
              #
              if {![info exists ::no(setVisualStudio)]} then {
                set ::test_visual_studio [file dirname $fileName]
              }
            }
          }
        }
      }

      if {[llength $visualStudioVersions] > 0} then {
        #
        # NOTE: Show where we found the latest version.
        #
        tputs $channel [appendArgs \
            "yes (" $visualStudioVersions ", \"" \
            [expr {[info exists ::test_visual_studio] ? \
                $::test_visual_studio : "<none>"}] "\")\n"]
      } else {
        tputs $channel no\n
      }
    }

    proc checkForNativeDebugger { channel } {
      tputs $channel "---- checking for native debugger... "
4185
4186
4187
4188
4189
4190
4191
4192
4193
4194
4195
4196
4197
4198
4199
4200
4201
4202
4203
4204

4205
4206
4207
4208
4209
4210
4211
    #
    # NOTE: We need several of our test constraint related commands in the
    #       global namespace.
    #
    exportAndImportPackageCommands [namespace current] [list \
        getKnownBuildTypes getKnownCompileOptions getKnownMonoVersions \
        addKnownMonoConstraints lpermute alwaysFullInterpReady canExecComSpec \
        canExecWhoAmI canExecTclShell canExecFossil isTestMono \
        isTestAdministrator canPing cleanPackageName checkForTestSuiteFiles \
        checkForPlatform checkForWindowsVersion checkForScriptLibrary \
        checkForVariable checkForTclOptions checkForWindowsCommandProcessor \
        checkForPackage checkForFossil checkForEagle checkForSymbols \
        checkForLogFile checkForGaruda checkForShell \
        checkForOfficialStableReleaseInProgress checkForDebug checkForTk \
        checkForVersion checkForCommand checkForSubCommand checkForNamespaces \
        checkForTestExec checkForTestMachine checkForTestPlatform \
        checkForTestConfiguration checkForTestSuffix checkForFile \
        checkForPathFile checkForNativeCode checkForTip127 checkForTip194 \
        checkForTip207 checkForTip241 checkForTip285 checkForTip405 \
        checkForTip426 checkForTip429 checkForTip440 checkForTiming \

        checkForPerformance checkForBigLists checkForProcessorIntensive \
        checkForTimeIntensive checkForFullTest checkForMemoryIntensive \
        checkForStackIntensive checkForStackSize checkForInteractive \
        checkForInteractiveCommand checkForUserInteraction checkForNetwork \
        checkForCompileOption checkForKnownCompileOptions] false false

    ###########################################################################







|



|
|
|
|
|
|
|
|
|
>







4567
4568
4569
4570
4571
4572
4573
4574
4575
4576
4577
4578
4579
4580
4581
4582
4583
4584
4585
4586
4587
4588
4589
4590
4591
4592
4593
4594
    #
    # NOTE: We need several of our test constraint related commands in the
    #       global namespace.
    #
    exportAndImportPackageCommands [namespace current] [list \
        getKnownBuildTypes getKnownCompileOptions getKnownMonoVersions \
        addKnownMonoConstraints lpermute alwaysFullInterpReady canExecComSpec \
        canExecWhoAmI canExecTclShell canExecFossil canExecVsWhere isTestMono \
        isTestAdministrator canPing cleanPackageName checkForTestSuiteFiles \
        checkForPlatform checkForWindowsVersion checkForScriptLibrary \
        checkForVariable checkForTclOptions checkForWindowsCommandProcessor \
        checkForPackage checkForFossil checkForVisualStudioViaVsWhere \
        checkForEagle checkForSymbols checkForLogFile checkForGaruda \
        checkForShell checkForOfficialStableReleaseInProgress checkForDebug \
        checkForTk checkForVersion checkForCommand checkForSubCommand \
        checkForNamespaces checkForTestExec checkForTestMachine \
        checkForTestPlatform checkForTestConfiguration checkForTestSuffix \
        checkForFile checkForPathFile checkForNativeCode checkForTip127 \
        checkForTip194 checkForTip207 checkForTip241 checkForTip285 \
        checkForTip405 checkForTip426 checkForTip429 checkForTip440 \
        checkForTip461 checkForTip463 checkForTip471 checkForTiming \
        checkForPerformance checkForBigLists checkForProcessorIntensive \
        checkForTimeIntensive checkForFullTest checkForMemoryIntensive \
        checkForStackIntensive checkForStackSize checkForInteractive \
        checkForInteractiveCommand checkForUserInteraction checkForNetwork \
        checkForCompileOption checkForKnownCompileOptions] false false

    ###########################################################################
Changes to Externals/Eagle/lib/Test1.0/epilogue.eagle.
208
209
210
211
212
213
214




215
216
217
218
219
220
221
222
223
224

225
226
227
228
229
230
231
232
233
234






235
236
237
238
239
240
241
242
243
244
245

246
247
248
249
250
251

252
253
254

255
256
257
258






259
260

261
262
263
264
265
266
267
      #
      set percent 0
    }

    #
    # NOTE: Has the test pass threshold been set?  If so, is it set to
    #       the default value?




    #
    if {![info exists test_threshold] || $test_threshold == 100} then {
      #
      # NOTE: The test pass threshold is set to the default value (100%).
      #       Check to make sure that all tests pass and then set the
      #       exit code to success; otherwise, we set it to failure.
      #
      set passedOrSkipped [expr {$eagle_tests(Passed) + \
          $eagle_tests(Skipped)}]


      if {$passedOrSkipped == $eagle_tests(Total)} then {
        set exitCode Success

        if {$eagle_tests(Total) > 0} then {
          tresult Ok "OVERALL RESULT: SUCCESS\n"
        } else {
          tresult Ok "OVERALL RESULT: NONE\n"
        }
      } else {
        set exitCode Failure







        tresult Error "OVERALL RESULT: FAILURE\n"
      }

      unset passedOrSkipped
    } else {
      #
      # NOTE: They specified a non-default test pass threshold.  Check to
      #       make sure that we meet or exceed the requirement and then
      #       set the exit code to success; otherwise, set it to failure.
      #

      if {$percent >= $test_threshold} then {
        set exitCode Success

        if {$eagle_tests(Total) > 0} then {
          tresult Ok [appendArgs \
              "OVERALL RESULT: SUCCESS (" $percent "% >= " $test_threshold %)\n]

        } else {
          tresult Ok [appendArgs \
              "OVERALL RESULT: NONE (" $percent "% >= " $test_threshold %)\n]

        }
      } else {
        set exitCode Failure







        tresult Error [appendArgs \
            "OVERALL RESULT: FAILURE (" $percent "% < " $test_threshold %)\n]

      }
    }

    unset percent

    tputs $test_channel \n; # NOTE: Blank line.
  } else {







>
>
>
>










>
|









>
>
>
>
>
>











>
|




|
>


|
>




>
>
>
>
>
>

|
>







208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
      #
      set percent 0
    }

    #
    # NOTE: Has the test pass threshold been set?  If so, is it set to
    #       the default value?
    #
    # HACK: If the test suite error message exists, the entire run will be
    #       considered a "failure", without regard for the pass percentage
    #       or the configured test pass threshold.
    #
    if {![info exists test_threshold] || $test_threshold == 100} then {
      #
      # NOTE: The test pass threshold is set to the default value (100%).
      #       Check to make sure that all tests pass and then set the
      #       exit code to success; otherwise, we set it to failure.
      #
      set passedOrSkipped [expr {$eagle_tests(Passed) + \
          $eagle_tests(Skipped)}]

      if {![info exists test_suite_errors] && \
          $passedOrSkipped == $eagle_tests(Total)} then {
        set exitCode Success

        if {$eagle_tests(Total) > 0} then {
          tresult Ok "OVERALL RESULT: SUCCESS\n"
        } else {
          tresult Ok "OVERALL RESULT: NONE\n"
        }
      } else {
        set exitCode Failure

        if {[info exists test_suite_errors]} then {
          tresult Error [appendArgs "OVERALL ERRORS: " \
              [expr {[llength $test_suite_errors] > 0 ? \
              $test_suite_errors : "<empty>"}] \n]
        }

        tresult Error "OVERALL RESULT: FAILURE\n"
      }

      unset passedOrSkipped
    } else {
      #
      # NOTE: They specified a non-default test pass threshold.  Check to
      #       make sure that we meet or exceed the requirement and then
      #       set the exit code to success; otherwise, set it to failure.
      #
      if {![info exists test_suite_errors] && \
          $percent >= $test_threshold} then {
        set exitCode Success

        if {$eagle_tests(Total) > 0} then {
          tresult Ok [appendArgs \
              "OVERALL RESULT: SUCCESS (" \
              $percent "% >= " $test_threshold %)\n]
        } else {
          tresult Ok [appendArgs \
              "OVERALL RESULT: NONE (" \
              $percent "% >= " $test_threshold %)\n]
        }
      } else {
        set exitCode Failure

        if {[info exists test_suite_errors]} then {
          tresult Error [appendArgs "OVERALL ERRORS: " \
              [expr {[llength $test_suite_errors] > 0 ? \
              $test_suite_errors : "<empty>"}] \n]
        }

        tresult Error [appendArgs \
            "OVERALL RESULT: FAILURE (" \
            $percent "% < " $test_threshold %)\n]
      }
    }

    unset percent

    tputs $test_channel \n; # NOTE: Blank line.
  } else {
Changes to Externals/Eagle/lib/Test1.0/prologue.eagle.
22
23
24
25
26
27
28





29
30
31
32
33
34
35
  #
  # NOTE: Make sure all the variables used by this prologue are unset.
  #
  unset -nocomplain expr pkg_dir pattern dummy directory name value \
      exec encoding host memory stack drive server database timeout \
      user password percent checkout timeStamp loaded






  #
  # NOTE: Indicate that the test suite is currently running.
  #
  if {![info exists test_suite_running] || !$test_suite_running} then {
    set test_suite_running true
  }








>
>
>
>
>







22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
  #
  # NOTE: Make sure all the variables used by this prologue are unset.
  #
  unset -nocomplain expr pkg_dir pattern dummy directory name value \
      exec encoding host memory stack drive server database timeout \
      user password percent checkout timeStamp loaded

  #
  # NOTE: Remove any stale test suite error messages from prior runs.
  #
  unset -nocomplain test_suite_errors

  #
  # NOTE: Indicate that the test suite is currently running.
  #
  if {![info exists test_suite_running] || !$test_suite_running} then {
    set test_suite_running true
  }

1142
1143
1144
1145
1146
1147
1148







1149
1150
1151
1152
1153
1154
1155
    # NOTE: Check the image runtime version (i.e. the runtime version that
    #       this assembly compiled against).
    #
    if {![info exists no(imageRuntimeVersion)]} then {
      checkForImageRuntimeVersion $test_channel
    }








    #
    # NOTE: Has process bits detection support been disabled?
    #
    if {![info exists no(processBits)]} then {
      checkForProcessBits $test_channel
    }








>
>
>
>
>
>
>







1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
    # NOTE: Check the image runtime version (i.e. the runtime version that
    #       this assembly compiled against).
    #
    if {![info exists no(imageRuntimeVersion)]} then {
      checkForImageRuntimeVersion $test_channel
    }

    #
    # NOTE: Check if the image runtime version matches the framework.
    #
    if {![info exists no(matchingFrameworkVersion)]} then {
      checkForMatchingFrameworkVersion $test_channel
    }

    #
    # NOTE: Has process bits detection support been disabled?
    #
    if {![info exists no(processBits)]} then {
      checkForProcessBits $test_channel
    }

1632
1633
1634
1635
1636
1637
1638
1639
1640
1641
1642
1643
1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
        }

        #
        # NOTE: Has Tcl threading support been enabled (at compile-time)?
        #
        if {![info exists no(compileTclThreaded)]} then {
          #
          # NOTE: For tests "tclLoad-3.1" and "tclLoad-3.2".
          #
          checkForCompileOption $test_channel TCL_THREADED
        }

        #
        # NOTE: Has Tcl isolated interpreter thread support been enabled (at
        #       compile-time)?
        #
        if {![info exists no(compileTclThreads)]} then {
          #
          # NOTE: For tests "tclLoad-3.1" and "tclLoad-3.2".
          #
          checkForCompileOption $test_channel TCL_THREADS
        }

        #
        # NOTE: Has GDI+ drawing support been enabled (at compile-time)?
        #







|










|







1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663
1664
1665
1666
1667
1668
1669
        }

        #
        # NOTE: Has Tcl threading support been enabled (at compile-time)?
        #
        if {![info exists no(compileTclThreaded)]} then {
          #
          # NOTE: For tests "tclLoad-3.*".
          #
          checkForCompileOption $test_channel TCL_THREADED
        }

        #
        # NOTE: Has Tcl isolated interpreter thread support been enabled (at
        #       compile-time)?
        #
        if {![info exists no(compileTclThreads)]} then {
          #
          # NOTE: For tests "tclLoad-3.*".
          #
          checkForCompileOption $test_channel TCL_THREADS
        }

        #
        # NOTE: Has GDI+ drawing support been enabled (at compile-time)?
        #
2514
2515
2516
2517
2518
2519
2520
2521
2522
2523
2524
2525
2526
2527
2528
      checkForNativeUtility $test_channel
    }

    #
    # NOTE: Has Visual Studio testing support been disabled?
    #
    if {![info exists no(visualStudio)]} then {
      checkForVisualStudio $test_channel
    }

    #
    # NOTE: Has WiX testing support been disabled?
    #
    if {![info exists no(wix)]} then {
      #







|







2526
2527
2528
2529
2530
2531
2532
2533
2534
2535
2536
2537
2538
2539
2540
      checkForNativeUtility $test_channel
    }

    #
    # NOTE: Has Visual Studio testing support been disabled?
    #
    if {![info exists no(visualStudio)]} then {
      checkForVisualStudioViaRegistry $test_channel
    }

    #
    # NOTE: Has WiX testing support been disabled?
    #
    if {![info exists no(wix)]} then {
      #
2687
2688
2689
2690
2691
2692
2693







2694
2695
2696
2697
2698
2699
2700
  if {[info exists no(monoHacks)]} then {
    addKnownMonoConstraints true
    addKnownMonoConstraints false

    tputs $test_channel \
        "---- added all known Mono test constraints (forced)\n"
  }








  #
  # NOTE: Check for Eagle core library package names...
  #
  if {![info exists no(corePackageNames)]} then {
    checkForPackage $test_channel {^Eagle\._Plugins\.Core, .*$}
    checkForPackage $test_channel {^Eagle\._Plugins\.Object, .*$}







>
>
>
>
>
>
>







2699
2700
2701
2702
2703
2704
2705
2706
2707
2708
2709
2710
2711
2712
2713
2714
2715
2716
2717
2718
2719
  if {[info exists no(monoHacks)]} then {
    addKnownMonoConstraints true
    addKnownMonoConstraints false

    tputs $test_channel \
        "---- added all known Mono test constraints (forced)\n"
  }

  #
  # NOTE: Has Visual Studio testing support been disabled?
  #
  if {![info exists no(visualStudio)]} then {
    checkForVisualStudioViaVsWhere $test_channel
  }

  #
  # NOTE: Check for Eagle core library package names...
  #
  if {![info exists no(corePackageNames)]} then {
    checkForPackage $test_channel {^Eagle\._Plugins\.Core, .*$}
    checkForPackage $test_channel {^Eagle\._Plugins\.Object, .*$}
3264
3265
3266
3267
3268
3269
3270
3271
3272
3273
3274
3275
3276
3277
3278
3279
  # NOTE: Has namespace detection support been disabled?
  #
  if {![info exists no(namespaces)]} then {
    checkForNamespaces $test_channel [haveConstraint quiet]
  }

  #
  # NOTE: Check for various features that were added through
  #       the TIP process.
  #
  if {![info exists no(tip127)]} then {
    checkForTip127 $test_channel
  }

  if {![info exists no(tip194)]} then {
    checkForTip194 $test_channel







|
|







3283
3284
3285
3286
3287
3288
3289
3290
3291
3292
3293
3294
3295
3296
3297
3298
  # NOTE: Has namespace detection support been disabled?
  #
  if {![info exists no(namespaces)]} then {
    checkForNamespaces $test_channel [haveConstraint quiet]
  }

  #
  # NOTE: Check for various native Tcl features that were added
  #       (or simply proposed) through the TIP process.
  #
  if {![info exists no(tip127)]} then {
    checkForTip127 $test_channel
  }

  if {![info exists no(tip194)]} then {
    checkForTip194 $test_channel
3302
3303
3304
3305
3306
3307
3308












3309
3310
3311
3312
3313
3314
3315
  if {![info exists no(tip429)]} then {
    checkForTip429 $test_channel
  }

  if {![info exists no(tip440)]} then {
    checkForTip440 $test_channel
  }













  #
  # NOTE: Has performance testing been disabled?
  #
  if {![info exists no(core)] && \
      ![info exists no(checkForPerformance)]} then {
    checkForPerformance $test_channel







>
>
>
>
>
>
>
>
>
>
>
>







3321
3322
3323
3324
3325
3326
3327
3328
3329
3330
3331
3332
3333
3334
3335
3336
3337
3338
3339
3340
3341
3342
3343
3344
3345
3346
  if {![info exists no(tip429)]} then {
    checkForTip429 $test_channel
  }

  if {![info exists no(tip440)]} then {
    checkForTip440 $test_channel
  }

  if {![info exists no(tip461)]} then {
    checkForTip461 $test_channel
  }

  if {![info exists no(tip463)]} then {
    checkForTip463 $test_channel
  }

  if {![info exists no(tip471)]} then {
    checkForTip471 $test_channel
  }

  #
  # NOTE: Has performance testing been disabled?
  #
  if {![info exists no(core)] && \
      ![info exists no(checkForPerformance)]} then {
    checkForPerformance $test_channel