mirror of https://github.com/flysand7/ciabatta.git
Quick and dirty file api
This commit is contained in:
parent
dbd10db051
commit
5e177fae50
14
build.py
14
build.py
|
@ -123,10 +123,8 @@ try:
|
|||
ciabatta_header.write('\n')
|
||||
ciabatta_header.write('// This file is AUTO-GENERATED by library.json\n')
|
||||
ciabatta_header.write('\n')
|
||||
# Write includes
|
||||
for include in library_config['includes']:
|
||||
ciabatta_header.write(f'#include <{include}>\n')
|
||||
ciabatta_header.write('\n')
|
||||
# Write main include
|
||||
ciabatta_header.write('#include <cia-def.h>\n')
|
||||
# Write platform includes
|
||||
platform_config = None
|
||||
for platform in library_config['platforms']:
|
||||
|
@ -138,10 +136,14 @@ try:
|
|||
include_path = os.path.join(platform_config['path'], include)
|
||||
ciabatta_header.write(f'#include "{include_path}"\n')
|
||||
ciabatta_header.write(f'#include "{target}/tinyrt-iface.h"\n')
|
||||
ciabatta_header.write(f'#include "tinyrt.h"\n')
|
||||
ciabatta_header.write(f'#include <tinyrt.h>\n')
|
||||
for tinyrt_source in platform_config['tinyrt']:
|
||||
ciabatta_header.write(f'#include "{target}/{tinyrt_source}"\n')
|
||||
# Write API includes
|
||||
# Write module includes
|
||||
for include in library_config['includes']:
|
||||
ciabatta_header.write(f'#include <{include}>\n')
|
||||
ciabatta_header.write('\n')
|
||||
# Write module sources
|
||||
ciabatta_header.write('\n')
|
||||
for api in library_config['apis']:
|
||||
api_name = api['name']
|
||||
|
|
|
@ -0,0 +1,25 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <cia-def.h>
|
||||
#include <tinyrt.h>
|
||||
|
||||
typedef u64 size_t;
|
||||
|
||||
typedef struct FILE FILE;
|
||||
struct FILE {
|
||||
_RT_File rt_file;
|
||||
};
|
||||
|
||||
#define EOF (-1)
|
||||
|
||||
extern FILE *stdin;
|
||||
extern FILE *stdout;
|
||||
extern FILE *stderr;
|
||||
|
||||
FILE *fopen(const char *restrict filename, const char *restrict mode);
|
||||
int fgetc(FILE *file);
|
||||
int fputc(int c, FILE *file);
|
||||
size_t fread(void *restrict buf, size_t size, size_t count, FILE *restrict file);
|
||||
size_t fwrite(void const *restrict buf, size_t size, size_t count, FILE *restrict file);
|
||||
int fclose(FILE *file);
|
|
@ -50,7 +50,6 @@ static _RT_Status _rt_deinit();
|
|||
#endif
|
||||
|
||||
// File API
|
||||
#if _RT_API_FILE == 1
|
||||
struct _RT_File typedef _RT_File;
|
||||
struct _RT_File {
|
||||
union {
|
||||
|
@ -59,7 +58,12 @@ static _RT_Status _rt_deinit();
|
|||
};
|
||||
i32 flags;
|
||||
};
|
||||
static _RT_Status _rt_file_open(_RT_File *file, char *name, int flags);
|
||||
#if _RT_API_FILE == 1
|
||||
static _RT_File _rt_file_stdin;
|
||||
static _RT_File _rt_file_stdout;
|
||||
static _RT_File _rt_file_stderr;
|
||||
static _RT_Status _rt_file_std_handles_init();
|
||||
static _RT_Status _rt_file_open(_RT_File *file, char const *name, int flags);
|
||||
static _RT_Status _rt_file_read(u64 size, void *buffer, _RT_File *from, u64 *out_bytes_read);
|
||||
static _RT_Status _rt_file_write(_RT_File *to, u64 size, void *buffer, u64 *out_bytes_written);
|
||||
static _RT_Status _rt_file_close(_RT_File *file);
|
|
@ -0,0 +1,85 @@
|
|||
|
||||
FILE *stdin;
|
||||
FILE *stdout;
|
||||
FILE *stderr;
|
||||
|
||||
// TODO: memory allocation
|
||||
static FILE _files[64];
|
||||
static int _files_cnt = 0;
|
||||
|
||||
static void _fileapi_init() {
|
||||
_rt_file_std_handles_init();
|
||||
stdin = &_files[_files_cnt++];
|
||||
stdin->rt_file = _rt_file_stdin;
|
||||
stdout = &_files[_files_cnt++];
|
||||
stdout->rt_file = _rt_file_stdout;
|
||||
stderr = &_files[_files_cnt++];
|
||||
stderr->rt_file = _rt_file_stderr;
|
||||
}
|
||||
|
||||
FILE *fopen(char const *restrict filename, char const *restrict mode) {
|
||||
_RT_File rt_file;
|
||||
int flags = 0;
|
||||
while(*mode) {
|
||||
if(*mode == 'r') flags |= _RT_FILE_READ;
|
||||
if(*mode == 'w') flags |= _RT_FILE_WRITE;
|
||||
// TODO: other flags
|
||||
mode += 1;
|
||||
}
|
||||
_RT_Status status = _rt_file_open(&rt_file, filename, flags);
|
||||
if(status != _RT_STATUS_OK) {
|
||||
return NULL;
|
||||
}
|
||||
FILE *file = &_files[_files_cnt];
|
||||
_files_cnt += 1;
|
||||
file->rt_file = rt_file;
|
||||
return file;
|
||||
}
|
||||
|
||||
int fgetc(FILE *file) {
|
||||
int c = 0;
|
||||
u64 bytes_read;
|
||||
_RT_Status status = _rt_file_read(1, &c, &file->rt_file, &bytes_read);
|
||||
if(status == _RT_STATUS_FILE_EOF) {
|
||||
return EOF;
|
||||
}
|
||||
else if(status != _RT_STATUS_OK) {
|
||||
return EOF;
|
||||
}
|
||||
return c;
|
||||
}
|
||||
|
||||
int fputc(int c, FILE *file) {
|
||||
u64 bytes_written;
|
||||
_RT_Status status = _rt_file_write(&file->rt_file, 1, &c, &bytes_written);
|
||||
if(status != _RT_STATUS_OK) {
|
||||
return EOF;
|
||||
}
|
||||
return c;
|
||||
}
|
||||
|
||||
size_t fread(void *restrict buf, size_t size, size_t count, FILE *restrict file) {
|
||||
u64 bytes_read;
|
||||
_RT_Status status = _rt_file_read(size*count, buf, &file->rt_file, &bytes_read);
|
||||
if(status != _RT_STATUS_OK) {
|
||||
return 0;
|
||||
}
|
||||
return bytes_read / size;
|
||||
}
|
||||
|
||||
size_t fwrite(void const *restrict buf, size_t size, size_t count, FILE *restrict file) {
|
||||
u64 bytes_written;
|
||||
_RT_Status status = _rt_file_write(&file->rt_file, size*count, (void *)buf, &bytes_written);
|
||||
if(status != _RT_STATUS_OK) {
|
||||
return 0;
|
||||
}
|
||||
return bytes_written / size;
|
||||
}
|
||||
|
||||
int fclose(FILE *file) {
|
||||
_RT_Status status = _rt_file_close(&file->rt_file);
|
||||
if(status != _RT_STATUS_OK) {
|
||||
return EOF;
|
||||
}
|
||||
return 0;
|
||||
}
|
|
@ -24,8 +24,8 @@
|
|||
// this module will not be included in the final build
|
||||
|
||||
includes: [
|
||||
"cia-def.h",
|
||||
"stdlib.h"
|
||||
"stdlib.h",
|
||||
"stdio.h",
|
||||
],
|
||||
|
||||
platforms: [
|
||||
|
@ -60,6 +60,16 @@ apis: [
|
|||
"rt_api_program",
|
||||
]
|
||||
},
|
||||
{
|
||||
name: "stdlib_file",
|
||||
path: "impl/stdlib-file",
|
||||
includes: [
|
||||
"file.c"
|
||||
],
|
||||
reqs: [
|
||||
"rt_api_file"
|
||||
]
|
||||
}
|
||||
]
|
||||
|
||||
// END
|
||||
|
|
|
@ -10,6 +10,8 @@ void __stack_chk_fail(void) {
|
|||
syscall_exit(1);
|
||||
}
|
||||
|
||||
static void _fileapi_init();
|
||||
|
||||
void __libc_start_main(
|
||||
int (*main)(int, char**, char**),
|
||||
int argc, char **argv,
|
||||
|
@ -21,6 +23,7 @@ void __libc_start_main(
|
|||
// Get the envp
|
||||
char **envp = argv + (argc + 1);
|
||||
init(argc, argv, envp);
|
||||
_fileapi_init();
|
||||
main(argc, argv, envp);
|
||||
fini();
|
||||
// glibc bug
|
||||
|
|
|
@ -1,7 +1,20 @@
|
|||
|
||||
// See src/tinyrt.h file for the interface this file implements
|
||||
|
||||
static _RT_Status _rt_file_open(_RT_File *file, char *name, int _rt_flags) {
|
||||
static _RT_File _rt_file_stdin;
|
||||
static _RT_File _rt_file_stderr;
|
||||
|
||||
static _RT_Status _rt_file_std_handles_init() {
|
||||
_rt_file_stdin.fd = 0;
|
||||
_rt_file_stdin.flags = _RT_FILE_READ;
|
||||
_rt_file_stdout.fd = 1;
|
||||
_rt_file_stdout.flags = _RT_FILE_WRITE;
|
||||
_rt_file_stderr.fd = 2;
|
||||
_rt_file_stdout.flags = _RT_FILE_WRITE;
|
||||
return _RT_STATUS_OK;
|
||||
}
|
||||
|
||||
static _RT_Status _rt_file_open(_RT_File *file, char const *name, int _rt_flags) {
|
||||
if((_rt_flags & 0x3) == 0) {
|
||||
return _RT_ERROR_BAD_PARAM;
|
||||
}
|
||||
|
|
|
@ -1,22 +1,9 @@
|
|||
|
||||
#include <cia-def.h>
|
||||
|
||||
#define STDOUT_FILENO 1
|
||||
#define SYS_write 1
|
||||
|
||||
static __inline i64 __syscall3(i64 n, i64 a1, i64 a2, i64 a3) {
|
||||
i64 ret;
|
||||
__asm__ __volatile__ ("syscall" : "=a"(ret) : "a"(n), "D"(a1), "S"(a2),
|
||||
"d"(a3) : "rcx", "r11", "memory");
|
||||
return ret;
|
||||
}
|
||||
|
||||
static inline i64 syscall_write(u32 fd, char const *buf, u64 count) {
|
||||
return __syscall3(SYS_write, (i64)fd, (i64)buf, (u64)count);
|
||||
}
|
||||
#include <stdio.h>
|
||||
|
||||
int main(int argc, char **argv, char **envp) {
|
||||
char string[] = "Hello, world!\n";
|
||||
syscall_write(STDOUT_FILENO, string, sizeof string);
|
||||
fwrite(string, 1, sizeof string-1, stdout);
|
||||
return 0;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue