aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Buland <eichlan@xagasoft.com>2006-07-31 22:50:47 +0000
committerMike Buland <eichlan@xagasoft.com>2006-07-31 22:50:47 +0000
commit73d53b0962cb19a6d2a7686de658a5540ab07017 (patch)
tree9a8fd737b8f77ec9ccab43d89dc54b7e72d4d90d
parentb672fa69c4c98509f8ee251b87300e3fcbe6bdc8 (diff)
downloadbuild-73d53b0962cb19a6d2a7686de658a5540ab07017.tar.gz
build-73d53b0962cb19a6d2a7686de658a5540ab07017.tar.bz2
build-73d53b0962cb19a6d2a7686de658a5540ab07017.tar.xz
build-73d53b0962cb19a6d2a7686de658a5540ab07017.zip
It almost builds, we need to get rid of duplicate list entries and actually
store the commands somewhere so the target handler can decide if they need to be run.
-rw-r--r--build.conf16
-rw-r--r--pymake.conf6
-rw-r--r--src/builder.cpp20
-rw-r--r--src/builder.h6
-rw-r--r--src/filetarget.cpp8
-rw-r--r--src/perform.cpp9
-rw-r--r--src/perform.h18
-rw-r--r--src/performcmd.cpp19
-rw-r--r--src/performcmd.h22
-rw-r--r--src/rule.cpp141
-rw-r--r--src/rule.h23
-rw-r--r--src/target.cpp6
12 files changed, 250 insertions, 44 deletions
diff --git a/build.conf b/build.conf
index b4792fb..9f6f5ab 100644
--- a/build.conf
+++ b/build.conf
@@ -7,16 +7,18 @@ create file build from files in src using rule exe
7set CXXFLAGS += "-Ilibbu++/src" 7set CXXFLAGS += "-Ilibbu++/src"
8set LDFLAGS += "-Llibbu++ -lbu++" 8set LDFLAGS += "-Llibbu++ -lbu++"
9 9
10build requires src/libbu++/libbu++.a
11
10/(.*)\.o/ requires from command "g++ {CXXFLAGS} -M {re:1}.c*" 12/(.*)\.o/ requires from command "g++ {CXXFLAGS} -M {re:1}.c*"
11 13
12rule exe matches all /(.*)\.o/ perform command ... 14rule exe matches all /(.*)\.o$/ perform command ...
13 "g++ {LDFLAGS} -o {target} {matches}" 15 "g++ {match} {LDFLAGS} -o {target}"
14 16
15rule cpp matches one /(.*)\.c(pp)?/ produces {1}.o perform command ... 17rule cpp matches one /(.*)\.c(pp)?$/ produces "{re:1}.o" perform command ...
16 "g++ {CXXFLAGS} -o {target} {match}" 18 "g++ {CXXFLAGS} -c -o {target} {match}"
17 19
18rule bison matches one /(.*)\.y/ produces {1}.tab.c, {1}.tab.h perform ... 20rule bison matches one /(.*)\.y$/ produces "{re:1}.tab.c", "{re:1}.tab.h" ...
19 command "bison {match}" 21 perform command "bison {match}"
20 22
21rule flex matches one /(.*)\.l/ produces {1}.yy.c perform ... 23rule flex matches one /(.*)\.l$/ produces "{re:1}.yy.c" perform ...
22 command "flex --bison-bridge --bison-locations -o {target} {match}" 24 command "flex --bison-bridge --bison-locations -o {target} {match}"
diff --git a/pymake.conf b/pymake.conf
index 4775d78..a941a7c 100644
--- a/pymake.conf
+++ b/pymake.conf
@@ -68,14 +68,14 @@ COMMAND: g++ -c {INPUT} {CXXFLAGS} -I{DIR} -o {OUTPUT}
68CHECK: g++ -M {INPUT} {CXXFLAGS} -I{DIR} 68CHECK: g++ -M {INPUT} {CXXFLAGS} -I{DIR}
69 69
70[TRIGGER] 70[TRIGGER]
71INPUT .y 71INPUT: .y
72OUTPUT: .tab.c 72OUTPUT: .tab.c
73COMMAND: bison {INPUT} 73COMMAND: bison {INPUT}
74 74
75[TRIGGER] 75[TRIGGER]
76INPUT .l 76INPUT: .l
77OUTPUT: .yy.c 77OUTPUT: .yy.c
78COMMAND: flex --bison-bridge -o {OUTPUT} {INPUT} 78COMMAND: flex --bison-bridge --bison-locations -o {OUTPUT} {INPUT}
79 79
80### Executable command ### 80### Executable command ###
81## Use this command if you want a simple executable 81## Use this command if you want a simple executable
diff --git a/src/builder.cpp b/src/builder.cpp
index 8e29c81..852d70d 100644
--- a/src/builder.cpp
+++ b/src/builder.cpp
@@ -132,18 +132,24 @@ void Builder::debug()
132 } 132 }
133 } 133 }
134 134
135 printf("Additional dependancies:\n"); 135 printf("Dependancies:\n");
136 for( std::map<std::string, std::list<std::string> *>::iterator i = 136 for( std::map<std::string, std::list<std::string> *>::iterator i =
137 mRequires.begin(); i != mRequires.end(); i++ ) 137 mRequires.begin(); i != mRequires.end(); i++ )
138 { 138 {
139 printf(" %s: ", (*i).first.c_str() ); 139 printf(" %s: ", (*i).first.c_str() );
140 std::list<std::string> *pList = (*i).second; 140 std::list<std::string> *pList = (*i).second;
141 int i = 0;
141 for( std::list<std::string>::iterator j = pList->begin(); 142 for( std::list<std::string>::iterator j = pList->begin();
142 j != pList->end(); j++ ) 143 j != pList->end(); j++ )
143 { 144 {
144 if( j != pList->begin() ) 145 if( j != pList->begin() )
145 printf(", "); 146 printf(", ");
146 printf("%s", (*j).c_str() ); 147 printf("%s", (*j).c_str() );
148 if( i++ >= 3 )
149 {
150 printf("...");
151 break;
152 }
147 } 153 }
148 printf("\n"); 154 printf("\n");
149 } 155 }
@@ -443,6 +449,18 @@ std::list<Rule *> Builder::findRuleChain( Rule *pRule )
443{ 449{
444 std::list<Rule *> ret; 450 std::list<Rule *> ret;
445 451
452 for( std::map<const char *, Rule *, ltstr>::iterator i = mRule.begin();
453 i != mRule.end(); i++ )
454 {
455 if( pRule == (*i).second )
456 continue;
457
458 if( pRule->willChain( (*i).second ) )
459 {
460 ret.push_back( (*i).second );
461 }
462 }
463
446 return ret; 464 return ret;
447} 465}
448 466
diff --git a/src/builder.h b/src/builder.h
index d7c0891..faa82c2 100644
--- a/src/builder.h
+++ b/src/builder.h
@@ -100,18 +100,18 @@ public:
100 return mTarget[sName]; 100 return mTarget[sName];
101 } 101 }
102 102
103private:
104 typedef std::map<std::string, std::string> varmap; 103 typedef std::map<std::string, std::string> varmap;
104 varmap *regexVars( RegExp *re );
105 std::string varRepl( const char *sSrc, const char *cont, varmap *mExtra );
106private:
105 107
106 void requiresNormal( const char *sBase, const char *sReq ); 108 void requiresNormal( const char *sBase, const char *sReq );
107 void requiresRegexp( const char *sBase, const char *sReq ); 109 void requiresRegexp( const char *sBase, const char *sReq );
108 void checkVar( const char *cont, const char *sName ); 110 void checkVar( const char *cont, const char *sName );
109 void scanBegin(); 111 void scanBegin();
110 void scanEnd(); 112 void scanEnd();
111 varmap *regexVars( RegExp *re );
112 113
113 bool hasVar( varmap *pMap, std::string &var ); 114 bool hasVar( varmap *pMap, std::string &var );
114 std::string varRepl( const char *sSrc, const char *cont, varmap *mExtra );
115 115
116 Action *pDefaultAction; 116 Action *pDefaultAction;
117 Action *pLastAddedAction; 117 Action *pLastAddedAction;
diff --git a/src/filetarget.cpp b/src/filetarget.cpp
index 65f9d70..3fefd9f 100644
--- a/src/filetarget.cpp
+++ b/src/filetarget.cpp
@@ -45,9 +45,10 @@ void FileTarget::addInputDir( const char *sDir )
45 } 45 }
46 46
47 char *cwd = gnu_getcwd(); 47 char *cwd = gnu_getcwd();
48 std::string base( cwd ); 48 std::string base;//( cwd );
49 base += "/"; 49 //base += "/";
50 base += sDir; 50 base += sDir;
51 base += "/";
51 delete[] cwd; 52 delete[] cwd;
52 53
53 struct dirent *de; 54 struct dirent *de;
@@ -58,7 +59,6 @@ void FileTarget::addInputDir( const char *sDir )
58 continue; 59 continue;
59 60
60 std::string s( base ); 61 std::string s( base );
61 s += "/";
62 s += de->d_name; 62 s += de->d_name;
63 addInput( s.c_str() ); 63 addInput( s.c_str() );
64 } 64 }
@@ -70,7 +70,7 @@ void FileTarget::check( Builder &bld )
70{ 70{
71 Rule *pRule = bld.getRule( sRule ); 71 Rule *pRule = bld.getRule( sRule );
72 72
73 std::list<std::string> tmp = pRule->execute( bld, lInput ); 73 std::list<std::string> tmp = pRule->execute( bld, lInput, getName() );
74 lOutput.insert( lOutput.end(), tmp.begin(), tmp.end() ); 74 lOutput.insert( lOutput.end(), tmp.begin(), tmp.end() );
75 75
76 bld.processRequires( lInput ); 76 bld.processRequires( lInput );
diff --git a/src/perform.cpp b/src/perform.cpp
new file mode 100644
index 0000000..937a76c
--- /dev/null
+++ b/src/perform.cpp
@@ -0,0 +1,9 @@
1#include "perform.h"
2
3Perform::Perform()
4{
5}
6
7Perform::~Perform()
8{
9}
diff --git a/src/perform.h b/src/perform.h
new file mode 100644
index 0000000..fefb05e
--- /dev/null
+++ b/src/perform.h
@@ -0,0 +1,18 @@
1#ifndef PERFORM_H
2#define PERFORM_H
3
4#include <stdint.h>
5
6class Perform
7{
8public:
9 Perform();
10 virtual ~Perform();
11
12 virtual void execute( class Builder &bld ) = 0;
13
14private:
15
16};
17
18#endif
diff --git a/src/performcmd.cpp b/src/performcmd.cpp
new file mode 100644
index 0000000..21ba737
--- /dev/null
+++ b/src/performcmd.cpp
@@ -0,0 +1,19 @@
1#include "performcmd.h"
2#include "builder.h"
3
4PerformCmd::PerformCmd( const char *sCmd, const char *sTarget ) :
5 sCommand( sCmd ),
6 sTarget( sTarget )
7{
8}
9
10PerformCmd::~PerformCmd()
11{
12}
13
14void PerformCmd::execute( class Builder &bld )
15{
16 printf("%s\n", sCommand.getString() );
17 system( sCommand.getString() );
18}
19
diff --git a/src/performcmd.h b/src/performcmd.h
new file mode 100644
index 0000000..3bc83aa
--- /dev/null
+++ b/src/performcmd.h
@@ -0,0 +1,22 @@
1#ifndef PERFORM_CMD_H
2#define PERFORM_CMD_H
3
4#include <stdint.h>
5
6#include "perform.h"
7#include "staticstring.h"
8
9class PerformCmd : public Perform
10{
11public:
12 PerformCmd( const char *sCmd, const char *sTarget );
13 virtual ~PerformCmd();
14
15 virtual void execute( class Builder &bld );
16
17private:
18 StaticString sCommand;
19 StaticString sTarget;
20};
21
22#endif
diff --git a/src/rule.cpp b/src/rule.cpp
index a240855..4425ea5 100644
--- a/src/rule.cpp
+++ b/src/rule.cpp
@@ -1,14 +1,17 @@
1#include "rule.h" 1#include "rule.h"
2#include "perform.h"
3#include "performcmd.h"
2#include "builder.h" // for BuildException 4#include "builder.h" // for BuildException
3 5
4Rule::Rule( const char *sName ) : 6Rule::Rule( const char *sName ) :
5 sName( sName ) 7 sName( sName ),
8 bNoProduces( true )
6{ 9{
10 lProduces.push_back("{target}");
7} 11}
8 12
9Rule::~Rule() 13Rule::~Rule()
10{ 14{
11 regfree( &rWhat );
12} 15}
13 16
14void Rule::debug() 17void Rule::debug()
@@ -34,7 +37,7 @@ void Rule::debug()
34 printf("one "); 37 printf("one ");
35 else if( mHow == matchAll ) 38 else if( mHow == matchAll )
36 printf("all "); 39 printf("all ");
37 printf("/%s/\n", sWhat.getString() ); 40 printf("/%s/\n", rWhat.getSource() );
38 41
39 printf(" Performs "); 42 printf(" Performs ");
40 if( pHow == perfCommand ) 43 if( pHow == perfCommand )
@@ -44,39 +47,139 @@ void Rule::debug()
44 47
45void Rule::addProduces( const char *sP ) 48void Rule::addProduces( const char *sP )
46{ 49{
50 if( bNoProduces )
51 {
52 lProduces.clear();
53 bNoProduces = false;
54 }
47 lProduces.push_back( sP ); 55 lProduces.push_back( sP );
48} 56}
49 57
50void Rule::setMatches( Matches how, const char *sW ) 58void Rule::setMatches( Matches how, const char *sW )
51{ 59{
52 sWhat = sW; 60 rWhat.compile( sW );
53 mHow = how; 61 mHow = how;
54
55 int nErr = regcomp( &rWhat, sW, REG_EXTENDED|REG_NEWLINE );
56 if( nErr )
57 {
58 size_t length = regerror( nErr, &rWhat, NULL, 0 );
59 char *buffer = new char[length];
60 (void) regerror( nErr, &rWhat, buffer, length );
61 StaticString s( buffer );
62 delete[] buffer;
63 throw BuildException( s.getString() );
64 }
65} 62}
66 63
67void Rule::setPerforms( Perform pwhat, const char *sperfcmd ) 64void Rule::setPerforms( ePerform pwhat, const char *sperfcmd )
68{ 65{
69 pHow = pwhat; 66 pHow = pwhat;
70 sPerfCmd = sperfcmd; 67 sPerfCmd = sperfcmd;
71} 68}
72 69
73std::list<std::string> Rule::execute( Builder &bld, std::list<std::string> lInput ) 70Perform *Rule::buildCommand( Builder &bld, const char *sCmd, const char *sTarget, const char *sMatches )
71{
72 Builder::varmap vars;
73 vars["target"] = sTarget;
74 vars["match"] = sMatches;
75 return new PerformCmd( bld.varRepl( sCmd, "", &vars ).c_str(), sTarget );
76}
77
78std::list<std::string> Rule::findTargets( Builder &bld, std::list<std::string> &lIn, std::string &sMatches, const char *sTarget )
79{
80 std::list<std::string> lTmp;
81
82 for( std::list<std::string>::iterator i = lIn.begin();
83 i != lIn.end(); i++ )
84 {
85 if( rWhat.execute( (*i).c_str() ) )
86 {
87 Builder::varmap *revars = bld.regexVars( &rWhat );
88 for( std::list<std::string>::iterator j = lProduces.begin();
89 j != lProduces.end(); j++ )
90 {
91 if( mHow == matchOne )
92 {
93 lTmp.push_back(
94 bld.varRepl(
95 (*j).c_str(),
96 "",
97 revars
98 )
99 );
100 Perform *p = buildCommand(
101 bld,
102 sPerfCmd,
103 (sTarget==NULL)?(lTmp.back().c_str()):(sTarget),
104 (*i).c_str()
105 );
106 p->execute( bld );
107 delete p;
108 }
109 else if( mHow == matchAll )
110 {
111 sMatches += " ";
112 sMatches += (*i);
113 }
114 }
115 delete revars;
116 }
117 }
118
119 return lTmp;
120}
121
122std::list<std::string> Rule::execute( Builder &bld, std::list<std::string> lInput, const char *sTarget )
74{ 123{
75 std::list<Rule *> lRule = bld.findRuleChain( this ); 124 std::list<Rule *> lRule = bld.findRuleChain( this );
76 125
77 std::list<std::string> ret; 126 if( !lRule.empty() )
127 {
128 printf("Rule %s chains to: ", sName.getString() );
129 for( std::list<Rule *>::iterator i = lRule.begin();
130 i != lRule.end(); i++ )
131 {
132 if( i != lRule.begin() )
133 printf(", ");
134 printf("%s", (*i)->sName.getString() );
135 }
136 printf("\n");
137 }
138
139 std::list<std::string> lOutput;
140 std::string sMatches;
141
142 for( std::list<Rule *>::iterator i = lRule.begin(); i != lRule.end(); i++ )
143 {
144 std::list<std::string> lTmp = (*i)->execute( bld, lInput );
145 lOutput.insert( lOutput.end(), lTmp.begin(), lTmp.end() );
146 }
147
148 std::list<std::string> lTmp = findTargets( bld, lInput, sMatches, sTarget );
149 lOutput.insert( lOutput.end(), lTmp.begin(), lTmp.end() );
150 lTmp = findTargets( bld, lOutput, sMatches, sTarget );
151 lOutput.insert( lOutput.end(), lTmp.begin(), lTmp.end() );
78 152
79 return ret; 153 if( mHow == matchAll )
154 {
155 lOutput.push_back(
156 bld.varRepl(
157 sTarget,
158 "",
159 NULL
160 )
161 );
162 Perform *p = buildCommand(
163 bld,
164 sPerfCmd,
165 sTarget,
166 sMatches.c_str()
167 );
168 p->execute( bld );
169 }
170
171 return lOutput;
172}
173
174bool Rule::willChain( Rule *pRule )
175{
176 for( std::list<std::string>::iterator i = pRule->lProduces.begin();
177 i != pRule->lProduces.end(); i++ )
178 {
179 if( rWhat.execute( (*i).c_str() ) )
180 return true;
181 }
80 182
183 return false;
81} 184}
82 185
diff --git a/src/rule.h b/src/rule.h
index 8371649..8246cc9 100644
--- a/src/rule.h
+++ b/src/rule.h
@@ -4,9 +4,11 @@
4#include <list> 4#include <list>
5#include <string> 5#include <string>
6#include <stdint.h> 6#include <stdint.h>
7#include <regex.h> 7#include "regexp.h"
8#include "staticstring.h" 8#include "staticstring.h"
9 9
10class Perform;
11
10class Rule 12class Rule
11{ 13{
12public: 14public:
@@ -16,7 +18,7 @@ public:
16 matchAll 18 matchAll
17 }; 19 };
18 20
19 enum Perform 21 enum ePerform
20 { 22 {
21 perfCommand 23 perfCommand
22 }; 24 };
@@ -34,20 +36,27 @@ public:
34 36
35 void addProduces( const char *sProduces ); 37 void addProduces( const char *sProduces );
36 void setMatches( Matches how, const char *sWhat ); 38 void setMatches( Matches how, const char *sWhat );
37 void setPerforms( Perform pwhat, const char *sPerfCmd ); 39 void setPerforms( ePerform pwhat, const char *sPerfCmd );
40
41 bool willChain( Rule *pRule );
38 42
39 std::list<std::string> execute( class Builder &bld, std::list<std::string> lInput ); 43 std::list<std::string> execute( class Builder &bld, std::list<std::string> lInput, const char *sTarget=NULL );
40 44
41private: 45private:
46 class Perform *buildCommand( class Builder &bld, const char *sCmd, const char *sTarget, const char *sMatches );
47 std::list<std::string> findTargets( class Builder &bld, std::list<std::string> &lIn, std::string &sMatches, const char *sTarget );
42 StaticString sName; 48 StaticString sName;
43 std::list<std::string> lProduces; 49 std::list<std::string> lProduces;
44 50
45 Matches mHow; 51 Matches mHow;
46 StaticString sWhat; 52 RegExp rWhat;
47 regex_t rWhat; 53 //StaticString sWhat;
54 //regex_t rWhat;
48 55
49 Perform pHow; 56 ePerform pHow;
50 StaticString sPerfCmd; 57 StaticString sPerfCmd;
58
59 bool bNoProduces;
51}; 60};
52 61
53#endif 62#endif
diff --git a/src/target.cpp b/src/target.cpp
index 00d16b4..8f4cc4b 100644
--- a/src/target.cpp
+++ b/src/target.cpp
@@ -26,6 +26,12 @@ void Target::debug()
26 { 26 {
27 printf(" %s\n", (*i).c_str() ); 27 printf(" %s\n", (*i).c_str() );
28 } 28 }
29 printf(" Output list:\n");
30 for( std::list<std::string>::iterator i = lOutput.begin();
31 i != lOutput.end(); i++ )
32 {
33 printf(" %s\n", (*i).c_str() );
34 }
29} 35}
30 36
31void Target::addInput( const char *sInput ) 37void Target::addInput( const char *sInput )