From 78b138b80fadc817d621f0a692fca857ee31399b Mon Sep 17 00:00:00 2001 From: Adam Dickmeiss Date: Mon, 30 Apr 2007 11:33:49 +0000 Subject: [PATCH] Restructure qualifier handling so we can have more rules per-field - such as stop word handling. --- include/yaz/ccl.h | 7 +- src/cclfind.c | 251 +++++++++++++++++++++++++++-------------------------- src/cclp.h | 12 ++- src/cclqual.c | 46 +++++----- 4 files changed, 164 insertions(+), 152 deletions(-) diff --git a/include/yaz/ccl.h b/include/yaz/ccl.h index 7772cff..65d2ffd 100644 --- a/include/yaz/ccl.h +++ b/include/yaz/ccl.h @@ -49,7 +49,7 @@ /* * CCL - header file * - * $Id: ccl.h,v 1.26 2007-04-26 21:45:16 adam Exp $ + * $Id: ccl.h,v 1.27 2007-04-30 11:33:49 adam Exp $ * * Old Europagate Log: * @@ -274,11 +274,6 @@ int ccl_stricmp(const char *s1, const char *s2); YAZ_EXPORT int ccl_memicmp(const char *s1, const char *s2, size_t n); -/** Search for qualifier 'name' in set 'b'. */ -YAZ_EXPORT -struct ccl_rpn_attr *ccl_qual_search(CCL_parser cclp, const char *name, - size_t len, int seq); - /** Create CCL parser */ YAZ_EXPORT CCL_parser ccl_parser_create(CCL_bibset bibset); diff --git a/src/cclfind.c b/src/cclfind.c index fc67b80..2ebd11f 100644 --- a/src/cclfind.c +++ b/src/cclfind.c @@ -56,7 +56,7 @@ /* CCL find (to rpn conversion) * Europagate, 1995 * - * $Id: cclfind.c,v 1.11 2007-04-26 21:45:17 adam Exp $ + * $Id: cclfind.c,v 1.12 2007-04-30 11:33:49 adam Exp $ * * Old Europagate log: * @@ -128,15 +128,16 @@ * value: Value of attribute to seach for * return: 1 if found; 0 otherwise. */ -static int qual_val_type (struct ccl_rpn_attr **qa, int type, int value, - char **attset) +static int qual_val_type(ccl_qualifier_t *qa, int type, int value, + char **attset) { int i; - struct ccl_rpn_attr *q; if (!qa) return 0; - for (i = 0; (q=qa[i]); i++) + for (i = 0; qa[i]; i++) + { + struct ccl_rpn_attr *q = ccl_qual_get_attr(qa[i]); while (q) { if (q->type == type && q->kind == CCL_RPN_ATTR_NUMERIC && @@ -148,6 +149,7 @@ static int qual_val_type (struct ccl_rpn_attr **qa, int type, int value, } q = q->next; } + } return 0; } @@ -157,7 +159,7 @@ static int qual_val_type (struct ccl_rpn_attr **qa, int type, int value, * src: Source string to be appended (not null-terminated) * len: Length of source string. */ -static void strxcat (char *n, const char *src, int len) +static void strxcat(char *n, const char *src, int len) { while (*n) n++; @@ -171,11 +173,11 @@ static void strxcat (char *n, const char *src, int len) * tp: Pointer to token info. * return: malloc(3) allocated copy of token name. */ -static char *copy_token_name (struct ccl_token *tp) +static char *copy_token_name(struct ccl_token *tp) { - char *str = (char *)xmalloc (tp->len + 1); - ccl_assert (str); - memcpy (str, tp->name, tp->len); + char *str = (char *)xmalloc(tp->len + 1); + ccl_assert(str); + memcpy(str, tp->name, tp->len); str[tp->len] = '\0'; return str; } @@ -188,8 +190,8 @@ static char *copy_token_name (struct ccl_token *tp) struct ccl_rpn_node *ccl_rpn_node_create(enum ccl_rpn_kind kind) { struct ccl_rpn_node *p; - p = (struct ccl_rpn_node *)xmalloc (sizeof(*p)); - ccl_assert (p); + p = (struct ccl_rpn_node *)xmalloc(sizeof(*p)); + ccl_assert(p); p->kind = kind; switch(kind) @@ -208,7 +210,7 @@ struct ccl_rpn_node *ccl_rpn_node_create(enum ccl_rpn_kind kind) * ccl_rpn_delete: Delete RPN tree. * rpn: Pointer to tree. */ -void ccl_rpn_delete (struct ccl_rpn_node *rpn) +void ccl_rpn_delete(struct ccl_rpn_node *rpn) { struct ccl_rpn_attr *attr, *attr1; if (!rpn) @@ -218,37 +220,36 @@ void ccl_rpn_delete (struct ccl_rpn_node *rpn) case CCL_RPN_AND: case CCL_RPN_OR: case CCL_RPN_NOT: - ccl_rpn_delete (rpn->u.p[0]); - ccl_rpn_delete (rpn->u.p[1]); + ccl_rpn_delete(rpn->u.p[0]); + ccl_rpn_delete(rpn->u.p[1]); break; case CCL_RPN_TERM: - xfree (rpn->u.t.term); + xfree(rpn->u.t.term); for (attr = rpn->u.t.attr_list; attr; attr = attr1) { attr1 = attr->next; if (attr->kind == CCL_RPN_ATTR_STRING) xfree(attr->value.str); if (attr->set) - xfree (attr->set); - xfree (attr); + xfree(attr->set); + xfree(attr); } break; case CCL_RPN_SET: - xfree (rpn->u.setname); + xfree(rpn->u.setname); break; case CCL_RPN_PROX: - ccl_rpn_delete (rpn->u.p[0]); - ccl_rpn_delete (rpn->u.p[1]); - ccl_rpn_delete (rpn->u.p[2]); + ccl_rpn_delete(rpn->u.p[0]); + ccl_rpn_delete(rpn->u.p[1]); + ccl_rpn_delete(rpn->u.p[2]); break; } - xfree (rpn); + xfree(rpn); } -static struct ccl_rpn_node *find_spec (CCL_parser cclp, - struct ccl_rpn_attr **qa); +static struct ccl_rpn_node *find_spec(CCL_parser cclp, ccl_qualifier_t *qa); -static int is_term_ok (int look, int *list) +static int is_term_ok(int look, int *list) { for (;*list >= 0; list++) if (look == *list) @@ -256,16 +257,15 @@ static int is_term_ok (int look, int *list) return 0; } -static struct ccl_rpn_node *search_terms (CCL_parser cclp, - struct ccl_rpn_attr **qa); +static struct ccl_rpn_node *search_terms(CCL_parser cclp, ccl_qualifier_t *qa); -static struct ccl_rpn_attr *add_attr_node (struct ccl_rpn_node *p, +static struct ccl_rpn_attr *add_attr_node(struct ccl_rpn_node *p, const char *set, int type) { struct ccl_rpn_attr *n; - n = (struct ccl_rpn_attr *)xmalloc (sizeof(*n)); - ccl_assert (n); + n = (struct ccl_rpn_attr *)xmalloc(sizeof(*n)); + ccl_assert(n); if (set) n->set = xstrdup(set); else @@ -313,9 +313,9 @@ void ccl_add_attr_string(struct ccl_rpn_node *p, const char *set, * multi: whether we accept "multiple" tokens * return: pointer to node(s); NULL on error. */ -static struct ccl_rpn_node *search_term_x (CCL_parser cclp, - struct ccl_rpn_attr **qa, - int *term_list, int multi) +static struct ccl_rpn_node *search_term_x(CCL_parser cclp, + ccl_qualifier_t *qa, + int *term_list, int multi) { struct ccl_rpn_node *p_top = 0; struct ccl_token *lookahead = cclp->look_token; @@ -329,9 +329,9 @@ static struct ccl_rpn_node *search_term_x (CCL_parser cclp, if (!truncation_aliases) truncation_aliases = "?"; - if (qual_val_type (qa, CCL_BIB1_STR, CCL_BIB1_STR_AND_LIST, 0)) + if (qual_val_type(qa, CCL_BIB1_STR, CCL_BIB1_STR_AND_LIST, 0)) and_list = 1; - if (qual_val_type (qa, CCL_BIB1_STR, CCL_BIB1_STR_OR_LIST, 0)) + if (qual_val_type(qa, CCL_BIB1_STR, CCL_BIB1_STR_OR_LIST, 0)) or_list = 1; while (1) { @@ -413,7 +413,7 @@ static struct ccl_rpn_node *search_term_x (CCL_parser cclp, { struct ccl_rpn_attr *attr; - for (attr = qa[i]; attr; attr = attr->next) + for (attr = ccl_qual_get_attr(qa[i]); attr; attr = attr->next) switch(attr->kind) { case CCL_RPN_ATTR_STRING: @@ -461,7 +461,7 @@ static struct ccl_rpn_node *search_term_x (CCL_parser cclp, /* no holds the number of CCL tokens (1 or more) */ if (structure_value == -1 && - qual_val_type (qa, CCL_BIB1_STR, CCL_BIB1_STR_WP, &attset)) + qual_val_type(qa, CCL_BIB1_STR, CCL_BIB1_STR_WP, &attset)) { /* no structure attribute met. Apply either structure attribute WORD or PHRASE depending on number of CCL tokens */ if (no == 1 && no_spaces == 0) @@ -471,8 +471,8 @@ static struct ccl_rpn_node *search_term_x (CCL_parser cclp, } /* make the RPN token */ - p->u.t.term = (char *)xmalloc (len); - ccl_assert (p->u.t.term); + p->u.t.term = (char *)xmalloc(len); + ccl_assert(p->u.t.term); p->u.t.term[0] = '\0'; for (i = 0; ilook_token->ws_prefix_len) { size_t len = strlen(p->u.t.term); @@ -493,45 +497,45 @@ static struct ccl_rpn_node *search_term_x (CCL_parser cclp, cclp->look_token->ws_prefix_len); p->u.t.term[len + cclp->look_token->ws_prefix_len] = '\0'; } - strxcat (p->u.t.term, src_str, src_len); + strxcat(p->u.t.term, src_str, src_len); ADVANCE; } if (left_trunc && right_trunc) { - if (!qual_val_type (qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_BOTH, + if (!qual_val_type(qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_BOTH, &attset)) { cclp->error_code = CCL_ERR_TRUNC_NOT_BOTH; - ccl_rpn_delete (p); + ccl_rpn_delete(p); return NULL; } ccl_add_attr_numeric(p, attset, CCL_BIB1_TRU, 3); } else if (right_trunc) { - if (!qual_val_type (qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_RIGHT, + if (!qual_val_type(qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_RIGHT, &attset)) { cclp->error_code = CCL_ERR_TRUNC_NOT_RIGHT; - ccl_rpn_delete (p); + ccl_rpn_delete(p); return NULL; } ccl_add_attr_numeric(p, attset, CCL_BIB1_TRU, 1); } else if (left_trunc) { - if (!qual_val_type (qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_LEFT, + if (!qual_val_type(qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_LEFT, &attset)) { cclp->error_code = CCL_ERR_TRUNC_NOT_LEFT; - ccl_rpn_delete (p); + ccl_rpn_delete(p); return NULL; } ccl_add_attr_numeric(p, attset, CCL_BIB1_TRU, 2); } else { - if (qual_val_type (qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_NONE, + if (qual_val_type(qa, CCL_BIB1_TRU, CCL_BIB1_TRU_CAN_NONE, &attset)) ccl_add_attr_numeric(p, attset, CCL_BIB1_TRU, 100); } @@ -543,16 +547,15 @@ static struct ccl_rpn_node *search_term_x (CCL_parser cclp, return p_top; } -static struct ccl_rpn_node *search_term (CCL_parser cclp, - struct ccl_rpn_attr **qa) +static struct ccl_rpn_node *search_term(CCL_parser cclp, ccl_qualifier_t *qa) { static int list[] = {CCL_TOK_TERM, CCL_TOK_COMMA, -1}; return search_term_x(cclp, qa, list, 0); } static -struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, - struct ccl_rpn_attr **ap, char *attset) +struct ccl_rpn_node *qualifiers_order(CCL_parser cclp, + ccl_qualifier_t *ap, char *attset) { int rel = 0; struct ccl_rpn_node *p; @@ -568,11 +571,11 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, } else if (cclp->look_token->len == 2) { - if (!memcmp (cclp->look_token->name, "<=", 2)) + if (!memcmp(cclp->look_token->name, "<=", 2)) rel = 2; - else if (!memcmp (cclp->look_token->name, ">=", 2)) + else if (!memcmp(cclp->look_token->name, ">=", 2)) rel = 4; - else if (!memcmp (cclp->look_token->name, "<>", 2)) + else if (!memcmp(cclp->look_token->name, "<>", 2)) rel = 6; } if (!rel) @@ -597,7 +600,7 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, if (cclp->look_token->len > 1 && i == 0) { /* -xx*/ - struct ccl_token *ntoken = ccl_token_add (cclp->look_token); + struct ccl_token *ntoken = ccl_token_add(cclp->look_token); ntoken->kind = CCL_TOK_TERM; ntoken->name = cclp->look_token->name + 1; @@ -608,7 +611,7 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, } else if (cclp->look_token->len > 1 && i == cclp->look_token->len-1) { /* xx- */ - struct ccl_token *ntoken = ccl_token_add (cclp->look_token); + struct ccl_token *ntoken = ccl_token_add(cclp->look_token); ntoken->kind = CCL_TOK_TERM; ntoken->name = "-"; @@ -618,8 +621,8 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, } else if (cclp->look_token->len > 2 && i < cclp->look_token->len) { /* xx-yy */ - struct ccl_token *ntoken1 = ccl_token_add (cclp->look_token); - struct ccl_token *ntoken2 = ccl_token_add (ntoken1); + struct ccl_token *ntoken1 = ccl_token_add(cclp->look_token); + struct ccl_token *ntoken2 = ccl_token_add(ntoken1); ntoken1->kind = CCL_TOK_TERM; /* generate - */ ntoken1->name = "-"; @@ -639,7 +642,7 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, { /* xx -yy */ /* we _know_ that xx does not have - in it */ - struct ccl_token *ntoken = ccl_token_add (cclp->look_token); + struct ccl_token *ntoken = ccl_token_add(cclp->look_token); ntoken->kind = CCL_TOK_TERM; /* generate - */ ntoken->name = "-"; @@ -657,16 +660,16 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, cclp->look_token->next->name[0] == '-') { struct ccl_rpn_node *p1; - if (!(p1 = search_term (cclp, ap))) + if (!(p1 = search_term(cclp, ap))) return NULL; ADVANCE; /* skip '-' */ if (KIND == CCL_TOK_TERM) /* = term - term ? */ { struct ccl_rpn_node *p2; - if (!(p2 = search_term (cclp, ap))) + if (!(p2 = search_term(cclp, ap))) { - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } p = ccl_rpn_node_create(CCL_RPN_AND); @@ -687,7 +690,7 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, cclp->look_token->name[0] == '-') /* = - term ? */ { ADVANCE; - if (!(p = search_term (cclp, ap))) + if (!(p = search_term(cclp, ap))) return NULL; ccl_add_attr_numeric(p, attset, CCL_BIB1_REL, 2); return p; @@ -695,12 +698,12 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, else if (KIND == CCL_TOK_LP) { ADVANCE; - if (!(p = find_spec (cclp, ap))) + if (!(p = find_spec(cclp, ap))) return NULL; if (KIND != CCL_TOK_RP) { cclp->error_code = CCL_ERR_RP_EXPECTED; - ccl_rpn_delete (p); + ccl_rpn_delete(p); return NULL; } ADVANCE; @@ -708,7 +711,7 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, } else { - if (!(p = search_terms (cclp, ap))) + if (!(p = search_terms(cclp, ap))) return NULL; ccl_add_attr_numeric(p, attset, CCL_BIB1_REL, rel); return p; @@ -718,7 +721,7 @@ struct ccl_rpn_node *qualifiers_order (CCL_parser cclp, } static -struct ccl_rpn_node *qualifiers2 (CCL_parser cclp, struct ccl_rpn_attr **ap) +struct ccl_rpn_node *qualifier_relation(CCL_parser cclp, ccl_qualifier_t *ap) { char *attset; struct ccl_rpn_node *p; @@ -737,36 +740,36 @@ struct ccl_rpn_node *qualifiers2 (CCL_parser cclp, struct ccl_rpn_attr **ap) if (KIND == CCL_TOK_LP) { ADVANCE; - if (!(p = find_spec (cclp, ap))) + if (!(p = find_spec(cclp, ap))) { return NULL; } if (KIND != CCL_TOK_RP) { cclp->error_code = CCL_ERR_RP_EXPECTED; - ccl_rpn_delete (p); + ccl_rpn_delete(p); return NULL; } ADVANCE; } else - p = search_terms (cclp, ap); + p = search_terms(cclp, ap); return p; } /** - * qualifiers1: Parse CCL qualifiers and search terms. + * qualifier_list: Parse CCL qualifiers and search terms. * cclp: CCL Parser * la: Token pointer to RELATION token. * qa: Qualifier attributes already applied. * return: pointer to node(s); NULL on error. */ -static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, - struct ccl_rpn_attr **qa) +static struct ccl_rpn_node *qualifier_list(CCL_parser cclp, struct ccl_token *la, + ccl_qualifier_t *qa) { struct ccl_token *lookahead = cclp->look_token; struct ccl_token *look_start = cclp->look_token; - struct ccl_rpn_attr **ap; + ccl_qualifier_t *ap; struct ccl_rpn_node *node = 0; const char *field_str; int no = 0; @@ -786,15 +789,15 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, if (qa) for (i=0; qa[i]; i++) no++; - ap = (struct ccl_rpn_attr **)xmalloc ((no ? (no+1) : 2) * sizeof(*ap)); - ccl_assert (ap); + ap = (ccl_qualifier_t *)xmalloc((no ? (no+1) : 2) * sizeof(*ap)); + ccl_assert(ap); field_str = ccl_qual_search_special(cclp->bibset, "field"); if (field_str) { - if (!strcmp (field_str, "or")) + if (!strcmp(field_str, "or")) mode_merge = 0; - else if (!strcmp (field_str, "merge")) + else if (!strcmp(field_str, "merge")) mode_merge = 1; } if (!mode_merge) @@ -805,17 +808,17 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, { ap[1] = 0; seq = 0; - while ((ap[0] = ccl_qual_search (cclp, lookahead->name, - lookahead->len, seq)) != 0) + while ((ap[0] = ccl_qual_search(cclp, lookahead->name, + lookahead->len, seq)) != 0) { struct ccl_rpn_node *node_sub; cclp->look_token = la; - node_sub = qualifiers2(cclp, ap); + node_sub = qualifier_relation(cclp, ap); if (!node_sub) { - ccl_rpn_delete (node); - xfree (ap); + ccl_rpn_delete(node); + xfree(ap); return 0; } if (node) @@ -834,7 +837,7 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, { cclp->look_token = lookahead; cclp->error_code = CCL_ERR_UNKNOWN_QUAL; - xfree (ap); + xfree(ap); return NULL; } lookahead = lookahead->next; @@ -852,18 +855,18 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, lookahead = look_start; for (i = 0; lookahead != la; i++) { - ap[i] = ccl_qual_search (cclp, lookahead->name, + ap[i] = ccl_qual_search(cclp, lookahead->name, lookahead->len, seq); if (ap[i]) found++; if (!ap[i] && seq > 0) - ap[i] = ccl_qual_search (cclp, lookahead->name, + ap[i] = ccl_qual_search(cclp, lookahead->name, lookahead->len, 0); if (!ap[i]) { cclp->look_token = lookahead; cclp->error_code = CCL_ERR_UNKNOWN_QUAL; - xfree (ap); + xfree(ap); return NULL; } lookahead = lookahead->next; @@ -872,7 +875,7 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, } if (qa) { - struct ccl_rpn_attr **qa0 = qa; + ccl_qualifier_t *qa0 = qa; while (*qa0) ap[i++] = *qa0++; @@ -884,10 +887,10 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, cclp->look_token = lookahead; - node_sub = qualifiers2(cclp, ap); + node_sub = qualifier_relation(cclp, ap); if (!node_sub) { - ccl_rpn_delete (node); + ccl_rpn_delete(node); break; } if (node) @@ -903,7 +906,7 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, seq++; } } - xfree (ap); + xfree(ap); return node; } @@ -914,13 +917,12 @@ static struct ccl_rpn_node *qualifiers1 (CCL_parser cclp, struct ccl_token *la, * qa: Qualifier attributes already applied. * return: pointer to node(s); NULL on error. */ -static struct ccl_rpn_node *search_terms (CCL_parser cclp, - struct ccl_rpn_attr **qa) +static struct ccl_rpn_node *search_terms(CCL_parser cclp, ccl_qualifier_t *qa) { static int list[] = { CCL_TOK_TERM, CCL_TOK_COMMA,CCL_TOK_EQ, CCL_TOK_REL, CCL_TOK_SET, -1}; struct ccl_rpn_node *p1, *p2, *pn; - p1 = search_term_x (cclp, qa, list, 1); + p1 = search_term_x(cclp, qa, list, 1); if (!p1) return NULL; while (1) @@ -938,10 +940,10 @@ static struct ccl_rpn_node *search_terms (CCL_parser cclp, p_prox->u.t.attr_list = 0; ADVANCE; - p2 = search_term_x (cclp, qa, list, 1); + p2 = search_term_x(cclp, qa, list, 1); if (!p2) { - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } pn = ccl_rpn_node_create(CCL_RPN_PROX); @@ -952,10 +954,10 @@ static struct ccl_rpn_node *search_terms (CCL_parser cclp, } else if (is_term_ok(KIND, list)) { - p2 = search_term_x (cclp, qa, list, 1); + p2 = search_term_x(cclp, qa, list, 1); if (!p2) { - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } pn = ccl_rpn_node_create(CCL_RPN_PROX); @@ -976,21 +978,21 @@ static struct ccl_rpn_node *search_terms (CCL_parser cclp, * qa: Qualifier attributes already applied. * return: pointer to node(s); NULL on error. */ -static struct ccl_rpn_node *search_elements (CCL_parser cclp, - struct ccl_rpn_attr **qa) +static struct ccl_rpn_node *search_elements(CCL_parser cclp, + ccl_qualifier_t *qa) { struct ccl_rpn_node *p1; struct ccl_token *lookahead; if (KIND == CCL_TOK_LP) { ADVANCE; - p1 = find_spec (cclp, qa); + p1 = find_spec(cclp, qa); if (!p1) return NULL; if (KIND != CCL_TOK_RP) { cclp->error_code = CCL_ERR_RP_EXPECTED; - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } ADVANCE; @@ -1007,7 +1009,7 @@ static struct ccl_rpn_node *search_elements (CCL_parser cclp, return NULL; } p1 = ccl_rpn_node_create(CCL_RPN_SET); - p1->u.setname = copy_token_name (cclp->look_token); + p1->u.setname = copy_token_name(cclp->look_token); ADVANCE; return p1; } @@ -1017,16 +1019,16 @@ static struct ccl_rpn_node *search_elements (CCL_parser cclp, { lookahead = lookahead->next; if (lookahead->kind == CCL_TOK_REL || lookahead->kind == CCL_TOK_EQ) - return qualifiers1 (cclp, lookahead, qa); + return qualifier_list(cclp, lookahead, qa); if (lookahead->kind != CCL_TOK_COMMA) break; lookahead = lookahead->next; } if (qa) - return search_terms (cclp, qa); + return search_terms(cclp, qa); else { - struct ccl_rpn_attr *qa[2]; + ccl_qualifier_t qa[2]; struct ccl_rpn_node *node = 0; int seq; lookahead = cclp->look_token; @@ -1041,10 +1043,10 @@ static struct ccl_rpn_node *search_elements (CCL_parser cclp, cclp->look_token = lookahead; - node_sub = search_terms (cclp, qa); + node_sub = search_terms(cclp, qa); if (!node_sub) { - ccl_rpn_delete (node); + ccl_rpn_delete(node); return 0; } if (node) @@ -1060,7 +1062,7 @@ static struct ccl_rpn_node *search_elements (CCL_parser cclp, node = node_sub; } if (!node) - node = search_terms (cclp, 0); + node = search_terms(cclp, 0); return node; } } @@ -1071,11 +1073,10 @@ static struct ccl_rpn_node *search_elements (CCL_parser cclp, * qa: Qualifier attributes already applied. * return: pointer to node(s); NULL on error. */ -static struct ccl_rpn_node *find_spec (CCL_parser cclp, - struct ccl_rpn_attr **qa) +static struct ccl_rpn_node *find_spec(CCL_parser cclp, ccl_qualifier_t *qa) { struct ccl_rpn_node *p1, *p2, *pn; - if (!(p1 = search_elements (cclp, qa))) + if (!(p1 = search_elements(cclp, qa))) return NULL; while (1) { @@ -1083,10 +1084,10 @@ static struct ccl_rpn_node *find_spec (CCL_parser cclp, { case CCL_TOK_AND: ADVANCE; - p2 = search_elements (cclp, qa); + p2 = search_elements(cclp, qa); if (!p2) { - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } pn = ccl_rpn_node_create(CCL_RPN_AND); @@ -1097,10 +1098,10 @@ static struct ccl_rpn_node *find_spec (CCL_parser cclp, continue; case CCL_TOK_OR: ADVANCE; - p2 = search_elements (cclp, qa); + p2 = search_elements(cclp, qa); if (!p2) { - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } pn = ccl_rpn_node_create(CCL_RPN_OR); @@ -1111,10 +1112,10 @@ static struct ccl_rpn_node *find_spec (CCL_parser cclp, continue; case CCL_TOK_NOT: ADVANCE; - p2 = search_elements (cclp, qa); + p2 = search_elements(cclp, qa); if (!p2) { - ccl_rpn_delete (p1); + ccl_rpn_delete(p1); return NULL; } pn = ccl_rpn_node_create(CCL_RPN_NOT); @@ -1144,14 +1145,14 @@ struct ccl_rpn_node *ccl_parser_find_token(CCL_parser cclp, struct ccl_rpn_node *p; cclp->look_token = list; - p = find_spec (cclp, NULL); + p = find_spec(cclp, NULL); if (p && KIND != CCL_TOK_EOL) { if (KIND == CCL_TOK_RP) cclp->error_code = CCL_ERR_BAD_RP; else cclp->error_code = CCL_ERR_OP_EXPECTED; - ccl_rpn_delete (p); + ccl_rpn_delete(p); p = NULL; } cclp->error_pos = cclp->look_token->name; @@ -1173,18 +1174,18 @@ struct ccl_rpn_node *ccl_parser_find_token(CCL_parser cclp, struct ccl_rpn_node *ccl_find_str(CCL_bibset bibset, const char *str, int *error, int *pos) { - CCL_parser cclp = ccl_parser_create (bibset); + CCL_parser cclp = ccl_parser_create(bibset); struct ccl_token *list; struct ccl_rpn_node *p; - list = ccl_parser_tokenize (cclp, str); + list = ccl_parser_tokenize(cclp, str); p = ccl_parser_find_token(cclp, list); *error = cclp->error_code; if (*error) *pos = cclp->error_pos - str; - ccl_parser_destroy (cclp); - ccl_token_del (list); + ccl_parser_destroy(cclp); + ccl_token_del(list); return p; } /* diff --git a/src/cclp.h b/src/cclp.h index 0cc5b5b..1f59728 100644 --- a/src/cclp.h +++ b/src/cclp.h @@ -2,7 +2,7 @@ * Copyright (C) 1995-2005, Index Data ApS * See the file LICENSE for details. * - * $Id: cclp.h,v 1.2 2007-04-27 09:50:35 adam Exp $ + * $Id: cclp.h,v 1.3 2007-04-30 11:33:49 adam Exp $ */ /** @@ -24,6 +24,7 @@ #define CCL_TOK_NOT 10 #define CCL_TOK_SET 11 +typedef struct ccl_qualifier *ccl_qualifier_t; /** CCL token */ struct ccl_token { @@ -88,6 +89,15 @@ struct ccl_rpn_node *ccl_parser_find_token(CCL_parser cclp, struct ccl_token *list); +YAZ_EXPORT +ccl_qualifier_t ccl_qual_search(CCL_parser cclp, const char *name, + size_t name_len, int seq); + +YAZ_EXPORT +struct ccl_rpn_attr *ccl_qual_get_attr(ccl_qualifier_t q); + +YAZ_EXPORT +const char *ccl_qual_get_name(ccl_qualifier_t q); /* * Local variables: diff --git a/src/cclqual.c b/src/cclqual.c index f187c5e..1c2dc1e 100644 --- a/src/cclqual.c +++ b/src/cclqual.c @@ -48,7 +48,7 @@ /* CCL qualifiers * Europagate, 1995 * - * $Id: cclqual.c,v 1.7 2007-04-26 22:11:32 adam Exp $ + * $Id: cclqual.c,v 1.8 2007-04-30 11:33:49 adam Exp $ * * Old Europagate Log: * @@ -327,52 +327,58 @@ void ccl_qual_rm(CCL_bibset *b) *b = NULL; } -/** \brief searches for qualifier attributes - \param cclp CCL parser - \param name qualifier name to for search (length given by len) - \param len length of name - \param seq attribute index (0=first, 1=second, ..) - \returns attribute or NULL if none is found -*/ -struct ccl_rpn_attr *ccl_qual_search(CCL_parser cclp, const char *name, - size_t len, int seq) +ccl_qualifier_t ccl_qual_search(CCL_parser cclp, const char *name, + size_t name_len, int seq) { - struct ccl_qualifier *q; + struct ccl_qualifier *q = 0; const char *aliases; int case_sensitive = cclp->ccl_case_sensitive; ccl_assert(cclp); if (!cclp->bibset) - return NULL; + return 0; aliases = ccl_qual_search_special(cclp->bibset, "case"); if (aliases) case_sensitive = atoi(aliases); for (q = cclp->bibset->list; q; q = q->next) - if (strlen(q->name) == len) + if (strlen(q->name) == name_len) { if (case_sensitive) { - if (!memcmp(name, q->name, len)) + if (!memcmp(name, q->name, name_len)) break; } else { - if (!ccl_memicmp(name, q->name, len)) + if (!ccl_memicmp(name, q->name, name_len)) break; } } if (q) { - if (q->attr_list && seq == 0) - return q->attr_list; - if (seq < q->no_sub && q->sub[seq]) + if (q->no_sub) { - return q->sub[seq]->attr_list; + if (seq < q->no_sub) + q = q->sub[seq]; + else + q = 0; } + else if (seq) + q = 0; } - return 0; + return q; +} + +struct ccl_rpn_attr *ccl_qual_get_attr(ccl_qualifier_t q) +{ + return q->attr_list; +} + +const char *ccl_qual_get_name(ccl_qualifier_t q) +{ + return q->name; } const char *ccl_qual_search_special(CCL_bibset b, const char *name) -- 1.7.10.4