2 // Mono.Unix/UnixFileSystemInfo.cs
5 // Jonathan Pryor (jonpryor@vt.edu)
7 // (C) 2004-2005 Jonathan Pryor
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:
17 // The above copyright notice and this permission notice shall be
18 // included in all copies or substantial portions of the Software.
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.
36 public abstract class UnixFileSystemInfo
39 private string fullPath;
40 private string originalPath;
41 private bool valid = false;
43 protected UnixFileSystemInfo (string path)
45 UnixPath.CheckPath (path);
46 this.originalPath = path;
47 this.fullPath = UnixPath.GetFullPath (path);
51 [Obsolete ("Use UnixFileSystemInfo (string, Mono.Unix.Native.Stat)")]
52 internal UnixFileSystemInfo (String path, Stat stat)
54 this.originalPath = path;
55 this.fullPath = UnixPath.GetFullPath (path);
60 internal UnixFileSystemInfo (String path, Native.Stat stat)
62 this.originalPath = path;
63 this.fullPath = UnixPath.GetFullPath (path);
68 protected string FullPath {
69 get {return fullPath;}
70 set {fullPath = value;}
73 protected string OriginalPath {
74 get {return originalPath;}
75 set {originalPath = value;}
78 private void AssertValid ()
82 throw new InvalidOperationException ("Path doesn't exist!");
85 public virtual string FullName {
86 get {return FullPath;}
89 public abstract string Name {get;}
98 [CLSCompliant (false)]
99 [Obsolete ("The type of this property will change to Int64 in the next release.")]
100 public ulong Device {
101 get {AssertValid (); return stat.st_dev;}
104 [CLSCompliant (false)]
105 [Obsolete ("The type of this property will change to Int64 in the next release.")]
107 get {AssertValid (); return stat.st_ino;}
110 [CLSCompliant (false)]
111 [Obsolete ("Use Protection.")]
112 public FilePermissions Mode {
113 get {AssertValid (); return stat.st_mode;}
116 [CLSCompliant (false)]
117 [Obsolete ("Use FileAccessPermissions.")]
118 public FilePermissions Permissions {
119 get {AssertValid (); return stat.st_mode & ~FilePermissions.S_IFMT;}
122 [CLSCompliant (false)]
123 [Obsolete ("The type of this property will change to FileTypes in the next release.")]
124 public FilePermissions FileType {
125 get {AssertValid (); return stat.st_mode & FilePermissions.S_IFMT;}
128 [CLSCompliant (false)]
129 public Native.FilePermissions Protection {
130 get {AssertValid (); return (Native.FilePermissions) stat.st_mode;}
132 int r = Native.Syscall.chmod (FullPath, value);
133 UnixMarshal.ThrowExceptionForLastErrorIf (r);
138 public FileTypes FileType {
141 int type = (int) stat.st_mode;
142 return (FileTypes) (type & (int) FileTypes.AllTypes);
144 // no set as chmod(2) won't accept changing the file type.
148 public FileAccessPermissions FileAccessPermissions {
151 int perms = (int) stat.st_mode;
152 return (FileAccessPermissions) (perms & (int) FileAccessPermissions.AllPermissions);
156 int perms = (int) stat.st_mode;
157 perms &= (int) ~FileAccessPermissions.AllPermissions;
158 perms |= (int) value;
159 Protection = (Native.FilePermissions) perms;
163 public FileSpecialAttributes FileSpecialAttributes {
166 int attrs = (int) stat.st_mode;
167 return (FileSpecialAttributes) (attrs & (int) FileSpecialAttributes.AllAttributes);
171 int perms = (int) stat.st_mode;
172 perms &= (int) ~FileSpecialAttributes.AllAttributes;
173 perms |= (int) value;
174 Protection = (Native.FilePermissions) perms;
178 [CLSCompliant (false)]
179 [Obsolete ("The type of this property will change to Int64 in the next release.")]
180 public ulong LinkCount {
181 get {AssertValid (); return (ulong) stat.st_nlink;}
184 [CLSCompliant (false)]
185 [Obsolete ("Use OwnerUserId. " +
186 "The type of this property will change to UnixUserInfo in the next release.")]
187 public uint OwnerUser {
188 get {AssertValid (); return stat.st_uid;}
191 public long OwnerUserId {
192 get {AssertValid (); return stat.st_uid;}
195 [CLSCompliant (false)]
196 [Obsolete ("Use OwnerGroupId. " +
197 "The type of this property will change to UnixGroupInfo in the next release.")]
198 public uint OwnerGroup {
199 get {AssertValid (); return stat.st_gid;}
202 public long OwnerGroupId {
203 get {AssertValid (); return stat.st_gid;}
206 [CLSCompliant (false)]
207 [Obsolete ("The type of this property will change to Int64 in the next release.")]
208 public ulong DeviceType {
209 get {AssertValid (); return stat.st_rdev;}
213 get {AssertValid (); return (long) stat.st_size;}
216 public long BlockSize {
217 get {AssertValid (); return (long) stat.st_blksize;}
220 public long BlocksAllocated {
221 get {AssertValid (); return (long) stat.st_blocks;}
224 public DateTime LastAccessTime {
225 get {AssertValid (); return UnixConvert.ToDateTime (stat.st_atime);}
228 public DateTime LastAccessTimeUtc {
229 get {return LastAccessTime.ToUniversalTime ();}
232 public DateTime LastWriteTime {
233 get {AssertValid (); return UnixConvert.ToDateTime (stat.st_mtime);}
236 public DateTime LastWriteTimeUtc {
237 get {return LastWriteTime.ToUniversalTime ();}
240 public DateTime LastStatusChangeTime {
241 get {AssertValid (); return UnixConvert.ToDateTime (stat.st_ctime);}
244 public DateTime LastStatusChangeTimeUtc {
245 get {return LastStatusChangeTime.ToUniversalTime ();}
248 public bool IsDirectory {
249 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFDIR);}
252 public bool IsCharacterDevice {
253 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFCHR);}
256 public bool IsBlockDevice {
257 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFBLK);}
261 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFREG);}
264 [Obsolete ("Use IsFifo")]
265 [CLSCompliant (false)]
267 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFIFO);}
271 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFIFO);}
274 public bool IsSymbolicLink {
275 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFLNK);}
278 public bool IsSocket {
279 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_IFSOCK);}
282 public bool IsSetUser {
283 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_ISUID);}
286 public bool IsSetGroup {
287 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_ISGID);}
290 public bool IsSticky {
291 get {AssertValid (); return IsType (stat.st_mode, FilePermissions.S_ISVTX);}
294 internal static bool IsType (FilePermissions mode, FilePermissions type)
296 return (mode & type) == type;
299 internal static bool IsType (Native.FilePermissions mode, Native.FilePermissions type)
301 return (mode & type) == type;
304 [CLSCompliant (false)]
305 [Obsolete ("Use CanAccess (Mono.Unix.Native.AccessModes)")]
306 public bool CanAccess (AccessMode mode)
308 int r = Syscall.access (FullPath, mode);
312 [CLSCompliant (false)]
313 public bool CanAccess (Native.AccessModes mode)
315 int r = Native.Syscall.access (FullPath, mode);
319 public UnixFileSystemInfo CreateLink (string path)
321 int r = Syscall.link (FullName, path);
322 UnixMarshal.ThrowExceptionForLastErrorIf (r);
323 return Create (path);
326 public UnixSymbolicLinkInfo CreateSymbolicLink (string path)
328 int r = Syscall.symlink (FullName, path);
329 UnixMarshal.ThrowExceptionForLastErrorIf (r);
330 return new UnixSymbolicLinkInfo (path);
333 public abstract void Delete ();
335 [CLSCompliant (false)]
336 [Obsolete ("Use GetConfigurationValue (Mono.Unix.Native.PathconfName)")]
337 public long GetConfigurationValue (PathConf name)
339 long r = Syscall.pathconf (FullPath, name);
340 if (r == -1 && Syscall.GetLastError() != (Error) 0)
341 UnixMarshal.ThrowExceptionForLastError ();
345 [CLSCompliant (false)]
346 public long GetConfigurationValue (Native.PathconfName name)
348 long r = Native.Syscall.pathconf (FullPath, name);
349 if (r == -1 && Syscall.GetLastError() != (Error) 0)
350 UnixMarshal.ThrowExceptionForLastError ();
354 public void Refresh ()
359 internal void Refresh (bool force)
363 int r = GetFileStatus (FullPath, out this.stat);
367 [Obsolete ("Use GetFileStatus (string, Mono.Unix.Native.Stat)")]
368 protected virtual int GetFileStatus (string path, out Stat stat)
370 return Syscall.stat (path, out stat);
373 protected virtual int GetFileStatus (string path, out Native.Stat stat)
375 return Native.Syscall.stat (path, out stat);
378 public void SetLength (long length)
382 r = Syscall.truncate (FullPath, length);
383 } while (UnixMarshal.ShouldRetrySyscall (r));
384 UnixMarshal.ThrowExceptionForLastErrorIf (r);
387 [CLSCompliant (false)]
388 [Obsolete ("Use Protection setter")]
389 public void SetPermissions (FilePermissions perms)
391 int r = Syscall.chmod (FullPath, perms);
392 UnixMarshal.ThrowExceptionForLastErrorIf (r);
395 [CLSCompliant (false)]
396 [Obsolete ("Use SetOwner (long, long)")]
397 public virtual void SetOwner (uint owner, uint group)
399 int r = Syscall.chown (FullPath, owner, group);
400 UnixMarshal.ThrowExceptionForLastErrorIf (r);
403 public virtual void SetOwner (long owner, long group)
405 uint _owner = Convert.ToUInt32 (owner);
406 uint _group = Convert.ToUInt32 (group);
407 int r = Syscall.chown (FullPath, _owner, _group);
408 UnixMarshal.ThrowExceptionForLastErrorIf (r);
411 public void SetOwner (string owner)
413 Passwd pw = Syscall.getpwnam (owner);
415 throw new ArgumentException (Locale.GetText ("invalid username"), "owner");
416 uint uid = pw.pw_uid;
417 uint gid = pw.pw_gid;
421 public void SetOwner (string owner, string group)
423 uint uid = UnixUser.GetUserId (owner);
424 uint gid = UnixGroup.GetGroupId (group);
429 public override string ToString ()
434 public Native.Stat ToStat ()
436 Native.Stat stat = new Native.Stat ();
437 stat.st_dev = this.stat.st_dev;
438 stat.st_ino = this.stat.st_ino;
439 stat.st_mode = (Native.FilePermissions) this.stat.st_mode;
440 stat.st_nlink = this.stat.st_nlink;
441 stat.st_uid = this.stat.st_uid;
442 stat.st_gid = this.stat.st_gid;
443 stat.st_rdev = this.stat.st_rdev;
444 stat.st_size = this.stat.st_size;
445 stat.st_blksize = this.stat.st_blksize;
446 stat.st_blocks = this.stat.st_blocks;
447 stat.st_atime = this.stat.st_atime;
448 stat.st_mtime = this.stat.st_mtime;
449 stat.st_ctime = this.stat.st_ctime;
453 internal static UnixFileSystemInfo Create (string path)
456 int r = Syscall.lstat (path, out stat);
457 UnixMarshal.ThrowExceptionForLastErrorIf (r);
459 if (IsType (stat.st_mode, FilePermissions.S_IFDIR))
460 return new UnixDirectoryInfo (path, stat);
461 else if (IsType (stat.st_mode, FilePermissions.S_IFLNK))
462 return new UnixSymbolicLinkInfo (path, stat);
463 return new UnixFileInfo (path, stat);