| 1 |
#include "gen/cl_options.h" |
|---|
| 2 |
#include "gen/cl_helpers.h" |
|---|
| 3 |
|
|---|
| 4 |
#include "llvm/Target/TargetMachine.h" |
|---|
| 5 |
#include "llvm/Target/TargetData.h" |
|---|
| 6 |
|
|---|
| 7 |
#include "gen/logger.h" |
|---|
| 8 |
|
|---|
| 9 |
#include "llvm/Support/CommandLine.h" |
|---|
| 10 |
|
|---|
| 11 |
namespace opts { |
|---|
| 12 |
|
|---|
| 13 |
// Positional options first, in order: |
|---|
| 14 |
cl::list<std::string> fileList( |
|---|
| 15 |
cl::Positional, cl::desc("files")); |
|---|
| 16 |
|
|---|
| 17 |
cl::list<std::string> runargs("run", |
|---|
| 18 |
cl::desc("program args..."), |
|---|
| 19 |
cl::Positional, |
|---|
| 20 |
cl::PositionalEatsArgs); |
|---|
| 21 |
|
|---|
| 22 |
|
|---|
| 23 |
static cl::opt<bool, true> useDeprecated("d", |
|---|
| 24 |
cl::desc("Allow deprecated language features"), |
|---|
| 25 |
cl::ZeroOrMore, |
|---|
| 26 |
cl::location(global.params.useDeprecated)); |
|---|
| 27 |
|
|---|
| 28 |
static cl::opt<ubyte, true> useDv1( |
|---|
| 29 |
cl::desc("Force language version:"), |
|---|
| 30 |
cl::ZeroOrMore, |
|---|
| 31 |
cl::values( |
|---|
| 32 |
clEnumValN(1, "v1", "D language version 1.00"), |
|---|
| 33 |
clEnumValEnd), |
|---|
| 34 |
cl::location(global.params.Dversion), |
|---|
| 35 |
cl::init(2), |
|---|
| 36 |
cl::Hidden); |
|---|
| 37 |
|
|---|
| 38 |
cl::opt<bool> compileOnly("c", |
|---|
| 39 |
cl::desc("Do not link"), |
|---|
| 40 |
cl::ZeroOrMore); |
|---|
| 41 |
|
|---|
| 42 |
static cl::opt<bool, true> verbose("v", |
|---|
| 43 |
cl::desc("Verbose"), |
|---|
| 44 |
cl::ZeroOrMore, |
|---|
| 45 |
cl::location(global.params.verbose)); |
|---|
| 46 |
|
|---|
| 47 |
static cl::opt<bool, true> verbose_cg("v-cg", |
|---|
| 48 |
cl::desc("Verbose codegen"), |
|---|
| 49 |
cl::ZeroOrMore, |
|---|
| 50 |
cl::location(global.params.verbose_cg)); |
|---|
| 51 |
|
|---|
| 52 |
static cl::opt<bool, true> warnings("w", |
|---|
| 53 |
cl::desc("Enable warnings"), |
|---|
| 54 |
cl::ZeroOrMore, |
|---|
| 55 |
cl::location(global.params.warnings)); |
|---|
| 56 |
|
|---|
| 57 |
static cl::opt<ubyte, true> debugInfo( |
|---|
| 58 |
cl::desc("Generating debug information:"), |
|---|
| 59 |
cl::ZeroOrMore, |
|---|
| 60 |
cl::values( |
|---|
| 61 |
clEnumValN(1, "g", "Generate debug information"), |
|---|
| 62 |
clEnumValN(2, "gc", "Same as -g, but pretend to be C"), |
|---|
| 63 |
clEnumValEnd), |
|---|
| 64 |
cl::location(global.params.symdebug), |
|---|
| 65 |
cl::init(0)); |
|---|
| 66 |
|
|---|
| 67 |
|
|---|
| 68 |
static cl::opt<bool, true> annotate("annotate", |
|---|
| 69 |
cl::desc("Annotate the bitcode with human readable source code"), |
|---|
| 70 |
cl::location(global.params.llvmAnnotate)); |
|---|
| 71 |
|
|---|
| 72 |
cl::opt<bool> noAsm("noasm", |
|---|
| 73 |
cl::desc("Disallow use of inline assembler")); |
|---|
| 74 |
|
|---|
| 75 |
// Output file options |
|---|
| 76 |
cl::opt<bool> dontWriteObj("o-", |
|---|
| 77 |
cl::desc("Do not write object file")); |
|---|
| 78 |
|
|---|
| 79 |
cl::opt<std::string> objectFile("of", |
|---|
| 80 |
cl::value_desc("filename"), |
|---|
| 81 |
cl::Prefix, |
|---|
| 82 |
cl::desc("Use <filename> as output file name")); |
|---|
| 83 |
|
|---|
| 84 |
cl::opt<std::string> objectDir("od", |
|---|
| 85 |
cl::value_desc("objdir"), |
|---|
| 86 |
cl::Prefix, |
|---|
| 87 |
cl::desc("Write object files to directory <objdir>")); |
|---|
| 88 |
|
|---|
| 89 |
|
|---|
| 90 |
// Output format options |
|---|
| 91 |
cl::opt<bool> output_bc("output-bc", |
|---|
| 92 |
cl::desc("Write LLVM bitcode")); |
|---|
| 93 |
|
|---|
| 94 |
cl::opt<bool> output_ll("output-ll", |
|---|
| 95 |
cl::desc("Write LLVM IR")); |
|---|
| 96 |
|
|---|
| 97 |
cl::opt<bool> output_s("output-s", |
|---|
| 98 |
cl::desc("Write native assembly")); |
|---|
| 99 |
|
|---|
| 100 |
cl::opt<cl::boolOrDefault> output_o("output-o", |
|---|
| 101 |
cl::desc("Write native object")); |
|---|
| 102 |
|
|---|
| 103 |
|
|---|
| 104 |
// DDoc options |
|---|
| 105 |
static cl::opt<bool, true> doDdoc("D", |
|---|
| 106 |
cl::desc("Generate documentation"), |
|---|
| 107 |
cl::location(global.params.doDocComments)); |
|---|
| 108 |
|
|---|
| 109 |
cl::opt<std::string> ddocDir("Dd", |
|---|
| 110 |
cl::desc("Write documentation file to <docdir> directory"), |
|---|
| 111 |
cl::value_desc("docdir"), |
|---|
| 112 |
cl::Prefix); |
|---|
| 113 |
|
|---|
| 114 |
cl::opt<std::string> ddocFile("Df", |
|---|
| 115 |
cl::desc("Write documentation file to <filename>"), |
|---|
| 116 |
cl::value_desc("filename"), |
|---|
| 117 |
cl::Prefix); |
|---|
| 118 |
|
|---|
| 119 |
|
|---|
| 120 |
// Header generation options |
|---|
| 121 |
#ifdef _DH |
|---|
| 122 |
static cl::opt<bool, true> doHdrGen("H", |
|---|
| 123 |
cl::desc("Generate 'header' file"), |
|---|
| 124 |
cl::location(global.params.doHdrGeneration)); |
|---|
| 125 |
|
|---|
| 126 |
cl::opt<std::string> hdrDir("Hd", |
|---|
| 127 |
cl::desc("Write 'header' file to <hdrdir> directory"), |
|---|
| 128 |
cl::value_desc("hdrdir"), |
|---|
| 129 |
cl::Prefix); |
|---|
| 130 |
|
|---|
| 131 |
cl::opt<std::string> hdrFile("Hf", |
|---|
| 132 |
cl::desc("Write 'header' file to <filename>"), |
|---|
| 133 |
cl::value_desc("filename"), |
|---|
| 134 |
cl::Prefix); |
|---|
| 135 |
#endif |
|---|
| 136 |
|
|---|
| 137 |
|
|---|
| 138 |
|
|---|
| 139 |
static cl::opt<bool, true> unittest("unittest", |
|---|
| 140 |
cl::desc("Compile in unit tests"), |
|---|
| 141 |
cl::location(global.params.useUnitTests)); |
|---|
| 142 |
|
|---|
| 143 |
|
|---|
| 144 |
static ArrayAdapter strImpPathStore("J", global.params.fileImppath); |
|---|
| 145 |
static cl::list<std::string, ArrayAdapter> stringImportPaths("J", |
|---|
| 146 |
cl::desc("Where to look for string imports"), |
|---|
| 147 |
cl::value_desc("path"), |
|---|
| 148 |
cl::location(strImpPathStore), |
|---|
| 149 |
cl::Prefix); |
|---|
| 150 |
|
|---|
| 151 |
|
|---|
| 152 |
|
|---|
| 153 |
// -d-debug is a bit messy, it has 3 modes: |
|---|
| 154 |
// -d-debug=ident, -d-debug=level and -d-debug (without argument) |
|---|
| 155 |
// That last of these must be acted upon immediately to ensure proper |
|---|
| 156 |
// interaction with other options, so it needs some special handling: |
|---|
| 157 |
std::vector<std::string> debugArgs; |
|---|
| 158 |
|
|---|
| 159 |
struct D_DebugStorage { |
|---|
| 160 |
void push_back(const std::string& str) { |
|---|
| 161 |
if (str.empty()) { |
|---|
| 162 |
// Bare "-d-debug" has a special meaning. |
|---|
| 163 |
global.params.useAssert = true; |
|---|
| 164 |
global.params.useArrayBounds = true; |
|---|
| 165 |
global.params.useInvariants = true; |
|---|
| 166 |
global.params.useIn = true; |
|---|
| 167 |
global.params.useOut = true; |
|---|
| 168 |
debugArgs.push_back("1"); |
|---|
| 169 |
} else { |
|---|
| 170 |
debugArgs.push_back(str); |
|---|
| 171 |
} |
|---|
| 172 |
} |
|---|
| 173 |
}; |
|---|
| 174 |
|
|---|
| 175 |
static D_DebugStorage dds; |
|---|
| 176 |
|
|---|
| 177 |
// -debug is already declared in LLVM (at least, in debug builds), |
|---|
| 178 |
// so we need to be a bit more verbose. |
|---|
| 179 |
static cl::list<std::string, D_DebugStorage> debugVersionsOption("d-debug", |
|---|
| 180 |
cl::desc("Compile in debug code >= <level> or identified by <idents>."), |
|---|
| 181 |
cl::value_desc("level/idents"), |
|---|
| 182 |
cl::location(dds), |
|---|
| 183 |
cl::CommaSeparated, |
|---|
| 184 |
cl::ValueOptional); |
|---|
| 185 |
|
|---|
| 186 |
|
|---|
| 187 |
|
|---|
| 188 |
// -version is also declared in LLVM, so again we need to be a bit more verbose. |
|---|
| 189 |
cl::list<std::string> versions("d-version", |
|---|
| 190 |
cl::desc("Compile in version code >= <level> or identified by <idents>"), |
|---|
| 191 |
cl::value_desc("level/idents"), |
|---|
| 192 |
cl::CommaSeparated); |
|---|
| 193 |
|
|---|
| 194 |
|
|---|
| 195 |
static ArrayAdapter linkSwitchStore("L", global.params.linkswitches); |
|---|
| 196 |
static cl::list<std::string, ArrayAdapter> linkerSwitches("L", |
|---|
| 197 |
cl::desc("Pass <linkerflag> to the linker"), |
|---|
| 198 |
cl::value_desc("linkerflag"), |
|---|
| 199 |
cl::location(linkSwitchStore), |
|---|
| 200 |
cl::Prefix); |
|---|
| 201 |
|
|---|
| 202 |
|
|---|
| 203 |
cl::opt<std::string> moduleDepsFile("deps", |
|---|
| 204 |
cl::desc("Write module dependencies to filename"), |
|---|
| 205 |
cl::value_desc("filename")); |
|---|
| 206 |
|
|---|
| 207 |
|
|---|
| 208 |
cl::opt<std::string> mArch("march", |
|---|
| 209 |
cl::desc("Architecture to generate code for:")); |
|---|
| 210 |
|
|---|
| 211 |
cl::opt<bool> m32bits("m32", |
|---|
| 212 |
cl::desc("32 bit target"), |
|---|
| 213 |
cl::ZeroOrMore); |
|---|
| 214 |
|
|---|
| 215 |
cl::opt<bool> m64bits("m64", |
|---|
| 216 |
cl::desc("64 bit target"), |
|---|
| 217 |
cl::ZeroOrMore); |
|---|
| 218 |
|
|---|
| 219 |
cl::opt<std::string> mCPU("mcpu", |
|---|
| 220 |
cl::desc("Target a specific cpu type (-mcpu=help for details)"), |
|---|
| 221 |
cl::value_desc("cpu-name"), |
|---|
| 222 |
cl::init("")); |
|---|
| 223 |
|
|---|
| 224 |
cl::list<std::string> mAttrs("mattr", |
|---|
| 225 |
cl::CommaSeparated, |
|---|
| 226 |
cl::desc("Target specific attributes (-mattr=help for details)"), |
|---|
| 227 |
cl::value_desc("a1,+a2,-a3,...")); |
|---|
| 228 |
|
|---|
| 229 |
cl::opt<std::string> mTargetTriple("mtriple", |
|---|
| 230 |
cl::desc("Override target triple")); |
|---|
| 231 |
|
|---|
| 232 |
|
|---|
| 233 |
// "Hidden debug switches" |
|---|
| 234 |
// Are these ever used? |
|---|
| 235 |
static cl::opt<bool, true> debuga("hidden-debug--a", |
|---|
| 236 |
cl::desc("Hidden debug option A"), |
|---|
| 237 |
cl::ReallyHidden, |
|---|
| 238 |
cl::location(global.params.debuga)); |
|---|
| 239 |
static cl::opt<bool, true> debugb("hidden-debug-b", |
|---|
| 240 |
cl::desc("Hidden debug option B"), |
|---|
| 241 |
cl::ReallyHidden, |
|---|
| 242 |
cl::location(global.params.debugb)); |
|---|
| 243 |
static cl::opt<bool, true> debugc("hidden-debug-c", |
|---|
| 244 |
cl::desc("Hidden debug option C"), |
|---|
| 245 |
cl::ReallyHidden, |
|---|
| 246 |
cl::location(global.params.debugc)); |
|---|
| 247 |
static cl::opt<bool, true> debugf("hidden-debug-f", |
|---|
| 248 |
cl::desc("Hidden debug option F"), |
|---|
| 249 |
cl::ReallyHidden, |
|---|
| 250 |
cl::location(global.params.debugf)); |
|---|
| 251 |
static cl::opt<bool, true> debugr("hidden-debug-r", |
|---|
| 252 |
cl::desc("Hidden debug option R"), |
|---|
| 253 |
cl::ReallyHidden, |
|---|
| 254 |
cl::location(global.params.debugr)); |
|---|
| 255 |
static cl::opt<bool, true> debugw("hidden-debug-w", |
|---|
| 256 |
cl::desc("Hidden debug option W"), |
|---|
| 257 |
cl::ReallyHidden, |
|---|
| 258 |
cl::location(global.params.debugw)); |
|---|
| 259 |
static cl::opt<bool, true> debugx("hidden-debug-x", |
|---|
| 260 |
cl::desc("Hidden debug option X"), |
|---|
| 261 |
cl::ReallyHidden, |
|---|
| 262 |
cl::location(global.params.debugx)); |
|---|
| 263 |
static cl::opt<bool, true> debugy("hidden-debug-y", |
|---|
| 264 |
cl::desc("Hidden debug option Y"), |
|---|
| 265 |
cl::ReallyHidden, |
|---|
| 266 |
cl::location(global.params.debugy)); |
|---|
| 267 |
|
|---|
| 268 |
|
|---|
| 269 |
static cl::opt<bool, true, FlagParser> asserts("asserts", |
|---|
| 270 |
cl::desc("(*) Enable assertions"), |
|---|
| 271 |
cl::value_desc("bool"), |
|---|
| 272 |
cl::location(global.params.useAssert), |
|---|
| 273 |
cl::init(true)); |
|---|
| 274 |
|
|---|
| 275 |
static cl::opt<bool, true, FlagParser> boundsChecks("boundscheck", |
|---|
| 276 |
cl::desc("(*) Enable array bounds checks"), |
|---|
| 277 |
cl::value_desc("bool"), |
|---|
| 278 |
cl::location(global.params.useArrayBounds), |
|---|
| 279 |
cl::init(true)); |
|---|
| 280 |
|
|---|
| 281 |
static cl::opt<bool, true, FlagParser> invariants("invariants", |
|---|
| 282 |
cl::desc("(*) Enable invariants"), |
|---|
| 283 |
cl::location(global.params.useInvariants), |
|---|
| 284 |
cl::init(true)); |
|---|
| 285 |
|
|---|
| 286 |
static cl::opt<bool, true, FlagParser> preconditions("preconditions", |
|---|
| 287 |
cl::desc("(*) Enable function preconditions"), |
|---|
| 288 |
cl::location(global.params.useIn), |
|---|
| 289 |
cl::init(true)); |
|---|
| 290 |
|
|---|
| 291 |
static cl::opt<bool, true, FlagParser> postconditions("postconditions", |
|---|
| 292 |
cl::desc("(*) Enable function postconditions"), |
|---|
| 293 |
cl::location(global.params.useOut), |
|---|
| 294 |
cl::init(true)); |
|---|
| 295 |
|
|---|
| 296 |
|
|---|
| 297 |
static MultiSetter ContractsSetter(false, |
|---|
| 298 |
&global.params.useIn, &global.params.useOut, NULL); |
|---|
| 299 |
static cl::opt<MultiSetter, true, FlagParser> contracts("contracts", |
|---|
| 300 |
cl::desc("(*) Enable function pre- and post-conditions"), |
|---|
| 301 |
cl::location(ContractsSetter)); |
|---|
| 302 |
|
|---|
| 303 |
static MultiSetter ReleaseSetter(true, &global.params.useAssert, |
|---|
| 304 |
&global.params.useArrayBounds, &global.params.useInvariants, |
|---|
| 305 |
&global.params.useOut, &global.params.useIn, NULL); |
|---|
| 306 |
static cl::opt<MultiSetter, true, cl::parser<bool> > release("release", |
|---|
| 307 |
cl::desc("Disables asserts, invariants, contracts and boundscheck"), |
|---|
| 308 |
cl::location(ReleaseSetter), |
|---|
| 309 |
cl::ValueDisallowed); |
|---|
| 310 |
|
|---|
| 311 |
|
|---|
| 312 |
cl::opt<bool> singleObj("singleobj", |
|---|
| 313 |
cl::desc("Create only a single output object file"), |
|---|
| 314 |
cl::ZeroOrMore); |
|---|
| 315 |
|
|---|
| 316 |
cl::opt<bool> linkonceTemplates("linkonce-templates", |
|---|
| 317 |
cl::desc("Use linkonce_odr linkage for template symbols instead of weak_odr"), |
|---|
| 318 |
cl::ZeroOrMore); |
|---|
| 319 |
|
|---|
| 320 |
static cl::extrahelp footer("\n" |
|---|
| 321 |
"-d-debug can also be specified without options, in which case it enables all\n" |
|---|
| 322 |
"debug checks (i.e. (asserts, boundchecks, contracts and invariants) as well\n" |
|---|
| 323 |
"as acting as -d-debug=1\n\n" |
|---|
| 324 |
"Options marked with (*) also have a -disable-FOO variant with inverted\n" |
|---|
| 325 |
"meaning.\n"); |
|---|
| 326 |
|
|---|
| 327 |
} // namespace opts |
|---|