Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can C# code be conditional on the compiler (or language) version? [closed]

I should like to know if arbitrary C# code can be made conditional on the compiler version. In particular, I should like to suppress Code Analysis warnings in the MSVS 2010 C# compiler that I know are not given by the 2013 compiler; I want to do this case by case, thus presumably in the source code.

Related questions

  • Predefined macros for method names
    • About predefined macros for a different purpose
  • How can compilation of C# code be made to require a given language or compiler version?
    • About making a compilation fail in the wrong version; answers not applicable

An example problem

While interested in this problem, I really want a general answer

MSVS 2010 gives a CA2204 (“Correct the spelling…”) warning about a class name in a string literal, while 2013 lets me eliminate this with the <Compound> element in the Custom Dictionary. The 2010 documentation suggests it only supports the elements <Dictionary> — <Words> — <Recognized> — <Word> (but it seems to have no problem using a dictionary including <Compound>).

I programme and test partly in MSVS 2013 (where various checks are better) and partly in 2010 (which is on our best test server). I have project definitions for both compilers. Ideally, I want 2010 to detect problems promptly rather than waiting till I compile with 2013, so I would like to suppress as little as possible, rather than a blanket suppression of CA2204 in the project.

I therefore thought of including a [CodeAnalysis.SuppressMessage("Microsoft.Naming", "CA2204…"…] attribute conditional on something like #if !MSVS2013, but it appears no such feature tests are feasible.

Possible solutions

In decreasing order of satisfactoriness I have considered the following, and would be interested to hear what others think works best:

  • (Something simple and reliable I haven’t spotted) That is what I am hoping for!
  • Suppress CA2204 in the MSVS projects. Easy but sweeping.
  • Manually define the macro MSVS2013 in MSVS projects for any compiler of at least that level and suppress as above. A bit awkward, but workable.
  • Automatically derive macros in MSVS projects, perhaps using Microsoft.Build.Tasks.Csc.LangVersion as alluded to in this answer. Sounds powerful but tricky to set up, have not investigated further.
  • Update our test server to MSVS 2013. May be wise if acceptable – but does not answer this question!
  • No go, I think:
    • A sub-class class SuppressMSVS2010MessageAttribute : SuppressMessageAttribute in 2010 which is a dummy in 2013. [SuppressMessage] is sealed!
    • Use of conditional attributes (Language Specification 3.0 §17.4.2.2) Being conditional is a property of the attribute class, not of the attribute instance! I have not followed this up, as I think it doesn’t help.
like image 967
PJTraill Avatar asked Nov 02 '25 01:11

PJTraill


1 Answers

Can C# code be conditional on the compiler (or language) version?

Sure. If you manually define a symbol according to the version of the compiler you're using. Otherwise, no.

From the documentation:

The C# compiler itself defines no symbols or macros that you can use in your source code; all symbol definitions must be user-defined.

I.e. "no symbols" includes there also being no pre-defined symbol that would allow you to determine the compiler version and thus conditionally control compilation.


Note: naturally, "manually define" does not preclude you authoring your own build process, in which you include a build step that inspects the csc.exe program to determine its version and then defines some symbol which you use to control compilation. This is still "manual" as far as the compiler itself is concerned, but you can certainly automate it yourself.

like image 97
Peter Duniho Avatar answered Nov 03 '25 17:11

Peter Duniho



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!