/****************************************************************************
**
** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the Qt Mobility Components.
**
** $QT_BEGIN_LICENSE:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "parsemanager.h"
#include "cplusplus/CppDocument.h"
#include "./parser/src/shared/cplusplus/Control.h"
#include "TranslationUnit.h"
#include "AST.h"
#include "Symbols.h"
#include <QDebug>
#include "Name.h"
#include "cpptools/cppmodelmanager.h"
#include <QTextStream>
using namespace CppTools;
using namespace CppTools::Internal;
using namespace CPlusPlus;
//<------------------------------------------------------- Compare function for the internal structures
/**********************************
Compares function with function
with return type, function name
and their arguments and arguments
types.
**********************************/
bool FUNCTIONITEM::isEqualTo(FUNCTIONITEM *cpfct, bool ignoreName/* = true*/)
{
if(ignoreName)
return function->isEqualTo(cpfct->function, true);
return function->isEqualTo(cpfct->function);
}
/*****************************************************************
Compares two property regarding
of their function definition,
type definition, function arguments
and function types.
Q_PROPERTY( ConnectionState state READ state NOTIFY stateChanged);
******************************************************************/
bool PROPERTYITEM::isEqualTo(PROPERTYITEM *cpppt)
{
QString thistype = this->trlUnit->spell(this->ast->type_token);
QString cppttype = cpppt->trlUnit->spell(cpppt->ast->type_token);
if(thistype != cppttype)
return false;
QString thistypename = this->trlUnit->spell(this->ast->type_name_token);
QString cppttypename = cpppt->trlUnit->spell(cpppt->ast->type_name_token);
if(thistypename != cppttypename)
return false;
if(this->readdefined != cpppt->readdefined)
return false;
if(this->writedefined != cpppt->writedefined)
return false;
if(this->resetdefined != cpppt->resetdefined)
return false;
if(this->notifydefined != cpppt->notifydefined)
return false;
//check for read function
if(this->readdefined){
if(!this->readFct || !cpppt->readFct)
return false;
if(!this->readFct->isEqualTo(cpppt->readFct))
return false;
}
//check for write function
if(this->writedefined){
if(!this->writeFct || !cpppt->writeFct)
return false;
if(!this->writeFct->isEqualTo(cpppt->writeFct))
return false;
}
//check for reset function
if(this->resetdefined){
if(!this->resetFct || !cpppt->resetFct)
return false;
if(!this->resetFct->isEqualTo(cpppt->resetFct))
return false;
}
//check for notify function
if(this->notifydefined){
if(!this->notifyFct || !cpppt->notifyFct)
return false;
if(!this->notifyFct->isEqualTo(cpppt->notifyFct))
return false;
}
return true;
}
/*****************************************************************
Compares two enums regarding
of their values created by the getEnumValueStringList function.
*****************************************************************/
bool QENUMITEM::isEqualTo(QENUMITEM *cpenum)
{
if(this->values.count() != cpenum->values.count())
return false;
foreach(QString str, this->values){
if(!cpenum->values.contains(str))
return false;
}
return true;
}
/*****************************************************************
Compares two flags regarding
of their enum definitions and their
values created by the getEnumValueStringList function.
*****************************************************************/
bool QFLAGITEM::isEqualTo(QFLAGITEM *cpflag)
{
if(this->enumvalues.count() != cpflag->enumvalues.count())
return false;
foreach(QString str, this->enumvalues){
if(!cpflag->enumvalues.contains(str))
return false;
}
return true;
}
ParseManager::ParseManager()
: pCppPreprocessor(0)
{
}
ParseManager::~ParseManager()
{
if(pCppPreprocessor)
delete pCppPreprocessor;
if(::m_resultFile){
::m_resultFile->close();
delete ::m_resultFile;
::m_resultFile = 0;
}
}
/**************************************
Function for setting the include
Paths
**************************************/
void ParseManager::setIncludePath(const QStringList &includePath)
{
m_includePaths = includePath;
}
/**************************************
public Function that starts the parsing
all of the files in the sourceFiles
string list.
**************************************/
void ParseManager::parse(const QStringList &sourceFiles)
{
m_errormsgs.clear();
if(pCppPreprocessor){
delete pCppPreprocessor;
pCppPreprocessor = 0;
}
if (! sourceFiles.isEmpty()) {
m_strHeaderFile = sourceFiles[0];
pCppPreprocessor = new CppTools::Internal::CppPreprocessor(QPointer<CPlusPlus::ParseManager>(this));
pCppPreprocessor->setIncludePaths(m_includePaths);
pCppPreprocessor->setFrameworkPaths(m_frameworkPaths);
parse(pCppPreprocessor, sourceFiles);
}
}
/*********************************************
private function that prepare the filelist
to parse and starts the parser.
*********************************************/
void ParseManager::parse(CppTools::Internal::CppPreprocessor *preproc,
const QStringList &files)
{
if (files.isEmpty())
return;
//check if file is C++ header file
QStringList headers;
foreach (const QString &file, files) {
const QFileInfo fileInfo(file);
QString ext = fileInfo.suffix();
if (ext.toLower() == "h")
headers.append(file);
}
foreach (const QString &file, files) {
preproc->snapshot.remove(file);
}
preproc->setTodo(headers);
QString conf = QLatin1String("<configuration>");
preproc->run(conf);
for (int i = 0; i < headers.size(); ++i) {
QString fileName = headers.at(i);
preproc->run(fileName);
}
}
//This function creates a class list for each class and its base classes in
//the header file that needs to be checked.
//e.g.
// Cl1 Cl2
// __|__ __|__
// | | | |
// Cl11 Cl12 Cl21 Cl22
//
//==> list[0] = {Cl1, Cl11, Cl12}
// list[1] = {Cl2, Cl21, Cl22}
QList<CLASSTREE*> ParseManager::CreateClassLists(bool isInterfaceHeader)
{
QList<CLASSTREE*>ret;
QList<CLASSLISTITEM*> classlist;
QList<CLASSLISTITEM*> allclasslist;
Trace("Following classes scaned for header file: " + m_strHeaderFile);
//Iteration over all parsed documents
if(getPreProcessor()){
for (Snapshot::const_iterator it = getPreProcessor()->snapshot.begin()
; it != getPreProcessor()->snapshot.end(); ++it)
{
Document::Ptr doc = (*it);
if(doc){
QFileInfo fileinf(doc->fileName());
QFileInfo fileinf1(m_strHeaderFile);
//Get the Translated unit
Control* ctrl = doc->control();
TranslationUnit* trlUnit = ctrl->translationUnit();
AST* pAst = trlUnit->ast();
TranslationUnitAST *ptrAst = 0;
if(pAst && (ptrAst = pAst->asTranslationUnit())){
//iteration over all translated declaration in this document
for (DeclarationListAST *pDecllist = ptrAst->declaration_list; pDecllist; pDecllist = pDecllist->next) {
if(pDecllist->value){
SimpleDeclarationAST *pSimpleDec = pDecllist->value->asSimpleDeclaration();
if(pSimpleDec){
//Iteration over class specifier
for (SpecifierListAST *pSimpleDecDecllist = pSimpleDec->decl_specifier_list; pSimpleDecDecllist; pSimpleDecDecllist = pSimpleDecDecllist->next) {
ClassSpecifierAST * pclassspec = pSimpleDecDecllist->value->asClassSpecifier();
if(pclassspec){
CLASSLISTITEM* item = new CLASSLISTITEM();
item->classspec = pclassspec;
item->trlUnit = trlUnit;
allclasslist.push_back(item);
QString classname = item->trlUnit->spell(item->classspec->name->firstToken());
Trace("- " + classname + " class scaned");
//We found a class that is defined in the header file that needs to be checked
if(fileinf.fileName().toLower() == fileinf1.fileName().toLower()){
CLASSTREE* cltree = new CLASSTREE();
cltree->highestlevelclass = item;
cltree->classlist.push_back(item);
ret.push_back(cltree);
}
}
}
}
}
}
}
}
}
}
//after we search for the classes we need to search for the baseclasses
Trace("Following classes found in Header file: " + m_strHeaderFile);
foreach(CLASSTREE *cltree, ret){
QString classname = cltree->highestlevelclass->trlUnit->spell(cltree->highestlevelclass->classspec->name->firstToken());
Trace("- " + classname + " class found");
QList<CLASSLISTITEM*> baseclasslist;
getBaseClasses(cltree->highestlevelclass, baseclasslist, allclasslist, 0, isInterfaceHeader);
cltree->classlist.append(baseclasslist);
}
return ret;
}
/********************************************
Gets all the baseclass from a class and
add those base classes into the baseclasslist
********************************************/
void ParseManager::getBaseClasses(const CLASSLISTITEM* pclass
, QList<CLASSLISTITEM*> &baseclasslist
, const QList<CLASSLISTITEM*> &allclasslist
, int level
, bool isInterfaceHeader)
{
//iteration over the base_clause_list of the current class
QString levelmarker = " ";
for(int i = 0; i < level; i++)
levelmarker += " ";
levelmarker += "|- ";
QList<CLASSLISTITEM*>child;
for(BaseSpecifierListAST *pBaseSpecList = pclass->classspec->base_clause_list; pBaseSpecList; pBaseSpecList = pBaseSpecList->next)
{
BaseSpecifierAST *pBaseSpec = pBaseSpecList->value;
bool found = false;
foreach(CLASSLISTITEM* pclspec, allclasslist)
{
if(pclspec->classspec->symbol->name()
&& pBaseSpec->symbol->name()
&& pclspec->classspec->symbol->name()->isEqualTo(pBaseSpec->symbol->name()))
{
child.push_back(pclspec);
baseclasslist.push_back(pclspec);
QString classname = pclspec->trlUnit->spell(pclspec->classspec->name->firstToken());
Trace(levelmarker + classname + " class found");
found = true;
break;
}
}
if(!found && pBaseSpec->name){
QString classname = pclass->trlUnit->spell(pBaseSpec->name->firstToken());
if(isInterfaceHeader)
Trace(levelmarker + classname + " class not found! Interface classes should not be inherited from Qt Objects!");
else
Trace(levelmarker + classname + " class not found!");
}
}
//call the function recursive because all the basclasses can have other base classes
foreach(CLASSLISTITEM* pchclass, child){
getBaseClasses(pchclass, baseclasslist, allclasslist, ++level, isInterfaceHeader);
}
}
/**************************************************
This function finds and creates all Elements wich
are significant for MetaDatas.
Those element will be added in the aparameter
lists.
**************************************************/
void ParseManager::getElements(QList<FUNCTIONITEM*> &functionlist
, QList<PROPERTYITEM*> &propertylist
, QList<QENUMITEM*> &qenumlist
, QList<ENUMITEM*> &enumlist
, QList<QFLAGITEM*> &qflaglist
, QList<QDECLAREFLAGSITEM*> &qdeclareflaglist
, const QList<CLASSLISTITEM*> classitems
, const CLASSLISTITEM* highestlevelclass)
{
foreach(CLASSLISTITEM* classitem, classitems){
QString classname = "";
if(classitem->classspec->name)
classname = classitem->trlUnit->spell(classitem->classspec->name->firstToken());
for (DeclarationListAST *pmemberlist = classitem->classspec->member_specifier_list; pmemberlist; pmemberlist = pmemberlist->next) {
/**********
Functions
**********/
FunctionDefinitionAST *pfctdef = pmemberlist->value->asFunctionDefinition();
if(pfctdef){
FUNCTIONITEM* item = new FUNCTIONITEM();
item->trlUnit = classitem->trlUnit;
item->function = pfctdef->symbol;
item->classAst = classitem->classspec;
item->highestlevelclass = highestlevelclass;
functionlist.push_back(item);
if(isMetaObjFunction(item))
Trace(" - " + getTraceFuntionString(item, classname) + " found");
}
SimpleDeclarationAST *pdecl = pmemberlist->value->asSimpleDeclaration();
if(pdecl){
for(List<Declaration*>* decllist = pdecl->symbols; decllist; decllist = decllist->next)
{
Function* pfct = decllist->value->type()->asFunctionType();
if(pfct){
FUNCTIONITEM* item = new FUNCTIONITEM();
item->trlUnit = classitem->trlUnit;
item->function = pfct;
item->classAst = classitem->classspec;
item->highestlevelclass = highestlevelclass;
functionlist.push_back(item);
if(isMetaObjFunction(item))
Trace(" - " + getTraceFuntionString(item, classname) + " found");
}
}
/******
enum
******/
for(List<SpecifierAST*>* decllist = pdecl->decl_specifier_list; decllist; decllist = decllist->next)
{
EnumSpecifierAST * penum = decllist->value->asEnumSpecifier();
if(penum){
ENUMITEM* item = new ENUMITEM();
item->ast = penum;
item->highestlevelclass = highestlevelclass;
item->trlUnit = classitem->trlUnit;
enumlist.push_back(item);
}
}
}
else{
/**********
Q_PROPERTY
**********/
QPropertyDeclarationAST *ppdecl = pmemberlist->value->asQPropertyDeclarationAST();
if(ppdecl){
PROPERTYITEM* item = new PROPERTYITEM();
item->ast = ppdecl;
item->highestlevelclass = highestlevelclass;
item->trlUnit = classitem->trlUnit;
item->readdefined = (ppdecl->read_token > 0);
item->writedefined = (ppdecl->write_token > 0);
item->resetdefined = (ppdecl->reset_token > 0);
item->notifydefined = (ppdecl->notify_token > 0);
propertylist.push_back(item);
if(item->ast->type_name_token > 0){
QString propertyname = item->trlUnit->spell(item->ast->type_name_token);
Trace(" - Q_PROPERTY: " + classname + "::" + propertyname + " found");
}
}
else{
/**********
Q_ENUM
**********/
QEnumDeclarationAST *pqenum = pmemberlist->value->asQEnumDeclarationAST();
if(pqenum){
if(pqenum->enumerator_list){
for (EnumeratorListAST *plist = pqenum->enumerator_list; plist; plist = plist->next) {
QENUMITEM* item = new QENUMITEM();
item->ast = plist->value;
item->highestlevelclass = highestlevelclass;
item->trlUnit = classitem->trlUnit;
qenumlist.push_back(item);
QString enumname = item->trlUnit->spell(item->ast->firstToken());
Trace(" - Q_ENUM: " + classname + "::" + enumname + " found");
}
}
}
else{
/**********
Q_FLAGS
**********/
QFlagsDeclarationAST *pqflags = pmemberlist->value->asQFlagsDeclarationAST();
if(pqflags){
if(pqflags->enumerator_list){
for (EnumeratorListAST *plist = pqflags->enumerator_list; plist; plist = plist->next) {
QFLAGITEM* item = new QFLAGITEM();
item->ast = plist->value;
item->highestlevelclass = highestlevelclass;
item->trlUnit = classitem->trlUnit;
qflaglist.push_back(item);
QString enumname = item->trlUnit->spell(plist->firstToken());
Trace(" - Q_FLAGS: " + classname + "::" + enumname + " found");
}
}
}
else {
/****************
Q_DECLARE_FLAGS
****************/
QDeclareFlagsDeclarationAST *pqdeclflags = pmemberlist->value->asQDeclareFlagsDeclarationAST();
if(pqdeclflags){
QDECLAREFLAGSITEM* item = new QDECLAREFLAGSITEM();
item->ast = pqdeclflags;
item->highestlevelclass = highestlevelclass;
item->trlUnit = classitem->trlUnit;
qdeclareflaglist.push_back(item);
}
}
}
}
}
}
}
}
/*********************************************
Function that starts the comare between the
parser result and their metadata content.
*********************************************/
bool ParseManager::checkAllMetadatas(ParseManager* pInterfaceParserManager, QString resultfile)
{
bool ret = true;
//Create output file
if(!resultfile.isEmpty() && ::m_resultFile == 0){
::m_resultFile = new QFile(resultfile);
if (!::m_resultFile->open(QFile::WriteOnly | QFile::Truncate)) {
delete ::m_resultFile;
::m_resultFile = 0;
}
}
/************************************************
Get all elements from the interface header file
************************************************/
Trace("### Get all elements from the interface header file ###");
QList<CLASSTREE*> ilookuplist = pInterfaceParserManager->CreateClassLists(true);
QList<QList<FUNCTIONITEM*> > ifunctionslookuplist;
QList<QList<PROPERTYITEM*> > ipropertieslookuplist;
QList<QList<QENUMITEM*> > iqenumlookuplist;
QList<QList<ENUMITEM*> > ienumlookuplist;
QList<QList<QFLAGITEM*> > iqflaglookuplist;
QList<QList<QDECLAREFLAGSITEM*> > iqdeclareflaglookuplist;
Trace("Following MetaData found:");
foreach(CLASSTREE* iclasstree, ilookuplist){
QList<FUNCTIONITEM*>functionlist;
QList<PROPERTYITEM*>propertylist;
QList<QENUMITEM*>qenumlist;
QList<ENUMITEM*>enumlist;
QList<QFLAGITEM*> qflaglist;
QList<QDECLAREFLAGSITEM*> qdeclareflag;
getElements(functionlist
, propertylist
, qenumlist
, enumlist
, qflaglist
, qdeclareflag
, iclasstree->classlist
, iclasstree->highestlevelclass);
if(functionlist.size() > 0)
ifunctionslookuplist.append(functionlist);
if(propertylist.size() > 0)
ipropertieslookuplist.append(propertylist);
if(qenumlist.size() > 0)
iqenumlookuplist.append(qenumlist);
if(enumlist.size() > 0)
ienumlookuplist.append(enumlist);
if(qflaglist.size() > 0)
iqflaglookuplist.append(qflaglist);
if(qdeclareflag.size() > 0)
iqdeclareflaglookuplist.append(qdeclareflag);
}
/************************************************
Get all elements from the compare header file
************************************************/
Trace("\n");
Trace("### Get all elements from the compare header file ###");
QList<CLASSTREE*> lookuplist = CreateClassLists(false);
QList<QList<FUNCTIONITEM*> > functionslookuplist;
QList<QList<PROPERTYITEM*> > propertieslookuplist;
QList<QList<QENUMITEM*> > qenumlookuplist;
QList<QList<ENUMITEM*> > enumlookuplist;
QList<QList<QFLAGITEM*> > qflaglookuplist;
QList<QList<QDECLAREFLAGSITEM*> > qdeclareflaglookuplist;
Trace("Following MetaData found:");
foreach(CLASSTREE* classtree, lookuplist){
QList<FUNCTIONITEM*>functionlist;
QList<PROPERTYITEM*>propertylist;
QList<QENUMITEM*>qenumlist;
QList<ENUMITEM*>enumlist;
QList<QFLAGITEM*> qflaglist;
QList<QDECLAREFLAGSITEM*> qdeclareflag;
getElements(functionlist
, propertylist
, qenumlist
, enumlist
, qflaglist
, qdeclareflag
, classtree->classlist
, classtree->highestlevelclass);
if(functionlist.size() > 0)
functionslookuplist.append(functionlist);
if(propertylist.size() > 0)
propertieslookuplist.append(propertylist);
if(qenumlist.size() > 0)
qenumlookuplist.append(qenumlist);
if(enumlist.size() > 0)
enumlookuplist.append(enumlist);
if(qflaglist.size() > 0)
qflaglookuplist.append(qflaglist);
if(qdeclareflag.size() > 0)
qdeclareflaglookuplist.append(qdeclareflag);
}
Trace("\n");
Trace("### Result: ###");
/******************************
Check for function
******************************/
Trace("Compare all interface MetaData functions:");
QList<FUNCTIONITEM*> missingifcts = checkMetadataFunctions(functionslookuplist, ifunctionslookuplist);
if(missingifcts.size() > 0){
foreach(FUNCTIONITEM* ifct, missingifcts){
m_errormsgs.append(getErrorMessage(ifct));
}
ret = false;
Trace("- Failed!");
}
else{
Trace("- OK");
}
/******************************
Check for properies
******************************/
Trace("Compare all interface MetaData properties:");
QList<PROPERTYITEM*> missingippts = checkMetadataProperties(propertieslookuplist, functionslookuplist, ipropertieslookuplist, ifunctionslookuplist);
if(missingippts.size() > 0){
foreach(PROPERTYITEM* ippt, missingippts){
m_errormsgs.append(getErrorMessage(ippt));
}
ret = false;
Trace("- Failed!");
}
else{
Trace("- OK");
}
/******************************
Check for enums
******************************/
Trace("Compare all interface MetaData enums:");
QList<QENUMITEM*> missingiqenums = checkMetadataEnums(qenumlookuplist, enumlookuplist, iqenumlookuplist, ienumlookuplist);
if(missingiqenums.size() > 0){
foreach(QENUMITEM* ienum, missingiqenums){
m_errormsgs.append(getErrorMessage(ienum));
}
ret = false;
Trace("- Failed!");
}
else{
Trace("- OK");
}
/******************************
Check for flags
******************************/
Trace("Compare all interface MetaData flags:");
QList<QFLAGITEM*> missingiqflags = checkMetadataFlags(qflaglookuplist, qdeclareflaglookuplist, enumlookuplist
, iqflaglookuplist, iqdeclareflaglookuplist, ienumlookuplist);
if(missingiqflags.size() > 0){
foreach(QFLAGITEM* iflags, missingiqflags){
m_errormsgs.append(getErrorMessage(iflags));
}
ret = false;
Trace("- Failed!");
}
else{
Trace("- OK");
}
/******************************
Add summary
******************************/
Trace("\n");
Trace("### summary ###");
if(m_errormsgs.size() > 0){
Trace("- Folowing interface items are missing:");
foreach(QString msg, m_errormsgs)
Trace(" - " + msg);
}
else
Trace("Interface is full defined.");
//now delet all Classitems
foreach(CLASSTREE* l, ilookuplist){
l->classlist.clear();
}
foreach(CLASSTREE* l, lookuplist){
l->classlist.clear();
}
//delete all functionitems
foreach(QList<FUNCTIONITEM*>l, ifunctionslookuplist){
l.clear();
}
foreach(QList<FUNCTIONITEM*>l, functionslookuplist){
l.clear();
}
//delete all properties
foreach(QList<PROPERTYITEM*>l, ipropertieslookuplist){
l.clear();
}
foreach(QList<PROPERTYITEM*>l, propertieslookuplist){
l.clear();
}
//delete all qenums
foreach(QList<QENUMITEM*>l, iqenumlookuplist){
l.clear();
}
foreach(QList<QENUMITEM*>l, iqenumlookuplist){
l.clear();
}
//delete all enums
foreach(QList<ENUMITEM*>l, ienumlookuplist){
l.clear();
}
foreach(QList<ENUMITEM*>l, enumlookuplist){
l.clear();
}
//delete all qflags
foreach(QList<QFLAGITEM*>l, iqflaglookuplist){
l.clear();
}
foreach(QList<QFLAGITEM*>l, qflaglookuplist){
l.clear();
}
//delete all qdeclareflags
foreach(QList<QDECLAREFLAGSITEM*>l, iqdeclareflaglookuplist){
l.clear();
}
foreach(QList<QDECLAREFLAGSITEM*>l, qdeclareflaglookuplist){
l.clear();
}
return ret;
}
//<------------------------------------------------------- Start of MetaData functions
/***********************************
Function that checks all functions
which will occur in the MetaData
***********************************/
QList<FUNCTIONITEM*> ParseManager::checkMetadataFunctions(const QList<QList<FUNCTIONITEM*> > &classfctlist, const QList<QList<FUNCTIONITEM*> > &iclassfctlist)
{
QList<FUNCTIONITEM*> missingifcts;
//Compare each function from interface with function from header (incl. baseclass functions)
QList<FUNCTIONITEM*> ifcts;
foreach(QList<FUNCTIONITEM*>ifunctionlist, iclassfctlist){
ifcts.clear();
//check if one header class contains all function from one interface header class
if(classfctlist.count() > 0){
foreach(QList<FUNCTIONITEM*>functionlist, classfctlist){
QList<FUNCTIONITEM*> tmpl = containsAllMetadataFunction(functionlist, ifunctionlist);
if(tmpl.size() == 0){
ifcts.clear();
break;
}
else
ifcts.append(tmpl);
}
}
else {
foreach(FUNCTIONITEM *pfct, ifunctionlist)
pfct->classWichIsNotFound << "<all classes>";
ifcts.append(ifunctionlist);
}
missingifcts.append(ifcts);
}
return missingifcts;
}
/*********************************************
Helper function to check if a function will
occure in the MetaData.
*********************************************/
bool ParseManager::isMetaObjFunction(FUNCTIONITEM* fct)
{
if(fct->function->isInvokable()
|| fct->function->isSignal()
|| fct->function->isSlot())
return true;
return false;
}
/****************************************************
Check if all function from iclassfctlist are defined
in the classfctlist as well.
It will return all the function they are missing.
****************************************************/
QList<FUNCTIONITEM*> ParseManager::containsAllMetadataFunction(const QList<FUNCTIONITEM*> &classfctlist, const QList<FUNCTIONITEM*> &iclassfctlist)
{
QList<FUNCTIONITEM*> ret;
foreach(FUNCTIONITEM* ifct, iclassfctlist){
if(isMetaObjFunction(ifct)){
bool found = false;
QStringList missingimplinclasses;
ClassSpecifierAST* clspec = 0;
QString classname = "";
foreach(FUNCTIONITEM* fct, classfctlist){
if(clspec != fct->highestlevelclass->classspec){
clspec = fct->highestlevelclass->classspec;
//get the classname
unsigned int firsttoken = clspec->name->firstToken();
classname += fct->trlUnit->spell(firsttoken);
if(missingimplinclasses.indexOf(classname) < 0)
missingimplinclasses.push_back(classname);
}
if(fct->isEqualTo(ifct, false)){
found = true;
missingimplinclasses.clear();
Trace("- " + getTraceFuntionString(fct, classname) + " implemented");
break;
}
}
if(!found){
ifct->classWichIsNotFound.append(missingimplinclasses);
ret.push_back(ifct);
QString classname = ifct->trlUnit->spell(ifct->highestlevelclass->classspec->name->firstToken());
Trace("- " + getTraceFuntionString(ifct, classname) + " not implemented!");
}
}
}
return ret;
}
/************************************
Function that gives back an error
string for a MetaData function
mismatch.
************************************/
QStringList ParseManager::getErrorMessage(FUNCTIONITEM* fct)
{
QStringList ret;
QString fctstring = "";
QString fcttype = "";
foreach(QString classname, fct->classWichIsNotFound){
QString tmp;
QTextStream out(&tmp);
fcttype = "";
fctstring = classname;
fctstring += "::";
unsigned int token = fct->function->sourceLocation() - 1;
if(token >= 0){
//tok.isNot(T_EOF_SYMBOL)
while(fct->trlUnit->tokenAt(token).isNot(T_EOF_SYMBOL)){
fctstring += fct->trlUnit->tokenAt(token).spell();
if(*fct->trlUnit->tokenAt(token).spell() == ')')
break;
fctstring += " ";
token++;
}
}
Function* pfct = fct->function;
if(pfct){
fcttype = "type: ";
//Check for private, protected and public
if(pfct->isPublic())
fcttype = "public ";
if(pfct->isProtected())
fcttype = "protected ";
if(pfct->isPrivate())
fcttype = "private ";
if(pfct->isVirtual())
fcttype += "virtual ";
if(pfct->isPureVirtual())
fcttype += "pure virtual ";
if(pfct->isSignal())
fcttype += "Signal ";
if(pfct->isSlot())
fcttype += "Slot ";
if(pfct->isNormal())
fcttype += "Normal ";
if(pfct->isInvokable())
fcttype += "Invokable ";
}
out << fcttype << fctstring;
ret << tmp;
}
return ret;
}
//--->
//<------------------------------------------------------- Start of Q_PROPERTY checks
/***********************************
Function that checks all Property
which will occur in the MetaData
***********************************/
QList<PROPERTYITEM*> ParseManager::checkMetadataProperties(const QList<QList<PROPERTYITEM*> > &classproplist
, const QList<QList<FUNCTIONITEM*> > &classfctlist
, const QList<QList<PROPERTYITEM*> > &iclassproplist
, const QList<QList<FUNCTIONITEM*> > &iclassfctlist)
{
QList<PROPERTYITEM*> missingiprops;
//assign the property functions
foreach(QList<PROPERTYITEM*>proplist, classproplist){
foreach(PROPERTYITEM* prop, proplist){
assignPropertyFunctions(prop, classfctlist);
}
}
foreach(QList<PROPERTYITEM*>proplist, iclassproplist){
foreach(PROPERTYITEM* prop, proplist){
assignPropertyFunctions(prop, iclassfctlist);
}
}
//Compare each qproperty from interface with qproperty from header (incl. baseclass functions)
QList<PROPERTYITEM*> ippts;
foreach(QList<PROPERTYITEM*>ipropertylist, iclassproplist){
ippts.clear();
//check if one header class contains all function from one interface header class
if(classproplist.count() > 0){
foreach(QList<PROPERTYITEM*>propertylist, classproplist){
QList<PROPERTYITEM*> tmpl = containsAllPropertyFunction(propertylist, ipropertylist);
if(tmpl.size() == 0)
ippts.clear();
else
ippts.append(tmpl);
}
}
else {
foreach(PROPERTYITEM *pprop, ipropertylist){
pprop->classWichIsNotFound << "<all classes>";
QString name = pprop->trlUnit->spell(pprop->ast->type_name_token);
Trace("- Property: <all classes>::" + name + " not found!");
}
ippts.append(ipropertylist);
}
missingiprops.append(ippts);
}
return missingiprops;
}
/**************************************
Function that resolves the dependensies
between Q_PROPERTY
and thier READ, WRITE, NOTIFY and RESET
functions.
***************************************/
void ParseManager::assignPropertyFunctions(PROPERTYITEM* prop, const QList<QList<FUNCTIONITEM*> > &fctlookuplist)
{
//get the name of the needed functions
QString type;
QString readfctname;
QString writefctname;
QString resetfctname;
QString notifyfctname;
int needtofind = 0;
type = prop->trlUnit->spell(prop->ast->type_token);
if(prop->readdefined){
readfctname = prop->trlUnit->spell(prop->ast->read_function_token);
needtofind++;
}
if(prop->writedefined){
writefctname = prop->trlUnit->spell(prop->ast->write_function_token);
needtofind++;
}
if(prop->resetdefined){
resetfctname = prop->trlUnit->spell(prop->ast->reset_function_token);
needtofind++;
}
if(prop->notifydefined){
notifyfctname = prop->trlUnit->spell(prop->ast->notify_function_token);
needtofind++;
}
//Now iterate over all function to find all functions wich are defined in the Q_PROPERTY macro
if(needtofind > 0){
prop->foundalldefinedfct = false;
foreach(QList<FUNCTIONITEM*> fctlist, fctlookuplist){
foreach(FUNCTIONITEM* pfct, fctlist){
QString fctname = pfct->trlUnit->spell(pfct->function->sourceLocation());
//check the function type against the property type
QString fcttype =pfct->trlUnit->spell(pfct->function->sourceLocation() - 1);
if(fctname.length() > 0 && fcttype.length() > 0){
if(prop->readdefined && fctname == readfctname){
if(type != fcttype)
continue;
prop->readFct = pfct;
needtofind--;
}
if(prop->writedefined && fctname == writefctname){
prop->writeFct = pfct;
needtofind--;
}
if(prop->resetdefined && fctname == resetfctname){
prop->resetFct = pfct;
needtofind--;
}
if(prop->notifydefined && fctname == notifyfctname){
prop->notifyFct = pfct;
needtofind--;
}
if(needtofind <= 0){
//a flag that indicates if a function was missing
prop->foundalldefinedfct = true;
return;
}
}
}
}
}
}
/**************************************
Function that checks if all functions
dependencies in Q_PROPERTY have the
same arguments and retunr value.
***************************************/
QList<PROPERTYITEM*> ParseManager::containsAllPropertyFunction(const QList<PROPERTYITEM*> &classproplist, const QList<PROPERTYITEM*> &iclassproplist)
{
QList<PROPERTYITEM*> ret;
foreach(PROPERTYITEM* ipropt, iclassproplist){
if(ipropt->foundalldefinedfct){
bool found = false;
QStringList missingimplinclasses;
ClassSpecifierAST* clspec = 0;
QString classname = "";
foreach(PROPERTYITEM* propt, classproplist){
if(clspec != propt->highestlevelclass->classspec){
clspec = propt->highestlevelclass->classspec;
//get the classname
unsigned int firsttoken = clspec->name->firstToken();
classname += propt->trlUnit->spell(firsttoken);
if(missingimplinclasses.indexOf(classname) < 0)
missingimplinclasses.push_back(classname);
}
if(propt->isEqualTo(ipropt)){
found = true;
missingimplinclasses.clear();
Trace("- Property: " + classname + "::" + propt->trlUnit->spell(propt->ast->type_name_token) + " found");
break;
}
}
if(!found){
ipropt->classWichIsNotFound.append(missingimplinclasses);
ret.push_back(ipropt);
QString classname = ipropt->trlUnit->spell(ipropt->highestlevelclass->classspec->name->firstToken());
Trace("- Property: " + classname + "::" + ipropt->trlUnit->spell(ipropt->ast->type_name_token) + " not found!");
}
}
else{
QString classname = ipropt->trlUnit->spell(ipropt->highestlevelclass->classspec->name->firstToken());
QString proptype = ipropt->trlUnit->spell(ipropt->ast->type_name_token);
Trace("- Property: " + classname + "::" + proptype + " functions are missing!");
ret.push_back(ipropt);
}
}
return ret;
}
/************************************
Function that gives back an error
string for a Q_PROPERTY mismatch.
************************************/
QStringList ParseManager::getErrorMessage(PROPERTYITEM* ppt)
{
QStringList ret;
QString pptstring = "";
if(!ppt->foundalldefinedfct)
{
QString tmp;
QTextStream out(&tmp);
unsigned int firsttoken = ppt->highestlevelclass->classspec->name->firstToken();
unsigned int lasttoken = ppt->highestlevelclass->classspec->name->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++){
out << ppt->trlUnit->spell(i);
}
out << "::";
firsttoken = ppt->ast->firstToken();
lasttoken = ppt->ast->lastToken();
for(unsigned int i = firsttoken; i <= lasttoken; i++){
out << ppt->trlUnit->spell(i) << " ";
}
out << endl << " -";
if(ppt->readdefined && !ppt->readFct)
out << "READ ";
if(ppt->writedefined && !ppt->writeFct)
out << "WRITE ";
if(ppt->resetdefined && !ppt->resetFct)
out << "RESET.";
if(ppt->notifydefined && !ppt->notifyFct)
out << "NOTIFY ";
out << "functions missing." << endl;
ret << tmp;
}
for(int i = 0; i < ppt->classWichIsNotFound.size(); i++){
QString tmp;
QTextStream out(&tmp);
pptstring = ppt->classWichIsNotFound[i];
pptstring += "::";
unsigned int firsttoken = ppt->ast->firstToken();
unsigned int lasttoken = ppt->ast->lastToken();
for(unsigned int i = firsttoken; i <= lasttoken; i++){
pptstring += ppt->trlUnit->spell(i);
pptstring += " ";
}
out << pptstring;
ret << tmp;
}
return ret;
}
//--->
//<------------------------------------------------------- Start of Q_ENUMS checks
/***********************************
Function that checks all enums
which will occur in the MetaData
***********************************/
QList<QENUMITEM*> ParseManager::checkMetadataEnums(const QList<QList<QENUMITEM*> > &classqenumlist
, const QList<QList<ENUMITEM*> > &classenumlist
, const QList<QList<QENUMITEM*> > &iclassqenumlist
, const QList<QList<ENUMITEM*> > &iclassenumlist)
{
QList<QENUMITEM*> missingiqenums;
//assign the property functions
foreach(QList<QENUMITEM*>qenumlist, classqenumlist){
foreach(QENUMITEM* qenum, qenumlist){
assignEnumValues(qenum, classenumlist);
}
}
foreach(QList<QENUMITEM*>qenumlist, iclassqenumlist){
foreach(QENUMITEM* qenum, qenumlist){
assignEnumValues(qenum, iclassenumlist);
}
}
//Compare each qenum from interface with qenum from header (incl. baseclass functions)
QList<QENUMITEM*> iqenums;
foreach(QList<QENUMITEM*>iqenumlist, iclassqenumlist){
iqenums.clear();
//check if one header class contains all function from one interface header class
if(classqenumlist.count() > 0){
foreach(QList<QENUMITEM*>qenumlist, classqenumlist){
QList<QENUMITEM*> tmpl = containsAllEnums(qenumlist, iqenumlist);
if(tmpl.size() == 0)
iqenums.clear();
else
iqenums.append(tmpl);
}
}
else {
foreach(QENUMITEM *qenum, iqenumlist){
qenum->classWichIsNotFound << "<all classes>";
QString name= qenum->trlUnit->spell(qenum->ast->firstToken());
Trace("- Enum: <all classes>::" + name + " not found!");
}
iqenums.append(iqenumlist);
}
missingiqenums.append(iqenums);
}
return missingiqenums;
}
/*********************************************
Helper function which creates a string out of
an enumerator including its values.
*********************************************/
QStringList ParseManager::getEnumValueStringList(ENUMITEM *penum, QString mappedenumname/* = ""*/)
{
QStringList ret;
EnumSpecifierAST *penumsec = penum->ast;
QString enumname = penum->trlUnit->spell(penumsec->name->firstToken());
int enumvalue = 0;
//now iterrate over all enumitems and create a string like following:
//EnumName.EnumItemName.Value
//ConnectionState.disconnected.0
for (EnumeratorListAST *plist = penum->ast->enumerator_list; plist; plist = plist->next) {
QString value = enumname;
if(mappedenumname.size() > 0)
value = mappedenumname;
value += ".";
value += penum->trlUnit->spell(plist->value->identifier_token);
value += ".";
if(plist->value->equal_token > 0 && plist->value->expression){
QString v = penum->trlUnit->spell(plist->value->expression->firstToken());
bool ch;
int newval = enumvalue;
if(v.indexOf("0x") >= 0)
newval = v.toInt(&ch, 16);
else
newval = v.toInt(&ch, 10);
if(ch)
enumvalue = newval;
}
value += QString::number(enumvalue);
enumvalue++;
// now add this enumitem string in the VALUE list
ret << value;
}
return ret;
}
/**************************************
Function that resolves the dependensies
between Q_ENUMS and enums.
***************************************/
void ParseManager::assignEnumValues(QENUMITEM* qenum, const QList<QList<ENUMITEM*> > &enumlookuplist)
{
QString enumname;
EnumeratorAST *penum = qenum->ast->asEnumerator();
if(penum){
//get the name of the enum definition
enumname = qenum->trlUnit->spell(penum->firstToken());
//iterate over all enums and find the one with the same name like enumname
bool found = false;
foreach (QList<ENUMITEM*> penumlist, enumlookuplist) {
foreach(ENUMITEM *penum, penumlist){
EnumSpecifierAST *penumsec = penum->ast;
QString enumname1 = penum->trlUnit->spell(penumsec->name->firstToken());
if(enumname == enumname1){
qenum->values << getEnumValueStringList(penum);
found = true;
break;
}
}
if(!found)
qenum->foundallenums = false;
}
}
}
/***********************************
Function that checkt if the Q_ENUMS
are completed defined and if the
Enum values are the same.
***********************************/
QList<QENUMITEM*> ParseManager::containsAllEnums(const QList<QENUMITEM*> &classqenumlist, const QList<QENUMITEM*> &iclassqenumlist)
{
QList<QENUMITEM*> ret;
foreach(QENUMITEM* iqenum, iclassqenumlist){
bool found = false;
QStringList missingimplinclasses;
ClassSpecifierAST* clspec = 0;
QString classname = "";
foreach(QENUMITEM* qenum, classqenumlist){
if(clspec != qenum->highestlevelclass->classspec){
clspec = qenum->highestlevelclass->classspec;
//get the classname
unsigned int firsttoken = clspec->name->firstToken();
classname += qenum->trlUnit->spell(firsttoken);
if(missingimplinclasses.indexOf(classname) < 0)
missingimplinclasses.push_back(classname);
}
if(qenum->isEqualTo(iqenum)){
found = true;
missingimplinclasses.clear();
Trace("- Enum: " + classname + "::" + qenum->trlUnit->spell(qenum->ast->firstToken()) + " found");
break;
}
}
if(!found){
iqenum->classWichIsNotFound.append(missingimplinclasses);
ret.push_back(iqenum);
QString classname = iqenum->trlUnit->spell(iqenum->highestlevelclass->classspec->name->firstToken());
Trace("- Enum: " + classname + "::" + iqenum->trlUnit->spell(iqenum->ast->firstToken()) + " not found!");
}
}
return ret;
}
/************************************
Function that gives back an error
string for a Q_ENUMS mismatch.
************************************/
QStringList ParseManager::getErrorMessage(QENUMITEM* qenum)
{
QStringList ret;
if(!qenum->foundallenums)
{
QString tmp;
QTextStream out(&tmp);
unsigned int firsttoken = qenum->highestlevelclass->classspec->name->firstToken();
unsigned int lasttoken = qenum->highestlevelclass->classspec->name->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++){
out << qenum->trlUnit->spell(i);
}
out << "::Q_ENUMS ( ";
firsttoken = qenum->ast->firstToken();
lasttoken = qenum->ast->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++)
out << qenum->trlUnit->spell(i) << " ";
out << ")";
out << endl << " - one or more Enums missing." << endl;
ret << tmp;
}
for(int i = 0; i < qenum->classWichIsNotFound.size(); i++){
QString tmp;
QTextStream out(&tmp);
out << qenum->classWichIsNotFound[i] << "::Q_ENUMS ( ";
unsigned int firsttoken = qenum->ast->firstToken();
unsigned int lasttoken = qenum->ast->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++)
out << qenum->trlUnit->spell(i) << " ";
out << ")";
ret << tmp;
}
return ret;
}
//--->
//<------------------------------------------------------- Start of Q_FLAGS checks
/***********************************
Function that checks all flags
which will occur in the MetaData
***********************************/
QList<QFLAGITEM*> ParseManager::checkMetadataFlags(const QList<QList<QFLAGITEM*> > &classqflaglist
, const QList<QList<QDECLAREFLAGSITEM*> > &classqdeclareflaglist
, const QList<QList<ENUMITEM*> > &classenumlist
, const QList<QList<QFLAGITEM*> > &iclassqflaglist
, const QList<QList<QDECLAREFLAGSITEM*> > &iclassqdeclareflaglist
, const QList<QList<ENUMITEM*> > &iclassenumlist)
{
QList<QFLAGITEM*> missingqflags;
//assign the enums to the flags
foreach(QList<QFLAGITEM*>qflaglist, classqflaglist){
foreach(QFLAGITEM* qflag, qflaglist){
assignFlagValues(qflag, classqdeclareflaglist, classenumlist);
}
}
foreach(QList<QFLAGITEM*>qflaglist, iclassqflaglist){
foreach(QFLAGITEM* qflag, qflaglist){
assignFlagValues(qflag, iclassqdeclareflaglist, iclassenumlist);
}
}
//Compare each qenum from interface with qenum from header (incl. baseclass functions)
QList<QFLAGITEM*> iqflags;
foreach(QList<QFLAGITEM*>iqflaglist, iclassqflaglist){
iqflags.clear();
//check if one header class contains all function from one interface header class
if(classqflaglist.count() >0){
foreach(QList<QFLAGITEM*>qflaglist, classqflaglist){
QList<QFLAGITEM*> tmpl = containsAllFlags(qflaglist, iqflaglist);
if(tmpl.size() == 0)
iqflags.clear();
else
iqflags.append(tmpl);
}
}
else {
foreach(QFLAGITEM *pflag, iqflaglist){
pflag->classWichIsNotFound << "<all classes>";
QString name= pflag->trlUnit->spell(pflag->ast->firstToken());
Trace("- Flag: <all classes>::" + name + " not found!");
}
iqflags.append(iqflaglist);
}
missingqflags.append(iqflags);
}
return missingqflags;
}
/**************************************
Function that resolves the dependensies
between Q_FLAG, Q_DECLARE_FLAGS
and enums.
***************************************/
void ParseManager::assignFlagValues(QFLAGITEM* qflags, const QList<QList<QDECLAREFLAGSITEM*> > &qdeclareflagslookuplist, const QList<QList<ENUMITEM*> > &enumlookuplist)
{
QString qflagname;
QString enumname;
//read the flag names
EnumeratorAST *pflags = qflags->ast->asEnumerator();
if(pflags){
qflagname = qflags->trlUnit->spell(pflags->firstToken());
enumname = qflagname;
//try to find if there is a deflare flag macro with the same name as in qflagname
bool found = false;
foreach(QList<QDECLAREFLAGSITEM*> qdeclarelist, qdeclareflagslookuplist){
foreach(QDECLAREFLAGSITEM* qdeclare, qdeclarelist){
QString declarename = qdeclare->trlUnit->spell(qdeclare->ast->flag_token);
if(declarename == qflagname){
//now map the right enum name to the flag
enumname = qdeclare->trlUnit->spell(qdeclare->ast->enum_token);
found = true;
break;
}
}
if(found)
break;
}
//now we have the right enum name now we need to find the enum
found = false;
foreach(QList<ENUMITEM*> enumitemlist, enumlookuplist){
foreach(ENUMITEM* enumitem, enumitemlist){
EnumSpecifierAST *penumspec = enumitem->ast;
QString enumspecname = enumitem->trlUnit->spell(penumspec->name->firstToken());
if(enumspecname == enumname){
qflags->enumvalues << getEnumValueStringList(enumitem, qflagname);
found = true;
break;
}
}
if(found)
break;
}
if(!found)
qflags->foundallenums = false;
}
}
/*****************************************
Function that compares if all enums
and flags assigned by using the Q_FLAGS
are complete defined.
*****************************************/
QList<QFLAGITEM*> ParseManager::containsAllFlags(const QList<QFLAGITEM*> &classqflaglist, const QList<QFLAGITEM*> &iclassqflaglist)
{
QList<QFLAGITEM*> ret;
foreach(QFLAGITEM* iqflags, iclassqflaglist){
if(iqflags->foundallenums){
bool found = false;
QStringList missingimplinclasses;
ClassSpecifierAST* clspec = 0;
QString classname = "";
foreach(QFLAGITEM* qflags, classqflaglist){
if(clspec != qflags->highestlevelclass->classspec){
clspec = qflags->highestlevelclass->classspec;
//get the classname
unsigned int firsttoken = clspec->name->firstToken();
classname += qflags->trlUnit->spell(firsttoken);
if(missingimplinclasses.indexOf(classname) < 0)
missingimplinclasses.push_back(classname);
}
if(qflags->isEqualTo(iqflags)){
found = true;
missingimplinclasses.clear();
Trace("- Flag: " + classname + "::" + qflags->trlUnit->spell(qflags->ast->firstToken()) + " found");
break;
}
}
if(!found){
iqflags->classWichIsNotFound.append(missingimplinclasses);
ret.push_back(iqflags);
QString classname = iqflags->trlUnit->spell(iqflags->highestlevelclass->classspec->name->firstToken());
Trace("- Flag: " + classname + "::" + iqflags->trlUnit->spell(iqflags->ast->firstToken()) + " not found!");
}
}
else
ret.push_back(iqflags);
}
return ret;
}
/************************************
Function that gives back an error
string for a Q_FLAGS mismatch.
************************************/
QStringList ParseManager::getErrorMessage(QFLAGITEM* pfg)
{
QStringList ret;
if(!pfg->foundallenums)
{
QString tmp;
QTextStream out(&tmp);
unsigned int firsttoken = pfg->highestlevelclass->classspec->name->firstToken();
unsigned int lasttoken = pfg->highestlevelclass->classspec->name->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++){
out << pfg->trlUnit->spell(i);
}
out << "::Q_FLAGS ( ";
firsttoken = pfg->ast->firstToken();
lasttoken = pfg->ast->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++)
out << pfg->trlUnit->spell(i) << " ";
out << ")";
out << endl << " - one or more Enums missing." << endl;
ret << tmp;
}
for(int i = 0; i < pfg->classWichIsNotFound.size(); i++){
QString tmp;
QTextStream out(&tmp);
out << pfg->classWichIsNotFound[i] << "::Q_FLAGS ( ";
unsigned int firsttoken = pfg->ast->firstToken();
unsigned int lasttoken = pfg->ast->lastToken();
for(unsigned int i = firsttoken; i < lasttoken; i++)
out << pfg->trlUnit->spell(i) << " ";
out << ")";
ret << tmp;
}
return ret;
}
inline QString ParseManager::getTraceFuntionString(const FUNCTIONITEM *fctitem, const QString& classname)
{
QString ret;
if(fctitem->function->isPublic())
ret = "public ";
if(fctitem->function->isProtected())
ret = "protected ";
if(fctitem->function->isPrivate())
ret = "private ";
if(fctitem->function->isVirtual())
ret += "virtual ";
if(fctitem->function->isPureVirtual())
ret += "pure virtual ";
if(fctitem->function->isSignal())
ret += "Signal ";
if(fctitem->function->isSlot())
ret += "Slot ";
if(fctitem->function->isNormal())
ret += "Normal ";
if(fctitem->function->isInvokable())
ret += "Invokable ";
ret += classname;
ret += "::";
ret += fctitem->trlUnit->spell(fctitem->function->sourceLocation());
return ret;
}
void ParseManager::Trace(QString value)
{
if(::m_resultFile){
QTextStream out(::m_resultFile);
if(value == "\n")
out << endl;
else
out << value << endl;
}
}
//--->