nfs4: readdir() should not read more than requested

Additionally, file attribute decoding checks more strictly whether
received data are sane.
This commit is contained in:
Pawel Dziepak 2012-06-05 14:30:57 +02:00
parent ed517d6c62
commit f29ac4afd9
3 changed files with 13 additions and 5 deletions

View File

@ -65,7 +65,6 @@ Inode::Inode(Filesystem* fs, const Filehandle &fh, bool root)
status_t
Inode::LookUp(const char* name, ino_t* id)
{
dprintf("nfs4: lookup: %s\n", name);
if (fType != NF4DIR)
return B_NOT_A_DIRECTORY;
@ -338,7 +337,7 @@ Inode::ReadDir(void* _buffer, uint32 size, uint32* _count, uint64* cookie)
}
while (count < *_count && !eof) {
this_count = *_count;
this_count = *_count - count;
DirEntry* dirents;
status_t result = _ReadDirOnce(&dirents, &this_count, cookie, &eof);
@ -346,7 +345,7 @@ Inode::ReadDir(void* _buffer, uint32 size, uint32* _count, uint64* cookie)
return result;
uint32 i;
for (i = 0; i < this_count; i++) {
for (i = 0; i < min_c(this_count, *_count - count); i++) {
struct dirent* de = reinterpret_cast<dirent*>(buffer + pos);
ino_t id;
@ -371,7 +370,7 @@ Inode::ReadDir(void* _buffer, uint32 size, uint32* _count, uint64* cookie)
return B_BUFFER_OVERFLOW;
*_count = count;
return B_OK;
}

View File

@ -99,7 +99,8 @@ enum Attribute {
FATTR4_TIME_METADATA = 52,
FATTR4_TIME_MODIFY = 53,
FATTR4_TIME_MODIFY_SET = 54,
FATTR4_MOUNTED_ON_FILEID = 55
FATTR4_MOUNTED_ON_FILEID = 55,
FATTR4_MAXIMUM_ATTR_ID
};
enum FileType {

View File

@ -155,6 +155,7 @@ ReplyInterpreter::ReadDir(uint64* cookie, DirEntry** dirents, uint32* _count,
return B_OK;
}
status_t
ReplyInterpreter::_DecodeAttrs(XDR::ReadStream& str, AttrValue** attrs,
uint32* count)
@ -170,6 +171,13 @@ ReplyInterpreter::_DecodeAttrs(XDR::ReadStream& str, AttrValue** attrs,
attr_count += sCountBits(bitmap[i]);
}
if (attr_count == 0) {
*attrs = NULL;
*count = 0;
return B_OK;
} else if (attr_count > FATTR4_MAXIMUM_ATTR_ID)
return B_BAD_VALUE;
uint32 size;
const void* ptr = str.GetOpaque(&size);
XDR::ReadStream stream(const_cast<void*>(ptr), size);