📄 output-file.c
字号:
result = fullwrite(file_fd, buffer, (size_t)write_count); if (result >= 0) { volume_info[fd].last_operation_write = 1; pos = volume_info[fd].file_current; put_record_size(&volume_info[fd].fi[pos], volume_info[fd].record_current, (size_t)result); volume_info[fd].record_current += (off_t)1; } return result;}intfile_tapefd_close( int fd){ off_t pos; int save_errno; char *line; size_t len; ssize_t result; struct file_info **fi_p; struct record_info **ri_p; /* * If our last operation was a write, write a tapemark. */ if (volume_info[fd].last_operation_write) { if ((result = (ssize_t)file_tapefd_weof(fd, (off_t)1)) != 0) { return (int)result; } } /* * If we are not at BOF, fsf to the next file unless we * are already at end of tape. */ if (! volume_info[fd].at_bof && ! volume_info[fd].at_eom) { if ((result = (ssize_t)file_tapefd_fsf(fd, (off_t)1)) != 0) { return (int)result; } } /* * Close the file if it is still open. */ file_close(fd); /* * Release the info structure areas. */ for (pos = 0; pos < (off_t)volume_info[fd].fi_limit; pos++) { amfree(volume_info[fd].fi[pos].name); ri_p = &volume_info[fd].fi[pos].ri; amtable_free((void **)ri_p, &volume_info[fd].fi[pos].ri_limit); volume_info[fd].fi[pos].ri_count = 0; } fi_p = &volume_info[fd].fi; amtable_free((void **)fi_p, &volume_info[fd].fi_limit); volume_info[fd].file_count = 0; amfree(volume_info[fd].basename); /* * Update the status file if we were online. */ if (volume_info[fd].is_online) { if (lseek(fd, (off_t)0, SEEK_SET) != (off_t)0) { save_errno = errno; aclose(fd); errno = save_errno; return -1; } if (ftruncate(fd, (off_t)0) != 0) { save_errno = errno; aclose(fd); errno = save_errno; return -1; } line = vstrallocf("position %05lld\n", (long long)volume_info[fd].file_current); len = strlen(line); result = write(fd, line, len); amfree(line); if (result != (ssize_t)len) { if (result >= 0) { errno = ENOSPC; } save_errno = errno; aclose(fd); errno = save_errno; return -1; } } areads_relbuf(fd); return close(fd);}voidfile_tapefd_resetofs( int fd){ (void)fd; /* Quiet unused parameter warning */}intfile_tapefd_status( int fd, struct am_mt_status *stat){ int result; /* * See if we are online. */ if ((result = check_online(fd)) != 0) { return result; } memset((void *)stat, 0, SIZEOF(*stat)); stat->online_valid = 1; stat->online = (char)volume_info[fd].is_online; return 0;}intfile_tape_stat( char * filename, struct stat * buf){ return stat(filename, buf);}intfile_tape_access( char * filename, int mode){ return access(filename, mode);}intfile_tapefd_rewind( int fd){ int result; /* * Make sure we are online. */ if ((result = check_online(fd)) != 0) { return result; } if (! volume_info[fd].is_online) { errno = EIO; return -1; } /* * If our last operation was a write, write a tapemark. */ if (volume_info[fd].last_operation_write) { if ((result = file_tapefd_weof(fd, (off_t)1)) != 0) { return result; } } /* * Close the file if it is still open. */ file_close(fd); /* * Adjust the position and reset the flags. */ volume_info[fd].file_current = 0; volume_info[fd].record_current = (off_t)0; volume_info[fd].at_bof = 1; volume_info[fd].at_eof = 0; volume_info[fd].at_eom = (volume_info[fd].file_current >= volume_info[fd].file_count); volume_info[fd].last_operation_write = 0; volume_info[fd].amount_written = (off_t)0; return result;}intfile_tapefd_unload( int fd){ int result; /* * Make sure we are online. */ if ((result = check_online(fd)) != 0) { return result; } if (! volume_info[fd].is_online) { errno = EIO; return -1; } (void)file_tapefd_rewind(fd); return 0;}intfile_tapefd_fsf( int fd, off_t count){ int result; /* * Make sure we are online. */ if ((result = check_online(fd)) != 0) { return result; } if (! volume_info[fd].is_online) { errno = EIO; return -1; } /* * If our last operation was a write and we are going to move * backward, write a tapemark. */ if (volume_info[fd].last_operation_write && count < 0) { if ((result = file_tapefd_weof(fd, (off_t)1)) != 0) { errno = EIO; return -1; } } /* * Close the file if it is still open. */ file_close(fd); /* * If we are at EOM and moving backward, adjust the count to go * one more file. */ if (volume_info[fd].at_eom && count < 0) { count--; } /* * Adjust the position and return an error if we go beyond either * end of the tape. */ volume_info[fd].file_current += count; if (volume_info[fd].file_current > volume_info[fd].file_count) { volume_info[fd].file_current = volume_info[fd].file_count; errno = EIO; result = -1; } else if (volume_info[fd].file_current < 0) { volume_info[fd].file_current = 0; errno = EIO; result = -1; } volume_info[fd].record_current = (off_t)0; /* * Set BOF to true so we can write. Set to EOF to false if the * fsf succeeded or if it failed but we were moving backward (and * thus we are at beginning of tape), otherwise set it to true so * a subsequent read will fail. Set EOM to whatever is right. * Reset amount_written if we ended up back at BOM. */ volume_info[fd].at_bof = 1; if (result == 0 || count < 0) { volume_info[fd].at_eof = 0; } else { volume_info[fd].at_eof = 1; } volume_info[fd].at_eom = (volume_info[fd].file_current >= volume_info[fd].file_count); volume_info[fd].last_operation_write = 0; if (volume_info[fd].file_current == 0) { volume_info[fd].amount_written = (off_t)0; } return result;}intfile_tapefd_weof( int fd, off_t count){ int file_fd; int result; char *save_host; char *save_disk; int save_level; int save_errno; /* * Make sure we are online. */ if ((result = check_online(fd)) != 0) { return result; } if (! volume_info[fd].is_online) { errno = EIO; return -1; } /* * Check for write access first. */ if ((volume_info[fd].flags & 3) == O_RDONLY) { errno = EACCES; return -1; } /* * Special case: allow a zero count. */ if (count == 0) { return 0; /* special case */ } /* * Disallow negative count. */ if (count < 0) { errno = EINVAL; return -1; } /* * Close out the current file if open. */ if ((file_fd = volume_info[fd].fd) >= 0) { off_t curpos; if ((curpos = lseek(file_fd, (off_t)0, SEEK_CUR)) < 0) { save_errno = errno; dbprintf(_(": Can not determine current file position <%s>"), strerror(errno)); file_close(fd); errno = save_errno; return -1; } if (ftruncate(file_fd, curpos) != 0) { save_errno = errno; dbprintf(_("ftruncate failed; Can not trim output file <%s>"), strerror(errno)); file_close(fd); errno = save_errno; return -1; } file_close(fd); volume_info[fd].file_current++; volume_info[fd].record_current = (off_t)0; volume_info[fd].at_bof = 1; volume_info[fd].at_eof = 0; volume_info[fd].at_eom = 1; volume_info[fd].last_operation_write = 0; count--; } /* * Release any data files from current through the end. */ file_release(fd); /* * Save any labelling information in case we clobber it. */ if ((save_host = tapefd_getinfo_host(fd)) != NULL) { save_host = stralloc(save_host); } if ((save_disk = tapefd_getinfo_disk(fd)) != NULL) { save_disk = stralloc(save_disk); } save_level = tapefd_getinfo_level(fd); /* * Add more tapemarks. */ while (--count >= 0) { if (file_open(fd) < 0) { break; } file_close(fd); volume_info[fd].file_current++; volume_info[fd].file_count = volume_info[fd].file_current; volume_info[fd].record_current = (off_t)0; volume_info[fd].at_bof = 1; volume_info[fd].at_eof = 0; volume_info[fd].at_eom = 1; volume_info[fd].last_operation_write = 0; /* * Only the first "file" terminated by an EOF gets the naming * information from the caller. */ tapefd_setinfo_host(fd, NULL); tapefd_setinfo_disk(fd, NULL); tapefd_setinfo_level(fd, -1); } /* * Restore the labelling information. */ save_errno = errno; tapefd_setinfo_host(fd, save_host); amfree(save_host); tapefd_setinfo_disk(fd, save_disk); amfree(save_disk); tapefd_setinfo_level(fd, save_level); errno = save_errno; return result;}intfile_tapefd_can_fork( int fd){ (void)fd; /* Quiet unused parameter warning */ return 0;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -