Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
56 changes: 28 additions & 28 deletions src/common/io/io_unix.c
Original file line number Diff line number Diff line change
Expand Up @@ -47,45 +47,45 @@ bool ffWriteFileData(const char* fileName, size_t dataSize, const void* data)
return write(fd, data, dataSize) > 0;
}

bool ffAppendFDBuffer(int fd, FFstrbuf* buffer)
static inline void readWithLength(int fd, FFstrbuf* buffer, uint32_t length)
{
ffStrbufEnsureFixedLengthFree(buffer, length);
ssize_t bytesRead = 0;

struct stat fileInfo;
if(fstat(fd, &fileInfo) != 0)
return false;

if (fileInfo.st_size > 0)
{
// optimize for files has a fixed length,
// file can be very large, only keep necessary memory to save time and resources.
ffStrbufEnsureFixedLengthFree(buffer, (uint32_t)fileInfo.st_size);
while(
length > 0 && (bytesRead = read(fd, buffer->chars + buffer->length, length)) > 0
) {
buffer->length += (uint32_t) bytesRead;
length -= (uint32_t) bytesRead;
}
else
ffStrbufEnsureFree(buffer, 31);
uint32_t free = ffStrbufGetFree(buffer);
// procfs file's st_size is always zero
// choose a signed int type so that can store a native number
ssize_t remain = fileInfo.st_size;
}

static inline void readUntilEOF(int fd, FFstrbuf* buffer)
{
ffStrbufEnsureFree(buffer, 31);
uint32_t available = ffStrbufGetFree(buffer);
ssize_t bytesRead = 0;
while(
(bytesRead = read(fd, buffer->chars + buffer->length, free)) > 0
(bytesRead = read(fd, buffer->chars + buffer->length, available)) > 0
) {
buffer->length += (uint32_t) bytesRead;
// if remain > 0, it means there is some data left in the file.
// if remain == 0, it means reading has completed, no need to grow up the buffer.
// if remain < 0, we are reading a file from procfs/sysfs and its st_size is zero,
// we cannot detect how many data remains in the file, we only can call ffStrbufEnsureFree and read again.
remain -= bytesRead;
if((uint32_t) bytesRead == free && remain != 0)
if((uint32_t) bytesRead == available)
ffStrbufEnsureFree(buffer, buffer->allocated - 1); // Doubles capacity every round. -1 for the null byte.
free = ffStrbufGetFree(buffer);
available = ffStrbufGetFree(buffer);
}
}

buffer->chars[buffer->length] = '\0';
bool ffAppendFDBuffer(int fd, FFstrbuf* buffer)
{
struct stat fileInfo;
if(fstat(fd, &fileInfo) != 0)
return false;

if (fileInfo.st_size > 0)
readWithLength(fd, buffer, (uint32_t)fileInfo.st_size);
else
readUntilEOF(fd, buffer);

ffStrbufTrimRight(buffer, '\n');
ffStrbufTrimRight(buffer, ' ');
buffer->chars[buffer->length] = '\0';

return buffer->length > 0;
}
Expand Down
55 changes: 31 additions & 24 deletions src/common/io/io_windows.c
Original file line number Diff line number Diff line change
Expand Up @@ -35,43 +35,50 @@ bool ffWriteFileData(const char* fileName, size_t dataSize, const void* data)
return !!WriteFile(handle, data, (DWORD)dataSize, &written, NULL);
}

bool ffAppendFDBuffer(HANDLE handle, FFstrbuf* buffer)
static inline void readWithLength(HANDLE handle, FFstrbuf* buffer, uint32_t length)
{
ffStrbufEnsureFixedLengthFree(buffer, length);
DWORD bytesRead = 0;

LARGE_INTEGER fileSize;
if(!GetFileSizeEx(handle, &fileSize))
fileSize.QuadPart = 0;

if (fileSize.QuadPart > 0)
{
// optimize for files has a fixed length,
// file can be very large, only keep necessary memory to save time and resources.
ffStrbufEnsureFixedLengthFree(buffer, (uint32_t)fileSize.QuadPart);
while(
length > 0 &&
ReadFile(handle, buffer->chars + buffer->length, length, &bytesRead, NULL) != FALSE &&
bytesRead > 0
) {
buffer->length += (uint32_t) bytesRead;
length -= (uint32_t) bytesRead;
}
else
ffStrbufEnsureFree(buffer, 31);
uint32_t free = ffStrbufGetFree(buffer);
ssize_t remain = fileSize.QuadPart;
}

bool success;
static inline void readUntilEOF(HANDLE handle, FFstrbuf* buffer)
{
ffStrbufEnsureFree(buffer, 31);
uint32_t available = ffStrbufGetFree(buffer);
DWORD bytesRead = 0;
while(
(success = !!ReadFile(handle, buffer->chars + buffer->length, free, &bytesRead, NULL)) &&
ReadFile(handle, buffer->chars + buffer->length, available, &bytesRead, NULL) != FALSE &&
bytesRead > 0
) {
buffer->length += (uint32_t) bytesRead;
remain -= (ssize_t)bytesRead;
if((uint32_t) bytesRead == free && remain != 0)
if((uint32_t) bytesRead == available)
ffStrbufEnsureFree(buffer, buffer->allocated - 1); // Doubles capacity every round. -1 for the null byte.
free = ffStrbufGetFree(buffer);
available = ffStrbufGetFree(buffer);
}
}

buffer->chars[buffer->length] = '\0';
bool ffAppendFDBuffer(HANDLE handle, FFstrbuf* buffer)
{
LARGE_INTEGER fileSize;
if(!GetFileSizeEx(handle, &fileSize))
fileSize.QuadPart = 0;

if (fileSize.QuadPart > 0)
readWithLength(handle, buffer, (uint32_t)fileSize.QuadPart);
else
readUntilEOF(handle, buffer);

ffStrbufTrimRight(buffer, '\n');
ffStrbufTrimRight(buffer, ' ');
buffer->chars[buffer->length] = '\0';

return success;
return buffer->length > 0;
}

ssize_t ffReadFileData(const char* fileName, size_t dataSize, void* data)
Expand Down
3 changes: 2 additions & 1 deletion src/util/FFstrbuf.c
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ void ffStrbufEnsureFree(FFstrbuf* strbuf, uint32_t free)
strbuf->allocated = allocate;
}

// for an empty buffer, free + 1 length memory will be allocated(+1 for the NUL)
void ffStrbufEnsureFixedLengthFree(FFstrbuf* strbuf, uint32_t free)
{
uint32_t oldFree = ffStrbufGetFree(strbuf);
Expand All @@ -64,7 +65,7 @@ void ffStrbufEnsureFixedLengthFree(FFstrbuf* strbuf, uint32_t free)

if(strbuf->allocated == 0)
{
newCap += strbuf->length + 1; // +1 for the NUL
newCap += strbuf->length + 1;
char* newbuf = malloc(sizeof(*strbuf->chars) * newCap);
if(strbuf->length == 0)
*newbuf = '\0';
Expand Down