mirror of
https://github.com/reactos/reactos.git
synced 2025-08-02 21:56:06 +00:00
Generate automatic dependencies.
svn path=/branches/xmlbuildsystem/; revision=13371
This commit is contained in:
parent
adeb8563b5
commit
6052ab4bd7
11 changed files with 325 additions and 83 deletions
|
@ -1,5 +1,6 @@
|
||||||
<module name="freeldr_base" type="objectlibrary">
|
<module name="freeldr_base" type="objectlibrary">
|
||||||
<include base="freeldr_base">include</include>
|
<include base="freeldr_base">include</include>
|
||||||
|
<include base="freeldr_base">cache</include>
|
||||||
<compilerflag>-nostdlib</compilerflag>
|
<compilerflag>-nostdlib</compilerflag>
|
||||||
<compilerflag>-nostdinc</compilerflag>
|
<compilerflag>-nostdinc</compilerflag>
|
||||||
<compilerflag>-ffreestanding</compilerflag>
|
<compilerflag>-ffreestanding</compilerflag>
|
||||||
|
|
|
@ -13,20 +13,42 @@
|
||||||
|
|
||||||
/* Read at most this amount of bytes from each file and assume that all #includes are located within this block */
|
/* Read at most this amount of bytes from each file and assume that all #includes are located within this block */
|
||||||
#define MAX_BYTES_TO_READ 4096
|
#define MAX_BYTES_TO_READ 4096
|
||||||
|
|
||||||
using std::string;
|
using std::string;
|
||||||
using std::vector;
|
using std::vector;
|
||||||
using std::map;
|
using std::map;
|
||||||
|
|
||||||
SourceFile::SourceFile ( AutomaticDependency* automaticDependency,
|
SourceFile::SourceFile ( AutomaticDependency* automaticDependency,
|
||||||
Module& module,
|
Module& module,
|
||||||
const string& filename )
|
const string& filename,
|
||||||
|
SourceFile* parent,
|
||||||
|
bool isNonAutomaticDependency )
|
||||||
: automaticDependency ( automaticDependency ),
|
: automaticDependency ( automaticDependency ),
|
||||||
module ( module ),
|
module ( module ),
|
||||||
filename ( filename )
|
filename ( filename ),
|
||||||
|
isNonAutomaticDependency ( isNonAutomaticDependency )
|
||||||
{
|
{
|
||||||
|
if ( parent != NULL )
|
||||||
|
parents.push_back ( parent );
|
||||||
|
GetDirectoryAndFilenameParts ();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
SourceFile::GetDirectoryAndFilenameParts ()
|
||||||
|
{
|
||||||
|
size_t index = filename.find_last_of ( CSEP );
|
||||||
|
if ( index != string::npos )
|
||||||
|
{
|
||||||
|
directoryPart = filename.substr ( 0, index );
|
||||||
|
filenamePart = filename.substr ( index + 1, filename.length () - index );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
directoryPart = "";
|
||||||
|
filenamePart = filename;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
SourceFile::Close ()
|
SourceFile::Close ()
|
||||||
{
|
{
|
||||||
|
@ -87,14 +109,65 @@ SourceFile::ReadInclude ( string& filename )
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
SourceFile::IsParentOf ( const SourceFile* parent,
|
||||||
|
const SourceFile* child )
|
||||||
|
{
|
||||||
|
size_t i;
|
||||||
|
for ( i = 0; i < child->parents.size (); i++ )
|
||||||
|
{
|
||||||
|
if ( child->parents[i] != NULL )
|
||||||
|
{
|
||||||
|
if ( child->parents[i] == parent )
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for ( i = 0; i < child->parents.size (); i++ )
|
||||||
|
{
|
||||||
|
if ( child->parents[i] != NULL )
|
||||||
|
{
|
||||||
|
if ( IsParentOf ( parent,
|
||||||
|
child->parents[i] ) )
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
SourceFile::IsIncludedFrom ( const string& normalizedFilename )
|
||||||
|
{
|
||||||
|
if ( normalizedFilename == filename )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
SourceFile* sourceFile = automaticDependency->RetrieveFromCache ( normalizedFilename );
|
||||||
|
if ( sourceFile == NULL )
|
||||||
|
return false;
|
||||||
|
|
||||||
|
return IsParentOf ( sourceFile,
|
||||||
|
this );
|
||||||
|
}
|
||||||
|
|
||||||
|
SourceFile*
|
||||||
|
SourceFile::GetParentSourceFile ()
|
||||||
|
{
|
||||||
|
if ( isNonAutomaticDependency )
|
||||||
|
return NULL;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
SourceFile*
|
SourceFile*
|
||||||
SourceFile::ParseFile ( const string& normalizedFilename )
|
SourceFile::ParseFile ( const string& normalizedFilename )
|
||||||
{
|
{
|
||||||
string extension = GetExtension ( normalizedFilename );
|
string extension = GetExtension ( normalizedFilename );
|
||||||
if ( extension == ".c" || extension == ".C" || extension == ".h" || extension == ".H")
|
if ( extension == ".c" || extension == ".C" || extension == ".h" || extension == ".H" )
|
||||||
{
|
{
|
||||||
|
if ( IsIncludedFrom ( normalizedFilename ) )
|
||||||
|
return NULL;
|
||||||
|
|
||||||
SourceFile* sourceFile = automaticDependency->RetrieveFromCacheOrParse ( module,
|
SourceFile* sourceFile = automaticDependency->RetrieveFromCacheOrParse ( module,
|
||||||
normalizedFilename );
|
normalizedFilename,
|
||||||
|
GetParentSourceFile () );
|
||||||
return sourceFile;
|
return sourceFile;
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
|
@ -118,7 +191,8 @@ SourceFile::Parse ()
|
||||||
if ( locatedFile )
|
if ( locatedFile )
|
||||||
{
|
{
|
||||||
SourceFile* sourceFile = ParseFile ( resolvedFilename );
|
SourceFile* sourceFile = ParseFile ( resolvedFilename );
|
||||||
files.push_back ( sourceFile );
|
if ( sourceFile != NULL )
|
||||||
|
files.push_back ( sourceFile );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
p++;
|
p++;
|
||||||
|
@ -173,10 +247,9 @@ AutomaticDependency::ProcessFile ( Module& module,
|
||||||
const File& file )
|
const File& file )
|
||||||
{
|
{
|
||||||
string normalizedFilename = NormalizeFilename ( file.name );
|
string normalizedFilename = NormalizeFilename ( file.name );
|
||||||
SourceFile sourceFile = SourceFile ( this,
|
RetrieveFromCacheOrParse ( module,
|
||||||
module,
|
normalizedFilename,
|
||||||
normalizedFilename );
|
NULL );
|
||||||
sourceFile.Parse ();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
@ -201,40 +274,54 @@ AutomaticDependency::LocateIncludedFile ( Module& module,
|
||||||
const string& includedFilename,
|
const string& includedFilename,
|
||||||
string& resolvedFilename )
|
string& resolvedFilename )
|
||||||
{
|
{
|
||||||
for ( size_t i = 0; i < module.includes.size (); i++ )
|
size_t i;
|
||||||
|
for ( i = 0; i < module.includes.size (); i++ )
|
||||||
{
|
{
|
||||||
Include* include = module.includes[0];
|
Include* include = module.includes[i];
|
||||||
if ( LocateIncludedFile ( include->directory,
|
if ( LocateIncludedFile ( include->directory,
|
||||||
includedFilename,
|
includedFilename,
|
||||||
resolvedFilename ) )
|
resolvedFilename ) )
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* FIXME: Ifs */
|
/* FIXME: Ifs */
|
||||||
|
|
||||||
|
for ( i = 0; i < module.project.includes.size (); i++ )
|
||||||
|
{
|
||||||
|
Include* include = module.project.includes[i];
|
||||||
|
if ( LocateIncludedFile ( include->directory,
|
||||||
|
includedFilename,
|
||||||
|
resolvedFilename ) )
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
resolvedFilename = "";
|
resolvedFilename = "";
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
SourceFile*
|
SourceFile*
|
||||||
AutomaticDependency::RetrieveFromCacheOrParse ( Module& module,
|
AutomaticDependency::RetrieveFromCacheOrParse ( Module& module,
|
||||||
const string& filename )
|
const string& filename,
|
||||||
|
SourceFile* parentSourceFile )
|
||||||
{
|
{
|
||||||
SourceFile* sourceFile = sourcefile_map[filename];
|
SourceFile* sourceFile = sourcefile_map[filename];
|
||||||
if ( sourceFile == NULL )
|
if ( sourceFile == NULL )
|
||||||
{
|
{
|
||||||
sourceFile = new SourceFile ( this,
|
sourceFile = new SourceFile ( this,
|
||||||
module,
|
module,
|
||||||
filename );
|
filename,
|
||||||
sourceFile->Parse ();
|
parentSourceFile,
|
||||||
|
false );
|
||||||
sourcefile_map[filename] = sourceFile;
|
sourcefile_map[filename] = sourceFile;
|
||||||
|
sourceFile->Parse ();
|
||||||
}
|
}
|
||||||
|
else if ( parentSourceFile != NULL )
|
||||||
|
sourceFile->parents.push_back ( parentSourceFile );
|
||||||
return sourceFile;
|
return sourceFile;
|
||||||
}
|
}
|
||||||
|
|
||||||
SourceFile*
|
SourceFile*
|
||||||
AutomaticDependency::RetrieveFromCache ( Module& module,
|
AutomaticDependency::RetrieveFromCache ( const string& filename )
|
||||||
const string& filename )
|
|
||||||
{
|
{
|
||||||
return sourcefile_map[filename];
|
return sourcefile_map[filename];
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,7 +19,8 @@ public:
|
||||||
|
|
||||||
|
|
||||||
MingwBackend::MingwBackend ( Project& project )
|
MingwBackend::MingwBackend ( Project& project )
|
||||||
: Backend ( project )
|
: Backend ( project ),
|
||||||
|
automaticDependencyUniqueIdCounter ( 0 )
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -240,12 +241,19 @@ MingwBackend::GenerateAllTarget () const
|
||||||
fprintf ( fMakefile, "\n\t\n\n" );
|
fprintf ( fMakefile, "\n\t\n\n" );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
string*
|
||||||
|
MingwBackend::GenerateAutomaticDependencyUniqueId ()
|
||||||
|
{
|
||||||
|
automaticDependencyUniqueIdCounter++;
|
||||||
|
return new string ( ssprintf ( "d%d",
|
||||||
|
automaticDependencyUniqueIdCounter ) );
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
MingwBackend::GenerateAutomaticDependencies () const
|
MingwBackend::GenerateAutomaticDependencies ()
|
||||||
{
|
{
|
||||||
AutomaticDependency automaticDependency ( ProjectNode );
|
AutomaticDependency automaticDependency ( ProjectNode );
|
||||||
automaticDependency.Process ();
|
automaticDependency.Process ();
|
||||||
|
|
||||||
for ( size_t mi = 0; mi < ProjectNode.modules.size (); mi++ )
|
for ( size_t mi = 0; mi < ProjectNode.modules.size (); mi++ )
|
||||||
{
|
{
|
||||||
Module& module = *ProjectNode.modules[mi];
|
Module& module = *ProjectNode.modules[mi];
|
||||||
|
@ -253,34 +261,110 @@ MingwBackend::GenerateAutomaticDependencies () const
|
||||||
{
|
{
|
||||||
File& file = *module.files[fi];
|
File& file = *module.files[fi];
|
||||||
string normalizedFilename = NormalizeFilename ( file.name );
|
string normalizedFilename = NormalizeFilename ( file.name );
|
||||||
SourceFile* sourceFile = automaticDependency.RetrieveFromCache ( module,
|
|
||||||
normalizedFilename );
|
SourceFile* sourceFile = automaticDependency.RetrieveFromCache ( normalizedFilename );
|
||||||
if ( sourceFile != NULL )
|
if ( sourceFile != NULL )
|
||||||
{
|
{
|
||||||
string dependencies ( "" );
|
string dependencies ( "" );
|
||||||
GenerateAutomaticDependenciesForFile ( sourceFile,
|
GenerateAutomaticDependenciesForFileCached ( sourceFile,
|
||||||
dependencies );
|
dependencies );
|
||||||
fprintf ( fMakefile,
|
if ( dependencies.size () > 0 )
|
||||||
"%s:: %s",
|
{
|
||||||
normalizedFilename.c_str (),
|
const string& objectFilename = MingwModuleHandler::GetObjectFilename ( normalizedFilename );
|
||||||
dependencies.c_str () );
|
string* uniqueId = automaticDependencyMap[dependencies];
|
||||||
|
if ( uniqueId == NULL )
|
||||||
|
{
|
||||||
|
uniqueId = GenerateAutomaticDependencyUniqueId ();
|
||||||
|
automaticDependencyMap[dependencies] = uniqueId;
|
||||||
|
fprintf ( fMakefile,
|
||||||
|
"%s = %s\n",
|
||||||
|
uniqueId->c_str (),
|
||||||
|
dependencies.c_str () );
|
||||||
|
}
|
||||||
|
fprintf ( fMakefile,
|
||||||
|
"%s: $(%s)\n",
|
||||||
|
objectFilename.c_str (),
|
||||||
|
uniqueId->c_str () );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
string
|
||||||
MingwBackend::GenerateAutomaticDependenciesForFile ( SourceFile* sourceFile,
|
MingwBackend::GetFilename ( const string& filename ) const
|
||||||
string& dependencies ) const
|
|
||||||
{
|
{
|
||||||
if ( dependencies.size () > 0 )
|
size_t index = filename.find_last_of ( CSEP );
|
||||||
dependencies += " ";
|
if ( index == string::npos )
|
||||||
dependencies += sourceFile->filename;
|
return filename;
|
||||||
|
else
|
||||||
|
return filename.substr ( index + 1, filename.length () - index );
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MingwBackend::GenerateAutomaticDependenciesForFileCached ( SourceFile* sourceFile,
|
||||||
|
string& dependencies )
|
||||||
|
{
|
||||||
for ( size_t i = 0; i < sourceFile->files.size (); i++)
|
for ( size_t i = 0; i < sourceFile->files.size (); i++)
|
||||||
{
|
{
|
||||||
SourceFile* childSourceFile = sourceFile->files[0];
|
SourceFile* childSourceFile = sourceFile->files[i];
|
||||||
|
|
||||||
|
string* uniqueId = automaticDependencyDirectoryMap[childSourceFile->directoryPart];
|
||||||
|
if ( uniqueId == NULL )
|
||||||
|
{
|
||||||
|
uniqueId = GenerateAutomaticDependencyUniqueId ();
|
||||||
|
automaticDependencyDirectoryMap[childSourceFile->directoryPart] = uniqueId;
|
||||||
|
fprintf ( fMakefile,
|
||||||
|
"%s = %s\n",
|
||||||
|
uniqueId->c_str (),
|
||||||
|
childSourceFile->directoryPart.c_str () );
|
||||||
|
}
|
||||||
|
dependencies += ssprintf ( "${%s}%s%s",
|
||||||
|
uniqueId->c_str (),
|
||||||
|
SSEP,
|
||||||
|
childSourceFile->filenamePart.c_str () );
|
||||||
|
|
||||||
|
string childDependencies;
|
||||||
|
if ( childSourceFile->cachedDependencies.length () > 0 )
|
||||||
|
childDependencies = childSourceFile->cachedDependencies;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
GenerateAutomaticDependenciesForFile ( childSourceFile,
|
||||||
|
childDependencies );
|
||||||
|
if ( childDependencies.length () > 200 )
|
||||||
|
{
|
||||||
|
childSourceFile->cachedDependencies = childDependencies;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
dependencies += " " + childDependencies;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MingwBackend::GenerateAutomaticDependenciesForFile ( SourceFile* sourceFile,
|
||||||
|
string& dependencies )
|
||||||
|
{
|
||||||
|
for ( size_t i = 0; i < sourceFile->files.size (); i++ )
|
||||||
|
{
|
||||||
|
SourceFile* childSourceFile = sourceFile->files[i];
|
||||||
|
|
||||||
|
if ( dependencies.length () > 0 )
|
||||||
|
dependencies += " ";
|
||||||
|
|
||||||
|
string* uniqueId = automaticDependencyDirectoryMap[childSourceFile->directoryPart];
|
||||||
|
if ( uniqueId == NULL )
|
||||||
|
{
|
||||||
|
uniqueId = GenerateAutomaticDependencyUniqueId ();
|
||||||
|
automaticDependencyDirectoryMap[childSourceFile->directoryPart] = uniqueId;
|
||||||
|
fprintf ( fMakefile,
|
||||||
|
"%s = %s\n",
|
||||||
|
uniqueId->c_str (),
|
||||||
|
childSourceFile->directoryPart.c_str () );
|
||||||
|
}
|
||||||
|
dependencies += ssprintf ( "${%s}%s%s",
|
||||||
|
uniqueId->c_str (),
|
||||||
|
SSEP,
|
||||||
|
childSourceFile->filenamePart.c_str () );
|
||||||
GenerateAutomaticDependenciesForFile ( childSourceFile,
|
GenerateAutomaticDependenciesForFile ( childSourceFile,
|
||||||
dependencies );
|
dependencies );
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,6 +8,7 @@ class MingwBackend : public Backend
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
MingwBackend ( Project& project );
|
MingwBackend ( Project& project );
|
||||||
|
virtual ~MingwBackend () { };
|
||||||
virtual void Process ();
|
virtual void Process ();
|
||||||
private:
|
private:
|
||||||
void ProcessModule ( Module& module ) const;
|
void ProcessModule ( Module& module ) const;
|
||||||
|
@ -27,10 +28,19 @@ private:
|
||||||
void GenerateGlobalVariables () const;
|
void GenerateGlobalVariables () const;
|
||||||
bool IncludeInAllTarget ( const Module& module ) const;
|
bool IncludeInAllTarget ( const Module& module ) const;
|
||||||
void GenerateAllTarget () const;
|
void GenerateAllTarget () const;
|
||||||
void GenerateAutomaticDependencies () const;
|
std::string* GenerateAutomaticDependencyUniqueId ();
|
||||||
|
void GenerateAutomaticDependencies ();
|
||||||
|
bool IsAutomaticDependencyGenerated ( SourceFile* sourceFile );
|
||||||
|
void OutputAutomaticDependenciesForFile ( SourceFile* sourceFile );
|
||||||
|
std::string GetFilename ( const std::string& filename ) const;
|
||||||
|
void GenerateAutomaticDependenciesForFileCached ( SourceFile* sourceFile,
|
||||||
|
std::string& dependencies );
|
||||||
void GenerateAutomaticDependenciesForFile ( SourceFile* sourceFile,
|
void GenerateAutomaticDependenciesForFile ( SourceFile* sourceFile,
|
||||||
std::string& dependencies ) const;
|
std::string& dependencies );
|
||||||
FILE* fMakefile;
|
FILE* fMakefile;
|
||||||
|
int automaticDependencyUniqueIdCounter;
|
||||||
|
std::map<std::string, std::string*> automaticDependencyMap;
|
||||||
|
std::map<std::string, std::string*> automaticDependencyDirectoryMap;
|
||||||
};
|
};
|
||||||
|
|
||||||
std::string FixupTargetFilename ( const std::string& targetFilename );
|
std::string FixupTargetFilename ( const std::string& targetFilename );
|
||||||
|
|
|
@ -22,6 +22,20 @@ MingwModuleHandler::ref = 0;
|
||||||
FILE*
|
FILE*
|
||||||
MingwModuleHandler::fMakefile = NULL;
|
MingwModuleHandler::fMakefile = NULL;
|
||||||
|
|
||||||
|
string
|
||||||
|
ReplaceExtension ( const string& filename,
|
||||||
|
const string& newExtension )
|
||||||
|
{
|
||||||
|
size_t index = filename.find_last_of ( '/' );
|
||||||
|
if (index == string::npos) index = 0;
|
||||||
|
string tmp = filename.substr( index, filename.size() - index );
|
||||||
|
size_t ext_index = tmp.find_last_of( '.' );
|
||||||
|
if (ext_index != string::npos)
|
||||||
|
return filename.substr ( 0, index + ext_index ) + newExtension;
|
||||||
|
return filename + newExtension;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
MingwModuleHandler::MingwModuleHandler ( ModuleType moduletype )
|
MingwModuleHandler::MingwModuleHandler ( ModuleType moduletype )
|
||||||
{
|
{
|
||||||
if ( !ref++ )
|
if ( !ref++ )
|
||||||
|
@ -72,10 +86,10 @@ MingwModuleHandler::GetWorkingDirectory () const
|
||||||
return ".";
|
return ".";
|
||||||
}
|
}
|
||||||
|
|
||||||
string
|
string
|
||||||
MingwModuleHandler::GetDirectory ( const string& filename ) const
|
MingwModuleHandler::GetDirectory ( const string& filename )
|
||||||
{
|
{
|
||||||
size_t index = filename.find_last_of ( '/' );
|
size_t index = filename.find_last_of ( CSEP );
|
||||||
if (index == string::npos)
|
if (index == string::npos)
|
||||||
return ".";
|
return ".";
|
||||||
else
|
else
|
||||||
|
@ -91,19 +105,6 @@ MingwModuleHandler::GetBasename ( const string& filename ) const
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
string
|
|
||||||
MingwModuleHandler::ReplaceExtension ( const string& filename,
|
|
||||||
const string& newExtension ) const
|
|
||||||
{
|
|
||||||
size_t index = filename.find_last_of ( '/' );
|
|
||||||
if (index == string::npos) index = 0;
|
|
||||||
string tmp = filename.substr( index, filename.size() - index );
|
|
||||||
size_t ext_index = tmp.find_last_of( '.' );
|
|
||||||
if (ext_index != string::npos)
|
|
||||||
return filename.substr ( 0, index + ext_index ) + newExtension;
|
|
||||||
return filename + newExtension;
|
|
||||||
}
|
|
||||||
|
|
||||||
string
|
string
|
||||||
MingwModuleHandler::GetActualSourceFilename ( const string& filename ) const
|
MingwModuleHandler::GetActualSourceFilename ( const string& filename ) const
|
||||||
{
|
{
|
||||||
|
@ -237,7 +238,7 @@ MingwModuleHandler::GetSourceFilenamesWithoutGeneratedFiles ( const Module& modu
|
||||||
}
|
}
|
||||||
|
|
||||||
string
|
string
|
||||||
MingwModuleHandler::GetObjectFilename ( const string& sourceFilename ) const
|
MingwModuleHandler::GetObjectFilename ( const string& sourceFilename )
|
||||||
{
|
{
|
||||||
string newExtension;
|
string newExtension;
|
||||||
string extension = GetExtension ( sourceFilename );
|
string extension = GetExtension ( sourceFilename );
|
||||||
|
@ -247,9 +248,8 @@ MingwModuleHandler::GetObjectFilename ( const string& sourceFilename ) const
|
||||||
newExtension = ".stubs.o";
|
newExtension = ".stubs.o";
|
||||||
else
|
else
|
||||||
newExtension = ".o";
|
newExtension = ".o";
|
||||||
return PassThruCacheDirectory (
|
return FixupTargetFilename (
|
||||||
FixupTargetFilename (
|
ReplaceExtension ( sourceFilename, newExtension ) );
|
||||||
ReplaceExtension ( sourceFilename, newExtension ) ) );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
string
|
string
|
||||||
|
@ -263,7 +263,7 @@ MingwModuleHandler::GetObjectFilenames ( const Module& module ) const
|
||||||
{
|
{
|
||||||
if ( objectFilenames.size () > 0 )
|
if ( objectFilenames.size () > 0 )
|
||||||
objectFilenames += " ";
|
objectFilenames += " ";
|
||||||
objectFilenames += GetObjectFilename ( module.files[i]->name );
|
objectFilenames += PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( module.files[i]->name ) );
|
||||||
}
|
}
|
||||||
return objectFilenames;
|
return objectFilenames;
|
||||||
}
|
}
|
||||||
|
@ -510,7 +510,7 @@ MingwModuleHandler::GenerateMacros (
|
||||||
fprintf ( fMakefile,
|
fprintf ( fMakefile,
|
||||||
"%s := %s $(%s)\n",
|
"%s := %s $(%s)\n",
|
||||||
objs_macro.c_str(),
|
objs_macro.c_str(),
|
||||||
GetObjectFilename(files[i]->name).c_str(),
|
PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( files[i]->name ) ).c_str (),
|
||||||
objs_macro.c_str() );
|
objs_macro.c_str() );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -530,7 +530,7 @@ MingwModuleHandler::GenerateMacros (
|
||||||
fMakefile,
|
fMakefile,
|
||||||
"%s%s",
|
"%s%s",
|
||||||
( i%10 == 9 ? "\\\n\t" : " " ),
|
( i%10 == 9 ? "\\\n\t" : " " ),
|
||||||
GetObjectFilename(files[i]->name).c_str() );
|
PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( files[i]->name ) ).c_str () );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fprintf ( fMakefile, "\n" );
|
fprintf ( fMakefile, "\n" );
|
||||||
|
@ -612,7 +612,7 @@ MingwModuleHandler::GenerateGccCommand ( const Module& module,
|
||||||
const string& cc,
|
const string& cc,
|
||||||
const string& cflagsMacro ) const
|
const string& cflagsMacro ) const
|
||||||
{
|
{
|
||||||
string objectFilename = GetObjectFilename ( sourceFilename );
|
string objectFilename = PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( sourceFilename ) );
|
||||||
fprintf ( fMakefile,
|
fprintf ( fMakefile,
|
||||||
"%s: %s\n",
|
"%s: %s\n",
|
||||||
objectFilename.c_str (),
|
objectFilename.c_str (),
|
||||||
|
@ -631,7 +631,7 @@ MingwModuleHandler::GenerateGccAssemblerCommand ( const Module& module,
|
||||||
const string& cc,
|
const string& cc,
|
||||||
const string& cflagsMacro ) const
|
const string& cflagsMacro ) const
|
||||||
{
|
{
|
||||||
string objectFilename = GetObjectFilename ( sourceFilename );
|
string objectFilename = PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( sourceFilename ) );
|
||||||
fprintf ( fMakefile,
|
fprintf ( fMakefile,
|
||||||
"%s: %s\n",
|
"%s: %s\n",
|
||||||
objectFilename.c_str (),
|
objectFilename.c_str (),
|
||||||
|
@ -649,7 +649,7 @@ MingwModuleHandler::GenerateNasmCommand ( const Module& module,
|
||||||
const string& sourceFilename,
|
const string& sourceFilename,
|
||||||
const string& nasmflagsMacro ) const
|
const string& nasmflagsMacro ) const
|
||||||
{
|
{
|
||||||
string objectFilename = GetObjectFilename ( sourceFilename );
|
string objectFilename = PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( sourceFilename ) );
|
||||||
fprintf ( fMakefile,
|
fprintf ( fMakefile,
|
||||||
"%s: %s\n",
|
"%s: %s\n",
|
||||||
objectFilename.c_str (),
|
objectFilename.c_str (),
|
||||||
|
@ -667,7 +667,7 @@ MingwModuleHandler::GenerateWindresCommand ( const Module& module,
|
||||||
const string& sourceFilename,
|
const string& sourceFilename,
|
||||||
const string& windresflagsMacro ) const
|
const string& windresflagsMacro ) const
|
||||||
{
|
{
|
||||||
string objectFilename = GetObjectFilename ( sourceFilename );
|
string objectFilename = PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( sourceFilename ) );
|
||||||
fprintf ( fMakefile,
|
fprintf ( fMakefile,
|
||||||
"%s: %s\n",
|
"%s: %s\n",
|
||||||
objectFilename.c_str (),
|
objectFilename.c_str (),
|
||||||
|
@ -908,7 +908,7 @@ MingwModuleHandler::GetCleanTargets ( vector<string>& out,
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
for ( i = 0; i < files.size(); i++ )
|
for ( i = 0; i < files.size(); i++ )
|
||||||
out.push_back ( GetObjectFilename(files[i]->name) );
|
out.push_back ( PassThruCacheDirectory ( MingwModuleHandler::GetObjectFilename ( files[i]->name ) ) );
|
||||||
|
|
||||||
for ( i = 0; i < ifs.size(); i++ )
|
for ( i = 0; i < ifs.size(); i++ )
|
||||||
GetCleanTargets ( out, ifs[i]->files, ifs[i]->ifs );
|
GetCleanTargets ( out, ifs[i]->files, ifs[i]->ifs );
|
||||||
|
|
|
@ -3,6 +3,11 @@
|
||||||
|
|
||||||
#include "../backend.h"
|
#include "../backend.h"
|
||||||
|
|
||||||
|
extern std::string
|
||||||
|
ReplaceExtension ( const std::string& filename,
|
||||||
|
const std::string& newExtension );
|
||||||
|
|
||||||
|
|
||||||
class MingwModuleHandler
|
class MingwModuleHandler
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
@ -16,15 +21,13 @@ public:
|
||||||
static MingwModuleHandler* LookupHandler ( const std::string& location,
|
static MingwModuleHandler* LookupHandler ( const std::string& location,
|
||||||
ModuleType moduletype_ );
|
ModuleType moduletype_ );
|
||||||
virtual void Process ( const Module& module ) = 0;
|
virtual void Process ( const Module& module ) = 0;
|
||||||
void GenerateDirectoryTargets () const;
|
void GenerateDirectoryTargets () const;
|
||||||
|
static std::string GetObjectFilename ( const std::string& sourceFilename );
|
||||||
|
static std::string GetDirectory ( const std::string& filename );
|
||||||
protected:
|
protected:
|
||||||
const std::string &PassThruCacheDirectory ( const std::string &f ) const;
|
const std::string &PassThruCacheDirectory ( const std::string &f ) const;
|
||||||
std::string GetWorkingDirectory () const;
|
std::string GetWorkingDirectory () const;
|
||||||
std::string GetDirectory (const std::string& filename ) const;
|
|
||||||
std::string GetBasename ( const std::string& filename ) const;
|
std::string GetBasename ( const std::string& filename ) const;
|
||||||
std::string ReplaceExtension ( const std::string& filename,
|
|
||||||
const std::string& newExtension ) const;
|
|
||||||
std::string GetActualSourceFilename ( const std::string& filename ) const;
|
std::string GetActualSourceFilename ( const std::string& filename ) const;
|
||||||
std::string GetModuleArchiveFilename ( const Module& module ) const;
|
std::string GetModuleArchiveFilename ( const Module& module ) const;
|
||||||
bool IsGeneratedFile ( const File& file ) const;
|
bool IsGeneratedFile ( const File& file ) const;
|
||||||
|
@ -37,7 +40,6 @@ protected:
|
||||||
std::string GetSourceFilenames ( const Module& module ) const;
|
std::string GetSourceFilenames ( const Module& module ) const;
|
||||||
std::string GetSourceFilenamesWithoutGeneratedFiles ( const Module& module ) const;
|
std::string GetSourceFilenamesWithoutGeneratedFiles ( const Module& module ) const;
|
||||||
|
|
||||||
std::string GetObjectFilename ( const std::string& sourceFilename ) const;
|
|
||||||
std::string GetObjectFilenames ( const Module& module ) const;
|
std::string GetObjectFilenames ( const Module& module ) const;
|
||||||
void GenerateMacrosAndTargetsHost ( const Module& module ) const;
|
void GenerateMacrosAndTargetsHost ( const Module& module ) const;
|
||||||
void GenerateMacrosAndTargetsTarget ( const Module& module ) const;
|
void GenerateMacrosAndTargetsTarget ( const Module& module ) const;
|
||||||
|
@ -47,6 +49,8 @@ protected:
|
||||||
std::string GetInvocationDependencies ( const Module& module ) const;
|
std::string GetInvocationDependencies ( const Module& module ) const;
|
||||||
std::string GetInvocationParameters ( const Invoke& invoke ) const;
|
std::string GetInvocationParameters ( const Invoke& invoke ) const;
|
||||||
void GenerateInvocations ( const Module& module ) const;
|
void GenerateInvocations ( const Module& module ) const;
|
||||||
|
|
||||||
|
std::string GetPreconditionDependenciesName ( const Module& module ) const;
|
||||||
void GeneratePreconditionDependencies ( const Module& module ) const;
|
void GeneratePreconditionDependencies ( const Module& module ) const;
|
||||||
std::string GetCFlagsMacro ( const Module& module ) const;
|
std::string GetCFlagsMacro ( const Module& module ) const;
|
||||||
std::string GetObjectsMacro ( const Module& module ) const;
|
std::string GetObjectsMacro ( const Module& module ) const;
|
||||||
|
@ -144,7 +148,6 @@ private:
|
||||||
const std::string& ar,
|
const std::string& ar,
|
||||||
const std::string* clags,
|
const std::string* clags,
|
||||||
const std::string* nasmflags ) const;
|
const std::string* nasmflags ) const;
|
||||||
std::string GetPreconditionDependenciesName ( const Module& module ) const;
|
|
||||||
std::string GetSpecObjectDependencies ( const std::string& filename ) const;
|
std::string GetSpecObjectDependencies ( const std::string& filename ) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -352,7 +352,9 @@ class SourceFile
|
||||||
public:
|
public:
|
||||||
SourceFile ( AutomaticDependency* automaticDependency,
|
SourceFile ( AutomaticDependency* automaticDependency,
|
||||||
Module& module,
|
Module& module,
|
||||||
const std::string& filename );
|
const std::string& filename,
|
||||||
|
SourceFile* parent,
|
||||||
|
bool isNonAutomaticDependency );
|
||||||
SourceFile* ParseFile ( const std::string& normalizedFilename );
|
SourceFile* ParseFile ( const std::string& normalizedFilename );
|
||||||
void Parse ();
|
void Parse ();
|
||||||
std::string Location () const;
|
std::string Location () const;
|
||||||
|
@ -360,11 +362,21 @@ public:
|
||||||
AutomaticDependency* automaticDependency;
|
AutomaticDependency* automaticDependency;
|
||||||
Module& module;
|
Module& module;
|
||||||
std::string filename;
|
std::string filename;
|
||||||
|
std::string filenamePart;
|
||||||
|
std::string directoryPart;
|
||||||
|
std::vector<SourceFile*> parents; /* List of files, this file is included from */
|
||||||
|
bool isNonAutomaticDependency;
|
||||||
|
std::string cachedDependencies;
|
||||||
private:
|
private:
|
||||||
|
void GetDirectoryAndFilenameParts ();
|
||||||
void Close ();
|
void Close ();
|
||||||
void Open ();
|
void Open ();
|
||||||
void SkipWhitespace ();
|
void SkipWhitespace ();
|
||||||
bool ReadInclude ( std::string& filename );
|
bool ReadInclude ( std::string& filename );
|
||||||
|
bool IsIncludedFrom ( const std::string& normalizedFilename );
|
||||||
|
SourceFile* GetParentSourceFile ();
|
||||||
|
bool IsParentOf ( const SourceFile* parent,
|
||||||
|
const SourceFile* child );
|
||||||
std::string buf;
|
std::string buf;
|
||||||
const char *p;
|
const char *p;
|
||||||
const char *end;
|
const char *end;
|
||||||
|
@ -387,9 +399,9 @@ public:
|
||||||
const std::string& includedFilename,
|
const std::string& includedFilename,
|
||||||
std::string& resolvedFilename );
|
std::string& resolvedFilename );
|
||||||
SourceFile* RetrieveFromCacheOrParse ( Module& module,
|
SourceFile* RetrieveFromCacheOrParse ( Module& module,
|
||||||
const std::string& filename );
|
const std::string& filename,
|
||||||
SourceFile* RetrieveFromCache ( Module& module,
|
SourceFile* parentSourceFile );
|
||||||
const std::string& filename );
|
SourceFile* RetrieveFromCache ( const std::string& filename );
|
||||||
private:
|
private:
|
||||||
void ProcessModule ( Module& module );
|
void ProcessModule ( Module& module );
|
||||||
void ProcessFile ( Module& module,
|
void ProcessFile ( Module& module,
|
||||||
|
|
|
@ -108,6 +108,10 @@ class SourceFileTest : public BaseTest
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
void Run();
|
void Run();
|
||||||
|
private:
|
||||||
|
bool IsParentOf ( const SourceFile* parent,
|
||||||
|
const SourceFile* child );
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* __TEST_H */
|
#endif /* __TEST_H */
|
||||||
|
|
|
@ -1,2 +1,3 @@
|
||||||
#include <sourcefile1/sourcefile1_header3.h>
|
#include "sourcefile1/sourcefile1_header3.h"
|
||||||
#include <sourcefile2/sourcefile1_dontexist.h>
|
#include <sourcefile2/sourcefile1_dontexist.h>
|
||||||
|
#include <sourcefile1_recurse.h>
|
||||||
|
|
2
reactos/tools/rbuild/tests/data/sourcefile1_recurse.h
Normal file
2
reactos/tools/rbuild/tests/data/sourcefile1_recurse.h
Normal file
|
@ -0,0 +1,2 @@
|
||||||
|
#include <sourcefile1_recurse.h>
|
||||||
|
#include <sourcefile1_header1.h>
|
|
@ -2,10 +2,48 @@
|
||||||
|
|
||||||
using std::string;
|
using std::string;
|
||||||
|
|
||||||
void SourceFileTest::Run()
|
bool
|
||||||
|
SourceFileTest::IsParentOf ( const SourceFile* parent,
|
||||||
|
const SourceFile* child )
|
||||||
|
{
|
||||||
|
size_t i;
|
||||||
|
for ( i = 0; i < child->parents.size (); i++ )
|
||||||
|
{
|
||||||
|
if ( child->parents[i] != NULL )
|
||||||
|
{
|
||||||
|
if ( child->parents[i] == parent )
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for ( i = 0; i < child->parents.size (); i++ )
|
||||||
|
{
|
||||||
|
if ( child->parents[i] != NULL )
|
||||||
|
{
|
||||||
|
if ( IsParentOf ( parent,
|
||||||
|
child->parents[i] ) )
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
SourceFileTest::Run ()
|
||||||
{
|
{
|
||||||
const Project project ( "tests/data/automaticdependency.xml" );
|
const Project project ( "tests/data/automaticdependency.xml" );
|
||||||
AutomaticDependency automaticDependency ( project );
|
AutomaticDependency automaticDependency ( project );
|
||||||
automaticDependency.Process ();
|
automaticDependency.Process ();
|
||||||
ARE_EQUAL(3, automaticDependency.sourcefile_map.size());
|
ARE_EQUAL( 5, automaticDependency.sourcefile_map.size () );
|
||||||
|
const SourceFile* header1 = automaticDependency.RetrieveFromCache ( "tests" SSEP "data" SSEP "sourcefile1_header1.h" );
|
||||||
|
IS_NOT_NULL( header1 );
|
||||||
|
const SourceFile* recurse = automaticDependency.RetrieveFromCache ( "tests" SSEP "data" SSEP "sourcefile1_recurse.h" );
|
||||||
|
IS_NOT_NULL( recurse );
|
||||||
|
IS_TRUE( IsParentOf ( header1,
|
||||||
|
recurse ) );
|
||||||
|
IS_FALSE( IsParentOf ( recurse,
|
||||||
|
header1 ) );
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue