create phony targets for each module name, so you can type 'make ntoskrnl' instead...
[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 char* op,
266 const vector<File*>& files,
267 const vector<Include*>& includes,
268 const vector<Define*>& defines,
269 const vector<If*>& ifs,
270 const string& cflags_macro,
271 const string& nasmflags_macro,
272 const string& objs_macro) const
273 {
274 size_t i;
275
276 if ( includes.size() || defines.size() )
277 {
278 fprintf (
279 fMakefile,
280 "%s %s",
281 cflags_macro.c_str(),
282 op );
283 for ( i = 0; i < includes.size(); i++ )
284 {
285 fprintf (
286 fMakefile,
287 " -I%s",
288 includes[i]->directory.c_str() );
289 }
290 for ( i = 0; i < defines.size(); i++ )
291 {
292 Define& d = *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 for ( i = 0; i < ifs.size(); i++ )
325 {
326 If& rIf = *ifs[i];
327 if ( rIf.defines.size() || rIf.includes.size() || rIf.files.size() || rIf.ifs.size() )
328 {
329 fprintf (
330 fMakefile,
331 "ifeq (\"$(%s)\",\"%s\")\n",
332 rIf.property.c_str(),
333 rIf.value.c_str() );
334 GenerateMacros (
335 "+=",
336 rIf.files,
337 rIf.includes,
338 rIf.defines,
339 rIf.ifs,
340 cflags_macro,
341 nasmflags_macro,
342 objs_macro );
343 fprintf (
344 fMakefile,
345 "endif\n\n" );
346 }
347 }
348 }
349
350 void
351 MingwModuleHandler::GenerateMacros (
352 const Module& module,
353 const string& cflags_macro,
354 const string& nasmflags_macro,
355 const string& objs_macro) const
356 {
357 GenerateMacros (
358 "=",
359 module.files,
360 module.includes,
361 module.defines,
362 module.ifs,
363 cflags_macro,
364 nasmflags_macro,
365 objs_macro );
366 fprintf ( fMakefile, "\n" );
367
368 fprintf (
369 fMakefile,
370 "%s += $(PROJECT_CFLAGS)\n\n",
371 cflags_macro.c_str () );
372 }
373
374 string
375 MingwModuleHandler::GenerateGccCommand ( const Module& module,
376 const string& sourceFilename,
377 const string& cc,
378 const string& cflagsMacro ) const
379 {
380 string objectFilename = GetObjectFilename ( sourceFilename );
381 return ssprintf ( "%s -c %s -o %s %s\n",
382 cc.c_str (),
383 sourceFilename.c_str (),
384 objectFilename.c_str (),
385 cflagsMacro.c_str () );
386 }
387
388 string
389 MingwModuleHandler::GenerateGccAssemblerCommand ( const Module& module,
390 const string& sourceFilename,
391 const string& cc,
392 const string& cflagsMacro ) const
393 {
394 string objectFilename = GetObjectFilename ( sourceFilename );
395 return ssprintf ( "%s -x assembler-with-cpp -c %s -o %s -D__ASM__ %s\n",
396 cc.c_str (),
397 sourceFilename.c_str (),
398 objectFilename.c_str (),
399 cflagsMacro.c_str () );
400 }
401
402 string
403 MingwModuleHandler::GenerateNasmCommand ( const Module& module,
404 const string& sourceFilename,
405 const string& nasmflagsMacro ) const
406 {
407 string objectFilename = GetObjectFilename ( sourceFilename );
408 return ssprintf ( "%s -f win32 %s -o %s %s\n",
409 "nasm",
410 sourceFilename.c_str (),
411 objectFilename.c_str (),
412 nasmflagsMacro.c_str () );
413 }
414
415 string
416 MingwModuleHandler::GenerateCommand ( const Module& module,
417 const string& sourceFilename,
418 const string& cc,
419 const string& cflagsMacro,
420 const string& nasmflagsMacro ) const
421 {
422 string extension = GetExtension ( sourceFilename );
423 if ( extension == ".c" || extension == ".C" )
424 return GenerateGccCommand ( module,
425 sourceFilename,
426 cc,
427 cflagsMacro );
428 else if ( extension == ".s" || extension == ".S" )
429 return GenerateGccAssemblerCommand ( module,
430 sourceFilename,
431 cc,
432 cflagsMacro );
433 else if ( extension == ".asm" || extension == ".ASM" )
434 return GenerateNasmCommand ( module,
435 sourceFilename,
436 nasmflagsMacro );
437
438 throw InvalidOperationException ( __FILE__,
439 __LINE__,
440 "Unsupported filename extension '%s' in file '%s'",
441 extension.c_str (),
442 sourceFilename.c_str () );
443 }
444
445 void
446 MingwModuleHandler::GenerateObjectFileTargets ( const Module& module,
447 const vector<File*>& files,
448 const vector<If*>& ifs,
449 const string& cc,
450 const string& cflagsMacro,
451 const string& nasmflagsMacro ) const
452 {
453 size_t i;
454
455 for ( i = 0; i < files.size (); i++ )
456 {
457 string sourceFilename = files[i]->name;
458 string objectFilename = GetObjectFilename ( sourceFilename );
459 fprintf ( fMakefile,
460 "%s: %s\n",
461 objectFilename.c_str (),
462 sourceFilename.c_str () );
463 fprintf ( fMakefile,
464 "\t%s\n",
465 GenerateCommand ( module,
466 sourceFilename,
467 cc,
468 cflagsMacro,
469 nasmflagsMacro ).c_str () );
470 }
471
472 for ( i = 0; i < ifs.size(); i++ )
473 GenerateObjectFileTargets ( module, ifs[i]->files, ifs[i]->ifs, cc, cflagsMacro, nasmflagsMacro );
474 }
475
476 void
477 MingwModuleHandler::GenerateObjectFileTargets ( const Module& module,
478 const string& cc,
479 const string& cflagsMacro,
480 const string& nasmflagsMacro ) const
481 {
482 GenerateObjectFileTargets ( module, module.files, module.ifs, cc, cflagsMacro, nasmflagsMacro );
483 fprintf ( fMakefile, "\n" );
484 }
485
486 void
487 MingwModuleHandler::GenerateArchiveTarget ( const Module& module,
488 const string& ar,
489 const string& objs_macro ) const
490 {
491 string archiveFilename = GetModuleArchiveFilename ( module );
492 string sourceFilenames = GetSourceFilenames ( module );
493
494 fprintf ( fMakefile,
495 "%s: %s\n",
496 archiveFilename.c_str (),
497 objs_macro.c_str ());
498
499 fprintf ( fMakefile,
500 "\t%s -rc %s %s\n\n",
501 ar.c_str (),
502 archiveFilename.c_str (),
503 objs_macro.c_str ());
504 }
505
506 void
507 MingwModuleHandler::GenerateMacrosAndTargets (
508 const Module& module,
509 const string& cc,
510 const string& ar ) const
511 {
512 string cflagsMacro = ssprintf("%s_CFLAGS",module.name.c_str());
513 string nasmflagsMacro = ssprintf("%s_NASMFLAGS",module.name.c_str());
514 string objectsMacro = ssprintf("%s_OBJS",module.name.c_str());
515
516 GenerateMacros ( module, cflagsMacro, nasmflagsMacro, objectsMacro );
517
518 // generate phony target for module name
519 fprintf ( fMakefile, ".PHONY: %s\n",
520 module.name.c_str() );
521 fprintf ( fMakefile, "%s: %s\n\n",
522 module.name.c_str(),
523 module.GetPath().c_str() );
524
525 // future references to the macros will be to get their values
526 cflagsMacro = ssprintf("$(%s)",cflagsMacro.c_str());
527 nasmflagsMacro = ssprintf("$(%s)",nasmflagsMacro.c_str());
528 objectsMacro = ssprintf("$(%s)",objectsMacro.c_str());
529
530 GenerateArchiveTarget ( module, ar, objectsMacro );
531 GenerateObjectFileTargets ( module, cc, cflagsMacro, nasmflagsMacro );
532 }
533
534 void
535 MingwModuleHandler::GenerateMacrosAndTargetsHost ( const Module& module ) const
536 {
537 GenerateMacrosAndTargets ( module, "${host_gcc}", "${host_ar}" );
538 }
539
540 void
541 MingwModuleHandler::GenerateMacrosAndTargetsTarget ( const Module& module ) const
542 {
543 GenerateMacrosAndTargets ( module, "${gcc}", "${ar}" );
544 }
545
546 string
547 MingwModuleHandler::GetInvocationDependencies ( const Module& module ) const
548 {
549 string dependencies;
550 for ( size_t i = 0; i < module.invocations.size (); i++ )
551 {
552 Invoke& invoke = *module.invocations[i];
553 if (invoke.invokeModule == &module)
554 /* Protect against circular dependencies */
555 continue;
556 if ( dependencies.length () > 0 )
557 dependencies += " ";
558 dependencies += invoke.GetTargets ();
559 }
560 return dependencies;
561 }
562
563 string
564 MingwModuleHandler::GetInvocationParameters ( const Invoke& invoke ) const
565 {
566 string parameters ( "" );
567 size_t i;
568 for (i = 0; i < invoke.output.size (); i++)
569 {
570 if (parameters.length () > 0)
571 parameters += " ";
572 InvokeFile& invokeFile = *invoke.output[i];
573 if (invokeFile.switches.length () > 0)
574 {
575 parameters += invokeFile.switches;
576 parameters += " ";
577 }
578 parameters += invokeFile.name;
579 }
580
581 for (i = 0; i < invoke.input.size (); i++)
582 {
583 if (parameters.length () > 0)
584 parameters += " ";
585 InvokeFile& invokeFile = *invoke.input[i];
586 if (invokeFile.switches.length () > 0)
587 {
588 parameters += invokeFile.switches;
589 parameters += " ";
590 }
591 parameters += invokeFile.name;
592 }
593
594 return parameters;
595 }
596
597 void
598 MingwModuleHandler::GenerateInvocations ( const Module& module ) const
599 {
600 if ( module.invocations.size () == 0 )
601 return;
602
603 for ( size_t i = 0; i < module.invocations.size (); i++ )
604 {
605 const Invoke& invoke = *module.invocations[i];
606
607 if ( invoke.invokeModule->type != BuildTool )
608 throw InvalidBuildFileException ( module.node.location,
609 "Only modules of type buildtool can be invoked." );
610
611 string invokeTarget = module.GetInvocationTarget ( i );
612 fprintf ( fMakefile,
613 "%s: %s\n\n",
614 invoke.GetTargets ().c_str (),
615 invokeTarget.c_str () );
616 fprintf ( fMakefile,
617 "%s: %s\n",
618 invokeTarget.c_str (),
619 FixupTargetFilename ( invoke.invokeModule->GetPath () ).c_str () );
620 fprintf ( fMakefile,
621 "\t%s %s\n\n",
622 FixupTargetFilename ( invoke.invokeModule->GetPath () ).c_str (),
623 GetInvocationParameters ( invoke ).c_str () );
624 fprintf ( fMakefile,
625 ".PNONY: %s\n\n",
626 invokeTarget.c_str () );
627 }
628 }
629
630 string
631 MingwModuleHandler::GetPreconditionDependenciesName ( const Module& module ) const
632 {
633 return ssprintf ( "%s_precondition",
634 module.name.c_str () );
635 }
636
637 void
638 MingwModuleHandler::GeneratePreconditionDependencies ( const Module& module ) const
639 {
640 string preconditionDependenciesName = GetPreconditionDependenciesName ( module );
641 string sourceFilenames = GetSourceFilenames ( module );
642 string dependencies = GetModuleDependencies ( module );
643 string s = GetInvocationDependencies ( module );
644 if ( s.length () > 0 )
645 {
646 if ( dependencies.length () > 0 )
647 dependencies += " ";
648 dependencies += s;
649 }
650
651 fprintf ( fMakefile,
652 ".PHONY: %s\n\n",
653 preconditionDependenciesName.c_str () );
654 fprintf ( fMakefile,
655 "%s: %s\n\n",
656 preconditionDependenciesName.c_str (),
657 dependencies.c_str () );
658 const char* p = sourceFilenames.c_str();
659 const char* end = p + strlen(p);
660 while ( p < end )
661 {
662 const char* p2 = &p[512];
663 if ( p2 > end )
664 p2 = end;
665 while ( p2 > p && !isspace(*p2) )
666 --p2;
667 if ( p == p2 )
668 {
669 p2 = strpbrk ( p, " \t" );
670 if ( !p2 )
671 p2 = end;
672 }
673 fprintf ( fMakefile,
674 "%.*s: %s\n",
675 p2-p,
676 p,
677 preconditionDependenciesName.c_str ());
678 p = p2;
679 p += strspn ( p, " \t" );
680 }
681 fprintf ( fMakefile, "\n" );
682 }
683
684
685 static MingwBuildToolModuleHandler buildtool_handler;
686
687 MingwBuildToolModuleHandler::MingwBuildToolModuleHandler()
688 : MingwModuleHandler ( BuildTool )
689 {
690 }
691
692 void
693 MingwBuildToolModuleHandler::Process ( const Module& module )
694 {
695 GeneratePreconditionDependencies ( module );
696 GenerateBuildToolModuleTarget ( module );
697 GenerateInvocations ( module );
698 }
699
700 void
701 MingwBuildToolModuleHandler::GenerateBuildToolModuleTarget ( const Module& module )
702 {
703 string target ( FixupTargetFilename ( module.GetPath () ) );
704 string archiveFilename = GetModuleArchiveFilename ( module );
705
706 GenerateMacrosAndTargetsHost ( module );
707
708 fprintf ( fMakefile, "%s: %s\n",
709 target.c_str (),
710 archiveFilename.c_str () );
711 fprintf ( fMakefile,
712 "\t${host_gcc} -o %s %s\n\n",
713 target.c_str (),
714 archiveFilename.c_str () );
715 }
716
717 static MingwKernelModuleHandler kernelmodule_handler;
718
719 MingwKernelModuleHandler::MingwKernelModuleHandler ()
720 : MingwModuleHandler ( Kernel )
721 {
722 }
723
724 void
725 MingwKernelModuleHandler::Process ( const Module& module )
726 {
727 GeneratePreconditionDependencies ( module );
728 GenerateKernelModuleTarget ( module );
729 GenerateInvocations ( module );
730 }
731
732 void
733 MingwKernelModuleHandler::GenerateKernelModuleTarget ( const Module& module )
734 {
735 static string ros_junk ( "$(ROS_TEMPORARY)" );
736 //static string ros_output ( "$(ROS_INTERMEDIATE)" );
737 string target ( FixupTargetFilename(module.GetPath()) );
738 string workingDirectory = GetWorkingDirectory ( );
739 string archiveFilename = GetModuleArchiveFilename ( module );
740 string importLibraryDependencies = GetImportLibraryDependencies ( module );
741 string base_tmp = ros_junk + module.name + ".base.tmp";
742 string junk_tmp = ros_junk + module.name + ".junk.tmp";
743 string temp_exp = ros_junk + module.name + ".temp.exp";
744 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",
745 module.GetBasePath ().c_str () );
746
747 GenerateMacrosAndTargetsTarget ( module );
748
749 fprintf ( fMakefile, "%s: %s %s\n",
750 target.c_str (),
751 archiveFilename.c_str (),
752 importLibraryDependencies.c_str () );
753 fprintf ( fMakefile,
754 "\t${gcc} %s -Wl,--base-file,%s -o %s %s %s\n",
755 gccOptions.c_str (),
756 base_tmp.c_str (),
757 junk_tmp.c_str (),
758 archiveFilename.c_str (),
759 importLibraryDependencies.c_str () );
760 fprintf ( fMakefile,
761 "\t${rm} %s\n",
762 junk_tmp.c_str () );
763 fprintf ( fMakefile,
764 "\t${dlltool} --dllname %s --base-file %s --output-exp %s --kill-at\n",
765 target.c_str (),
766 base_tmp.c_str (),
767 temp_exp.c_str ());
768 fprintf ( fMakefile,
769 "\t${rm} %s\n",
770 base_tmp.c_str () );
771 fprintf ( fMakefile,
772 "\t${gcc} %s -Wl,%s -o %s %s %s\n",
773 gccOptions.c_str (),
774 temp_exp.c_str (),
775 target.c_str (),
776 archiveFilename.c_str (),
777 importLibraryDependencies.c_str () );
778 fprintf ( fMakefile,
779 "\t${rm} %s\n\n",
780 temp_exp.c_str () );
781 }
782
783
784 static MingwStaticLibraryModuleHandler staticlibrary_handler;
785
786 MingwStaticLibraryModuleHandler::MingwStaticLibraryModuleHandler ()
787 : MingwModuleHandler ( StaticLibrary )
788 {
789 }
790
791 void
792 MingwStaticLibraryModuleHandler::Process ( const Module& module )
793 {
794 GeneratePreconditionDependencies ( module );
795 GenerateStaticLibraryModuleTarget ( module );
796 GenerateInvocations ( module );
797 }
798
799 void
800 MingwStaticLibraryModuleHandler::GenerateStaticLibraryModuleTarget ( const Module& module )
801 {
802 GenerateMacrosAndTargetsTarget ( module );
803 }
804
805
806 static MingwKernelModeDLLModuleHandler kernelmodedll_handler;
807
808 MingwKernelModeDLLModuleHandler::MingwKernelModeDLLModuleHandler ()
809 : MingwModuleHandler ( KernelModeDLL )
810 {
811 }
812
813 void
814 MingwKernelModeDLLModuleHandler::Process ( const Module& module )
815 {
816 GeneratePreconditionDependencies ( module );
817 GenerateKernelModeDLLModuleTarget ( module );
818 GenerateInvocations ( module );
819 }
820
821 void
822 MingwKernelModeDLLModuleHandler::GenerateKernelModeDLLModuleTarget ( const Module& module )
823 {
824 static string ros_junk ( "$(ROS_TEMPORARY)" );
825 string target ( FixupTargetFilename ( module.GetPath () ) );
826 string workingDirectory = GetWorkingDirectory ( );
827 string archiveFilename = GetModuleArchiveFilename ( module );
828 string importLibraryDependencies = GetImportLibraryDependencies ( module );
829
830 if (module.importLibrary != NULL)
831 {
832 fprintf ( fMakefile, "%s:\n",
833 module.GetDependencyPath ().c_str () );
834
835 fprintf ( fMakefile,
836 "\t${dlltool} --dllname %s --def %s --output-lib %s --kill-at\n\n",
837 module.GetTargetName ().c_str (),
838 FixupTargetFilename ( module.GetBasePath () + SSEP + module.importLibrary->definition ).c_str (),
839 FixupTargetFilename ( module.GetDependencyPath () ).c_str () );
840 }
841
842 if (module.files.size () > 0)
843 {
844 GenerateMacrosAndTargetsTarget ( module );
845
846 fprintf ( fMakefile, "%s: %s %s\n",
847 target.c_str (),
848 archiveFilename.c_str (),
849 importLibraryDependencies.c_str () );
850
851 fprintf ( fMakefile,
852 "\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",
853 target.c_str (),
854 archiveFilename.c_str (),
855 importLibraryDependencies.c_str () );
856 }
857 else
858 {
859 fprintf ( fMakefile, "%s:\n",
860 target.c_str ());
861 fprintf ( fMakefile, ".PHONY: %s\n\n",
862 target.c_str ());
863 }
864 }
865
866
867 static MingwNativeDLLModuleHandler nativedll_handler;
868
869 MingwNativeDLLModuleHandler::MingwNativeDLLModuleHandler ()
870 : MingwModuleHandler ( NativeDLL )
871 {
872 }
873
874 void
875 MingwNativeDLLModuleHandler::Process ( const Module& module )
876 {
877 GeneratePreconditionDependencies ( module );
878 GenerateNativeDLLModuleTarget ( module );
879 GenerateInvocations ( module );
880 }
881
882 void
883 MingwNativeDLLModuleHandler::GenerateNativeDLLModuleTarget ( const Module& module )
884 {
885 static string ros_junk ( "$(ROS_TEMPORARY)" );
886 string target ( FixupTargetFilename ( module.GetPath () ) );
887 string workingDirectory = GetWorkingDirectory ( );
888 string archiveFilename = GetModuleArchiveFilename ( module );
889 string importLibraryDependencies = GetImportLibraryDependencies ( module );
890
891 if (module.importLibrary != NULL)
892 {
893 fprintf ( fMakefile, "%s:\n",
894 module.GetDependencyPath ().c_str () );
895
896 fprintf ( fMakefile,
897 "\t${dlltool} --dllname %s --def %s --output-lib %s --kill-at\n\n",
898 module.GetTargetName ().c_str (),
899 FixupTargetFilename ( module.GetBasePath () + SSEP + module.importLibrary->definition ).c_str (),
900 FixupTargetFilename ( module.GetDependencyPath () ).c_str () );
901 }
902
903 if (module.files.size () > 0)
904 {
905 GenerateMacrosAndTargetsTarget ( module );
906
907 fprintf ( fMakefile, "%s: %s %s\n",
908 target.c_str (),
909 archiveFilename.c_str (),
910 importLibraryDependencies.c_str () );
911
912 fprintf ( fMakefile,
913 "\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",
914 target.c_str (),
915 archiveFilename.c_str (),
916 importLibraryDependencies.c_str () );
917 }
918 else
919 {
920 fprintf ( fMakefile, "%s:\n\n",
921 target.c_str ());
922 fprintf ( fMakefile, ".PHONY: %s\n\n",
923 target.c_str ());
924 }
925 }
926
927
928 static MingwWin32DLLModuleHandler win32dll_handler;
929
930 MingwWin32DLLModuleHandler::MingwWin32DLLModuleHandler ()
931 : MingwModuleHandler ( Win32DLL )
932 {
933 }
934
935 void
936 MingwWin32DLLModuleHandler::Process ( const Module& module )
937 {
938 GeneratePreconditionDependencies ( module );
939 GenerateWin32DLLModuleTarget ( module );
940 GenerateInvocations ( module );
941 }
942
943 void
944 MingwWin32DLLModuleHandler::GenerateWin32DLLModuleTarget ( const Module& module )
945 {
946 static string ros_junk ( "$(ROS_TEMPORARY)" );
947 string target ( FixupTargetFilename ( module.GetPath () ) );
948 string workingDirectory = GetWorkingDirectory ( );
949 string archiveFilename = GetModuleArchiveFilename ( module );
950 string importLibraryDependencies = GetImportLibraryDependencies ( module );
951
952 if (module.importLibrary != NULL)
953 {
954 fprintf ( fMakefile, "%s:\n",
955 module.GetDependencyPath ().c_str () );
956
957 fprintf ( fMakefile,
958 "\t${dlltool} --dllname %s --def %s --output-lib %s --kill-at\n\n",
959 module.GetTargetName ().c_str (),
960 FixupTargetFilename ( module.GetBasePath () + SSEP + module.importLibrary->definition ).c_str (),
961 FixupTargetFilename ( module.GetDependencyPath () ).c_str () );
962 }
963
964 if (module.files.size () > 0)
965 {
966 GenerateMacrosAndTargetsTarget ( module );
967
968 fprintf ( fMakefile, "%s: %s %s\n",
969 target.c_str (),
970 archiveFilename.c_str (),
971 importLibraryDependencies.c_str () );
972
973 fprintf ( fMakefile,
974 "\t${gcc} -Wl,--subsystem,console -Wl,--entry,_DllMain@12 -Wl,--image-base,0x10000 -Wl,--file-alignment,0x1000 -Wl,--section-alignment,0x1000 -nostartfiles -nostdlib -mdll -o %s %s %s\n",
975 target.c_str (),
976 archiveFilename.c_str (),
977 importLibraryDependencies.c_str () );
978 }
979 else
980 {
981 fprintf ( fMakefile, "%s:\n\n",
982 target.c_str ());
983 fprintf ( fMakefile, ".PHONY: %s\n\n",
984 target.c_str ());
985 }
986 }