Re: Programmatically detect removed usb stick?
On Sat, Jun 11, 2011 at 3:47 PM, Benny Lofgren bl-li...@lofgren.biz wrote: On 2011-06-11 10.08, T wrote: I'm writing a small program which changes working dir to a specific directory (using chdir()), and then opens, reads, and closes files in that directory, depending on user actions. Sometimes this directory is located on a mounted USB stick. I'm looking for a simple way to detect, from within my program, if a user have removed the USB stick without first unmounting it. The simplest way, I thought, was to check errno for EIO or ENXIO (depending on whether an error occurs in fread() or fopen()). However, that does not seem to work, because if I call fopen() after the USB stick has been removed, the return value is NULL, and the errno code is ENOENT instead of ENXIO, which sort of makes sense (the file certainly is not there any more), but the cause of the error cannot be differentiated from a regular mis-spelling of the file name. So is there some reliable way of detecting whether the underlying storage device has gone away when a library/system call fails, even if the OS still regards the filesystem as being mounted? Can I, upon detecting errno==ENOENT after fopen(), use some other calls (for example ioctl(), getfsstat(), or statfs()) to determine whether the cause is a mis-spelled filename or removed USB stick? What is the recommended/preferred way? Can/should I perhaps do something before attempting the fopen(), to find out whether the USB stick is still attached? I prefer simple solutions using standard library/system calls, and would like to avoid attaching to some notification mechanism, and tailing the kernel log looking for USB detach messages is a clumsy last chance solution. Try to do an open(., O_RDONLY) if your fopen()/fread() fails. If you get -1 and ENOENT then the file system where you've parked your cwd is no longer mounted (statfs() should also work equally well, but then you'd need to declare a statfs struct you'd have no further use for). It's not wise to check before your fopen():s, because they may still fail if the user pulls the USB stick in the right moment, only use it as a verification of *what* actually went wrong. Thanks for the replies, on- and off-list. I ended up going with Benny's open(., O_RDONLY); suggestion, which felt cleanest, easiest, and had the highest probability of being portable, should the need arise. Works like a charm. Dave
Programmatically detect removed usb stick?
Hello, I'm writing a small program which changes working dir to a specific directory (using chdir()), and then opens, reads, and closes files in that directory, depending on user actions. Sometimes this directory is located on a mounted USB stick. I'm looking for a simple way to detect, from within my program, if a user have removed the USB stick without first unmounting it. The simplest way, I thought, was to check errno for EIO or ENXIO (depending on whether an error occurs in fread() or fopen()). However, that does not seem to work, because if I call fopen() after the USB stick has been removed, the return value is NULL, and the errno code is ENOENT instead of ENXIO, which sort of makes sense (the file certainly is not there any more), but the cause of the error cannot be differentiated from a regular mis-spelling of the file name. So is there some reliable way of detecting whether the underlying storage device has gone away when a library/system call fails, even if the OS still regards the filesystem as being mounted? Can I, upon detecting errno==ENOENT after fopen(), use some other calls (for example ioctl(), getfsstat(), or statfs()) to determine whether the cause is a mis-spelled filename or removed USB stick? What is the recommended/preferred way? Can/should I perhaps do something before attempting the fopen(), to find out whether the USB stick is still attached? I prefer simple solutions using standard library/system calls, and would like to avoid attaching to some notification mechanism, and tailing the kernel log looking for USB detach messages is a clumsy last chance solution. Dave
Re: Programmatically detect removed usb stick?
On 2011-06-11 10.08, T wrote: I'm writing a small program which changes working dir to a specific directory (using chdir()), and then opens, reads, and closes files in that directory, depending on user actions. Sometimes this directory is located on a mounted USB stick. I'm looking for a simple way to detect, from within my program, if a user have removed the USB stick without first unmounting it. The simplest way, I thought, was to check errno for EIO or ENXIO (depending on whether an error occurs in fread() or fopen()). However, that does not seem to work, because if I call fopen() after the USB stick has been removed, the return value is NULL, and the errno code is ENOENT instead of ENXIO, which sort of makes sense (the file certainly is not there any more), but the cause of the error cannot be differentiated from a regular mis-spelling of the file name. So is there some reliable way of detecting whether the underlying storage device has gone away when a library/system call fails, even if the OS still regards the filesystem as being mounted? Can I, upon detecting errno==ENOENT after fopen(), use some other calls (for example ioctl(), getfsstat(), or statfs()) to determine whether the cause is a mis-spelled filename or removed USB stick? What is the recommended/preferred way? Can/should I perhaps do something before attempting the fopen(), to find out whether the USB stick is still attached? I prefer simple solutions using standard library/system calls, and would like to avoid attaching to some notification mechanism, and tailing the kernel log looking for USB detach messages is a clumsy last chance solution. Try to do an open(., O_RDONLY) if your fopen()/fread() fails. If you get -1 and ENOENT then the file system where you've parked your cwd is no longer mounted (statfs() should also work equally well, but then you'd need to declare a statfs struct you'd have no further use for). It's not wise to check before your fopen():s, because they may still fail if the user pulls the USB stick in the right moment, only use it as a verification of *what* actually went wrong. Regards, /Benny -- internetlabbet.se / work: +46 8 551 124 80 / Words must Benny Lvfgren/ mobile: +46 70 718 11 90 / be weighed, / fax:+46 8 551 124 89/not counted. /email: benny -at- internetlabbet.se
Re: Programmatically detect removed usb stick?
2011/6/11 Benny Lofgren bl-li...@lofgren.biz: If you get -1 and ENOENT then the file system where you've parked your cwd is no longer mounted (statfs() should also work equally What if the cwd has been removed by another process instead? Best Martin
Re: Programmatically detect removed usb stick?
On Sat, Jun 11, 2011 at 4:08 AM, T jatd...@gmail.com wrote: So is there some reliable way of detecting whether the underlying storage device has gone away when a library/system call fails, even if the OS still regards the filesystem as being mounted? Can I, upon detecting errno==ENOENT after fopen(), use some other calls (for example ioctl(), getfsstat(), or statfs()) to determine whether the cause is a mis-spelled filename or removed USB stick? What is the recommended/preferred way? Can/should I perhaps do something before attempting the fopen(), to find out whether the USB stick is still attached? There are no filesystems without storage, they are force unmounted when the device is removed. You should look into hotplugd if you want notification of device removal.