static int recycle_connect | ( | vfs_handle_struct * | handle, | |
const char * | service, | |||
const char * | user | |||
) | [static] |
static void recycle_disconnect | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 59 行で定義されています。
参照先 handle.
00060 { 00061 DEBUG(10,("recycle_disconnect() connect to service[%s].\n", 00062 lp_servicename(SNUM(handle->conn)))); 00063 00064 SMB_VFS_NEXT_DISCONNECT(handle); 00065 }
static int recycle_unlink | ( | vfs_handle_struct * | handle, | |
const char * | name | |||
) | [static] |
Check if file should be recycled
vfs_recycle.c の 411 行で定義されています。
参照先 asprintf()・connection_struct::connectpath・current_user_info・userdom_struct::domain・errno・get_current_username()・connection_struct::gid・handle・matchdirparam()・matchparam()・recycle_create_dir()・recycle_directory_exist()・recycle_do_touch()・recycle_exclude()・recycle_exclude_dir()・recycle_file_exist()・recycle_get_file_size()・recycle_keep_dir_tree()・recycle_maxsize()・recycle_minsize()・recycle_noversions()・recycle_repository()・recycle_touch()・recycle_touch_mtime()・recycle_versions()・strerror()・talloc_sub_advanced()・trim_char()・connection_struct::user.
00412 { 00413 connection_struct *conn = handle->conn; 00414 char *path_name = NULL; 00415 char *temp_name = NULL; 00416 char *final_name = NULL; 00417 const char *base; 00418 char *repository = NULL; 00419 int i = 1; 00420 SMB_OFF_T maxsize, minsize; 00421 SMB_OFF_T file_size; /* space_avail; */ 00422 BOOL exist; 00423 int rc = -1; 00424 00425 repository = talloc_sub_advanced(NULL, lp_servicename(SNUM(conn)), 00426 conn->user, 00427 conn->connectpath, conn->gid, 00428 get_current_username(), 00429 current_user_info.domain, 00430 recycle_repository(handle)); 00431 ALLOC_CHECK(repository, done); 00432 /* shouldn't we allow absolute path names here? --metze */ 00433 /* Yes :-). JRA. */ 00434 trim_char(repository, '\0', '/'); 00435 00436 if(!repository || *(repository) == '\0') { 00437 DEBUG(3, ("recycle: repository path not set, purging %s...\n", file_name)); 00438 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00439 goto done; 00440 } 00441 00442 /* we don't recycle the recycle bin... */ 00443 if (strncmp(file_name, repository, strlen(repository)) == 0) { 00444 DEBUG(3, ("recycle: File is within recycling bin, unlinking ...\n")); 00445 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00446 goto done; 00447 } 00448 00449 file_size = recycle_get_file_size(handle, file_name); 00450 /* it is wrong to purge filenames only because they are empty imho 00451 * --- simo 00452 * 00453 if(fsize == 0) { 00454 DEBUG(3, ("recycle: File %s is empty, purging...\n", file_name)); 00455 rc = SMB_VFS_NEXT_UNLINK(handle,file_name); 00456 goto done; 00457 } 00458 */ 00459 00460 /* FIXME: this is wrong, we should check the whole size of the recycle bin is 00461 * not greater then maxsize, not the size of the single file, also it is better 00462 * to remove older files 00463 */ 00464 maxsize = recycle_maxsize(handle); 00465 if(maxsize > 0 && file_size > maxsize) { 00466 DEBUG(3, ("recycle: File %s exceeds maximum recycle size, purging... \n", file_name)); 00467 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00468 goto done; 00469 } 00470 minsize = recycle_minsize(handle); 00471 if(minsize > 0 && file_size < minsize) { 00472 DEBUG(3, ("recycle: File %s lowers minimum recycle size, purging... \n", file_name)); 00473 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00474 goto done; 00475 } 00476 00477 /* FIXME: this is wrong: moving files with rename does not change the disk space 00478 * allocation 00479 * 00480 space_avail = SMB_VFS_NEXT_DISK_FREE(handle, ".", True, &bsize, &dfree, &dsize) * 1024L; 00481 DEBUG(5, ("space_avail = %Lu, file_size = %Lu\n", space_avail, file_size)); 00482 if(space_avail < file_size) { 00483 DEBUG(3, ("recycle: Not enough diskspace, purging file %s\n", file_name)); 00484 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00485 goto done; 00486 } 00487 */ 00488 00489 /* extract filename and path */ 00490 base = strrchr(file_name, '/'); 00491 if (base == NULL) { 00492 base = file_name; 00493 path_name = SMB_STRDUP("/"); 00494 ALLOC_CHECK(path_name, done); 00495 } 00496 else { 00497 path_name = SMB_STRDUP(file_name); 00498 ALLOC_CHECK(path_name, done); 00499 path_name[base - file_name] = '\0'; 00500 base++; 00501 } 00502 00503 DEBUG(10, ("recycle: fname = %s\n", file_name)); /* original filename with path */ 00504 DEBUG(10, ("recycle: fpath = %s\n", path_name)); /* original path */ 00505 DEBUG(10, ("recycle: base = %s\n", base)); /* filename without path */ 00506 00507 if (matchparam(recycle_exclude(handle), base)) { 00508 DEBUG(3, ("recycle: file %s is excluded \n", base)); 00509 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00510 goto done; 00511 } 00512 00513 if (matchdirparam(recycle_exclude_dir(handle), path_name)) { 00514 DEBUG(3, ("recycle: directory %s is excluded \n", path_name)); 00515 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00516 goto done; 00517 } 00518 00519 if (recycle_keep_dir_tree(handle) == True) { 00520 asprintf(&temp_name, "%s/%s", repository, path_name); 00521 } else { 00522 temp_name = SMB_STRDUP(repository); 00523 } 00524 ALLOC_CHECK(temp_name, done); 00525 00526 exist = recycle_directory_exist(handle, temp_name); 00527 if (exist) { 00528 DEBUG(10, ("recycle: Directory already exists\n")); 00529 } else { 00530 DEBUG(10, ("recycle: Creating directory %s\n", temp_name)); 00531 if (recycle_create_dir(handle, temp_name) == False) { 00532 DEBUG(3, ("recycle: Could not create directory, purging %s...\n", file_name)); 00533 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00534 goto done; 00535 } 00536 } 00537 00538 asprintf(&final_name, "%s/%s", temp_name, base); 00539 ALLOC_CHECK(final_name, done); 00540 DEBUG(10, ("recycle: recycled file name: %s\n", final_name)); /* new filename with path */ 00541 00542 /* check if we should delete file from recycle bin */ 00543 if (recycle_file_exist(handle, final_name)) { 00544 if (recycle_versions(handle) == False || matchparam(recycle_noversions(handle), base) == True) { 00545 DEBUG(3, ("recycle: Removing old file %s from recycle bin\n", final_name)); 00546 if (SMB_VFS_NEXT_UNLINK(handle, final_name) != 0) { 00547 DEBUG(1, ("recycle: Error deleting old file: %s\n", strerror(errno))); 00548 } 00549 } 00550 } 00551 00552 /* rename file we move to recycle bin */ 00553 i = 1; 00554 while (recycle_file_exist(handle, final_name)) { 00555 SAFE_FREE(final_name); 00556 asprintf(&final_name, "%s/Copy #%d of %s", temp_name, i++, base); 00557 } 00558 00559 DEBUG(10, ("recycle: Moving %s to %s\n", file_name, final_name)); 00560 rc = SMB_VFS_NEXT_RENAME(handle, file_name, final_name); 00561 if (rc != 0) { 00562 DEBUG(3, ("recycle: Move error %d (%s), purging file %s (%s)\n", errno, strerror(errno), file_name, final_name)); 00563 rc = SMB_VFS_NEXT_UNLINK(handle, file_name); 00564 goto done; 00565 } 00566 00567 /* touch access date of moved file */ 00568 if (recycle_touch(handle) == True || recycle_touch_mtime(handle)) 00569 recycle_do_touch(handle, final_name, recycle_touch_mtime(handle)); 00570 00571 done: 00572 SAFE_FREE(path_name); 00573 SAFE_FREE(temp_name); 00574 SAFE_FREE(final_name); 00575 TALLOC_FREE(repository); 00576 return rc; 00577 }
static const char* recycle_repository | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 67 行で定義されています。
参照先 handle・lp_parm_const_string().
参照元 recycle_unlink().
00068 { 00069 const char *tmp_str = NULL; 00070 00071 00072 tmp_str = lp_parm_const_string(SNUM(handle->conn), "recycle", "repository",".recycle"); 00073 00074 DEBUG(10, ("recycle: repository = %s\n", tmp_str)); 00075 00076 return tmp_str; 00077 }
static BOOL recycle_keep_dir_tree | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 79 行で定義されています。
参照先 handle・lp_parm_bool().
参照元 recycle_unlink().
00080 { 00081 BOOL ret; 00082 00083 ret = lp_parm_bool(SNUM(handle->conn), "recycle", "keeptree", False); 00084 00085 DEBUG(10, ("recycle_bin: keeptree = %s\n", ret?"True":"False")); 00086 00087 return ret; 00088 }
static BOOL recycle_versions | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 90 行で定義されています。
参照先 handle・lp_parm_bool().
参照元 recycle_unlink().
00091 { 00092 BOOL ret; 00093 00094 ret = lp_parm_bool(SNUM(handle->conn), "recycle", "versions", False); 00095 00096 DEBUG(10, ("recycle: versions = %s\n", ret?"True":"False")); 00097 00098 return ret; 00099 }
static BOOL recycle_touch | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 101 行で定義されています。
参照先 handle・lp_parm_bool().
参照元 recycle_unlink().
00102 { 00103 BOOL ret; 00104 00105 ret = lp_parm_bool(SNUM(handle->conn), "recycle", "touch", False); 00106 00107 DEBUG(10, ("recycle: touch = %s\n", ret?"True":"False")); 00108 00109 return ret; 00110 }
static BOOL recycle_touch_mtime | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 112 行で定義されています。
参照先 handle・lp_parm_bool().
参照元 recycle_unlink().
00113 { 00114 BOOL ret; 00115 00116 ret = lp_parm_bool(SNUM(handle->conn), "recycle", "touch_mtime", False); 00117 00118 DEBUG(10, ("recycle: touch_mtime = %s\n", ret?"True":"False")); 00119 00120 return ret; 00121 }
static const char** recycle_exclude | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 123 行で定義されています。
参照先 handle・lp_parm_string_list().
参照元 recycle_unlink().
00124 { 00125 const char **tmp_lp; 00126 00127 tmp_lp = lp_parm_string_list(SNUM(handle->conn), "recycle", "exclude", NULL); 00128 00129 DEBUG(10, ("recycle: exclude = %s ...\n", tmp_lp?*tmp_lp:"")); 00130 00131 return tmp_lp; 00132 }
static const char** recycle_exclude_dir | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 134 行で定義されています。
参照先 handle・lp_parm_string_list().
参照元 recycle_unlink().
00135 { 00136 const char **tmp_lp; 00137 00138 tmp_lp = lp_parm_string_list(SNUM(handle->conn), "recycle", "exclude_dir", NULL); 00139 00140 DEBUG(10, ("recycle: exclude_dir = %s ...\n", tmp_lp?*tmp_lp:"")); 00141 00142 return tmp_lp; 00143 }
static const char** recycle_noversions | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 145 行で定義されています。
参照先 handle・lp_parm_string_list().
参照元 recycle_unlink().
00146 { 00147 const char **tmp_lp; 00148 00149 tmp_lp = lp_parm_string_list(SNUM(handle->conn), "recycle", "noversions", NULL); 00150 00151 DEBUG(10, ("recycle: noversions = %s\n", tmp_lp?*tmp_lp:"")); 00152 00153 return tmp_lp; 00154 }
static SMB_OFF_T recycle_maxsize | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 156 行で定義されています。
参照先 conv_str_size()・handle・lp_parm_const_string().
参照元 recycle_unlink().
00157 { 00158 SMB_OFF_T maxsize; 00159 00160 maxsize = conv_str_size(lp_parm_const_string(SNUM(handle->conn), 00161 "recycle", "maxsize", NULL)); 00162 00163 DEBUG(10, ("recycle: maxsize = %lu\n", (long unsigned int)maxsize)); 00164 00165 return maxsize; 00166 }
static SMB_OFF_T recycle_minsize | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 168 行で定義されています。
参照先 conv_str_size()・handle・lp_parm_const_string().
参照元 recycle_unlink().
00169 { 00170 SMB_OFF_T minsize; 00171 00172 minsize = conv_str_size(lp_parm_const_string(SNUM(handle->conn), 00173 "recycle", "minsize", NULL)); 00174 00175 DEBUG(10, ("recycle: minsize = %lu\n", (long unsigned int)minsize)); 00176 00177 return minsize; 00178 }
static mode_t recycle_directory_mode | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 180 行で定義されています。
参照先 handle・lp_parm_const_string().
参照元 recycle_create_dir()・recycle_subdir_mode().
00181 { 00182 int dirmode; 00183 const char *buff; 00184 00185 buff = lp_parm_const_string(SNUM(handle->conn), "recycle", "directory_mode", NULL); 00186 00187 if (buff != NULL ) { 00188 sscanf(buff, "%o", &dirmode); 00189 } else { 00190 dirmode=S_IRUSR | S_IWUSR | S_IXUSR; 00191 } 00192 00193 DEBUG(10, ("recycle: directory_mode = %o\n", dirmode)); 00194 return (mode_t)dirmode; 00195 }
static mode_t recycle_subdir_mode | ( | vfs_handle_struct * | handle | ) | [static] |
vfs_recycle.c の 197 行で定義されています。
参照先 handle・lp_parm_const_string()・recycle_directory_mode().
参照元 recycle_create_dir().
00198 { 00199 int dirmode; 00200 const char *buff; 00201 00202 buff = lp_parm_const_string(SNUM(handle->conn), "recycle", "subdir_mode", NULL); 00203 00204 if (buff != NULL ) { 00205 sscanf(buff, "%o", &dirmode); 00206 } else { 00207 dirmode=recycle_directory_mode(handle); 00208 } 00209 00210 DEBUG(10, ("recycle: subdir_mode = %o\n", dirmode)); 00211 return (mode_t)dirmode; 00212 }
static BOOL recycle_directory_exist | ( | vfs_handle_struct * | handle, | |
const char * | dname | |||
) | [static] |
vfs_recycle.c の 214 行で定義されています。
参照先 handle.
参照元 recycle_create_dir()・recycle_unlink().
00215 { 00216 SMB_STRUCT_STAT st; 00217 00218 if (SMB_VFS_NEXT_STAT(handle, dname, &st) == 0) { 00219 if (S_ISDIR(st.st_mode)) { 00220 return True; 00221 } 00222 } 00223 00224 return False; 00225 }
static BOOL recycle_file_exist | ( | vfs_handle_struct * | handle, | |
const char * | fname | |||
) | [static] |
vfs_recycle.c の 227 行で定義されています。
参照先 handle.
参照元 recycle_unlink().
00228 { 00229 SMB_STRUCT_STAT st; 00230 00231 if (SMB_VFS_NEXT_STAT(handle, fname, &st) == 0) { 00232 if (S_ISREG(st.st_mode)) { 00233 return True; 00234 } 00235 } 00236 00237 return False; 00238 }
static SMB_OFF_T recycle_get_file_size | ( | vfs_handle_struct * | handle, | |
const char * | fname | |||
) | [static] |
Return file size
conn | connection | |
fname | file name |
vfs_recycle.c の 246 行で定義されています。
参照先 errno・handle・strerror().
参照元 recycle_unlink().
00247 { 00248 SMB_STRUCT_STAT st; 00249 00250 if (SMB_VFS_NEXT_STAT(handle, fname, &st) != 0) { 00251 DEBUG(0,("recycle: stat for %s returned %s\n", fname, strerror(errno))); 00252 return (SMB_OFF_T)0; 00253 } 00254 00255 return(st.st_size); 00256 }
static BOOL recycle_create_dir | ( | vfs_handle_struct * | handle, | |
const char * | dname | |||
) | [static] |
Create directory tree
conn | connection | |
dname | Directory tree to be created |
vfs_recycle.c の 264 行で定義されています。
参照先 errno・handle・len・mode・recycle_directory_exist()・recycle_directory_mode()・recycle_subdir_mode()・strerror().
参照元 recycle_unlink().
00265 { 00266 size_t len; 00267 mode_t mode; 00268 char *new_dir = NULL; 00269 char *tmp_str = NULL; 00270 char *token; 00271 char *tok_str; 00272 BOOL ret = False; 00273 00274 mode = recycle_directory_mode(handle); 00275 00276 tmp_str = SMB_STRDUP(dname); 00277 ALLOC_CHECK(tmp_str, done); 00278 tok_str = tmp_str; 00279 00280 len = strlen(dname)+1; 00281 new_dir = (char *)SMB_MALLOC(len + 1); 00282 ALLOC_CHECK(new_dir, done); 00283 *new_dir = '\0'; 00284 if (dname[0] == '/') { 00285 /* Absolute path. */ 00286 safe_strcat(new_dir,"/",len); 00287 } 00288 00289 /* Create directory tree if neccessary */ 00290 for(token = strtok(tok_str, "/"); token; token = strtok(NULL, "/")) { 00291 safe_strcat(new_dir, token, len); 00292 if (recycle_directory_exist(handle, new_dir)) 00293 DEBUG(10, ("recycle: dir %s already exists\n", new_dir)); 00294 else { 00295 DEBUG(5, ("recycle: creating new dir %s\n", new_dir)); 00296 if (SMB_VFS_NEXT_MKDIR(handle, new_dir, mode) != 0) { 00297 DEBUG(1,("recycle: mkdir failed for %s with error: %s\n", new_dir, strerror(errno))); 00298 ret = False; 00299 goto done; 00300 } 00301 } 00302 safe_strcat(new_dir, "/", len); 00303 mode = recycle_subdir_mode(handle); 00304 } 00305 00306 ret = True; 00307 done: 00308 SAFE_FREE(tmp_str); 00309 SAFE_FREE(new_dir); 00310 return ret; 00311 }
static BOOL matchdirparam | ( | const char ** | dir_exclude_list, | |
char * | path | |||
) | [static] |
Check if any of the components of "exclude_list" are contained in path.
Return True if found
vfs_recycle.c の 318 行で定義されています。
参照先 unix_wild_match().
参照元 recycle_unlink().
00319 { 00320 char *startp = NULL, *endp = NULL; 00321 00322 if (dir_exclude_list == NULL || dir_exclude_list[0] == NULL || 00323 *dir_exclude_list[0] == '\0' || path == NULL || *path == '\0') { 00324 return False; 00325 } 00326 00327 /* 00328 * Walk the components of path, looking for matches with the 00329 * exclude list on each component. 00330 */ 00331 00332 for (startp = path; startp; startp = endp) { 00333 int i; 00334 00335 while (*startp == '/') { 00336 startp++; 00337 } 00338 endp = strchr(startp, '/'); 00339 if (endp) { 00340 *endp = '\0'; 00341 } 00342 00343 for(i=0; dir_exclude_list[i] ; i++) { 00344 if(unix_wild_match(dir_exclude_list[i], startp)) { 00345 /* Repair path. */ 00346 if (endp) { 00347 *endp = '/'; 00348 } 00349 return True; 00350 } 00351 } 00352 00353 /* Repair path. */ 00354 if (endp) { 00355 *endp = '/'; 00356 } 00357 } 00358 00359 return False; 00360 }
static BOOL matchparam | ( | const char ** | haystack_list, | |
const char * | needle | |||
) | [static] |
Check if needle is contained in haystack, * and ? patterns are resolved
haystack | list of parameters separated by delimimiter character | |
needle | string to be matched exectly to haystack including pattern matching |
vfs_recycle.c の 368 行で定義されています。
参照先 unix_wild_match().
参照元 recycle_unlink().
00369 { 00370 int i; 00371 00372 if (haystack_list == NULL || haystack_list[0] == NULL || 00373 *haystack_list[0] == '\0' || needle == NULL || *needle == '\0') { 00374 return False; 00375 } 00376 00377 for(i=0; haystack_list[i] ; i++) { 00378 if(unix_wild_match(haystack_list[i], needle)) { 00379 return True; 00380 } 00381 } 00382 00383 return False; 00384 }
static void recycle_do_touch | ( | vfs_handle_struct * | handle, | |
const char * | fname, | |||
BOOL | touch_mtime | |||
) | [static] |
Touch access or modify date
vfs_recycle.c の 389 行で定義されています。
参照先 errno・get_mtimespec()・handle・strerror()・timespec_current().
参照元 recycle_unlink().
00390 { 00391 SMB_STRUCT_STAT st; 00392 struct timespec ts[2]; 00393 00394 if (SMB_VFS_NEXT_STAT(handle, fname, &st) != 0) { 00395 DEBUG(0,("recycle: stat for %s returned %s\n", fname, strerror(errno))); 00396 return; 00397 } 00398 ts[0] = timespec_current(); /* atime */ 00399 ts[1] = touch_mtime ? ts[0] : get_mtimespec(&st); /* mtime */ 00400 00401 if (SMB_VFS_NEXT_NTIMES(handle, fname, ts) == -1 ) { 00402 DEBUG(0, ("recycle: touching %s failed, reason = %s\n", fname, strerror(errno))); 00403 } 00404 }
NTSTATUS vfs_recycle_init | ( | void | ) |
vfs_recycle.c の 580 行で定義されています。
参照先 debug_add_class()・recycle_ops・smb_register_vfs()・vfs_recycle_debug_level.
00581 { 00582 NTSTATUS ret = smb_register_vfs(SMB_VFS_INTERFACE_VERSION, "recycle", recycle_ops); 00583 00584 if (!NT_STATUS_IS_OK(ret)) 00585 return ret; 00586 00587 vfs_recycle_debug_level = debug_add_class("recycle"); 00588 if (vfs_recycle_debug_level == -1) { 00589 vfs_recycle_debug_level = DBGC_VFS; 00590 DEBUG(0, ("vfs_recycle: Couldn't register custom debugging class!\n")); 00591 } else { 00592 DEBUG(10, ("vfs_recycle: Debug class number of 'recycle': %d\n", vfs_recycle_debug_level)); 00593 } 00594 00595 return ret; 00596 }
int vfs_recycle_debug_level = DBGC_VFS [static] |
vfs_op_tuple recycle_ops[] [static] |
初期値:
{ {SMB_VFS_OP(recycle_connect), SMB_VFS_OP_CONNECT, SMB_VFS_LAYER_TRANSPARENT}, {SMB_VFS_OP(recycle_disconnect), SMB_VFS_OP_DISCONNECT, SMB_VFS_LAYER_TRANSPARENT}, {SMB_VFS_OP(recycle_unlink), SMB_VFS_OP_UNLINK, SMB_VFS_LAYER_TRANSPARENT}, {SMB_VFS_OP(NULL), SMB_VFS_OP_NOOP, SMB_VFS_LAYER_NOOP} }
vfs_recycle.c の 39 行で定義されています。
参照元 vfs_recycle_init().
substitute.c の 29 行で定義されています。