ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/cvsroot/Linux-Inotify2/Inotify2.pm
Revision: 1.1
Committed: Mon Aug 22 09:51:38 2005 UTC (18 years, 10 months ago) by root
Branch: MAIN
Log Message:
*** empty log message ***

File Contents

# Content
1 =head1 NAME
2
3 Linux::Inotify2 - scalable directory/file change notification
4
5 =head1 SYNOPSIS
6
7 use Linux::Inotify2;
8
9 =head1 DESCRIPTION
10
11 =head2 The Linux::Inotify2 Class
12
13 =over 4
14
15 =cut
16
17 package Linux::Inotify2;
18
19 use Carp ();
20 use Scalar::Util ();
21
22 use base 'Exporter';
23
24 BEGIN {
25 $VERSION = 0.1;
26
27 @constants = qw(
28 IN_ACCESS IN_MODIFY IN_ATTRIB IN_CLOSE_WRITE
29 IN_CLOSE_NOWRITE IN_OPEN IN_MOVED_FROM IN_MOVED_TO
30 IN_CREATE IN_DELETE IN_DELETE_SELF
31 IN_ALL_EVENTS
32 IN_UNMOUNT IN_Q_OVERFLOW IN_IGNORED
33 IN_CLOSE IN_MOVE
34 IN_ISDIR IN_ONESHOT
35 );
36
37 @EXPORT = @constants;
38
39 require XSLoader;
40 XSLoader::load Linux::Inotify2, $VERSION;
41 }
42
43 =item my $inotify = new Linux::Inotify2
44
45 Create a new notify object and return it. A notify object is kind of a
46 container that stores watches on filesystem names and is responsible for
47 handling event data.
48
49 On error, C<undef> is returned and C<$!> will be set accordingly. The followign errors
50 are documented:
51
52 ENFILE The system limit on the total number of file descriptors has been reached.
53 EMFILE The user limit on the total number of inotify instances has been reached.
54 ENOMEM Insufficient kernel memory is available.
55
56 =cut
57
58 sub new {
59 my ($class) = @_;
60
61 my $fd = inotify_init;
62
63 return unless $fd >= 0;
64
65 bless { fd => $fd }, $class
66 }
67
68 =item $watch = $inotify2->watch ($name, $mask, $cb)
69
70 Add a new watcher to the given notifier. The watcher will create events
71 on the pathname C<$name> as given in C<$mask>, which can be any of the
72 following constants (all exported by default) ORed together:
73
74 IN_ACCESS File was accessed
75 IN_MODIFY File was modified
76 IN_ATTRIB Metadata changed
77 IN_CLOSE_WRITE Writtable file was closed
78 IN_CLOSE_NOWRITE Unwrittable file closed
79 IN_OPEN File was opened
80 IN_MOVED_FROM File was moved from X
81 IN_MOVED_TO File was moved to Y
82 IN_CREATE Subfile was created
83 IN_DELETE Subfile was deleted
84 IN_DELETE_SELF Self was deleted
85 IN_ONESHOT only send event once
86 IN_ALL_EVENTS All of the above events
87
88 IN_CLOSE Same as IN_CLOSE_WRITE | IN_CLOSE_NOWRITE
89 IN_MOVE Same as IN_MOVED_FROM | IN_MOVED_TO
90
91 C<$cb> is a perl code reference that is called for each event. It receives
92 a C<Linux::Inotify2::Event> object.
93
94 The returned C<$watch> object is of class C<Linux::Inotify2::Watch>.
95
96 On error, C<undef> is returned and C<$!> will be set accordingly. The
97 following errors are documented:
98
99 EBADF The given file descriptor is not valid.
100 EINVAL The given event mask contains no legal events.
101 ENOMEM Insufficient kernel memory was available.
102 ENOSPC The user limit on the total number of inotify watches was reached or the kernel failed to allocate a needed resource.
103 EACCESS Read access to the given file is not permitted.
104
105 Example, show when C</etc/passwd> gets accessed and/or modified once:
106
107 $inotify->watch ("/etc/passwd", IN_ACCESS | IN_MODIFY, sub {
108 my $e = shift;
109 print "$e->{w}{name} was accessed\n" if $e->IN_ACCESS;
110 print "$e->{w}{name} was modified\n" if $e->IN_MODIFY;
111 print "$e->{w}{name} is no longer mounted\n" if $e->IN_UNMOUNT;
112 print "events for $e->{w}{name} have been lost\n" if $e->IN_Q_OVERFLOW;
113
114 $e->w->cancel;
115 });
116
117 =cut
118
119 sub watch {
120 my ($self, $name, $mask, $cb) = @_;
121
122 my $wd = inotify_add_watch $self->{fd}, $name, $mask;
123
124 return unless $wd >= 0;
125
126 my $w = $self->{w}{$wd} = bless {
127 inotify => $self,
128 wd => $wd,
129 name => $name,
130 mask => $mask,
131 cb => $cb,
132 }, Linux::Inotify2::Watch;
133
134 Scalar::Util::weaken $w->{inotify};
135
136 $w
137 }
138
139 =item $inotify2->fileno
140
141 Returns the fileno for this notify object. You are responsible for calling
142 the C<poll> method when this fileno becomes ready for reading.
143
144 =cut
145
146 sub fileno {
147 $_[0]{fd}
148 }
149
150 =item $count = $inotify2->poll
151
152 Reads events from the kernel and handles them. If the notify fileno
153 is blocking (the default), then this method waits for at least one
154 event. Otherwise it returns immediately when no pending events could be
155 read.
156
157 Returns the count of events that have been handled.
158
159 =cut
160
161 # TODO: potential race with recently-canceled watchers
162
163 sub poll {
164 my ($self) = @_;
165
166 for (inotify_read $self->{fd}) {
167 $_->{w} = $self->{w}{$_->{wd}}
168 or next; # no such watcher
169 $_->{w}{cb}->(bless $_, Linux::Inotify2::Event);
170 }
171 }
172
173 sub DESTROY {
174 inotify_close $_[0]{fd}
175 }
176
177 =back
178
179 =head2 The Linux::Inotify2::Event Class
180
181 Objects of this class are handed as first argument to the watch
182 callback. It has the following members and methods:
183
184 =over 4
185
186 =item $event->w
187
188 =item $event->{w}
189
190 The watcher object for this event.
191
192 =item $event->name
193
194 =item $event->{name}
195
196 The path of the filesystem object, relative to the watch name.
197
198 =item $watch->fullname
199
200 Returns the "full" name of the relevant object, i.e. including the C<name>
201 component of the watcher.
202
203 =item $event->mask
204
205 =item $event->{mask}
206
207 The received event mask. In addition the the events described for
208 C<$inotify->watch>, the following flags (exported by default) can be set:
209
210 IN_ISDIR event occurred against dir
211
212 IN_UNMOUNT Backing fs was unmounted
213 IN_Q_OVERFLOW Event queued overflowed
214 IN_IGNORED File was ignored (no more events will be delivered)
215
216 =item $event->IN_xxx
217
218 Returns a boolean that returns true if the event mask matches the
219 event. All of the C<IN_xxx> constants can be used as methods.
220
221 =item $event->cookie
222
223 =item $event->{cookie}
224
225 The event cookie, can be used to synchronize two related events.
226
227 =back
228
229 =cut
230
231 package Linux::Inotify2::Event;
232
233 sub w { $_[0]{w} }
234 sub name { $_[0]{name} }
235 sub mask { $_[0]{mask} }
236 sub cookie { $_[0]{cookie} }
237
238 sub fullname {
239 length $_[0]{name}
240 ? "$_[0]{w}{name}/$_[0]{name}"
241 : $_[0]{w}{name};
242 }
243
244 for my $name (@Linux::Inotify2::constants) {
245 my $mask = &{"Linux::Inotify2::$name"};
246
247 *$name = sub { ($_[0]{mask} & $mask) == $mask };
248 }
249
250 =head2 The Linux::Inotify2::Watch Class
251
252 Watch objects are created by calling the C<watch> method of a notifier.
253
254 It has the following members and methods:
255
256 =item $watch->name
257
258 =item $watch->{name}
259
260 The name as specified in the C<watch> call. For the object itself, this is
261 the empty string. For directory watches, this is the name of the entry
262 without leading path elements.
263
264 =item $watch->mask
265
266 =item $watch->{mask}
267
268 The mask as specified in the C<watch> call.
269
270 =item $watch->cb ([new callback])
271
272 =item $watch->{cb}
273
274 The callback as specified in the C<watch> call. Can optionally be changed.
275
276 =item $watch->cancel
277
278 Cancels/removes this watch. Future events, even if already queued queued,
279 will not be handled and resources will be freed.
280
281 =cut
282
283 package Linux::Inotify2::Watch;
284
285 sub name { $_[0]{name} }
286 sub mask { $_[0]{mask} }
287
288 sub cb {
289 $_[0]{cb} = $_[1] if @_ > 1;
290 $_[0]{cb}
291 }
292
293 sub cancel {
294 my ($self) = @_;
295
296 (Linux::Inotify2::inotify_rm_watch $self->{inotify}{fd}, $self->{wd})
297 ? 1 : undef
298 }
299
300 =head1 SEE ALSO
301
302 L<Linux::Inotify>.
303
304 =head1 AUTHOR
305
306 Marc Lehmann <schmorp@schmorp.de>
307 http://home.schmorp.de/
308
309 =cut
310
311 1