diff options
author | Pixel <pixel@nobis-crew.org> | 2011-11-15 11:53:58 -0800 |
---|---|---|
committer | Pixel <pixel@nobis-crew.org> | 2011-11-15 11:53:58 -0800 |
commit | 1a5dacb93f2c3f2cfc8f4a9da6599beaebcc6845 (patch) | |
tree | f03f1502575f51c36b94d232384c42e5f2845f74 /src/Handle.cc | |
parent | 5154e80b61bc5678cd1ce6018fd52b023c4b9079 (diff) |
Adding the forceRead/Write methods, to circumvent the potential problem that a file descriptor can do less than being asked.
Diffstat (limited to 'src/Handle.cc')
-rw-r--r-- | src/Handle.cc | 50 |
1 files changed, 50 insertions, 0 deletions
diff --git a/src/Handle.cc b/src/Handle.cc index 0ec39be..8fa0417 100644 --- a/src/Handle.cc +++ b/src/Handle.cc @@ -83,6 +83,56 @@ ssize_t Balau::Handle::write(const void * buf, size_t count) throw (GeneralExcep return -1; } +ssize_t Balau::Handle::forceRead(void * _buf, size_t count) throw (GeneralException) { + ssize_t total; + uint8_t * buf = (uint8_t *) _buf; + if (!canRead()) + throw GeneralException("Handle can't read"); + + while (count && !isClosed()) { + ssize_t r; + try { + r = read(buf, count); + } + catch (EAgain e) { + Task::yield(e.getEvent()); + continue; + } + if (r < 0) + return r; + total += r; + count -= r; + buf += r; + } + + return total; +} + +ssize_t Balau::Handle::forceWrite(const void * _buf, size_t count) throw (GeneralException) { + ssize_t total; + const uint8_t * buf = (const uint8_t *) _buf; + if (!canWrite()) + throw GeneralException("Handle can't write"); + + while (count && !isClosed()) { + ssize_t r; + try { + r = write(buf, count); + } + catch (EAgain e) { + Task::yield(e.getEvent()); + continue; + } + if (r < 0) + return r; + total += r; + count -= r; + buf += r; + } + + return total; +} + void Balau::Handle::rseek(off_t offset, int whence) throw (GeneralException) { if (canSeek()) throw GeneralException(String("Handle ") + getName() + " can seek, but rseek() not implemented (missing in class " + ClassName(this).c_str() + ")"); |