* Mono.Unix/FileAccessPermissions.cs: Remove UserMask, GroupMask, OtherMask values.
[mono.git] / mcs / class / Mono.Posix / Mono.Unix / UnixDirectoryInfo.cs
1 //
2 // Mono.Unix/UnixDirectoryInfo.cs
3 //
4 // Authors:
5 //   Jonathan Pryor (jonpryor@vt.edu)
6 //
7 // (C) 2004-2006 Jonathan Pryor
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
29 using System;
30 using System.Collections;
31 using System.IO;
32 using System.Text;
33 using System.Text.RegularExpressions;
34 using Mono.Unix;
35
36 namespace Mono.Unix {
37
38         public sealed class UnixDirectoryInfo : UnixFileSystemInfo
39         {
40                 public UnixDirectoryInfo (string path)
41                         : base (path)
42                 {
43                 }
44
45                 internal UnixDirectoryInfo (string path, Native.Stat stat)
46                         : base (path, stat)
47                 {
48                 }
49
50                 public override string Name {
51                         get {
52                                 string r = UnixPath.GetFileName (FullPath);
53                                 if (r == null || r.Length == 0)
54                                         return FullPath;
55                                 return r;
56                         }
57                 }
58
59                 public UnixDirectoryInfo Parent {
60                         get {
61                                 string dirname = UnixPath.GetDirectoryName (FullPath);
62                                 if (dirname == null)
63                                         return null;
64                                 return new UnixDirectoryInfo (dirname);
65                         }
66                 }
67
68                 public UnixDirectoryInfo Root {
69                         get {
70                                 string root = UnixPath.GetPathRoot (FullPath);
71                                 if (root == null)
72                                         return null;
73                                 return new UnixDirectoryInfo (root);
74                         }
75                 }
76
77                 [CLSCompliant (false)]
78                 [Obsolete ("Use Create(Mono.Unix.Native.FilePermissions)")]
79                 public void Create (FilePermissions mode)
80                 {
81                         Mono.Unix.Native.FilePermissions _mode = 
82                                 (Mono.Unix.Native.FilePermissions) mode;
83                         Create (_mode);
84                 }
85
86                 [CLSCompliant (false)]
87                 public void Create (Mono.Unix.Native.FilePermissions mode)
88                 {
89                         int r = Mono.Unix.Native.Syscall.mkdir (FullPath, mode);
90                         UnixMarshal.ThrowExceptionForLastErrorIf (r);
91                         base.Refresh ();
92                 }
93
94                 public void Create (FileAccessPermissions mode)
95                 {
96                         Create ((Native.FilePermissions) mode);
97                 }
98
99                 public void Create ()
100                 {
101                         Mono.Unix.Native.FilePermissions mode = 
102                                 Mono.Unix.Native.FilePermissions.ACCESSPERMS;
103                         Create (mode);
104                 }
105
106                 public override void Delete ()
107                 {
108                         Delete (false);
109                 }
110
111                 public void Delete (bool recursive)
112                 {
113                         if (recursive) {
114                                 foreach (UnixFileSystemInfo e in GetFileSystemEntries ()) {
115                                         UnixDirectoryInfo d = e as UnixDirectoryInfo;
116                                         if (d != null)
117                                                 d.Delete (true);
118                                         else
119                                                 e.Delete ();
120                                 }
121                         }
122                         int r = Native.Syscall.rmdir (FullPath);
123                         UnixMarshal.ThrowExceptionForLastErrorIf (r);
124                         base.Refresh ();
125                 }
126
127                 public Native.Dirent[] GetEntries ()
128                 {
129                         IntPtr dirp = Native.Syscall.opendir (FullPath);
130                         if (dirp == IntPtr.Zero)
131                                 UnixMarshal.ThrowExceptionForLastError ();
132
133                         bool complete = false;
134                         try {
135                                 Native.Dirent[] entries = GetEntries (dirp);
136                                 complete = true;
137                                 return entries;
138                         }
139                         finally {
140                                 int r = Native.Syscall.closedir (dirp);
141                                 // don't throw an exception if an exception is in progress
142                                 if (complete)
143                                         UnixMarshal.ThrowExceptionForLastErrorIf (r);
144                         }
145                 }
146
147                 private static Native.Dirent[] GetEntries (IntPtr dirp)
148                 {
149                         ArrayList entries = new ArrayList ();
150
151                         int r;
152                         IntPtr result;
153                         do {
154                                 Native.Dirent d = new Native.Dirent ();
155                                 r = Native.Syscall.readdir_r (dirp, d, out result);
156                                 if (r == 0 && result != IntPtr.Zero)
157                                         // don't include current & parent dirs
158                                         if (d.d_name != "." && d.d_name != "..")
159                                                 entries.Add (d);
160                         } while  (r == 0 && result != IntPtr.Zero);
161                         if (r != 0)
162                                 UnixMarshal.ThrowExceptionForLastErrorIf (r);
163
164                         return (Native.Dirent[]) entries.ToArray (typeof(Native.Dirent));
165                 }
166
167                 public Native.Dirent[] GetEntries (Regex regex)
168                 {
169                         IntPtr dirp = Native.Syscall.opendir (FullPath);
170                         if (dirp == IntPtr.Zero)
171                                 UnixMarshal.ThrowExceptionForLastError ();
172
173                         try {
174                                 return GetEntries (dirp, regex);
175                         }
176                         finally {
177                                 int r = Native.Syscall.closedir (dirp);
178                                 UnixMarshal.ThrowExceptionForLastErrorIf (r);
179                         }
180                 }
181
182                 private static Native.Dirent[] GetEntries (IntPtr dirp, Regex regex)
183                 {
184                         ArrayList entries = new ArrayList ();
185
186                         int r;
187                         IntPtr result;
188                         do {
189                                 Native.Dirent d = new Native.Dirent ();
190                                 r = Native.Syscall.readdir_r (dirp, d, out result);
191                                 if (r == 0 && result != IntPtr.Zero && regex.Match (d.d_name).Success) {
192                                         // don't include current & parent dirs
193                                         if (d.d_name != "." && d.d_name != "..")
194                                                 entries.Add (d);
195                                 }
196                         } while  (r == 0 && result != IntPtr.Zero);
197                         if (r != 0)
198                                 UnixMarshal.ThrowExceptionForLastError ();
199
200                         return (Native.Dirent[]) entries.ToArray (typeof(Native.Dirent));
201                 }
202
203                 public Native.Dirent[] GetEntries (string regex)
204                 {
205                         Regex re = new Regex (regex);
206                         return GetEntries (re);
207                 }
208
209                 public UnixFileSystemInfo[] GetFileSystemEntries ()
210                 {
211                         Native.Dirent[] dentries = GetEntries ();
212                         return GetFileSystemEntries (dentries);
213                 }
214
215                 private UnixFileSystemInfo[] GetFileSystemEntries (Native.Dirent[] dentries)
216                 {
217                         UnixFileSystemInfo[] entries = new UnixFileSystemInfo[dentries.Length];
218                         for (int i = 0; i != entries.Length; ++i)
219                                 entries [i] = UnixFileSystemInfo.Create (
220                                                 UnixPath.Combine (FullPath, dentries[i].d_name));
221                         return entries;
222                 }
223
224                 public UnixFileSystemInfo[] GetFileSystemEntries (Regex regex)
225                 {
226                         Native.Dirent[] dentries = GetEntries (regex);
227                         return GetFileSystemEntries (dentries);
228                 }
229
230                 public UnixFileSystemInfo[] GetFileSystemEntries (string regex)
231                 {
232                         Regex re = new Regex (regex);
233                         return GetFileSystemEntries (re);
234                 }
235
236                 public static string GetCurrentDirectory ()
237                 {
238                         StringBuilder buf = new StringBuilder (16);
239                         IntPtr r = IntPtr.Zero;
240                         do {
241                                 buf.Capacity *= 2;
242                                 r = Native.Syscall.getcwd (buf, (ulong) buf.Capacity);
243                         } while (r == IntPtr.Zero && Native.Syscall.GetLastError() == Native.Errno.ERANGE);
244                         if (r == IntPtr.Zero)
245                                 UnixMarshal.ThrowExceptionForLastError ();
246                         return buf.ToString ();
247                 }
248
249                 public static void SetCurrentDirectory (string path)
250                 {
251                         int r = Native.Syscall.chdir (path);
252                         UnixMarshal.ThrowExceptionForLastErrorIf (r);
253                 }
254         }
255 }
256
257 // vim: noexpandtab