1 /*
   2  * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 import static java.nio.file.FileVisitResult.CONTINUE;
  26 
  27 import java.io.IOException;
  28 import java.nio.file.FileSystems;
  29 import java.nio.file.FileVisitResult;
  30 import java.nio.file.Files;
  31 import java.nio.file.Path;
  32 import java.nio.file.attribute.BasicFileAttributes;
  33 import java.util.Stack;
  34 import java.util.Vector;
  35 
  36 public class FileTreeCreatorVC10 extends FileTreeCreator {
  37 
  38       public FileTreeCreatorVC10(Path startDir, Vector<BuildConfig> allConfigs, WinGammaPlatformVC10 wg) {
  39          super(startDir, allConfigs, wg);
  40       }
  41 
  42       @Override
  43       public FileVisitResult visitFile(Path file, BasicFileAttributes attr) {
  44          DirAttributes currentFileAttr = attributes.peek().clone();
  45          boolean usePch = false;
  46          boolean disablePch = false;
  47          boolean useIgnore = false;
  48          boolean isAltSrc = false;  // only needed as a debugging crumb
  49          boolean isReplacedByAltSrc = false;
  50          String fileName = file.getFileName().toString();
  51 
  52          // TODO hideFile
  53 
  54          // usePch applies to all configs for a file.
  55          if (fileName.equals(BuildConfig.getFieldString(null, "UseToGeneratePch"))) {
  56             usePch = true;
  57          }
  58 
  59          String fileLoc = vcProjLocation.relativize(file).toString();
  60 
  61          // isAltSrc and isReplacedByAltSrc applies to all configs for a file
  62          if (BuildConfig.matchesRelativeAltSrcInclude(
  63                file.toAbsolutePath().toString())) {
  64             // current file is an alternate source file so track it
  65             isAltSrc = true;
  66             BuildConfig.trackRelativeAltSrcFile(
  67                 file.toAbsolutePath().toString());
  68          } else if (BuildConfig.matchesRelativeAltSrcFile(
  69                     file.toAbsolutePath().toString())) {
  70             // current file is a regular file that matches an alternate
  71             // source file so yack about replacing the regular file
  72             isReplacedByAltSrc = true;
  73             System.out.println("INFO: alternate source file '" +
  74                                BuildConfig.getMatchingRelativeAltSrcFile(
  75                                    file.toAbsolutePath().toString()) +
  76                                "' replaces '" + fileLoc + "'");
  77          }
  78 
  79          for (BuildConfig cfg : allConfigs) {
  80             if (cfg.lookupHashFieldInContext("IgnoreFile", fileName) != null) {
  81                useIgnore = true;
  82                currentFileAttr.setIgnore(cfg);
  83             } else if (cfg.matchesIgnoredPath(file.toAbsolutePath().toString())) {
  84                useIgnore = true;
  85                currentFileAttr.setIgnore(cfg);
  86             }
  87 
  88             if (cfg.lookupHashFieldInContext("DisablePch", fileName) != null) {
  89                disablePch = true;
  90                currentFileAttr.setDisablePch(cfg);
  91             }
  92 
  93             Vector<String> rv = new Vector<String>();
  94             cfg.collectRelevantVectors(rv, "AdditionalFile");
  95             for(String addFile : rv) {
  96                if (addFile.equals(fileName)) {
  97                   // supress any ignore
  98                   // TODO - may need some adjustments
  99                   if (file.toAbsolutePath().toString().contains(cfg.get("Flavour"))) {
 100                      currentFileAttr.removeFromIgnored(cfg);
 101                   }
 102                }
 103             }
 104          }
 105 
 106          String tagName = wg.getFileTagFromSuffix(fileName);
 107 
 108          if (!useIgnore && !disablePch && !usePch && !isReplacedByAltSrc) {
 109             wg.tag(tagName, new String[] { "Include", fileLoc});
 110          } else {
 111             wg.startTag(
 112                   tagName,
 113                   new String[] { "Include", fileLoc});
 114 
 115             for (BuildConfig cfg : allConfigs) {
 116                boolean ignore = currentFileAttr.hasIgnore(cfg);
 117                if (ignore) {
 118                   wg.tagData("ExcludedFromBuild", "true", "Condition", "'$(Configuration)|$(Platform)'=='" + cfg.get("Name") + "'");
 119                }
 120                if (usePch) {
 121                   wg.tagData("PrecompiledHeader", "Create", "Condition", "'$(Configuration)|$(Platform)'=='" + cfg.get("Name") + "'");
 122                }
 123                if (disablePch) {
 124                   wg.tag("PrecompiledHeader", "Condition", "'$(Configuration)|$(Platform)'=='" + cfg.get("Name") + "'");
 125                }
 126                if (isReplacedByAltSrc) {
 127                   wg.tagData("ExcludedFromBuild", "true", "Condition",
 128                              "'$(Configuration)|$(Platform)'=='" +
 129                              cfg.get("Name") + "'");
 130                }
 131             }
 132             wg.endTag();
 133          }
 134 
 135          String filter = startDir.relativize(file.getParent().toAbsolutePath()).toString();
 136          wg.addFilterDependency(fileLoc, filter);
 137 
 138          return CONTINUE;
 139       }
 140 
 141       @Override
 142       public FileVisitResult preVisitDirectory(Path path, BasicFileAttributes attrs)
 143             throws IOException {
 144          Boolean hide = false;
 145          // TODO remove attrs, if path is matched in this dir, then it is too in every subdir.
 146          // And we will check anyway
 147          DirAttributes newAttr = attributes.peek().clone();
 148 
 149          // check per config ignorePaths!
 150          for (BuildConfig cfg : allConfigs) {
 151             if (cfg.matchesIgnoredPath(path.toAbsolutePath().toString())) {
 152                newAttr.setIgnore(cfg);
 153             }
 154 
 155             // Hide is always on all configs. And additional files are never hiddden
 156             if (cfg.matchesHidePath(path.toAbsolutePath().toString())) {
 157                hide = true;
 158                break;
 159             }
 160          }
 161 
 162          if (!hide) {
 163             String name = startDir.relativize(path.toAbsolutePath()).toString();
 164             if (!"".equals(name)) {
 165                wg.addFilter(name);
 166             }
 167 
 168             attributes.push(newAttr);
 169             return super.preVisitDirectory(path, attrs);
 170          } else {
 171             return FileVisitResult.SKIP_SUBTREE;
 172          }
 173       }
 174 
 175       @Override
 176       public FileVisitResult postVisitDirectory(Path dir, IOException exc) {
 177          //end matching attributes set by ignorepath
 178          attributes.pop();
 179          return CONTINUE;
 180       }
 181 
 182       @Override
 183       public FileVisitResult visitFileFailed(Path file, IOException exc) {
 184          return CONTINUE;
 185       }
 186 
 187       public void writeFileTree() throws IOException {
 188          Files.walkFileTree(this.startDir, this);
 189       }
 190 }