dovecot-2.2: fts: Change filter API to be able to return errors
dovecot at dovecot.org
dovecot at dovecot.org
Sat May 9 08:32:19 UTC 2015
details: http://hg.dovecot.org/dovecot-2.2/rev/95a827d97e5b
changeset: 18552:95a827d97e5b
user: Teemu Huovila <teemu.huovila at dovecot.fi>
date: Sat May 09 11:06:45 2015 +0300
description:
fts: Change filter API to be able to return errors
Modify fts_filter_filter() to return integer status codes. It returns
1 if a token was returned, 0 if it was filtered away and -1 on error.
diffstat:
src/lib-fts/fts-filter-normalizer-icu.c | 42 +++++++------
src/lib-fts/fts-filter-normalizer-simple.c | 15 ++-
src/lib-fts/fts-filter-private.h | 2 +-
src/lib-fts/fts-filter-stemmer-snowball.c | 16 ++--
src/lib-fts/fts-filter-stopwords.c | 14 ++-
src/lib-fts/fts-filter.c | 14 ++--
src/lib-fts/fts-filter.h | 9 +-
src/lib-fts/test-fts-filter.c | 95 +++++++++++++++++------------
src/plugins/fts/fts-build-mail.c | 6 +-
src/plugins/fts/fts-search-args.c | 8 +-
10 files changed, 126 insertions(+), 95 deletions(-)
diffs (truncated from 584 to 300 lines):
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter-normalizer-icu.c
--- a/src/lib-fts/fts-filter-normalizer-icu.c Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter-normalizer-icu.c Sat May 09 11:06:45 2015 +0300
@@ -98,8 +98,9 @@
return 0;
}
-static int make_utf8(const UChar *src, char **dst, const char **error_r)
+static int make_utf8(const UChar *src, const char **_dst, const char **error_r)
{
+ char *dst;
char *retp = NULL;
int32_t dsize = 0;
int32_t dsize_actual = 0;
@@ -120,9 +121,9 @@
i_assert(NULL == retp);
dsize++; /* room for '\0' byte */
- *dst = t_malloc(dsize);
+ dst = t_malloc(dsize);
err = U_ZERO_ERROR;
- retp = u_strToUTF8WithSub(*dst, dsize, &dsize_actual, src, usrc_len,
+ retp = u_strToUTF8WithSub(dst, dsize, &dsize_actual, src, usrc_len,
UNICODE_REPLACEMENT_CHAR, &sub_num, &err);
if (U_FAILURE(err))
i_panic("Lib ICU u_strToUTF8WithSub() failed: %s",
@@ -137,8 +138,9 @@
" Substitutions (%d) were made.", sub_num);
return -1;
}
- i_assert(retp == *dst);
+ i_assert(retp == dst);
+ *_dst = dst;
return 0;
}
@@ -212,27 +214,24 @@
return 0;
}
-/* Returns 0 on success and -1 on error. */
-/* TODO: delay errors until _deinit() and return some other values? */
-static const char *
-fts_filter_normalizer_icu_filter(struct fts_filter *filter, const char *token)
+static int
+fts_filter_normalizer_icu_filter(struct fts_filter *filter, const char **token)
{
UErrorCode err = U_ZERO_ERROR;
UChar *utext = NULL;
int32_t utext_cap = 0;
int32_t utext_len = -1;
int32_t utext_limit;
- char *normalized = NULL;
struct fts_filter_normalizer *np =
(struct fts_filter_normalizer *)filter;
/* TODO: fix error handling */
if (np->error != NULL)
- return NULL;
+ goto err_exit;
- if (make_uchar(token, &utext, &utext_cap) < 0) {
+ if (make_uchar(*token, &utext, &utext_cap) < 0) {
fts_filter_normalizer_icu_error(&np->error, "Conversion to UChar failed");
- return NULL;
+ goto err_exit;
}
/*
TODO: Some problems here. How much longer can the result
@@ -249,8 +248,9 @@
size utrans_transUChars indicated */
utext_len++; /* room for '\0' bytes(2) */
utext_cap = utext_len;
- if (make_uchar(token, &utext, &utext_cap) < 0)
- return NULL;
+ if (make_uchar(*token, &utext, &utext_cap) < 0) {
+ goto err_exit;
+ }
i_assert(utext_cap == utext_len);
utext_limit = u_strlen(utext);
utext_len = -1;
@@ -262,13 +262,17 @@
if (U_FAILURE(err)) {
icu_error(&np->error, err, "utrans_transUChars()");
- return NULL;
+ goto err_exit;
}
- if (make_utf8(utext, &normalized, &np->error) < 0)
- return NULL;
+ if (make_utf8(utext, token, &np->error) < 0) {
+ goto err_exit;
+ }
- return normalized;
+ return 1;
+ err_exit:
+ *token = NULL;
+ return -1;
}
#else
@@ -289,7 +293,7 @@
return -1;
}
-static const char *
+static int
fts_filter_normalizer_icu_filter(struct fts_filter *filter ATTR_UNUSED,
const char *token ATTR_UNUSED)
{
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter-normalizer-simple.c
--- a/src/lib-fts/fts-filter-normalizer-simple.c Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter-normalizer-simple.c Sat May 09 11:06:45 2015 +0300
@@ -48,18 +48,21 @@
return 0;
}
-static const char *
+static int
fts_filter_normalizer_simple_filter(struct fts_filter *_filter,
- const char *token)
+ const char **token)
{
struct fts_filter_normalizer_simple *filter =
(struct fts_filter_normalizer_simple *)_filter;
str_truncate(filter->str, 0);
- if (uni_utf8_to_decomposed_titlecase(token, strlen(token),
- filter->str) < 0)
- return NULL;
- return str_c(filter->str);
+ if (uni_utf8_to_decomposed_titlecase(*token, strlen(*token),
+ filter->str) < 0) {
+ *token = NULL;
+ return -1;
+ }
+ *token = str_c(filter->str);
+ return 1;
}
static const struct fts_filter_vfuncs normalizer_filter_vfuncs = {
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter-private.h
--- a/src/lib-fts/fts-filter-private.h Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter-private.h Sat May 09 11:06:45 2015 +0300
@@ -17,7 +17,7 @@
const char *const *settings,
struct fts_filter **filter_r,
const char **error_r);
- const char * (*filter)(struct fts_filter *filter, const char *token);
+ int (*filter)(struct fts_filter *filter, const char **token);
void (*destroy)(struct fts_filter *filter);
};
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter-stemmer-snowball.c
--- a/src/lib-fts/fts-filter-stemmer-snowball.c Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter-stemmer-snowball.c Sat May 09 11:06:45 2015 +0300
@@ -66,18 +66,20 @@
return 0;
}
-static const char *
+static int
fts_filter_stemmer_snowball_filter(struct fts_filter *filter,
- const char *token)
+ const char **token)
{
const sb_symbol *base;
int len;
struct fts_filter_stemmer_snowball *sp =
(struct fts_filter_stemmer_snowball *) filter;
- base = sb_stemmer_stem(sp->stemmer, (const unsigned char *)token, strlen(token));
+ base = sb_stemmer_stem(sp->stemmer, (const unsigned char *)*token, strlen(*token));
len = sb_stemmer_length(sp->stemmer);
- return t_strdup_until(base, base + len);
+ *token = t_strdup_until(base, base + len);
+
+ return *token != NULL? 1: -1;
}
#else
@@ -101,11 +103,11 @@
{
}
-static const char *
+static int
fts_filter_stemmer_snowball_filter(struct fts_filter *filter ATTR_UNUSED,
- const char *token ATTR_UNUSED)
+ const char **token ATTR_UNUSED)
{
- return NULL;
+ return -1;
}
#endif
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter-stopwords.c
--- a/src/lib-fts/fts-filter-stopwords.c Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter-stopwords.c Sat May 09 11:06:45 2015 +0300
@@ -125,18 +125,20 @@
return ret;
}
-static const char *
-fts_filter_stopwords_filter(struct fts_filter *filter, const char *token)
+static int
+fts_filter_stopwords_filter(struct fts_filter *filter, const char **token)
{
const char *stopword;
struct fts_filter_stopwords *sp =
(struct fts_filter_stopwords *) filter;
- stopword = hash_table_lookup(sp->stopwords, token);
- if (stopword != NULL)
- return NULL;
+ stopword = hash_table_lookup(sp->stopwords, *token);
+ if (stopword != NULL) {
+ *token = NULL;
+ return 0;
+ }
else
- return token;
+ return 1;
}
const struct fts_filter_vfuncs stopwords_filter_vfuncs = {
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter.c
--- a/src/lib-fts/fts-filter.c Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter.c Sat May 09 11:06:45 2015 +0300
@@ -92,19 +92,19 @@
/* TODO: Avoid multiple allocations by using a buffer in v->filter?
Do this non-recursively? */
-const char *
-fts_filter_filter(struct fts_filter *filter, const char *token)
+int
+fts_filter_filter(struct fts_filter *filter, const char **token)
{
- const char *filtered = NULL;
+ int ret;
if (filter->parent == NULL)
return filter->v->filter(filter, token);
- filtered = fts_filter_filter(filter->parent, token);
+ ret = fts_filter_filter(filter->parent, token);
- if(filtered != NULL)
- return filter->v->filter(filter, filtered);
+ if(ret > 0)
+ return filter->v->filter(filter, token);
- return NULL;
+ return ret;
}
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/fts-filter.h
--- a/src/lib-fts/fts-filter.h Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/fts-filter.h Sat May 09 11:06:45 2015 +0300
@@ -58,8 +58,11 @@
void fts_filter_ref(struct fts_filter *filter);
void fts_filter_unref(struct fts_filter **filter);
-/* Returns the filtered token or NULL, if it was completely removed */
-const char *
-fts_filter_filter(struct fts_filter *filter, const char *token);
+/* Returns 1 if token is returned in *token, 0 if token was filtered
+ out and -1 on error.
+ Input is also given via *token.
+*/
+int
+fts_filter_filter(struct fts_filter *filter, const char **token);
#endif
diff -r 7fe766887394 -r 95a827d97e5b src/lib-fts/test-fts-filter.c
--- a/src/lib-fts/test-fts-filter.c Sat May 09 11:05:04 2015 +0300
+++ b/src/lib-fts/test-fts-filter.c Sat May 09 11:06:45 2015 +0300
@@ -24,7 +24,7 @@
"drive", NULL, NULL, NULL, "reason",
NULL, NULL, NULL, "sing"};
const char **ip, **op;
- const char *filtered;
+ const char *token;
test_begin("fts filter stopwords, English");
filter_class = fts_filter_find(STOPWORDS_FILTER_NAME);
@@ -34,12 +34,14 @@
ip = input;
op = output;
while (*ip != NULL) {
- filtered = fts_filter_filter(filter, *ip);
- if (filtered == NULL)
+ token = *ip;
+ ret = fts_filter_filter(filter, &token);
+ test_assert(ret >= 0);
+ if (ret == 0)
test_assert(*op == NULL);
More information about the dovecot-cvs
mailing list