bcb4e51a409d94ae670de96afb8483a4f7855294Stephan Bosch/* Copyright (c) 2007-2018 Dovecot authors, see the included COPYING file */
f67e08c0dbd9c0441e818d07a0b40b897f907495Timo Sirainen/* @UNSAFE: whole file */
1d5e52e398381873081455ad99edec945038eec0Timo Sirainenstatic void init_badtab(struct str_find_context *ctx)
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (i = 0; i <= UCHAR_MAX; i++)
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (i = 0; i < len_1; i++)
1d5e52e398381873081455ad99edec945038eec0Timo Sirainenstatic void init_suffixes(struct str_find_context *ctx, unsigned int *suffixes)
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen int f = 0, g, i;
1384fac439fea3026b16a9d8d24954200e413bccTimo Sirainen for (i = (int)ctx->key_len - 2; i >= 0; i--) {
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen if (i > g && (int)suffixes[i + len_1 - f] < i - g)
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen while (g >= 0 && ctx->key[g] == ctx->key[g + len_1 - f])
1d5e52e398381873081455ad99edec945038eec0Timo Sirainenstatic void init_goodtab(struct str_find_context *ctx)
f67e08c0dbd9c0441e818d07a0b40b897f907495Timo Sirainen suffixes = t_buffer_get(sizeof(*suffixes) * ctx->key_len);
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen if (i < 0 || suffixes[i] == (unsigned int)i + 1) {
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (; j < len_1 - i; j++) {
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen ctx->goodtab[len_1 - suffixes[i]] = len_1 - i;
1d5e52e398381873081455ad99edec945038eec0Timo Sirainenstruct str_find_context *str_find_init(pool_t pool, const char *key)
e7d0bea63a08b08c47c4b5c187d2cb7127859657Timo Sirainen ctx = p_malloc(pool, MALLOC_ADD(sizeof(struct str_find_context),
e7d0bea63a08b08c47c4b5c187d2cb7127859657Timo Sirainen MALLOC_MULTIPLY(sizeof(ctx->goodtab[0]), key_len)));
f609bd50846f898583ef481d8aac927b10aa8395Timo Sirainen ctx->matches = p_new(pool, unsigned int, key_len);
1d5e52e398381873081455ad99edec945038eec0Timo Sirainenvoid str_find_deinit(struct str_find_context **_ctx)
1d5e52e398381873081455ad99edec945038eec0Timo Sirainenbool str_find_more(struct str_find_context *ctx,
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen unsigned int i, j, a, b;
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen /* we can fully determine this match now */
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (; a < key_len; a++) {
49a7e4dba84bbf35d82669d1ae79ad43949eed19Timo Sirainen ctx->match_end_pos = key_len - ctx->matches[i];
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (b = 0; b < size; b++) {
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen /* Boyer-Moore searching */
49a7e4dba84bbf35d82669d1ae79ad43949eed19Timo Sirainen if (i == 0) {
1384fac439fea3026b16a9d8d24954200e413bccTimo Sirainen bad_value = (int)(ctx->badtab[data[i + j]] + i + 1) -
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (; j < size; j++) {
1d5e52e398381873081455ad99edec945038eec0Timo Sirainen for (i = j; i < size; i++) {
49a7e4dba84bbf35d82669d1ae79ad43949eed19Timo Sirainensize_t str_find_get_match_end_pos(struct str_find_context *ctx)