13 self.logger = PuginsRootInstance.logger |
15 self.logger = PuginsRootInstance.logger |
14 self.exe = PuginsRootInstance.GetProjectName() + self.extension |
16 self.exe = PuginsRootInstance.GetProjectName() + self.extension |
15 self.buildpath = PuginsRootInstance._getBuildPath() |
17 self.buildpath = PuginsRootInstance._getBuildPath() |
16 self.exe_path = os.path.join(self.buildpath, self.exe) |
18 self.exe_path = os.path.join(self.buildpath, self.exe) |
17 self.md5key = None |
19 self.md5key = None |
|
20 self.srcmd5 = {} |
18 |
21 |
19 def GetBinaryCode(self): |
22 def GetBinaryCode(self): |
20 try: |
23 try: |
21 return open(self.exe_path, "rb").read() |
24 return open(self.exe_path, "rb").read() |
22 except Exception, e: |
25 except Exception, e: |
31 else: |
34 else: |
32 try: |
35 try: |
33 return open(self._GetMD5FileName(), "r").read() |
36 return open(self._GetMD5FileName(), "r").read() |
34 except Exception, e: |
37 except Exception, e: |
35 return None |
38 return None |
|
39 |
|
40 def check_and_update_hash_and_deps(self, bn): |
|
41 # Get latest computed hash and deps |
|
42 oldhash, deps = self.srcmd5.get(bn,(None,[])) |
|
43 # read source |
|
44 src = open(os.path.join(self.buildpath, bn)).read() |
|
45 # compute new hash |
|
46 newhash = hashlib.md5(src).hexdigest() |
|
47 # compare |
|
48 match = (oldhash == newhash) |
|
49 if not match: |
|
50 # file have changed |
|
51 # update direct dependencies |
|
52 deps = [] |
|
53 for l in src.splitlines(): |
|
54 res = includes_re.match(l) |
|
55 if res is not None: |
|
56 depfn = res.groups()[0] |
|
57 if os.path.exists(os.path.join(self.buildpath, depfn)): |
|
58 #print bn + " depends on "+depfn |
|
59 deps.append(depfn) |
|
60 # store that hashand deps |
|
61 self.srcmd5[bn] = (newhash, deps) |
|
62 # recurse through deps |
|
63 # TODO detect cicular deps. |
|
64 return reduce(operator.and_, map(self.check_and_update_hash_and_deps, deps), match) |
36 |
65 |
37 |
|
38 def build(self): |
66 def build(self): |
39 # Retrieve toolchain user parameters |
67 # Retrieve toolchain user parameters |
40 toolchain_params = self.PuginsRootInstance.BeremizRoot.getTargetType().getcontent()["value"] |
68 toolchain_params = self.PuginsRootInstance.BeremizRoot.getTargetType().getcontent()["value"] |
41 self.compiler = toolchain_params.getCompiler() |
69 self.compiler = toolchain_params.getCompiler() |
42 self._CFLAGS = toolchain_params.getCFLAGS() |
70 self._CFLAGS = toolchain_params.getCFLAGS() |
50 if Location: |
78 if Location: |
51 self.logger.write("Plugin : " + self.PuginsRootInstance.GetChildByIECLocation(Location).GetCurrentName() + " " + str(Location)+"\n") |
79 self.logger.write("Plugin : " + self.PuginsRootInstance.GetChildByIECLocation(Location).GetCurrentName() + " " + str(Location)+"\n") |
52 else: |
80 else: |
53 self.logger.write("PLC :\n") |
81 self.logger.write("PLC :\n") |
54 |
82 |
|
83 relink = False |
55 for CFile, CFLAGS in CFilesAndCFLAGS: |
84 for CFile, CFLAGS in CFilesAndCFLAGS: |
56 bn = os.path.basename(CFile) |
85 bn = os.path.basename(CFile) |
57 obn = os.path.splitext(bn)[0]+".o" |
86 obn = os.path.splitext(bn)[0]+".o" |
|
87 objectfilename = os.path.splitext(CFile)[0]+".o" |
|
88 |
|
89 match = self.check_and_update_hash_and_deps(bn) |
|
90 |
|
91 if match: |
|
92 self.logger.write(" [pass] "+bn+" -> "+obn+"\n") |
|
93 else: |
|
94 relink = True |
|
95 |
|
96 self.logger.write(" [CC] "+bn+" -> "+obn+"\n") |
|
97 |
|
98 status, result, err_result = ProcessLogger( |
|
99 self.logger, |
|
100 "\"%s\" -c \"%s\" -o \"%s\" %s %s"% |
|
101 (self.compiler, CFile, objectfilename, self._CFLAGS, CFLAGS) |
|
102 ).spin() |
|
103 |
|
104 if status : |
|
105 self.logger.write_error("C compilation of "+ bn +" failed.\n") |
|
106 return False |
|
107 |
58 obns.append(obn) |
108 obns.append(obn) |
59 self.logger.write(" [CC] "+bn+" -> "+obn+"\n") |
|
60 objectfilename = os.path.splitext(CFile)[0]+".o" |
|
61 |
|
62 status, result, err_result = ProcessLogger( |
|
63 self.logger, |
|
64 "\"%s\" -c \"%s\" -o \"%s\" %s %s"% |
|
65 (self.compiler, CFile, objectfilename, self._CFLAGS, CFLAGS) |
|
66 ).spin() |
|
67 |
|
68 if status : |
|
69 self.logger.write_error("C compilation of "+ bn +" failed.\n") |
|
70 return False |
|
71 objs.append(objectfilename) |
109 objs.append(objectfilename) |
72 |
110 |
73 ######### GENERATE library FILE ######################################## |
111 ######### GENERATE library FILE ######################################## |
74 # Link all the object files into one binary file |
112 # Link all the object files into one binary file |
75 self.logger.write("Linking :\n") |
113 self.logger.write("Linking :\n") |
76 objstring = [] |
114 if relink: |
77 |
115 objstring = [] |
78 # Generate list .o files |
116 |
79 listobjstring = '"' + '" "'.join(objs) + '"' |
117 # Generate list .o files |
80 |
118 listobjstring = '"' + '" "'.join(objs) + '"' |
81 ALLldflags = ' '.join(self.CustomLDFLAGS+self.PuginsRootInstance.LDFLAGS+[self._LDFLAGS]) |
119 |
82 |
120 ALLldflags = ' '.join(self.CustomLDFLAGS+self.PuginsRootInstance.LDFLAGS+[self._LDFLAGS]) |
83 self.logger.write(" [CC] " + ' '.join(obns)+" -> " + self.exe + "\n") |
121 |
84 |
122 self.logger.write(" [CC] " + ' '.join(obns)+" -> " + self.exe + "\n") |
85 status, result, err_result = ProcessLogger( |
123 |
86 self.logger, |
124 status, result, err_result = ProcessLogger( |
87 "\"%s\" %s -o \"%s\" %s"% |
125 self.logger, |
88 (self.linker, |
126 "\"%s\" %s -o \"%s\" %s"% |
89 listobjstring, |
127 (self.linker, |
90 self.exe_path, |
128 listobjstring, |
91 ALLldflags) |
129 self.exe_path, |
92 ).spin() |
130 ALLldflags) |
93 |
131 ).spin() |
94 if status : |
132 |
95 return False |
133 if status : |
96 else : |
134 return False |
97 # Calculate md5 key and get data for the new created PLC |
135 else : |
98 data=self.GetBinaryCode() |
136 # Calculate md5 key and get data for the new created PLC |
99 self.md5key = hashlib.md5(data).hexdigest() |
137 data=self.GetBinaryCode() |
100 |
138 self.md5key = hashlib.md5(data).hexdigest() |
101 # Store new PLC filename based on md5 key |
139 |
102 file = open(self._GetMD5FileName(), "w") |
140 # Store new PLC filename based on md5 key |
103 file.write(self.md5key) |
141 f = open(self._GetMD5FileName(), "w") |
104 file.close() |
142 f.write(self.md5key) |
|
143 f.close() |
|
144 else: |
|
145 self.logger.write(" [pass] " + ' '.join(obns)+" -> " + self.exe + "\n") |
|
146 |
105 |
147 |
106 return True |
148 return True |
107 |
149 |