"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.FreeBSDExporter = void 0; const Exporter_1 = require("kmake/Exporters/Exporter"); const Options_1 = require("kmake/Options"); const Platform_1 = require("kmake/Platform"); const Compiler_1 = require("kmake/Compiler"); const fs = require("kmake/fsextra"); const path = require("path"); const CLionExporter_1 = require("kmake/Exporters/CLionExporter"); class FreeBSDExporter extends Exporter_1.Exporter { constructor(options) { super(options); this.clion = new CLionExporter_1.CLionExporter(options); } async exportSolution(project, from, to, platform, vrApi, options) { this.exportMakefile(project, from, to, platform, vrApi, options); this.exportCodeBlocks(project, from, to, platform, vrApi, options); this.clion.exportSolution(project, from, to, platform, vrApi, options); this.exportCompileCommands(project, from, to, platform, vrApi, options); } exportMakefile(project, from, to, platform, vrApi, options) { const cCompiler = Options_1.Options.compiler === Compiler_1.Compiler.GCC ? 'gcc' : 'clang'; const cppCompiler = Options_1.Options.compiler === Compiler_1.Compiler.GCC ? 'g++' : 'clang++'; let objects = {}; let ofiles = {}; let outputPath = path.resolve(to, options.buildPath); fs.ensureDirSync(outputPath); for (let fileobject of project.getFiles()) { let file = fileobject.file; if (file.endsWith('.cpp') || file.endsWith('.c') || file.endsWith('.cc') || file.endsWith('.s') || file.endsWith('.S')) { let name = file.toLowerCase(); if (name.indexOf('/') >= 0) name = name.substr(name.lastIndexOf('/') + 1); name = name.substr(0, name.lastIndexOf('.')); if (!objects[name]) { objects[name] = true; ofiles[file] = name; } else { while (objects[name]) { name = name + '_'; } objects[name] = true; ofiles[file] = name; } } } let gchfilelist = ''; let precompiledHeaders = []; for (let file of project.getFiles()) { if (file.options && file.options.pch && precompiledHeaders.indexOf(file.options.pch) < 0) { precompiledHeaders.push(file.options.pch); } } for (let file of project.getFiles()) { let precompiledHeader = null; for (let header of precompiledHeaders) { if (file.file.endsWith(header)) { precompiledHeader = header; break; } } if (precompiledHeader !== null) { // let realfile = path.relative(outputPath, path.resolve(from, file.file)); gchfilelist += path.basename(file.file) + '.gch '; } } let ofilelist = ''; for (let o in objects) { ofilelist += o + '.o '; } this.writeFile(path.resolve(outputPath, 'makefile')); let incline = '-I./ '; // local directory to pick up the precompiled header hxcpp.h.gch for (let inc of project.getIncludeDirs()) { inc = path.relative(outputPath, path.resolve(from, inc)); incline += '-I' + inc + ' '; } incline += '-I/usr/local/include'; // Add search dir for FreeBSD this.p('INC=' + incline); let libsline = '-static-libgcc -static-libstdc++ -pthread'; /*if (project.cmd) { libsline += ' -static'; }*/ for (let lib of project.getLibs()) { libsline += ' -l' + lib; } libsline += ' -L/usr/local/lib'; // Add search dir for FreeBSD this.p('LIB=' + libsline); let defline = ''; for (const def of project.getDefines()) { if (def.config && def.config.toLowerCase() === 'debug' && !options.debug) { continue; } if (def.config && def.config.toLowerCase() === 'release' && options.debug) { continue; } defline += '-D' + def.value + ' '; } if (!options.debug) { defline += '-DNDEBUG '; } this.p('DEF=' + defline); this.p(); let cline = '-std=c99 '; if (project.cStd !== '') { cline = '-std=' + project.cStd + ' '; } if (options.dynlib) { cline += '-fPIC '; } for (let flag of project.cFlags) { cline += flag + ' '; } this.p('CFLAGS=' + cline); let cppline = ''; if (project.cppStd !== '') { cppline = '-std=' + project.cppStd + ' '; } if (options.dynlib) { cppline += '-fPIC '; } for (let flag of project.cppFlags) { cppline += flag + ' '; } this.p('CPPFLAGS=' + cppline); let optimization = ''; if (!options.debug) optimization = '-O2'; else optimization = '-g'; let executableName = project.getSafeName(); if (project.getExecutableName()) { executableName = project.getExecutableName(); } if (options.lib) { this.p(executableName + '.a: ' + gchfilelist + ofilelist); } else if (options.dynlib) { this.p(executableName + '.so: ' + gchfilelist + ofilelist); } else { this.p(executableName + ': ' + gchfilelist + ofilelist); } let cpp = ''; let output = '-o "' + executableName + '"'; if (options.lib) { output = '-o "' + executableName + '.a"'; } else if (options.dynlib) { output = '-shared -o "' + executableName + '.so"'; } this.p('\t' + (options.lib ? 'ar rcs' : cppCompiler) + ' ' + output + ' ' + cpp + ' ' + optimization + ' ' + ofilelist + ' $(LIB)'); for (let file of project.getFiles()) { let precompiledHeader = null; for (let header of precompiledHeaders) { if (file.file.endsWith(header)) { precompiledHeader = header; break; } } if (precompiledHeader !== null) { let realfile = path.relative(outputPath, path.resolve(from, file.file)); this.p(path.basename(realfile) + '.gch: ' + realfile); this.p('\t' + cppCompiler + ' ' + cpp + ' ' + optimization + ' $(INC) $(DEF) -c ' + realfile + ' -o ' + path.basename(file.file) + '.gch'); } } for (let fileobject of project.getFiles()) { let file = fileobject.file; if (file.endsWith('.c') || file.endsWith('.cpp') || file.endsWith('.cc') || file.endsWith('.s') || file.endsWith('.S')) { if (fileobject.options && fileobject.options.nocompile) { continue; } this.p(); let name = ofiles[file]; let realfile = path.relative(outputPath, path.resolve(from, file)); this.p(name + '.o: ' + realfile); let compiler = cppCompiler; let flags = '$(CPPFLAGS)'; if (file.endsWith('.c')) { compiler = cCompiler; flags = '$(CFLAGS)'; } else if (file.endsWith('.s') || file.endsWith('.S')) { compiler = cCompiler; flags = ''; } this.p('\t' + compiler + ' ' + cpp + ' ' + optimization + ' $(INC) $(DEF) ' + flags + ' -c ' + realfile + ' -o ' + name + '.o'); } } // project.getDefines() // project.getIncludeDirs() this.closeFile(); } exportCodeBlocks(project, from, to, platform, vrApi, options) { this.writeFile(path.resolve(to, project.getSafeName() + '.cbp')); this.p(''); this.p(''); this.p('', 1); this.p('', 1); this.p('', 1); this.p(''); this.closeFile(); } exportCompileCommands(project, _from, to, platform, vrApi, options) { let from = path.resolve(process.cwd(), _from); // TODO : assembly files, precompiled headers and all that stuff // compile_commands.json is primarily for code completion so those things shouldn't matter too much this.writeFile(path.resolve(to, 'compile_commands.json')); let includes = []; for (let inc of project.getIncludeDirs()) { includes.push('-I'); includes.push(path.resolve(from, inc)); } let defines = []; for (let def of project.getDefines()) { defines.push('-D'); defines.push(def.value.replace(/\"/g, '\\"')); } let libs = []; for (let lib of project.getLibs()) { libs.push('-l' + lib); } let optimization = options.debug ? '-g' : '-O2'; let objects = {}; let ofiles = {}; for (let fileobject of project.getFiles()) { let file = fileobject.file; if (file.endsWith('.cpp') || file.endsWith('.c') || file.endsWith('.cc') || file.endsWith('.s') || file.endsWith('.S')) { let name = file.toLowerCase(); if (name.indexOf('/') >= 0) name = name.substr(name.lastIndexOf('/') + 1); name = name.substr(0, name.lastIndexOf('.')); if (!objects[name]) { objects[name] = true; ofiles[file] = name; } else { while (objects[name]) { name = name + '_'; } objects[name] = true; ofiles[file] = name; } } } let commands = []; for (let fileobject of project.getFiles()) { let file = fileobject.file; if (file.endsWith('.c') || file.endsWith('.cpp') || file.endsWith('.cc')) { let args = [file.endsWith('.c') ? '/usr/bin/clang' : '/usr/bin/clang++', optimization, '-c', '-o', (options.debug ? 'debug' : 'release') + ofiles[file] + '.o']; if (file.endsWith('.c')) { args.push('-std=' + (project.cStd !== '' ? project.cStd : 'c99')); } else if (file.endsWith('.cpp')) { args.push('-std=' + (project.cppStd !== '' ? project.cppStd : 'c++11')); } if (options.dynlib) { args.push('-fPIC'); } args.push(path.resolve(from, file)); let command = { directory: from, file: path.resolve(from, file), output: path.resolve(to, ofiles[file] + '.o'), arguments: args.concat(includes).concat(defines) }; commands.push(command); } } /*let linker_args = ['/usr/bin/clang', '-O2', '-static-libgcc', '-static-libstdc++', '-pthread']; for (let file in ofiles) { linker_args.push(path.resolve(to, ofiles[file] + '.o')); } linker_args.push('-o'); if (options.lib) { linker_args.push('-o'); linker_args.push(project.getSafeName() + '.a'); } else if (options.dynlib) { linker_args.push('-shared'); linker_args.push('-fPIC'); linker_args.push('-o'); linker_args.push(project.getSafeName() + '.so'); } else { linker_args.push('-o'); linker_args.push(project.getSafeName()); } commands.push({ directory: from, output: linker_args[linker_args.length - 1], arguments: linker_args.concat(libs) });*/ this.p(JSON.stringify(commands)); this.closeFile(); } } exports.FreeBSDExporter = FreeBSDExporter; //# sourceMappingURL=FreeBSDExporter.js.map