35#ifndef HAVE_STRCASECMP
37# define strcasecmp _stricmp
41#ifndef HAVE_STRNCASECMP
43# define strncasecmp _strnicmp
48#define STRINGP(s) ((s != NULL) && (*(s) != '\0'))
50static const char *srs_separators =
"=-+";
64#define X(e,s) if (code == e) return s;
96 return "Unknown SRS error.";
108 memset(srs, 0,
sizeof(
srs_t));
131 int newlen = (srs->
numsecrets + 1) *
sizeof(
char *);
139 if (idx < srs->numsecrets)
144#define SRS_PARAM_DEFINE(n, t) \
145 int srs_set_ ## n (srs_t *srs, t value) { \
147 return SRS_SUCCESS; \
149 t srs_get_ ## n (srs_t *srs) { \
155 if (strchr(srs_separators, value) == NULL)
178#define SRS_TIME_PRECISION (60 * 60 * 24)
179#define SRS_TIME_BASEBITS 5
183#define SRS_TIME_SIZE 2
184#define SRS_TIME_SLOTS (1<<(SRS_TIME_BASEBITS<<(SRS_TIME_SIZE-1)))
206 for (sp =
stamp; *sp; sp++) {
219 if (now <= then + srs->maxage)
225 "abcdefghijklmnopqrstuvwxyz"
228static void srs_hash_create_v(
srs_t *srs,
int idx,
char *
buf,
int nargs, va_list ap)
245 for (i = 0; i < nargs; i++) {
246 data = va_arg(ap,
char *);
248 lcdata = alloca(len + 1);
249 for (
j = 0;
j < len;
j++) {
250 if (isupper(
data[
j]))
251 lcdata[
j] = tolower(
data[
j]);
262 hp = (
unsigned char *)srshash;
264 for (i = 0; i < srs->
hashlen; i++) {
271 j = ((*hp & 0x03) << 4) |
272 ((*(hp + 1) & 0xF0) >> 4);
276 j = ((*hp & 0x0F) << 2) |
277 ((*(hp + 1) & 0xC0) >> 6);
303 srs_hash_create_v(srs, 0,
buf, nargs, ap);
318 if (len < srs->hashmin)
320 if (len < srs->hashlen) {
330 srshash = alloca(srs->
hashlen + 1);
331 srs_hash_create_v(srs, i, srshash, nargs, ap);
333 if (strncasecmp(
hash, srshash, len) == 0)
341 char *
buf,
int buflen,
342 char *sendhost,
char *senduser,
343 const char *aliashost) {
350 if ((strncasecmp(senduser,
SRS0TAG, 4) == 0) &&
351 (strchr(srs_separators, senduser[4]) != NULL)) {
352 sendhost = senduser + 5;
353 if (*sendhost ==
'\0')
355 senduser = strchr(sendhost,
SRSSEP);
356 if ((senduser == NULL) || (*senduser ==
'\0'))
363 strlen(sendhost) + 1 + strlen(senduser)
364 + 1 + strlen(aliashost);
371 srshash = alloca(srs->
hashlen + 1);
378 sendhost,
SRSSEP, senduser,
385 char *
buf,
int buflen,
386 char *sendhost,
char *senduser,
387 const char *aliashost) {
394 if ((strncasecmp(senduser,
SRS1TAG, 4) == 0) &&
395 (strchr(srs_separators, senduser[4]) != NULL)) {
397 srshash = senduser + 5;
398 if (*srshash ==
'\0')
409 srshash = alloca(srs->
hashlen + 1);
415 strlen(
srshost) + 1 + strlen(srsuser)
416 + 1 + strlen(aliashost);
425 else if ((strncasecmp(senduser,
SRS0TAG, 4) == 0) &&
426 (strchr(srs_separators, senduser[4]) != NULL)) {
427 srsuser = senduser + 4;
429 srshash = alloca(srs->
hashlen + 1);
435 strlen(
srshost) + 1 + strlen(srsuser)
436 + 1 + strlen(aliashost);
446 sendhost, senduser, aliashost);
460 if (strncasecmp(senduser,
SRS0TAG, 4) == 0) {
461 srshash = senduser + 5;
464 srsstamp = strchr(srshash,
SRSSEP);
497 if (strncasecmp(senduser,
SRS1TAG, 4) == 0) {
498 srshash = senduser + 5;
521 const char *
sender,
const char *alias)
532 while ((
tmp = strchr(alias,
'@')) != NULL)
543 if (strcasecmp(sendhost, alias) == 0) {
544 if (strlen(
sender) >= buflen)
552 senduser = alloca(len + 1);
559 sendhost, senduser, alias);
563 const char *
sender,
const char *alias)
575 alen = strlen(alias);
579 buf = (
char *)srs_f_malloc(len);
606 senduser = alloca(len + 1);
610 tmp = strchr(senduser,
'@');
631 buf = (
char *)srs_f_malloc(len);
void sha1_final(uint8_t hash[SHA1_DIGESTSIZE], sha1_ctx *context)
void sha1_init(sha1_ctx *context)
void sha1_update(sha1_ctx *context, const uint8_t *data, uint32_t len)
char stamp[FMT_ULONG+FMT_ULONG+3]
const char * srs_strerror(int code)
void srs_init(srs_t *srs)
int srs_set_separator(srs_t *srs, char value)
#define SRS_TIME_PRECISION
int srs_hash_create(srs_t *srs, char *buf, int nargs,...)
int srs_hash_check(srs_t *srs, char *hash, int nargs,...)
int srs_timestamp_check(srs_t *srs, const char *stamp)
int srs_reverse(srs_t *srs, char *buf, int buflen, const char *sender)
const char * srs_get_secret(srs_t *srs, int idx)
char srs_get_separator(srs_t *srs)
int srs_parse_guarded(srs_t *srs, char *buf, int buflen, char *senduser)
const char * SRS_TIME_BASECHARS
void srs_free(srs_t *srs)
int srs_reverse_alloc(srs_t *srs, char **sptr, const char *sender)
int srs_forward_alloc(srs_t *srs, char **sptr, const char *sender, const char *alias)
int srs_add_secret(srs_t *srs, const char *secret)
int srs_compile_guarded(srs_t *srs, char *buf, int buflen, char *sendhost, char *senduser, const char *aliashost)
int srs_set_malloc(srs_malloc_t m, srs_realloc_t r, srs_free_t f)
int srs_forward(srs_t *srs, char *buf, int buflen, const char *sender, const char *alias)
#define SRS_PARAM_DEFINE(n, t)
int srs_parse_shortcut(srs_t *srs, char *buf, int buflen, char *senduser)
int srs_timestamp_create(srs_t *srs, char *buf, time_t now)
int srs_compile_shortcut(srs_t *srs, char *buf, int buflen, char *sendhost, char *senduser, const char *aliashost)
#define SRS_TIME_BASEBITS
const char * SRS_HASH_BASECHARS
#define SRS_ETIMESTAMPOUTOFDATE
void *(* srs_malloc_t)(size_t)
#define SRS_ENOSENDERATSIGN
void(* srs_free_t)(void *)
void *(* srs_realloc_t)(void *, size_t)
#define SRS_EHASHTOOSHORT
#define SRS_ESEPARATORINVALID
#define SRS_ENOTREWRITTEN
#define SRS_IS_SRS_ADDRESS(x)
#define SRS_EBADTIMESTAMPCHAR
#define SRS_ENOTSRSADDRESS