Browse Source

More libc

K. Lange 4 years ago
parent
commit
22a3321c25

+ 1 - 0
.gitignore

@@ -13,3 +13,4 @@ util/build
 util/local
 .gdb_history
 kernel/symbols.S
+base/usr/python

+ 2 - 0
base/usr/include/math.h

@@ -27,3 +27,5 @@ extern double log2(double x);
 extern double sinh(double x);
 extern double tan(double x);
 extern double tanh(double x);
+
+extern double modf(double x, double *iptr);

+ 2 - 0
base/usr/include/string.h

@@ -24,6 +24,8 @@ extern char * strrchr(const char * s, int c);
 extern char * strpbrk(const char * s, const char * b);
 extern char * strstr(const char * h, const char * n);
 
+extern char * strncpy(char * dest, const char * src, size_t n);
+
 extern int strcmp(const char * l, const char * r);
 extern int strncmp(const char *s1, const char *s2, size_t n);
 extern int strcoll(const char * s1, const char * s2);

+ 4 - 0
base/usr/include/time.h

@@ -17,6 +17,10 @@ struct tm {
 
 extern struct tm *localtime(const time_t *timep);
 extern struct tm *gmtime(const time_t *timep);
+
+extern struct tm *localtime_r(const time_t *timep, struct tm * buf);
+extern struct tm *gmtime_r(const time_t *timep, struct tm * buf);
+
 extern size_t strftime(char *s, size_t max, const char *format, const struct tm *tm);
 extern time_t time(time_t * out);
 extern double difftime(time_t a, time_t b);

+ 11 - 1
base/usr/include/unistd.h

@@ -6,6 +6,7 @@
 extern char **environ;
 
 extern pid_t getpid(void);
+extern pid_t getppid(void);
 
 extern int close(int fd);
 
@@ -40,7 +41,7 @@ extern int symlink(const char *target, const char *linkpath);
 extern ssize_t readlink(const char *pathname, char *buf, size_t bufsiz);
 
 extern int chdir(const char *path);
-extern int fchdir(int fd);
+//extern int fchdir(int fd);
 extern int isatty(int fd);
 
 extern unsigned int sleep(unsigned int seconds);
@@ -56,6 +57,15 @@ extern int optind, opterr, optopt;
 
 extern int unlink(const char * pathname);
 
+/* Unimplemented stubs */
+struct utimbuf {
+    time_t actime;
+    time_t modtime;
+};
+extern char * ttyname(int fd);
+extern int utime(const char *filename, const struct utimbuf *times);
+extern int rmdir(const char *pathname); /* TODO  rm probably just works */
+
 #define STDIN_FILENO 0
 #define STDOUT_FILENO 1
 #define STDERR_FILENO 2

+ 9 - 0
base/usr/include/wchar.h

@@ -7,5 +7,14 @@ extern wchar_t * wcsncpy(wchar_t * dest, const wchar_t * src, size_t n);
 extern size_t wcslen(const wchar_t * s);
 extern int wcscmp(const wchar_t *s1, const wchar_t *s2);
 extern wchar_t * wcscat(wchar_t *dest, const wchar_t *src);
+extern wchar_t * wcstok(wchar_t * str, const wchar_t * delim, wchar_t ** saveptr);
+extern size_t wcsspn(const wchar_t * wcs, const wchar_t * accept);
+extern wchar_t *wcspbrk(const wchar_t *wcs, const wchar_t *accept);
+extern wchar_t * wcschr(const wchar_t *wcs, wchar_t wc);
+extern wchar_t * wcsrchr(const wchar_t *wcs, wchar_t wc);
+extern wchar_t * wcsncat(wchar_t *dest, const wchar_t * src, size_t n);
+
+/* TODO */
+extern size_t wcstombs(char * dest, const wchar_t *src, size_t n);
 
 typedef unsigned int wint_t;

+ 0 - 1
libc/main.c

@@ -37,7 +37,6 @@ DEFN_SYSCALL2(sleepabs,  45, unsigned long, unsigned long);
 DEFN_SYSCALL3(ioctl, 47, int, int, void *);
 DEFN_SYSCALL2(access, 48, char *, int);
 DEFN_SYSCALL2(stat, 49, char *, void *);
-DEFN_SYSCALL1(umask, 51, int);
 DEFN_SYSCALL3(waitpid, 53, int, int *, int);
 DEFN_SYSCALL5(mount, SYS_MOUNT, char *, char *, char *, unsigned long, void *);
 DEFN_SYSCALL2(lstat, SYS_LSTAT, char *, void *);

+ 7 - 0
libc/math/modf.c

@@ -0,0 +1,7 @@
+#include <math.h>
+
+double modf(double x, double *iptr) {
+	int i = (int)x;
+	*iptr = (double)i;
+	return x - i;
+}

+ 13 - 0
libc/string/strncpy.c

@@ -0,0 +1,13 @@
+#include <string.h>
+
+char * strncpy(char * dest, const char * src, size_t n) {
+	char * out = dest;
+	while (n > 0) {
+		if (!*src) break;
+		*out = *src;
+		++out;
+		++src;
+		--n;
+	}
+	return out;
+}

+ 20 - 11
libc/time/localtime.c

@@ -56,7 +56,7 @@ static long secs_of_month(int months, int year) {
 	return days * SEC_DAY;
 }
 
-struct tm *localtime(const time_t *timep) {
+struct tm *localtime_r(const time_t *timep, struct tm * _timevalue) {
 
 	fprintf(stderr, "Hello world?\n");
 
@@ -71,7 +71,7 @@ struct tm *localtime(const time_t *timep) {
 		long secs = added * 86400;
 
 		if (seconds + secs >= *timep) {
-			_timevalue.tm_year = year - 1900;
+			_timevalue->tm_year = year - 1900;
 			year_sec = seconds;
 			fprintf(stderr, "The year is %d, year_sec=%d\n", year, year_sec);
 			for (int month = 1; month <= 12; ++month) {
@@ -80,24 +80,24 @@ struct tm *localtime(const time_t *timep) {
 				fprintf(stderr, "%d vs %d\n", seconds + secs, *timep);
 				if (seconds + secs >= *timep) {
 					fprintf(stderr, "The month is %d.\n", month);
-					_timevalue.tm_mon = month - 1;
+					_timevalue->tm_mon = month - 1;
 					for (int day = 1; day <= days_in_month(month, year); ++day) {
 						secs = 60 * 60 * 24;
 						fprintf(stderr, "Checking day %d, %d vs . %d\n", day, seconds + secs, *timep);
 						if (seconds + secs >= *timep) {
 							fprintf(stderr, "The day is %d.\n", day);
-							_timevalue.tm_mday = day;
+							_timevalue->tm_mday = day;
 							for (int hour = 1; hour <= 24; ++hour) {
 								secs = 60 * 60;
 								if (seconds + secs >= *timep) {
 									long remaining = *timep - seconds;
-									_timevalue.tm_hour = hour-1;
-									_timevalue.tm_min = remaining / 60;
-									_timevalue.tm_sec = remaining % 60; // can be 60 on a leap second, ignore that
-									_timevalue.tm_wday = day_of_week(*timep); // oh shit
-									_timevalue.tm_yday = (*timep - year_sec) / SEC_DAY;
-									_timevalue.tm_isdst = 0; // never because UTC
-									return &_timevalue;
+									_timevalue->tm_hour = hour-1;
+									_timevalue->tm_min = remaining / 60;
+									_timevalue->tm_sec = remaining % 60; // can be 60 on a leap second, ignore that
+									_timevalue->tm_wday = day_of_week(*timep); // oh shit
+									_timevalue->tm_yday = (*timep - year_sec) / SEC_DAY;
+									_timevalue->tm_isdst = 0; // never because UTC
+									return _timevalue;
 								} else {
 									seconds += secs;
 								}
@@ -150,6 +150,15 @@ time_t mktime(struct tm *tm) {
 
 }
 
+struct tm * gmtime_r(const time_t * timep, struct tm * tm) {
+	return localtime_r(timep, tm);
+}
+
+struct tm * localtime(const time_t *timep) {
+	return localtime_r(timep, &_timevalue);
+}
+
 struct tm *gmtime(const time_t *timep) {
 	return localtime(timep);
 }
+

+ 4 - 0
libc/unistd/dup2.c

@@ -6,3 +6,7 @@ DEFN_SYSCALL2(dup2, 22, int, int);
 int dup2(int oldfd, int newfd) {
 	return syscall_dup2(oldfd, newfd);
 }
+
+int dup(int oldfd) {
+	return dup2(oldfd, -1);
+}

+ 4 - 0
libc/unistd/execvp.c

@@ -47,3 +47,7 @@ int execvp(const char *file, char *const argv[]) {
 	errno = ENOENT;
 	return -1;
 }
+
+int execv(const char * file, char * const argv[]) {
+	return execve(file, argv, environ);
+}

+ 8 - 1
libc/unistd/getpid.c

@@ -1,8 +1,15 @@
 #include <unistd.h>
+#include <errno.h>
 #include <syscall.h>
+#include <syscall_nums.h>
 
-DEFN_SYSCALL0(getpid, 9);
+DEFN_SYSCALL0(getpid, SYS_GETPID);
 
 pid_t getpid(void) {
 	return syscall_getpid();
 }
+
+pid_t getppid(void) {
+	errno = ENOTSUP;
+	return -1;
+}

+ 7 - 0
libc/unistd/rmdir.c

@@ -0,0 +1,7 @@
+#include <unistd.h>
+#include <errno.h>
+
+int rmdir(const char *pathname) {
+	errno = ENOTSUP;
+	return -1;
+}

+ 7 - 0
libc/unistd/ttyname.c

@@ -0,0 +1,7 @@
+#include <unistd.h>
+#include <errno.h>
+
+char * ttyname(int fd) {
+	errno = ENOTSUP;
+	return NULL;
+}

+ 9 - 0
libc/unistd/umask.c

@@ -0,0 +1,9 @@
+#include <unistd.h>
+#include <syscall.h>
+#include <syscall_nums.h>
+
+DEFN_SYSCALL1(umask, SYS_UMASK, int);
+
+mode_t umask(mode_t mask) {
+	return syscall_umask(mask);
+}

+ 8 - 0
libc/unistd/utime.c

@@ -0,0 +1,8 @@
+#include <unistd.h>
+#include <errno.h>
+
+int utime(const char *filename, const struct utimbuf *times) {
+	/* Unimplemented */
+	errno = ENOTSUP;
+	return -1;
+}

+ 21 - 0
libc/wchar/wcs.c

@@ -0,0 +1,21 @@
+#include <wchar.h>
+
+size_t wcstombs(char * dest, const wchar_t *src, size_t n) {
+	/* TODO */
+	size_t c = 0;
+	while (c < n && *src) {
+		*dest = *src;
+		c++;
+	}
+	return c;
+}
+
+size_t mbstowcs(wchar_t * dest, const char *src, size_t n) {
+	/* TODO */
+	size_t c = 0;
+	while (c < n && *src) {
+		*dest = *src;
+		c++;
+	}
+	return c;
+}

+ 20 - 0
libc/wchar/wcscat.c

@@ -13,3 +13,23 @@ wchar_t * wcscat(wchar_t *dest, const wchar_t *src) {
 	*end = 0;
 	return dest;
 }
+
+wchar_t * wcsncat(wchar_t *dest, const wchar_t * src, size_t n) {
+	wchar_t * end = dest;
+	size_t c = 0;
+	while (*end != 0) {
+		++end;
+		c++;
+	}
+	if (c >= n) return dest;
+
+	while (*src && c < n) {
+		*end = *src;
+		end++;
+		src++;
+		c++;
+	}
+	*end = 0;
+	return dest;
+
+}

+ 74 - 0
libc/wchar/wcstok.c

@@ -0,0 +1,74 @@
+#include <wchar.h>
+
+size_t wcsspn(const wchar_t * wcs, const wchar_t * accept) {
+	size_t out = 0;
+
+	while (*wcs) {
+		int good = 0;
+		for (const wchar_t * a = accept; *a; ++a) {
+			if (*wcs == *a) {
+				good = 1;
+				break;
+			}
+		}
+		if (!good) break;
+		out++;
+		wcs++;
+	}
+
+	return out;
+}
+
+wchar_t *wcspbrk(const wchar_t *wcs, const wchar_t *accept) {
+	while (*wcs) {
+		for (const wchar_t * a = accept; *a; ++a) {
+			if (*wcs == *a) {
+				return (wchar_t *)wcs;
+			}
+		}
+		wcs++;
+	}
+	return NULL;
+}
+
+wchar_t * wcschr(const wchar_t *wcs, wchar_t wc) {
+	while (*wcs != wc && *wcs != L'0') {
+		wcs++;
+	}
+	if (!*wcs) return NULL;
+	return (wchar_t *)wcs;
+}
+
+wchar_t * wcsrchr(const wchar_t *wcs, wchar_t wc) {
+	wchar_t * last = NULL;
+	while (*wcs != L'0') {
+		if (*wcs == wc) {
+			last = (wchar_t *)wcs;
+		}
+		wcs++;
+	}
+	return last;
+}
+
+wchar_t * wcstok(wchar_t * str, const wchar_t * delim, wchar_t ** saveptr) {
+	wchar_t * token;
+	if (str == NULL) {
+		str = *saveptr;
+	}
+	str += wcsspn(str, delim);
+	if (*str == '\0') {
+		*saveptr = str;
+		return NULL;
+	}
+	token = str;
+	str = wcspbrk(token, delim);
+	if (str == NULL) {
+		*saveptr = (wchar_t *)wcschr(token, '\0');
+	} else {
+		*str = '\0';
+		*saveptr = str + 1;
+	}
+	return token;
+}
+
+