📄 os0file.c
字号:
access = 0; ut_error; } file = CreateFile((LPCTSTR) name, access, share_mode, NULL, /* default security attributes */ create_flag, attributes, NULL); /* no template file */ if (file == INVALID_HANDLE_VALUE) { *success = FALSE; } else { *success = TRUE; } return(file);#else /* __WIN__ */ os_file_t file; int create_flag; ut_a(name); if (create_mode == OS_FILE_OPEN) { if (access_type == OS_FILE_READ_ONLY) { create_flag = O_RDONLY; } else { create_flag = O_RDWR; } } else if (create_mode == OS_FILE_CREATE) { create_flag = O_RDWR | O_CREAT | O_EXCL; } else { create_flag = 0; ut_error; } if (create_mode == OS_FILE_CREATE) { file = open(name, create_flag, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP); } else { file = open(name, create_flag); } if (file == -1) { *success = FALSE;#ifdef USE_FILE_LOCK } else if (access_type == OS_FILE_READ_WRITE && os_file_lock(file, name)) { *success = FALSE; close(file); file = -1;#endif } else { *success = TRUE; } return(file); #endif /* __WIN__ */}/********************************************************************Opens an existing file or creates a new. */os_file_tos_file_create(/*===========*/ /* out, own: handle to the file, not defined if error, error number can be retrieved with os_file_get_last_error */ const char* name, /* in: name of the file or path as a null-terminated string */ ulint create_mode,/* in: OS_FILE_OPEN if an existing file is opened (if does not exist, error), or OS_FILE_CREATE if a new file is created (if exists, error), OS_FILE_OVERWRITE if a new file is created or an old overwritten; OS_FILE_OPEN_RAW, if a raw device or disk partition should be opened */ ulint purpose,/* in: OS_FILE_AIO, if asynchronous, non-buffered i/o is desired, OS_FILE_NORMAL, if any normal file; NOTE that it also depends on type, os_aio_.. and srv_.. variables whether we really use async i/o or unbuffered i/o: look in the function source code for the exact rules */ ulint type, /* in: OS_DATA_FILE or OS_LOG_FILE */ ibool* success)/* out: TRUE if succeed, FALSE if error */{#ifdef __WIN__ os_file_t file; DWORD share_mode = FILE_SHARE_READ; DWORD create_flag; DWORD attributes; ibool retry;try_again: ut_a(name); if (create_mode == OS_FILE_OPEN_RAW) { create_flag = OPEN_EXISTING; share_mode = FILE_SHARE_WRITE; } else if (create_mode == OS_FILE_OPEN || create_mode == OS_FILE_OPEN_RETRY) { create_flag = OPEN_EXISTING; } else if (create_mode == OS_FILE_CREATE) { create_flag = CREATE_NEW; } else if (create_mode == OS_FILE_OVERWRITE) { create_flag = CREATE_ALWAYS; } else { create_flag = 0; ut_error; } if (purpose == OS_FILE_AIO) { /* If specified, use asynchronous (overlapped) io and no buffering of writes in the OS */ attributes = 0;#ifdef WIN_ASYNC_IO if (os_aio_use_native_aio) { attributes = attributes | FILE_FLAG_OVERLAPPED; }#endif #ifdef UNIV_NON_BUFFERED_IO if (type == OS_LOG_FILE && srv_flush_log_at_trx_commit == 2) { /* Do not use unbuffered i/o to log files because value 2 denotes that we do not flush the log at every commit, but only once per second */ } else if (srv_win_file_flush_method == SRV_WIN_IO_UNBUFFERED) { attributes = attributes | FILE_FLAG_NO_BUFFERING; }#endif } else if (purpose == OS_FILE_NORMAL) { attributes = 0;#ifdef UNIV_NON_BUFFERED_IO if (type == OS_LOG_FILE && srv_flush_log_at_trx_commit == 2) { /* Do not use unbuffered i/o to log files because value 2 denotes that we do not flush the log at every commit, but only once per second */ } else if (srv_win_file_flush_method == SRV_WIN_IO_UNBUFFERED) { attributes = attributes | FILE_FLAG_NO_BUFFERING; }#endif } else { attributes = 0; ut_error; } file = CreateFile((LPCTSTR) name, GENERIC_READ | GENERIC_WRITE, /* read and write access */ share_mode, /* File can be read also by other processes; we must give the read permission because of ibbackup. We do not give the write permission to others because if one would succeed to start 2 instances of mysqld on the SAME files, that could cause severe database corruption! When opening raw disk partitions, Microsoft manuals say that we must give also the write permission. */ NULL, /* default security attributes */ create_flag, attributes, NULL); /* no template file */ if (file == INVALID_HANDLE_VALUE) { *success = FALSE; retry = os_file_handle_error(name, create_mode == OS_FILE_CREATE ? "create" : "open"); if (retry) { goto try_again; } } else { *success = TRUE; } return(file);#else /* __WIN__ */ os_file_t file; int create_flag; ibool retry; const char* mode_str = NULL; const char* type_str = NULL; const char* purpose_str = NULL; try_again: ut_a(name); if (create_mode == OS_FILE_OPEN || create_mode == OS_FILE_OPEN_RAW || create_mode == OS_FILE_OPEN_RETRY) { mode_str = "OPEN"; create_flag = O_RDWR; } else if (create_mode == OS_FILE_CREATE) { mode_str = "CREATE"; create_flag = O_RDWR | O_CREAT | O_EXCL; } else if (create_mode == OS_FILE_OVERWRITE) { mode_str = "OVERWRITE"; create_flag = O_RDWR | O_CREAT | O_TRUNC; } else { create_flag = 0; ut_error; } if (type == OS_LOG_FILE) { type_str = "LOG"; } else if (type == OS_DATA_FILE) { type_str = "DATA"; } else { ut_error; } if (purpose == OS_FILE_AIO) { purpose_str = "AIO"; } else if (purpose == OS_FILE_NORMAL) { purpose_str = "NORMAL"; } else { ut_error; }/* fprintf(stderr, "Opening file %s, mode %s, type %s, purpose %s\n", name, mode_str, type_str, purpose_str); */#ifdef O_SYNC /* We let O_SYNC only affect log files; note that we map O_DSYNC to O_SYNC because the datasync options seemed to corrupt files in 2001 in both Linux and Solaris */ if (type == OS_LOG_FILE && srv_unix_file_flush_method == SRV_UNIX_O_DSYNC) {/* fprintf(stderr, "Using O_SYNC for file %s\n", name); */ create_flag = create_flag | O_SYNC; }#endif#ifdef O_DIRECT /* We let O_DIRECT only affect data files */ if (type != OS_LOG_FILE && srv_unix_file_flush_method == SRV_UNIX_O_DIRECT) {/* fprintf(stderr, "Using O_DIRECT for file %s\n", name); */ create_flag = create_flag | O_DIRECT; }#endif if (create_mode == OS_FILE_CREATE) { file = open(name, create_flag, os_innodb_umask); } else { file = open(name, create_flag); } if (file == -1) { *success = FALSE; retry = os_file_handle_error(name, create_mode == OS_FILE_CREATE ? "create" : "open"); if (retry) { goto try_again; }#ifdef USE_FILE_LOCK } else if (create_mode != OS_FILE_OPEN_RAW && os_file_lock(file, name)) { *success = FALSE; if (create_mode == OS_FILE_OPEN_RETRY) { int i; ut_print_timestamp(stderr); fputs(" InnoDB: Retrying to lock the first data file\n", stderr); for (i = 0; i < 100; i++) { os_thread_sleep(1000000); if (!os_file_lock(file, name)) { *success = TRUE; return(file); } } ut_print_timestamp(stderr); fputs(" InnoDB: Unable to open the first data file\n", stderr); } close(file); file = -1;#endif } else { *success = TRUE; } return(file); #endif /* __WIN__ */}/***************************************************************************Deletes a file if it exists. The file has to be closed before calling this. */iboolos_file_delete_if_exists(/*=====================*/ /* out: TRUE if success */ const char* name) /* in: file path as a null-terminated string */{#ifdef __WIN__ BOOL ret; ulint count = 0;loop: /* In Windows, deleting an .ibd file may fail if ibbackup is copying it */ ret = DeleteFile((LPCTSTR)name); if (ret) { return(TRUE); } if (GetLastError() == ERROR_FILE_NOT_FOUND) { /* the file does not exist, this not an error */ return(TRUE); } count++; if (count > 100 && 0 == (count % 10)) { fprintf(stderr,"InnoDB: Warning: cannot delete file %s\n""InnoDB: Are you running ibbackup to back up the file?\n", name); os_file_get_last_error(TRUE); /* print error information */ } os_thread_sleep(1000000); /* sleep for a second */ if (count > 2000) { return(FALSE); } goto loop;#else int ret; ret = unlink((const char*)name); if (ret != 0 && errno != ENOENT) { os_file_handle_error_no_exit(name, "delete"); return(FALSE); } return(TRUE);#endif}/***************************************************************************Deletes a file. The file has to be closed before calling this. */iboolos_file_delete(/*===========*/ /* out: TRUE if success */ const char* name) /* in: file path as a null-terminated string */{#ifdef __WIN__ BOOL ret; ulint count = 0;loop: /* In Windows, deleting an .ibd file may fail if ibbackup is copying it */ ret = DeleteFile((LPCTSTR)name); if (ret) { return(TRUE); } if (GetLastError() == ERROR_FILE_NOT_FOUND) { /* If the file does not exist, we classify this as a 'mild' error and return */ return(FALSE); } count++; if (count > 100 && 0 == (count % 10)) { fprintf(stderr,"InnoDB: Warning: cannot delete file %s\n""InnoDB: Are you running ibbackup to back up the file?\n", name); os_file_get_last_error(TRUE); /* print error information */ } os_thread_sleep(1000000); /* sleep for a second */ if (count > 2000) { return(FALSE); } goto loop;#else int ret; ret = unlink((const char*)name); if (ret != 0) { os_file_handle_error_no_exit(name, "delete"); return(FALSE); } return(TRUE);#endif}/***************************************************************************Renames a file (can also move it to another directory). It is safest that thefile is closed before calling this function. */iboolos_file_rename(/*===========*/ /* out: TRUE if success */ const char* oldpath,/* in: old file path as a null-terminated string */ const char* newpath)/* in: new file path */{#ifdef __WIN__ BOOL ret; ret = MoveFile((LPCTSTR)oldpath, (LPCTSTR)newpath); if (ret) { return(TRUE); } os_file_handle_error(oldpath, "rename"); return(FALSE);#else int ret; ret = rename((const char*)oldpath, (const char*)newpath); if (ret != 0) { os_file_handle_error(oldpath, "rename"); return(FALSE); } return(TRUE);#endif}/***************************************************************************Closes a file handle. In case of error, error number can be retrieved withos_file_get_last_error. */iboolos_file_close(/*==========*/ /* out: TRUE if success */ os_file_t file) /* in, own: handle to a file */{#ifdef __WIN__ BOOL ret; ut_a(file); ret = CloseHandle(file); if (ret) { return(TRUE); } os_file_handle_error(NULL, "close"); return(FALSE);#else int ret; ret = close(file); if (ret == -1) { os_file_handle_error(NULL, "close"); return(FALSE); } return(TRUE);#endif}/***************************************************************************Closes a file handle. */iboolos_file_close_no_error_handling(/*============================*/ /* out: TRUE if success */ os_file_t file) /* in, own: handle to a file */{#ifdef __WIN__ BOOL ret; ut_a(file); ret = CloseHandle(file); if (ret) { return(TRUE); } return(FALSE);#else int ret; ret = close(file); if (ret == -1) { return(FALSE); }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -