r5739: sync for 3.0.12rc1 (current with SAMBA_3_0 r5738)
[Samba.git] / source / smbd / close.c
blobb3244432ff559be4a6146f2aedb017522f663808
1 /*
2 Unix SMB/CIFS implementation.
3 file closing
4 Copyright (C) Andrew Tridgell 1992-1998
5 Copyright (C) Jeremy Allison 1992-2004.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 #include "includes.h"
24 /****************************************************************************
25 Run a file if it is a magic script.
26 ****************************************************************************/
28 static void check_magic(files_struct *fsp,connection_struct *conn)
30 if (!*lp_magicscript(SNUM(conn)))
31 return;
33 DEBUG(5,("checking magic for %s\n",fsp->fsp_name));
36 char *p;
37 if (!(p = strrchr_m(fsp->fsp_name,'/')))
38 p = fsp->fsp_name;
39 else
40 p++;
42 if (!strequal(lp_magicscript(SNUM(conn)),p))
43 return;
47 int ret;
48 pstring magic_output;
49 pstring fname;
50 SMB_STRUCT_STAT st;
51 int tmp_fd, outfd;
53 pstrcpy(fname,fsp->fsp_name);
54 if (*lp_magicoutput(SNUM(conn)))
55 pstrcpy(magic_output,lp_magicoutput(SNUM(conn)));
56 else
57 slprintf(magic_output,sizeof(fname)-1, "%s.out",fname);
59 chmod(fname,0755);
60 ret = smbrun(fname,&tmp_fd);
61 DEBUG(3,("Invoking magic command %s gave %d\n",fname,ret));
62 unlink(fname);
63 if (ret != 0 || tmp_fd == -1) {
64 if (tmp_fd != -1)
65 close(tmp_fd);
66 return;
68 outfd = open(magic_output, O_CREAT|O_EXCL|O_RDWR, 0600);
69 if (outfd == -1) {
70 close(tmp_fd);
71 return;
74 if (sys_fstat(tmp_fd,&st) == -1) {
75 close(tmp_fd);
76 close(outfd);
77 return;
80 transfer_file(tmp_fd,outfd,(SMB_OFF_T)st.st_size);
81 close(tmp_fd);
82 close(outfd);
86 /****************************************************************************
87 Common code to close a file or a directory.
88 ****************************************************************************/
90 static int close_filestruct(files_struct *fsp)
92 connection_struct *conn = fsp->conn;
93 int ret = 0;
95 if (fsp->fd != -1) {
96 if(flush_write_cache(fsp, CLOSE_FLUSH) == -1)
97 ret = -1;
99 delete_write_cache(fsp);
102 conn->num_files_open--;
103 SAFE_FREE(fsp->wbmpx_ptr);
105 return ret;
108 /****************************************************************************
109 If any deferred opens are waiting on this close, notify them.
110 ****************************************************************************/
112 static void notify_deferred_opens(files_struct *fsp)
114 deferred_open_entry *de_array = NULL;
115 int num_de_entries, i;
116 pid_t mypid = sys_getpid();
118 if (!lp_defer_sharing_violations()) {
119 return;
122 num_de_entries = get_deferred_opens(fsp->conn, fsp->dev, fsp->inode, &de_array);
123 for (i = 0; i < num_de_entries; i++) {
124 deferred_open_entry *entry = &de_array[i];
125 if (entry->pid == mypid) {
127 * We need to notify ourself to retry the open.
128 * Do this by finding the queued SMB record, moving it
129 * to the head of the queue and changing the wait time to zero.
131 schedule_sharing_violation_open_smb_message(entry->mid);
132 } else {
133 send_deferred_open_retry_message(entry);
138 /****************************************************************************
139 Close a file.
141 If normal_close is 1 then this came from a normal SMBclose (or equivalent)
142 operation otherwise it came as the result of some other operation such as
143 the closing of the connection. In the latter case printing and
144 magic scripts are not run.
145 ****************************************************************************/
147 static int close_normal_file(files_struct *fsp, BOOL normal_close)
149 share_mode_entry *share_entry = NULL;
150 size_t share_entry_count = 0;
151 BOOL delete_on_close = False;
152 connection_struct *conn = fsp->conn;
153 int saved_errno = 0;
154 int err = 0;
155 int err1 = 0;
157 remove_pending_lock_requests_by_fid(fsp);
160 * If we're flushing on a close we can get a write
161 * error here, we must remember this.
164 if (close_filestruct(fsp) == -1) {
165 saved_errno = errno;
166 err1 = -1;
169 if (fsp->print_file) {
170 print_fsp_end(fsp, normal_close);
171 file_free(fsp);
172 return 0;
176 * Lock the share entries, and determine if we should delete
177 * on close. If so delete whilst the lock is still in effect.
178 * This prevents race conditions with the file being created. JRA.
181 lock_share_entry_fsp(fsp);
183 if (fsp->delete_on_close) {
186 * Modify the share mode entry for all files open
187 * on this device and inode to tell other smbds we have
188 * changed the delete on close flag. The last closer will delete the file
189 * if flag is set.
192 NTSTATUS status =set_delete_on_close_over_all(fsp, fsp->delete_on_close);
193 if (NT_STATUS_V(status) != NT_STATUS_V(NT_STATUS_OK))
194 DEBUG(0,("close_normal_file: failed to change delete on close flag for file %s\n",
195 fsp->fsp_name ));
198 share_entry_count = del_share_mode(fsp, &share_entry);
200 DEBUG(10,("close_normal_file: share_entry_count = %lu for file %s\n",
201 (unsigned long)share_entry_count, fsp->fsp_name ));
204 * We delete on close if it's the last open, and the
205 * delete on close flag was set in the entry we just deleted.
208 if ((share_entry_count == 0) && share_entry &&
209 GET_DELETE_ON_CLOSE_FLAG(share_entry->share_mode) )
210 delete_on_close = True;
212 SAFE_FREE(share_entry);
214 /* Notify any deferred opens waiting on this close. */
215 notify_deferred_opens(fsp);
218 * NT can set delete_on_close of the last open
219 * reference to a file.
222 if (normal_close && delete_on_close) {
223 DEBUG(5,("close_file: file %s. Delete on close was set - deleting file.\n",
224 fsp->fsp_name));
225 if(SMB_VFS_UNLINK(conn,fsp->fsp_name) != 0) {
227 * This call can potentially fail as another smbd may have
228 * had the file open with delete on close set and deleted
229 * it when its last reference to this file went away. Hence
230 * we log this but not at debug level zero.
233 DEBUG(5,("close_file: file %s. Delete on close was set and unlink failed \
234 with error %s\n", fsp->fsp_name, strerror(errno) ));
236 process_pending_change_notify_queue((time_t)0);
239 unlock_share_entry_fsp(fsp);
241 if(fsp->oplock_type)
242 release_file_oplock(fsp);
244 locking_close_file(fsp);
246 err = fd_close(conn, fsp);
248 /* Only save errno if fd_close failed and we don't already
249 have an errno saved from a flush call. */
250 if ((err1 != -1) && (err == -1)) {
251 saved_errno = errno;
254 /* check for magic scripts */
255 if (normal_close) {
256 check_magic(fsp,conn);
260 * Ensure pending modtime is set after close.
263 if(fsp->pending_modtime && fsp->pending_modtime_owner) {
264 set_filetime(conn, fsp->fsp_name, fsp->pending_modtime);
265 } else if (fsp->last_write_time) {
266 set_filetime(conn, fsp->fsp_name, fsp->last_write_time);
269 DEBUG(2,("%s closed file %s (numopen=%d) %s\n",
270 conn->user,fsp->fsp_name,
271 conn->num_files_open,
272 (err == -1 || err1 == -1) ? strerror(saved_errno) : ""));
274 if (fsp->fsp_name)
275 string_free(&fsp->fsp_name);
277 file_free(fsp);
279 if (err == -1 || err1 == -1) {
280 errno = saved_errno;
281 return saved_errno;
282 } else {
283 return 0;
287 /****************************************************************************
288 Close a directory opened by an NT SMB call.
289 ****************************************************************************/
291 static int close_directory(files_struct *fsp, BOOL normal_close)
293 remove_pending_change_notify_requests_by_fid(fsp);
296 * NT can set delete_on_close of the last open
297 * reference to a directory also.
300 if (normal_close && fsp->directory_delete_on_close) {
301 BOOL ok = rmdir_internals(fsp->conn, fsp->fsp_name);
302 DEBUG(5,("close_directory: %s. Delete on close was set - deleting directory %s.\n",
303 fsp->fsp_name, ok ? "succeeded" : "failed" ));
306 * Ensure we remove any change notify requests that would
307 * now fail as the directory has been deleted.
310 if(ok)
311 remove_pending_change_notify_requests_by_filename(fsp);
312 process_pending_change_notify_queue((time_t)0);
316 * Do the code common to files and directories.
318 close_filestruct(fsp);
320 if (fsp->fsp_name)
321 string_free(&fsp->fsp_name);
323 file_free(fsp);
324 return 0;
327 /****************************************************************************
328 Close a 'stat file' opened internally.
329 ****************************************************************************/
331 static int close_stat(files_struct *fsp)
334 * Do the code common to files and directories.
336 close_filestruct(fsp);
338 if (fsp->fsp_name)
339 string_free(&fsp->fsp_name);
341 file_free(fsp);
342 return 0;
345 /****************************************************************************
346 Close a files_struct.
347 ****************************************************************************/
349 int close_file(files_struct *fsp, BOOL normal_close)
351 if(fsp->is_directory)
352 return close_directory(fsp, normal_close);
353 else if (fsp->is_stat)
354 return close_stat(fsp);
355 else
356 return close_normal_file(fsp, normal_close);