Skip to content
Snippets Groups Projects
Commit 7bf3fd24 authored by Henry's avatar Henry
Browse files

Coco/R based parsers are no longer supported

parent bf3cd16f
Branches
Tags
No related merge requests found
......@@ -58,7 +58,7 @@ include $(RULES)/$(WM_LINK_LANGUAGE)
# targets
#------------------------------------------------------------------------------
all: $(WMAKE_BIN)/dirToString $(WMAKE_BIN)/wmkdep $(WMAKE_BIN)/wmkdepend
all: $(WMAKE_BIN)/dirToString $(WMAKE_BIN)/wmkdep
clean:
rm -f $(WMAKE_BIN)/* 2>/dev/null
......@@ -76,13 +76,4 @@ $(WMAKE_BIN)/wmkdep: wmkdep.l
@rm -f lex.yy.c 2>/dev/null
# for bootstrapping - use generated files directly (instead of from .atg file)
$(WMAKE_BIN)/wmkdepend: wmkdepend.cpp \
wmkdependParser.cpp wmkdependScanner.cpp \
wmkdependParser.h wmkdependScanner.h
@mkdir -p $(WMAKE_BIN)
$(CC) $(c++FLAGS) \
wmkdepend.cpp wmkdependParser.cpp wmkdependScanner.cpp \
-o $(WMAKE_BIN)/wmkdepend
#------------------------------------------------------------------------------
#!/bin/sh
#------------------------------------------------------------------------------
# ========= |
# \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
# \\ / O peration |
# \\ / A nd | Copyright (C) 2011-2014 OpenFOAM Foundation
# \\/ M anipulation |
#------------------------------------------------------------------------------
# License
# This file is part of OpenFOAM.
#
# OpenFOAM is free software: you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# for more details.
#
# You should have received a copy of the GNU General Public License
# along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
#
# Script
# makeParserCode
#
# Description
# Use coco-cpp to create parser code
#
#------------------------------------------------------------------------------
cd ${0%/*} || exit 1 # Run from this directory
Script=${0##*/}
binDir=$WM_THIRD_PARTY_DIR/platforms/$WM_ARCH$WM_COMPILER/coco-cpp/bin
frames=$binDir/../share/coco-cpp
[ -d "$binDir" -a -x "$binDir/coco-cpp" ] || {
echo "$Script error: no coco-cpp binary found"
exit 1
}
[ -d "$frames" -a -f "$frames/Parser.frame" -a -f "$frames/Scanner.frame" ] || {
echo "$Script error: no coco-cpp frames found"
exit 1
}
# Run coco-cpp:
$binDir/coco-cpp wmkdependParser.atg
echo
echo Done
#------------------------------------------------------------------------------
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation |
------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
OpenFOAM is free software: you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Application
wmkdepend
Description
A fast dependency list generator that emulates the behaviour and
output of cpp -M. However, the output contains no duplications and
is ~40% faster than cpp.
The algorithm uses flex to scan for includes and searches the files
found. Each file is entered into a hash table so that files are scanned
only once. This is why this program is faster than cpp.
Usage
wmkdepend [ -Idir ... -Idir ] [ -iheader .. -iheader ] filename
\*---------------------------------------------------------------------------*/
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include "wmkdependParser.h"
// Note: since we use the Coco/R default error messages, we must use
// wide streams for stderr.
void printUsage(const char* message = NULL)
{
if (message)
{
fwprintf(stderr, L"\nError: %s\n\n", message);
}
fwprintf
(
stderr,
L"Usage: wmkdepend %s filename\nOptions:\n%s\n",
"[ -Idir ... -Idir ] [ -iheader .. -iheader ]",
" -Idir specify include directory\n"
" -iheader specify header name to ignore\n"
);
}
int main(int argc, char* argv[])
{
if (argc == 1)
{
printUsage("input file not supplied");
::exit(1);
}
for (int i=1; i < argc; i++)
{
if (strncmp(argv[i], "-I", 2) == 0)
{
if (strlen(argv[i]) > 2)
{
std::string dirName(argv[i] + 2);
// add trailing slash if required
if (dirName.rfind('/') != dirName.size()-1)
{
dirName += '/';
}
wmake::Parser::includeDirs.push_back(dirName);
}
}
else if (strncmp(argv[i], "-i", 2) == 0)
{
if (strlen(argv[i]) > 2)
{
wmake::Parser::visitedFiles.insert(argv[i] + 2);
}
}
}
std::string sourceFile(argv[argc-1]);
fwprintf
(
stderr,
L"Making dependency list for source file %s\n",
sourceFile.c_str()
);
std::string::size_type basePos = sourceFile.rfind('/');
if (basePos == std::string::npos)
{
basePos = 0;
}
else
{
basePos++;
}
std::string::size_type dotPos = sourceFile.rfind('.');
if
(
dotPos == std::string::npos
|| dotPos == sourceFile.size()-1
|| dotPos <= basePos
)
{
fwprintf
(
stderr,
L"cannot find extension in source file name %s\n",
sourceFile.c_str()
);
::exit(1);
}
std::string depFile = sourceFile.substr(0, dotPos);
depFile += ".dep";
const std::string sourceExt = sourceFile.substr(dotPos);
if (sourceExt == ".java")
{
// import directories to ignore
wmake::Parser::ignoreDir("java.*");
wmake::Parser::ignoreDir("org.*");
wmake::Parser::ignoreDir("com.*");
wmake::Parser::ignoreDir("sunw.*");
wmake::Parser::ignoreDir("sun.*");
wmake::Parser::ignoreDir("launcher.*");
std::cout
<< "$(CLASSES_DIR)/"
<< sourceFile.substr(basePos, dotPos - basePos) << ".class: "
<< depFile << "\n";
}
else
{
std::cout
<< "$(OBJECTS_DIR)/"
<< sourceFile.substr(basePos, dotPos - basePos) << ".o: "
<< depFile << "\n";
}
wmake::Parser::sourceFile = sourceFile;
wmake::Parser::depFile = depFile;
wmake::Parser::includeFile(sourceFile);
return 0;
}
/*****************************************************************************/
/*---------------------------------------------------------------------------*\
Attributed Grammar for Coco/R (-*- C++ -*- version)
compile with:
coco-cpp wmkdependParser.atg
\*---------------------------------------------------------------------------*/
[copy]
/*---------------------------------*- C++ -*---------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
OpenFOAM is free software: you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
@file wmkdependParser.atg
Description
An attributed Coco/R grammar to parse C/C++, Fortran and Java files
for include and import statements.
SourceFiles
generated
\*---------------------------------------------------------------------------*/
[/copy]
#include <iostream>
#include <string>
#include <list>
#include <set>
/*---------------------------------------------------------------------------*/
COMPILER wmkdepend
// grammar pragmas:
$namespace=wmake
$prefix=wmkdepend
$define=FORCE_UTF8
/*---------------------------------------------------------------------------*/
private:
//! Set of (java) directories already visited
static std::set<std::string> visitedDirs_;
//! Replace all '.' with '/'
static void dotToSlash(std::string& name);
//! Import (java) directories
static void importDir(const std::string& dirName);
//! Import (java) file
static void importFile(const std::string& name);
public:
//! Set of files already visited
static std::set<std::string> visitedFiles;
//! Include directories to search
static std::list<std::string> includeDirs;
//! The name of the top-level source file
static std::string sourceFile;
//! The name of the top-level dep file
static std::string depFile;
//! Add directory to list of visited dirs, thus effectively ignoring it
static void ignoreDir(const std::string& name);
//! Include file
static void includeFile(const std::string& name);
/*---------------------------------------------------------------------------*/
[code]
#include <sys/types.h>
#include <dirent.h>
std::set<std::string> Parser::visitedDirs_;
std::set<std::string> Parser::visitedFiles;
std::list<std::string> Parser::includeDirs;
std::string Parser::sourceFile;
std::string Parser::depFile;
void Parser::dotToSlash(std::string& name)
{
std::string::size_type start = 0;
while ((start = name.find('.', start)) != std::string::npos)
{
name.replace(start, 1, 1, '/');
start++;
}
}
void Parser::ignoreDir(const std::string& name)
{
visitedDirs_.insert(name);
}
void Parser::includeFile(const std::string& name)
{
if (!visitedFiles.insert(name).second)
{
return; // already existed (did not insert)
}
// use stdio and buffering within Coco/R -- (faster)
FILE *fh = fopen(name.c_str(), "r");
if (fh)
{
std::cout << depFile << ": " << name << "\n";
}
else
{
for
(
std::list<std::string>::const_iterator iter = includeDirs.begin();
iter != includeDirs.end();
++iter
)
{
const std::string pathName = *iter + name;
fh = fopen(pathName.c_str(), "r");
if (fh)
{
std::cout << depFile << ": " << pathName << "\n";
break;
}
}
}
if (fh)
{
Scanner scanner(fh);
Parser parser(&scanner);
parser.Parse();
fclose(fh);
}
else
{
fwprintf
(
stderr,
L"could not open file %s for source file %s\n",
name.c_str(), sourceFile.c_str()
);
// only report the first occurance
visitedFiles.insert(name);
}
}
void Parser::importFile(const std::string& name)
{
// check if a globbed form was already visited
std::string::size_type dotPos = name.find('.');
if (dotPos != std::string::npos)
{
std::string dirGlob = name.substr(0, dotPos);
dirGlob += ".*";
if (visitedDirs_.find(dirGlob) != visitedDirs_.end())
{
return;
}
}
std::string javaFileName = name;
dotToSlash(javaFileName);
javaFileName += ".java";
includeFile(javaFileName);
}
void Parser::importDir(const std::string& name)
{
if (!visitedDirs_.insert(name).second)
{
return; // already existed (did not insert)
}
std::string dirName = name;
dotToSlash(dirName);
DIR *source = opendir(dirName.c_str());
if (source)
{
struct dirent *list;
// Read and parse all the entries in the directory
while ((list = readdir(source)) != NULL)
{
const char* ext = strstr(list->d_name, ".java");
// avoid matching on something like '.java~'
if (ext && strlen(ext) == 5)
{
std::string pathName = dirName + list->d_name;
includeFile(pathName);
}
}
closedir(source);
}
else
{
fwprintf
(
stderr,
L"could not open directory %s\n",
dirName.c_str()
);
return;
}
}
[/code]
/*---------------------------------------------------------------------------*/
CHARACTERS
letter = 'A'..'Z' + 'a'..'z' + '_'.
digit = "0123456789".
cr = '\r'.
lf = '\n'.
tab = '\t'.
stringCh = ANY - '"' - '\\' - cr - lf.
printable = '\u0020' .. '\u007e'.
java_letter = letter + '$'.
// * * * * * * * * * * * * * * * * TOKENS * * * * * * * * * * * * * * * * * //
TOKENS
// string
string =
'"' { stringCh | '\\' printable } '"'.
// single-quoted string (eg, Fortran)
sqstring =
'\'' { stringCh | '\\' printable } '\''.
// for java import
package_name =
java_letter { java_letter | digit }
{ '.' java_letter { java_letter | digit } } .
// for java import
package_dir =
java_letter { java_letter | digit }
{ '.' java_letter { java_letter | digit } } ".*" .
// * * * * * * * * * * * PRAGMAS / COMMENTS / IGNORE * * * * * * * * * * * //
COMMENTS FROM "/*" TO "*/" NESTED
COMMENTS FROM "//" TO lf
IGNORE tab
// * * * * * * * * * * * * * * * PRODUCTIONS * * * * * * * * * * * * * * * //
PRODUCTIONS
wmkdepend
=
{
// C/C++-style includes
'#'
[
"include"
[
string (.
if (isUTF8())
{
includeFile(t->toStringUTF8(1, t->length()-2));
}
else
{
includeFile(t->toString(1, t->length()-2));
}
.)
]
]
[ ANY { ANY } ] '\n' // skip trailing junk
// Fortran-style includes
| "include"
[
sqstring (.
if (isUTF8())
{
includeFile(t->toStringUTF8(1, t->length()-2));
}
else
{
includeFile(t->toString(1, t->length()-2));
}
.)
]
[ ANY { ANY } ] '\n' // skip trailing junk
// Java imports
| "import"
(
package_dir (.
if (isUTF8())
{
importDir(t->toStringUTF8());
}
else
{
importDir(t->toString());
}
.)
| package_name (.
if (isUTF8())
{
importFile(t->toStringUTF8());
}
else
{
importFile(t->toString());
}
.)
)
';'
[ ANY { ANY } ] '\n' // skip trailing junk
| [ ANY { ANY } ] '\n' // skip any other lines
}
.
/*---------------------------------------------------------------------------*/
END wmkdepend.
// ************************************************************************* //
/*---------------------------------*- C++ -*---------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
OpenFOAM is free software: you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
@file wmkdependParser.atg
Description
An attributed Coco/R grammar to parse C/C++, Fortran and Java files
for include and import statements.
SourceFiles
generated
\*---------------------------------------------------------------------------*/
// This file was generated with Coco/R C++ (10 Mar 2010)
// http://www.ssw.uni-linz.ac.at/coco/
// with these defines:
// - FORCE_UTF8
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cwchar>
#include <sstream>
#include "wmkdependParser.h"
namespace wmake {
#include <sys/types.h>
#include <dirent.h>
std::set<std::string> Parser::visitedDirs_;
std::set<std::string> Parser::visitedFiles;
std::list<std::string> Parser::includeDirs;
std::string Parser::sourceFile;
std::string Parser::depFile;
void Parser::dotToSlash(std::string& name)
{
std::string::size_type start = 0;
while ((start = name.find('.', start)) != std::string::npos)
{
name.replace(start, 1, 1, '/');
start++;
}
}
void Parser::ignoreDir(const std::string& name)
{
visitedDirs_.insert(name);
}
void Parser::includeFile(const std::string& name)
{
if (!visitedFiles.insert(name).second)
{
return; // already existed (did not insert)
}
// use stdio and buffering within Coco/R -- (faster)
FILE *fh = fopen(name.c_str(), "r");
if (fh)
{
std::cout << depFile << ": " << name << "\n";
}
else
{
for
(
std::list<std::string>::const_iterator iter = includeDirs.begin();
iter != includeDirs.end();
++iter
)
{
const std::string pathName = *iter + name;
fh = fopen(pathName.c_str(), "r");
if (fh)
{
std::cout << depFile << ": " << pathName << "\n";
break;
}
}
}
if (fh)
{
Scanner scanner(fh);
Parser parser(&scanner);
parser.Parse();
fclose(fh);
}
else
{
fwprintf
(
stderr,
L"could not open file %s for source file %s\n",
name.c_str(), sourceFile.c_str()
);
// only report the first occurance
visitedFiles.insert(name);
}
}
void Parser::importFile(const std::string& name)
{
// check if a globbed form was already visited
std::string::size_type dotPos = name.find('.');
if (dotPos != std::string::npos)
{
std::string dirGlob = name.substr(0, dotPos);
dirGlob += ".*";
if (visitedDirs_.find(dirGlob) != visitedDirs_.end())
{
return;
}
}
std::string javaFileName = name;
dotToSlash(javaFileName);
javaFileName += ".java";
includeFile(javaFileName);
}
void Parser::importDir(const std::string& name)
{
if (!visitedDirs_.insert(name).second)
{
return; // already existed (did not insert)
}
std::string dirName = name;
dotToSlash(dirName);
DIR *source = opendir(dirName.c_str());
if (source)
{
struct dirent *list;
// Read and parse all the entries in the directory
while ((list = readdir(source)) != NULL)
{
const char* ext = strstr(list->d_name, ".java");
// avoid matching on something like '.java~'
if (ext && strlen(ext) == 5)
{
std::string pathName = dirName + list->d_name;
includeFile(pathName);
}
}
closedir(source);
}
else
{
fwprintf
(
stderr,
L"could not open directory %s\n",
dirName.c_str()
);
return;
}
}
//! @cond fileScope
//
// Create by copying str - only used locally
inline static wchar_t* coco_string_create(const wchar_t* str)
{
const int len = wcslen(str);
wchar_t* dst = new wchar_t[len + 1];
wcsncpy(dst, str, len);
dst[len] = 0;
return dst;
}
// Free storage and nullify the argument
inline static void coco_string_delete(wchar_t* &str)
{
delete[] str;
str = NULL;
}
//
//! @endcond
// ----------------------------------------------------------------------------
// Parser Implementation
// ----------------------------------------------------------------------------
void Parser::SynErr(int n)
{
if (errDist >= minErrDist) errors->SynErr(la->line, la->col, n);
errDist = 0;
}
void Parser::SemErr(const std::wstring& msg)
{
if (errDist >= minErrDist) errors->Error(t->line, t->col, msg);
errDist = 0;
}
bool Parser::isUTF8() const
{
return scanner && scanner->buffer && scanner->buffer->isUTF8();
}
void Parser::Get()
{
for (;;)
{
t = la;
la = scanner->Scan();
if (la->kind <= maxT)
{
++errDist;
break;
}
if (dummyToken != t)
{
dummyToken->kind = t->kind;
dummyToken->pos = t->pos;
dummyToken->col = t->col;
dummyToken->line = t->line;
dummyToken->next = NULL;
coco_string_delete(dummyToken->val);
dummyToken->val = coco_string_create(t->val);
t = dummyToken;
}
la = t;
}
}
void Parser::Expect(int n)
{
if (la->kind == n)
{
Get();
}
else
{
SynErr(n);
}
}
void Parser::ExpectWeak(int n, int follow)
{
if (la->kind == n)
{
Get();
}
else
{
SynErr(n);
while (!StartOf(follow))
{
Get();
}
}
}
bool Parser::WeakSeparator(int n, int syFol, int repFol)
{
if (la->kind == n)
{
Get();
return true;
}
else if (StartOf(repFol))
{
return false;
}
else
{
SynErr(n);
while (!(StartOf(syFol) || StartOf(repFol) || StartOf(0)))
{
Get();
}
return StartOf(syFol);
}
}
void Parser::wmkdepend()
{
while (StartOf(1)) {
if (la->kind == 5) {
Get();
if (la->kind == 6) {
Get();
if (la->kind == 1) {
Get();
if (isUTF8())
{
includeFile(t->toStringUTF8(1, t->length()-2));
}
else
{
includeFile(t->toString(1, t->length()-2));
}
}
}
if (StartOf(2)) {
Get();
while (StartOf(3)) {
Get();
}
}
Expect(7);
} else if (la->kind == 6) {
Get();
if (la->kind == 2) {
Get();
if (isUTF8())
{
includeFile(t->toStringUTF8(1, t->length()-2));
}
else
{
includeFile(t->toString(1, t->length()-2));
}
}
if (StartOf(4)) {
Get();
while (StartOf(3)) {
Get();
}
}
Expect(7);
} else if (la->kind == 8) {
Get();
if (la->kind == 4) {
Get();
if (isUTF8())
{
importDir(t->toStringUTF8());
}
else
{
importDir(t->toString());
}
} else if (la->kind == 3) {
Get();
if (isUTF8())
{
importFile(t->toStringUTF8());
}
else
{
importFile(t->toString());
}
} else SynErr(11);
Expect(9);
if (StartOf(3)) {
Get();
while (StartOf(3)) {
Get();
}
}
Expect(7);
} else {
if (StartOf(5)) {
Get();
while (StartOf(3)) {
Get();
}
}
Expect(7);
}
}
}
void Parser::Parse()
{
t = NULL;
// might call Parse() twice
if (dummyToken) {
coco_string_delete(dummyToken->val);
delete dummyToken;
}
dummyToken = new Token(coco_string_create(L"Dummy Token"));
la = dummyToken;
Get();
wmkdepend();
Expect(0); // expect end-of-file automatically added
}
Parser::Parser(Scanner* scan, Errors* err)
:
dummyToken(NULL),
deleteErrorsDestruct_(!err),
errDist(minErrDist),
scanner(scan),
errors(err),
t(NULL),
la(NULL)
{
if (!errors) // add in default error handling
{
errors = new Errors();
}
// user-defined initializations:
}
bool Parser::StartOf(int s)
{
const bool T = true;
const bool x = false;
static const bool set[6][12] =
{
{T,x,x,x, x,x,x,x, x,x,x,x},
{x,T,T,T, T,T,T,T, T,T,T,x},
{x,x,T,T, T,T,x,x, T,T,T,x},
{x,T,T,T, T,T,T,x, T,T,T,x},
{x,T,x,T, T,T,T,x, T,T,T,x},
{x,T,T,T, T,x,x,x, x,T,T,x}
};
return set[s][la->kind];
}
Parser::~Parser()
{
if (deleteErrorsDestruct_) { delete errors; } // delete default error handling
if (dummyToken) {
coco_string_delete(dummyToken->val);
delete dummyToken;
}
// user-defined destruction:
}
// ----------------------------------------------------------------------------
// Errors Implementation
// ----------------------------------------------------------------------------
Errors::Errors()
:
count(0)
{}
Errors::~Errors()
{}
void Errors::clear()
{
count = 0;
}
std::wstring Errors::strerror(int n)
{
switch (n) {
case 0: return L"EOF expected"; break;
case 1: return L"string expected"; break;
case 2: return L"sqstring expected"; break;
case 3: return L"package_name expected"; break;
case 4: return L"package_dir expected"; break;
case 5: return L"\"#\" expected"; break;
case 6: return L"\"include\" expected"; break;
case 7: return L"\"\\n\" expected"; break;
case 8: return L"\"import\" expected"; break;
case 9: return L"\";\" expected"; break;
case 10: return L"??? expected"; break;
case 11: return L"invalid wmkdepend"; break;
default:
{
// std::wostringstream buf; (this typedef might be missing)
std::basic_ostringstream<wchar_t> buf;
buf << "error " << n;
return buf.str();
}
break;
}
}
void Errors::Warning(const std::wstring& msg)
{
fwprintf(stderr, L"%ls\n", msg.c_str());
}
void Errors::Warning(int line, int col, const std::wstring& msg)
{
fwprintf(stderr, L"-- line %d col %d: %ls\n", line, col, msg.c_str());
}
void Errors::Error(int line, int col, const std::wstring& msg)
{
fwprintf(stderr, L"-- line %d col %d: %ls\n", line, col, msg.c_str());
count++;
}
void Errors::SynErr(int line, int col, int n)
{
this->Error(line, col, this->strerror(n));
}
void Errors::Exception(const std::wstring& msg)
{
fwprintf(stderr, L"%ls", msg.c_str());
::exit(1);
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace
// ************************************************************************* //
/*---------------------------------*- C++ -*---------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
OpenFOAM is free software: you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
@file wmkdependParser.atg
Description
An attributed Coco/R grammar to parse C/C++, Fortran and Java files
for include and import statements.
SourceFiles
generated
\*---------------------------------------------------------------------------*/
// This file was generated with Coco/R C++ (10 Mar 2010)
// http://www.ssw.uni-linz.ac.at/coco/
// with these defines:
// - FORCE_UTF8
#ifndef COCO_wmkdependPARSER_H__
#define COCO_wmkdependPARSER_H__
#include <iostream>
#include <string>
#include <list>
#include <set>
/*---------------------------------------------------------------------------*/
#include "wmkdependScanner.h"
namespace wmake {
/*---------------------------------------------------------------------------*\
Class Errors Declaration
\*---------------------------------------------------------------------------*/
//! Parser error handling
class Errors
{
public:
int count; //!< The number of errors detected
//! Return a string describing the given error code.
static std::wstring strerror(int n);
Errors(); //!< Construct null - start with no errors
virtual ~Errors(); //!< Destructor
virtual void clear(); //!< Clear the error count
//! Handle a general warning 'msg'
virtual void Warning(const std::wstring& msg);
//! Handle a general warning 'msg'
virtual void Warning(int line, int col, const std::wstring& msg);
//! Handle general error 'msg' (eg, a semantic error)
virtual void Error(int line, int col, const std::wstring& msg);
//! Handle syntax error 'n', uses strerror for the message, calls Error()
virtual void SynErr(int line, int col, int n);
//! Handle a general exception 'msg'
virtual void Exception(const std::wstring& msg);
}; // Errors
/*---------------------------------------------------------------------------*\
Class Parser Declaration
\*---------------------------------------------------------------------------*/
//! A Coco/R Parser
class Parser
{
enum {
_EOF=0,
_string=1,
_sqstring=2,
_package_name=3,
_package_dir=4,
maxT = 10 //<! max term (w/o pragmas)
};
static const int minErrDist = 2; //!< min. distance before reporting errors
Token *dummyToken;
bool deleteErrorsDestruct_; //!< delete the 'errors' member in destructor
int errDist;
void SynErr(int n); //!< Handle syntax error 'n'
void Get();
void Expect(int n);
bool StartOf(int s);
void ExpectWeak(int n, int follow);
bool WeakSeparator(int n, int syFol, int repFol);
public:
Scanner *scanner;
Errors *errors;
Token *t; //!< last recognized token
Token *la; //!< lookahead token
private:
//! Set of (java) directories already visited
static std::set<std::string> visitedDirs_;
//! Replace all '.' with '/'
static void dotToSlash(std::string& name);
//! Import (java) directories
static void importDir(const std::string& dirName);
//! Import (java) file
static void importFile(const std::string& name);
public:
//! Set of files already visited
static std::set<std::string> visitedFiles;
//! Include directories to search
static std::list<std::string> includeDirs;
//! The name of the top-level source file
static std::string sourceFile;
//! The name of the top-level dep file
static std::string depFile;
//! Add directory to list of visited dirs, thus effectively ignoring it
static void ignoreDir(const std::string& name);
//! Include file
static void includeFile(const std::string& name);
/*---------------------------------------------------------------------------*/
//! Construct for the specified scanner
/*!
* Use the default error handling, or optionally provide an error
* handler, which will not be deleted upon destruction.
*/
Parser(Scanner* scan, Errors* err = 0);
~Parser();
void Parse(); //!< Execute the parse operation
void SemErr(const std::wstring& msg); //!< Handle semantic error
bool isUTF8() const; //!< Return true if scanner buffer is UTF8
void wmkdepend();
}; // end Parser
} // End namespace
#endif // COCO_wmkdependPARSER_H__
// ************************************************************************* //
This diff is collapsed.
/*---------------------------------*- C++ -*---------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
OpenFOAM is free software: you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
@file wmkdependParser.atg
Description
An attributed Coco/R grammar to parse C/C++, Fortran and Java files
for include and import statements.
SourceFiles
generated
\*---------------------------------------------------------------------------*/
// This file was generated with Coco/R C++ (10 Mar 2010)
// http://www.ssw.uni-linz.ac.at/coco/
// with these defines:
// - FORCE_UTF8
#ifndef COCO_wmkdependSCANNER_H__
#define COCO_wmkdependSCANNER_H__
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cwchar>
#include <string>
#include <fstream>
#include <iostream>
namespace wmake {
// * * * * * * * * * * * Miscellaneous String Routines * * * * * * * * * * * //
//! Simple lower-case string transformation
template<class StringT>
inline void coco_string_toLower(StringT& str)
{
for
(
typename StringT::iterator iter = str.begin();
iter != str.end();
++iter
)
{
if (*iter >= 'A' && *iter <= 'Z')
{
*iter += ('a' - 'A'); // lower-case
}
}
}
//! Simple string hashing function
template<class StringT>
inline int coco_string_hash(const StringT& str)
{
int h = 0;
for
(
typename StringT::const_iterator iter = str.begin();
iter != str.end();
++iter
)
{
h = (h * 7) ^ *iter;
}
return h < 0 ? -h : h;
}
//
// String conversions
// ~~~~~~~~~~~~~~~~~~
//! Convert wide string to double
inline double coco_string_toDouble(const wchar_t* str)
{
return str ? wcstod(str, NULL) : 0;
}
//! Convert wide string to long
inline long coco_string_toLong(const wchar_t* str)
{
return str ? wcstol(str, NULL, 10) : 0;
}
//! A byte string (restricted to 8bit values) by copying str
std::string coco_stdString(const wchar_t* str);
//! A byte string (restricted to 8bit values) by copying str,
//! up to length characters long
std::string coco_stdString(const wchar_t* str, unsigned length);
//! A byte substring (restricted to 8bit values) of str,
//! starting at index and length characters long
std::string coco_stdString(const wchar_t* str, unsigned index, unsigned length);
//! A UTF8 byte string by copying str
std::string coco_stdStringUTF8(const wchar_t* str);
//! A UTF8 byte string by copying str, up to length characters long
std::string coco_stdStringUTF8(const wchar_t* str, unsigned length);
//! A UTF8 byte substring, starting at index and length characters long
std::string coco_stdStringUTF8(const wchar_t* str, unsigned index, unsigned length);
// * * * * * * * * * * * * End of String Routines * * * * * * * * * * * * * //
/*---------------------------------------------------------------------------*\
Class Token Declaration
\*---------------------------------------------------------------------------*/
/*!
* @brief Scanner Token
*
* @note since each Token is allocated by the internal heap mechanism,
* the destructor does not clean up the val member.
*/
class Token
{
public:
int kind; //!< token kind
int pos; //!< token position in the source text (starting at 0)
int col; //!< token column (starting at 1)
int line; //!< token line (starting at 1)
wchar_t* val; //!< token value (normally allocated from the internal heap)
Token *next; //!< Peek tokens are kept in linked list
int length() const; //!< The length of val, or 0 if val is NULL
//! Construct null Token, optionally with pointer to a string value
Token(wchar_t* value = 0);
~Token(); //!< Destructor - does not cleanup val member
//! Token val as byte string (restricted to 8bit values)
inline std::string toString() const
{
return coco_stdString(val);
}
//! Token val as byte string (restricted to 8bit values), up to length characters long
inline std::string toString(unsigned length) const
{
return coco_stdString(val, length);
}
//! Token val as byte string (restricted to 8bit values), starting at index and length characters long
inline std::string toString(unsigned index, unsigned length) const
{
return coco_stdString(val, index, length);
}
//! Token val as UTF8 byte string
inline std::string toStringUTF8() const
{
return coco_stdStringUTF8(val);
}
//! Token val as UTF8 byte string, up to length characters long
inline std::string toStringUTF8(unsigned length) const
{
return coco_stdStringUTF8(val, length);
}
//! Token val as UTF8 byte substring, starting at index and length characters long
inline std::string toStringUTF8(unsigned index, unsigned length) const
{
return coco_stdStringUTF8(this->val, index, length);
}
};
/*---------------------------------------------------------------------------*\
Class Buffer Declaration
\*---------------------------------------------------------------------------*/
/*!
* @brief Scanner Buffer
*
* This Buffer supports the following cases:
* -# seekable stream (file)
* -# whole stream in buffer
* -# part of stream in buffer
* -# non seekable stream (network, console)
*/
class Buffer
{
unsigned char *buf; //!< input buffer
int bufCapacity; //!< capacity of buf
int bufLen; //!< length of buffer
int bufPos; //!< current position in buffer
int bufStart; //!< position of first byte in buffer relative to input stream
int fileLen; //!< length of input stream (may change if the stream is no file)
FILE* cStream; //!< input stdio stream (normally seekable)
std::istream* stdStream; //!< STL std stream (seekable)
bool isUserStream_; //!< was the stream opened by the user?
int ReadNextStreamChunk();
bool CanSeek() const; //!< true if stream can be seeked otherwise false
protected:
Buffer(Buffer*); //!< for the UTF8Buffer
public:
//! max unicode characters is 0xFFFF (16bit storage)
static const int MaxChar = 65535;
static const int EoF = MaxChar + 1;
//! Copy buffer contents from constant character string
Buffer(const char* chars, int len);
//! Copy buffer contents from constant character string
Buffer(const unsigned char* chars, int len);
//! @brief Attach buffer to a stdio stream.
//! User streams are not closed in the destructor
Buffer(FILE*, bool isUserStream = true);
//! @brief Attach buffer to an STL standard stream
//! User streams are not closed in the destructor
explicit Buffer(std::istream*, bool isUserStream = true);
//! Close stream (but not user streams) and free buf (if any)
virtual ~Buffer();
virtual void Close(); //!< Close stream (but not user streams)
virtual int Read(); //!< Get character from stream or buffer
virtual int Peek(); //!< Peek character from stream or buffer
virtual int GetPos() const;
virtual void SetPos(int value);
virtual bool isUTF8() const; //!< Return false - buffer is not UTF8
};
/*---------------------------------------------------------------------------*\
Class UTF8Buffer Declaration
\*---------------------------------------------------------------------------*/
//! A Scanner Buffer variant that decodes UTF-8 characters into 16bit unicode
class UTF8Buffer : public Buffer
{
public:
UTF8Buffer(Buffer* b) : Buffer(b) {}
virtual int Read();
virtual bool isUTF8() const; //!< Return true - buffer is UTF8
};
/*---------------------------------------------------------------------------*\
Class StartStates Declaration
\*---------------------------------------------------------------------------*/
//! maps characters (integers) to start states of tokens as a HashTable
class StartStates
{
//! HashTable entry
struct Entry
{
int key; //<! The lookup key
int val; //<! The data
Entry *next; //<! Pointer next Entry in sub-list
Entry(int k, int v, Entry *n=0)
:
key(k), val(v), next(n)
{}
};
static const int size_ = 128; //<! fixed HashTable size
Entry **table_;
public:
StartStates()
:
table_(new Entry*[size_])
{
memset(table_, 0, size_*sizeof(Entry*));
}
virtual ~StartStates()
{
for (int i = 0; i < size_; ++i)
{
Entry *e = table_[i];
while (e)
{
Entry *next = e->next;
delete e;
e = next;
}
}
delete[] table_;
}
void set(int key, int val)
{
const int hashIndex = unsigned(key) % size_;
table_[hashIndex] = new Entry(key, val, table_[hashIndex]);
}
int state(int key)
{
Entry *e = table_[unsigned(key) % size_];
while (e && e->key != key) e = e->next;
return e ? e->val : 0;
}
};
/*---------------------------------------------------------------------------*\
Class KeywordMap Declaration
\*---------------------------------------------------------------------------*/
//! maps strings to integers (identifiers to keyword kinds) as a HashTable
class KeywordMap
{
//! HashTable entry
struct Entry
{
const std::wstring key; //<! The lookup key
int val; //<! The data
Entry *next; //<! Pointer next Entry in sub-list
Entry(const std::wstring& k, int v, Entry *n=0)
:
key(k), val(v), next(n)
{}
};
static const int size_ = 128; //<! fixed HashTable size
Entry **table_;
public:
KeywordMap()
:
table_(new Entry*[size_])
{
memset(table_, 0, size_*sizeof(Entry*));
}
virtual ~KeywordMap()
{
for (int i = 0; i < size_; ++i)
{
Entry *e = table_[i];
while (e)
{
Entry *next = e->next;
delete e;
e = next;
}
}
delete[] table_;
}
void set(const std::wstring& key, int val)
{
const int hashIndex = coco_string_hash(key) % size_;
table_[hashIndex] = new Entry(key, val, table_[hashIndex]);
}
int get(const std::wstring& key, int defaultVal)
{
Entry *e = table_[coco_string_hash(key) % size_];
while (e && e->key != key) e = e->next;
return e ? e->val : defaultVal;
}
};
/*---------------------------------------------------------------------------*\
Class Scanner Declaration
\*---------------------------------------------------------------------------*/
//! A Coco/R Scanner
class Scanner
{
static const int maxT = 10;
static const int noSym = 10;
static const int eofSym = 0; //!< end-of-file token id
static const char EOL = '\n'; //!< end-of-line character
void *firstHeap; //!< the start of the heap management
void *heap; //!< the currently active block
void *heapTop; //!< the top of the heap
void **heapEnd; //!< the end of the last heap block
StartStates start; //!< A map of start states for particular characters
KeywordMap keywords; //!< A hash of keyword literals to token kind
Token *t; //!< current token
wchar_t *tval; //!< text of current token
int tvalLength; //!< maximum capacity (length) for tval
int tlen; //!< length of tval
Token *tokens; //!< list of tokens already peeked (first token is a dummy)
Token *pt; //!< current peek token
int ch; //!< current input character
int pos; //!< byte position of current character
int line; //!< line number of current character
int col; //!< column number of current character
int oldEols; //!< the number of EOLs that appeared in a comment
void CreateHeapBlock(); //!< add a heap block, freeing unused ones
Token* CreateToken(); //!< fit token on the heap
void AppendVal(Token* tok); //!< adjust tok->val to point to the heap and copy tval into it
void SetScannerBehindT();
void Init(); //!< complete the initialization for the constructors
void NextCh(); //!< get the next input character into ch
void AddCh(); //!< append the character ch to tval
bool Comment0();
bool Comment1();
Token* NextToken(); //!< get the next token
public:
//! The scanner buffer
Buffer *buffer;
//! Attach scanner to an existing character buffer
Scanner(const char* chars, int len);
//! Attach scanner to an existing character buffer
Scanner(const unsigned char* chars, int len);
//! Attach scanner to an existing open file handle
Scanner(FILE*);
#ifdef _WIN32
//! Open a file for reading and attach scanner - Windows only
explicit Scanner(const std::wstring& fileName);
#endif
//! Open a file for reading and attach scanner
explicit Scanner(const std::string& fileName);
//! Attach scanner to an existing open STL standard stream
explicit Scanner(std::istream&);
~Scanner(); //!< free heap and allocated memory
Token* Scan(); //!< get the next token (possibly a token already seen during peeking)
Token* Peek(); //!< peek for the next token, ignore pragmas
void ResetPeek(); //!< ensure that peeking starts at the current scan position
int Line() const; //!< Return the current line
void Line(int lineNo); //!< Define the starting line for reporting errors
}; // end Scanner
} // End namespace
#endif // COCO_wmkdependSCANNER_H__
// ************************************************************************* //
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment