From: jwang36 Date: Thu, 21 Sep 2006 05:11:58 +0000 (+0000) Subject: 1) Add FileTimeStamp class to centralize the cache mechanism for file time stamp... X-Git-Tag: edk2-stable201903~24290 X-Git-Url: https://git.proxmox.com/?p=mirror_edk2.git;a=commitdiff_plain;h=4b1348478851a4b30978fabf9c4315cdbc44e99f 1) Add FileTimeStamp class to centralize the cache mechanism for file time stamp check, and changed related classes 2) Fixed the FlashMapTask dependency issue 3) Fixed empty target issue in OnDenpendency class git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@1584 6f19259b-4bc3-4df7-8a09-765794883524 --- diff --git a/Tools/Source/Common/org/tianocore/common/cache/FileTimeStamp.java b/Tools/Source/Common/org/tianocore/common/cache/FileTimeStamp.java new file mode 100644 index 0000000000..968d31f15c --- /dev/null +++ b/Tools/Source/Common/org/tianocore/common/cache/FileTimeStamp.java @@ -0,0 +1,83 @@ +/** @file +This file is to define the FileTimeStamp class for speeding up the dependency check. + +Copyright (c) 2006, Intel Corporation +All rights reserved. This program and the accompanying materials +are licensed and made available under the terms and conditions of the BSD License +which accompanies this distribution. The full text of the license may be found at +http://opensource.org/licenses/bsd-license.php + +THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +**/ +package org.tianocore.common.cache; + +import java.io.File; +import java.util.Map; +import java.util.TreeMap; +import java.util.HashMap; + +/** + FileTimeStamp class is used to cache the time stamp of accessing file, which + will speed up the dependency check for build + **/ +public class FileTimeStamp { + // + // cache the modified timestamp of files accessed, to speed up the depencey check + // + private static Map timeStampCache = new HashMap(); + + /** + Get the time stamp of given file. It will try the cache first and then + get from file system if no time stamp of the file is cached. + + @param file File name + + @return long The time stamp of the file + **/ + synchronized public static long get(String file) { + long timeStamp = 0; + + Long value = timeStampCache.get(file); + if (value != null) { + timeStamp = value.longValue(); + } else { + timeStamp = new File(file).lastModified(); + timeStampCache.put(file, new Long(timeStamp)); + } + + return timeStamp; + } + + /** + Force update the time stamp for the given file + + @param file File name + @param timeStamp The time stamp of the file + **/ + synchronized public static void update(String file, long timeStamp) { + timeStampCache.put(file, new Long(timeStamp)); + } + + /** + Force update the time stamp for the given file + + @param file File name + **/ + synchronized public static void update(String file) { + long timeStamp = new File(file).lastModified(); + timeStampCache.put(file, new Long(timeStamp)); + } + + /** + Check if the time stamp of given file has been cached for not + + @param file The file name + + @return boolean + **/ + synchronized public static boolean containsKey(String file) { + return timeStampCache.containsKey(file); + } +} diff --git a/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/FlashMapTask.java b/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/FlashMapTask.java index 5c3e88920a..c6f5099afa 100644 --- a/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/FlashMapTask.java +++ b/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/FlashMapTask.java @@ -17,6 +17,14 @@ package org.tianocore.framework.tasks; import java.io.File; +import java.io.FileReader; +import java.io.BufferedReader; + +import java.util.List; +import java.util.ArrayList; +import java.util.regex.Pattern; +import java.util.regex.Matcher; + import org.apache.tools.ant.Task; import org.apache.tools.ant.Project; import org.apache.tools.ant.BuildException; @@ -35,8 +43,14 @@ public class FlashMapTask extends Task implements EfiDefine { // // tool name // - private final String toolName = "FlashMap"; + private static final String toolName = "FlashMap"; + // + // + // + private static Pattern fileBlock = Pattern.compile("\\s*File\\s*\\{([^\\{\\}]+)\\}"); + private static Pattern fileNameDef = Pattern.compile("\\bName\\s*=\\s*\"([^\"]+)\""); + // // Flash definition file // @@ -135,7 +149,6 @@ public class FlashMapTask extends Task implements EfiDefine { @throws BuidException **/ public void execute() throws BuildException { - /* if (isUptodate()) { EdkLog.log(this, EdkLog.EDK_VERBOSE, headerFile.toFileList() + imageOutFile.toFileList() @@ -143,10 +156,9 @@ public class FlashMapTask extends Task implements EfiDefine { + dscFile.toFileList() + asmIncFile.toFileList() + outStrFile - + " is/are up-to-date!"); + + " is up-to-date!"); return; } - */ Project project = this.getOwningTarget().getProject(); // @@ -689,6 +701,13 @@ public class FlashMapTask extends Task implements EfiDefine { EdkLog.log(this, EdkLog.EDK_VERBOSE, srcName + " has been changed since last build!"); return false; } + + // + // we need to check the time stamp of each FV file specified in fdf file + // + if (!isFdUptodate(dstName, getFvFiles(flashDefFile.getValue()))) { + return false; + } } if (!mcoFile.isEmpty()) { @@ -749,4 +768,82 @@ public class FlashMapTask extends Task implements EfiDefine { return true; } + + // + // Parse the flash definition file and find out the FV file names + // + private List getFvFiles(String fdfFileName) { + File fdfFile = new File(fdfFileName); + int fileLength = (int)fdfFile.length(); + char[] fdfContent = new char[fileLength]; + List fileList = new ArrayList(); + + try { + FileReader reader = new FileReader(fdfFile); + BufferedReader in = new BufferedReader(reader); + + in.read(fdfContent, 0, fileLength); + String str = new String(fdfContent); + + // + // match the + // File { + // ... + // } + // block + // + Matcher matcher = fileBlock.matcher(str); + while (matcher.find()) { + String fileBlockContent = str.substring(matcher.start(1), matcher.end(1)); + // + // match the definition like + // Name = "..." + // + Matcher nameMatcher = fileNameDef.matcher(fileBlockContent); + if (nameMatcher.find()) { + fileList.add(fileBlockContent.substring(nameMatcher.start(1), nameMatcher.end(1))); + } + } + + in.close(); + reader.close(); + } catch (Exception ex) { + throw new BuildException(ex.getMessage()); + } + + return fileList; + } + + private boolean isFdUptodate(String fdFile, List fvFileList) { + String fvDir = "."; + File fd = new File(fdFile); + + if (outputDir.equals(".")) { + if (!fd.isAbsolute()) { + // + // If we cannot get the absolute path of fd file, we caanot + // get its time stamp. Re-generate it always in such situation. + // + EdkLog.log(this, EdkLog.EDK_VERBOSE, "Cannot retrieve the time stamp of " + fdFile); + return false; + } + fvDir = fd.getParent(); + } else { + fvDir = outputDir; + if (!fd.isAbsolute()) { + fd = new File(fvDir + File.separator + fdFile); + } + } + + long fdTimeStamp = fd.lastModified(); + for (int i = 0; i < fvFileList.size(); ++i) { + File fv = new File(fvDir + File.separator + fvFileList.get(i)); + if (fv.lastModified() > fdTimeStamp) { + EdkLog.log(this, EdkLog.EDK_VERBOSE, fv.getPath() + " has been changed since last build!"); + return false; + } + } + + return true; + } } diff --git a/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/MakeDeps.java b/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/MakeDeps.java index bd305fa079..1486bd384e 100644 --- a/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/MakeDeps.java +++ b/Tools/Source/FrameworkTasks/org/tianocore/framework/tasks/MakeDeps.java @@ -31,6 +31,7 @@ import org.apache.tools.ant.types.Commandline; import org.apache.tools.ant.types.Path; import org.tianocore.common.logger.EdkLog; +import org.tianocore.common.cache.FileTimeStamp; /** Class MakeDeps is used to wrap MakeDeps.exe as an ANT task. @@ -233,12 +234,12 @@ public class MakeDeps extends Task { // If the source file(s) is newer than dependency list file, we need to // re-generate the dependency list file // - long depsFileTimeStamp = df.lastModified(); + long depsFileTimeStamp = FileTimeStamp.get(dfName); List fileList = inputFileList.getNameList(); for (int i = 0, length = fileList.size(); i < length; ++i) { - File sf = new File(fileList.get(i)); - if (sf.lastModified() > depsFileTimeStamp) { - EdkLog.log(this, EdkLog.EDK_VERBOSE, sf.getPath() + " has been changed since last build!"); + String sf = fileList.get(i); + if (FileTimeStamp.get(sf) > depsFileTimeStamp) { + EdkLog.log(this, EdkLog.EDK_VERBOSE, sf + " has been changed since last build!"); return false; } } @@ -279,7 +280,7 @@ public class MakeDeps extends Task { // If a file cannot be found (moved or removed) or newer, regenerate the dep file // File sourceFile = new File(line); - if ((!sourceFile.exists()) || (sourceFile.lastModified() > depsFileTimeStamp)) { + if ((!sourceFile.exists()) || (FileTimeStamp.get(line) > depsFileTimeStamp)) { EdkLog.log(this, EdkLog.EDK_VERBOSE, sourceFile.getPath() + " has been (re)moved or changed since last build!"); ret = false; break; diff --git a/Tools/Source/GenBuild/org/tianocore/build/global/OnDependency.java b/Tools/Source/GenBuild/org/tianocore/build/global/OnDependency.java index 173528ab39..fbffb3bcb7 100644 --- a/Tools/Source/GenBuild/org/tianocore/build/global/OnDependency.java +++ b/Tools/Source/GenBuild/org/tianocore/build/global/OnDependency.java @@ -22,6 +22,7 @@ import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Task; import org.apache.tools.ant.taskdefs.Sequential; import org.tianocore.common.logger.EdkLog; +import org.tianocore.common.cache.FileTimeStamp; /** Class OnDepdendency is used to check the timestamp between source files and @@ -29,26 +30,24 @@ import org.tianocore.common.logger.EdkLog; be re-generated from source files. **/ public class OnDependency extends Task { - /// - /// cache the modified timestamp of files accessed, to speed up the depencey check - /// - private Map timeStampCache = new HashMap(); - /// - /// source files list - /// + // + // source files list + // private DpFileList sources = null; - /// - /// target files list - /// + + // + // target files list + // private DpFileList targets = null; - /// - /// tasks to be performed to generate target files - /// + + // + // tasks to be performed to generate target files + // private Sequential task = null; - /// - /// An empty constructor for an ANT task can avoid some potential issues - /// + /** + An empty constructor for an ANT task can avoid some potential issues + **/ public OnDependency(){ } @@ -59,11 +58,18 @@ public class OnDependency extends Task { if (isOutOfDate() && task != null) { task.perform(); } + + // + // Update the time stamp of target files since they are just re-generated + // + for (Iterator dstIt = targets.nameList.iterator(); dstIt.hasNext();) { + FileTimeStamp.update((String)dstIt.next()); + } } - /// - /// check if the target files are outofdate - /// + // + // check if the target files are outofdate + // private boolean isOutOfDate() { /// /// if no source files specified, take it as a fresh start @@ -87,21 +93,17 @@ public class OnDependency extends Task { return true; } - long dstTimeStamp = dstFile.lastModified(); + long dstTimeStamp = FileTimeStamp.get(dstFileName); Iterator srcIt = sources.nameList.iterator(); while (srcIt.hasNext()) { String srcFileName = (String)srcIt.next(); - long srcTimeStamp; - - if (timeStampCache.containsKey(srcFileName)) { - srcTimeStamp = ((Long)timeStampCache.get(srcFileName)).longValue(); - } else { - File srcFile = new File(srcFileName); - if (!srcFile.exists()) { - throw new BuildException("Source File name: " + srcFileName + " doesn't exist!!!"); - } - srcTimeStamp = srcFile.lastModified(); - timeStampCache.put(srcFileName, new Long(srcTimeStamp)); + long srcTimeStamp = FileTimeStamp.get(srcFileName); + + if (srcTimeStamp == 0) { + // + // time stamp 0 means that the file doesn't exist + // + throw new BuildException("Source File name: " + srcFileName + " doesn't exist!!!"); } if (dstTimeStamp < srcTimeStamp) {