1 #ifndef MAKEFILE_GENERATOR
7 enum DirExpressionType { unknown, targetDir, intermediateObjectsDir }; // "type" is not right
9 class DirExpression : struct
12 DirExpressionType type;
19 property const char * dir
23 return dir ? dir : "";
29 dir = CopyString(value);
35 void Evaluate(const char * expression, Project project, CompilerConfig compiler, ProjectConfig config, int bitDepth)
38 const char * expr = expression;
44 expr = ideSettings.projectDefaultTargetDir;
45 else if(type == intermediateObjectsDir)
46 expr = ideSettings.projectDefaultIntermediateObjDir;
49 expr = defaultObjDirExpression;
51 if((len = strlen(expr)))
54 const char * configName = config && config.name && config.name[0] ? config.name : "Common";
55 const char * moduleName = project.moduleName ? project.moduleName : "";
56 const char * compilerName = (compiler && compiler.name) ? compiler.name : defaultCompilerName;
57 const char * targetPlatformName = compiler && compiler.targetPlatform ? compiler.targetPlatform : "";
58 char buffer[MAX_LOCATION];
59 for(c = 0, d = 0; c < len; c++)
61 if(expr[c] == '$' && c < len - 1 && expr[c + 1] == '(')
64 for(i = c + 2; i < len; i++)
71 if(!strnicmp(&expr[c + 2], "Config", n) || !strnicmp(&expr[c + 2], "Config", n))
74 strcat(buffer, configName);
75 CamelCase(&buffer[d]);
76 d += strlen(configName);
79 else if(!strnicmp(&expr[c + 2], "Module", n) || !strnicmp(&expr[c + 2], "Project", n))
82 strcat(buffer, moduleName);
83 //CamelCase(&buffer[d]);
84 d += strlen(moduleName);
87 else if(!strnicmp(&expr[c + 2], "Platform", n))
90 strcat(buffer, targetPlatformName);
91 CamelCase(&buffer[d]);
92 d += strlen(targetPlatformName);
95 else if(!strnicmp(&expr[c + 2], "Compiler", n))
98 strcat(buffer, compilerName);
99 CamelCase(&buffer[d]);
100 d += strlen(compilerName);
103 else if(!strnicmp(&expr[c + 2], "Debug_Suffix", n))
105 // We don't support .debug from the IDE yet...
108 else if(!strnicmp(&expr[c + 2], "Compiler_Suffix", n))
110 if(bitDepth || (compilerName[0] && strcmpi(compilerName, "default")))
112 if(compilerName[0] && strcmpi(compilerName, "default"))
116 strcat(buffer, compilerName);
117 CamelCase(&buffer[d]);
118 d += strlen(compilerName);
122 strcat(buffer, ".x32");
125 else if(bitDepth == 64)
127 strcat(buffer, ".x64");
135 buffer[d++] = expr[c];
140 buffer[d++] = expr[c];
145 else if(expr[i] == '\\' || expr[i] == '/')
148 strncat(buffer, &expr[i], i - c);
156 buffer[d++] = expr[c];
160 buffer[d++] = expr[c];
164 if(dir && strcmp(buffer, dir))
167 dir = CopyString(buffer);
172 dir = CopyString("");
177 public enum TargetTypes { unset, executable, sharedLibrary, staticLibrary };
178 public enum OptimizationStrategy { unset, none, speed, size };
179 public enum WarningsOption { unset, normal, none, all }; // TOCHECK: More options?
180 public enum BuildBitDepth { all, bits32, bits64 };
182 Array<String> CopyArrayString(Array<String> array)
184 Array<String> copy = null;
188 for(s : array) copy.Add(CopyString(s));
193 public class ProjectOptions
197 property SetBool allWarnings
205 WarningsOption warnings;
209 SetBool noLineNumbers;
210 OptimizationStrategy optimization;
211 Array<String> preprocessorDefinitions;
212 property Array<String> includeDirs
218 if(value && value.count)
223 includeDirs.Add(CopyValidateMakefilePath(s));
230 get { return includeDirs; }
231 isset { return includeDirs && includeDirs.count; }
233 String defaultNameSpace;
234 SetBool strictNameSpaces;
237 TargetTypes targetType;
238 // NOTE: The JSON Parser deletes strings after setting a String property, so we do a copy here.
239 // (This behavior is different from Objects (class instances) values which are not deleted)
240 // Code calling these properties should *NOT* use CopyString().
241 property char * targetFileName
243 set { delete targetFileName; if(value && value[0]) targetFileName = CopyValidateMakefilePath(value); }
244 get { return targetFileName; }
245 isset { return targetFileName && targetFileName[0]; }
247 property char * targetDirectory
249 set { delete targetDirectory; if(value /*&& value[0]*/) targetDirectory = CopyValidateMakefilePath(value); }
250 get { return targetDirectory; }
251 isset { return targetDirectory != null/*&& targetDirectory[0]*/; }
253 property char * objectsDirectory
255 set { delete objectsDirectory; if(value /*&& value[0]*/) objectsDirectory = CopyValidateMakefilePath(value); }
256 get { return objectsDirectory; }
257 isset { return objectsDirectory != null/*&& objectsDirectory[0]*/; }
259 Array<String> libraries;
260 Array<String> compilerOptions;
261 Array<String> linkerOptions;
262 property Array<String> libraryDirs
268 if(value && value.count)
273 libraryDirs.Add(CopyValidateMakefilePath(s));
274 value.Free(); // why do I have to do this here? it's a property, shouldn't json deal with this?
280 get { return libraryDirs; }
281 isset { return libraryDirs && libraryDirs.count; }
286 // todo; move those to compiler/linker sections
287 SetBool excludeFromBuild;
288 BuildBitDepth buildBitDepth;
291 property Array<String> prebuildCommands
296 prebuildCommands.Free();
297 if(value && value.count)
299 if(!prebuildCommands)
300 prebuildCommands = { };
302 prebuildCommands.Add(CopyValidateMakefilePath(s));
307 delete prebuildCommands;
309 get { return prebuildCommands; }
310 isset { return prebuildCommands && prebuildCommands.count; }
312 property Array<String> postbuildCommands
316 if(postbuildCommands)
317 postbuildCommands.Free();
318 if(value && value.count)
320 if(!postbuildCommands)
321 postbuildCommands = { };
323 postbuildCommands.Add(CopyValidateMakefilePath(s));
328 delete postbuildCommands;
330 get { return postbuildCommands; }
331 isset { return postbuildCommands && postbuildCommands.count; }
333 property Array<String> installCommands
338 installCommands.Free();
339 if(value && value.count)
342 installCommands = { };
344 installCommands.Add(CopyValidateMakefilePath(s));
349 delete installCommands;
351 get { return installCommands; }
352 isset { return installCommands && installCommands.count; }
355 ProjectOptions Copy()
357 // TODO: We'll want some solution so that we can use OnCopy for copying containers (Array<String>)
362 memoryGuard = memoryGuard,
364 noLineNumbers = noLineNumbers;
365 optimization = optimization,
366 defaultNameSpace = CopyString(defaultNameSpace),
367 strictNameSpaces = strictNameSpaces,
368 targetType = targetType,
369 targetFileName = /*CopyString(*/targetFileName/*)*/,
370 targetDirectory = /*CopyString(*/targetDirectory/*)*/,
371 objectsDirectory = /*CopyString(*/objectsDirectory/*)*/,
374 excludeFromBuild = excludeFromBuild,
376 preprocessorDefinitions = CopyArrayString(preprocessorDefinitions),
377 includeDirs = CopyArrayString(includeDirs),
378 libraries = CopyArrayString(libraries),
379 compilerOptions = CopyArrayString(compilerOptions),
380 linkerOptions = CopyArrayString(linkerOptions),
381 libraryDirs = CopyArrayString(libraryDirs),
382 prebuildCommands = CopyArrayString(prebuildCommands),
383 postbuildCommands = CopyArrayString(postbuildCommands),
384 installCommands = CopyArrayString(installCommands)
391 PrintLn("warnings:", warnings);
392 PrintLn("debug:", debug);
393 PrintLn("memoryGuard:", memoryGuard);
394 PrintLn("profile:", profile);
395 //PrintLn("noLineNumbers:", noLineNumbers);
396 PrintLn("optimization:", optimization);
399 //PrintLn("dddddddd:", dddddddd);
401 PrintLn("fastMath:", fastMath);
403 PrintLn("preprocessorDefinitions:", preprocessorDefinitions);
404 PrintLn("compilerOptions:", compilerOptions);
405 PrintLn("linkerOptions:", linkerOptions);
406 PrintLn("includeDirs:", includeDirs);
409 //PrintLn("dddddddd:", dddddddd);
417 if(preprocessorDefinitions) { preprocessorDefinitions.Free(); delete preprocessorDefinitions; }
418 if(includeDirs) { includeDirs.Free(); delete includeDirs; }
419 delete defaultNameSpace;
420 delete targetFileName;
421 delete targetDirectory;
422 delete objectsDirectory;
423 if(libraries) { libraries.Free(); delete libraries; }
424 if(compilerOptions) { compilerOptions.Free(); delete compilerOptions; }
425 if(linkerOptions) { linkerOptions.Free(); delete linkerOptions; }
426 if(libraryDirs) { libraryDirs.Free(); delete libraryDirs; }
427 if(prebuildCommands) { prebuildCommands.Free(); delete prebuildCommands; }
428 if(postbuildCommands) { postbuildCommands.Free(); delete postbuildCommands; }
429 if(installCommands) { installCommands.Free(); delete installCommands; }
432 Array<String> includeDirs;
433 String targetFileName;
434 String targetDirectory;
435 String objectsDirectory;
436 Array<String> libraryDirs;
437 Array<String> prebuildCommands;
438 Array<String> postbuildCommands;
439 Array<String> installCommands;
441 property bool isEmpty
445 if(warnings == unset &&
447 memoryGuard == unset &&
449 noLineNumbers == unset &&
450 optimization == unset &&
451 !preprocessorDefinitions &&
452 (!includeDirs || !includeDirs.count) &&
454 strictNameSpaces == unset &&
455 targetType == unset &&
462 (!libraryDirs || !libraryDirs.count) &&
465 excludeFromBuild == unset &&
467 (!prebuildCommands || !prebuildCommands.count) &&
468 (!postbuildCommands || !postbuildCommands.count) &&
469 (!installCommands || !installCommands.count))
476 public class PlatformOptions
480 property ProjectOptions options { get { return options; } set { options = value; } isset { return options && !options.isEmpty; } }
488 PlatformOptions Copy()
493 options ? options.Copy() : null
497 ProjectOptions options;
500 class ProjectConfig : struct
504 property ProjectOptions options { get { return options; } set { options = value; } isset { return options && !options.isEmpty; } }
505 property Array<PlatformOptions> platforms
507 get { return platforms; }
510 if(platforms) { platforms.Free(); delete platforms; }
513 List<PlatformOptions> empty { };
514 Iterator<PlatformOptions> it { value };
516 for(p : platforms; !p.options || p.options.isEmpty) empty.Add(p);
517 for(p : empty; it.Find(p)) platforms.Delete(it.pointer);
527 if(p.options && !p.options.isEmpty)
536 ProjectOptions options;
538 bool compilingModified, linkingModified, symbolGenModified;
539 Array<PlatformOptions> platforms;
546 if(platforms) { platforms.Free(); delete platforms; }
551 Array<PlatformOptions> platforms = null;
555 for(p : this.platforms)
557 platforms.Add(p.Copy());
563 options ? options.Copy() : null,