1 | /* |
2 | Copyright (c) 2000, 2010, Oracle and/or its affiliates |
3 | |
4 | This program is free software; you can redistribute it and/or modify |
5 | it under the terms of the GNU General Public License as published by |
6 | the Free Software Foundation; version 2 of the License. |
7 | |
8 | This program is distributed in the hope that it will be useful, |
9 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
10 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
11 | GNU General Public License for more details. |
12 | |
13 | You should have received a copy of the GNU General Public License |
14 | along with this program; if not, write to the Free Software |
15 | Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ |
16 | |
17 | #include "mysys_priv.h" |
18 | #include "mysys_err.h" |
19 | |
20 | /* |
21 | Seek to a position in a file. |
22 | |
23 | ARGUMENTS |
24 | File fd The file descriptor |
25 | my_off_t pos The expected position (absolute or relative) |
26 | int whence A direction parameter and one of |
27 | {SEEK_SET, SEEK_CUR, SEEK_END} |
28 | myf MyFlags MY_THREADSAFE must be set in case my_seek may be mixed |
29 | with my_pread/my_pwrite calls and fd is shared among |
30 | threads. |
31 | |
32 | DESCRIPTION |
33 | The my_seek function is a wrapper around the system call lseek and |
34 | repositions the offset of the file descriptor fd to the argument |
35 | offset according to the directive whence as follows: |
36 | SEEK_SET The offset is set to offset bytes. |
37 | SEEK_CUR The offset is set to its current location plus offset bytes |
38 | SEEK_END The offset is set to the size of the file plus offset bytes |
39 | |
40 | RETURN VALUE |
41 | my_off_t newpos The new position in the file. |
42 | MY_FILEPOS_ERROR An error was encountered while performing |
43 | the seek. my_errno is set to indicate the |
44 | actual error. |
45 | */ |
46 | |
47 | my_off_t my_seek(File fd, my_off_t pos, int whence, myf MyFlags) |
48 | { |
49 | os_off_t newpos= -1; |
50 | DBUG_ENTER("my_seek" ); |
51 | DBUG_PRINT("my" ,("fd: %d Pos: %llu Whence: %d MyFlags: %lu" , |
52 | fd, (ulonglong) pos, whence, MyFlags)); |
53 | DBUG_ASSERT(pos != MY_FILEPOS_ERROR); /* safety check */ |
54 | |
55 | /* |
56 | Make sure we are using a valid file descriptor! |
57 | */ |
58 | DBUG_ASSERT(fd != -1); |
59 | #ifdef _WIN32 |
60 | newpos= my_win_lseek(fd, pos, whence); |
61 | #else |
62 | newpos= lseek(fd, pos, whence); |
63 | #endif |
64 | if (newpos == (os_off_t) -1) |
65 | { |
66 | my_errno= errno; |
67 | if (MyFlags & MY_WME) |
68 | my_error(EE_CANT_SEEK, MYF(0), my_filename(fd), my_errno); |
69 | DBUG_PRINT("error" , ("lseek: %llu errno: %d" , (ulonglong) newpos, errno)); |
70 | DBUG_RETURN(MY_FILEPOS_ERROR); |
71 | } |
72 | if ((my_off_t) newpos != pos) |
73 | { |
74 | DBUG_PRINT("exit" ,("pos: %llu" , (ulonglong) newpos)); |
75 | } |
76 | DBUG_RETURN((my_off_t) newpos); |
77 | } /* my_seek */ |
78 | |
79 | |
80 | /* Tell current position of file */ |
81 | /* ARGSUSED */ |
82 | |
83 | my_off_t my_tell(File fd, myf MyFlags) |
84 | { |
85 | os_off_t pos; |
86 | DBUG_ENTER("my_tell" ); |
87 | DBUG_PRINT("my" ,("fd: %d MyFlags: %lu" ,fd, MyFlags)); |
88 | DBUG_ASSERT(fd >= 0); |
89 | #if defined (HAVE_TELL) && !defined (_WIN32) |
90 | pos= tell(fd); |
91 | #else |
92 | pos= my_seek(fd, 0L, MY_SEEK_CUR,0); |
93 | #endif |
94 | if (pos == (os_off_t) -1) |
95 | { |
96 | my_errno= errno; |
97 | if (MyFlags & MY_WME) |
98 | my_error(EE_CANT_SEEK, MYF(0), my_filename(fd), my_errno); |
99 | DBUG_PRINT("error" , ("tell: %llu errno: %d" , (ulonglong) pos, my_errno)); |
100 | } |
101 | DBUG_PRINT("exit" ,("pos: %llu" , (ulonglong) pos)); |
102 | DBUG_RETURN((my_off_t) pos); |
103 | } /* my_tell */ |
104 | |