summaryrefslogtreecommitdiff
path: root/idlc/source/scanner.ll
diff options
context:
space:
mode:
Diffstat (limited to 'idlc/source/scanner.ll')
-rw-r--r--idlc/source/scanner.ll523
1 files changed, 523 insertions, 0 deletions
diff --git a/idlc/source/scanner.ll b/idlc/source/scanner.ll
new file mode 100644
index 000000000000..4125195f5916
--- /dev/null
+++ b/idlc/source/scanner.ll
@@ -0,0 +1,523 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org 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 version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+%{
+/*
+ * scanner.ll - Lexical scanner for IDLC 1.0
+ */
+
+#include <ctype.h>
+#include <stdlib.h>
+#include <string.h>
+
+#ifndef _IDLC_IDLC_HXX_
+#include <idlc/idlc.hxx>
+#endif
+#ifndef _IDLC_ERRORHANDLER_HXX_
+#include <idlc/errorhandler.hxx>
+#endif
+#ifndef _IDLC_FEHELPER_HXX_
+#include <idlc/fehelper.hxx>
+#endif
+
+#include "attributeexceptions.hxx"
+
+class AstExpression;
+class AstArray;
+class AstMember;
+
+#include <parser.hxx>
+
+sal_Int32 beginLine = 0;
+::rtl::OString docu;
+
+static int asciiToInteger(char const * s, sal_Int64 * sval, sal_uInt64 * uval) {
+ bool neg = false;
+ if (*s == '-') {
+ neg = true;
+ ++s;
+ }
+ unsigned int base = 10;
+ if (*s == '0') {
+ base = 8;
+ ++s;
+ if (*s == 'X' || *s == 'x') {
+ base = 16;
+ ++s;
+ }
+ }
+ sal_uInt64 val = 0;
+ for (; *s != 0; ++s) {
+ unsigned int n;
+ if (*s >= '0' && *s <= '9') {
+ n = *s - '0';
+ } else {
+ switch (*s) {
+ case 'A':
+ case 'a':
+ n = 10;
+ break;
+ case 'B':
+ case 'b':
+ n = 11;
+ break;
+ case 'C':
+ case 'c':
+ n = 12;
+ break;
+ case 'D':
+ case 'd':
+ n = 13;
+ break;
+ case 'E':
+ case 'e':
+ n = 14;
+ break;
+ case 'F':
+ case 'f':
+ n = 15;
+ break;
+ default:
+ goto done;
+ }
+ }
+ // The following guarantees the invariant val <= SAL_MAX_UINT64 (because
+ // base and n are sufficiently small), *if*
+ // std::numeric_limits<sal_uInt64>::max() == SAL_MAX_UINT64:
+ sal_uInt64 nval = val * base + n;
+ if (nval < val) {
+ idlc()->error()->syntaxError(
+ PS_NoState, idlc()->getLineNumber(),
+ "integral constant too large");
+ val = 0;
+ break;
+ }
+ val = nval;
+ }
+ done:
+ if (neg) {
+ if (val < SAL_CONST_UINT64(0x8000000000000000)) {
+ *sval = -static_cast< sal_Int64 >(val);
+ } else if (val == SAL_CONST_UINT64(0x8000000000000000)) {
+ *sval = SAL_MIN_INT64;
+ } else {
+ idlc()->error()->syntaxError(
+ PS_NoState, idlc()->getLineNumber(),
+ "negative integral constant too large");
+ *sval = 0;
+ }
+ return IDL_INTEGER_LITERAL;
+ } else if (val <= static_cast< sal_uInt64 >(SAL_MAX_INT64)) {
+ *sval = static_cast< sal_Int64 >(val);
+ return IDL_INTEGER_LITERAL;
+ } else {
+ *uval = val;
+ return IDL_INTEGER_ULITERAL;
+ }
+}
+
+static double asciiToFloat(const sal_Char *s)
+{
+ double d = 0.0;
+ double e, k;
+ sal_Int32 neg = 0, negexp = 0;
+
+ if (*s == '-')
+ {
+ neg = 1;
+ s++;
+ }
+ while (*s >= '0' && *s <= '9')
+ {
+ d = (d * 10) + *s - '0';
+ s++;
+ }
+ if (*s == '.')
+ {
+ s++;
+ e = 10;
+ while (*s >= '0' && *s <= '9')
+ {
+ d += (*s - '0') / (e * 1.0);
+ e *= 10;
+ s++;
+ }
+ }
+ if (*s == 'e' || *s == 'E')
+ {
+ s++;
+ if (*s == '-')
+ {
+ negexp = 1;
+ s++;
+ } else
+ {
+ if (*s == '+')
+ s++;
+ e = 0;
+ while (*s >= '0' && *s <= '9')
+ {
+ e = (e * 10) + *s - '0';
+ s++;
+ }
+ if (e > 0)
+ {
+ for (k = 1; e > 0; k *= 10, e--) ;
+ if (negexp)
+ d /= k;
+ else
+ d *= k;
+ }
+ }
+ }
+ if (neg) d *= -1.0;
+ return d;
+}
+
+static void idlParsePragma(sal_Char* pPragma)
+{
+ ::rtl::OString pragma(pPragma);
+ sal_Int32 index = pragma.indexOf("include");
+ sal_Char* begin = pPragma + index + 8;
+ sal_Char* offset = begin;
+ while (*offset != ',') offset++;
+ //::rtl::OString include = pragma.copy(index + 8, offset - begin);
+ idlc()->insertInclude(pragma.copy(index + 8, (sal_Int32)(offset - begin)));
+}
+
+static void parseLineAndFile(sal_Char* pBuf)
+{
+ sal_Char *r = pBuf;
+ sal_Char *h;
+ sal_Bool bIsInMain = sal_False;
+
+ /* Skip initial '#' */
+ if (*r != '#')
+ return;
+
+ /* Find line number */
+ for (r++; *r == ' ' || *r == '\t' || isalpha(*r); r++) ;
+ h = r;
+ for (; *r != '\0' && *r != ' ' && *r != '\t'; r++) ;
+ *r++ = 0;
+ idlc()->setLineNumber((sal_uInt32)atol(h));
+
+ /* Find file name, if present */
+ for (; *r != '"'; r++)
+ {
+ if (*r == '\n' || *r == '\0')
+ return;
+ }
+ h = ++r;
+ for (; *r != '"'; r++) ;
+ *r = 0;
+ if (*h == '\0')
+ idlc()->setFileName(::rtl::OString("standard input"));
+ else
+ idlc()->setFileName(::rtl::OString(h));
+
+ bIsInMain = (idlc()->getFileName() == idlc()->getRealFileName()) ? sal_True : sal_False;
+ idlc()->setInMainfile(bIsInMain);
+}
+
+// Suppress any warnings from generated code:
+#if defined __GNUC__
+#pragma GCC system_header
+#elif defined __SUNPRO_CC
+#pragma disable_warn
+#elif defined _MSC_VER
+#pragma warning(push, 1)
+/**/
+#ifdef yywrap
+#undef yywrap
+#define yywrap() 1
+#endif
+/**/
+#endif
+%}
+
+%option noyywrap
+%option never-interactive
+
+%x DOCU
+%x COMMENT
+
+DIGIT [0-9]
+OCT_DIGIT [0-7]
+HEX_DIGIT [a-fA-F0-9]
+CAPITAL [A-Z]
+ALPHA [a-zA-Z]
+INT_LITERAL [1-9][0-9]*
+OCT_LITERAL 0{OCT_DIGIT}*
+HEX_LITERAL (0x|0X){HEX_DIGIT}*
+
+IDENTIFIER_NEW ({ALPHA}({ALPHA}|{DIGIT})*)|({CAPITAL}("_"?({ALPHA}|{DIGIT})+)*)
+IDENTIFIER ("_"?({ALPHA}|{DIGIT})+)*
+
+%%
+
+[ \t\r]+ ; /* eat up whitespace */
+[\n] {
+ idlc()->incLineNumber();
+}
+
+attribute return IDL_ATTRIBUTE;
+bound return IDL_BOUND;
+case return IDL_CASE;
+const return IDL_CONST;
+constants return IDL_CONSTANTS;
+constrained return IDL_CONSTRAINED;
+default return IDL_DEFAULT;
+enum return IDL_ENUM;
+exception return IDL_EXCEPTION;
+interface return IDL_INTERFACE;
+maybeambiguous return IDL_MAYBEAMBIGUOUS;
+maybedefault return IDL_MAYBEDEFAULT;
+maybevoid return IDL_MAYBEVOID;
+module return IDL_MODULE;
+needs return IDL_NEEDS;
+observes return IDL_OBSERVES;
+optional return IDL_OPTIONAL;
+property return IDL_PROPERTY;
+raises return IDL_RAISES;
+readonly return IDL_READONLY;
+removable return IDL_REMOVEABLE;
+service return IDL_SERVICE;
+sequence return IDL_SEQUENCE;
+singleton return IDL_SINGLETON;
+struct return IDL_STRUCT;
+switch return IDL_SWITCH;
+transient return IDL_TRANSIENT;
+typedef return IDL_TYPEDEF;
+union return IDL_UNION;
+
+any return IDL_ANY;
+boolean return IDL_BOOLEAN;
+byte return IDL_BYTE;
+char return IDL_CHAR;
+double return IDL_DOUBLE;
+float return IDL_FLOAT;
+hyper return IDL_HYPER;
+long return IDL_LONG;
+short return IDL_SHORT;
+string return IDL_STRING;
+type return IDL_TYPE;
+unsigned return IDL_UNSIGNED;
+void return IDL_VOID;
+
+TRUE return IDL_TRUE;
+True return IDL_TRUE;
+FALSE return IDL_FALSE;
+False return IDL_FALSE;
+
+in return IDL_IN;
+out return IDL_OUT;
+inout return IDL_INOUT;
+oneway return IDL_ONEWAY;
+
+get return IDL_GET;
+set return IDL_SET;
+
+published return IDL_PUBLISHED;
+
+"..." return IDL_ELLIPSIS;
+
+("-")?{INT_LITERAL}+(l|L|u|U)? {
+ return asciiToInteger(yytext, &yylval.ival, &yylval.uval);
+ }
+
+("-")?{OCT_LITERAL}+(l|L|u|U)? {
+ return asciiToInteger(yytext, &yylval.ival, &yylval.uval);
+ }
+
+("-")?{HEX_LITERAL}+(l|L|u|U)? {
+ return asciiToInteger(yytext, &yylval.ival, &yylval.uval);
+ }
+
+("-")?{DIGIT}+(e|E){1}(("+"|"-")?{DIGIT}+)+(f|F)? |
+("-")?"."{DIGIT}+((e|E)("+"|"-")?{DIGIT}+)?(f|F)? |
+("-")?{DIGIT}*"."{DIGIT}+((e|E)("+"|"-")?{DIGIT}+)?(f|F)? {
+ yylval.dval = asciiToFloat( yytext );
+ return IDL_FLOATING_PT_LITERAL;
+ }
+
+{IDENTIFIER} {
+ yylval.sval = new ::rtl::OString(yytext);
+ return IDL_IDENTIFIER;
+ }
+
+\<\< {
+ yylval.strval = yytext;
+ return IDL_LEFTSHIFT;
+ }
+\>\> {
+ yylval.strval = yytext;
+ return IDL_RIGHTSHIFT;
+ }
+\:\: {
+ yylval.strval = yytext;
+ return IDL_SCOPESEPARATOR;
+ }
+
+"/*" {
+ BEGIN( COMMENT );
+ docu = ::rtl::OString();
+ beginLine = idlc()->getLineNumber();
+ }
+
+"/***" {
+ BEGIN( COMMENT );
+ docu = ::rtl::OString();
+ beginLine = idlc()->getLineNumber();
+ }
+
+<COMMENT>[^*]+ {
+ docu += ::rtl::OString(yytext);
+ }
+
+<COMMENT>"*"[^*/]+ {
+ docu += ::rtl::OString(yytext);
+ }
+
+<COMMENT>"**" {
+ docu += ::rtl::OString(yytext);
+ }
+
+<COMMENT>[*]+"/" {
+ docu = docu.trim();
+ sal_Int32 nIndex = 0;
+ int count = 0;
+ do { docu.getToken( 0, '\n', nIndex ); count++; } while( nIndex != -1 );
+ idlc()->setLineNumber( beginLine + count - 1);
+ BEGIN( INITIAL );
+ }
+
+"/**" {
+ BEGIN( DOCU );
+ docu = ::rtl::OString();
+ beginLine = idlc()->getLineNumber();
+ }
+
+<DOCU>[^*\n]+ {
+ docu += ::rtl::OString(yytext);
+ }
+
+<DOCU>"\n"[ \t]*"*"{1} {
+ idlc()->setLineNumber( idlc()->getLineNumber() + 1);
+ docu += ::rtl::OString("\n");
+ }
+
+<DOCU>"\n" {
+ idlc()->setLineNumber( idlc()->getLineNumber() + 1);
+ docu += ::rtl::OString(yytext);
+ }
+
+<DOCU>"*"[^*^/\n]* {
+ docu += ::rtl::OString(yytext);
+ }
+
+<DOCU>"\n"[ \t]*"*/" {
+ docu = docu.trim();
+ sal_Int32 nIndex = 0;
+ int count = 0;
+ do { docu.getToken( 0, '\n', nIndex ); count++; } while( nIndex != -1 );
+ idlc()->setLineNumber( beginLine + count - 1);
+ if ( (nIndex = docu.indexOf("/*")) >= 0 || (nIndex = docu.indexOf("///")) >= 0 )
+ {
+ if ( 0 != nIndex &&
+ (docu.getStr()[nIndex - 1] != '"' && docu.getStr()[nIndex - 1] != ':') )
+ idlc()->error()->syntaxError(PS_NoState, idlc()->getLineNumber(),
+ "nested documentation strings are not allowed!");
+ }
+ idlc()->setDocumentation(docu);
+ BEGIN( INITIAL );
+ }
+
+<DOCU>"*/" {
+ docu = docu.trim();
+ sal_Int32 nIndex = 0;
+ int count = 0;
+ do { docu.getToken( 0, '\n', nIndex ); count++; } while( nIndex != -1 );
+ idlc()->setLineNumber( beginLine + count - 1);
+ if ( docu.indexOf("/*") >= 0 || docu.indexOf("//") >= 0 )
+ {
+ if ( 0 != nIndex &&
+ (docu.getStr()[nIndex - 1] != '"' && docu.getStr()[nIndex - 1] != ':') )
+ idlc()->error()->syntaxError(PS_NoState, idlc()->getLineNumber(),
+ "nested documentation strings are not allowed!");
+ }
+ idlc()->setDocumentation(docu);
+ BEGIN( INITIAL );
+ }
+
+"//"[^/]{1}.*"\n" {
+ /* only a comment */
+ ::rtl::OString docStr(yytext);
+ docStr = docStr.copy( 0, docStr.lastIndexOf('\n') );
+ docStr = docStr.copy( docStr.lastIndexOf('/')+1 );
+ docStr = docStr.trim();
+ idlc()->incLineNumber();
+ }
+
+"///".*"\n" {
+ ::rtl::OString docStr(yytext);
+ docStr = docStr.copy( 0, docStr.lastIndexOf('\n') );
+ docStr = docStr.copy( docStr.lastIndexOf('/')+1 );
+ docStr = docStr.trim();
+ idlc()->incLineNumber();
+ idlc()->setDocumentation(docStr);
+ }
+
+. return yytext[0];
+
+^#[ \t]*line[ \t]*[0-9]*" ""\""[^\"]*"\""\n {
+ parseLineAndFile(yytext);
+}
+
+^#[ \t]*[0-9]*" ""\""[^\"]*"\""" "[0-9]*\n {
+ parseLineAndFile(yytext);
+}
+
+^#[ \t]*[0-9]*" ""\""[^\"]*"\""\n {
+ parseLineAndFile(yytext);
+}
+
+^#[ \t]*[0-9]*\n {
+ parseLineAndFile(yytext);
+}
+
+^#[ \t]*ident.*\n {
+ /* ignore cpp ident */
+ idlc()->incLineNumber();
+}
+
+^#[ \t]*pragma[ \t].*\n { /* remember pragma */
+ idlParsePragma(yytext);
+ idlc()->incLineNumber();
+}
+
+%%