forgot to recurse If elements when generating macros
[reactos.git] / reactos / tools / rbuild / backend / mingw / modulehandler.cpp
1
2 #include "../../pch.h"
3 #include <assert.h>
4
5 #include "../../rbuild.h"
6 #include "mingw.h"
7 #include "modulehandler.h"
8
9 using std::string;
10 using std::vector;
11 using std::map;
12
13 map<ModuleType,MingwModuleHandler*>*
14 MingwModuleHandler::handler_map = NULL;
15 int
16 MingwModuleHandler::ref = 0;
17
18 FILE*
19 MingwModuleHandler::fMakefile = NULL;
20
21 MingwModuleHandler::MingwModuleHandler ( ModuleType moduletype )
22 {
23 if ( !ref++ )
24 handler_map = new map<ModuleType,MingwModuleHandler*>;
25 (*handler_map)[moduletype] = this;
26 }
27
28 MingwModuleHandler::~MingwModuleHandler()
29 {
30 if ( !--ref )
31 {
32 delete handler_map;
33 handler_map = NULL;
34 }
35 }
36
37 /*static*/ void
38 MingwModuleHandler::SetMakefile ( FILE* f )
39 {
40 fMakefile = f;
41 }
42
43 /*static*/ MingwModuleHandler*
44 MingwModuleHandler::LookupHandler ( const string& location,
45 ModuleType moduletype )
46 {
47 if ( !handler_map )
48 throw Exception ( "internal tool error: no registered module handlers" );
49 MingwModuleHandler* h = (*handler_map)[moduletype];
50 if ( !h )
51 {
52 throw UnknownModuleTypeException ( location, moduletype );
53 return NULL;
54 }
55 return h;
56 }
57
58 string
59 MingwModuleHandler::GetWorkingDirectory () const
60 {
61 return ".";
62 }
63
64 string
65 MingwModuleHandler::GetExtension ( const string& filename ) const
66 {
67 size_t index = filename.find_last_of ( '.' );
68 if (index != string::npos)
69 return filename.substr ( index );
70 return "";
71 }
72
73 string
74 MingwModuleHandler::ReplaceExtension ( const string& filename,
75 const string& newExtension ) const
76 {
77 size_t index = filename.find_last_of ( '.' );
78 if (index != string::npos)
79 return filename.substr ( 0, index ) + newExtension;
80 return filename;
81 }
82
83 string
84 MingwModuleHandler::GetModuleArchiveFilename ( const Module& module ) const
85 {
86 return ReplaceExtension ( FixupTargetFilename ( module.GetPath () ).c_str (),
87 ".a" );
88 }
89
90 string
91 MingwModuleHandler::GetImportLibraryDependencies ( const Module& module ) const
92 {
93 if ( module.libraries.size () == 0 )
94 return "";
95
96 string dependencies ( "" );
97 for ( size_t i = 0; i < module.libraries.size (); i++ )
98 {
99 if ( dependencies.size () > 0 )
100 dependencies += " ";
101 const Module* importedModule = module.project.LocateModule ( module.libraries[i]->name );
102 assert ( importedModule != NULL );
103 dependencies += FixupTargetFilename ( importedModule->GetDependencyPath () ).c_str ();
104 }
105 return dependencies;
106 }
107
108 string
109 MingwModuleHandler::GetModuleDependencies ( const Module& module ) const
110 {
111 if ( module.dependencies.size () == 0 )
112 return "";
113
114 string dependencies ( "" );
115 for ( size_t i = 0; i < module.dependencies.size (); i++ )
116 {
117 if ( dependencies.size () > 0 )
118 dependencies += " ";
119 const Dependency* dependency = module.dependencies[i];
120 const Module* dependencyModule = dependency->dependencyModule;
121 dependencies += dependencyModule->GetTargets ();
122 }
123 return dependencies;
124 }
125
126 string
127 MingwModuleHandler::GetAllDependencies ( const Module& module ) const
128 {
129 string dependencies = GetImportLibraryDependencies ( module );
130 string s = GetModuleDependencies ( module );
131 if (s.length () > 0)
132 {
133 dependencies += " ";
134 dependencies += s;
135 }
136 return dependencies;
137 }
138
139 string
140 MingwModuleHandler::GetSourceFilenames ( const Module& module ) const
141 {
142 if ( module.files.size () == 0 )
143 return "";
144
145 string sourceFilenames ( "" );
146 for ( size_t i = 0; i < module.files.size (); i++ )
147 {
148 if ( sourceFilenames.size () > 0 )
149 sourceFilenames += " ";
150 sourceFilenames += module.files[i]->name;
151 }
152 return sourceFilenames;
153 }
154
155 string
156 MingwModuleHandler::GetObjectFilename ( const string& sourceFilename ) const
157 {
158 return FixupTargetFilename ( ReplaceExtension ( sourceFilename,
159 ".o" ) );
160 }
161
162 string
163 MingwModuleHandler::GetObjectFilenames ( const Module& module ) const
164 {
165 if ( module.files.size () == 0 )
166 return "";
167
168 string objectFilenames ( "" );
169 for ( size_t i = 0; i < module.files.size (); i++ )
170 {
171 if ( objectFilenames.size () > 0 )
172 objectFilenames += " ";
173 objectFilenames += GetObjectFilename ( module.files[i]->name );
174 }
175 return objectFilenames;
176 }
177
178 string
179 MingwModuleHandler::GenerateGccDefineParametersFromVector ( const vector<Define*>& defines ) const
180 {
181 string parameters;
182 for (size_t i = 0; i < defines.size (); i++)
183 {
184 Define& define = *defines[i];
185 if (parameters.length () > 0)
186 parameters += " ";
187 parameters += "-D";
188 parameters += define.name;
189 if (define.value.length () > 0)
190 {
191 parameters += "=";
192 parameters += define.value;
193 }
194 }
195 return parameters;
196 }
197
198 string
199 MingwModuleHandler::GenerateGccDefineParameters ( const Module& module ) const
200 {
201 string parameters = GenerateGccDefineParametersFromVector ( module.project.defines );
202 string s = GenerateGccDefineParametersFromVector ( module.defines );
203 if (s.length () > 0)
204 {
205 parameters += " ";
206 parameters += s;
207 }
208 return parameters;
209 }
210
211 string
212 MingwModuleHandler::ConcatenatePaths ( const string& path1,
213 const string& path2 ) const
214 {
215 if ( ( path1.length () == 0 ) || ( path1 == "." ) || ( path1 == "./" ) )
216 return path2;
217 if ( path1[path1.length ()] == CSEP )
218 return path1 + path2;
219 else
220 return path1 + CSEP + path2;
221 }
222
223 string
224 MingwModuleHandler::GenerateGccIncludeParametersFromVector ( const vector<Include*>& includes ) const
225 {
226 string parameters;
227 for ( size_t i = 0; i < includes.size (); i++ )
228 {
229 Include& include = *includes[i];
230 if (parameters.length () > 0)
231 parameters += " ";
232 parameters += "-I" + include.directory;
233 }
234 return parameters;
235 }
236
237 void
238 MingwModuleHandler::GenerateGccModuleIncludeVariable ( const Module& module ) const
239 {
240 #if 0
241 string name ( module.name + "_CFLAGS" );
242 fprintf ( fMakefile,
243 "%s := %s %s\n",
244 name.c_str(),
245 GenerateGccDefineParameters(module).c_str(),
246 GenerateGccIncludeParameters(module).c_str() );
247 #endif
248 }
249
250 string
251 MingwModuleHandler::GenerateGccIncludeParameters ( const Module& module ) const
252 {
253 string parameters = GenerateGccIncludeParametersFromVector ( module.includes );
254 string s = GenerateGccIncludeParametersFromVector ( module.project.includes );
255 if ( s.length () > 0 )
256 {
257 parameters += " ";
258 parameters += s;
259 }
260 return parameters;
261 }
262
263 void
264 MingwModuleHandler::GenerateMacros (
265 const Module& module,
266 const char* op,
267 const vector<File*>& files,
268 const vector<Include*>* includes,
269 const vector<Define*>& defines,
270 const vector<If*>* ifs,
271 const string& cflags_macro,
272 const string& nasmflags_macro,
273 const string& objs_macro) const
274 {
275 size_t i;
276
277 if ( (includes && includes->size()) || defines.size() )
278 {
279 fprintf (
280 fMakefile,
281 "%s %s",
282 cflags_macro.c_str(),
283 op );
284 if ( includes )
285 for ( i = 0; i < includes->size(); i++ )
286 fprintf (
287 fMakefile,
288 " -I%s",
289 (*includes)[i]->directory.c_str() );
290 for ( i = 0; i < module.defines.size(); i++ )
291 {
292 Define& d = *module.defines[i];
293 fprintf (
294 fMakefile,
295 " -D%s",
296 d.name.c_str() );
297 if ( d.value.size() )
298 fprintf (
299 fMakefile,
300 "=%s",
301 d.value.c_str() );
302 }
303 fprintf ( fMakefile, "\n" );
304 }
305
306 if ( files.size() )
307 {
308 fprintf (
309 fMakefile,
310 "%s %s",
311 objs_macro.c_str(),
312 op );
313 for ( i = 0; i < files.size(); i++ )
314 {
315 fprintf (
316 fMakefile,
317 "%s%s",
318 ( i%10 == 9 ? "\\\n\t" : " " ),
319 GetObjectFilename(files[i]->name).c_str() );
320 }
321 fprintf ( fMakefile, "\n" );
322 }
323
324 if ( ifs && ifs->size() )
325 {
326 for ( size_t i = 0; i < module.ifs.size(); i++ )
327 {
328 If& rIf = *(*ifs)[i];
329 if ( rIf.defines.size() || rIf.files.size() || rIf.ifs.size() )
330 {
331 fprintf (
332 fMakefile,
333 "ifeq ($(%s),\"%s\")\n",
334 rIf.property.c_str(),
335 rIf.value.c_str() );
336 GenerateMacros (
337 module,
338 "+=",
339 rIf.files,
340 NULL,
341 rIf.defines,
342 &rIf.ifs,
343 cflags_macro,
344 nasmflags_macro,
345 objs_macro );
346 fprintf (
347 fMakefile,
348 "endif\n\n" );
349 }
350 }
351 }
352 }
353
354 void
355 MingwModuleHandler::GenerateMacros (
356 const Module& module,
357 const string& cflags_macro,
358 const string& nasmflags_macro,
359 const string& objs_macro) const
360 {
361 GenerateMacros (
362 module,
363 "=",
364 module.files,
365 &module.includes,
366 module.defines,
367 NULL,
368 cflags_macro,
369 nasmflags_macro,
370 objs_macro );
371 fprintf ( fMakefile, "\n" );
372
373 for ( size_t i = 0; i < module.ifs.size(); i++ )
374 {
375 If& rIf = *module.ifs[i];
376 if ( rIf.defines.size() || rIf.files.size() || rIf.ifs.size() )
377 {
378 fprintf (
379 fMakefile,
380 "ifeq ($(%s),\"%s\")\n",
381 rIf.property.c_str(),
382 rIf.value.c_str() );
383 GenerateMacros (
384 module,
385 "+=",
386 rIf.files,
387 NULL,
388 rIf.defines,
389 &rIf.ifs,
390 cflags_macro,
391 nasmflags_macro,
392 objs_macro );
393 fprintf (
394 fMakefile,
395 "endif\n\n" );
396 }
397 }
398 }
399
400 string
401 MingwModuleHandler::GenerateGccCommand ( const Module& module,
402 const string& sourceFilename,
403 const string& cc,
404 const string& cflagsMacro ) const
405 {
406 string objectFilename = GetObjectFilename ( sourceFilename );
407 return ssprintf ( "%s -c %s -o %s %s\n",
408 cc.c_str (),
409 sourceFilename.c_str (),
410 objectFilename.c_str (),
411 cflagsMacro.c_str () );
412 }
413
414 string
415 MingwModuleHandler::GenerateGccAssemblerCommand ( const Module& module,
416 const string& sourceFilename,
417 const string& cc,
418 const string& cflagsMacro ) const
419 {
420 string objectFilename = GetObjectFilename ( sourceFilename );
421 return ssprintf ( "%s -x assembler-with-cpp -c %s -o %s -D__ASM__ %s\n",
422 cc.c_str (),
423 sourceFilename.c_str (),
424 objectFilename.c_str (),
425 cflagsMacro.c_str () );
426 }
427
428 string
429 MingwModuleHandler::GenerateNasmCommand ( const Module& module,
430 const string& sourceFilename,
431 const string& nasmflagsMacro ) const
432 {
433 string objectFilename = GetObjectFilename ( sourceFilename );
434 return ssprintf ( "%s -f win32 %s -o %s %s\n",
435 "nasm",
436 sourceFilename.c_str (),
437 objectFilename.c_str (),
438 nasmflagsMacro.c_str () );
439 }
440
441 string
442 MingwModuleHandler::GenerateCommand ( const Module& module,
443 const string& sourceFilename,
444 const string& cc,
445 const string& cflagsMacro,
446 const string& nasmflagsMacro ) const
447 {
448 string extension = GetExtension ( sourceFilename );
449 if ( extension == ".c" || extension == ".C" )
450 return GenerateGccCommand ( module,
451 sourceFilename,
452 cc,
453 cflagsMacro );
454 else if ( extension == ".s" || extension == ".S" )
455 return GenerateGccAssemblerCommand ( module,
456 sourceFilename,
457 cc,
458 cflagsMacro );
459 else if ( extension == ".asm" || extension == ".ASM" )
460 return GenerateNasmCommand ( module,
461 sourceFilename,
462 nasmflagsMacro );
463
464 throw InvalidOperationException ( __FILE__,
465 __LINE__,
466 "Unsupported filename extension '%s' in file '%s'",
467 extension.c_str (),
468 sourceFilename.c_str () );
469 }
470
471 void
472 MingwModuleHandler::GenerateObjectFileTargets ( const Module& module,
473 const vector<File*>& files,
474 const string& cc,
475 const string& cflagsMacro,
476 const string& nasmflagsMacro ) const
477 {
478 if ( files.size () == 0 )
479 return;
480
481 for ( size_t i = 0; i < files.size (); i++ )
482 {
483 string sourceFilename = files[i]->name;
484 string objectFilename = GetObjectFilename ( sourceFilename );
485 fprintf ( fMakefile,
486 "%s: %s\n",
487 objectFilename.c_str (),
488 sourceFilename.c_str () );
489 fprintf ( fMakefile,
490 "\t%s\n",
491 GenerateCommand ( module,
492 sourceFilename,
493 cc,
494 cflagsMacro,
495 nasmflagsMacro ).c_str () );
496 }
497
498 fprintf ( fMakefile, "\n" );
499 }
500
501 void
502 MingwModuleHandler::GenerateObjectFileTargets ( const Module& module,
503 const string& cc,
504 const string& cflagsMacro,
505 const string& nasmflagsMacro ) const
506 {
507 GenerateObjectFileTargets ( module, module.files, cc, cflagsMacro, nasmflagsMacro );
508 for ( size_t i = 0; i < module.ifs.size(); i++ )
509 GenerateObjectFileTargets ( module, module.ifs[i]->files, cc, cflagsMacro, nasmflagsMacro );
510 }
511
512 void
513 MingwModuleHandler::GenerateArchiveTarget ( const Module& module,
514 const string& ar,
515 const string& objs_macro ) const
516 {
517 string archiveFilename = GetModuleArchiveFilename ( module );
518 string sourceFilenames = GetSourceFilenames ( module );
519
520 fprintf ( fMakefile,
521 "%s: %s\n",
522 archiveFilename.c_str (),
523 objs_macro.c_str ());
524
525 fprintf ( fMakefile,
526 "\t%s -rc %s %s\n\n",
527 ar.c_str (),
528 archiveFilename.c_str (),
529 objs_macro.c_str ());
530 }
531
532 void
533 MingwModuleHandler::GenerateMacrosAndTargets (
534 const Module& module,
535 const string& cc,
536 const string& ar ) const
537 {
538 string cflagsMacro = ssprintf("%s_CFLAGS",module.name.c_str());
539 string nasmflagsMacro = ssprintf("%s_NASMFLAGS",module.name.c_str());
540 string objectsMacro = ssprintf("%s_OBJS",module.name.c_str());
541
542 GenerateMacros ( module, cflagsMacro, nasmflagsMacro, objectsMacro );
543
544 // future references to the macros will be to get their values
545 cflagsMacro = ssprintf("$(%s)",cflagsMacro.c_str());
546 nasmflagsMacro = ssprintf("$(%s)",nasmflagsMacro.c_str());
547 objectsMacro = ssprintf("$(%s)",objectsMacro.c_str());
548
549 GenerateArchiveTarget ( module, ar, objectsMacro );
550 GenerateObjectFileTargets ( module, cc, cflagsMacro, nasmflagsMacro );
551 }
552
553 void
554 MingwModuleHandler::GenerateMacrosAndTargetsHost ( const Module& module ) const
555 {
556 GenerateMacrosAndTargets ( module, "${host_gcc}", "${host_ar}" );
557 }
558
559 void
560 MingwModuleHandler::GenerateMacrosAndTargetsTarget ( const Module& module ) const
561 {
562 GenerateMacrosAndTargets ( module, "${gcc}", "${ar}" );
563 }
564
565 string
566 MingwModuleHandler::GetInvocationDependencies ( const Module& module ) const
567 {
568 string dependencies;
569 for ( size_t i = 0; i < module.invocations.size (); i++ )
570 {
571 Invoke& invoke = *module.invocations[i];
572 if (invoke.invokeModule == &module)
573 /* Protect against circular dependencies */
574 continue;
575 if ( dependencies.length () > 0 )
576 dependencies += " ";
577 dependencies += invoke.GetTargets ();
578 }
579 return dependencies;
580 }
581
582 string
583 MingwModuleHandler::GetInvocationParameters ( const Invoke& invoke ) const
584 {
585 string parameters ( "" );
586 size_t i;
587 for (i = 0; i < invoke.output.size (); i++)
588 {
589 if (parameters.length () > 0)
590 parameters += " ";
591 InvokeFile& invokeFile = *invoke.output[i];
592 if (invokeFile.switches.length () > 0)
593 {
594 parameters += invokeFile.switches;
595 parameters += " ";
596 }
597 parameters += invokeFile.name;
598 }
599
600 for (i = 0; i < invoke.input.size (); i++)
601 {
602 if (parameters.length () > 0)
603 parameters += " ";
604 InvokeFile& invokeFile = *invoke.input[i];
605 if (invokeFile.switches.length () > 0)
606 {
607 parameters += invokeFile.switches;
608 parameters += " ";
609 }
610 parameters += invokeFile.name;
611 }
612
613 return parameters;
614 }
615
616 void
617 MingwModuleHandler::GenerateInvocations ( const Module& module ) const
618 {
619 if ( module.invocations.size () == 0 )
620 return;
621
622 for ( size_t i = 0; i < module.invocations.size (); i++ )
623 {
624 const Invoke& invoke = *module.invocations[i];
625
626 if ( invoke.invokeModule->type != BuildTool )
627 throw InvalidBuildFileException ( module.node.location,
628 "Only modules of type buildtool can be invoked." );
629
630 string invokeTarget = module.GetInvocationTarget ( i );
631 fprintf ( fMakefile,
632 "%s: %s\n\n",
633 invoke.GetTargets ().c_str (),
634 invokeTarget.c_str () );
635 fprintf ( fMakefile,
636 "%s: %s\n",
637 invokeTarget.c_str (),
638 FixupTargetFilename ( invoke.invokeModule->GetPath () ).c_str () );
639 fprintf ( fMakefile,
640 "\t%s %s\n\n",
641 FixupTargetFilename ( invoke.invokeModule->GetPath () ).c_str (),
642 GetInvocationParameters ( invoke ).c_str () );
643 fprintf ( fMakefile,
644 ".PNONY: %s\n\n",
645 invokeTarget.c_str () );
646 }
647 }
648
649 string
650 MingwModuleHandler::GetPreconditionDependenciesName ( const Module& module ) const
651 {
652 return ssprintf ( "%s_precondition",
653 module.name.c_str () );
654 }
655
656 void
657 MingwModuleHandler::GeneratePreconditionDependencies ( const Module& module ) const
658 {
659 string preconditionDependenciesName = GetPreconditionDependenciesName ( module );
660 string sourceFilenames = GetSourceFilenames ( module );
661 string dependencies = GetModuleDependencies ( module );
662 string s = GetInvocationDependencies ( module );
663 if ( s.length () > 0 )
664 {
665 if ( dependencies.length () > 0 )
666 dependencies += " ";
667 dependencies += s;
668 }
669
670 fprintf ( fMakefile,
671 ".PHONY: %s\n\n",
672 preconditionDependenciesName.c_str () );
673 fprintf ( fMakefile,
674 "%s: %s\n\n",
675 preconditionDependenciesName.c_str (),
676 dependencies.c_str () );
677 const char* p = sourceFilenames.c_str();
678 const char* end = p + strlen(p);
679 while ( p < end )
680 {
681 const char* p2 = &p[512];
682 if ( p2 > end )
683 p2 = end;
684 while ( p2 > p && !isspace(*p2) )
685 --p2;
686 if ( p == p2 )
687 {
688 p2 = strpbrk ( p, " \t" );
689 if ( !p2 )
690 p2 = end;
691 }
692 fprintf ( fMakefile,
693 "%.*s: %s\n",
694 p2-p,
695 p,
696 preconditionDependenciesName.c_str ());
697 p = p2;
698 p += strspn ( p, " \t" );
699 }
700 fprintf ( fMakefile, "\n" );
701 }
702
703
704 static MingwBuildToolModuleHandler buildtool_handler;
705
706 MingwBuildToolModuleHandler::MingwBuildToolModuleHandler()
707 : MingwModuleHandler ( BuildTool )
708 {
709 }
710
711 void
712 MingwBuildToolModuleHandler::Process ( const Module& module )
713 {
714 GeneratePreconditionDependencies ( module );
715 GenerateBuildToolModuleTarget ( module );
716 GenerateInvocations ( module );
717 }
718
719 void
720 MingwBuildToolModuleHandler::GenerateBuildToolModuleTarget ( const Module& module )
721 {
722 string target ( FixupTargetFilename ( module.GetPath () ) );
723 string archiveFilename = GetModuleArchiveFilename ( module );
724 fprintf ( fMakefile, "%s: %s\n",
725 target.c_str (),
726 archiveFilename.c_str () );
727 fprintf ( fMakefile,
728 "\t${host_gcc} -o %s %s\n\n",
729 target.c_str (),
730 archiveFilename.c_str () );
731 GenerateMacrosAndTargetsHost ( module );
732 }
733
734 static MingwKernelModuleHandler kernelmodule_handler;
735
736 MingwKernelModuleHandler::MingwKernelModuleHandler ()
737 : MingwModuleHandler ( Kernel )
738 {
739 }
740
741 void
742 MingwKernelModuleHandler::Process ( const Module& module )
743 {
744 GeneratePreconditionDependencies ( module );
745 GenerateKernelModuleTarget ( module );
746 GenerateInvocations ( module );
747 }
748
749 void
750 MingwKernelModuleHandler::GenerateKernelModuleTarget ( const Module& module )
751 {
752 static string ros_junk ( "$(ROS_TEMPORARY)" );
753 //static string ros_output ( "$(ROS_INTERMEDIATE)" );
754 string target ( FixupTargetFilename(module.GetPath()) );
755 string workingDirectory = GetWorkingDirectory ( );
756 string archiveFilename = GetModuleArchiveFilename ( module );
757 string importLibraryDependencies = GetImportLibraryDependencies ( module );
758 string base_tmp = ros_junk + module.name + ".base.tmp";
759 string junk_tmp = ros_junk + module.name + ".junk.tmp";
760 string temp_exp = ros_junk + module.name + ".temp.exp";
761 string gccOptions = ssprintf ("-Wl,-T,%s" SSEP "ntoskrnl.lnk -Wl,--subsystem,native -Wl,--entry,_NtProcessStartup -Wl,--image-base,0xC0000000 -Wl,--file-alignment,0x1000 -Wl,--section-alignment,0x1000 -nostartfiles -mdll",
762 module.GetBasePath ().c_str () );
763 fprintf ( fMakefile, "%s: %s %s\n",
764 target.c_str (),
765 archiveFilename.c_str (),
766 importLibraryDependencies.c_str () );
767 fprintf ( fMakefile,
768 "\t${gcc} %s -Wl,--base-file,%s -o %s %s %s\n",
769 gccOptions.c_str (),
770 base_tmp.c_str (),
771 junk_tmp.c_str (),
772 archiveFilename.c_str (),
773 importLibraryDependencies.c_str () );
774 fprintf ( fMakefile,
775 "\t${rm} %s\n",
776 junk_tmp.c_str () );
777 fprintf ( fMakefile,
778 "\t${dlltool} --dllname %s --base-file %s --output-exp %s --kill-at\n",
779 target.c_str (),
780 base_tmp.c_str (),
781 temp_exp.c_str ());
782 fprintf ( fMakefile,
783 "\t${rm} %s\n",
784 base_tmp.c_str () );
785 fprintf ( fMakefile,
786 "\t${gcc} %s -Wl,%s -o %s %s %s\n",
787 gccOptions.c_str (),
788 temp_exp.c_str (),
789 target.c_str (),
790 archiveFilename.c_str (),
791 importLibraryDependencies.c_str () );
792 fprintf ( fMakefile,
793 "\t${rm} %s\n\n",
794 temp_exp.c_str () );
795
796 GenerateMacrosAndTargetsTarget ( module );
797 }
798
799
800 static MingwStaticLibraryModuleHandler staticlibrary_handler;
801
802 MingwStaticLibraryModuleHandler::MingwStaticLibraryModuleHandler ()
803 : MingwModuleHandler ( StaticLibrary )
804 {
805 }
806
807 void
808 MingwStaticLibraryModuleHandler::Process ( const Module& module )
809 {
810 GeneratePreconditionDependencies ( module );
811 GenerateStaticLibraryModuleTarget ( module );
812 GenerateInvocations ( module );
813 }
814
815 void
816 MingwStaticLibraryModuleHandler::GenerateStaticLibraryModuleTarget ( const Module& module )
817 {
818 GenerateMacrosAndTargetsTarget ( module );
819 }
820
821
822 static MingwKernelModeDLLModuleHandler kernelmodedll_handler;
823
824 MingwKernelModeDLLModuleHandler::MingwKernelModeDLLModuleHandler ()
825 : MingwModuleHandler ( KernelModeDLL )
826 {
827 }
828
829 void
830 MingwKernelModeDLLModuleHandler::Process ( const Module& module )
831 {
832 GeneratePreconditionDependencies ( module );
833 GenerateKernelModeDLLModuleTarget ( module );
834 GenerateInvocations ( module );
835 }
836
837 void
838 MingwKernelModeDLLModuleHandler::GenerateKernelModeDLLModuleTarget ( const Module& module )
839 {
840 static string ros_junk ( "$(ROS_TEMPORARY)" );
841 string target ( FixupTargetFilename ( module.GetPath () ) );
842 string workingDirectory = GetWorkingDirectory ( );
843 string archiveFilename = GetModuleArchiveFilename ( module );
844 string importLibraryDependencies = GetImportLibraryDependencies ( module );
845
846 if (module.importLibrary != NULL)
847 {
848 fprintf ( fMakefile, "%s:\n",
849 module.GetDependencyPath ().c_str () );
850
851 fprintf ( fMakefile,
852 "\t${dlltool} --dllname %s --def %s --output-lib %s --kill-at\n\n",
853 module.GetTargetName ().c_str (),
854 FixupTargetFilename ( module.GetBasePath () + SSEP + module.importLibrary->definition ).c_str (),
855 FixupTargetFilename ( module.GetDependencyPath () ).c_str () );
856 }
857
858 if (module.files.size () > 0)
859 {
860 fprintf ( fMakefile, "%s: %s %s\n",
861 target.c_str (),
862 archiveFilename.c_str (),
863 importLibraryDependencies.c_str () );
864
865 fprintf ( fMakefile,
866 "\t${gcc} -Wl,--subsystem,native -Wl,--entry,_DriverEntry@8 -Wl,--image-base,0x10000 -Wl,--file-alignment,0x1000 -Wl,--section-alignment,0x1000 -nostartfiles -mdll -o %s %s %s\n\n",
867 target.c_str (),
868 archiveFilename.c_str (),
869 importLibraryDependencies.c_str () );
870
871 GenerateMacrosAndTargetsTarget ( module );
872 }
873 else
874 {
875 fprintf ( fMakefile, "%s:\n",
876 target.c_str ());
877 fprintf ( fMakefile, ".PHONY: %s\n\n",
878 target.c_str ());
879 }
880 }
881
882
883 static MingwNativeDLLModuleHandler nativedll_handler;
884
885 MingwNativeDLLModuleHandler::MingwNativeDLLModuleHandler ()
886 : MingwModuleHandler ( NativeDLL )
887 {
888 }
889
890 void
891 MingwNativeDLLModuleHandler::Process ( const Module& module )
892 {
893 GeneratePreconditionDependencies ( module );
894 GenerateNativeDLLModuleTarget ( module );
895 GenerateInvocations ( module );
896 }
897
898 void
899 MingwNativeDLLModuleHandler::GenerateNativeDLLModuleTarget ( const Module& module )
900 {
901 static string ros_junk ( "$(ROS_TEMPORARY)" );
902 string target ( FixupTargetFilename ( module.GetPath () ) );
903 string workingDirectory = GetWorkingDirectory ( );
904 string archiveFilename = GetModuleArchiveFilename ( module );
905 string importLibraryDependencies = GetImportLibraryDependencies ( module );
906
907 if (module.importLibrary != NULL)
908 {
909 fprintf ( fMakefile, "%s:\n",
910 module.GetDependencyPath ().c_str () );
911
912 fprintf ( fMakefile,
913 "\t${dlltool} --dllname %s --def %s --output-lib %s --kill-at\n\n",
914 module.GetTargetName ().c_str (),
915 FixupTargetFilename ( module.GetBasePath () + SSEP + module.importLibrary->definition ).c_str (),
916 FixupTargetFilename ( module.GetDependencyPath () ).c_str () );
917 }
918
919 if (module.files.size () > 0)
920 {
921 fprintf ( fMakefile, "%s: %s %s\n",
922 target.c_str (),
923 archiveFilename.c_str (),
924 importLibraryDependencies.c_str () );
925
926 fprintf ( fMakefile,
927 "\t${gcc} -Wl,--subsystem,native -Wl,--entry,_DllMainCRTStartup@12 -Wl,--image-base,0x10000 -Wl,--file-alignment,0x1000 -Wl,--section-alignment,0x1000 -nostartfiles -nostdlib -mdll -o %s %s %s\n\n",
928 target.c_str (),
929 archiveFilename.c_str (),
930 importLibraryDependencies.c_str () );
931
932 GenerateMacrosAndTargetsTarget ( module );
933 }
934 else
935 {
936 fprintf ( fMakefile, "%s:\n\n",
937 target.c_str ());
938 fprintf ( fMakefile, ".PHONY: %s\n\n",
939 target.c_str ());
940 }
941 }