pull up r19430 from trunk
authorTom Yu <tlyu@mit.edu>
Wed, 18 Apr 2007 22:15:07 +0000 (22:15 +0000)
committerTom Yu <tlyu@mit.edu>
Wed, 18 Apr 2007 22:15:07 +0000 (22:15 +0000)
 r19430@cathode-dark-space:  kpkoch | 2007-04-12 10:29:07 -0400
 Target_Version: 1.6.1
 Ticket: 5521
 Tags: pullup

 KfW build automation:

 Consolidate all command line switch info in one section of the config.xml, flatten structure.
 Don't prune .../site/... .
 Use getopts negate option where possible.
 New method of dealing with repository options, driven from config xml.
 Adjust code to find switches in new place.

 Hardwire default config to bkwconfig.xml.  Makes "bkw.pl" the out-of-the-box command line.
 Hardwire unixfind path to C:\tools\cygwin\bin.
 Add filver to required programs list.

 Update documentation.

ticket: 5521

git-svn-id: svn://anonsvn.mit.edu/krb5/branches/krb5-1-6@19494 dc483132-0cff-0310-8789-dd5450dbe970

src/windows/build/BKWconfig.xml
src/windows/build/bkw-automation.html
src/windows/build/bkw.pl
src/windows/build/copyfiles.pl
src/windows/build/makeZip.pl
src/windows/build/pruneFiles.pl
src/windows/build/signFiles.pl

index 35ba0565056fe4b7a2df1a27a4e4b75123565640..31294ea66994f7ebbc7f8e05f6f30ca98315efab 100644 (file)
@@ -1,38 +1,55 @@
 <?xml version="1.0" encoding="utf-8" ?>\r
 <!-- BKW: Build Kerberos for Windows -->\r
 <BKW_Config>\r
-    <CommandLine>\r
-        <!-- The most changeable parameters can be specified on the command line.    -->\r
-        <Tags>\r
-            <cvs        value="" />\r
-            <svntag     value="" />\r
-            <svnbranch  value="" />\r
-            </Tags>\r
-        <Directories>\r
-            <!--    Sources will be checked out of repositories into <src>.  The structure\r
-                    of the repositories will cause pismere/athena to be created under <src>.    -->\r
-            <src        path    ="C:\projects\Autobuild" />\r
-            <out        path    ="C:\projects\Autobuild\public" /> <!-- Must be absolute path. -->\r
-            </Directories>\r
-        <Options>\r
-            <debug      value="0" />\r
-            <logfile    value="1" path="bkw.pl.log" />\r
-            <repository value="skip" />\r
-            <clean      value="0" />\r
-            <nomake     value="0" />\r
-            <nopackage  value="0" />\r
-            <sign       value="0" />\r
-            <verbose    value="0" />\r
-            <vverbose   value="0" />\r
-            </Options>\r
-        </CommandLine>\r
+    <Config>\r
+        <!-- All the parameters are specified here.  They can be over-ridden\r
+                on the command line.\r
+\r
+            Parameters are grouped into Options, Directories, Repository and Environment.\r
+\r
+            Attributes a parameter can have:\r
+            def:  defined or not.  A value of 'A' for 'always' means the    \r
+               option can't be negated on the command line.                 \r
+            value:  string value, if the option can have a value.  If the option\r
+               can't take a value, omit the value attribute.\r
+            options:  space-delimited list, the 1st element is the default.\r
+               Synonyms for a valid option are concatenated with '|'.      \r
+            env: an environment variable will be set to value or deleted,  \r
+                depending on def.                                                    \r
+            -->\r
+        <!-- Options: -->\r
+        <clean      def="0" />\r
+        <debug      def="0" />\r
+        <help       def="0" />\r
+        <logfile    def="1" value="bkw.pl.log" />\r
+        <make       def="1" />\r
+        <package    def="1" />\r
+        <repository def="1" value="skip" options="skip checkout|co update|up" />\r
+        <sign       def="0" />\r
+        <verbose    def="0" />\r
+        <vverbose   def="0" />\r
+\r
+        <!-- Directory settings: -->\r
+        <!--    Sources will be checked out of repositories into <src>.  The structure\r
+                of the repositories will cause pismere/athena to be created under <src>.    -->\r
+        <src        def="A" value="C:\KfW" />        <!-- Must be absolute path. -->\r
+        <out        def="A" value="C:\KfW\public" /> <!-- Must be absolute path. -->\r
+\r
+        <!-- Repository settings: -->\r
+        <cvstag     def="0" value="" />\r
+        <svntag     def="0" value="" />\r
+        <svnbranch  def="0" value="" />\r
+        <CVSROOT    def="A" value=":kserver:cvs.mit.edu:/cvs/pismere" />\r
+        <SVNURL     def="A" value="svn.mit.edu" />   <!-- NB:  No protocol or slashes!! -->\r
+        <USERNAME   def="0" value="" />  <!-- Needed for svn/plink.  Override from command line -->\r
+\r
+        <!-- Environment variables: -->>\r
+        <KH_RELEASE def="1" env="1" value="OFFICIAL" options="OFFICIAL PRERELEASE PRIVATE" />\r
+        <NODEBUG    def="1" env="1" />  <!-- Interacts with /DEBUG -->\r
+        \r
+        </Config>\r
     <Stages>\r
         <FetchSources>\r
-            <Config>\r
-                <CVSROOT    name=":kserver:cvs.mit.edu:/cvs/pismere" />\r
-                <SVNURL     name="svn.mit.edu" />   <!-- NB:  No protocol or slashes!! -->\r
-                <USERNAME   name="" />              <!-- Needed for svn/plink.  Override from command line -->\r
-                </Config>\r
             <Zips>\r
                 <Zip dummy="foo" /> <!-- To force desired XML::Simple behavior    -->\r
                 <Zip name="SRC" filename="%filestem%-src.zip" topdir="%filestem%-final">\r
@@ -52,7 +69,7 @@
                         <Prune name="CVS" />\r
                         <Prune name=".cvsignore" flags="i" />\r
                         <Prune name="Changelog"  flags="i" />\r
-                        <Prune name="site" />\r
+<!--                        <Prune name="site" />   -->\r
                         </Prunes>\r
                     <Requires>\r
                         <Switch dummy="foo" />\r
index eb41053c5b1e28abcdbb32c8173927a375eb2bd5..d463df3a6bd389fc3e2b4bf68b7e30e2b9b0ae71 100644 (file)
 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">\r
-<!-- saved from url=(0066)https://confab.mit.edu/confluence/display/ISDA/lore-bkw-automation -->\r
-<HTML>\r
-       <HEAD>\r
-               <TITLE>lore-bkw-automation - Confluence</TITLE>\r
-               <META http-equiv="Content-Type" content="text/html; charset=utf-8">\r
-               <META http-equiv="Pragma" content="no-cache">\r
-               <META http-equiv="Expires" content="-1">\r
-               <LINK href="css/main-action.css" type="text/css" rel="stylesheet">\r
-                       <LINK href="css\main-action(1).css" type="text/css" rel="stylesheet">\r
-                               <META content="MSHTML 6.00.2900.3059" name="GENERATOR"></HEAD>\r
-       <BODY>\r
-               <DIV style="MARGIN-LEFT: 10px; MARGIN-RIGHT: 10px" align="left">\r
-                       <DIV class="wiki-content" style="MARGIN-TOP: 5px; MARGIN-BOTTOM: 5px" align="left">The \r
-                               Kerberos For Windows build is being automated. This description consists of\r
-                       </DIV>\r
-                       <UL>\r
-                               <LI>\r
-                                       <A href="#lore-bkw-automation-Buildsteps">Build steps</A>\r
-                               <LI>\r
-                                       <A href="#Script-structure">Script structure</A>\r
-                               <LI>\r
-                                       <A href="#Configfile">Config file</A>\r
-                               <LI>\r
-                                       <A href="#Remainingwork">Remaining work / bug list</A>\r
-                               <LI>\r
-                                       <A href="#Troubleshooting">Troubleshooting</A></LI>\r
-                       </UL>\r
-                       <H2><A name="lore-bkw-automation-Buildsteps"></A>Build steps</H2>\r
-                       <P>Building the complete KfW product consists of these steps:</P>\r
-                       <UL>\r
-                               <LI>\r
-                               Setting up the environment\r
-                               <LI>\r
-                               Fetching sources from repositories\r
-                               <LI>\r
-                               Building the sources with nmake\r
-                               <LI>\r
-                               Setting up the packaging environment\r
-                               <LI>\r
-                               Building the two installers -- a msi installer and an exe installer\r
-                               <LI>\r
-                                       Building other distribution components\r
-                                       <UL>\r
-                                               <LI>\r
-                                               KfW source distribution\r
-                                               <LI>\r
-                                               KfW core binaries\r
-                                               <LI>\r
-                                               KfW SDK\r
-                                               <LI>\r
-                                               Microsoft redistributable components\r
-                                               <LI>\r
-                                                       Individual files: release notes, Leash user guide, MSI Deployment Guide.\r
-                                               </LI>\r
-                                       </UL>\r
-                               </LI>\r
-                       </UL>\r
-                       <H2><A name="Script-structure"></A>Script structure</H2>\r
-                       <P>The build is a perl script controlled by command line switches and an XML \r
-                               configuration file. The config file is required. Settings in the config file \r
-                               can be overridden by optional command line switches.</P>\r
-                       <P>The main steps in the script are</P>\r
-                       <UL>\r
-                               <LI>\r
-                               Setting up the environment\r
-                               <LI>\r
-                               Fetching the sources from repositories\r
-                               <LI>\r
-                               Building the sources\r
-                               <LI>\r
-                               Setting up the packaging environment\r
-                               <LI>\r
-                               Building the msi with the package nmake\r
-                               <LI>\r
-                                       Building the rest of the components\r
-                               </LI>\r
-                       </UL>\r
-                       <P>The usage message shows the available switches:</P>\r
-                       <P><TT>C:\Projects\KfW&gt;perl bkw.pl /?</TT><BR>\r
-                               <TT>Usage: bkw.pl (-f --config) config-file [options] NMAKE-options</TT></P>\r
-                       <P><TT>Options are case insensitive.</TT></P>\r
-                       <P><TT>Options:</TT><BR>\r
-                               <TT>/help /? usage information (what you now see)</TT><BR>\r
-                               <TT>/srcdir dir&nbsp;&nbsp; Source directory to use. Should contain</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       pismere/athena. If cvstag or svntag is null,</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       the directory should be prepopulated.</TT><BR>\r
-                               <TT>/cvstag tag&nbsp;&nbsp; \ For whichever of these tags is specified,</TT><BR>\r
-                               <TT>/svntag url&nbsp;&nbsp; / a checkout will be done into srcdir</TT><BR>\r
-                               <TT>/debug&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Do debug make instead of \r
-                                       release make</TT><BR>\r
-                               <TT>/outdir dir&nbsp;&nbsp; Directory to be created where build results will go</TT><BR>\r
-                               <TT>/nomake&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Skip make step</TT><BR>\r
-                               <TT>/nopackage&nbsp;&nbsp;&nbsp;&nbsp;Skip packaging step</TT><BR>\r
-                               <TT>/clean&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Build clean target</TT><BR>\r
-                               <TT>/verbose&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Debug mode - verbose output</TT><BR>\r
-                               <TT>/vverbose&nbsp;&nbsp;&nbsp;&nbsp; very verbose output</TT><BR>\r
-                               <TT>/config path&nbsp; Path to config file</TT><BR>\r
-                               <TT>/logfile path Where to write output. If omitted, ...</TT><BR>\r
-                               <TT>/srcdir dir&nbsp;&nbsp; Source directory to use. Should contain\r
-                                       <BR>\r
-                                       &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TT><TT>pismere/athena. \r
-                                       If cvstag or svntag is null,\r
-                                       <BR>\r
-                                       &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       the directory should be prepopulated.\r
-                                       <BR>\r
-                               </TT><TT>/outdir dir&nbsp;&nbsp; Directory to be created where build results will \r
-                                       go\r
-                                       <BR>\r
-                                       /repository checkout | co \ What repository action to take.\r
-                                       <BR>\r
-                                       &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </TT><TT>update&nbsp;&nbsp; \r
-                                       | up | Options are to checkout, update or<BR>\r
-                                       &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;skip&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       / take no action [skip].\r
-                                       <BR>\r
-                                       /cvstag tag&nbsp;&nbsp; \ For whichever of these tags is specified,\r
-                                       <BR>\r
-                               </TT><TT>/svntag url&nbsp;&nbsp; / the repository action will be done into srcdir\r
-                                       <BR>\r
-                                       /debug&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Do debug make instead of \r
-                                       release make\r
-                                       <BR>\r
-                                       /nomake&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Skip make step\r
-                                       <BR>\r
-                                       /nopackage&nbsp;&nbsp;&nbsp; Skip packaging step\r
-                                       <BR>\r
-                                       /clean&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Build clean target\r
-                                       <BR>\r
-                                       /verbose&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Debug mode - verbose output\r
-                                       <BR>\r
-                                       /config path&nbsp; Path to config file\r
-                                       <BR>\r
-                                       /logfile path Where to write output. If omitted, ...<BR>\r
-                               </TT><TT>Other:</TT><BR>\r
-                               <TT>NMAKE-options any options you want to pass to NMAKE, which can be:</TT><BR>\r
-                               <TT>(note: /nologo is always used)</TT><BR>\r
-                               <TT>[ nmake options follow ]</TT></P>\r
-                       <P>Additional controls, not available from the command line:</P>\r
-                       <P><TT>&lt;CVSROOT name=":kserver:cvs.mit.edu:/cvs/pismere" /&gt;</TT><BR>\r
-                               <TT>&lt;SVNURL name="" /&gt;</TT><BR>\r
-                               <TT>&lt;CopyList&gt;&lt;Config&gt;&lt;DebugArea value="dbg" /&gt;</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       &lt;ReleaseArea value="rel" /&gt;</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;AlwaysTag \r
-                                       value="%bldtype%" /&gt;</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       &lt;DebugTag value="%debug%" /&gt;</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       &lt;ReleaseTag value="%release%" /&gt;</TT><BR>\r
-                               <TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
-                                       &lt;Files&gt;&lt;Include path="copyfiles.xml" /&gt;</TT></P>\r
-                       <P><TT><FONT face="Verdana">The pre-package steps gathers up build results and puts them in \r
-                                               a <FONT face="Courier">target</FONT> area.&nbsp; "target" is hardwired in the \r
-                                               build script.</FONT></TT></P>\r
-                       <P><TT><FONT face="Verdana">The post-package step zips up various files and then copies the \r
-                                               zips and other files to<FONT face="Courier"><EM>srcdir</EM></FONT>/<FONT face="Courier">public</FONT>.&nbsp; \r
-                                               "public" is hardwired in the build script.</FONT></TT></P>\r
-                       <H2><A name="#Configfile"></A>Config file</H2>\r
-                       <H3>\r
-                               CopyLists</H3>\r
-                       <P>\r
-                               CopyLists are used in many places.&nbsp;&nbsp;There is an optional \r
-                               Configuration section and a required Files section.&nbsp;</P>\r
-                       <P>The configuration section defines the roots of the from and to paths and can \r
-                               optionally define path substitutions.&nbsp;\r
-                       </P>\r
-                       <P>Internally, the to and from paths are required.&nbsp; They are forced by the \r
-                               script rather than being set in the config file.&nbsp; Comments in the copyfile \r
-                               xml indicate this.</P>\r
-                       <P>The overall build configuration specifies a debug or release build.&nbsp; The \r
-                               debug and release results are put in different places.&nbsp; File entries can \r
-                               indicate a variable part of a path with a tag such as %bldtype%.&nbsp; The \r
-                               script will substitute %bldtype% with either dbg or rel, depending on the build \r
-                               type.&nbsp; The substitution tags are specified with these declarations:</P>\r
-                       <P>\r
-                               <TABLE id="Table1" height="0" cellSpacing="1" cellPadding="1" border="1">\r
-                                       <TR>\r
-                                               <TD>DebugArea</TD>\r
-                                               <TD height="21">Path value used in debug build.&nbsp; Must match what the build \r
-                                                       script uses.&nbsp; Typically "dbg."</TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD>ReleaseArea</TD>\r
-                                               <TD height="9">Path value used in release build.&nbsp; Must match the build \r
-                                                       script.&nbsp; Typically "rel."</TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD>AlwaysTag</TD>\r
-                                               <TD height="17">String in file entries which will always be changed to either \r
-                                                       DebugArea or ReleaseArea. File is always copied.&nbsp; Typically "%bldtype%."</TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD>DebugTag</TD>\r
-                                               <TD>String in file entries which will only be changed to DebugArea during a debug \r
-                                                       build.&nbsp; File is only copied in a debug build.&nbsp; Typically "%debug%."</TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD>ReleaseTag</TD>\r
-                                               <TD>String in file entries which will only be changed to ReleaseArea during a \r
-                                                       release build.&nbsp; File is only copied in a release build.&nbsp; Typically \r
-                                                       "%release%."</TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD>FileStem</TD>\r
-                                               <TD>%filestem% will always be changed to FileStem.&nbsp; Example:&nbsp; \r
-                                                       "kfw-3-2-0."&nbsp; This is used in when building or copying the final build \r
-                                                       results.</TD>\r
-                                       </TR>\r
-                               </TABLE>\r
-                       </P>\r
-                       <P><STRONG>Example</STRONG></P>\r
-                       <P>Each segment of the file's path that comes from a different place is in a \r
-                               different color.</P>\r
-                       <P>\r
-                               Release build.&nbsp; Config file:\r
-                       </P>\r
-                       <P>\r
-                               <TABLE id="Table2" cellSpacing="1" cellPadding="1" border="0">\r
-                                       <TR>\r
-                                               <TD colspan="4"><FONT face="courier">&lt;BKW_Config&gt;</FONT></TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD width="23"></TD>\r
-                                               <TD colspan="3"><FONT face="courier">&lt;CommandLine&gt;</FONT></TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD width="23"></TD>\r
-                                               <TD width="20"></TD>\r
-                                               <TD colspan="2"><FONT face="courier">&lt;Directories&gt;</FONT></TD>\r
-                                       </TR>\r
-                                       <TR>\r
-                                               <TD width="23"></TD>\r
-                                               <TD width="20"></TD>\r
-                                               <TD width="22"></TD>\r
-                                               <TD><FONT face="courier">&lt;src path ="<FONT color="#000099">C:\projects\Autobuild"</FONT>\r
-                                                               /&gt;</FONT>\r
-                                               </TD>\r
-                                       </TR>\r
-                               </TABLE>\r
-                       </P>\r
-                       <P>Copylist comments:</P>\r
-                       <P class="code">\r
-                               &lt;!-- File from paths are relative to\r
-                               <src>\<FONT color="#ff00cc">pismere\athena</FONT> --&gt; \r
-<BR>  \r
-               &lt;!-- File to                 paths are relative to <src>\<FONT color="#00ff00">pismere\staging</FONT>\r
-                               --&gt;\r
-                       </P>\r
-                       <P>When the script processes this copylist, it will force the from and to paths as \r
-                               indicated.</P>\r
-                       <P>This line\r
-                       </P>\r
-                       <P class="code">&lt;File name="<FONT color="#00ffff">comerr32.dll</FONT>" from="<FONT color="#ff9933">..\target\bin\i386</FONT>\<FONT color="#ff0000">%bldtype%</FONT>\" \r
-                               to="\<FONT color="#9966ff">bin\i386</FONT>" /&gt;</P>\r
-                       <P>will result in <FONT face="Courier"><FONT color="#000099">C:\projects\Autobuild</FONT>\<FONT color="#ff00cc">pismere\athena</FONT>\<FONT color="#ff9933">..\target\bin\i386</FONT>\<FONT color="#ff0000">rel</FONT>\<FONT color="#00ffff">comerr32.dll</FONT></FONT></P>\r
-                       <P>being copied to <FONT face="Courier"><FONT color="#000099">C:\projects\Autobuild</FONT>\<FONT color="#00ff00">pismere\staging</FONT>\<FONT color="#9966ff">bin\i386</FONT>\<FONT color="#00ffff">comerr32.dll</FONT></FONT>.</P>\r
-                       <TT>\r
-                               <P>\r
-                                       Other possible attributes in a copylist entry:</P>\r
-                               <UL>\r
-                                       <LI>\r
-                                               <TT>notrequired</TT>\r
-                                       <LI>\r
-                                               <TT>newname="filename"</TT>\r
-                                       </LI>\r
-                               </UL>\r
-                               <P>By default, copylist entries are required and the script will die if they aren't \r
-                                       present. To ignore missing files, add <TT>notrequired</TT>.</P>\r
-                               <P>To rename the file, set the <TT>newname</TT> attribute.</P>\r
-                               <P>Lengthy copy lists can be kept in separate files and included with the Include \r
-                                       directive.&nbsp; Example:</P>\r
-                               <P class="code">&lt;Include path="sdkfiles.xml" /&gt;</P>\r
-                               <H2><FONT face="Verdana"><A name="Remainingwork"></A>Remaining work / bug list</FONT></H2>\r
-                               <P>This is a work in progress. What's left:</P>\r
-                               <P>Bugs:</P>\r
-                               <UL>\r
-                                       <LI>\r
-                                               <FONT face="Verdana">Eliminate need for redundant <TT>/debug debug</TT>. </FONT>\r
-                                       <LI>\r
-                                               <FONT face="Verdana">Handle checkout into non-existant directory.</FONT>\r
-                                       </LI>\r
-                               </UL>\r
-                               <H2><FONT face="Verdana"><A name="Troubleshooting"></A>Troubleshooting</FONT>\r
-                       </TT></H2>\r
-                       <P><TT><FONT face="Verdana"><STRONG>svn can't create tunnel:<BR>\r
-                                               </STRONG>Make sure environment variable SVN_SSH points to a valid \r
-                                               plink.exe.&nbsp; Path separators must be backslashes and must be doubled.</FONT></TT><TT></P>\r
-                       </TT>\r
-               </DIV>\r
-       </BODY>\r
+<!-- saved from url=(0066)https://confab.mit.edu/confluence/display/ISDA/lore-bkw-automation --><HTML><HEAD>\r
+        <TITLE>lore-bkw-automation - Confluence</TITLE>\r
+        <META http-equiv="Content-Type" content="text/html; charset=utf-8">\r
+        <META http-equiv="Pragma" content="no-cache">\r
+        <META http-equiv="Expires" content="-1">\r
+        <LINK href="css/main-action.css" type="text/css" rel="stylesheet">\r
+            <LINK href="css\main-action(1).css" type="text/css" rel="stylesheet">\r
+                <META content="MSHTML 6.00.2900.3059" name="GENERATOR"></HEAD>\r
+    <BODY>\r
+        <DIV style="MARGIN-LEFT: 10px; MARGIN-RIGHT: 10px" align="left">\r
+            <DIV class="wiki-content" style="MARGIN-TOP: 5px; MARGIN-BOTTOM: 5px" align="left">The \r
+                Kerberos for Windows (KfW) build is automated.&nbsp; A script will fetch the \r
+                sources from a repository and then build, sign and package all the KfW \r
+                distribution components.\r
+            </DIV>\r
+            <DIV class="wiki-content" style="MARGIN-TOP: 5px; MARGIN-BOTTOM: 5px" align="left">This \r
+                description consists of\r
+            </DIV>\r
+            <UL>\r
+                <LI>\r
+                    <A href="#Environment">Setting up the build environment</A>\r
+                <LI>\r
+                    <A href="#Running">Running the script</A>\r
+                <LI>\r
+                    <A href="Details">Script internal details</A>\r
+                <LI>\r
+                    <A href="#Remainingwork">Remaining work / bug list</A>\r
+                <LI>\r
+                    <A href="#Troubleshooting">Troubleshooting</A>\r
+                </LI>\r
+            </UL>\r
+            <H2>Setting Up the Build Environment</H2>\r
+            <P>KfW is built on a Windows PC, in the default Windows shell (cmd.exe). These \r
+                components must be installed:</P>\r
+            <UL>\r
+                <LI>\r
+                    Visual Studio 2003<BR>\r
+                Versions of Visual Studio before or after 2003 are not supported.\r
+                <LI>\r
+                    A recent release of the\r
+                    <SPAN class="nobr">\r
+                        <A href="http://www.microsoft.com/downloads/details.aspx?FamilyId=0BAF2B35-C656-4969-ACE8-E4C0C0716ADB&amp;displaylang=en">\r
+                            Microsoft Platform SDK</A></SPAN>\r
+                &nbsp;\r
+                <LI>\r
+                    <SPAN class="nobr">\r
+                        <A title="Visit page outside Confluence" href="http://www.activestate.com" rel="nofollow">\r
+                            ActiveState Perl 5.8 or more recent</A></SPAN><BR>\r
+                Build 631 is known to work.\r
+                <LI>\r
+                    <SPAN class="nobr">\r
+                        <A title="Visit page outside Confluence" href="http://www.doxygen.org/" rel="nofollow">\r
+                            Doxygen</A></SPAN>\r
+                <LI>\r
+                    sed, awk, cat, rm and find<BR>\r
+                    These can be obtained from the\r
+                    <SPAN class="nobr">\r
+                        <A title="Visit page outside Confluence" href="http://cygwin.com/" rel="nofollow">Cygwin \r
+                            distribution</A></SPAN>.\r
+                    <BR clear="all">\r
+                    <BR clear="all">\r
+                    find must be in C:\tools\cygwin\bin, so install Cygwin in C:\tools\cygwin.\r
+                    <BR>\r
+                    <BR>\r
+                    The cygwin awk is a link and the MS shell doesn't deal well with that.&nbsp; <TT>C</TT>\r
+                    opy <TT>c:\tools\cygwin\bin\gawk</TT> to <TT>c:\tools\cygwin\bin\awk</TT>.\r
+                <LI>\r
+                    <SPAN class="nobr">\r
+                        <A title="Visit page outside Confluence" href="http://sourceforge.net/project/showfiles.php?group_id=105970"\r
+                            rel="nofollow">Wix</A></SPAN>\r
+                <LI>\r
+                    <SPAN class="nobr">\r
+                        <A title="Visit page outside Confluence" href="http://nsis.sourceforge.net" rel="nofollow">\r
+                            NSIS</A></SPAN></LI></UL>\r
+            <H3>Environment variables</H3>\r
+            <P>\r
+                All the components above must be in PATH. Installing ActivePerl puts perl in \r
+                the PATH. Doxygen, Cygwin, hhc, wix and&nbsp;nsis need to be added.</P>\r
+            <P>perl must be installed so that .pl files are automatically executed with perl. \r
+                The ActivePerl installation will do this for you.</P>\r
+            <P>In the INCLUDE path, the Microsoft Platform SDK must come before the Microsoft \r
+                Visual C++ include files. Using a Platform SDK Build Environment window will \r
+                set this up the right way.&nbsp;</P>\r
+            <P>If you make your path modifications permanent via Control Panel / System / \r
+                Advanced / Environment Variables:&nbsp; If you use a Platform SDK Build \r
+                Environment window, it appears that you need to put your PATH components in the \r
+                System PATH, not the User PATH.</P>\r
+            <P>Visual Studio installs hhc in C:\Program Files\HTML Help Workshop.</P>\r
+            <P>nmake must be in PATH. If you use a Platform SDK build environment window, it is \r
+                already done for you.</P>\r
+            <h2>Running the Script<A name="Running"></A></h2>\r
+            <P>\r
+                The build is a perl script controlled by command line switches and an XML \r
+                configuration file. The config file is required. Settings in the config file \r
+                can be overridden by optional command line switches.&nbsp;</P>\r
+            <P>There are options for controlling most steps of the build process.&nbsp; The \r
+                steps are</P>\r
+            <UL>\r
+                <LI>\r
+                Verifying the environment\r
+                <LI>\r
+                Fetching the sources from repositories\r
+                <LI>\r
+                Building the sources\r
+                <LI>\r
+                Setting up the packaging environment\r
+                <LI>\r
+                Building the installers\r
+                <LI>\r
+                    Building the rest of the components\r
+                </LI>\r
+            </UL>\r
+            <P>The usage message shows the switches that control these steps:</P>\r
+            <P><TT>C:\Projects\KfW&gt;perl bkw.pl /?</TT><BR>\r
+                <TT>Usage: bkw.pl [options] NMAKE-options</TT></P>\r
+            <P><TT>&nbsp; Options are case insensitive. </TT>\r
+            </P>\r
+            <P><TT>&nbsp; Options:&nbsp;\r
+                    <BR>\r
+                </TT><TT>&nbsp; /help /?&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    usage information (what you now see).\r
+                    <BR>\r
+                    &nbsp; /config /f path&nbsp;&nbsp; Path to config file. Default is \r
+                    bkwconfig.xml.\r
+                    <BR>\r
+                    &nbsp; /src /r dir&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Source directory to use. \r
+                    Should contain\r
+                    <BR>\r
+                    &nbsp;&nbsp;&nbsp; \r
+                    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    pismere/athena. If cvstag or svntag is&nbsp;null,\r
+                    <BR>\r
+                    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    the directory should be prepopulated.\r
+                    <BR>\r
+                    &nbsp; /out /o dir&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Directory to be created \r
+                    where build results will go\r
+                    <BR>\r
+                </TT><TT>&nbsp; /repository checkout | co \ What repository action to take.\r
+                    <BR>\r
+                    &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    update&nbsp;&nbsp; | up&nbsp; ) Options are to checkout, update or\r
+                    <BR>\r
+                    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    skip&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;/ take no \r
+                    action [skip].\r
+                    <BR>\r
+                    &nbsp; /username /u name username used to access svn if checking out.\r
+                    <BR>\r
+                    &nbsp; /cvstag /c tag&nbsp;&nbsp;&nbsp; use -r &lt;tag&gt;\r
+                    <TAG>in cvs \r
+command <BR>&nbsp; /svnbranch /b tag use \r
+/branches/&lt;tag&gt;<TAG>&nbsp;instead of /trunk.<BR>&nbsp; /svntag /s tag&nbsp;&nbsp;&nbsp; use \r
+/tags/&lt;tag&gt;<TAG>&nbsp;instead of /trunk.<BR>&nbsp; /debug \r
+/d&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Do&nbsp;debug make instead of \r
+release make. <BR>&nbsp; \r
+/[no]make&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+Control the make \r
+step. <BR>&nbsp; \r
+/clean&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Build \r
+clean target. <BR>&nbsp; \r
+/[no]package&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Control the packaging step. <BR>&nbsp; \r
+/[no]sign&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Control \r
+signinf \r
+of executable&nbsp;files. <BR>&nbsp; /verbose \r
+/v&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Debug mode - verbose output. <BR>&nbsp; /logfile /l path&nbsp; Where to write output. \r
+Default is bkw.pl.log. <BR>&nbsp; \r
+                    /nolog&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Don't \r
+                    save output. </TT>\r
+            </P>\r
+            <P><TT>&nbsp; Other:\r
+                    <BR>\r
+                    &nbsp;&nbsp;&nbsp; NMAKE-options any options you want to pass to NMAKE, which \r
+                    can be:\r
+                    <BR>\r
+                    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; \r
+                    (note: /nologo is always used)<BR>\r
+                    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NODEBUG=1</TT></P>\r
+            <P><TT>NMAKE-options any options you want to pass to NMAKE, which can be:</TT><BR>\r
+                <TT>(note: /nologo is always used)</TT><BR>\r
+                <TT>[ nmake options follow ]</TT></P>\r
+            <P><BR>\r
+                Notes on the script steps:</P>\r
+            <P><STRONG>Verifying the environment</STRONG>:&nbsp;\r
+                <BR>\r
+                The script tests for each program that it needs and warns if the program isn't \r
+                found.</P>\r
+            <P><STRONG>Fetching sources from repositories</STRONG>:&nbsp;\r
+                <BR>\r
+                If building from a source distribution kit, this section does not apply.</P>\r
+            <P>CVSROOT and SVNURL must be specified in the configuration file.</P>\r
+            <P>A source zip file can only be produced if checking out fresh sources from a \r
+                repository.&nbsp;</P>\r
+            <P>If checking out, the entire pismere directory will be deleted.&nbsp; A warning \r
+                message requires that you confirm this action.</P>\r
+            <P><STRONG>Building the sources:</STRONG><BR>\r
+                /DEBUG controls whether a debug or release build is done.&nbsp; /CLEAN will \r
+                build the CLEAN target.</P>\r
+            <P><STRONG>Setting up the packaging environment :<BR>\r
+                </STRONG>The pre-package steps gathers up build results and puts them in a <FONT face="Courier">\r
+                    staging</FONT> area.&nbsp;\r
+            </P>\r
+            <P>If /SIGN is specified, <FONT face="Courier">.exe</FONT>s, <FONT face="Courier">.dll</FONT>s \r
+                and <FONT face="Courier">.cpl</FONT>s are signed.&nbsp; The signing command \r
+                template is in the configuration file.</P>\r
+            <P><STRONG>Building the installers:</STRONG><BR>\r
+                The <FONT face="Courier">staging </FONT>area is copied into a fresh area for \r
+                each of the installers.&nbsp; The installer results are copied back to the <FONT face="Courier">\r
+                    staging </FONT>area.</P>\r
+            <P><STRONG>Building the rest of the components:</STRONG><BR>\r
+                Zip files are built in temporary areas and copied to <FONT face="Courier">outdir</FONT>.&nbsp; \r
+                The installers and assorted files are copied from <FONT face="Courier">staging</FONT>\r
+                to <FONT face="Courier">outdir</FONT>.&nbsp; If /SIGN is specified, the \r
+                installers will be signed.</P>\r
+            <P>&nbsp;</P>\r
+            <H2><A name="Details"></A>Script Internal Details</H2>\r
+            <H3><A name="Copylists"></A>Copy Lists</H3>\r
+            <P>CopyLists are used in many places.&nbsp;&nbsp;For example, files to be put into \r
+                a .zip are copied to a fresh directory which is then zipped up.&nbsp; There is \r
+                an optional Configuration section and a required Files section.&nbsp;</P>\r
+            <P>The configuration section defines the roots of the from and to paths and can \r
+                optionally define path substitutions.&nbsp;\r
+            </P>\r
+            <P>The to and from paths are forced by the script rather than being set in the \r
+                config file.&nbsp; Comments in the copyfile xml indicate this.</P>\r
+            <P>Lengthy copy lists can be kept in separate files and included with the Include \r
+                directive.&nbsp; Example:</P>\r
+            <P><TT>&lt;Include path="sdkfiles.xml" /&gt;</TT></P>\r
+            <H3>Substitution tags</H3>\r
+            <P>Filenames in copylists can contain variable 'tags' that are replaced before the \r
+                file is copied.&nbsp; Some configuration files contain substitution tags which \r
+                customize the configuration.&nbsp; The supported tags are</P>\r
+            <P>\r
+                <TABLE id="Table3" height="0" cellSpacing="1" cellPadding="1" border="1">\r
+                    <TR>\r
+                        <TD width="136">%VERSION_MAJOR%</TD>\r
+                        <TD height="21">KfW Version from pismere/athena/include/kerberos.ver.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%VERSION_MINOR%</TD>\r
+                        <TD height="9">KfW Version from pismere/athena/include/kerberos.ver.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%VERSION_PATCH%</TD>\r
+                        <TD height="17">KfW Version from pismere/athena/include/kerberos.ver.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%filestem%</TD>\r
+                        <TD height="17">Defined as kfw-%VERSION_MAJOR%-%VERSION_MINOR%-%VERSION_PATCH%.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%debug%</TD>\r
+                        <TD>'dbg.'&nbsp; Only substituted during a debug build.&nbsp;</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%release%</TD>\r
+                        <TD>'rel.'&nbsp; Only substituted during a release build.&nbsp;\r
+                        </TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%bldtype%</TD>\r
+                        <TD>Always substituted, to 'dbg' or 'rel,' depending on the type of build.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%-DEBUG%</TD>\r
+                        <TD>'-DEBUG' during a debug build; otherwise empty.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%BUILDDIR%</TD>\r
+                        <TD>SRCDIR\pismere.&nbsp; Used in site-local installer configuration files.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%TARGETDIR%</TD>\r
+                        <TD>SRCDIR\pismere\staging.&nbsp; Used in site-local installer configuration files.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%CONFIGDIR-WIX%</TD>\r
+                        <TD>SRCDIR\pismere\staging\sample.&nbsp; Used in site-local installer configuration \r
+                            files.</TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="136">%CONFIGDIR-NSI%</TD>\r
+                        <TD>SRCDIR\pismere\staging.&nbsp; Used in site-local installer configuration files.</TD>\r
+                    </TR>\r
+                </TABLE>\r
+            </P>\r
+            <P>The overall build configuration specifies a debug or release build.&nbsp; Debug \r
+                and release results are put in different places.&nbsp; Files whose location \r
+                depend on the build type can use %bldtype% in their names.&nbsp; The script \r
+                will substitute %bldtype% with either dbg or rel, depending on the build \r
+                type.&nbsp;<STRONG></P>\r
+        </DIV>\r
+        <DIV style="MARGIN-LEFT: 10px; MARGIN-RIGHT: 10px" align="left">\r
+            <H3>Example</H3>\r
+            </STRONG>\r
+            <P>Here is&nbsp;a copylist entry.&nbsp; Each segment of the file's path that comes \r
+                from a different place is in a different color.</P>\r
+            <P>Release build.&nbsp; Config file:\r
+            </P>\r
+            <P>\r
+                <TABLE id="Table2" cellSpacing="1" cellPadding="1" border="0">\r
+                    <TR>\r
+                        <TD colSpan="4"><FONT face="courier">&lt;BKW_Config&gt;</FONT></TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="23"></TD>\r
+                        <TD colSpan="3"><FONT face="courier">&lt;CommandLine&gt;</FONT></TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="23"></TD>\r
+                        <TD width="20"></TD>\r
+                        <TD colSpan="2"><FONT face="courier">&lt;Directories&gt;</FONT></TD>\r
+                    </TR>\r
+                    <TR>\r
+                        <TD width="23"></TD>\r
+                        <TD width="20"></TD>\r
+                        <TD width="22"></TD>\r
+                        <TD><FONT face="courier">&lt;src path ="<FONT color="#000099">C:\bkw"</FONT> /&gt;</FONT>\r
+                        </TD>\r
+                    </TR>\r
+                </TABLE>\r
+            </P>\r
+            <P>Copylist comments:</P>\r
+            <P><tt>&lt;!-- File from paths are relative to\r
+                    <src>\<FONT color="#ff00cc">pismere\athena</FONT> --&gt; <BR>&lt;!-- File to paths are relative to <src>\<FONT color="#00ff00">\r
+                                pismere\staging</FONT>\r
+                    --&gt; </tt>\r
+            </P>\r
+            <P>When the script processes this copylist, it will force the from and to paths as \r
+                indicated.</P>\r
+            <P>This line\r
+            </P>\r
+            <P><tt>&lt;File name="<FONT color="#00ffff">comerr32.dll</FONT>" from="<FONT color="#ff9933">..\target\bin\i386</FONT>\<FONT color="#ff0000">%bldtype%</FONT>\" \r
+                    to="\<FONT color="#9966ff">bin\i386</FONT>" /&gt;</tt></P>\r
+            <P>will result in <FONT face="Courier"><FONT color="#000099">C:\bkw</FONT>\<FONT color="#ff00cc">pismere\athena</FONT>\<FONT color="#ff9933">..\target\bin\i386</FONT>\<FONT color="#ff0000">rel</FONT>\<FONT color="#00ffff">comerr32.dll</FONT></FONT></P>\r
+            <P>being copied to <FONT face="Courier"><FONT color="#000099">C:\bkw</FONT>\<FONT color="#00ff00">pismere\staging</FONT>\<FONT color="#9966ff">bin\i386</FONT>\<FONT color="#00ffff">comerr32.dll</FONT></FONT>.</P>\r
+            <P>Other possible attributes in a copylist entry:</P>\r
+            <UL>\r
+                <LI>\r
+                    <TT>notrequired</TT>\r
+                <LI>\r
+                    <TT>newname="filename"</TT>\r
+                </LI>\r
+            </UL>\r
+            <P>By default, copylist entries are required and the script will die if they aren't \r
+                present. To ignore missing files, add <TT>notrequired</TT>.</P>\r
+            <P>To rename the file, set the <TT>newname</TT> attribute.</P>\r
+            <H2><FONT face="Verdana"><A name="Remainingwork"></A>Remaining Work / Bug List</FONT></H2>\r
+            <P>Implement RETAIL, OFFICIAL, PRERELEASE, PRIVATE, SPECIAL.</P>\r
+            <P>Figure out what MIT_ONLY, BUILD_KFW, DEBUG_SYMBOL should be.</P>\r
+            <P>TARGET, APPVER.</P>\r
+            <P>NODEBUG=1.&nbsp; Set if release build.</P>\r
+            <H2><FONT face="Verdana"><A name="Troubleshooting"></A>Troubleshooting</FONT>\r
+            </H2>\r
+            <P><STRONG>Can't clean directory; can't delete file or directory</STRONG><BR>\r
+                Make sure a file in the named directory isn't open in another application.</P>\r
+        </DIV>\r
+    </BODY>\r
 </HTML>\r
index 2f7c6be1379ae4e8570dbf7caf4c583578cb31df..ea7c192ac942b8d049845a5d9223a5c2583fd4dd 100644 (file)
@@ -34,13 +34,13 @@ sub get_info {
 \r
 sub usage {\r
     print <<USAGE;\r
-Usage: $0 (-f --config) config-file [options] NMAKE-options\r
+Usage: $0 [options] NMAKE-options\r
 \r
   Options are case insensitive.\r
 \r
   Options:\r
     /help /?           usage information (what you now see).\r
-    /config /f path    Path to config file.\r
+    /config /f path    Path to config file.  Default is bkwconfig.xml.\r
     /srcdir /r dir     Source directory to use.  Should contain \r
                        pismere/athena.  If cvstag or svntag is null, \r
                        the directory should be prepopulated.\r
@@ -50,17 +50,16 @@ Usage: $0 (-f --config) config-file [options] NMAKE-options
                 skip          /  take no action [skip].\r
     /username /u name  username used to access svn if checking out.\r
     /cvstag /c tag     use -r <tag> in cvs command\r
-    /svnbranch /b tag  append /branches/<tag> to svn path.\r
-    /svntag /s tag     append /tags/<tag> to svn path.\r
+    /svnbranch /b tag  use /branches/<tag> instead of /trunk.\r
+    /svntag /s tag     use /tags/<tag> instead of /trunk.\r
     /debug /d          Do debug make instead of release make.\r
-    /nomake            Skip make step.\r
+    /[no]make          Control the make step.\r
     /clean             Build clean target.\r
-    /nopackage         Skip packaging step.\r
-    /sign              Sign files\r
-    /nosign            Don't sign files\r
+    /[no]package       Control the packaging step.\r
+    /[no]sign          Control signing of executable files.\r
     /verbose /v        Debug mode - verbose output.\r
-    /logfile /l path   Where to write output.  Default is bkw.pl.log\r
-    /nolog             Don't save output\r
+    /logfile /l path   Where to write output.  Default is bkw.pl.log.\r
+    /nolog             Don't save output.\r
   Other:\r
     NMAKE-options      any options you want to pass to NMAKE, which can be:\r
                        (note: /nologo is always used)\r
@@ -82,6 +81,9 @@ EOH
 }\r
 \r
 sub main {\r
+    local $cmdline = "bkw.pl";\r
+    foreach $arg (@ARGV) {$cmdline .= " $arg";}\r
+\r
     Getopt::Long::Configure('no_bundling', 'no_auto_abbrev',\r
            'no_getopt_compat', 'require_order',\r
            'ignore_case', 'pass_through',\r
@@ -92,21 +94,21 @@ sub main {
            'cvstag|c:s',\r
            'svntag|s:s',\r
            'svnbranch|b:s',\r
-           'srcdir|r:s',\r
-           'outdir|o:s',\r
+           'src|r:s',\r
+           'out|o:s',\r
            'debug|d',\r
-           'config|f:s',\r
+           'nodebug',\r
+           'config|f=s',\r
            'logfile|l:s',\r
            'nolog',\r
            'repository:s',\r
            'username|u:s',\r
            'verbose|v',\r
            'vverbose',\r
-           'nomake',\r
+           'make!',\r
            'clean',\r
-           'nopackage',\r
-           'sign',\r
-           'nosign',\r
+           'package!',\r
+           'sign!',\r
            );\r
 \r
     if ( $OPT->{help} ) {\r
@@ -114,17 +116,22 @@ sub main {
         exit(0);\r
         }\r
         \r
+    delete $OPT->{foo};        \r
+\r
 ##++ Validate required conditions:\r
 \r
-    if ($OPT->{config}) {}\r
-    else {\r
-        print "Fatal -- Configuration file must be specified.\n";\r
+    local $argvsize = @ARGV;\r
+    if ($argvsize > 0) {\r
+        print "Error -- invalid argument:  $ARGV[0]\n";\r
         usage();\r
-        exit(0);\r
+        die;\r
         }\r
+        \r
+    if (! exists $OPT->{config}) {$OPT->{config}  = "bkwconfig.xml";}\r
 \r
     # List of programs which must be in PATH:\r
-    my @required_list = ('sed', 'awk', 'which', 'cat', 'rm', 'cvs', 'svn', 'doxygen', 'hhc', 'candle', 'light', 'makensis', 'nmake', 'plink');\r
+    my @required_list = ('sed', 'awk', 'which', 'cat', 'rm', 'cvs', 'svn', 'doxygen', \r
+                         'hhc', 'candle', 'light', 'makensis', 'nmake', 'plink', 'filever');\r
     my $requirements_met    = 1;\r
     my $first_missing       = 0;\r
     my $error_list          = "";\r
@@ -161,66 +168,78 @@ sub main {
     # Get configuration file:\r
     my $xml = new XML::Simple();\r
     $config = $xml->XMLin($configfile);\r
-\r
     # Set up convenience variables:\r
-    my (@switches, @paths, @tags, @fetch);\r
-    @switches   = $config->{CommandLine}->{Options};\r
-    @paths      = $config->{CommandLine}->{Directories};\r
-    @tags       = $config->{CommandLine}->{Tags};\r
-    @fetch      = $config->{Stages}->{FetchSources}->{Config};\r
-\r
-    # Update the configuration with overrides from the command line:\r
-    $tags[0]->{cvs}->{value}            = $OPT->{cvstag}        if exists $OPT->{cvstag};\r
-    $tags[0]->{svntag}->{value}         = $OPT->{svntag}        if exists $OPT->{svntag};\r
-    $tags[0]->{svnbranch}->{value}      = $OPT->{svnbranch}     if exists $OPT->{svnbranch};\r
-    $paths[0]->{src}->{path}            = $OPT->{srcdir}        if exists $OPT->{srcdir};\r
-    $paths[0]->{out}->{path}            = $OPT->{outdir}        if exists $OPT->{outdir};\r
-    $switches[0]->{debug}->{value}      = $OPT->{debug}         if exists $OPT->{debug};\r
-    $switches[0]->{clean}->{value}      = 1                     if exists $OPT->{clean};\r
-    $switches[0]->{repository}->{value} = $OPT->{repository}    if exists $OPT->{repository};\r
-    $fetch[0]->{USERNAME}->{name}       = $OPT->{username}      if exists $OPT->{username};\r
-    $switches[0]->{nomake}->{value}     = 1                     if exists $OPT->{nomake};\r
-    $switches[0]->{nopackage}->{value}  = 1                     if exists $OPT->{nopackage};\r
-    $switches[0]->{verbose}->{value}    = $OPT->{verbose}       if exists $OPT->{verbose};\r
-    $switches[0]->{vverbose}->{value}   = $OPT->{verbose}       if exists $OPT->{vverbose};\r
-    if (exists $OPT->{logfile}) {\r
-        $switches[0]->{logfile}->{path} = $OPT->{logfile};\r
-        $switches[0]->{logfile}->{value} = 1;\r
-        }\r
-    if (exists $OPT->{nolog}) {\r
-        $switches[0]->{logfile}->{value} = 0;\r
-        }\r
-    if (exists $OPT->{sign}) {\r
-        $switches[0]->{sign}->{timestampserver} = $OPT->{sign};\r
-        $switches[0]->{sign}->{value} = 1;\r
-        }\r
-    if (exists $OPT->{nosign}) {\r
-        $switches[0]->{sign}->{value} = 0;\r
+    local $odr  = $config->{Config};    ## Options, directories, repository, environment.\r
+\r
+#while ($v = each %$OPT) {print "$v: $OPT->{$v}\n";}\r
+\r
+    # Scan the configuration for switch definitions:\r
+    while (($sw, $val) = each %$odr) {\r
+        next if (! exists $val->{def}); ## ?? Should always exist.\r
+        # If the switch is in the command line, override the stored value:\r
+        if (exists $OPT->{$sw}) {\r
+            if (exists $val->{value}) {\r
+                $val->{value}   = $OPT->{$sw};  \r
+                $val->{def}     = 1;\r
+                }\r
+            else {\r
+                $val->{def}   = $OPT->{$sw};    ## If no<switch>, value will be zero.\r
+                }\r
+            }\r
+        # If the switch can be negated, test that, too:\r
+        if ( ! ($val->{def} =~ /A/)) {\r
+            local $nosw = "no".$sw;\r
+            if (exists $OPT->{$nosw}) {\r
+                $val->{def} = 0;\r
+                }\r
+            }\r
+    \r
+        # For any switch definition with fixed values ("options"), validate:\r
+        if (exists $val->{options}) {\r
+            local $bValid   = 0;\r
+            # options can be like value1|syn1 value2|syn2|syn3\r
+            foreach $option (split(/ /, $val->{options})) {\r
+                local $bFirst   = 1;\r
+                local $sFirst;\r
+                foreach $opt (split(/\|/, $option)) {\r
+                    # opt will be like value2, syn2, syn3\r
+                    if ($bFirst) {\r
+                        $sFirst = $opt; ## Remember the full name of the option.\r
+                        $bFirst = 0;\r
+                        }\r
+                    if ($val->{value} =~ /$opt/i) {\r
+                        $val->{value} = $sFirst;    ## Save the full name.\r
+                        $bValid = 1;\r
+                        }\r
+                    }\r
+                }\r
+            if (! $bValid) {\r
+                print "Fatal -- invalid $sw value $val->{value}.  Possible values are $val->{options}.\n";\r
+                usage();\r
+                die;\r
+                }\r
+            }\r
         }\r
-    our $verbose    = $config->{CommandLine}->{Options}->{verbose}->{value};\r
-    our $vverbose   = $config->{CommandLine}->{Options}->{vverbose}->{value};\r
-    our $clean      = $switches[0]->{clean}->{value};\r
-    local $src      = $paths[0]->{src}->{path};\r
-    local $out      = $paths[0]->{out}->{path};\r
 \r
-    if ($clean && !$switches[0]->{nopackage}->{value}) {\r
+    # Set up convenience variables:\r
+    our $verbose    = $odr->{verbose}->{def};\r
+    our $vverbose   = $odr->{vverbose}->{def};\r
+    our $clean      = $clean->{clean}->{def};\r
+    local $src      = $odr->{src}->{value};\r
+    local $out      = $odr->{out}->{value};\r
+\r
+    if ($clean && $odr->{package}->{def}) {\r
         print "Info -- /clean forces /nopackage.\n";\r
-        $switches[0]->{nopackage}->{value} = 1;\r
+        $odr->{package}->{def} = 0;\r
         }\r
 \r
     if ($vverbose) {print "Debug -- Config: ".Dumper($config);}\r
     \r
-    # Examples of use:\r
-    #print "Logfile path: $switches[0]->{log}->{path}\n";\r
-    #print "src path: $paths[0]->{src}->{path}\n";\r
-    #print "cvs tag: $tags[0]->{cvs}->{value}\n";\r
-    #print "CVSROOT:   $fetch[0]->{CVSROOT}->{name}\n";\r
-\r
     # Test the unix find command:\r
-    if (! exists $config->{CommandLine}->{Directories}->{unixfind}->{path})    {\r
-        $config->{CommandLine}->{Directories}->{unixfind}->{path}   = "C:\\tools\\cygwin\\bin";\r
+    if (! exists $odr->{unixfind}->{value})    {\r
+        $odr->{unixfind}->{value}   = "C:\\tools\\cygwin\\bin";\r
         }\r
-    local $unixfind     = $config->{CommandLine}->{Directories}->{unixfind}->{path};\r
+    local $unixfind     = $odr->{unixfind}->{value};\r
 \r
     local $savedPATH    = $ENV{PATH};\r
     $ENV{PATH}          = $unixfind.";".$savedPATH;\r
@@ -234,38 +253,25 @@ sub main {
         }\r
         \r
     # Don't allow /svntag and /svnbranch simultaneously:\r
-    if ( (length $tags[0]->{svntag}->{value} > 0)   && \r
-         (length $tags[0]->{svnbranch}->{value} > 0) ) {\r
+    if ( (length $odr->{svntag}->{value} > 0)   && \r
+         (length $odr->{svnbranch}->{value} > 0) ) {\r
         die "Fatal -- Can't specify both /SVNTAG and /SVNBRANCH.";\r
         }\r
 \r
 ##-- Assemble configuration from config file and command line.\r
 \r
-    my $sw = $switches[0]->{repository}->{value};\r
-    my $rverb;\r
-    if       ($sw =~ /skip/i)       {$rverb = "skip";}\r
-    elsif    ($sw =~ /update/i)     {$rverb = "update";}\r
-    elsif    ($sw =~ /up/i)         {$rverb = "update";}\r
-    elsif    ($sw =~ /checkout/i)   {$rverb = "checkout";}\r
-    elsif    ($sw =~ /co/i)         {$rverb = "checkout";}\r
-    else {\r
-        print "Fatal -- invalid /repository value.\n";\r
-        usage();\r
-        die;\r
-        }\r
-    $switches[0]->{repository}->{value} = $rverb;   ## Save canonicalized repository verb.\r
-\r
+    local $rverb = $odr->{repository}->{value};\r
     if ( ($rverb =~ /checkout/) && $clean) {\r
         print "Warning -- Because sources afe being checked out, make clean will not be run.\n";\r
-        $clean  = $switches[0]->{clean}->{value}    = 0;\r
+        $clean  = $odr->{clean}->{def}    = 0;\r
         }\r
 \r
     my $wd  = $src."\\pismere";\r
 \r
     if (! ($rverb =~ /skip/)) {\r
         local $len = 0;\r
-        if (exists $fetch[0]->{USERNAME}->{name}) {\r
-            $len = length $fetch[0]->{USERNAME}->{name};\r
+        if (exists $odr->{USERNAME}->{value}) {\r
+            $len = length $odr->{USERNAME}->{value};\r
             }\r
         if ($len < 1) {\r
             die "Fatal -- you won't get far accessing the repository without specifying a username.";\r
@@ -285,13 +291,15 @@ sub main {
 \r
 # Begin logging:\r
     my $l;\r
-    if ($switches[0]->{logfile}->{value}) {\r
-        print "Info -- logging to $switches[0]->{logfile}->{path}.\n";\r
-        $l = new Logger $switches[0]->{logfile}->{path};\r
+    if ($odr->{logfile}->{def}) {\r
+        print "Info -- logging to $odr->{logfile}->{value}.\n";\r
+        $l = new Logger $odr->{logfile}->{value};\r
         $l->start;\r
         $l->no_die_handler;        ## Needed so XML::Simple won't throw exceptions.\r
         }\r
 \r
+    print "Executing $cmdline\n";\r
+       \r
 ##++ Begin repository action:\r
     if ($rverb =~ /skip/) {print "Info -- *** Skipping repository access.\n"    if ($verbose);}\r
     else {\r
@@ -305,12 +313,12 @@ sub main {
             }\r
         \r
         # Set up cvs environment variables:\r
-        $ENV{CVSROOT}       = $fetch[0]->{CVSROOT}->{name};\r
+        $ENV{CVSROOT}       = $odr->{CVSROOT}->{value};\r
         local $krb5dir      = "$wd\\athena\\auth\\krb5";\r
 \r
         local $cvscmdroot   = "cvs $rverb";\r
-        if (length $tags[0]->{cvs}->{value} > 0) {\r
-            $cvscmdroot .= " -r $tags[0]->{cvs}->{value}";\r
+        if (length $odr->{cvstag}->{value} > 0) {\r
+            $cvscmdroot .= " -r $odr->{cvstag}->{value}";\r
             }\r
 \r
         if ($rverb =~ /checkout/) {        \r
@@ -351,12 +359,12 @@ sub main {
         my $svncmd = "svn $rverb ";\r
         if ($rverb =~ /checkout/) {        # Append the rest of the checkout command:\r
             chdir("..");\r
-            $svncmd .= "svn+ssh://".$fetch[0]->{USERNAME}->{name}."@".$fetch[0]->{SVNURL}->{name}."/krb5/";\r
-            if (length $tags[0]->{svntag}->{value} > 0) {\r
-                $svncmd .= "tags/$tags[0]->{svntag}->{value}";\r
+            $svncmd .= "svn+ssh://".$odr->{USERNAME}->{value}."@".$odr->{SVNURL}->{value}."/krb5/";\r
+            if (length $odr->{svntag}->{value} > 0) {\r
+                $svncmd .= "tags/$odr->{svntag}->{value}";\r
                 }\r
-            elsif (length $tags[0]->{svnbranch}->{value} > 0) {\r
-                $svncmd .= "branches/$tags[0]->{svnbranch}->{value}";\r
+            elsif (length $odr->{svnbranch}->{value} > 0) {\r
+                $svncmd .= "branches/$odr->{svnbranch}->{value}";\r
                 }\r
             else {\r
                 $svncmd .= "trunk";\r
@@ -442,7 +450,7 @@ sub main {
 ##-- End  repository action, part 2.\r
 \r
 ##++ Make action:\r
-    if (    (!$switches[0]->{nomake}->{value}) ) {\r
+    if (    ($odr->{make}->{def}) ) {\r
         if ($verbose) {print "Info -- *** Begin preparing for build.\n";}\r
 \r
         chdir("$wd") or die "Fatal -- couldn't chdir to $wd\n";\r
@@ -482,8 +490,8 @@ sub main {
         \r
         chdir("$wd\\athena") or die "Fatal -- couldn't chdir to source directory $wd\\athena\n";\r
         print "Info -- chdir to ".`cd`."\n"         if ($verbose);\r
-        local $dbgswitch = ($switches[0]->{debug}->{value}) ? " " : "NODEBUG=1";\r
-        !system("perl ../scripts/build.pl --softdirs --nolog $buildtarget $dbgswitch")    or die "Fatal -- build $buildtarget failed.";\r
+        local $dbgswitch = ($odr->{debug}->{def}) ? " " : "NODEBUG=1";\r
+        !system("perl ../scripts/build.pl --softdirs --nolog $buildtarget $dbgswitch BUILD_OFFICIAL=1")    or die "Fatal -- build $buildtarget failed.";\r
             \r
         chdir("$wd")               or die "Fatal -- couldn't chdir to $wd.";\r
         if ($clean) {\r
@@ -498,7 +506,7 @@ sub main {
 ##-- Make action.\r
         \r
 ##++ Package action:\r
-    if ($switches[0]->{nopackage}->{value}) {      ## If /clean, nopackage will be set.\r
+    if (! $odr->{package}->{def}) {      ## If /clean, nopackage will be set.\r
         print "Info -- *** Skipping packaging.\n";\r
         if ((-d $out) && ! $bOutputCleaned) {\r
             print "Warning -- *** Output directory $out will not be cleaned.\n";\r
@@ -534,7 +542,7 @@ sub main {
         # Sign files:\r
         chdir($staging) or die "Fatal -- couldn't chdir to $staging\n";\r
         print "Info -- chdir to ".`cd`."\n"     if ($verbose);\r
-        if ($switches[0]->{sign}->{value}) {\r
+        if ($odr->{sign}->{def}) {\r
             signFiles($config->{Stages}->{PostPackage}->{Config}->{Signing}, $config);\r
             }\r
             \r
@@ -576,7 +584,7 @@ sub main {
         !system("sed -f ..\\wix\\$tmpfile site-local-tagged.nsi > b.tmp")   or die "Fatal -- Couldn't modify site-local.wxi.";\r
         !system("rm site-local-tagged.nsi")                                 or die "Fatal -- Couldn't remove site-local-tagged.nsi.";\r
         # Add DEBUG or RELEASE:\r
-        if ($switches[0]->{debug}->{value}) {                               ## debug build\r
+        if ($odr->{debug}->{def}) {                               ## debug build\r
             !system("echo !define DEBUG >> b.tmp")                          or die "Fatal -- Couldn't modify b.tmp.";    \r
             }\r
         else {                                                              ## release build\r
@@ -632,7 +640,7 @@ sub main {
         copyFiles($config->{Stages}->{PostPackage}->{CopyList}, $config);       ## Copy any files\r
 \r
         print "Info -- chdir to ".`cd`."\n"     if ($verbose);\r
-        if ($switches[0]->{sign}->{value}) {\r
+        if ($odr->{sign}->{def}) {\r
             signFiles($config->{Stages}->{PostPackage}->{Config}->{Signing}, $config);\r
             }\r
 \r
@@ -645,7 +653,7 @@ sub main {
     system("rm -rf $out/ziptemp");              ## Clean up junk.\r
 \r
 # End logging:\r
-    if ($switches[0]->{logfile}->{value})   {$l->stop;}\r
+    if ($odr->{logfile}->{def})   {$l->stop;}\r
 \r
     return 0;\r
     }                                           ## End subroutine main.\r
index 9160db07bc78b4327feea5d85401a6afaf41b5e5..79b6e156baae1aab5730ee80fd4f6bd5f62fd825 100644 (file)
@@ -6,7 +6,7 @@ use Data::Dumper;
 \r
 sub copyFiles {\r
     local ($xml, $config)   = @_;\r
-    local @switches         = $config->{CommandLine}->{Options};\r
+    local @odr              = $config->{Config};\r
     local @files            = $xml->{Files};\r
     # Check for includes:\r
     if (exists $xml->{Files}->{Include}->{path}) {\r
@@ -38,7 +38,7 @@ sub copyFiles {
     my $bPathTags    = (exists $xml->{Config}->{DebugArea}) && (exists $xml->{Config}->{ReleaseArea});\r
     my $bFileStem    = (exists $xml->{Config}->{FileStem});\r
     \r
-    if ($switches[0]->{debug}->{value}) {   ## Debug build tags:\r
+    if ($odr->{debug}->{def}) {   ## Debug build tags:\r
         $PathFragment       = $xml->{Config}->{DebugArea}->{value};\r
         $BuildDependentTag  = $xml->{Config}->{DebugTag}->{value};\r
         $IgnoreTag          = $xml->{Config}->{ReleaseTag}->{value};\r
@@ -84,7 +84,7 @@ sub copyFiles {
                     $to     =~ s/%filestem%/$FileStemFragment/g;\r
                     }        \r
                 # %-DEBUG% substitution:\r
-                local $DebugFragment    = ($switches[0]->{debug}->{value}) ? "-DEBUG" : "";\r
+                local $DebugFragment    = ($odr->{debug}->{def}) ? "-DEBUG" : "";\r
                 $from       =~ s/%\-DEBUG%/$DebugFragment/g;\r
                 $to         =~ s/%\-DEBUG%/$DebugFragment/g;\r
                 $to         =~ s/\*.*//;                ## Truncate to path before any wildcard\r
index 12215ddcd66e1ade352fd4317672a8c7f0800b92..1a1b533c33feb80a7ebfe5da3cb6e4797ab21577 100644 (file)
@@ -9,15 +9,15 @@ use Data::Dumper;
 sub makeZip {\r
     local ($zip, $config)   = @_;\r
 \r
-    local $src          = $config->{CommandLine}->{Directories}->{src}->{path};\r
-    local $out          = $config->{CommandLine}->{Directories}->{out}->{path};\r
-    local @switches     = $config->{CommandLine}->{Options};\r
-    local $zipname      = $zip->{filename};\r
-    local $filestem     = $config->{Stages}->{PostPackage}->{Config}->{FileStem}->{name};\r
-    $zipname            =~ s/%filestem%/$filestem/g;\r
+    local $odr      = $config->{Config};    ## Options, directories, repository, environment.\r
+    local $src      = $odr->{src}->{value};\r
+    local $out      = $odr->{out}->{value};\r
+    local $zipname  = $zip->{filename};\r
+    local $filestem = $config->{Stages}->{PostPackage}->{Config}->{FileStem}->{name};\r
+    $zipname        =~ s/%filestem%/$filestem/g;\r
     if (exists $zip->{Requires}) {\r
         local $bMakeIt  = 1;\r
-        local $rverb    = $switches[0]->{repository}->{value};\r
+        local $rverb    = $odr->{repository}->{value};\r
         local $j        = 0;\r
         while ($zip->{Requires}->{Switch}[$j]) {                    ## Check Require switches\r
             local $switch    = $zip->{Requires}->{Switch}[$j];\r
index 2406c770ec172bd7c2a42d64edcbc7deb8cef5c2..a62da536e8f16e2a57c2549d2f49f650208b8d8b 100644 (file)
@@ -10,7 +10,7 @@ sub pruneFiles {
     \r
     # Use Unix find instead of Windows find.  Save PATH so we can restore it when we're done:\r
     local $savedPATH    = $ENV{PATH};\r
-    $ENV{PATH}          = $config->{CommandLine}->{Directories}->{unixfind}->{path}.";".$savedPATH;\r
+    $ENV{PATH}          = $config->{Config}->{Directories}->{unixfind}->{path}.";".$savedPATH;\r
     local $j=0;\r
     print "Info -- Processing prunes in ".`cd`."\n"     if ($verbose);\r
     while ($prunes->{Prune}->[$j]) {\r
index d2ffb2c0e3541408024fea7e6359782349d330f0..65ccb0a11cd1efe9d0aa39f13c208255acb5dcc4 100644 (file)
@@ -9,7 +9,7 @@ sub signFiles {
     local $template = $signing->{CommandTemplate}->{value};\r
     # Use Unix find instead of Windows find.  Save PATH so we can restore it when we're done:\r
     local $savedPATH= $ENV{PATH};\r
-    $ENV{PATH}      = $config->{CommandLine}->{Directories}->{unixfind}->{path}.";".$savedPATH;\r
+    $ENV{PATH}      = $config->{Config}->{unixfind}->{value}.";".$savedPATH;\r
     foreach $expr (split(" ", $exprs)) {            ## exprs is something like "*.exe *.dll"\r
         local $cmd  = "find . -iname \"$expr\"";\r
         local $list = `$cmd`;                       ## $list is files matching *.exe, for example.\r