int _nisam_write_static_record(N_INFO *info, const byte *record) { uchar temp[4]; /* Not sizeof(long) */ if (info->s->state.dellink != NI_POS_ERROR) { ulong filepos=info->s->state.dellink; info->rec_cache.seek_not_done=1; /* We have done a seek */ VOID(my_seek(info->dfile,info->s->state.dellink+1,MY_SEEK_SET,MYF(0))); if (my_read(info->dfile,(char*) &temp[0],sizeof(temp), MYF(MY_NABP))) goto err; info->s->state.dellink=uint4korr(temp); if (info->s->state.dellink == (uint32) ~0) /* Fix for 64 bit long */ info->s->state.dellink=NI_POS_ERROR; info->s->state.del--; info->s->state.empty-=info->s->base.reclength; VOID(my_seek(info->dfile,filepos,MY_SEEK_SET,MYF(0))); if (my_write(info->dfile, (char*) record, info->s->base.reclength, MYF(MY_NABP))) goto err; } else { if (info->s->state.data_file_length > info->s->base.max_data_file_length) { my_errno=HA_ERR_RECORD_FILE_FULL; return(2); } if (info->opt_flag & WRITE_CACHE_USED) { /* Cash in use */ if (my_b_write(&info->rec_cache, (byte*) record, info->s->base.reclength)) goto err; } else { info->rec_cache.seek_not_done=1; /* We have done a seek */ VOID(my_seek(info->dfile,info->s->state.data_file_length, MY_SEEK_SET,MYF(0))); if (my_write(info->dfile,(char*) record,info->s->base.reclength, MYF(MY_NABP | MY_WAIT_IF_FULL))) goto err; } info->s->state.data_file_length+=info->s->base.reclength; info->s->state.splitt++; } return 0; err: return 1; }
int _nisam_cmp_static_record(register N_INFO *info, register const byte *old) { DBUG_ENTER("_nisam_rectest"); /* We are going to do changes; dont let anybody disturb */ dont_break(); /* Dont allow SIGHUP or SIGINT */ if (info->opt_flag & WRITE_CACHE_USED) { if (flush_io_cache(&info->rec_cache)) { DBUG_RETURN(-1); } info->rec_cache.seek_not_done=1; /* We have done a seek */ } if ((info->opt_flag & READ_CHECK_USED)) { /* If check isn't disabled */ info->rec_cache.seek_not_done=1; /* We have done a seek */ VOID(my_seek(info->dfile,info->lastpos,MY_SEEK_SET,MYF(0))); if (my_read(info->dfile, (char*) info->rec_buff, info->s->base.reclength, MYF(MY_NABP))) DBUG_RETURN(-1); if (memcmp((byte*) info->rec_buff, (byte*) old, (uint) info->s->base.reclength)) { DBUG_DUMP("read",old,info->s->base.reclength); DBUG_DUMP("disk",info->rec_buff,info->s->base.reclength); my_errno=HA_ERR_RECORD_CHANGED; /* Record have changed */ DBUG_RETURN(1); } } DBUG_RETURN(0); }
int _nisam_update_static_record(N_INFO *info, ulong pos, const byte *record) { info->rec_cache.seek_not_done=1; /* We have done a seek */ VOID(my_seek(info->dfile,pos,MY_SEEK_SET,MYF(0))); return (my_write(info->dfile,(char*) record,info->s->base.reclength, MYF(MY_NABP)) != 0); }
my_off_t my_b_append_tell(IO_CACHE* info) { /* Sometimes we want to make sure that the variable is not put into a register in debugging mode so we can see its value in the core */ #ifndef DBUG_OFF # define dbug_volatile volatile #else # define dbug_volatile #endif /* Prevent optimizer from putting res in a register when debugging we need this to be able to see the value of res when the assert fails */ dbug_volatile my_off_t res; /* We need to lock the append buffer mutex to keep flush_io_cache() from messing with the variables that we need in order to provide the answer to the question. */ mysql_mutex_lock(&info->append_buffer_lock); #ifndef DBUG_OFF /* Make sure EOF is where we think it is. Note that we cannot just use my_tell() because we have a reader thread that could have left the file offset in a non-EOF location */ { volatile my_off_t save_pos; save_pos = my_tell(info->file,MYF(0)); my_seek(info->file,(my_off_t)0,MY_SEEK_END,MYF(0)); /* Save the value of my_tell in res so we can see it when studying coredump */ DBUG_ASSERT(info->end_of_file - (info->append_read_pos-info->write_buffer) == (res=my_tell(info->file,MYF(0)))); my_seek(info->file,save_pos,MY_SEEK_SET,MYF(0)); } #endif res = info->end_of_file + (info->write_pos-info->append_read_pos); mysql_mutex_unlock(&info->append_buffer_lock); return res; }
my_off_t my_b_filelength(IO_CACHE *info) { if (info->type == WRITE_CACHE) return my_b_tell(info); info->seek_not_done= 1; return my_seek(info->file, 0L, MY_SEEK_END, MYF(0)); }
int _nisam_delete_static_record(N_INFO *info) { uchar temp[5]; /* 1+sizeof(uint32) */ info->s->state.del++; info->s->state.empty+=info->s->base.reclength; temp[0]= '\0'; /* Mark that record is deleted */ int4store(temp+1,info->s->state.dellink); info->s->state.dellink = info->lastpos; info->rec_cache.seek_not_done=1; VOID(my_seek(info->dfile,info->lastpos,MY_SEEK_SET,MYF(0))); return (my_write(info->dfile,(byte*) temp,(uint) sizeof(temp), MYF(MY_NABP)) != 0); }
my_off_t my_tell(File fd, myf MyFlags) { os_off_t pos; DBUG_ENTER("my_tell"); DBUG_PRINT("my",("fd: %d MyFlags: %d",fd, MyFlags)); DBUG_ASSERT(fd >= 0); #if defined (HAVE_TELL) && !defined (_WIN32) pos= tell(fd); #else pos= my_seek(fd, 0L, MY_SEEK_CUR,0); #endif if (pos == (os_off_t) -1) { my_errno= errno; if (MyFlags & MY_WME) my_error(EE_CANT_SEEK, MYF(0), my_filename(fd), my_errno); DBUG_PRINT("error", ("tell: %llu errno: %d", (ulonglong) pos, my_errno)); } DBUG_PRINT("exit",("pos: %llu", (ulonglong) pos)); DBUG_RETURN((my_off_t) pos); } /* my_tell */
size_t my_b_fill(IO_CACHE *info) { my_off_t pos_in_file=(info->pos_in_file+ (size_t) (info->read_end - info->buffer)); size_t diff_length, length, max_length; if (info->seek_not_done) { /* File touched, do seek */ if (my_seek(info->file,pos_in_file,MY_SEEK_SET,MYF(0)) == MY_FILEPOS_ERROR) { info->error= 0; return 0; } info->seek_not_done=0; } diff_length=(size_t) (pos_in_file & (IO_SIZE-1)); max_length=(info->read_length-diff_length); if (max_length >= (info->end_of_file - pos_in_file)) max_length= (size_t) (info->end_of_file - pos_in_file); if (!max_length) { info->error= 0; return 0; /* EOF */ } if ((length= my_read(info->file,info->buffer,max_length, info->myflags)) == (size_t) -1) { info->error= -1; return 0; } info->read_pos=info->buffer; info->read_end=info->buffer+length; info->pos_in_file=pos_in_file; return length; }
int _nisam_read_cache(IO_CACHE *info, byte *buff, ulong pos, uint length, int flag) { uint read_length,in_buff_length; ulong offset; char *in_buff_pos; if (pos < info->pos_in_file) { read_length= (uint) min((ulong) length,(ulong) (info->pos_in_file-pos)); info->seek_not_done=1; VOID(my_seek(info->file,pos,MY_SEEK_SET,MYF(0))); if (my_read(info->file,buff,read_length,MYF(MY_NABP))) return 1; if (!(length-=read_length)) return 0; pos+=read_length; buff+=read_length; } if ((offset=pos - (ulong) info->pos_in_file) < (ulong) (info->read_end - info->request_pos)) { in_buff_pos=info->request_pos+(uint) offset; in_buff_length= min(length,(uint) (info->read_end-in_buff_pos)); memcpy(buff,info->request_pos+(uint) offset,(size_t) in_buff_length); if (!(length-=in_buff_length)) return 0; pos+=in_buff_length; buff+=in_buff_length; } else in_buff_length=0; if (flag & READING_NEXT) { if (pos != ((info)->pos_in_file + (uint) ((info)->read_end - (info)->request_pos))) { info->pos_in_file=pos; /* Force start here */ info->read_pos=info->read_end=info->request_pos; /* Everything used */ info->seek_not_done=1; } else info->read_pos=info->read_end; /* All block used */ if (!(*info->read_function)(info,buff,length)) return 0; if (!(flag & READING_HEADER) || info->error == -1 || (uint) info->error+in_buff_length < 3) return 1; if (BLOCK_INFO_HEADER_LENGTH < in_buff_length + (uint) info->error) bzero(buff+info->error,BLOCK_INFO_HEADER_LENGTH - in_buff_length - (uint) info->error); return 0; } info->seek_not_done=1; VOID(my_seek(info->file,pos,MY_SEEK_SET,MYF(0))); if ((read_length=my_read(info->file,buff,length,MYF(0))) == length) return 0; if (!(flag & READING_HEADER) || (int) read_length == -1 || read_length+in_buff_length < 3) return 1; bzero(buff+read_length,BLOCK_INFO_HEADER_LENGTH - in_buff_length - read_length); return 0; } /* _nisam_read_cache */
/* =========================================================================== Opens a gzip (.gz) file for reading or writing. The mode parameter is as in fopen ("rb" or "wb"). The file is given either by file descriptor or path name (if fd == -1). az_open returns NULL if the file could not be opened or if there was insufficient memory to allocate the (de)compression state; errno can be checked to distinguish the two cases (if errno is zero, the zlib error is Z_MEM_ERROR). */ int az_open (azio_stream *s, const char *path, int Flags, File fd) { int err; int level = Z_DEFAULT_COMPRESSION; /* compression level */ int strategy = Z_DEFAULT_STRATEGY; /* compression strategy */ s->stream.zalloc = (alloc_func)0; s->stream.zfree = (free_func)0; s->stream.opaque = (voidpf)0; memset(s->inbuf, 0, AZ_BUFSIZE_READ); memset(s->outbuf, 0, AZ_BUFSIZE_WRITE); s->stream.next_in = s->inbuf; s->stream.next_out = s->outbuf; s->stream.avail_in = s->stream.avail_out = 0; s->z_err = Z_OK; s->z_eof = 0; s->in = 0; s->out = 0; s->back = EOF; s->crc = crc32(0L, Z_NULL, 0); s->transparent = 0; s->mode = 'r'; s->version = (unsigned char)az_magic[1]; /* this needs to be a define to version */ s->minor_version= (unsigned char) az_magic[2]; /* minor version */ s->dirty= AZ_STATE_CLEAN; /* We do our own version of append by nature. We must always have write access to take card of the header. */ DBUG_ASSERT(Flags | O_APPEND); DBUG_ASSERT(Flags | O_WRONLY); if (Flags & O_RDWR) s->mode = 'w'; if (s->mode == 'w') { err = deflateInit2(&(s->stream), level, Z_DEFLATED, -MAX_WBITS, 8, strategy); /* windowBits is passed < 0 to suppress zlib header */ s->stream.next_out = s->outbuf; if (err != Z_OK) { destroy(s); return Z_NULL; } } else { s->stream.next_in = s->inbuf; err = inflateInit2(&(s->stream), -MAX_WBITS); /* windowBits is passed < 0 to tell that there is no zlib header. * Note that in this case inflate *requires* an extra "dummy" byte * after the compressed stream in order to complete decompression and * return Z_STREAM_END. Here the gzip CRC32 ensures that 4 bytes are * present after the compressed stream. */ if (err != Z_OK) { destroy(s); return Z_NULL; } } s->stream.avail_out = AZ_BUFSIZE_WRITE; errno = 0; s->file = fd < 0 ? my_open(path, Flags, MYF(0)) : fd; if (s->file < 0 ) { destroy(s); return Z_NULL; } if (Flags & O_CREAT || Flags & O_TRUNC) { s->rows= 0; s->forced_flushes= 0; s->shortest_row= 0; s->longest_row= 0; s->auto_increment= 0; s->check_point= 0; s->comment_start_pos= 0; s->comment_length= 0; s->frm_start_pos= 0; s->frm_length= 0; s->dirty= 1; /* We create the file dirty */ s->start = AZHEADER_SIZE + AZMETA_BUFFER_SIZE; write_header(s); my_seek(s->file, 0, MY_SEEK_END, MYF(0)); } else if (s->mode == 'w') { uchar buffer[AZHEADER_SIZE + AZMETA_BUFFER_SIZE]; my_pread(s->file, buffer, AZHEADER_SIZE + AZMETA_BUFFER_SIZE, 0, MYF(0)); read_header(s, buffer); /* skip the .az header */ my_seek(s->file, 0, MY_SEEK_END, MYF(0)); } else { check_header(s); /* skip the .az header */ } return 1; }
size_t my_pwrite(File Filedes, const uchar *Buffer, size_t Count, my_off_t offset, myf MyFlags) { size_t writtenbytes; size_t sum_written= 0; uint errors= 0; const size_t initial_count= Count; DBUG_ENTER("my_pwrite"); DBUG_PRINT("my",("fd: %d Seek: %llu Buffer: %p Count: %lu MyFlags: %d", Filedes, offset, Buffer, (ulong)Count, MyFlags)); for (;;) { errno= 0; #if defined (_WIN32) writtenbytes= my_win_pwrite(Filedes, Buffer, Count, offset); #else writtenbytes= pwrite(Filedes, Buffer, Count, offset); #endif if(writtenbytes == Count) { sum_written+= writtenbytes; break; } my_errno= errno; if (writtenbytes != (size_t) -1) { sum_written+= writtenbytes; Buffer+= writtenbytes; Count-= writtenbytes; offset+= writtenbytes; } DBUG_PRINT("error",("Write only %u bytes", (uint) writtenbytes)); if (my_thread_var->abort) MyFlags&= ~ MY_WAIT_IF_FULL; /* End if aborted by user */ if ((my_errno == ENOSPC || my_errno == EDQUOT) && (MyFlags & MY_WAIT_IF_FULL)) { wait_for_free_space(my_filename(Filedes), errors); errors++; continue; } if (writtenbytes != 0 && writtenbytes != (size_t) -1) continue; else if (my_errno == EINTR) { continue; /* Retry */ } else if (writtenbytes == 0 && !errors++) /* Retry once */ { /* We may come here if the file quota is exeeded */ continue; } break; /* Return bytes written */ } if (MyFlags & (MY_NABP | MY_FNABP)) { if (sum_written == initial_count) DBUG_RETURN(0); /* Want only errors, not bytes written */ if (MyFlags & (MY_WME | MY_FAE | MY_FNABP)) { char errbuf[MYSYS_STRERROR_SIZE]; my_error(EE_WRITE, MYF(ME_BELL | ME_WAITTANG), my_filename(Filedes), my_errno, my_strerror(errbuf, sizeof(errbuf), my_errno)); } DBUG_RETURN(MY_FILE_ERROR); } DBUG_EXECUTE_IF("check", my_seek(Filedes, -1, SEEK_SET, MYF(0)););
int my_lock(File fd, int locktype, my_off_t start, my_off_t length, myf MyFlags) { #ifdef HAVE_FCNTL int value; ALARM_VARIABLES; #endif DBUG_ENTER("my_lock"); DBUG_PRINT("my",("fd: %d Op: %d start: %ld Length: %ld MyFlags: %d", fd,locktype,(long) start,(long) length,MyFlags)); if (my_disable_locking) DBUG_RETURN(0); #if defined(_WIN32) { int timeout_sec; if (MyFlags & MY_DONT_WAIT) timeout_sec= 0; else timeout_sec= WIN_LOCK_INFINITE; if (win_lock(fd, locktype, start, length, timeout_sec) == 0) DBUG_RETURN(0); } #else #if defined(HAVE_FCNTL) { struct flock lock; lock.l_type= (short) locktype; lock.l_whence= SEEK_SET; lock.l_start= (off_t) start; lock.l_len= (off_t) length; if (MyFlags & MY_DONT_WAIT) { if (fcntl(fd,F_SETLK,&lock) != -1) /* Check if we can lock */ DBUG_RETURN(0); /* Ok, file locked */ DBUG_PRINT("info",("Was locked, trying with alarm")); ALARM_INIT; while ((value=fcntl(fd,F_SETLKW,&lock)) && ! ALARM_TEST && errno == EINTR) { /* Setup again so we don`t miss it */ ALARM_REINIT; } ALARM_END; if (value != -1) DBUG_RETURN(0); if (errno == EINTR) errno=EAGAIN; } else if (fcntl(fd,F_SETLKW,&lock) != -1) /* Wait until a lock */ DBUG_RETURN(0); } #else if (MyFlags & MY_SEEK_NOT_DONE) { if (my_seek(fd,start,MY_SEEK_SET,MYF(MyFlags & ~MY_SEEK_NOT_DONE)) == MY_FILEPOS_ERROR) { /* If an error has occured in my_seek then we will already have an error code in my_errno; Just return error code. */ DBUG_RETURN(-1); } } if (lockf(fd,locktype,length) != -1) DBUG_RETURN(0); #endif /* HAVE_FCNTL */ #endif /* HAVE_LOCKING */ /* We got an error. We don't want EACCES errors */ my_errno=(errno == EACCES) ? EAGAIN : errno ? errno : -1; if (MyFlags & MY_WME) { char errbuf[MYSYS_STRERROR_SIZE]; if (locktype == F_UNLCK) my_error(EE_CANTUNLOCK, MYF(ME_BELL+ME_WAITTANG), my_errno, my_strerror(errbuf, sizeof(errbuf), my_errno)); else my_error(EE_CANTLOCK, MYF(ME_BELL+ME_WAITTANG), my_errno, my_strerror(errbuf, sizeof(errbuf), my_errno)); } DBUG_PRINT("error",("my_errno: %d (%d)",my_errno,errno)); DBUG_RETURN(-1); } /* my_lock */
int test_file(PAGECACHE_FILE file, char *file_name, off_t size, size_t buff_size, struct file_desc *desc) { unsigned char *buffr= my_malloc(buff_size, MYF(0)); off_t pos= 0; size_t byte; int step= 0; int res= 1; /* ok */ #ifdef __WIN__ /* On Windows, the info returned by stat(), specifically file length is not necessarily current, because this is the behavior of underlying FindFirstFile() function. */ WIN32_FILE_ATTRIBUTE_DATA file_attr; LARGE_INTEGER li; if(GetFileAttributesEx(file_name, GetFileExInfoStandard, &file_attr) == 0) { diag("Can't GetFileAttributesEx %s (errno: %d)\n", file_name, GetLastError()); res= 0; goto err; } li.HighPart= file_attr.nFileSizeHigh; li.LowPart= file_attr.nFileSizeLow; if(li.QuadPart != size) { diag("file %s size is %llu (should be %llu)\n", file_name, (ulonglong)size, (ulonglong)li.QuadPart); res= 0; /* failed */ /* continue to get more information */ } #else MY_STAT stat_buff, *stat; if ((stat= my_stat(file_name, &stat_buff, MYF(0))) == NULL) { diag("Can't stat() %s (errno: %d)\n", file_name, errno); res= 0; goto err; } if (stat->st_size != size) { diag("file %s size is %lu (should be %lu)\n", file_name, (ulong) stat->st_size, (ulong) size); res= 0; /* failed */ /* continue to get more information */ } #endif /* check content */ my_seek(file.file, 0, SEEK_SET, MYF(MY_WME)); while (desc[step].length != 0) { if (my_read(file.file, buffr, desc[step].length, MYF(0)) != desc[step].length) { diag("Can't read %u bytes from %s (file: %d errno: %d)\n", (uint)desc[step].length, file_name, file.file, errno); res= 0; goto err; } for (byte= 0; byte < desc[step].length; byte++) { if (buffr[byte] != desc[step].content) { diag("content of %s mismatch 0x%x in position %lu instead of 0x%x\n", file_name, (uint) buffr[byte], (ulong) (pos + byte), desc[step].content); res= 0; goto err; } } pos+= desc[step].length; step++; } err: my_free(buffr); return res; }
int my_lock(File fd, int locktype, my_off_t start, my_off_t length, myf MyFlags) { #ifdef HAVE_FCNTL int value; ALARM_VARIABLES; #endif #ifdef __NETWARE__ int nxErrno; #endif DBUG_ENTER("my_lock"); DBUG_PRINT("my",("Fd: %d Op: %d start: %ld Length: %ld MyFlags: %d", fd,locktype,(long) start,(long) length,MyFlags)); #ifdef VMS DBUG_RETURN(0); #else if (my_disable_locking) DBUG_RETURN(0); #if defined(__NETWARE__) { NXSOffset_t nxLength = length; unsigned long nxLockFlags = 0; if (length == F_TO_EOF) { /* EOF is interpreted as a very large length. */ nxLength = 0x7FFFFFFFFFFFFFFF; } if (locktype == F_UNLCK) { /* The lock flags are currently ignored by NKS. */ if (!(nxErrno= NXFileRangeUnlock(fd, 0L, start, nxLength))) DBUG_RETURN(0); } else { if (locktype == F_RDLCK) { /* A read lock is mapped to a shared lock. */ nxLockFlags = NX_RANGE_LOCK_SHARED; } else { /* A write lock is mapped to an exclusive lock. */ nxLockFlags = NX_RANGE_LOCK_EXCL; } if (MyFlags & MY_DONT_WAIT) { /* Don't block on the lock. */ nxLockFlags |= NX_RANGE_LOCK_TRYLOCK; } if (!(nxErrno= NXFileRangeLock(fd, nxLockFlags, start, nxLength))) DBUG_RETURN(0); } } #elif defined(HAVE_LOCKING) /* Windows */ { my_bool error= FALSE; pthread_mutex_lock(&my_file_info[fd].mutex); if (MyFlags & MY_SEEK_NOT_DONE) { if( my_seek(fd,start,MY_SEEK_SET,MYF(MyFlags & ~MY_SEEK_NOT_DONE)) == MY_FILEPOS_ERROR ) { /* If my_seek fails my_errno will already contain an error code; just unlock and return error code. */ DBUG_PRINT("error",("my_errno: %d (%d)",my_errno,errno)); pthread_mutex_unlock(&my_file_info[fd].mutex); DBUG_RETURN(-1); } } error= locking(fd,locktype,(ulong) length) && errno != EINVAL; pthread_mutex_unlock(&my_file_info[fd].mutex); if (!error) DBUG_RETURN(0); } #else #if defined(HAVE_FCNTL) { struct flock lock; lock.l_type= (short) locktype; lock.l_whence= SEEK_SET; lock.l_start= (off_t) start; lock.l_len= (off_t) length; if (MyFlags & MY_DONT_WAIT) { if (fcntl(fd,F_SETLK,&lock) != -1) /* Check if we can lock */ DBUG_RETURN(0); /* Ok, file locked */ DBUG_PRINT("info",("Was locked, trying with alarm")); ALARM_INIT; while ((value=fcntl(fd,F_SETLKW,&lock)) && ! ALARM_TEST && errno == EINTR) { /* Setup again so we don`t miss it */ ALARM_REINIT; } ALARM_END; if (value != -1) DBUG_RETURN(0); if (errno == EINTR) errno=EAGAIN; } else if (fcntl(fd,F_SETLKW,&lock) != -1) /* Wait until a lock */ DBUG_RETURN(0); } #else if (MyFlags & MY_SEEK_NOT_DONE) { if (my_seek(fd,start,MY_SEEK_SET,MYF(MyFlags & ~MY_SEEK_NOT_DONE)) == MY_FILEPOS_ERROR) { /* If an error has occured in my_seek then we will already have an error code in my_errno; Just return error code. */ DBUG_RETURN(-1); } } if (lockf(fd,locktype,length) != -1) DBUG_RETURN(0); #endif /* HAVE_FCNTL */ #endif /* HAVE_LOCKING */ #ifdef __NETWARE__ my_errno = nxErrno; #else /* We got an error. We don't want EACCES errors */ my_errno=(errno == EACCES) ? EAGAIN : errno ? errno : -1; #endif if (MyFlags & MY_WME) { if (locktype == F_UNLCK) my_error(EE_CANTUNLOCK,MYF(ME_BELL+ME_WAITTANG),my_errno); else my_error(EE_CANTLOCK,MYF(ME_BELL+ME_WAITTANG),my_errno); } DBUG_PRINT("error",("my_errno: %d (%d)",my_errno,errno)); DBUG_RETURN(-1); #endif /* ! VMS */ } /* my_lock */
/* Change size of file. SYNOPSIS my_chsize() fd File descriptor new_length New file size filler If we don't have truncate, fill up all bytes after new_length with this character MyFlags Flags DESCRIPTION my_chsize() truncates file if shorter else fill with the filler character. The function also changes the file pointer. Usually it points to the end of the file after execution. RETURN VALUE 0 Ok 1 Error */ int my_chsize(File fd, my_off_t newlength, int filler, myf MyFlags) { my_off_t oldsize; uchar buff[IO_SIZE]; DBUG_ENTER("my_chsize"); DBUG_PRINT("my",("fd: %d length: %lu MyFlags: %d",fd,(ulong) newlength, MyFlags)); if ((oldsize= my_seek(fd, 0L, MY_SEEK_END, MYF(MY_WME+MY_FAE))) == newlength) DBUG_RETURN(0); DBUG_PRINT("info",("old_size: %ld", (ulong) oldsize)); if (oldsize > newlength) { #ifdef _WIN32 if (my_win_chsize(fd, newlength)) { my_errno= errno; goto err; } DBUG_RETURN(0); #elif defined(HAVE_FTRUNCATE) if (ftruncate(fd, (off_t) newlength)) { my_errno= errno; goto err; } DBUG_RETURN(0); #elif defined(HAVE_CHSIZE) if (chsize(fd, (off_t) newlength)) { my_errno=errno; goto err; } DBUG_RETURN(0); #else /* Fill space between requested length and true length with 'filler' We should never come here on any modern machine */ if (my_seek(fd, newlength, MY_SEEK_SET, MYF(MY_WME+MY_FAE)) == MY_FILEPOS_ERROR) { goto err; } swap_variables(my_off_t, newlength, oldsize); #endif } /* Full file with 'filler' until it's as big as requested */ bfill(buff, IO_SIZE, filler); while (newlength-oldsize > IO_SIZE) { if (my_write(fd, buff, IO_SIZE, MYF(MY_NABP))) goto err; oldsize+= IO_SIZE; } if (my_write(fd,buff,(size_t) (newlength-oldsize), MYF(MY_NABP))) goto err; DBUG_RETURN(0); err: DBUG_PRINT("error", ("errno: %d", errno)); if (MyFlags & MY_WME) my_error(EE_CANT_CHSIZE, MYF(ME_BELL+ME_WAITTANG), my_errno); DBUG_RETURN(1); } /* my_chsize */
size_t my_pwrite(int Filedes, const uchar *Buffer, size_t Count, my_off_t offset, myf MyFlags) { size_t writenbytes, written; uint errors; DBUG_ENTER("my_pwrite"); DBUG_PRINT("my",("Fd: %d Seek: %lu Buffer: 0x%lx Count: %u MyFlags: %d", Filedes, (ulong) offset, (long) Buffer, (uint) Count, MyFlags)); errors= 0; written= 0; for (;;) { #ifndef HAVE_PREAD int error; writenbytes= (size_t) -1; pthread_mutex_lock(&my_file_info[Filedes].mutex); error= (lseek(Filedes, offset, MY_SEEK_SET) != (my_off_t) -1 && (writenbytes = write(Filedes, Buffer, (uint) Count)) == Count); pthread_mutex_unlock(&my_file_info[Filedes].mutex); if (error) break; #else if ((writenbytes= pwrite(Filedes, Buffer, Count,offset)) == Count) break; my_errno= errno; #endif if (writenbytes != (size_t) -1) { /* Safegueard */ written+=writenbytes; Buffer+=writenbytes; Count-=writenbytes; offset+=writenbytes; } DBUG_PRINT("error",("Write only %u bytes", (uint) writenbytes)); #ifndef NO_BACKGROUND #ifdef THREAD if (my_thread_var->abort) MyFlags&= ~ MY_WAIT_IF_FULL; /* End if aborted by user */ #endif if ((my_errno == ENOSPC || my_errno == EDQUOT) && (MyFlags & MY_WAIT_IF_FULL)) { wait_for_free_space(my_filename(Filedes), errors); errors++; continue; } if ((writenbytes && writenbytes != (size_t) -1) || my_errno == EINTR) continue; /* Retry */ #endif if (MyFlags & (MY_NABP | MY_FNABP)) { if (MyFlags & (MY_WME | MY_FAE | MY_FNABP)) { my_error(EE_WRITE, MYF(ME_BELL | ME_WAITTANG), my_filename(Filedes),my_errno); } DBUG_RETURN(MY_FILE_ERROR); /* Error on read */ } else break; /* Return bytes written */ } DBUG_EXECUTE_IF("check", my_seek(Filedes, -1, SEEK_SET, MYF(0)););
int my_chsize(File fd, my_off_t newlength, myf MyFlags) { DBUG_ENTER("my_chsize"); DBUG_PRINT("my",("fd: %d length: %lu MyFlags: %d",fd,(ulong) newlength, MyFlags)); #ifdef HAVE_CHSIZE if (chsize(fd,(off_t) newlength)) { DBUG_PRINT("error",("errno: %d",errno)); my_errno=errno; if (MyFlags & MY_WME) my_error(EE_CANT_CHSIZE,MYF(ME_BELL+ME_WAITTANG),errno); DBUG_RETURN(1); } DBUG_RETURN(0); #else /* if file is shorter, expand with null, else fill unused part with null */ { my_off_t oldsize; char buff[IO_SIZE]; oldsize = my_seek(fd, 0L, MY_SEEK_END, MYF(MY_WME+MY_FAE)); DBUG_PRINT("info",("old_size: %ld", (ulong) oldsize)); #ifdef HAVE_FTRUNCATE if (oldsize > newlength) { if (ftruncate(fd, (off_t) newlength)) { my_errno=errno; DBUG_PRINT("error",("errno: %d",errno)); if (MyFlags & MY_WME) my_error(EE_CANT_CHSIZE, MYF(ME_BELL+ME_WAITTANG), errno); DBUG_RETURN(1); } DBUG_RETURN(0); } #else if (oldsize > newlength) { /* Fill diff with null */ VOID(my_seek(fd, newlength, MY_SEEK_SET, MYF(MY_WME+MY_FAE))); swap(my_off_t, newlength, oldsize); } #endif /* Full file with 0 until it's as big as requested */ bzero(buff,IO_SIZE); while (newlength-oldsize > IO_SIZE) { if (my_write(fd,(byte*) buff,IO_SIZE,MYF(MY_NABP))) goto err; oldsize+= IO_SIZE; } if (my_write(fd,(byte*) buff,(uint) (newlength-oldsize),MYF(MY_NABP))) goto err; DBUG_RETURN(0); err: if (MyFlags & MY_WME) my_error(EE_CANT_CHSIZE,MYF(ME_BELL+ME_WAITTANG),my_errno); DBUG_PRINT("error",("errno: %d",my_errno)); DBUG_RETURN(1); } #endif } /* my_chsize */