{"id":10545,"date":"2016-10-05T11:00:25","date_gmt":"2016-10-05T18:00:25","guid":{"rendered":"https:\/\/blogs.msdn.microsoft.com\/vcblog\/?p=10545"},"modified":"2019-02-18T18:04:41","modified_gmt":"2019-02-18T18:04:41","slug":"c-compiler-diagnostics-improvements-in-vs-15-rc","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/cppblog\/c-compiler-diagnostics-improvements-in-vs-15-rc\/","title":{"rendered":"C++ compiler diagnostics improvements in VS \u201c15\u201d Preview 5"},"content":{"rendered":"<p><em>This post written by Andrew Marino and Andrew Pardoe<\/em><\/p>\n<p>Visual C++ in <a href=\"https:\/\/devblogs.microsoft.com\/visualstudio\/2016\/10\/05\/announcing-visual-studio-15-preview-5\/\">VS \u201c15\u201d Preview 5<\/a> now allows you to see where errors are in a line of code\u2014the column number\u2014as opposed to just showing the line number. As C++ has grown it\u2019s increasingly useful to have a little more help finding your errors.<\/p>\n<p>Consider this somewhat contrived example:<\/p>\n<pre class=\"prettyprint\">\nint f(int, int);\n \nint main() {\n    return f(f(f(1, 2), f(3, 4), 5), f(6, 7));\n}\n<\/pre>\n<p>Traditionally Visual C++ would just tell you <code>t.cpp(6): 'f': function does not take 3 arguments<\/code>. With five different calls to <code>f<\/code> on one line, it\u2019s hard to figure out where your error is.<\/p>\n<p>Providing column numbers helps greatly: <code>t.cpp(5,<strong>32<\/strong>): error C2660: 'f': function does not take 3 arguments<\/code>. Now at least the compiler has identified which call to <code>f<\/code> is incorrect.<\/p>\n<p>But you can do more! You can now show the source context with the column information:<\/p>\n<pre>t.cpp(4,32): error C2660: 'f': function does not take 3 arguments\n     return f(f(f(1, 2), f(3, 4), 5), f(6, 7));\n                                   ^\n<\/pre>\n<p>In this mode, the compiler doesn\u2019t just tell you the column, it also points out the error with a caret.<\/p>\n<h3>Controlling diagnostics output<\/h3>\n<p>You can control the diagnostics format with a new compiler flag, <code>\/diagnostics:<\/code>. There are currently three arguments accepted: <code>classic<\/code>, <code>column<\/code>, and <code>caret<\/code>.<\/p>\n<ul>\n<li><code>classic<\/code> is the default, showing only the line number. We didn\u2019t change the default because it\u2019s often not a human reading the compiler\u2019s output. Frequently a build system or some other program will be reading the output. In this scenario you want the output to be simple and easily parsed.<\/li>\n<li><code>column<\/code> provides the next level of information: the column where the error was encountered.<\/li>\n<li><code>caret<\/code> provides the richest level of information: the context of where the parser found the error and a caret (^) indicating where in the code the error was found.<\/li>\n<\/ul>\n<h3>Customizing output in Visual Studio<\/h3>\n<p>Controlling the diagnostic output in Visual Studio is as easy as selecting the level under C\/C++ -&gt; General options:<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/9\/2019\/02\/diag_props.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/9\/2019\/02\/diag_props-300x167.png\" alt=\"Project properties page\" width=\"300\" height=\"167\" class=\"aligncenter size-large wp-image-10595\" \/><\/a><\/p>\n<p>If you select either <code>column<\/code> or <code>caret<\/code>, clicking on the error in the error windows will bring the cursor to the column where the error was encountered. For example, the cursor is on the closing parentheses of the call to <code>f<\/code> that erroneously includes three arguments. Parentheses highlighting (in light grey) shows the scope of the function arguments.<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/9\/2019\/02\/diag_error.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/9\/2019\/02\/diag_error-300x163.png\" alt=\"Diagnostics message in VS\" width=\"300\" height=\"163\" class=\"aligncenter size-medium wp-image-10585\" \/><\/a><\/p>\n<p>At the bottom of this screen you can see the \u201cCol\u201d column. This is off by default in the errors window. Right-clicking on the column headers brings up a dialog where you can select what columns are shown. Selecting the &#8220;Col&#8221; column allows you to see the column number.<\/p>\n<h3>Deleted special member function errors<\/h3>\n<p>We haven\u2019t just improved diagnostics formatting\u2014we\u2019re making our diagnostics clearer and more helpful across the board. We\u2019ve made improvements in areas such as static asserts, <code>constexpr<\/code>, and special member functions.<\/p>\n<p>Here\u2019s an example where code references a deleted special member function. The compiler has generated a default constructor as a special member function. But because the developer supplied an explicit constructor, <code>A(int)<\/code>, the compiler deleted the default constructor. Instantiating a variable with the type of the union that contains <code>A<\/code> will result in an error to find the default constructor.<\/p>\n<pre class=\"prettyprint\">\nstruct A\n{\n    A(int); \/\/ non-trivial constructor\n};\n\nstruct B {}; \/\/ trivial constructor\n\nunion variant\n{\n    A a;\n    B b;\n};\n\nint main()\n{\n    variant var;\n}\n<\/pre>\n<p>Previously the compiler would tell you the nature of the error:<\/p>\n<pre>source.cpp(16): error C2280: 'variant::variant(void)': attempting to reference a deleted function\nsource.cpp(12): note: compiler has generated 'variant::variant' here\n<\/pre>\n<p>Now, it additionally tells you why the function was deleted and points you back at the source of the error:<\/p>\n<pre>source.cpp(16,1): error C2280: 'variant::variant(void)': attempting to reference a deleted function\nsource.cpp(12): note: compiler has generated 'variant::variant' here\nsource.cpp(12,1): note: 'variant::variant(void)': function was implicitly deleted because a data member 'variant::a' has either no appropriate default constructor or overload resolution was ambiguous\nsource.cpp(10): note: see declaration of 'variant::a'\n<\/pre>\n<h3>Looking ahead<\/h3>\n<p>There are many improvements we can make to our compiler diagnostics going forward. The perfect diagnostic would tell you exactly where your error is and how to fix it: we have a long way to go before we get to that point! But we\u2019re committed to making improvements in the accuracy and completeness of our compiler diagnostics.<\/p>\n<p>You may occasionally notice that the column information in a diagnostic is incorrect. This can happen because the code contains multiple-byte characters or because of a bug in the compiler\u2019s parser. Because we\u2019ve never displayed the column number there are a few places where we\u2019ve recorded it incorrectly and haven\u2019t yet found the error. Please let us know if you find a code sample where the diagnostic column information is incorrect!<\/p>\n<p>There area also places where the compiler just won&#8217;t emit a column number, even though you&#8217;ve asked for columns. There are a couple of examples in the diagnostics above:<\/p>\n<pre>source.cpp(12): note: compiler has generated 'variant::variant' here\n...\nsource.cpp(10): note: see declaration of 'variant::a'\n<\/pre>\n<p>This happens because we don&#8217;t have column number information in all of our diagnostics. We&#8217;re working on expanding the coverage.<\/p>\n<p>We know that we\u2019ve got a long way to go before our diagnostics rival those of other popular C++ compilers. A lot of the 30+ year legacy of the Visual C++ compiler shows in our diagnostics quality. But this is a first step, and we\u2019re committed to continuing the improvements.<\/p>\n<h3>Send us your feedback!<\/h3>\n<p>As always, we welcome your feedback. For problems, let us know via the Report a Problem option, either from the installer or the Visual Studio IDE itself. For suggestions, let us know through <a href=\"https:\/\/visualstudio.uservoice.com\/forums\/121579-visual-studio-2015\/category\/30937-languages-c\">UserVoice<\/a>. And you can always reach us through e-mail at <a href=\"mailto:visualcpp@microsoft.com\">visualcpp@microsoft.com<\/a>.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>This post written by Andrew Marino and Andrew Pardoe Visual C++ in VS \u201c15\u201d Preview 5 now allows you to see where errors are in a line of code\u2014the column number\u2014as opposed to just showing the line number. As C++ has grown it\u2019s increasingly useful to have a little more help finding your errors. Consider [&hellip;]<\/p>\n","protected":false},"author":312,"featured_media":35994,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[270],"tags":[140,194],"class_list":["post-10545","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-announcement","tag-c","tag-diagnostics"],"acf":[],"blog_post_summary":"<p>This post written by Andrew Marino and Andrew Pardoe Visual C++ in VS \u201c15\u201d Preview 5 now allows you to see where errors are in a line of code\u2014the column number\u2014as opposed to just showing the line number. As C++ has grown it\u2019s increasingly useful to have a little more help finding your errors. Consider [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/posts\/10545","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/users\/312"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/comments?post=10545"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/posts\/10545\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/media\/35994"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/media?parent=10545"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/categories?post=10545"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/tags?post=10545"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}