links/fn_impl.c

401 lines
7.4 KiB
C

#include "links.h"
#ifndef HAVE_SNPRINTF
#define B_SZ 65536
static char snprtintf_buffer[B_SZ];
int my_snprintf(char *str, int n, char *f, ...)
{
int i;
va_list l;
if (!n) return -1;
va_start(l, f);
#ifdef HAVE_VPRINTF
vsprintf(snprtintf_buffer, f, l);
#elif defined(HAVE_DOPRNT)
{
struct _iobuf strbuf;
strbuf._flag = _IOWRT+_IOSTRG;
strbuf._ptr = snprtintf_buffer;
strbuf._cnt = 32767;
_doprnt(f, l, &strbuf);
putc('\0', &strbuf);
}
#else
fatal_exit("No vsprintf!");
#endif
va_end(l);
i = strlen(snprtintf_buffer);
if (i >= B_SZ) {
fatal_exit("String size too large!");
}
if (i >= n) {
memcpy(str, snprtintf_buffer, n);
str[n - 1] = 0;
return -1;
}
strcpy(str, snprtintf_buffer);
return i;
}
#endif
#ifndef HAVE_RAISE
int raise(int s)
{
#ifdef HAVE_GETPID
pid_t p;
EINTRLOOP(p, getpid());
if (p == -1) return -1;
return kill(p, s);
#else
return 0;
#endif
};
#endif
#ifndef HAVE_GETTIMEOFDAY
int gettimeofday(struct timeval *tv, struct timezone *tz)
{
time_t t;
errno = 0;
EINTRLOOPX(t, time(NULL), (time_t)-1);
if (tv) tv->tv_sec = t, tv->tv_usec = 0;
if (tz) tz->tz_minuteswest = tz->tz_dsttime = 0;
return 0;
}
#endif
#ifndef HAVE_GETCWD
char *getcwd(char *buf, size_t size)
{
#ifndef MAXPATHLEN
#define MAXPATHLEN 1024
#endif
static char cwd[MAXPATHLEN];
if (!getwd(cwd))
return NULL;
if (strlen(cwd) >= size) {
errno = ERANGE;
return NULL;
}
strcpy(buf, cwd);
return 0;
}
#endif
#ifndef HAVE_TEMPNAM
char *tempnam(const char *dir, const char *pfx)
{
static int counter = 0;
unsigned char *d, *s, *a;
int l;
if (!(d = cast_uchar getenv("TMPDIR"))) {
if (dir) d = cast_uchar dir;
else if (!(d = cast_uchar getenv("TMP")) && !(d = cast_uchar getenv("TEMP"))) {
#ifdef P_tmpdir
d = cast_uchar(P_tmpdir);
#else
d = cast_uchar "/tmp";
#endif
}
}
l = 0;
s = init_str();
add_to_str(&s, &l, d);
if (s[0] && s[strlen(cast_const_char s) - 1] != '/') add_chr_to_str(&s, &l, '/');
add_to_str(&s, &l, cast_uchar pfx);
add_num_to_str(&s, &l, counter++);
a = cast_uchar strdup(cast_const_char s);
mem_free(s);
return cast_char a;
}
#endif
#ifndef HAVE_STRDUP
char *strdup(const char *s)
{
char *a = malloc(strlen(s) + 1);
if (!a) return NULL;
return strcpy(a, s);
}
#endif
#ifndef HAVE_STRTOL
long strtol(const char *nptr, char **endptr, int base)
{
unsigned long result;
char negative = 0;
if (*nptr == '-') {
negative = 1;
nptr++;
}
result = 0;
while (1) {
char c = *nptr;
char val;
unsigned long nr;
if (c >= '0' && c <= '9') val = c - '0';
else if (c >= 'A' && c <= 'Z') val = c - 'A' + 10;
else if (c >= 'a' && c <= 'z') val = c - 'a' + 10;
else break;
if (val >= base) break;
nr = result * base + val;
if ((long)nr < val || (nr - val) / base != result) break;
result = nr;
nptr++;
}
if (endptr) *endptr = (char *)nptr;
if (negative) return -result;
return result;
}
#endif
#ifndef HAVE_STRTOUL
unsigned long strtoul(const char *nptr, char **endptr, int base)
{
if (*nptr == '-') {
if (endptr) *endptr = nptr;
return 0;
}
return (unsigned long)strtol(nptr,endptr,base);
};
#endif
#ifndef HAVE_STRTOD
double strtod(const char *nptr, char **endptr)
{
double d = 0;
char dummy;
if (endptr) *endptr = (char *)nptr;
if (sscanf(nptr, "%lf%c", &d, &dummy) == 1) {
if (endptr) *endptr = strchr(nptr, 0);
}
return d;
}
#endif
#ifndef HAVE_STRLEN
size_t strlen(const char *s)
{
size_t len = 0;
while (s[len]) len++;
return len;
}
#endif
#ifndef HAVE_STRNLEN
size_t strnlen(const char *s, size_t max)
{
size_t len = 0;
while (len < max && s[len]) len++;
return len;
}
#endif
#ifndef HAVE_STRCPY
char *strcpy(char *dst, const char *src)
{
return memcpy(dst, src, strlen(src) + 1);
}
#endif
#ifndef HAVE_STRNCPY
char *strncpy(char *dst, const char *src, size_t len)
{
size_t sl = strlen(src);
if (sl >= len) {
memcpy(dst, src, len);
} else {
memcpy(dst, src, sl);
memset(dst + sl, 0, len - sl);
}
return dst;
}
#endif
#ifndef HAVE_STRCHR
char *strchr(const char *s, int c)
{
do {
if (*s == (char)c)
return (char *)s;
} while (*s++);
return NULL;
}
#endif
#ifndef HAVE_STRRCHR
char *strrchr(const char *s, int c)
{
char *ret = NULL;
do {
if (*s == (char)c)
ret = (char *)s;
} while (*s++);
return ret;
}
#endif
#ifndef HAVE_STRCMP
int strcmp(const char *s1, const char *s2)
{
while (1) {
unsigned char c1 = (unsigned char)*s1;
unsigned char c2 = (unsigned char)*s2;
if (c1 != c2) {
return (int)c1 - (int)c2;
}
if (!c1) break;
s1++, s2++;
}
return 0;
}
#endif
#ifndef HAVE_STRNCMP
int strncmp(const char *s1, const char *s2, size_t n)
{
while (n--) {
unsigned char c1 = (unsigned char)*s1;
unsigned char c2 = (unsigned char)*s2;
if (c1 != c2) {
return (int)c1 - (int)c2;
}
if (!c1) break;
s1++, s2++;
}
return 0;
}
#endif
#ifndef HAVE_STRCSPN
size_t strcspn(const char *s, const char *reject)
{
size_t r;
for (r = 0; *s; r++, s++) {
const char *rj;
for (rj = reject; *rj; rj++) if (*s == *rj) goto brk;
}
brk:
return r;
}
#endif
#ifndef HAVE_STRSPN
size_t strspn(const char *s, const char *accept)
{
size_t r;
for (r = 0; *s; r++, s++) {
const char *rj;
for (rj = accept; *rj; rj++) if (*s == *rj) goto ac;
break;
ac:;
}
return r;
}
#endif
#ifndef HAVE_STRSTR
char *strstr(const char *haystack, const char *needle)
{
size_t hs = strlen(haystack);
size_t ns = strlen(needle);
if (!ns) return (char *)haystack;
while (hs >= ns) {
if (*haystack == *needle && !memcmp(haystack, needle, ns)) return (char *)haystack;
haystack++, hs--;
}
return NULL;
}
#endif
#ifndef HAVE_MEMCHR
void *memchr(const void *s, int c, size_t length)
{
const char *sp = s;
while (length--) {
if (*sp == (char)c)
return (char *)s;
sp++;
}
return NULL;
}
#endif
#ifndef HAVE_MEMRCHR
void *memrchr(const void *s, int c, size_t length)
{
const char *sp = s;
char *ret = NULL;
while (length--) {
if (*sp == (char)c)
ret = (char *)s;
sp++;
}
return ret;
}
#endif
#ifndef HAVE_MEMCMP
int memcmp(const void *src0, const void *src1, size_t length)
{
const unsigned char *s0, *s1;
#ifdef HAVE_BCMP
if (!bcmp(src0, src1, length))
return 0;
#endif
s0 = src0;
s1 = src1;
while (length--) {
int c = *s0 - *s1;
if (c) return c;
s0++, s1++;
}
return 0;
}
#endif
#ifndef HAVE_MEMCPY
void *memcpy(void *dst0, const void *src0, size_t length)
{
return memmove(dst0, src0, length);
}
#endif
#ifndef HAVE_MEMMOVE
void *memmove(void *dst0, const void *src0, size_t length)
{
#ifdef HAVE_BCOPY
bcopy(src0, dst0, length);
return dst0;
#else
unsigned char *dst = dst0;
const unsigned char *src = src0;
if ((const unsigned char *)dst == src || !length)
return dst0;
if ((const unsigned char *)dst <= src) {
while (length--) *dst++ = *src++;
} else {
dst += length - 1;
src += length - 1;
while (length--) *dst-- = *src--;
}
return dst0;
#endif
}
#endif
#ifndef HAVE_MEMSET
void *memset(void *s, int c, size_t n)
{
char *sc = s;
#ifdef HAVE_BZERO
if (!c) bzero(s, n);
else
#endif
while (n--) *sc++ = c;
return s;
}
#endif
#ifndef HAVE_MEMMEM
void *memmem(const void *haystack, size_t hs, const void *needle, size_t ns)
{
if (!ns) return (void *)haystack;
while (hs >= ns) {
if (*(const char *)haystack == *(const char *)needle && !memcmp(haystack, needle, ns)) return (void *)haystack;
haystack = (const void *)((const char *)haystack + 1), hs--;
}
return NULL;
}
#endif
#ifndef HAVE_STRERROR
extern char *sys_errlist[];
extern int sys_nerr;
char *strerror(int errnum)
{
if (errnum < 0 || errnum >= sys_nerr) return "Unknown error";
return sys_errlist[errnum];
};
#endif