diff options
author | Mike Buland <eichlan@xagasoft.com> | 2006-08-05 00:04:34 +0000 |
---|---|---|
committer | Mike Buland <eichlan@xagasoft.com> | 2006-08-05 00:04:34 +0000 |
commit | 8dd79b7b5a0309f9bc1185019a4af16b3b52aece (patch) | |
tree | a703325cb9bc074179aeaf38f4851a4c38ebfd87 | |
parent | 13bda5d4f77ca469bbbe0d9b1f268682a9f0ec71 (diff) | |
download | build-8dd79b7b5a0309f9bc1185019a4af16b3b52aece.tar.gz build-8dd79b7b5a0309f9bc1185019a4af16b3b52aece.tar.bz2 build-8dd79b7b5a0309f9bc1185019a4af16b3b52aece.tar.xz build-8dd79b7b5a0309f9bc1185019a4af16b3b52aece.zip |
Build now uses a cachefile for all of it's requires that are generated from
other means (running other programs). It's really fast, and seems to work
pretty well.
Diffstat (limited to '')
-rw-r--r-- | src/builder.cpp | 113 | ||||
-rw-r--r-- | src/builder.h | 9 | ||||
-rw-r--r-- | src/cache.cpp | 78 | ||||
-rw-r--r-- | src/cache.h | 33 | ||||
-rw-r--r-- | src/filetarget.cpp | 5 | ||||
-rw-r--r-- | src/main.cpp | 27 |
6 files changed, 193 insertions, 72 deletions
diff --git a/src/builder.cpp b/src/builder.cpp index d3cb2c0..a21bc99 100644 --- a/src/builder.cpp +++ b/src/builder.cpp | |||
@@ -7,6 +7,8 @@ | |||
7 | #include "build.tab.h" | 7 | #include "build.tab.h" |
8 | #include "rule.h" | 8 | #include "rule.h" |
9 | #include "viewer.h" | 9 | #include "viewer.h" |
10 | #include "cache.h" | ||
11 | #include "serializerbinary.h" | ||
10 | 12 | ||
11 | subExceptionDef( BuildException ) | 13 | subExceptionDef( BuildException ) |
12 | 14 | ||
@@ -21,6 +23,18 @@ Builder::Builder( Viewer &rView ) : | |||
21 | 23 | ||
22 | Builder::~Builder() | 24 | Builder::~Builder() |
23 | { | 25 | { |
26 | if( sCacheFile.getLength() > 0 ) | ||
27 | { | ||
28 | try | ||
29 | { | ||
30 | SerializerBinary ar( sCacheFile, Serializer::save ); | ||
31 | |||
32 | ar << cRequires; | ||
33 | } | ||
34 | catch( ExceptionBase &e ) | ||
35 | { | ||
36 | } | ||
37 | } | ||
24 | } | 38 | } |
25 | 39 | ||
26 | void yyparse( Builder &bld ); | 40 | void yyparse( Builder &bld ); |
@@ -53,6 +67,21 @@ void Builder::build( const char *sAct ) | |||
53 | rView.endAction(); | 67 | rView.endAction(); |
54 | } | 68 | } |
55 | 69 | ||
70 | void Builder::setCache( const std::string &sFile ) | ||
71 | { | ||
72 | sCacheFile = sFile.c_str(); | ||
73 | |||
74 | try | ||
75 | { | ||
76 | SerializerBinary ar( sCacheFile, Serializer::load ); | ||
77 | |||
78 | ar >> cRequires; | ||
79 | } | ||
80 | catch( ExceptionBase &e ) | ||
81 | { | ||
82 | } | ||
83 | } | ||
84 | |||
56 | void Builder::execute( Action *pAct ) | 85 | void Builder::execute( Action *pAct ) |
57 | { | 86 | { |
58 | pAct->execute( *this ); | 87 | pAct->execute( *this ); |
@@ -247,75 +276,31 @@ void Builder::processRequires( std::list<std::string> &lInput ) | |||
247 | } | 276 | } |
248 | } | 277 | } |
249 | 278 | ||
250 | // These are only done on request now, they were too expensive | 279 | } |
251 | /* | 280 | |
252 | for( regreqlist::iterator i = lRequiresRegexpCommand.begin(); | 281 | void Builder::genRequiresFor( const char *sName, time_t tNewTime ) |
253 | i != lRequiresRegexpCommand.end(); i++ ) | 282 | { |
283 | Cache::Entry *ent = cRequires.get( sName ); | ||
284 | if( ent && tNewTime > 0 ) | ||
254 | { | 285 | { |
255 | RegExp *re = (*i).first; | 286 | if( ent->tCreated >= tNewTime ) |
256 | for( std::list<std::string>::iterator j = lInput.begin(); | ||
257 | j != lInput.end(); j++ ) | ||
258 | { | 287 | { |
259 | if( re->execute( (*j).c_str() ) ) | 288 | for( std::list<std::string>::iterator i = ent->lData.begin(); |
289 | i != ent->lData.end(); i++ ) | ||
260 | { | 290 | { |
261 | varmap *revars = regexVars( re ); | 291 | requiresNormal( |
262 | std::string s = varRepl( (*i).second.c_str(), "", revars ); | 292 | sName, |
263 | FILE *fcmd = popen( s.c_str(), "r" ); | 293 | (*i).c_str() |
264 | std::string rhs; | 294 | ); |
265 | bool bHeader = true; | ||
266 | for(;;) | ||
267 | { | ||
268 | if( feof( fcmd ) ) | ||
269 | break; | ||
270 | int cc = fgetc( fcmd ); | ||
271 | if( cc == EOF ) | ||
272 | break; | ||
273 | unsigned char c = cc; | ||
274 | if( bHeader ) | ||
275 | { | ||
276 | if( c == ':' ) | ||
277 | bHeader = false; | ||
278 | } | ||
279 | else | ||
280 | { | ||
281 | if( c == ' ' || c == '\t' ) | ||
282 | { | ||
283 | if( rhs != "" ) | ||
284 | { | ||
285 | requiresNormal( | ||
286 | (*j).c_str(), | ||
287 | rhs.c_str() | ||
288 | ); | ||
289 | rhs = ""; | ||
290 | } | ||
291 | } | ||
292 | else | ||
293 | { | ||
294 | if( c == '\\' ) | ||
295 | c = fgetc( fcmd ); | ||
296 | if( c != '\n' ) | ||
297 | rhs += c; | ||
298 | } | ||
299 | } | ||
300 | } | ||
301 | if( rhs != "" ) | ||
302 | { | ||
303 | requiresNormal( | ||
304 | (*j).c_str(), | ||
305 | rhs.c_str() | ||
306 | ); | ||
307 | rhs = ""; | ||
308 | } | ||
309 | pclose( fcmd ); | ||
310 | delete revars; | ||
311 | } | 295 | } |
296 | |||
297 | return; | ||
312 | } | 298 | } |
313 | } | 299 | } |
314 | */ | ||
315 | } | ||
316 | 300 | ||
317 | void Builder::genRequiresFor( const char *sName ) | 301 | ent = new Cache::Entry; |
318 | { | 302 | ent->tCreated = tNewTime; |
303 | |||
319 | for( regreqlist::iterator i = lRequiresRegexpCommand.begin(); | 304 | for( regreqlist::iterator i = lRequiresRegexpCommand.begin(); |
320 | i != lRequiresRegexpCommand.end(); i++ ) | 305 | i != lRequiresRegexpCommand.end(); i++ ) |
321 | { | 306 | { |
@@ -352,6 +337,7 @@ void Builder::genRequiresFor( const char *sName ) | |||
352 | sName, | 337 | sName, |
353 | rhs.c_str() | 338 | rhs.c_str() |
354 | ); | 339 | ); |
340 | ent->lData.push_back( rhs ); | ||
355 | rhs = ""; | 341 | rhs = ""; |
356 | } | 342 | } |
357 | } | 343 | } |
@@ -370,6 +356,7 @@ void Builder::genRequiresFor( const char *sName ) | |||
370 | sName, | 356 | sName, |
371 | rhs.c_str() | 357 | rhs.c_str() |
372 | ); | 358 | ); |
359 | ent->lData.push_back( rhs ); | ||
373 | rhs = ""; | 360 | rhs = ""; |
374 | } | 361 | } |
375 | pclose( fcmd ); | 362 | pclose( fcmd ); |
@@ -377,6 +364,8 @@ void Builder::genRequiresFor( const char *sName ) | |||
377 | rView.endExtraRequiresCheck(); | 364 | rView.endExtraRequiresCheck(); |
378 | } | 365 | } |
379 | } | 366 | } |
367 | |||
368 | cRequires.put( sName, ent ); | ||
380 | } | 369 | } |
381 | 370 | ||
382 | std::map<std::string, std::string> *Builder::regexVars( RegExp *re ) | 371 | std::map<std::string, std::string> *Builder::regexVars( RegExp *re ) |
diff --git a/src/builder.h b/src/builder.h index 06e84f3..56a7b07 100644 --- a/src/builder.h +++ b/src/builder.h | |||
@@ -8,6 +8,7 @@ | |||
8 | #include "exceptionbase.h" | 8 | #include "exceptionbase.h" |
9 | #include "staticstring.h" | 9 | #include "staticstring.h" |
10 | #include "regexp.h" | 10 | #include "regexp.h" |
11 | #include "cache.h" | ||
11 | 12 | ||
12 | subExceptionDecl( BuildException ) | 13 | subExceptionDecl( BuildException ) |
13 | 14 | ||
@@ -17,6 +18,7 @@ class Command; | |||
17 | class Rule; | 18 | class Rule; |
18 | class Target; | 19 | class Target; |
19 | class Viewer; | 20 | class Viewer; |
21 | class Cache; | ||
20 | 22 | ||
21 | #define YY_DECL int yylex( YYSTYPE *yylval_param, YYLTYPE *yylloc_param, Builder &bld ) | 23 | #define YY_DECL int yylex( YYSTYPE *yylval_param, YYLTYPE *yylloc_param, Builder &bld ) |
22 | YY_DECL; | 24 | YY_DECL; |
@@ -48,6 +50,8 @@ public: | |||
48 | { | 50 | { |
49 | return rView; | 51 | return rView; |
50 | } | 52 | } |
53 | |||
54 | void setCache( const std::string &sFile ); | ||
51 | void add( Action *pAct ); | 55 | void add( Action *pAct ); |
52 | void add( Command *pCmd ); | 56 | void add( Command *pCmd ); |
53 | void add( Rule *pRule ); | 57 | void add( Rule *pRule ); |
@@ -59,7 +63,7 @@ public: | |||
59 | void processRequires( std::list<std::string> &lInput ); | 63 | void processRequires( std::list<std::string> &lInput ); |
60 | void requires( const char *sBase, const char *sReq ); | 64 | void requires( const char *sBase, const char *sReq ); |
61 | void requiresFromCommand( const char *sBase, const char *sReq ); | 65 | void requiresFromCommand( const char *sBase, const char *sReq ); |
62 | void genRequiresFor( const char *sName ); | 66 | void genRequiresFor( const char *sName, time_t tNewTime ); |
63 | void requiresRegexp( bool on ) | 67 | void requiresRegexp( bool on ) |
64 | { | 68 | { |
65 | bReqRegexp = on; | 69 | bReqRegexp = on; |
@@ -152,6 +156,9 @@ private: | |||
152 | bool bReqRegexp; | 156 | bool bReqRegexp; |
153 | 157 | ||
154 | Viewer &rView; | 158 | Viewer &rView; |
159 | |||
160 | StaticString sCacheFile; | ||
161 | class Cache cRequires; | ||
155 | }; | 162 | }; |
156 | 163 | ||
157 | void cleanList( std::list<std::string> &lst ); | 164 | void cleanList( std::list<std::string> &lst ); |
diff --git a/src/cache.cpp b/src/cache.cpp new file mode 100644 index 0000000..43e69dc --- /dev/null +++ b/src/cache.cpp | |||
@@ -0,0 +1,78 @@ | |||
1 | #include "cache.h" | ||
2 | #include "serializer.h" | ||
3 | |||
4 | Cache::Cache() | ||
5 | { | ||
6 | } | ||
7 | |||
8 | Cache::~Cache() | ||
9 | { | ||
10 | for( std::map<std::string, Entry *>::iterator i = mCache.begin(); | ||
11 | i != mCache.end(); i++ ) | ||
12 | { | ||
13 | delete (*i).second; | ||
14 | } | ||
15 | } | ||
16 | |||
17 | void Cache::serialize( class Serializer &ar ) | ||
18 | { | ||
19 | if( ar.isLoading() ) | ||
20 | { | ||
21 | int sCache, sData; | ||
22 | ar >> sCache; | ||
23 | std::string sTmp; | ||
24 | |||
25 | for( int i = 0; i < sCache; i++ ) | ||
26 | { | ||
27 | Entry *e = new Entry; | ||
28 | ar >> e->tCreated; | ||
29 | ar >> sData; | ||
30 | std::list<std::string> &lData = e->lData; | ||
31 | for( int j = 0; j < sData; j++ ) | ||
32 | { | ||
33 | ar >> sTmp; | ||
34 | lData.push_back( sTmp ); | ||
35 | } | ||
36 | ar >> sTmp; | ||
37 | mCache[sTmp] = e; | ||
38 | } | ||
39 | } | ||
40 | else | ||
41 | { | ||
42 | ar << mCache.size(); | ||
43 | for( std::map<std::string, Entry *>::iterator i = mCache.begin(); | ||
44 | i != mCache.end(); i++ ) | ||
45 | { | ||
46 | ar << (*i).second->tCreated; | ||
47 | std::list<std::string> &lData = (*i).second->lData; | ||
48 | ar << lData.size(); | ||
49 | for( std::list<std::string>::iterator j = lData.begin(); | ||
50 | j != lData.end(); j++ ) | ||
51 | { | ||
52 | ar << (*j); | ||
53 | } | ||
54 | |||
55 | std::string str = (*i).first; | ||
56 | ar << str; | ||
57 | } | ||
58 | } | ||
59 | } | ||
60 | |||
61 | Cache::Entry *Cache::get( const std::string &id ) | ||
62 | { | ||
63 | std::map<std::string, Entry *>::iterator i = mCache.find( id ); | ||
64 | if( i != mCache.end() ) | ||
65 | return (*i).second; | ||
66 | |||
67 | return NULL; | ||
68 | } | ||
69 | |||
70 | void Cache::put( const std::string &id, Entry *data ) | ||
71 | { | ||
72 | std::map<std::string, Entry *>::iterator i = mCache.find( id ); | ||
73 | if( i != mCache.end() ) | ||
74 | delete (*i).second; | ||
75 | |||
76 | mCache[id] = data; | ||
77 | } | ||
78 | |||
diff --git a/src/cache.h b/src/cache.h new file mode 100644 index 0000000..944aa24 --- /dev/null +++ b/src/cache.h | |||
@@ -0,0 +1,33 @@ | |||
1 | #ifndef CACHE_H | ||
2 | #define CACHE_H | ||
3 | |||
4 | #include <stdint.h> | ||
5 | #include <time.h> | ||
6 | #include "serializable.h" | ||
7 | #include <list> | ||
8 | #include <map> | ||
9 | #include <string> | ||
10 | |||
11 | class Cache : public Serializable | ||
12 | { | ||
13 | public: | ||
14 | Cache(); | ||
15 | virtual ~Cache(); | ||
16 | |||
17 | virtual void serialize( class Serializer &ar ); | ||
18 | |||
19 | class Entry | ||
20 | { | ||
21 | public: | ||
22 | int tCreated; | ||
23 | std::list<std::string> lData; | ||
24 | }; | ||
25 | |||
26 | Entry *get( const std::string &id ); | ||
27 | void put( const std::string &id, Entry *data ); | ||
28 | |||
29 | private: | ||
30 | std::map<std::string, Entry *> mCache; | ||
31 | }; | ||
32 | |||
33 | #endif | ||
diff --git a/src/filetarget.cpp b/src/filetarget.cpp index e89cd5f..7a714a5 100644 --- a/src/filetarget.cpp +++ b/src/filetarget.cpp | |||
@@ -98,7 +98,8 @@ void FileTarget::check( Builder &bld ) | |||
98 | for( std::list<std::string>::iterator j = lReqs->begin(); | 98 | for( std::list<std::string>::iterator j = lReqs->begin(); |
99 | j != lReqs->end(); j++ ) | 99 | j != lReqs->end(); j++ ) |
100 | { | 100 | { |
101 | if( getTime( bld, *j ) > target ) | 101 | time_t srcfile = getTime( bld, *j ); |
102 | if( srcfile > target ) | ||
102 | { | 103 | { |
103 | bld.view().beginExecute(); | 104 | bld.view().beginExecute(); |
104 | (*i)->execute( bld ); | 105 | (*i)->execute( bld ); |
@@ -113,7 +114,7 @@ void FileTarget::check( Builder &bld ) | |||
113 | if( k == lReqs->end() ) | 114 | if( k == lReqs->end() ) |
114 | { | 115 | { |
115 | bExtraReqs = true; | 116 | bExtraReqs = true; |
116 | bld.genRequiresFor( (*i)->getTarget() ); | 117 | bld.genRequiresFor( (*i)->getTarget(), srcfile ); |
117 | } | 118 | } |
118 | } | 119 | } |
119 | } | 120 | } |
diff --git a/src/main.cpp b/src/main.cpp index 70a3ffc..009aac5 100644 --- a/src/main.cpp +++ b/src/main.cpp | |||
@@ -8,13 +8,18 @@ class Param : public ParamProc | |||
8 | { | 8 | { |
9 | public: | 9 | public: |
10 | Param() : | 10 | Param() : |
11 | sFile("build.conf") | 11 | sFile("build.conf"), |
12 | sCache("build.cache") | ||
12 | { | 13 | { |
13 | addHelpBanner("Build r?\n\n"); | 14 | addHelpBanner("Build r?\n\n"); |
14 | addParam("file", 'f', &sFile, | 15 | addParam("file", 'f', &sFile, |
15 | "Set the input script, default: build.conf"); | 16 | "Set the input script, default: build.conf"); |
16 | addParam('p', mkproc(Param::procViewPercent), | 17 | addParam('p', mkproc(Param::procViewPercent), |
17 | "Switch to percent view."); | 18 | "Switch to percent view."); |
19 | addParam("cache", &sCache, | ||
20 | "Set an alternative cache file." ); | ||
21 | addParam('d', &bDebug, | ||
22 | "Print out a debug dump of the read build.conf", "true" ); | ||
18 | addParam("help", mkproc(ParamProc::help), | 23 | addParam("help", mkproc(ParamProc::help), |
19 | "This help"); | 24 | "This help"); |
20 | pViewer = new ViewerPlain; | 25 | pViewer = new ViewerPlain; |
@@ -42,9 +47,11 @@ public: | |||
42 | pViewer = new ViewerPercent; | 47 | pViewer = new ViewerPercent; |
43 | } | 48 | } |
44 | 49 | ||
50 | std::string sCache; | ||
45 | std::string sFile; | 51 | std::string sFile; |
46 | StaticString sAction; | 52 | StaticString sAction; |
47 | Viewer *pViewer; | 53 | Viewer *pViewer; |
54 | bool bDebug; | ||
48 | 55 | ||
49 | private: | 56 | private: |
50 | }; | 57 | }; |
@@ -56,14 +63,20 @@ int main( int argc, char *argv[] ) | |||
56 | 63 | ||
57 | Builder bld( *prm.pViewer ); | 64 | Builder bld( *prm.pViewer ); |
58 | 65 | ||
66 | bld.setCache( prm.sCache ); | ||
59 | bld.load( prm.sFile.c_str() ); | 67 | bld.load( prm.sFile.c_str() ); |
60 | 68 | ||
61 | if( prm.sAction > 0 ) | 69 | if( prm.bDebug ) |
62 | bld.build( prm.sAction ); | 70 | { |
71 | printf("\n\n----------\nDebug dump\n----------\n"); | ||
72 | bld.debug(); | ||
73 | } | ||
63 | else | 74 | else |
64 | bld.build(); | 75 | { |
65 | /* | 76 | if( prm.sAction > 0 ) |
66 | printf("\n\n----------\nDebug dump\n----------\n"); | 77 | bld.build( prm.sAction ); |
67 | bld.debug();*/ | 78 | else |
79 | bld.build(); | ||
80 | } | ||
68 | } | 81 | } |
69 | 82 | ||