| /* |
| * XSLPattern lexer |
| * |
| * Copyright 2010 Adam Martinson for CodeWeavers |
| * |
| * This library is free software; you can redistribute it and/or |
| * modify it under the terms of the GNU Lesser General Public |
| * License as published by the Free Software Foundation; either |
| * version 2.1 of the License, or (at your option) any later version. |
| * |
| * This library is distributed in the hope that it will be useful, |
| * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
| * Lesser General Public License for more details. |
| * |
| * You should have received a copy of the GNU Lesser General Public |
| * License along with this library; if not, write to the Free Software |
| * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA |
| */ |
| |
| %{ |
| #include "config.h" |
| #include "wine/port.h" |
| |
| #ifdef HAVE_LIBXML2 |
| |
| #include "xslpattern.h" |
| #include "xslpattern.tab.h" |
| #include "wine/debug.h" |
| |
| WINE_DEFAULT_DEBUG_CHANNEL(msxml); |
| |
| #define SCAN xslpattern_get_extra(yyscanner) |
| |
| #define YY_INPUT(tok_buf, tok_len, max) \ |
| do { \ |
| if (SCAN->pos <= SCAN->len) \ |
| { \ |
| tok_len = SCAN->len - SCAN->pos; \ |
| if (tok_len > max) tok_len = max; \ |
| memcpy(tok_buf, SCAN->in + SCAN->pos, tok_len); \ |
| SCAN->pos += tok_len; \ |
| } \ |
| else \ |
| { \ |
| tok_len = YY_NULL; \ |
| } \ |
| } while (0); |
| |
| #define TOK(tok) TRACE("token: %s : %s\n", #tok, yytext); return tok |
| #define OP(tok) *yylval=NULL; TOK(tok) |
| #define SYM(tok) *yylval=NULL; TOK(tok) |
| #define STR(tok) *yylval=xmlStrdup(BAD_CAST yytext); TOK(tok) |
| |
| |
| %} |
| |
| %option reentrant bison-bridge |
| %option noyywrap |
| %option prefix="xslpattern_" |
| %option noinput nounput never-interactive |
| |
| /* From the w3c XML standard |
| * <http://www.w3.org/TR/REC-xml/> */ |
| |
| /* [2.3] Common Syntactic Constructs */ |
| WSpace ([[:space:]]) |
| |
| NCNameStartChar ([A-Za-z_]|[\xc0-\xd6\xd8-\xf6\xf8-\xff]) |
| |
| NameCharEx ([0-9]|[-._\xb7]) |
| |
| NCNameChar ({NCNameStartChar}|{NameCharEx}) |
| |
| /* From the w3c XML Namespace standard |
| * <http://www.w3.org/TR/REC-xml-names/> */ |
| |
| /* [3] Declaring Namespaces*/ |
| NCName ({NCNameStartChar}{NCNameChar}*) |
| |
| /* Mostly verbatim from the w3c XPath standard. |
| * <http://www.w3.org/TR/xpath/> */ |
| |
| |
| /* [3.4] Booleans |
| * ||, &&, $foo$ are XSLPattern only */ |
| |
| OP_Or ("or"|"||"|"$or$") |
| OP_And ("and"|"&&"|"$and$") |
| OP_Eq ("="|"$eq$") |
| OP_IEq ("$ieq$") |
| OP_NEq ("!="|"$ne$") |
| OP_INEq ("$ine$") |
| OP_Lt ("<"|"$lt$") |
| OP_ILt ("$ilt$") |
| OP_Gt (">"|"$gt$") |
| OP_IGt ("$igt$") |
| OP_LEq ("<="|"$le$") |
| OP_ILEq ("$ile$") |
| OP_GEq (">="|"$ge$") |
| OP_IGEq ("$ige$") |
| OP_Not ("$not$") |
| OP_All ("$all$") |
| OP_Any ("$any$") |
| |
| /* [3.7] Lexical Structure */ |
| Literal (([\x22]([^\x22]*)[\x22])|([\x27]([^\x27]*)[\x27])) |
| Number ({Digits}("."{Digits}?)?|"."{Digits}) |
| Digits ([0-9]+) |
| |
| ANY (.) |
| |
| %% |
| |
| {WSpace}+ { /* ignored */ } |
| {Literal} { STR(TOK_Literal); } |
| "//" { SYM(TOK_DblFSlash); } |
| "/" { SYM(TOK_FSlash); } |
| ".." { SYM(TOK_Parent); } |
| "." { SYM(TOK_Self); } |
| "::" { SYM(TOK_Axis); } |
| ":" { SYM(TOK_Colon); } |
| "(" { SYM('('); } |
| ")" { SYM(')'); } |
| "[" { SYM('['); } |
| "]" { SYM(']'); } |
| "@" { SYM('@'); } |
| "," { SYM(','); } |
| "*" { SYM('*'); } |
| {OP_And} { OP(TOK_OpAnd); } |
| {OP_Or} { OP(TOK_OpOr); } |
| {OP_Not} { OP(TOK_OpNot); } |
| {OP_Eq} { OP(TOK_OpEq); } |
| {OP_IEq} { OP(TOK_OpIEq); } |
| {OP_NEq} { OP(TOK_OpNEq); } |
| {OP_INEq} { OP(TOK_OpINEq); } |
| {OP_Lt} { OP(TOK_OpLt); } |
| {OP_ILt} { OP(TOK_OpILt); } |
| {OP_Gt} { OP(TOK_OpGt); } |
| {OP_IGt} { OP(TOK_OpIGt); } |
| {OP_LEq} { OP(TOK_OpLEq); } |
| {OP_ILEq} { OP(TOK_OpILEq); } |
| {OP_GEq} { OP(TOK_OpGEq); } |
| {OP_IGEq} { OP(TOK_OpIGEq); } |
| {OP_All} { OP(TOK_OpAll); } |
| {OP_Any} { OP(TOK_OpAny); } |
| "|" { SYM('|'); } |
| "!" { SYM('!'); } |
| {NCName} { STR(TOK_NCName); } |
| {Number} { STR(TOK_Number); } |
| {ANY} { FIXME("Unexpected character '%s'.\n",yytext); } |
| |
| %% |
| |
| xmlChar* XSLPattern_to_XPath(xmlXPathContextPtr, xmlChar const*) DECLSPEC_HIDDEN; |
| xmlChar* XSLPattern_to_XPath(xmlXPathContextPtr ctxt, xmlChar const* xslpat_str) |
| { |
| parser_param p; |
| TRACE("(%s)\n", debugstr_a((char const*)xslpat_str)); |
| memset(&p, 0, sizeof(parser_param)); |
| p.ctx = ctxt; |
| p.in = xslpat_str; |
| p.len = xmlStrlen(xslpat_str); |
| |
| xslpattern_lex_init(&p.yyscanner); |
| xslpattern_set_extra(&p, p.yyscanner); |
| |
| xslpattern_parse(&p, p.yyscanner); |
| |
| TRACE("=> %s\n", debugstr_a((char const*)p.out)); |
| xslpattern_lex_destroy(p.yyscanner); |
| |
| if (p.err) |
| { |
| xmlFree(p.out); |
| return xmlStrdup(xslpat_str); |
| } |
| else |
| { |
| return p.out; |
| } |
| |
| } |
| |
| #endif /* HAVE_LIBXML2 */ |