Merge pull request #796 from alesliehughes/master
[mono.git] / mcs / class / corlib / System.IO / FileSystemInfo.cs
1 //------------------------------------------------------------------------------
2 // 
3 // System.IO.FileSystemInfo.cs 
4 //
5 // Copyright (C) 2001 Moonlight Enterprises, All Rights Reserved
6 // Copyright 2011 Xamarin Inc (http://www.xamarin.com).
7 // 
8 // Author:         Jim Richardson, develop@wtfo-guru.com
9 //                 Dan Lewis (dihlewis@yahoo.co.uk)
10 // Created:        Monday, August 13, 2001 
11 //
12 //------------------------------------------------------------------------------
13
14 //
15 // Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
16 //
17 // Permission is hereby granted, free of charge, to any person obtaining
18 // a copy of this software and associated documentation files (the
19 // "Software"), to deal in the Software without restriction, including
20 // without limitation the rights to use, copy, modify, merge, publish,
21 // distribute, sublicense, and/or sell copies of the Software, and to
22 // permit persons to whom the Software is furnished to do so, subject to
23 // the following conditions:
24 // 
25 // The above copyright notice and this permission notice shall be
26 // included in all copies or substantial portions of the Software.
27 // 
28 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
29 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
30 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
31 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
32 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
33 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
34 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
35 //
36
37 using System.Runtime.InteropServices;
38 using System.Runtime.Serialization;
39 using System.Security;
40 using System.Security.Permissions;
41
42 namespace System.IO {
43         
44         [Serializable]
45         [FileIOPermission (SecurityAction.InheritanceDemand, Unrestricted = true)]
46         [ComVisible (true)]
47 #if NET_2_1
48         public abstract class FileSystemInfo {
49 #else
50         public abstract class FileSystemInfo : MarshalByRefObject, ISerializable {
51
52                 #region Implementation of ISerializable
53
54                 [ComVisible(false)]
55                 public virtual void GetObjectData (SerializationInfo info, StreamingContext context)
56                 {
57                         info.AddValue ("OriginalPath", OriginalPath, typeof(string));
58                         info.AddValue ("FullPath", FullPath, typeof(string));
59                 }
60
61                 #endregion Implementation of ISerializable
62 #endif
63                 // public properties
64
65                 public abstract bool Exists { get; }
66
67                 public abstract string Name { get; }
68
69                 public virtual string FullName {
70                         get {
71                                 return FullPath;
72                         }
73                 }
74
75                 public string Extension {
76                         get {
77                                 return Path.GetExtension (Name);
78                         }
79                 }
80
81                 public FileAttributes Attributes {
82                         get {
83                                 Refresh (false);
84                                 return stat.Attributes;
85                         }
86
87                         set {
88                                 MonoIOError error;
89                                 
90                                 if (!MonoIO.SetFileAttributes (FullName,
91                                                                value,
92                                                                out error))
93                                         throw MonoIO.GetException (FullName,
94                                                                    error);
95                                 Refresh (true);
96                         }
97                 }
98
99                 public DateTime CreationTime {
100                         get {
101                                 Refresh (false);
102                                 return DateTime.FromFileTime (stat.CreationTime);
103                         }
104
105                         set {
106                                 SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
107
108                                 long filetime = value.ToFileTime ();
109                         
110                                 MonoIOError error;
111                                 
112                                 if (!MonoIO.SetFileTime (FullName, filetime,
113                                                          -1, -1, out error))
114                                         throw MonoIO.GetException (FullName,
115                                                                    error);
116                                 Refresh (true);
117                         }
118                 }
119
120                 [ComVisible(false)]
121                 public DateTime CreationTimeUtc {
122                         get {
123                                 return CreationTime.ToUniversalTime ();
124                         }
125
126                         set {
127                                 CreationTime = value.ToLocalTime ();
128                         }
129                 }
130
131                 public DateTime LastAccessTime {
132                         get {
133                                 Refresh (false);
134                                 return DateTime.FromFileTime (stat.LastAccessTime);
135                         }
136
137                         set {
138                                 SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
139
140                                 long filetime = value.ToFileTime ();
141
142                                 MonoIOError error;
143                                 
144                                 if (!MonoIO.SetFileTime (FullName, -1,
145                                                          filetime, -1,
146                                                          out error))
147                                         throw MonoIO.GetException (FullName,
148                                                                    error);
149                                 Refresh (true);
150                         }
151                 }
152
153                 [ComVisible(false)]
154                 public DateTime LastAccessTimeUtc {
155                         get {
156                                 Refresh (false);
157                                 return LastAccessTime.ToUniversalTime ();
158                         }
159
160                         set {
161                                 LastAccessTime = value.ToLocalTime ();
162                         }
163                 }
164
165                 public DateTime LastWriteTime {
166                         get {
167                                 Refresh (false);
168                                 return DateTime.FromFileTime (stat.LastWriteTime);
169                         }
170
171                         set {
172                                 SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
173
174                                 long filetime = value.ToFileTime ();
175
176                                 MonoIOError error;
177                                 
178                                 if (!MonoIO.SetFileTime (FullName, -1, -1,
179                                                          filetime, out error))
180                                         throw MonoIO.GetException (FullName,
181                                                                    error);
182                                 Refresh (true);
183                         }
184                 }
185
186                 [ComVisible(false)]
187                 public DateTime LastWriteTimeUtc {
188                         get {
189                                 Refresh (false);
190                                 return LastWriteTime.ToUniversalTime ();
191                         }
192
193                         set {
194                                 LastWriteTime = value.ToLocalTime ();
195                         }
196                 }
197
198                 // public methods
199
200                 public abstract void Delete ();
201
202                 public void Refresh ()
203                 {
204                         Refresh (true);
205                 }
206
207                 // protected
208
209                 protected FileSystemInfo ()
210                 {
211                         this.valid = false;
212                         this.FullPath = null;
213                 }
214
215                 protected FileSystemInfo (SerializationInfo info, StreamingContext context)
216                 {
217                         if (info == null)
218                         {
219                                 throw new ArgumentNullException("info");
220                         }
221
222                         FullPath = info.GetString("FullPath");
223                         OriginalPath = info.GetString("OriginalPath");
224                 }
225
226                 protected string FullPath;
227                 protected string OriginalPath;
228
229                 // internal
230
231                 internal void Refresh (bool force)
232                 {
233                         if (valid && !force)
234                                 return;
235
236                         MonoIOError error;
237                         
238                         MonoIO.GetFileStat (FullName, out stat, out error);
239                         /* Don't throw on error here, too much other
240                          * stuff relies on it not doing so...
241                          */
242                         
243                         valid = true;
244                         
245                         InternalRefresh ();
246                 }
247                 
248                 internal virtual void InternalRefresh ()
249                 {
250                 }
251
252                 internal void CheckPath (string path)
253                 {
254                         if (path == null)
255                                 throw new ArgumentNullException ("path");
256                         if (path.Length == 0)
257                                 throw new ArgumentException ("An empty file name is not valid.");
258                         if (path.IndexOfAny (Path.InvalidPathChars) != -1)
259                                 throw new ArgumentException ("Illegal characters in path.");
260                         if (Environment.IsRunningOnWindows) {
261                                 int idx = path.IndexOf (':');
262                                 if (idx >= 0 && idx != 1)
263                                         throw new ArgumentException ("path");
264                         }
265                 }
266
267                 internal MonoIOStat stat;
268                 internal bool valid;
269         }
270 }