summaryrefslogtreecommitdiff
path: root/app/bin/stringxtc.c
blob: e65a97dab96cf70da80cf792a0349d300e8a74fb (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
/** \file stringxtc.c
 *
 *  Copyright (C) 1991, 1992  Linus Torvalds
 */

/*
 * stupid library routines.
 */

#include <ctype.h>
#include <stddef.h>
#include <errno.h>
#include <string.h>
#include "include/stringxtc.h"

/**
 * strscpy - Copy a C-string into a sized buffer
 * @dest: Where to copy the string to
 * @src: Where to copy the string from
 * @count: Size of destination buffer
 *
 * Copy the string, or as much of it as fits, into the dest buffer.  The
 * behavior is undefined if the string buffers overlap.  The destination
 * buffer is always NUL terminated, unless it's zero-sized.
 *
 * Preferred to strlcpy() since the API doesn't require reading memory
 * from the src string beyond the specified "count" bytes, and since
 * the return value is easier to error-check than strlcpy()'s.
 * In addition, the implementation is robust to the string changing out
 * from underneath it, unlike the current strlcpy() implementation.
 *
 * Preferred to strncpy() since it always returns a valid string, and
 * doesn't unnecessarily force the tail of the destination buffer to be
 * zeroed.  If zeroing is desired please use strscpy_pad().
 *
 * Return: The number of characters copied (not including the trailing
 *         %NUL) or -E2BIG if the destination buffer wasn't big enough.
 */

size_t strscpy(char *dest, const char *src, size_t count)
{
	long res = 0;

	if (count == 0) {
		return -E2BIG;
	}

	while (count) {
		char c;

		c = src[res];
		dest[res] = c;
		if (!c) {
			return res;
		}
		res++;
		count--;
	}

	/* Hit buffer length without finding a NUL; force NUL-termination. */
	if (res) {
		dest[res - 1] = '\0';
	}

	return -E2BIG;
}

/* Safe version of strcat - will not overflow buffer
 * Return: The number of characters in buffer (not including the trailing
 *         % NUL) or -E2BIG if the destination buffer wasn't big enough.
 */
size_t
strscat(char* dest, const char* src, size_t count)
{
	long sptr = 0;
	long dptr = strlen(dest);
	count -= dptr;

	if (count <= 0) {
		return -E2BIG;
	}

	while (count) {
		char c;

		c = src[sptr];
		dest[dptr] = c;
		if (!c) {
			return dptr;
		}
		sptr++;
		dptr++;
		count--;
	}

	/* Hit buffer length without finding a NUL; force NUL-termination. */
	if (dptr) {
		dest[dptr - 1] = '\0';
	}

	return -E2BIG;
}

/**
 * Convert a string to lower case
 * Taken from https://stackoverflow.com/questions/23618316/undefined-reference-to-strlwr
 *
 * \param str IN string to convert
 * \return pointer to converted string
 */

char *
XtcStrlwr(char *str)
{
	unsigned char *p = (unsigned char *)str;

	while (*p) {
		*p = tolower((unsigned char)*p);
		p++;
	}

	return str;
}

/**
 * Compare two strings case insensitive
 * Taken from https://stackoverflow.com/questions/30733786/c99-remove-stricmp-and-strnicmp
 *
 * \param a, b IN strings to compare
  * \return
 */

int
XtcStricmp(const char *a, const char *b)
{
	int ca, cb;
	do {
		ca = (unsigned char) *a++;
		cb = (unsigned char) *b++;
		ca = tolower(toupper(ca));
		cb = tolower(toupper(cb));
	} while ((ca == cb) && (ca != '\0'));
	return ca - cb;
}