Пример #1
0
int main(int argc, char** argv){
	int opt;
	int r;
	AST_Class modelica_class;
	
	while((opt = getopt(argc, argv, "d:")) != -1){
		switch(opt){
			case 'd':
				if(optarg != NULL && isDebugParam(optarg)){
					debugInit(optarg);		
				}else{
					ERROR("Command line option d requires an argument\n");
				}
				break;
		}		
	}
	
	if(optind < argc){
		modelica_class = parseClass(argv[optind],&r);
	}else{ 
		/* si no se especifico un archivo leo de stdin*/
		modelica_class = parseClass("", &r);	
	}
	if(r!=0){
		return -1;
	}
	
	/* creamos la clase MicroModelica */
	TypeSymbolTable ty = newTypeSymbolTable();
	MMO_Class mmo_class = newMMO_Class(modelica_class, ty); 

	ReducedGraphBuilder *gb = new ReducedGraphBuilder(mmo_class);
	CausalizationGraph g = gb->makeGraph();

	//para debuggeo: crea archivo grafo.dot 
	if(debugIsEnabled('g')){
		GraphPrinter gp(g);
		gp.printGraph();
	}

	CausalizationStrategy2 *cs = new CausalizationStrategy2(g);
	if(cs->causalize()){
		if(debugIsEnabled('c')){
			cout << "Result of causalization (variable, [range,] equationID):" << endl;
			cs->print();
		}
	}else{
		//si no anduvo, probamos con la estrategia clasica
		DEBUG('c', "Executing the classic strategy\n");
		CausalizationStrategy *cs_clasica = new CausalizationStrategy(mmo_class);
		AST_ClassList cl = newAST_ClassList();
		cs_clasica->causalize(mmo_class->name(), cl);
  		DEBUG('c', "Causalized Equations:\n");
  		MMO_EquationList causalEqs = mmo_class->getEquations();
  		MMO_EquationListIterator causalEqsIter;
  		foreach(causalEqsIter, causalEqs) {
    		DEBUG('c', "%s", current_element(causalEqsIter)->print().c_str());
  		}
	}
Пример #2
0
static void findEiffelTags (void)
{
	tokenInfo *const token = newToken ();

	while (findKeyword (token, KEYWORD_class))
		parseClass (token);
	deleteToken (token);
}
Пример #3
0
CObject *MfcArchive::readClass() {
	bool isCopyReturned;
	CObject *res = parseClass(&isCopyReturned);

	if (res && !isCopyReturned)
		res->load(*this);

	return res;
}
Пример #4
0
bool TypeInfo::parseString(const QString &str)
{
    QStringList fields = str.split(",,");

    if(fields.size() != 3) return false;

    class_ = parseClass(fields[0]);
    name_  = fields[1];
    type_  = fields[2];

    return true;
}
Пример #5
0
static void findEiffelTags (void)
{
    tokenInfo *const token = newToken ();
    exception_t exception;

    exception = (exception_t) (setjmp (Exception));
    while (exception == ExceptionNone)
    {
        findKeyword (token, KEYWORD_class);
        parseClass (token);
    }
    deleteToken (token);
}
Пример #6
0
static void scanFile(const QString& in)
      {
      QList<Prop> props;
      QList<Proc> procs;

      QRegExp re("@@ ([^\\n]*)");
      int gpos = 0;
      QString className;
      for (;;) {
            int rv = re.indexIn(in, gpos);
            if (rv == -1) {
                  if (!className.isEmpty())
                        parseClass(className, in.mid(gpos, in.size() - gpos));
                  break;
                  }
            int next = rv + re.matchedLength();
            if (gpos)
                  parseClass(className, in.mid(gpos, next-gpos));

            className = re.cap(1).simplified();
            gpos = next;
            }
      }
Пример #7
0
/// tokenize first, then parse with recursive descent
bool PSClass::parse(ifstream &in)
{
	// remove comments
	bool result=tokenize(in);
	// print tokens
	cout << "--------start of token--------" <<endl;
	cout << tokens.str() <<endl;
	cout << "---------end of token---------" <<endl;

	istringstream token(tokens.str());
	// parseClass
	token >> nextToken;
	result=result && parseClass(token);

	return result;
}
Пример #8
0
NFAUNode * WCPattern::parse(const bool inParen, const bool inOr, NFAUNode ** end)
{
	NFAUNode * start, *cur, *next = NULL;
	CMString t;
	int grc = groupCount++;
	bool inv, quo;
	bool ahead = 0, pos = 0, noncap = 0, indep = 0;
	unsigned long oldFlags = flags;

	if (inParen) {
		if (pattern[curInd] == '?') {
			++curInd;
			--groupCount;
			if (pattern[curInd] == ':')   { noncap = 1; ++curInd;     grc = --nonCapGroupCount; }
			else if (pattern[curInd] == '=')   { ++curInd;     ahead = 1;  pos = 1; }
			else if (pattern[curInd] == '!')   { ++curInd;     ahead = 1;  pos = 0; }
			else if (pattern.Mid(curInd, 2) == L"<=")  { curInd += 2;  return parseBehind(1, end); }
			else if (pattern.Mid(curInd, 2) == L"<!")  { curInd += 2;  return parseBehind(0, end); }
			else if (pattern[curInd] == '>')   { ++curInd;     indep = 1; }
			else {
				bool negate = false, done = false;
				while (!done) {
					if (curInd >= pattern.GetLength()) {
						raiseError();
						return NULL;
					}
					else if (negate) {
						switch (pattern[curInd]) {
						case 'i': flags &= ~WCPattern::CASE_INSENSITIVE;   break;
						case 'd': flags &= ~WCPattern::UNIX_LINE_MODE;     break;
						case 'm': flags &= ~WCPattern::MULTILINE_MATCHING; break;
						case 's': flags &= ~WCPattern::DOT_MATCHES_ALL;    break;
						case ':': done = true;                             break;
						case ')':
							++curInd;
							*end = registerNode(new NFALookBehindUNode(L"", true));
							return *end;
						case '-':
						default:
							raiseError();
							return NULL;
						}
					}
					else {
						switch (pattern[curInd]) {
						case 'i': flags |= WCPattern::CASE_INSENSITIVE;    break;
						case 'd': flags |= WCPattern::UNIX_LINE_MODE;      break;
						case 'm': flags |= WCPattern::MULTILINE_MATCHING;  break;
						case 's': flags |= WCPattern::DOT_MATCHES_ALL;     break;
						case ':': done = true;                             break;
						case '-': negate = true;                           break;
						case ')':
							++curInd;
							*end = registerNode(new NFALookBehindUNode(L"", true));
							return *end;
						default:
							raiseError();
							return NULL;
						}
					}
					++curInd;
				}
				noncap = 1;
				grc = --nonCapGroupCount;
			}

			if (noncap) cur = start = registerNode(new NFAGroupHeadUNode(grc));
			else        cur = start = registerNode(new NFASubStartUNode);
		}
		else cur = start = registerNode(new NFAGroupHeadUNode(grc));
	}
	else cur = start = registerNode(new NFASubStartUNode);

	while (curInd < pattern.GetLength()) {
		wchar_t ch = pattern[curInd++];

		next = NULL;
		if (error) return NULL;
		switch (ch) {
		case '^':
			if ((flags & WCPattern::MULTILINE_MATCHING) != 0) next = registerNode(new NFAStartOfLineUNode);
			else                                            next = registerNode(new NFAStartOfInputUNode);
			break;
		case '$':
			if ((flags & WCPattern::MULTILINE_MATCHING) != 0) next = registerNode(new NFAEndOfLineUNode);
			else                                            next = registerNode(new NFAEndOfInputUNode(0));
			break;
		case '|':
			--groupCount;
			cur->next = registerNode(new NFAAcceptUNode);
			cur = start = registerNode(new NFAOrUNode(start, parse(inParen, 1)));
			break;
		case '\\':
			if (curInd < pattern.GetLength()) {
				bool eoi = 0;
				switch (pattern[curInd]) {
				case '1':
				case '2':
				case '3':
				case '4':
				case '5':
				case '6':
				case '7':
				case '8':
				case '9': next = parseBackref(); break;
				case 'A': ++curInd; next = registerNode(new NFAStartOfInputUNode);     break;
				case 'B': ++curInd; next = registerNode(new NFAWordBoundaryUNode(0));  break;
				case 'b': ++curInd; next = registerNode(new NFAWordBoundaryUNode(1));  break;
				case 'G': ++curInd; next = registerNode(new NFAEndOfMatchUNode);       break;
				case 'Z': eoi = 1;
				case 'z': ++curInd; next = registerNode(new NFAEndOfInputUNode(eoi));  break;
				default:
					t = parseEscape(inv, quo);
					//printf("inv quo classes { %c %c %s }\n", inv ? 't' : 'f', quo ? 't' : 'f', t.c_str());
					if (!quo) {
						if (t.GetLength() > 1 || inv) {
							if ((flags & WCPattern::CASE_INSENSITIVE) != 0) next = registerNode(new NFACIClassUNode(t, inv));
							else                                            next = registerNode(new NFAClassUNode(t, inv));
						}
						else next = registerNode(new NFACharUNode(t[0]));
					}
					else next = parseQuote();
				}
			}
			else raiseError();
			break;
		case '[':
			if ((flags & WCPattern::CASE_INSENSITIVE) == 0) {
				NFAClassUNode * clazz = new NFAClassUNode();
				CMString s = parseClass();
				for (int i = 0; i < (int)s.GetLength(); ++i) clazz->vals[s[i]] = 1;
				next = registerNode(clazz);
			}
			else {
				NFACIClassUNode * clazz = new NFACIClassUNode();
				CMString s = parseClass();
				for (int i = 0; i < s.GetLength(); ++i) clazz->vals[to_lower(s[i])] = 1;
				next = registerNode(clazz);
			}
			break;
		case '.':
			{
				bool useN = 1, useR = 1;
				NFAClassUNode * clazz = new NFAClassUNode(1);
				if ((flags & WCPattern::UNIX_LINE_MODE) != 0) useR = 0;
				if ((flags & WCPattern::DOT_MATCHES_ALL) != 0) useN = useR = 0;
				if (useN) clazz->vals['\n'] = 1;
				if (useR) clazz->vals['\r'] = 1;
				next = registerNode(clazz);
			}
			break;
		case '(':
			{
				NFAUNode *end, *t1, *t2;
				t1 = parse(1, 0, &end);
				if (!t1) raiseError();
				else if (t1->isGroupHeadNode() && (t2 = quantifyGroup(t1, end, grc)) != NULL) {
					cur->next = t2;
					cur = t2->next;
				}
				else {
					cur->next = t1;
					cur = end;
				}
			}
			break;
		case ')':
			if (!inParen) raiseError();
			else if (inOr) {
				--curInd;
				cur = cur->next = registerNode(new NFAAcceptUNode);
				flags = oldFlags;
				return start;
			}
			else {
				if (ahead) {
					cur = cur->next = registerNode(new NFAAcceptUNode);
					flags = oldFlags;
					return *end = registerNode(new NFALookAheadUNode(start, pos));
				}
				else if (indep) {
					cur = cur->next = registerNode(new NFAAcceptUNode);
					flags = oldFlags;
					return *end = registerNode(new NFAPossessiveQuantifierUNode(this, start, 1, 1));
				}
				else { // capping or noncapping, it doesnt matter
					*end = cur = cur->next = registerNode(new NFAGroupTailUNode(grc));
					next = quantifyGroup(start, *end, grc);
					if (next) {
						start = next;
						*end = next->next;
					}
					flags = oldFlags;
					return start;
				}
			}
			break;
		case '{': // registered pattern
			cur->next = parseRegisteredWCPattern(&next);
			if (cur->next) cur = next;
			break;
		case '*':
		case '+':
		case '?':
			//    case '}':
			//    case ']':
			raiseError();
			break;
		default:
			if ((flags & WCPattern::CASE_INSENSITIVE) != 0) next = registerNode(new NFACICharUNode(ch));
			else                                          next = registerNode(new NFACharUNode(ch));
			break;
		}
		if (next) cur = cur->next = quantify(next);
	}
	if (inParen) raiseError();
	else {
		if (inOr) cur = cur->next = registerNode(new NFAAcceptUNode);
		if (end) *end = cur;
	}

	flags = oldFlags;
	if (error) return NULL;

	return start;
}
Пример #9
0
CMString WCPattern::parseClass()
{
	CMString t, ret;
	wchar_t ch, c1, c2;
	bool inv = 0, neg = 0, quo = 0;

	if (curInd < pattern.GetLength() && pattern[curInd] == '^') {
		++curInd;
		neg = 1;
	}

	while (curInd < pattern.GetLength() && pattern[curInd] != ']') {
		ch = pattern[curInd++];
		if (ch == '[') {
			t = parseClass();
			ret = classUnion(ret, t);
		}
		else if (ch == '&' && curInd < pattern.GetLength() && pattern[curInd] == '&') {
			if (pattern[++curInd] != '[') {
				raiseError();
				curInd = pattern.GetLength();
			}
			else {
				++curInd;
				t = parseClass();
				ret = classIntersect(ret, t);
			}
		}
		else if (ch == '\\') {
			t = parseEscape(inv, quo);
			if (quo) {
				raiseError();
				curInd = pattern.GetLength();
			}
			else if (inv || t.GetLength() > 1) { // cant be part of a range (a-z)
				if (inv) t = classNegate(t);
				ret = classUnion(ret, t);
			}
			else if (curInd < pattern.GetLength() && pattern[curInd] == '-') { // part of a range (a-z) 
				c1 = t[0];
				++curInd;
				if (curInd >= pattern.GetLength()) raiseError();
				else {
					c2 = pattern[curInd++];
					if (c2 == '\\') {
						t = parseEscape(inv, quo);
						if (quo) {
							raiseError();
							curInd = pattern.GetLength();
						}
						else if (inv || t.GetLength() > 1) raiseError();
						else ret = classUnion(ret, classCreateRange(c1, c2));
					}
					else if (c2 == '[' || c2 == ']' || c2 == '-' || c2 == '&') {
						raiseError();
						curInd = pattern.GetLength();
					}
					else ret = classUnion(ret, classCreateRange(c1, c2));
				}
			}
			else ret = classUnion(ret, t);
		}
		else if (curInd < pattern.GetLength() && pattern[curInd] == '-') {
			c1 = ch;
			++curInd;
			if (curInd >= pattern.GetLength()) raiseError();
			else {
				c2 = pattern[curInd++];
				if (c2 == '\\') {
					t = parseEscape(inv, quo);
					if (quo) {
						raiseError();
						curInd = pattern.GetLength();
					}
					else if (inv || t.GetLength() > 1) raiseError();
					else ret = classUnion(ret, classCreateRange(c1, c2));
				}
				else if (c2 == '[' || c2 == ']' || c2 == '-' || c2 == '&') {
					raiseError();
					curInd = pattern.GetLength();
				}
				else ret = classUnion(ret, classCreateRange(c1, c2));
			}
		}
		else ret.AppendChar(ch);
	}

	if (curInd >= pattern.GetLength() || pattern[curInd] != ']') {
		raiseError();
		ret = L"";
	}
	else {
		++curInd;
		if (neg) ret = classNegate(ret);
	}
	return ret;
}
Пример #10
0
bool ClassParser::parseHeader(const char *strHeader, const char *strHeaderFullFilePath)
{
    unsigned int i;
    unsigned int iCount = strlen(strHeader);
    int iSquareBracketsOfClassIndex = 0;
    unsigned int iPosition;
    bool bIsParsed;

    EParseAction eAction = PARSE_ACTION_NOTHING;
    EParseActionSecondary eSecondaryAction = PARSE_ACTION_SECONDARY_NOTHING;

    for (i=0; i<iCount; i++) {

        switch (eAction) {

        case PARSE_ACTION_NOTHING:
            if (strncmp(strHeader+i, "/*", 2) == 0) {
                eAction = PARSE_ACTION_COMMENTS_OUT_MULTI_LINE;
                i++;

                if (ClassParserFind::findToNextChar(strHeader+i+1, "*/", &iPosition)) {

                    i+=iPosition+2;
                    eAction = PARSE_ACTION_NOTHING;
                }
            }
            else if (strncmp(strHeader+i, "//", 2) == 0) {
                eAction = PARSE_ACTION_COMMENTS_OUT_SINGLE_LINE;
                i++;
                if (ClassParserFind::findToNextChar(strHeader+i+1, "\n", &iPosition)) {

                    i+=iPosition+1;
                    eAction = PARSE_ACTION_NOTHING;
                }
            }
            else {
                if (eSecondaryAction != PARSE_ACTION_SECONDARY_NOTHING &&
                        eSecondaryAction != PARSE_ACTION_SECONDARY_IN_CLASS_BEGIN &&
                        eSecondaryAction != PARSE_ACTION_SECONDARY_IN_GOT_CLASS_NAME)
                {

                    if (strHeader[i] == '{') {

                        iSquareBracketsOfClassIndex++;
                    }
                    else if (strHeader[i] == '}') {

                        iSquareBracketsOfClassIndex--;
                        if (iSquareBracketsOfClassIndex == 0) {
                            eSecondaryAction = PARSE_ACTION_SECONDARY_NOTHING;
                            if (ClassParserFind::findToNextChar(strHeader+i, ";", &iPosition)) {

                                i+=iPosition;
                            }
                        }
                    }
                }

                switch (eSecondaryAction) {

                case PARSE_ACTION_SECONDARY_NOTHING:
                    if (strncmp(strHeader+i, "class", 5) == 0) {
                        ClassParserInformation s;
                        s.m_strClassType = "class";
                        s.m_strFromHeaderFile = strHeaderFullFilePath;
                        m_listClassInformation.append(s);
                        i += 5;
                        i += parseClass(strHeader+i, m_listClassInformation.size()-1);
                    }
                    else if (strncmp(strHeader+i, "struct", 6) == 0) {
                        ClassParserInformation s;
                        s.m_strClassType = "struct";
                        s.m_strFromHeaderFile = strHeaderFullFilePath;
                        m_listClassInformation.append(s);
                        i += 6;
                        i += parseClass(strHeader+i, m_listClassInformation.size()-1);
                    }
                    else if (strncmp(strHeader+i, "enum", 4) == 0) {
                        ClassParserInformation s;
                        s.m_strClassType = "enum";
                        s.m_strFromHeaderFile = strHeaderFullFilePath;
                        m_listClassInformation.append(s);
                        i += 4;
                        i += parseEnum(strHeader+i, m_listClassInformation.size()-1);
                    }
                    else if (strncmp(strHeader+i, "typedef", 7) == 0) {
                        ClassParserInformation s;
                        s.m_strClassType = "typedef";
                        s.m_strFromHeaderFile = strHeaderFullFilePath;
                        m_listClassInformation.append(s);
                        i += 7;
                        i += parseTypedef(strHeader+i, m_listClassInformation.size()-1);
                    }
                    else if (strncmp(strHeader+i, "template", 8) == 0) {
                        ClassParserInformation s;
                        s.m_strClassType = "template";
                        s.m_strFromHeaderFile = strHeaderFullFilePath;
                        i += 8;
                        i += ClassParserFind::parseTemplate(strHeader+i, &s);
                        m_listClassInformation.append(s);
                    }
                    else if (strncmp(strHeader+i, "union", 5) == 0) {
                        ClassParserInformation s;
                        s.m_strClassType = "union";
                        s.m_strFromHeaderFile = strHeaderFullFilePath;
                        i += 5;
                        i += ClassParserFind::parseTemplate(strHeader+i, &s);
                        m_listClassInformation.append(s);
                    }
                    else if (strncmp(strHeader+i, "#define", 7) == 0) {
                        i += 7;
                        i += ClassParserFind::parseDefine(strHeader+i, this);
                    }
                    else if (strncmp(strHeader+i, "#include", 8) == 0) {

                        bool bInPublicIncludeFolders;
                        QString strInclude = ClassParserFind::getIncludeHeader(strHeader+i+8, &iPosition, &bInPublicIncludeFolders);
                        if (strInclude.length() != 0) {

                            i+=8+iPosition;
                            ClassParserIncludeHeaderInformation s;
                            s.m_bInPublicIncludeFolders = bInPublicIncludeFolders;
                            s.m_strIncludeHeader = strInclude;
                            s.m_strIncludeHeaderWithFullFilePath = findFullFilePathForHeaderInformation(&s, strHeaderFullFilePath);
                            bIsParsed = isIncludeHeaderParsed(&s);
                            m_listIncludeHeader.append(s);

                            if (bIsParsed == false && s.m_strIncludeHeaderWithFullFilePath.length() != 0) {

                                QByteArray ba = s.m_strIncludeHeaderWithFullFilePath.toLatin1();
                                parse(ba.data());
                            }
                        }
                    }
                    else if (ClassParserFind::skipThisLine(strHeader, i, &iPosition) ) {

                        i=iPosition;
                    }
                    else  {

                        i+= ClassParserFind::parsePossibleFunctionFromThisLine(strHeader+i);
                    }

                    break;

                default:
                    break;
                }
            }

            break;
        case PARSE_ACTION_COMMENTS_OUT_MULTI_LINE:
            if (strncmp(strHeader+i, "*/", 2) == 0) {
                eAction = PARSE_ACTION_NOTHING;
                i++;
            }
            break;
        case PARSE_ACTION_COMMENTS_OUT_SINGLE_LINE:
            if (strncmp(strHeader+i, "\n", 1) == 0) {
                eAction = PARSE_ACTION_NOTHING;
                i++;
            }
            break;
        }
    }

    return false;
}
Пример #11
0
unsigned int ClassParser::parseClass(const char *strHeader, int iClassIndex) {

    unsigned int i;
    unsigned int iCount = strlen(strHeader);
    unsigned int iPreviousImportantActionIndex = 0;
    int iSquareBracketsIndex = 0;
    int iSquareBracketsOfClassIndex = 0;
    int iBracketsIndex = 0;
    unsigned int iPosition;
    unsigned int iPositionAdd;
    int iMacroIndex;
    bool bInTheQuotes = false;
    EParseAction eAction = PARSE_ACTION_NOTHING;
    EParseActionSecondary eSecondaryAction = PARSE_ACTION_SECONDARY_IN_CLASS_BEGIN;
    EClassParserMemberType eFunctionType = FUNCTION_TYPE_PRIVATE;
    EClassParserMemberType eMemberType;

    for (i=0; i<iCount; i++) {
        switch (eAction) {

        case PARSE_ACTION_NOTHING:
            if (bInTheQuotes == false && strncmp(strHeader+i, "/*", 2) == 0) {
                eAction = PARSE_ACTION_COMMENTS_OUT_MULTI_LINE;
                i++;

                if (ClassParserFind::findToNextChar(strHeader+i+1, "*/", &iPosition)) {

                    i+=iPosition+2;
                    eAction = PARSE_ACTION_NOTHING;
                }
            }
            else if (bInTheQuotes == false && strncmp(strHeader+i, "//", 2) == 0) {
                eAction = PARSE_ACTION_COMMENTS_OUT_SINGLE_LINE;
                i++;
                if (ClassParserFind::findToNextChar(strHeader+i+1, "\n", &iPosition)) {

                    i+=iPosition+1;
                    eAction = PARSE_ACTION_NOTHING;
                }
            }
            else {
                if (eSecondaryAction != PARSE_ACTION_SECONDARY_NOTHING &&
                        eSecondaryAction != PARSE_ACTION_SECONDARY_IN_CLASS_BEGIN &&
                        eSecondaryAction != PARSE_ACTION_SECONDARY_IN_GOT_CLASS_NAME)
                {

                    if (strHeader[i] == '{') {

                        iSquareBracketsOfClassIndex++;
                    }
                    else if (strHeader[i] == '}') {

                        iSquareBracketsOfClassIndex--;
                        if (iSquareBracketsOfClassIndex == 0) {
                            eSecondaryAction = PARSE_ACTION_SECONDARY_NOTHING;
                            if (ClassParserFind::findToNextChar(strHeader+i, ";", &iPosition)) {

                                i+=iPosition;
                                return i;
                            }
                        }
                    }
                }

                if (bInTheQuotes == false) {

                    if (strHeader[i] == '\"') {

                        bInTheQuotes = true;
                        continue;
                    }
                }
                else {

                    if (i == 0 && strHeader[i] == '\"') {

                        bInTheQuotes = false;
                        continue;
                    }
                    else if (i != 0 && strHeader[i-1] != '\\' && strHeader[i] == '\"') {

                        bInTheQuotes = false;
                        continue;
                    }
                }

                if (bInTheQuotes == false) {

                    switch (eSecondaryAction) {

                    case PARSE_ACTION_SECONDARY_NOTHING:
                        break;

                    case PARSE_ACTION_SECONDARY_IN_CLASS_BEGIN:

                        eSecondaryAction = PARSE_ACTION_SECONDARY_IN_GOT_CLASS_NAME;
                        iPreviousImportantActionIndex = i;

                        i += ClassParserFind::parseClassName(strHeader+i, &m_listClassInformation[iClassIndex]);
                        if (strHeader[i] == ';') {
                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            return i;
                        }
                        else {
                            if (strHeader[i] == '{') {

                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                                eFunctionType = FUNCTION_TYPE_PRIVATE;
                                iSquareBracketsOfClassIndex++;
                            }
                        }
                        break;

                    case PARSE_ACTION_SECONDARY_IN_GOT_CLASS_NAME:

                        if (strHeader[i] == '{') {

                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            eFunctionType = FUNCTION_TYPE_PRIVATE;
                            iSquareBracketsOfClassIndex++;
                        }
                        break;

                    case PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING:
                    case PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FIRST_HAND_INFO:
                    case PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_BRACETS_OUT:

                        if ( !ClassParserFind::isThisEqualToSpace(strHeader[i]) &&
                                iSquareBracketsIndex == 0 && iBracketsIndex == 0 &&
                                strHeader[i] != '(' && strHeader[i] != '{' &&
                                strHeader[i] != ';' &&
                                strHeader[i] != ')' && strHeader[i] != '}' && strHeader[i] != '=') {

                            if (eSecondaryAction == PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_BRACETS_OUT) {

                                if (strncmp(strHeader+i, "const", 5) == 0) {

                                    i+=4;
                                    continue;
                                }
                                else if (iSquareBracketsIndex == 0 && iBracketsIndex == 0) {

                                    SClassParserPossibleMacroWithoutKnownledge s;
                                    s.m_pType = eFunctionType;
                                    s.m_strMacroLine = ClassParserFind::getStringBetween(strHeader, iPreviousImportantActionIndex, i) ;
                                    m_listClassInformation[iClassIndex].m_listPossibleMacroWithoutKnownledge.append( s );
                                }
                            }

                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            EClassParserClassMainType eClassType = ClassParserFind::isStartWithClassType(strHeader+i, &iPosition);

                            if (eClassType == CLASS_MAIN_TYPE_CLASS) {

                                ClassParserInformation s;
                                s.m_strClassType = "class";
                                s.m_iParentClassIndex = iClassIndex;
                                s.m_strFromHeaderFile = m_listClassInformation[iClassIndex].m_strFromHeaderFile;
                                m_listClassInformation.append(s);
                                i += iPosition;
                                i += parseClass(strHeader+i, m_listClassInformation.size()-1);
                            }
                            else if (eClassType == CLASS_MAIN_TYPE_STRUCT) {

                                ClassParserInformation s;
                                s.m_strClassType = "struct";
                                s.m_iParentClassIndex = iClassIndex;
                                s.m_strFromHeaderFile = m_listClassInformation[iClassIndex].m_strFromHeaderFile;
                                m_listClassInformation.append(s);
                                i += iPosition;
                                i += parseClass(strHeader+i, m_listClassInformation.size()-1);
                            }
                            else if (eClassType == CLASS_MAIN_TYPE_ENUM) {

                                ClassParserInformation s;
                                s.m_strClassType = "enum";
                                s.m_iParentClassIndex = iClassIndex;
                                s.m_strFromHeaderFile = m_listClassInformation[iClassIndex].m_strFromHeaderFile;
                                m_listClassInformation.append(s);
                                i += iPosition;
                                i += parseEnum(strHeader+i, m_listClassInformation.size()-1);
                            }
                            else if (eClassType == CLASS_MAIN_TYPE_TYPEDEF) {

                                ClassParserInformation s;
                                s.m_strClassType = "typedef";
                                s.m_iParentClassIndex = iClassIndex;
                                s.m_strFromHeaderFile = m_listClassInformation[iClassIndex].m_strFromHeaderFile;
                                m_listClassInformation.append(s);
                                i += iPosition;
                                i += parseTypedef(strHeader+i, m_listClassInformation.size()-1);
                            }
                            else if (eClassType == CLASS_MAIN_TYPE_TEMPLATE) {

                                ClassParserInformation s;
                                s.m_strClassType = "template";
                                s.m_iParentClassIndex = iClassIndex;
                                s.m_strFromHeaderFile = m_listClassInformation[iClassIndex].m_strFromHeaderFile;
                                i += iPosition;
                                i += ClassParserFind::parseTemplate(strHeader+i, &s);
                                m_listClassInformation.append(s);
                            }
                            else if (eClassType == CLASS_MAIN_TYPE_UNION) {

                                ClassParserInformation s;
                                s.m_strClassType = "union";
                                s.m_iParentClassIndex = iClassIndex;
                                s.m_strFromHeaderFile = m_listClassInformation[iClassIndex].m_strFromHeaderFile;
                                i += iPosition;
                                i += ClassParserFind::parseTemplate(strHeader+i, &s);
                                m_listClassInformation.append(s);
                            }
                            else if (ClassParserFind::skipThisLine(strHeader, i, &iPosition) ) {

                                i=iPosition;
                            }
                            else if (isStartWithMacroBeginForFunction(strHeader+i, &iMacroIndex)) {

                                ClassParserFind::getFunctionWithMacroBegin(strHeader, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPosition, m_listMacroBeginForMember[iMacroIndex]);
                                i += iPosition;
                            }
                            else {

                                eMemberType = ClassParserFind::isStartWithMemberType(strHeader+i, &iPosition);
                                if (eMemberType != FUNCTION_TYPE_NONE) {

                                    i+=iPosition;
                                    eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FIRST_HAND_INFO;
                                    eFunctionType = eMemberType;
                                }
                                else {

                                    eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_OR_DATATYPE;
                                    iPreviousImportantActionIndex = i;
                                }
                            }
                        }
                        else if (eSecondaryAction == PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_BRACETS_OUT) {

                            if (strHeader[i] == '{' ) {

                                iSquareBracketsIndex = 1;
                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_INLINE;
                            }
                            else if (strHeader[i] == ';' ) {

                                // This call creates function from
                                // emit foo(); in inline function.
                                // Also Q_OBJECT handled incorrectly.
                                ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                                i+=iPositionAdd;
                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            }
                            else if (strHeader[i] == '=' && iBracketsIndex == 0 && iSquareBracketsIndex == 0) {

                                ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                                i+=iPositionAdd;
                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            }
                        }
                        break;
                    case PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_OR_DATATYPE:
                        if (strHeader[i] == ';') {

                            if (iSquareBracketsIndex == 0 && iBracketsIndex == 0) {

                                ClassParserFind::getDataTypeBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex]);
                            }
                            else {


                                ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                                i+=iPositionAdd;
                            }
                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                        }
                        else if (strHeader[i] == '(' ) {

                            iBracketsIndex++;
                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_BRACETS_IN;
                        }
                        break;
                    case PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_BRACETS_IN:
                        if (strHeader[i] == ';' ) {

                            ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                            i+=iPositionAdd;
                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                        }
                        else if (strHeader[i] == '(' ) {

                            iBracketsIndex++;
                        }
                        else if (strHeader[i] == ')' ) {

                            iBracketsIndex--;
                            if (iBracketsIndex == 0) {

                                char c = ClassParserFind::findToNextNextValidNonSpaceChar(strHeader+i+1, &iPosition);

                                if (c == '(') { // function? still continues

                                    i += iPosition;
                                    iBracketsIndex++;
                                }
                                else {

                                    eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_BRACETS_OUT;
                                }
                            }
                        }
                        else if (strHeader[i] == '=' && iBracketsIndex == 0 && iSquareBracketsIndex == 0) {

                            ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                            i+=iPositionAdd;
                            eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                        }
                        break;

                    case PARSE_ACTION_SECONDARY_IN_THE_CLASS_GETTING_FUNCTION_INLINE:

                        if (strHeader[i] == '{' ) {

                            iSquareBracketsIndex++;
                        }
                        else if (strHeader[i] == '}' ) {

                            iSquareBracketsIndex--;
                            if (iSquareBracketsIndex==0) {

                                ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                                i+=iPositionAdd;
                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            }

                        }
                        else if (strHeader[i] == ';' ) {

                            if (iSquareBracketsIndex==0) {

                                ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                                i+=iPositionAdd;
                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            }
                        }
                        else if (strHeader[i] == '=') {

                            if (iSquareBracketsIndex == 0) {

                                ClassParserFind::getFunctionBetween(strHeader, iPreviousImportantActionIndex, i, eFunctionType, &m_listClassInformation[iClassIndex], &iPositionAdd, "");
                                i+=iPositionAdd;
                                eSecondaryAction = PARSE_ACTION_SECONDARY_IN_THE_CLASS_NOTHING;
                            }
                        }
                        break;
                    }
                }
            }

            break;
        case PARSE_ACTION_COMMENTS_OUT_MULTI_LINE:
            if (strncmp(strHeader+i, "*/", 2) == 0) {
                eAction = PARSE_ACTION_NOTHING;
                i++;
            }
            break;
        case PARSE_ACTION_COMMENTS_OUT_SINGLE_LINE:
            if (strncmp(strHeader+i, "\n", 1) == 0) {
                eAction = PARSE_ACTION_NOTHING;
                i++;
            }
            break;
        }
    }

    return i;
}
Пример #12
0
void PackageParser::parse() {
    while (stream_.hasMoreTokens()) {
        auto documentation = parseDocumentationToken();
        
        auto exported = Attribute<E_EARTH_GLOBE_EUROPE_AFRICA>().parse(&stream_);
        auto theToken = stream_.consumeToken(IDENTIFIER);
        switch (theToken.value[0]) {
            case E_PACKAGE: {
                exported.disallow();
                
                auto nameToken = stream_.consumeToken(VARIABLE);
                auto namespaceToken = stream_.consumeToken(IDENTIFIER);
                
                auto name = nameToken.value.utf8CString();
                package_->loadPackage(name, namespaceToken.value[0], theToken);
                
                continue;
            }
            case E_CROCODILE:
                parseProtocol(documentation, theToken, exported.set());
                continue;
            case E_TURKEY:
                parseEnum(documentation, exported.set());
                continue;
            case E_RADIO:
                exported.disallow();
                package_->setRequiresBinary();
                if (strcmp(package_->name(), "_") == 0) {
                    throw CompilerErrorException(theToken, "You may not set 📻 for the _ package.");
                }
                continue;
            case E_CRYSTAL_BALL: {
                exported.disallow();
                if (package_->validVersion()) {
                    throw CompilerErrorException(theToken, "Package version already declared.");
                }
                
                auto major = stream_.consumeToken(INTEGER).value.utf8CString();
                auto minor = stream_.consumeToken(INTEGER).value.utf8CString();
                
                uint16_t majori = strtol(major, nullptr, 0);
                uint16_t minori = strtol(minor, nullptr, 0);
                
                delete [] major;
                delete [] minor;
                
                package_->setPackageVersion(PackageVersion(majori, minori));
                if (!package_->validVersion()) {
                    throw CompilerErrorException(theToken, "The provided package version is not valid.");
                }
                
                continue;
            }
            case E_WALE: {
                exported.disallow();
                EmojicodeChar className, enamespace;
                bool optional;
                auto &classNameToken = parseTypeName(&className, &enamespace, &optional);
                
                if (optional) {
                    throw CompilerErrorException(classNameToken, "Optional types are not extendable.");
                }
                
                Type type = typeNothingness;
                
                if (!package_->fetchRawType(className, enamespace, optional, theToken, &type)) {
                    throw CompilerErrorException(classNameToken, "Class does not exist.");
                }
                if (type.type() != TT_CLASS) {
                    throw CompilerErrorException(classNameToken, "Only classes are extendable.");
                }
                
                // Native extensions are allowed if the class was defined in this package.
                parseClassBody(type.eclass, nullptr, type.eclass->package() == package_);
                
                continue;
            }
            case E_RABBIT:
                parseClass(documentation, theToken, exported.set());
                continue;
            case E_SCROLL: {
                exported.disallow();
                auto pathString = stream_.consumeToken(STRING);
                auto relativePath = pathString.position().file;
                auto fileString = pathString.value.utf8CString();
                
                char *str = fileString;
                const char *lastSlash = strrchr(relativePath, '/');
                if (lastSlash != nullptr) {
                    const char *directory = strndup(relativePath, lastSlash - relativePath);
                    asprintf(&str, "%s/%s", directory, fileString);
                    delete [] fileString;
                    delete [] directory;
                }
                
                PackageParser(package_, lex(str)).parse();
                
                delete [] str;
                continue;
            }
            default:
                ecCharToCharStack(theToken.value[0], f);
                throw CompilerErrorException(theToken, "Unexpected identifier %s", f);
                break;
        }
    }
}