This repository has been archived on 2025-02-26. You can view files and clone it, but cannot push or open issues or pull requests.
hilbert-os/euler/source/std/cstdio.cpp

60 lines
1.6 KiB
C++

#include <cstdio>
#include <string>
extern "C" FILE *fopen(const char *filename, const char *mode) {
bool r = false, w = false, a = false, p = false, x = false;
for (size_t i = 0; mode[i] != '\0'; ++i)
if (mode[i] == 'r') r = true;
else if (mode[i] == 'w') w = true;
else if (mode[i] == 'a') a = true;
else if (mode[i] == 'p') p = true;
else if (mode[i] == 'x') x = true;
euler::syscall::stream_handle handle;
if (euler::syscall::open_file(filename, !r, x, handle) !=
euler::syscall::stream_result::success)
return 0;
if (w && euler::syscall::set_stream_length(handle, 0) !=
euler::syscall::stream_result::success)
return 0;
if (a && euler::syscall::seek_stream(
handle, euler::syscall::seek_from::end, 0) !=
euler::syscall::stream_result::success) {
euler::syscall::close_stream(handle);
return 0;
}
uint64_t length;
if (euler::syscall::get_stream_length(handle, length) !=
euler::syscall::stream_result::success) {
euler::syscall::close_stream(handle);
return 0;
}
return new euler::file_stream(handle, r || p, length, a ? length : 0);
}
extern "C" void fclose(FILE *stream) {
stream->close();
delete stream;
}
extern "C" int fseek(FILE *stream, long offset, int origin) {
if (origin < 0 || origin > 2)
return -1;
return (int)stream->seek((euler::syscall::seek_from)origin, offset);
}
extern "C" size_t fread(
void *buffer, size_t size, size_t count, FILE *stream) {
return (stream->read(size * count, buffer).first - 1) / size + 1;
}