corn/src/lib.c

318 lines
5.4 KiB
C
Raw Normal View History

#include "memory.h"
2024-01-27 07:14:19 +00:00
#include <lib.h>
2024-01-27 08:01:34 +00:00
#include <stddef.h>
int memcmp(const void *restrict vl, const void *restrict vr, unsigned long n) {
2024-01-31 18:11:47 +00:00
const unsigned char *l = vl, *r = vr;
for (; n && *l == *r; n--, l++, r++);
return n ? *l-*r : 0;
2024-01-27 08:01:34 +00:00
}
void *memcpy(void *restrict dest, const void *restrict src, unsigned long n) {
char *d = dest;
2024-01-31 18:11:47 +00:00
const char *s = src;
for (; n; n--) *d++ = *s++;
return dest;
2024-01-27 08:01:34 +00:00
}
volatile void *memcpyv(volatile void *dest, const volatile void *src, unsigned long n) {
volatile char *d = dest;
const volatile char *s = src;
for (; n; n--) *d++ = *s++;
return dest;
}
2024-01-27 08:01:34 +00:00
void *memmove(void *dest, const void *src, unsigned long n) {
2024-01-31 18:11:47 +00:00
char *d = dest;
const char *s = src;
2024-01-27 08:01:34 +00:00
2024-01-31 18:11:47 +00:00
if (d==s) return d;
2024-01-27 08:01:34 +00:00
2024-01-31 18:11:47 +00:00
if (d<s) {
for (; n; n--) *d++ = *s++;
} else {
while (n) n--, d[n] = s[n];
}
2024-01-27 08:01:34 +00:00
2024-01-31 18:11:47 +00:00
return dest;
2024-01-27 08:01:34 +00:00
}
void *memset(void *restrict dest, int c, unsigned long n) {
2024-01-31 18:11:47 +00:00
unsigned char *d = dest;
for (; n; n--) {
*d++ = c;
};
2024-01-31 18:11:47 +00:00
return dest;
2024-01-27 08:01:34 +00:00
}
volatile void *memsetv(volatile void *dest, int c, unsigned long n) {
volatile unsigned char *d = dest;
for (; n; n--) {
*d++ = c;
};
return dest;
}
2024-01-27 08:01:34 +00:00
int strncmp(const char *restrict lhs, const char *restrict rhs, unsigned long n) {
2024-01-27 07:14:19 +00:00
const unsigned char *l=(void *)lhs, *r=(void *)rhs;
if (!n--) return 0;
for (; *l && *r && n && *l == *r ; l++, r++, n--);
return *l - *r;
}
2024-01-27 08:38:27 +00:00
char *strcpy(char *restrict dest, const char *restrict src) {
2024-02-01 03:30:35 +00:00
char *d = dest;
for (; (*d = *src); d++, src++);
2024-01-27 08:38:27 +00:00
return dest;
}
char *strncpy(char *restrict dest, const char *restrict src, unsigned long n) {
2024-02-01 03:30:35 +00:00
char *d = dest;
for (; (*d = *src) && n; d++, src++, n--);
memset(d, 0, n);
2024-01-27 08:38:27 +00:00
return dest;
}
2024-01-30 02:10:29 +00:00
size_t strlen(const char *str) {
2024-01-31 18:11:47 +00:00
const char *p;
2024-02-01 03:30:35 +00:00
for (p = str; *p != 0; p++) {}
2024-01-31 18:11:47 +00:00
return p - str;
2024-01-30 02:10:29 +00:00
}
char *strcat(char *restrict dst, const char *restrict src) {
2024-01-31 18:11:47 +00:00
strcpy(dst + strlen(dst), src);
return dst;
2024-01-30 02:10:29 +00:00
}
2024-01-27 08:01:34 +00:00
int isspace(int c) {
2024-01-31 18:11:47 +00:00
switch (c) {
case ' ':
case '\t':
case '\v':
case '\f':
case '\r':
case '\n':
return 1;
default:
return 0;
}
2024-01-27 07:14:19 +00:00
}
2024-01-27 08:01:34 +00:00
int isdigit(int c) {
2024-01-31 18:11:47 +00:00
return c - '0' > -1 && c - '0' < 10;
2024-01-27 08:01:34 +00:00
}
#define ATOX(name, type) \
2024-02-01 03:30:35 +00:00
type name(const char *s) { \
for (; isspace(*s); s++); \
2024-01-31 18:11:47 +00:00
int neg = 0; \
switch (*s) { \
case '-': \
neg = 1; \
/* FALLTHRU */ \
case '+': \
s++; \
break; \
} \
type num = 0; \
for (; *s == '0'; s++); \
for (; isdigit(*s); s++) { \
num *= 10; \
num += *s - '0'; \
} \
return num * (neg ? -1 : 1); \
}
2024-01-27 08:01:34 +00:00
ATOX(atoi, int)
ATOX(atol, long int)
ATOX(atoll, long long int)
char itoc(int i) {
2024-02-01 03:30:35 +00:00
if (i < 10) {
2024-01-27 08:01:34 +00:00
return '0' + i;
} else {
return 'a' + (i - 10);
}
}
int ctoi(char c) {
2024-02-01 03:30:35 +00:00
if (c < 'A') {
2024-01-27 08:01:34 +00:00
return c - '0';
2024-02-01 03:30:35 +00:00
} else if (c < 'a') {
2024-01-27 08:01:34 +00:00
return c - 'A' + 10;
} else {
return c - 'a' + 10;
}
}
2024-02-01 20:53:11 +00:00
static char fs_endings[] = {'K', 'M', 'G', 'T', 'P'};
static size_t nth_pow(size_t i, size_t e) {
size_t a = i;
while(--e)
a *= i;
return a;
}
static char nth_digit(size_t bytes, size_t place) {
while (1) {
if (bytes < nth_pow(10, place))
break;
bytes /= 10;
}
return bytes %= 10;
}
char *btoa(const size_t bytes, char *buf) {
char *start = buf;
int idx = -1;
size_t b = bytes;
size_t s = b;
while (1) {
if (b < 1000)
break;
s = b;
b /= 1024;
idx++;
}
if (idx == -1) {
ultoa(bytes, buf, 10);
return start;
}
s = s * 1000 / 1024;
if (s < 1024) {
b = 1024;
idx--;
}
char fd = nth_digit(s, 1);
char sd = nth_digit(s, 2);
char td = nth_digit(s, 3);
*buf = fd + '0';
buf++;
if (b < 10) {
*buf = '.';
buf++;
}
*buf = sd + '0';
buf++;
if (b < 10)
goto end;
if (b > 99) {
*buf = td + '0';
buf++;
}
end:
*buf = fs_endings[idx];
buf++;
*buf = '\0';
return start;
}
2024-01-27 08:01:34 +00:00
#define UXTOA(type, name) \
2024-01-31 18:11:47 +00:00
char *name(unsigned type n, char *buffer, int radix) { \
if (n == 0) { \
buffer[0] = '0'; \
buffer[1] = '\0'; \
2024-02-01 21:53:07 +00:00
return buffer + 1; \
2024-01-31 18:11:47 +00:00
} \
char *start = buffer; \
for (; n; n /= radix) { \
*buffer++ = itoc(n % radix); \
} \
2024-02-01 03:30:35 +00:00
char *buf_end = buffer; \
2024-01-31 18:11:47 +00:00
*buffer-- = '\0'; \
2024-02-01 03:30:35 +00:00
while (buffer > start) { \
2024-01-31 18:11:47 +00:00
char tmp = *start; \
*start++ = *buffer; \
*buffer-- = tmp; \
} \
2024-02-01 03:30:35 +00:00
return buf_end; \
2024-01-31 18:11:47 +00:00
}
2024-01-27 08:01:34 +00:00
UXTOA(int, utoa)
UXTOA(long int, ultoa)
UXTOA(long long int, ulltoa)
2024-01-27 08:01:34 +00:00
#define XTOA(type, name) \
2024-02-01 03:30:35 +00:00
char *name(type n, char *buffer, int radix) { \
2024-01-31 18:11:47 +00:00
if (n == 0) { \
buffer[0] = '0'; \
buffer[1] = '\0'; \
2024-02-01 21:53:07 +00:00
return buffer + 1; \
2024-01-31 18:11:47 +00:00
} \
if (n < 0) { \
*buffer++ = '-'; \
n = -n; \
} \
char *start = buffer; \
for (; n; n /= radix) { \
*buffer++ = itoc(n % radix); \
} \
2024-02-01 03:30:35 +00:00
char *buf_end = buffer; \
2024-01-31 18:11:47 +00:00
*buffer-- = '\0'; \
2024-02-01 03:30:35 +00:00
while (buffer > start) { \
2024-01-31 18:11:47 +00:00
char tmp = *start; \
*start++ = *buffer; \
*buffer-- = tmp; \
} \
2024-02-01 03:30:35 +00:00
return buf_end; \
2024-01-31 18:11:47 +00:00
}
2024-01-27 08:01:34 +00:00
XTOA(int, itoa)
XTOA(long int, ltoa)
XTOA(long long int, lltoa)
2024-01-27 08:01:34 +00:00
#define STRTOX(name, type) \
2024-01-31 18:11:47 +00:00
type name(const char *s, char **endptr, int radix) { \
*endptr = NULL; \
2024-02-01 03:30:35 +00:00
for (; isspace(*s); s++); \
2024-01-31 18:11:47 +00:00
int neg = 0; \
switch (*s) { \
case '-': \
neg = 1; \
/* FALLTHRU */ \
case '+': \
s++; \
break; \
} \
if (!radix) { \
if (*s == '0') { \
s++; \
if (*s == 'x' || *s == 'X') { \
s++; \
radix = 16; \
} else { \
radix = 8; \
} \
} else { \
radix = 10; \
} \
} \
2024-02-01 03:30:35 +00:00
for (; *s == '0'; s++, *endptr = (void *) s); \
2024-01-31 18:11:47 +00:00
type num = 0; \
2024-02-01 03:30:35 +00:00
for (; isdigit(*s); s++, *endptr = (void *) s) { \
2024-01-31 18:11:47 +00:00
num *= radix; \
num += *s - '0'; \
} \
return num * (neg ? -1 : 1); \
}
2024-01-27 08:01:34 +00:00
STRTOX(strtoi, int)
STRTOX(strtol, long int)
STRTOX(strtoll, long long int)