1 // 2 // ReservedNameUtils.cs 3 // 4 // Author: 5 // Marek Sieradzki (marek.sieradzki@gmail.com) 6 // 7 // (C) 2006 Marek Sieradzki 8 // 9 // Permission is hereby granted, free of charge, to any person obtaining 10 // a copy of this software and associated documentation files (the 11 // "Software"), to deal in the Software without restriction, including 12 // without limitation the rights to use, copy, modify, merge, publish, 13 // distribute, sublicense, and/or sell copies of the Software, and to 14 // permit persons to whom the Software is furnished to do so, subject to 15 // the following conditions: 16 // 17 // The above copyright notice and this permission notice shall be 18 // included in all copies or substantial portions of the Software. 19 // 20 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 21 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 22 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 23 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 24 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 25 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 26 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 27 28 using System; 29 using System.Collections; 30 using System.Collections.Specialized; 31 using System.IO; 32 using System.Text; 33 34 namespace Mono.XBuild.Utilities { 35 36 internal static class ReservedNameUtils { 37 38 static string[] reservedMetadataNames; 39 static Hashtable reservedMetadataHash; 40 ReservedNameUtils()41 static ReservedNameUtils () 42 { 43 reservedMetadataNames = new string [] { 44 "FullPath", "RootDir", "Filename", "Extension", "RelativeDir", "Directory", 45 "RecursiveDir", "Identity", "ModifiedTime", "CreatedTime", "AccessedTime"}; 46 reservedMetadataHash = CollectionsUtil.CreateCaseInsensitiveHashtable (ReservedMetadataNameCount); 47 foreach (string s in reservedMetadataNames) { 48 reservedMetadataHash.Add (s, null); 49 } 50 } 51 52 public static ICollection ReservedMetadataNames { 53 get { 54 return (ICollection) reservedMetadataNames.Clone (); 55 } 56 } 57 58 public static int ReservedMetadataNameCount { 59 get { 60 return reservedMetadataNames.Length; 61 } 62 } 63 IsReservedMetadataName(string metadataName)64 public static bool IsReservedMetadataName (string metadataName) 65 { 66 return reservedMetadataHash.Contains (metadataName); 67 } 68 GetReservedMetadata(string itemSpec, string metadataName, IDictionary metadata)69 public static string GetReservedMetadata (string itemSpec, 70 string metadataName, IDictionary metadata) 71 { 72 if (metadataName == null) 73 throw new ArgumentNullException (); 74 75 if (String.IsNullOrEmpty (itemSpec)) 76 return String.Empty; 77 78 switch (metadataName.ToLowerInvariant ()) { 79 case "fullpath": 80 var unescapedItemSpec = MSBuildUtils.Unescape (itemSpec); 81 return MSBuildUtils.Escape (Path.GetFullPath (unescapedItemSpec)); 82 case "rootdir": 83 if (Path.IsPathRooted (itemSpec)) 84 return Path.GetPathRoot (itemSpec); 85 else 86 return Path.GetPathRoot (Environment.CurrentDirectory); 87 case "filename": 88 return Path.GetFileNameWithoutExtension (itemSpec); 89 case "extension": 90 return Path.GetExtension (itemSpec); 91 case "relativedir": 92 return WithTrailingSlash (AbsoluteToRelativePath (Environment.CurrentDirectory, Path.GetDirectoryName (itemSpec))); 93 case "directory": 94 string fullpath = Path.GetFullPath (itemSpec); 95 return WithTrailingSlash ( 96 Path.GetDirectoryName (fullpath).Substring (Path.GetPathRoot (fullpath).Length)); 97 case "recursivedir": 98 if (metadata != null && metadata.Contains ("RecursiveDir")) 99 return (string)metadata ["RecursiveDir"]; 100 else 101 return String.Empty; 102 case "identity": 103 return itemSpec; 104 case "modifiedtime": 105 if (File.Exists (itemSpec)) 106 return File.GetLastWriteTime (itemSpec).ToString (); 107 else if (Directory.Exists (itemSpec)) 108 return Directory.GetLastWriteTime (itemSpec).ToString (); 109 else 110 return String.Empty; 111 case "createdtime": 112 if (File.Exists (itemSpec)) 113 return File.GetCreationTime (itemSpec).ToString (); 114 else if (Directory.Exists (itemSpec)) 115 return Directory.GetCreationTime (itemSpec).ToString (); 116 else 117 return String.Empty; 118 case "accessedtime": 119 if (File.Exists (itemSpec)) 120 return File.GetLastAccessTime (itemSpec).ToString (); 121 else if (Directory.Exists (itemSpec)) 122 return Directory.GetLastAccessTime (itemSpec).ToString (); 123 else 124 return String.Empty; 125 default: 126 throw new ArgumentException ("Invalid reserved metadata name"); 127 } 128 } 129 WithTrailingSlash(string path)130 static string WithTrailingSlash (string path) 131 { 132 if (String.IsNullOrEmpty (path)) 133 return String.Empty; 134 135 if (path.Length > 0) 136 return path + Path.DirectorySeparatorChar; 137 else 138 return path; 139 } 140 141 readonly static char[] separators = { Path.DirectorySeparatorChar, Path.VolumeSeparatorChar, Path.AltDirectorySeparatorChar }; AbsoluteToRelativePath(string baseDirectoryPath, string absPath)142 static string AbsoluteToRelativePath (string baseDirectoryPath, string absPath) 143 { 144 if (!Path.IsPathRooted (absPath)) 145 return absPath; 146 147 absPath = Path.GetFullPath (absPath); 148 baseDirectoryPath = Path.GetFullPath (baseDirectoryPath.TrimEnd (Path.DirectorySeparatorChar)); 149 150 string[] bPath = baseDirectoryPath.Split (separators); 151 string[] aPath = absPath.Split (separators); 152 int indx = 0; 153 154 for (; indx < System.Math.Min (bPath.Length, aPath.Length); indx++) { 155 if (!bPath[indx].Equals(aPath[indx])) 156 break; 157 } 158 159 if (indx == 0) 160 return absPath; 161 162 StringBuilder result = new StringBuilder (); 163 164 for (int i = indx; i < bPath.Length; i++) { 165 result.Append (".."); 166 if (i + 1 < bPath.Length || aPath.Length - indx > 0) 167 result.Append (Path.DirectorySeparatorChar); 168 } 169 170 171 result.Append (String.Join(Path.DirectorySeparatorChar.ToString(), aPath, indx, aPath.Length - indx)); 172 if (result.Length == 0) 173 return "."; 174 return result.ToString (); 175 } 176 RelativeToAbsolutePath(string baseDirectoryPath, string relPath)177 static string RelativeToAbsolutePath (string baseDirectoryPath, string relPath) 178 { 179 return Path.GetFullPath (Path.Combine (baseDirectoryPath, relPath)); 180 } 181 } 182 } 183