Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
Tobias Hunger
qt-creator
Commits
01473fec
Commit
01473fec
authored
Nov 09, 2009
by
Roberto Raggi
Browse files
Addeed generator for the cast methods.
Done with: erikv
parent
36d0d850
Changes
3
Expand all
Hide whitespace changes
Inline
Side-by-side
src/shared/cplusplus/AST.h
View file @
01473fec
This diff is collapsed.
Click to expand it.
src/tools/cplusplus/Main.cpp
0 → 100644
View file @
01473fec
#include
<QCoreApplication>
#include
<QStringList>
#include
<QTextDocument>
#include
<QTextCursor>
#include
<QTextBlock>
#include
<QDebug>
#include
<Control.h>
#include
<Parser.h>
#include
<AST.h>
#include
<ASTVisitor.h>
#include
<Symbols.h>
#include
<CoreTypes.h>
#include
<Literals.h>
#include
<CppDocument.h>
#include
<Overview.h>
#include
<iostream>
#include
<cstdlib>
using
namespace
CPlusPlus
;
class
ASTNodes
{
public:
ASTNodes
()
:
base
(
0
)
{}
ClassSpecifierAST
*
base
;
// points to "class AST"
QList
<
ClassSpecifierAST
*>
deriveds
;
// n where n extends AST
QList
<
QTextCursor
>
endOfPublicClassSpecifiers
;
};
class
FindASTNodes
:
protected
ASTVisitor
{
public:
FindASTNodes
(
Document
::
Ptr
doc
,
QTextDocument
*
document
)
:
ASTVisitor
(
doc
->
control
()),
document
(
document
)
{
}
ASTNodes
operator
()(
AST
*
ast
)
{
accept
(
ast
);
return
_nodes
;
}
protected:
virtual
bool
visit
(
ClassSpecifierAST
*
ast
)
{
Class
*
klass
=
ast
->
symbol
;
Q_ASSERT
(
klass
!=
0
);
const
QString
className
=
oo
(
klass
->
name
());
if
(
className
.
endsWith
(
"AST"
))
{
if
(
className
==
QLatin1String
(
"AST"
))
_nodes
.
base
=
ast
;
else
{
_nodes
.
deriveds
.
append
(
ast
);
AccessDeclarationAST
*
accessDeclaration
=
0
;
for
(
DeclarationListAST
*
it
=
ast
->
member_specifiers
;
it
;
it
=
it
->
next
)
{
if
(
AccessDeclarationAST
*
decl
=
it
->
declaration
->
asAccessDeclaration
())
{
if
(
tokenKind
(
decl
->
access_specifier_token
)
==
T_PUBLIC
)
accessDeclaration
=
decl
;
}
}
if
(
!
accessDeclaration
)
qDebug
()
<<
"no access declaration for class:"
<<
className
;
Q_ASSERT
(
accessDeclaration
!=
0
);
unsigned
endLine
,
endColumn
;
getTokenEndPosition
(
accessDeclaration
->
lastToken
()
-
1
,
&
endLine
,
&
endColumn
);
QTextCursor
tc
(
document
);
tc
.
setPosition
(
document
->
findBlockByNumber
(
endLine
-
1
).
position
()
+
endColumn
-
1
);
int
charsToSkip
=
0
;
forever
{
QChar
ch
=
document
->
characterAt
(
tc
.
position
()
+
charsToSkip
);
if
(
!
ch
.
isSpace
())
break
;
++
charsToSkip
;
if
(
ch
==
QChar
::
ParagraphSeparator
)
break
;
}
tc
.
setPosition
(
tc
.
position
()
+
charsToSkip
);
_nodes
.
endOfPublicClassSpecifiers
.
append
(
tc
);
}
}
return
true
;
}
private:
QTextDocument
*
document
;
ASTNodes
_nodes
;
Overview
oo
;
};
class
RemoveCastMethods
:
protected
ASTVisitor
{
public:
RemoveCastMethods
(
Document
::
Ptr
doc
,
QTextDocument
*
document
)
:
ASTVisitor
(
doc
->
control
()),
document
(
document
)
{}
QList
<
QTextCursor
>
operator
()(
AST
*
ast
)
{
_cursors
.
clear
();
accept
(
ast
);
return
_cursors
;
}
protected:
virtual
bool
visit
(
FunctionDefinitionAST
*
ast
)
{
Function
*
fun
=
ast
->
symbol
;
const
QString
functionName
=
oo
(
fun
->
name
());
if
(
functionName
.
length
()
>
3
&&
functionName
.
startsWith
(
QLatin1String
(
"as"
))
&&
functionName
.
at
(
2
).
isUpper
())
{
unsigned
startLine
,
startColumn
,
endLine
,
endColumn
;
getTokenStartPosition
(
ast
->
firstToken
(),
&
startLine
,
&
startColumn
);
getTokenEndPosition
(
ast
->
lastToken
()
-
1
,
&
endLine
,
&
endColumn
);
QTextCursor
tc
(
document
);
tc
.
setPosition
(
document
->
findBlockByNumber
(
startLine
-
1
).
position
());
tc
.
setPosition
(
document
->
findBlockByNumber
(
endLine
-
1
).
position
()
+
endColumn
-
1
,
QTextCursor
::
KeepAnchor
);
int
charsToSkip
=
0
;
forever
{
QChar
ch
=
document
->
characterAt
(
tc
.
position
()
+
charsToSkip
);
if
(
!
ch
.
isSpace
())
break
;
++
charsToSkip
;
if
(
ch
==
QChar
::
ParagraphSeparator
)
break
;
}
tc
.
setPosition
(
tc
.
position
()
+
charsToSkip
,
QTextCursor
::
KeepAnchor
);
//qDebug() << qPrintable(tc.selectedText());
_cursors
.
append
(
tc
);
}
return
true
;
}
private:
QTextDocument
*
document
;
QList
<
QTextCursor
>
_cursors
;
Overview
oo
;
};
int
main
(
int
argc
,
char
*
argv
[])
{
QCoreApplication
app
(
argc
,
argv
);
QStringList
files
=
app
.
arguments
();
files
.
removeFirst
();
if
(
files
.
isEmpty
())
{
std
::
cerr
<<
"Usage: cplusplus AST.h"
<<
std
::
endl
;
return
EXIT_FAILURE
;
}
Snapshot
snapshot
;
//const QString configuration = QLatin1String("#define CPLUSPLUS_EXPORT\n");
foreach
(
const
QString
&
fileName
,
files
)
{
QFile
file
(
fileName
);
if
(
!
file
.
open
(
QFile
::
ReadOnly
))
continue
;
const
QString
source
=
QTextStream
(
&
file
).
readAll
();
QTextDocument
document
;
document
.
setPlainText
(
source
);
Document
::
Ptr
doc
=
Document
::
create
(
fileName
);
//doc->control()->setDiagnosticClient(0);
const
QByteArray
preprocessedCode
=
snapshot
.
preprocessedCode
(
source
,
fileName
);
doc
->
setSource
(
preprocessedCode
);
doc
->
check
();
FindASTNodes
process
(
doc
,
&
document
);
ASTNodes
astNodes
=
process
(
doc
->
translationUnit
()
->
ast
());
RemoveCastMethods
removeCastMethods
(
doc
,
&
document
);
QList
<
QTextCursor
>
baseCastMethodCursors
=
removeCastMethods
(
astNodes
.
base
);
QMap
<
ClassSpecifierAST
*
,
QList
<
QTextCursor
>
>
cursors
;
QMap
<
ClassSpecifierAST
*
,
QString
>
replacementCastMethods
;
Overview
oo
;
QStringList
castMethods
;
foreach
(
ClassSpecifierAST
*
classAST
,
astNodes
.
deriveds
)
{
cursors
[
classAST
]
=
removeCastMethods
(
classAST
);
const
QString
className
=
oo
(
classAST
->
symbol
->
name
());
const
QString
methodName
=
QLatin1String
(
"as"
)
+
className
.
mid
(
0
,
className
.
length
()
-
3
);
replacementCastMethods
[
classAST
]
=
QString
(
" virtual %1 *%2() { return this; }
\n
"
).
arg
(
className
,
methodName
);
castMethods
.
append
(
QString
(
" virtual %1 *%2() { return 0; }"
).
arg
(
className
,
methodName
));
}
if
(
!
baseCastMethodCursors
.
isEmpty
())
{
castMethods
.
sort
();
for
(
int
i
=
0
;
i
<
baseCastMethodCursors
.
length
();
++
i
)
{
baseCastMethodCursors
[
i
].
removeSelectedText
();
}
baseCastMethodCursors
.
first
().
insertText
(
castMethods
.
join
(
QLatin1String
(
"
\n
"
)));
}
for
(
int
classIndex
=
0
;
classIndex
<
astNodes
.
deriveds
.
size
();
++
classIndex
)
{
ClassSpecifierAST
*
classAST
=
astNodes
.
deriveds
.
at
(
classIndex
);
// remove the cast methods.
QList
<
QTextCursor
>
c
=
cursors
.
value
(
classAST
);
for
(
int
i
=
0
;
i
<
c
.
length
();
++
i
)
{
c
[
i
].
removeSelectedText
();
}
astNodes
.
endOfPublicClassSpecifiers
[
classIndex
].
insertText
(
replacementCastMethods
.
value
(
classAST
));
}
std
::
cout
<<
qPrintable
(
document
.
toPlainText
());
}
}
src/tools/cplusplus/cplusplus.pro
0 → 100644
View file @
01473fec
######################################################################
#
Automatically
generated
by
qmake
(
2.01
a
)
Mon
Nov
9
11
:
48
:
58
2009
######################################################################
QT
=
core
gui
macx
:
CONFIG
-=
app_bundle
TEMPLATE
=
app
TARGET
=
DEPENDPATH
+=
.
INCLUDEPATH
+=
.
include
(..
/../
libs
/
cplusplus
/
cplusplus
-
lib
.
pri
)
#
Input
SOURCES
+=
Main
.
cpp
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment