[xbuild] Copy metadata from Project items to target outputs.
[mono.git] / mcs / class / Microsoft.Build.Tasks / Microsoft.Build.Tasks / Utilities.cs
1 //
2 // Utilities.cs:
3 //
4 // Author:
5 //      Ankit Jain (jankit@novell.com)
6 //
7 // Copyright (c) 2009 Novell, Inc (http://www.novell.com)
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 #if NET_2_0
29
30 using System;
31 using System.IO;
32 using System.Runtime.InteropServices;
33
34 namespace Microsoft.Build.Tasks {
35         internal static class Utilities {
36
37                 public readonly static bool RunningOnMac;
38                 public readonly static bool RunningOnWindows;
39
40                 static Utilities ()
41                 {
42                         RunningOnWindows = Path.DirectorySeparatorChar == '\\';
43                         RunningOnMac = !RunningOnWindows && IsRunningOnMac ();
44                 }
45
46                 [DllImport ("libc")]
47                 static extern int uname (IntPtr buf);
48
49                 //From Managed.Windows.Forms/XplatUI
50                 static bool IsRunningOnMac ()
51                 {
52                         IntPtr buf = IntPtr.Zero;
53                         try {
54                                 buf = System.Runtime.InteropServices.Marshal.AllocHGlobal (8192);
55                                 // This is a hacktastic way of getting sysname from uname ()
56                                 if (uname (buf) == 0) {
57                                         string os = System.Runtime.InteropServices.Marshal.PtrToStringAnsi (buf);
58                                         if (os == "Darwin")
59                                                 return true;
60                                 }
61                         } catch {
62                         } finally {
63                                 if (buf != IntPtr.Zero)
64                                         System.Runtime.InteropServices.Marshal.FreeHGlobal (buf);
65                         }
66                         return false;
67                 }
68
69                 internal static string FromMSBuildPath (string relPath)
70                 {
71                         if (relPath == null || relPath.Length == 0)
72                                 return null;
73
74                         bool is_windows = Path.DirectorySeparatorChar == '\\';
75                         string path = relPath;
76                         if (!is_windows)
77                                 path = path.Replace ("\\", "/");
78
79                         // a path with drive letter is invalid/unusable on non-windows
80                         if (!is_windows && char.IsLetter (path [0]) && path.Length > 1 && path[1] == ':')
81                                 return null;
82
83                         if (System.IO.File.Exists (path)){
84                                 return Path.GetFullPath (path);
85                         }
86
87                         if (Path.IsPathRooted (path)) {
88
89                                 // Windows paths are case-insensitive. When mapping an absolute path
90                                 // we can try to find the correct case for the path.
91
92                                 string[] names = path.Substring (1).Split ('/');
93                                 string part = "/";
94
95                                 for (int n=0; n<names.Length; n++) {
96                                         string[] entries;
97
98                                         if (names [n] == ".."){
99                                                 if (part == "/")
100                                                         return ""; // Can go further back. It's not an existing file
101                                                 part = Path.GetFullPath (part + "/..");
102                                                 continue;
103                                         }
104
105                                         entries = Directory.GetFileSystemEntries (part);
106
107                                         string fpath = null;
108                                         foreach (string e in entries) {
109                                                 if (string.Compare (Path.GetFileName (e), names[n], true) == 0) {
110                                                         fpath = e;
111                                                         break;
112                                                 }
113                                         }
114                                         if (fpath == null) {
115                                                 // Part of the path does not exist. Can't do any more checking.
116                                                 part = Path.GetFullPath (part);
117                                                 for (; n < names.Length; n++)
118                                                         part += "/" + names[n];
119                                                 return part;
120                                         }
121
122                                         part = fpath;
123                                 }
124                                 return Path.GetFullPath (part);
125                         } else {
126                                 return Path.GetFullPath (path);
127                         }
128                 }
129
130         }
131
132 }
133
134 #endif