问题的引出:
当对同一文件句柄(在Windows下)或是文件描述符(在Linux下)进行随机读写操作时,会存在文件指针的定位与读/写俩个步骤,但由于这不是一个原子操作,就可能产生如下问题:进程A对某文件先定位到 f1 处,然后被中断,然后进程B对同一文件定位到 f2 处,然后被中断,进程A再次执行,从文件的当前指针处开始读或是写,于是这便产生了不是期望的结果了。(这里要注意,对同一文件的俩次打开,得到的将是俩个不同的句柄或是描述符,所以不用担心这种情况会出问题)
解决办法:
在Linux下,pread函数就好像是专门为上面的问题服务的,它本身就是原子性的操作,定位文件指针与读操作一气呵成,而且读操作并不改变文件指针。
在windows下,参考其api时我并没有查到像pread这么直接的函数,而是ReadFile它的一个参数lpOverlapped来实现的:
1)若文件是以 FILE_FLAG_OVERLAPPED打开的,且 lpOverlapped 不为NULL,则读操作会在 lpOverlapped结构中指定的offset处开始读文件,且函数可能会在读操作完成前就返回了(即异步模式)
2)若文件不是以 FILE_FLAG_OVERLAPPED打开的,但lpOverlapped 不为NULL,则 读操作会在 lpOverlapped结构中指定的offset处开始读文件,且函数会一直阻塞直到读操作完成(即同步模式)
从上面可知,好似Windows下ReadFile无法实现pread在Linux下的功能,初步想法是对文件句柄进行加锁来避免问题的出现,并实施对文件进行第二次空读取(即读0个字符)来文件指针回到第一次读取的位置,但没实现,不知可否。(待续)