kolibri-libc:

- Added full import console.obj
- Added dir.h
- Fixed dirent bug
- Added dirent example
- Fixed localtime bug.

git-svn-id: svn://kolibrios.org@8744 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
turbocat 2021-05-25 15:38:14 +00:00
parent 4bc3d82296
commit a749f672ce
18 changed files with 169 additions and 904 deletions

View File

@ -96,8 +96,7 @@ extern int _FUNC(getc)(FILE *);
#define getc() _FUNC(fgetc)(stdin) #define getc() _FUNC(fgetc)(stdin)
extern int _FUNC(getchar)(void); extern int _FUNC(getchar)(void);
extern int _FUNC(printf)(const char *restrict, ...); extern int _FUNC(printf)(const char *restrict, ...);
extern int _FUNC(putc)(int, FILE *); #define putc(ch) _FUNC(fputc)(ch, stdout)
extern int _FUNC(putchar)(int);
extern int _FUNC(puts)(const char *); extern int _FUNC(puts)(const char *);
extern int _FUNC(scanf)(const char *restrict, ...); extern int _FUNC(scanf)(const char *restrict, ...);
extern char* _FUNC(gets)(char *str); extern char* _FUNC(gets)(char *str);
@ -136,6 +135,4 @@ extern size_t _FUNC(fread)(void *restrict, size_t, size_t, FILE *restrict);
extern int _FUNC(getchar)(void); extern int _FUNC(getchar)(void);
extern void _FUNC(con_set_title)(const char*);
#endif // _STDIO_H_ #endif // _STDIO_H_

View File

@ -24,11 +24,11 @@ typedef struct{
}DIR; }DIR;
int _FUNC(closedir)(DIR *dir); extern int _FUNC(closedir)(DIR *dir);
DIR* _FUNC(opendir)(const char *path); extern DIR* _FUNC(opendir)(const char *path);
struct dirent* _FUNC(readdir)(DIR *); extern struct dirent* _FUNC(readdir)(DIR *);
void _FUNC(rewinddir)(DIR *dir); extern void _FUNC(rewinddir)(DIR *dir);
void _FUNC(seekdir)(DIR *dir, unsigned pos); extern void _FUNC(seekdir)(DIR *dir, unsigned pos);
unsigned _FUNC(telldir)(DIR *dir); extern unsigned _FUNC(telldir)(DIR *dir);
#endif // _DIRENT_H_ #endif // _DIRENT_H_

View File

@ -0,0 +1,45 @@
#include <sys/dirent.h>
#include <sys/dir.h>
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
const char *folder_type = "Folder";
const char *file_type = "File";
int main()
{
char *path=getcwd(NULL, PATH_MAX);
printf("Current directory: %s\n", path);
if(mkdir("test")){
puts("Test folder created!");
}
else{
puts("Error creating folder!");
}
DIR *mydir = opendir(path);
if(!mydir){
puts("File system error.");
return -1;
}
struct dirent *file_info;
char *str_type=NULL;
putc(' ');
while((file_info = readdir(mydir))!=NULL){
if(file_info->d_type==IS_FOLDER){
(*con_set_flags)(CON_COLOR_GREEN);
str_type = (char*)folder_type;
}else {
(*con_set_flags)(7);
str_type = (char*)file_type;
}
printf("%3d %20s %s\n ", file_info->d_ino ,file_info->d_name, str_type);
};
setcwd("/sys/develop");
path=getcwd(NULL, PATH_MAX);
printf("Move to the directory: %s\n", path);
free(path);
}

View File

@ -14,6 +14,7 @@ unsigned _libc_get_version(){
#include "sys/opendir.c" #include "sys/opendir.c"
#include "sys/telldir.c" #include "sys/telldir.c"
#include "sys/closedir.c" #include "sys/closedir.c"
#include "sys/dir.c"
#include "stdio/clearerr.c" #include "stdio/clearerr.c"
#include "stdio/gets.c" #include "stdio/gets.c"

View File

@ -1,56 +1,62 @@
#include <sys/ksys.h> #include <sys/ksys.h>
#include "conio.h" #include <conio.h>
#include "stdio.h"
static char* __con_caption = "Console application"; static char* __con_caption = "Console application";
static char* __con_dllname = "/sys/lib/console.obj"; static char* __con_dllname = "/sys/lib/console.obj";
int __con_is_load = 0; int __con_is_load = 0;
void stdcall (*__con_init_hidden)(int wnd_width, int wnd_height,int scr_width, int scr_height, const char* title); void stdcall (*__con_init_hidden)(int wnd_width, unsigned wnd_height, int scr_width, int scr_height, const char* title);
void stdcall (*__con_write_asciiz)(const char* str); void stdcall (*con_exit)(int);
void stdcall (*__con_write_string)(const char* str, unsigned length); void stdcall (*con_set_title)(const char* title);
int stdcall (*__con_getch)(void); void stdcall (*con_write_asciiz)(const char* str);
short stdcall (*__con_getch2)(void); void stdcall (*con_write_string)(const char* str, dword length);
int stdcall (*__con_kbhit)(void); int cdecl (*con_printf)(const char* format, ...);
char* stdcall (*__con_gets)(char* str, int n); dword stdcall (*con_get_flags)(void);
char* stdcall (*__con_gets2)(__con_gets2_callback callback, char* str, int n); dword stdcall (*con_set_flags)(dword new_flags);
void stdcall (*__con_exit)(int status); int stdcall (*con_get_font_height)(void);
void stdcall (*__con_set_title)(const char* title); int stdcall (*con_get_cursor_height)(void);
int stdcall (*con_set_cursor_height)(int new_height);
int stdcall (*con_getch)(void);
word stdcall (*con_getch2)(void);
int stdcall (*con_kbhit)(void);
char* stdcall (*con_gets)(char* str, int n);
char* stdcall (*con_gets2)(con_gets2_callback callback, char* str, int n);
void stdcall (*con_cls)();
void stdcall (*con_get_cursor_pos)(int* px, int* py);
void stdcall (*con_set_cursor_pos)(int x, int y);
static void __con_panic(char* func_name) static void __con_panic(char* func_name)
{ {
_ksys_debug_puts("libc.obj: "); debug_printf("In console.obj %s=NULL!\n", func_name);
_ksys_debug_puts(func_name);
_ksys_debug_puts(" = NULL\n");
_ksys_exit(); _ksys_exit();
} }
static void __con_lib_link(ksys_coff_etable_t *exp) static void __con_lib_link(ksys_coff_etable_t *exp)
{ {
__con_init_hidden = _ksys_get_coff_func(exp, "con_init", __con_panic); __con_init_hidden = _ksys_get_coff_func(exp, "con_init", __con_panic);
__con_write_asciiz = _ksys_get_coff_func(exp, "con_write_asciiz", __con_panic); con_exit = _ksys_get_coff_func(exp, "con_exit", __con_panic);
__con_write_string = _ksys_get_coff_func(exp, "con_write_string", __con_panic); con_set_title = _ksys_get_coff_func(exp, "con_set_title", __con_panic);
__con_getch = _ksys_get_coff_func(exp, "con_getch", __con_panic); con_write_asciiz = _ksys_get_coff_func(exp, "con_write_asciiz", __con_panic);
__con_getch2 = _ksys_get_coff_func(exp, "con_getch2", __con_panic); con_write_string = _ksys_get_coff_func(exp, "con_write_string", __con_panic);
__con_kbhit = _ksys_get_coff_func(exp, "con_kbhit", __con_panic); con_printf = _ksys_get_coff_func(exp, "con_printf", __con_panic);
__con_gets = _ksys_get_coff_func(exp, "con_gets", __con_panic); con_get_flags = _ksys_get_coff_func(exp, "con_get_flags", __con_panic);
__con_gets2 = _ksys_get_coff_func(exp, "con_gets2", __con_panic); con_set_flags = _ksys_get_coff_func(exp, "con_set_flags", __con_panic);
__con_exit = _ksys_get_coff_func(exp, "con_exit", __con_panic); con_get_font_height = _ksys_get_coff_func(exp, "con_get_font_height", __con_panic);
__con_set_title = _ksys_get_coff_func(exp, "con_set_title", __con_panic); con_get_cursor_height = _ksys_get_coff_func(exp, "con_get_cursor_height", __con_panic);
con_set_cursor_height = _ksys_get_coff_func(exp, "con_set_cursor_height", __con_panic);
con_getch = _ksys_get_coff_func(exp, "con_getch", __con_panic);
con_getch2 = _ksys_get_coff_func(exp, "con_getch2", __con_panic);
con_kbhit = _ksys_get_coff_func(exp, "con_kbhit", __con_panic);
con_gets = _ksys_get_coff_func(exp, "con_gets", __con_panic);
con_gets2 = _ksys_get_coff_func(exp, "con_gets2", __con_panic);
con_cls = _ksys_get_coff_func(exp, "con_cls", __con_panic);
con_get_cursor_pos = _ksys_get_coff_func(exp, "con_get_cursor_pos", __con_panic);
con_set_cursor_pos = _ksys_get_coff_func(exp, "con_set_cursor_pos", __con_panic);
} }
int con_init_opt(dword wnd_width, dword wnd_height, dword scr_width, dword scr_height, const char* title)
int __con_init(void)
{
return __con_init_opt(-1, -1, -1, -1, __con_caption);
}
void con_set_title(const char* title){
__con_init();
__con_set_title(title);
}
int __con_init_opt(int wnd_width, int wnd_height,int scr_width, int scr_height, const char* title)
{ {
if(!__con_is_load){ if(!__con_is_load){
ksys_coff_etable_t *__con_lib; ksys_coff_etable_t *__con_lib;
@ -66,3 +72,10 @@ int __con_init_opt(int wnd_width, int wnd_height,int scr_width, int scr_height,
} }
return 1; return 1;
} }
int con_init(void)
{
return con_init_opt(-1, -1, -1, -1, __con_caption);
}

View File

@ -1,76 +0,0 @@
/*
This is adapded thunk for console.obj sys library
Only for internal use in stdio.h
Adapted for tcc by Siemargl, 2016
*/
#ifndef _CONIO_H_
#define _CONIO_H_
#define cdecl __attribute__ ((cdecl))
#define stdcall __attribute__ ((stdcall))
void stdcall (*__con_write_asciiz)(const char* str);
/* Display ASCIIZ-string to the console at the current position, shifting
the current position. */
void stdcall (*__con_write_string)(const char* str, unsigned length);
/* Similar to __con_write_asciiz, but length of the string must be given as a
separate parameter */
int stdcall (*__con_getch)(void);
/* Get one character from the keyboard.
For normal characters function returns ASCII-code. For extended
characters (eg, Fx, and arrows), first function call returns 0
and second call returns the extended code (similar to the DOS-function
input). Starting from version 7, after closing the console window,
this function returns 0. */
short stdcall (*__con_getch2)(void);
/* Reads a character from the keyboard. Low byte contains the ASCII-code
(0 for extended characters), high byte - advanced code (like in BIOS
input functions). Starting from version 7, after closing the console
window, this function returns 0. */
int stdcall (*__con_kbhit)(void);
/* Returns 1 if a key was pressed, 0 otherwise. To read pressed keys use
__con_getch and __con_getch2. Starting from version 6, after closing
the console window, this function returns 1. */
char* stdcall (*__con_gets)(char* str, int n);
/* Reads a string from the keyboard. Reading is interrupted when got
"new line" character, or after reading the (n-1) characters (depending on
what comes first). In the first case the newline is also recorded in the
str. The acquired line is complemented by a null character.
Starting from version 6, the function returns a pointer to the entered
line if reading was successful, and NULL if the console window was closed. */
typedef int (stdcall * __con_gets2_callback)(int keycode, char** pstr, int* pn,
int* ppos);
char* stdcall (*__con_gets2)(__con_gets2_callback callback, char* str, int n);
/* Con_gets completely analogous, except that when the user
press unrecognized key, it calls the specified callback-procedure
(which may, for example, handle up / down for history and tab to enter
autocompletion). You should pass to the procedure: key code and three pointers
- to the string, to the maximum length and to the current position.
function may change the contents of string and may change the string
itself (for example, to reallocate memory for increase the limit),
maximum length, and position of the line - pointers are passed for it.
Return value: 0 = line wasn't changed 1 = line changed, you should
remove old string and display new, 2 = line changed, it is necessary
to display it; 3 = immediately exit the function.
Starting from version 6, the function returns a pointer to the entered
line with the successful reading, and NULL if the console window was closed. */
int __con_is_load;
unsigned *__con_dll_ver;
int __con_init(void);
int __con_init_opt(int wnd_width, int wnd_height, int scr_width, int scr_height, const char* title);
void stdcall (*__con_exit)(int status);
#endif

View File

@ -13,8 +13,8 @@ size_t fread(void *restrict ptr, size_t size, size_t nmemb, FILE *restrict strea
} }
if(stream==stdin){ if(stream==stdin){
__con_init(); con_init();
__con_gets((char*)ptr, bytes_count+1); con_gets((char*)ptr, bytes_count+1);
return nmemb; return nmemb;
} }

View File

@ -3,7 +3,6 @@
#include <sys/ksys.h> #include <sys/ksys.h>
#include <errno.h> #include <errno.h>
size_t fwrite(const void *restrict ptr, size_t size, size_t nmemb, FILE *restrict stream) { size_t fwrite(const void *restrict ptr, size_t size, size_t nmemb, FILE *restrict stream) {
unsigned bytes_written = 0; unsigned bytes_written = 0;
unsigned bytes_count = size * nmemb; unsigned bytes_count = size * nmemb;
@ -14,8 +13,8 @@ size_t fwrite(const void *restrict ptr, size_t size, size_t nmemb, FILE *restric
} }
if(stream==stdout){ if(stream==stdout){
__con_init(); con_init();
__con_write_string((char*)ptr, bytes_count); con_write_string((char*)ptr, bytes_count);
return nmemb; return nmemb;
} }
else if(stream==stderr){ else if(stream==stderr){

View File

@ -1,10 +1,10 @@
#include <stdio.h> #include <stdio.h>
#include "conio.h" #include <conio.h>
int getchar(void) { int getchar(void) {
__con_init(); con_init();
char c = 0; char c = 0;
__con_gets(&c, 2); con_gets(&c, 2);
if (c == 0) { if (c == 0) {
c = EOF; c = EOF;
} }

View File

@ -6,8 +6,8 @@
char *gets(char* str) char *gets(char* str)
{ {
__con_init(); con_init();
if(__con_gets(str, STDIO_MAX_MEM)==NULL){ if(con_gets(str, STDIO_MAX_MEM)==NULL){
errno = EIO; errno = EIO;
return NULL; return NULL;
} }

View File

@ -7,8 +7,8 @@
int puts(const char *str) int puts(const char *str)
{ {
__con_init(); con_init();
__con_write_asciiz(str); con_write_asciiz(str);
__con_write_asciiz("\n"); con_write_asciiz("\n");
return strlen(str); return strlen(str);
} }

View File

@ -18,9 +18,9 @@ int vprintf ( const char * format, va_list arg )
errno = ENOMEM; errno = ENOMEM;
return errno; return errno;
} }
__con_init(); con_init();
len = vsnprintf(s, STDIO_MAX_MEM, format, arg); len = vsnprintf(s, STDIO_MAX_MEM, format, arg);
__con_write_string(s, len); con_write_string(s, len);
free(s); free(s);
return(len); return(len);
} }

View File

@ -1,12 +1,12 @@
/* Copyright (C) 2021 Logaev Maxim (turbocat2001), GPLv2 */ /* Copyright (C) 2021 Logaev Maxim (turbocat2001), GPLv2 */
#include "../stdio/conio.h" #include <conio.h>
#include <sys/ksys.h> #include <sys/ksys.h>
void exit(int status) void exit(int status)
{ {
if(__con_is_load){ if(__con_is_load){
__con_exit(status); con_exit(status);
} }
_ksys_exit(); _ksys_exit();
} }

View File

@ -1,763 +0,0 @@
/* TCC runtime library.
Parts of this code are (c) 2002 Fabrice Bellard
Copyright (C) 1987, 1988, 1992, 1994, 1995 Free Software Foundation, Inc.
This file is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 2, or (at your option) any
later version.
In addition to the permissions in the GNU General Public License, the
Free Software Foundation gives you unlimited permission to link the
compiled version of this file into combinations with other programs,
and to distribute those combinations without any restriction coming
from the use of this file. (The General Public License restrictions
do apply in other respects; for example, they cover modification of
the file, and distribution when not linked into a combine
executable.)
This file is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; see the file COPYING. If not, write to
the Free Software Foundation, 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA.
*/
//#include <stdint.h>
#define TCC_TARGET_I386
#define W_TYPE_SIZE 32
#define BITS_PER_UNIT 8
typedef int Wtype;
typedef unsigned int UWtype;
typedef unsigned int USItype;
typedef long long DWtype;
typedef unsigned long long UDWtype;
struct DWstruct {
Wtype low, high;
};
typedef union
{
struct DWstruct s;
DWtype ll;
} DWunion;
typedef long double XFtype;
#define WORD_SIZE (sizeof (Wtype) * BITS_PER_UNIT)
#define HIGH_WORD_COEFF (((UDWtype) 1) << WORD_SIZE)
/* the following deal with IEEE single-precision numbers */
#define EXCESS 126
#define SIGNBIT 0x80000000
#define HIDDEN (1 << 23)
#define SIGN(fp) ((fp) & SIGNBIT)
#define EXP(fp) (((fp) >> 23) & 0xFF)
#define MANT(fp) (((fp) & 0x7FFFFF) | HIDDEN)
#define PACK(s,e,m) ((s) | ((e) << 23) | (m))
/* the following deal with IEEE double-precision numbers */
#define EXCESSD 1022
#define HIDDEND (1 << 20)
#define EXPD(fp) (((fp.l.upper) >> 20) & 0x7FF)
#define SIGND(fp) ((fp.l.upper) & SIGNBIT)
#define MANTD(fp) (((((fp.l.upper) & 0xFFFFF) | HIDDEND) << 10) | \
(fp.l.lower >> 22))
#define HIDDEND_LL ((long long)1 << 52)
#define MANTD_LL(fp) ((fp.ll & (HIDDEND_LL-1)) | HIDDEND_LL)
#define PACKD_LL(s,e,m) (((long long)((s)+((e)<<20))<<32)|(m))
/* the following deal with x86 long double-precision numbers */
#define EXCESSLD 16382
#define EXPLD(fp) (fp.l.upper & 0x7fff)
#define SIGNLD(fp) ((fp.l.upper) & 0x8000)
/* only for x86 */
union ldouble_long {
long double ld;
struct {
unsigned long long lower;
unsigned short upper;
} l;
};
union double_long {
double d;
#if 1
struct {
unsigned int lower;
int upper;
} l;
#else
struct {
int upper;
unsigned int lower;
} l;
#endif
long long ll;
};
union float_long {
float f;
unsigned int l;
};
/* XXX: we don't support several builtin supports for now */
#if !defined(TCC_TARGET_X86_64) && !defined(TCC_TARGET_ARM)
/* XXX: use gcc/tcc intrinsic ? */
#if defined(TCC_TARGET_I386)
#define sub_ddmmss(sh, sl, ah, al, bh, bl) \
__asm__ ("subl %5,%1\n\tsbbl %3,%0" \
: "=r" ((USItype) (sh)), \
"=&r" ((USItype) (sl)) \
: "0" ((USItype) (ah)), \
"g" ((USItype) (bh)), \
"1" ((USItype) (al)), \
"g" ((USItype) (bl)))
#define umul_ppmm(w1, w0, u, v) \
__asm__ ("mull %3" \
: "=a" ((USItype) (w0)), \
"=d" ((USItype) (w1)) \
: "%0" ((USItype) (u)), \
"rm" ((USItype) (v)))
#define udiv_qrnnd(q, r, n1, n0, dv) \
__asm__ ("divl %4" \
: "=a" ((USItype) (q)), \
"=d" ((USItype) (r)) \
: "0" ((USItype) (n0)), \
"1" ((USItype) (n1)), \
"rm" ((USItype) (dv)))
#define count_leading_zeros(count, x) \
do { \
USItype __cbtmp; \
__asm__ ("bsrl %1,%0" \
: "=r" (__cbtmp) : "rm" ((USItype) (x))); \
(count) = __cbtmp ^ 31; \
} while (0)
#else
#error unsupported CPU type
#endif
/* most of this code is taken from libgcc2.c from gcc */
UDWtype __udivmoddi4 (UDWtype n, UDWtype d, UDWtype *rp)
{
DWunion ww;
DWunion nn, dd;
DWunion rr;
UWtype d0, d1, n0, n1, n2;
UWtype q0, q1;
UWtype b, bm;
nn.ll = n;
dd.ll = d;
d0 = dd.s.low;
d1 = dd.s.high;
n0 = nn.s.low;
n1 = nn.s.high;
#if !defined(UDIV_NEEDS_NORMALIZATION)
if (d1 == 0)
{
if (d0 > n1)
{
/* 0q = nn / 0D */
udiv_qrnnd (q0, n0, n1, n0, d0);
q1 = 0;
/* Remainder in n0. */
}
else
{
/* qq = NN / 0d */
if (d0 == 0)
d0 = 1 / d0; /* Divide intentionally by zero. */
udiv_qrnnd (q1, n1, 0, n1, d0);
udiv_qrnnd (q0, n0, n1, n0, d0);
/* Remainder in n0. */
}
if (rp != 0)
{
rr.s.low = n0;
rr.s.high = 0;
*rp = rr.ll;
}
}
#else /* UDIV_NEEDS_NORMALIZATION */
if (d1 == 0)
{
if (d0 > n1)
{
/* 0q = nn / 0D */
count_leading_zeros (bm, d0);
if (bm != 0)
{
/* Normalize, i.e. make the most significant bit of the
denominator set. */
d0 = d0 << bm;
n1 = (n1 << bm) | (n0 >> (W_TYPE_SIZE - bm));
n0 = n0 << bm;
}
udiv_qrnnd (q0, n0, n1, n0, d0);
q1 = 0;
/* Remainder in n0 >> bm. */
}
else
{
/* qq = NN / 0d */
if (d0 == 0)
d0 = 1 / d0; /* Divide intentionally by zero. */
count_leading_zeros (bm, d0);
if (bm == 0)
{
/* From (n1 >= d0) /\ (the most significant bit of d0 is set),
conclude (the most significant bit of n1 is set) /\ (the
leading quotient digit q1 = 1).
This special case is necessary, not an optimization.
(Shifts counts of W_TYPE_SIZE are undefined.) */
n1 -= d0;
q1 = 1;
}
else
{
/* Normalize. */
b = W_TYPE_SIZE - bm;
d0 = d0 << bm;
n2 = n1 >> b;
n1 = (n1 << bm) | (n0 >> b);
n0 = n0 << bm;
udiv_qrnnd (q1, n1, n2, n1, d0);
}
/* n1 != d0... */
udiv_qrnnd (q0, n0, n1, n0, d0);
/* Remainder in n0 >> bm. */
}
if (rp != 0)
{
rr.s.low = n0 >> bm;
rr.s.high = 0;
*rp = rr.ll;
}
}
#endif /* UDIV_NEEDS_NORMALIZATION */
else
{
if (d1 > n1)
{
/* 00 = nn / DD */
q0 = 0;
q1 = 0;
/* Remainder in n1n0. */
if (rp != 0)
{
rr.s.low = n0;
rr.s.high = n1;
*rp = rr.ll;
}
}
else
{
/* 0q = NN / dd */
count_leading_zeros (bm, d1);
if (bm == 0)
{
/* From (n1 >= d1) /\ (the most significant bit of d1 is set),
conclude (the most significant bit of n1 is set) /\ (the
quotient digit q0 = 0 or 1).
This special case is necessary, not an optimization. */
/* The condition on the next line takes advantage of that
n1 >= d1 (true due to program flow). */
if (n1 > d1 || n0 >= d0)
{
q0 = 1;
sub_ddmmss (n1, n0, n1, n0, d1, d0);
}
else
q0 = 0;
q1 = 0;
if (rp != 0)
{
rr.s.low = n0;
rr.s.high = n1;
*rp = rr.ll;
}
}
else
{
UWtype m1, m0;
/* Normalize. */
b = W_TYPE_SIZE - bm;
d1 = (d1 << bm) | (d0 >> b);
d0 = d0 << bm;
n2 = n1 >> b;
n1 = (n1 << bm) | (n0 >> b);
n0 = n0 << bm;
udiv_qrnnd (q0, n1, n2, n1, d1);
umul_ppmm (m1, m0, q0, d0);
if (m1 > n1 || (m1 == n1 && m0 > n0))
{
q0--;
sub_ddmmss (m1, m0, m1, m0, d1, d0);
}
q1 = 0;
/* Remainder in (n1n0 - m1m0) >> bm. */
if (rp != 0)
{
sub_ddmmss (n1, n0, n1, n0, m1, m0);
rr.s.low = (n1 << b) | (n0 >> bm);
rr.s.high = n1 >> bm;
*rp = rr.ll;
}
}
}
}
ww.s.low = q0;
ww.s.high = q1;
return ww.ll;
}
#define __negdi2(a) (-(a))
long long __divdi3(long long u, long long v)
{
int c = 0;
DWunion uu, vv;
DWtype w;
uu.ll = u;
vv.ll = v;
if (uu.s.high < 0) {
c = ~c;
uu.ll = __negdi2 (uu.ll);
}
if (vv.s.high < 0) {
c = ~c;
vv.ll = __negdi2 (vv.ll);
}
w = __udivmoddi4 (uu.ll, vv.ll, (UDWtype *) 0);
if (c)
w = __negdi2 (w);
return w;
}
// https://github.com/KaMeHb-UA/UE4m/blob/1d9ad5bfead06520570c7f24dad062f9f8717c1a/\
Engine/Extras/ThirdPartyNotUE/emsdk/emscripten/incoming/system/lib/compiler-rt/lib/\
builtins/divmoddi4.c
long long __divmoddi4(long long a, long long b, long long* rem)
{
long long d = __divdi3(a, b);
*rem = a - (d * b);
return d;
}
long long __moddi3(long long u, long long v)
{
int c = 0;
DWunion uu, vv;
DWtype w;
uu.ll = u;
vv.ll = v;
if (uu.s.high < 0) {
c = ~c;
uu.ll = __negdi2 (uu.ll);
}
if (vv.s.high < 0)
vv.ll = __negdi2 (vv.ll);
__udivmoddi4 (uu.ll, vv.ll, (UDWtype *) &w);
if (c)
w = __negdi2 (w);
return w;
}
unsigned long long __udivdi3(unsigned long long u, unsigned long long v)
{
return __udivmoddi4 (u, v, (UDWtype *) 0);
}
unsigned long long __umoddi3(unsigned long long u, unsigned long long v)
{
UDWtype w;
__udivmoddi4 (u, v, &w);
return w;
}
/* XXX: fix tcc's code generator to do this instead */
long long __ashrdi3(long long a, int b)
{
#ifdef __TINYC__
DWunion u;
u.ll = a;
if (b >= 32) {
u.s.low = u.s.high >> (b - 32);
u.s.high = u.s.high >> 31;
} else if (b != 0) {
u.s.low = ((unsigned)u.s.low >> b) | (u.s.high << (32 - b));
u.s.high = u.s.high >> b;
}
return u.ll;
#else
return a >> b;
#endif
}
/* XXX: fix tcc's code generator to do this instead */
unsigned long long __lshrdi3(unsigned long long a, int b)
{
#ifdef __TINYC__
DWunion u;
u.ll = a;
if (b >= 32) {
u.s.low = (unsigned)u.s.high >> (b - 32);
u.s.high = 0;
} else if (b != 0) {
u.s.low = ((unsigned)u.s.low >> b) | (u.s.high << (32 - b));
u.s.high = (unsigned)u.s.high >> b;
}
return u.ll;
#else
return a >> b;
#endif
}
/* XXX: fix tcc's code generator to do this instead */
long long __ashldi3(long long a, int b)
{
#ifdef __TINYC__
DWunion u;
u.ll = a;
if (b >= 32) {
u.s.high = (unsigned)u.s.low << (b - 32);
u.s.low = 0;
} else if (b != 0) {
u.s.high = ((unsigned)u.s.high << b) | ((unsigned)u.s.low >> (32 - b));
u.s.low = (unsigned)u.s.low << b;
}
return u.ll;
#else
return a << b;
#endif
}
#ifndef COMMIT_4ad186c5ef61_IS_FIXED
long long __tcc_cvt_ftol(long double x)
{
unsigned c0, c1;
long long ret;
__asm__ __volatile__ ("fnstcw %0" : "=m" (c0));
c1 = c0 | 0x0C00;
__asm__ __volatile__ ("fldcw %0" : : "m" (c1));
__asm__ __volatile__ ("fistpll %0" : "=m" (ret));
__asm__ __volatile__ ("fldcw %0" : : "m" (c0));
return ret;
}
#endif
#endif /* !__x86_64__ */
/* XXX: fix tcc's code generator to do this instead */
float __floatundisf(unsigned long long a)
{
DWunion uu;
XFtype r;
uu.ll = a;
if (uu.s.high >= 0) {
return (float)uu.ll;
} else {
r = (XFtype)uu.ll;
r += 18446744073709551616.0;
return (float)r;
}
}
double __floatundidf(unsigned long long a)
{
DWunion uu;
XFtype r;
uu.ll = a;
if (uu.s.high >= 0) {
return (double)uu.ll;
} else {
r = (XFtype)uu.ll;
r += 18446744073709551616.0;
return (double)r;
}
}
long double __floatundixf(unsigned long long a)
{
DWunion uu;
XFtype r;
uu.ll = a;
if (uu.s.high >= 0) {
return (long double)uu.ll;
} else {
r = (XFtype)uu.ll;
r += 18446744073709551616.0;
return (long double)r;
}
}
unsigned long long __fixunssfdi (float a1)
{
register union float_long fl1;
register int exp;
register unsigned long l;
fl1.f = a1;
if (fl1.l == 0)
return (0);
exp = EXP (fl1.l) - EXCESS - 24;
l = MANT(fl1.l);
if (exp >= 41)
return (unsigned long long)-1;
else if (exp >= 0)
return (unsigned long long)l << exp;
else if (exp >= -23)
return l >> -exp;
else
return 0;
}
unsigned long long __fixunsdfdi (double a1)
{
register union double_long dl1;
register int exp;
register unsigned long long l;
dl1.d = a1;
if (dl1.ll == 0)
return (0);
exp = EXPD (dl1) - EXCESSD - 53;
l = MANTD_LL(dl1);
if (exp >= 12)
return (unsigned long long)-1;
else if (exp >= 0)
return l << exp;
else if (exp >= -52)
return l >> -exp;
else
return 0;
}
unsigned long long __fixunsxfdi (long double a1)
{
register union ldouble_long dl1;
register int exp;
register unsigned long long l;
dl1.ld = a1;
if (dl1.l.lower == 0 && dl1.l.upper == 0)
return (0);
exp = EXPLD (dl1) - EXCESSLD - 64;
l = dl1.l.lower;
if (exp > 0)
return (unsigned long long)-1;
else if (exp >= -63)
return l >> -exp;
else
return 0;
}
long long __fixsfdi (float a1)
{
long long ret; int s;
ret = __fixunssfdi((s = a1 >= 0) ? a1 : -a1);
return s ? ret : -ret;
}
long long __fixdfdi (double a1)
{
long long ret; int s;
ret = __fixunsdfdi((s = a1 >= 0) ? a1 : -a1);
return s ? ret : -ret;
}
long long __fixxfdi (long double a1)
{
long long ret; int s;
ret = __fixunsxfdi((s = a1 >= 0) ? a1 : -a1);
return s ? ret : -ret;
}
#if defined(TCC_TARGET_X86_64) && !defined(_WIN64)
#ifndef __TINYC__
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#else
/* Avoid including stdlib.h because it is not easily available when
cross compiling */
#include <stddef.h> /* size_t definition is needed for a x86_64-tcc to parse memset() */
void *malloc(unsigned long long);
void *memset(void *s, int c, size_t n);
void free(void*);
void abort(void);
#endif
enum __va_arg_type {
__va_gen_reg, __va_float_reg, __va_stack
};
//This should be in sync with the declaration on our include/stdarg.h
/* GCC compatible definition of va_list. */
typedef struct {
unsigned int gp_offset;
unsigned int fp_offset;
union {
unsigned int overflow_offset;
char *overflow_arg_area;
};
char *reg_save_area;
} __va_list_struct;
#undef __va_start
#undef __va_arg
#undef __va_copy
#undef __va_end
void __va_start(__va_list_struct *ap, void *fp)
{
memset(ap, 0, sizeof(__va_list_struct));
*ap = *(__va_list_struct *)((char *)fp - 16);
ap->overflow_arg_area = (char *)fp + ap->overflow_offset;
ap->reg_save_area = (char *)fp - 176 - 16;
}
void *__va_arg(__va_list_struct *ap,
enum __va_arg_type arg_type,
int size, int align)
{
size = (size + 7) & ~7;
align = (align + 7) & ~7;
switch (arg_type) {
case __va_gen_reg:
if (ap->gp_offset + size <= 48) {
ap->gp_offset += size;
return ap->reg_save_area + ap->gp_offset - size;
}
goto use_overflow_area;
case __va_float_reg:
if (ap->fp_offset < 128 + 48) {
ap->fp_offset += 16;
return ap->reg_save_area + ap->fp_offset - 16;
}
size = 8;
goto use_overflow_area;
case __va_stack:
use_overflow_area:
ap->overflow_arg_area += size;
ap->overflow_arg_area = (char*)((intptr_t)(ap->overflow_arg_area + align - 1) & -(intptr_t)align);
return ap->overflow_arg_area - size;
default:
#ifndef __TINYC__
fprintf(stderr, "unknown ABI type for __va_arg\n");
#endif
abort();
}
}
#endif /* __x86_64__ */
/* Flushing for tccrun */
#if defined(TCC_TARGET_X86_64) || defined(TCC_TARGET_I386)
void __clear_cache(void *beginning, void *end)
{
}
#elif defined(TCC_TARGET_ARM)
#define _GNU_SOURCE
#include <unistd.h>
#include <sys/syscall.h>
#include <stdio.h>
void __clear_cache(void *beginning, void *end)
{
/* __ARM_NR_cacheflush is kernel private and should not be used in user space.
* However, there is no ARM asm parser in tcc so we use it for now */
#if 1
syscall(__ARM_NR_cacheflush, beginning, end, 0);
#else
__asm__ ("push {r7}\n\t"
"mov r7, #0xf0002\n\t"
"mov r2, #0\n\t"
"swi 0\n\t"
"pop {r7}\n\t"
"ret");
#endif
}
#else
#warning __clear_cache not defined for this architecture, avoid using tcc -run
#endif

View File

@ -15,7 +15,7 @@ struct tm * localtime (const time_t * timer)
int bcd_year = (kos_date & 0xFF); int bcd_year = (kos_date & 0xFF);
buffertime.tm_mday = ((bcd_day & 0xF0)>>4)*10 + (bcd_day & 0x0F); buffertime.tm_mday = ((bcd_day & 0xF0)>>4)*10 + (bcd_day & 0x0F);
buffertime.tm_mon = ((bcd_mon & 0xF0)>>4)*10 + (bcd_mon & 0x0F) - 1; buffertime.tm_mon = ((bcd_mon & 0xF0)>>4)*10 + (bcd_mon & 0x0F) - 1;
buffertime.tm_year = ((bcd_year & 0xF0)>>4)*10 + (bcd_year & 0x0F) + 100; buffertime.tm_year = ((bcd_year & 0xF0)>>4)*10 + (bcd_year & 0x0F);
buffertime.tm_wday = buffertime.tm_yday = buffertime.tm_isdst = -1; /* temporary */ buffertime.tm_wday = buffertime.tm_yday = buffertime.tm_isdst = -1; /* temporary */

View File

@ -96,6 +96,11 @@ readdir
rewinddir rewinddir
seekdir seekdir
telldir telldir
getcwd
mkdir
rmdir
setcwd
getcwd
!____UNISTD____ !____UNISTD____
!____MATH____ !____MATH____
acosh acosh
@ -132,5 +137,24 @@ tolower
toupper toupper
!___CONIO___ !___CONIO___
con_set_title con_set_title
con_init
con_init_opt
con_write_asciiz
con_write_string
con_printf
con_exit
con_get_flags
con_set_flags
con_kbhit
con_getch
con_getch2
con_gets
con_gets2
con_get_font_height
con_get_cursor_height
con_set_cursor_height
con_cls
con_get_cursor_pos
con_set_cursor_pos
!___LIBC_VERSION___ !___LIBC_VERSION___
_libc_get_version _libc_get_version

View File

@ -0,0 +1,25 @@
#include <sys/ksys.h>
#include <sys/dir.h>
#include <stdlib.h>
char *getcwd(char *buf, unsigned size){
if(!buf){
if((buf = malloc(size))==NULL){
return NULL;
}
}
_ksys_getcwd(buf, size);
return(buf);
}
void setcwd(const char* cwd){
_ksys_setcwd((char*)cwd);
}
int rmdir(const char* dir){
return _ksys_file_delete(dir);
}
int mkdir(const char* dir){
return _ksys_mkdir(dir);
}