1997 lines · html
1<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"2 "http://www.w3.org/TR/html4/strict.dtd">3<html>4<head>5 <title>List of potential checkers</title>6 <link type="text/css" rel="stylesheet" href="content.css">7 <link type="text/css" rel="stylesheet" href="menu.css">8 <script type="text/javascript" src="scripts/expandcollapse.js"></script>9 <script type="text/javascript" src="scripts/menu.js"></script>10</head>11<body onload="initExpandCollapse()">12 13<div id="page">14 15<!-- menu -->16<!--#include virtual="menu.html.incl"-->17<!-- page content -->18<div id="content">19<h1>List of potential checkers</h1>20 21<p>This page contains a list of potential checkers to implement in the static analyzer. If you are interested in contributing to the analyzer's development, this is a good resource to help you get started. The specific names of the checkers are subject to review, and are provided here as suggestions.</p>22 23<!-- ========================= allocation/deallocation ======================= -->24<h3>memory</h3>25<table class="checkers">26<col class="namedescr"><col class="example"><col class="progress">27<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>28 29<tr><td><div class="namedescr expandable"><span class="name">30memory.LeakEvalOrder</span><span class="lang">31(C, C++)</span><div class="descr">32Potential memory leaks caused by an undefined argument evaluation order.33<p>Source: <a href="https://www.boost.org/doc/libs/1_49_0/libs/smart_ptr/shared_ptr.htm#BestPractices">34boost docs: shared_ptr</a>.</p></div></div></td>35<td><div class="exampleContainer expandable">36<div class="example"><pre>37void f(int, int);38int g(void *);39int h() __attribute__((noreturn));40 41void test() {42 // It is possible that 'malloc(1)' is called first,43 // then 'h()', that is (or calls) noreturn and eventually44 // 'g()' is never called.45 f(g(malloc(1)), h()); // warn: 'g()' may never be called.46}47</pre></div>48<div class="example"><pre>49void f(int, int);50int g(int *);51int h() { throw 1; };52 53void test() {54 // It is possible that 'new int' is called first,55 // then 'h()', that throws an exception and eventually56 // 'g()' is never called.57 f(g(new int), h()); // warn: 'g()' may never be called.58}59</pre></div></div></td>60<td class="aligned"></td></tr>61 62 63<tr><td><div class="namedescr expandable"><span class="name">64memory.DstBufferTooSmall</span><span class="lang">65(C, C++)</span><div class="descr">66Destination buffer passed to memory function is too small.67<br>Note: <span class="name">security.insecureAPI.strcpy</span> currently warns68on usage of <code>strcpy</code> and suggests to replace it.69<br>Note: <span class="name">alpha.unix.CStringChecker</span> contains some similar checks.70<p>Source: <a href="https://cwe.mitre.org/data/definitions/120.html">CWE-120</a>.</p></div></div></td>71<td><div class="exampleContainer expandable">72<div class="example"><pre>73void test() {74 const char* s1 = "abc";75 char *s2 = new char;76 strcpy(s2, s1); // warn77}78</pre></div>79<div class="example"><pre>80void test() {81 int* p1 = new int[3];82 int* p2 = new int;83 memcpy(p2, p1, 3); // warn84}85</pre></div></div></td>86<td class="aligned"></td></tr>87 88 89<tr><td><div class="namedescr expandable"><span class="name">90memory.NegativeArraySize</span><span class="lang">91(C, C++)</span><div class="descr">92'n' is used to specify the buffer size may be negative.93<p>Source: <a href="https://cwe.mitre.org/data/definitions/20.html">CWE-20,94Example 2</a>.</p></div></div></td>95<td><div class="exampleContainer expandable">96<div class="example"><pre>97void test() {98 int *p;99 int n1 = -1;100 p = new int[n1]; // warn101}102</pre></div></div></td>103<td class="aligned"></td></tr>104 105<tr><td><div class="namedescr expandable"><span class="name">106memory.ZeroAlloc</span><span class="lang">107(C, C++)</span><div class="descr">108Allocation of zero bytes.109<br>Note: an enhancement to <span class="name">unix.Malloc</span>.110<br>Note: <span class="name">unix.API</span> perform C-checks for zero111allocation. This should be moved to <span class="name">unix.Malloc</span>.112<p>Source: C++03 3.7.3.1p2; C++11 3.7.4.1p2.</p></div></div></td>113<td><div class="exampleContainer expandable">114<div class="example"><pre>115#include <stdlib.h>116 117void test() {118 int *p = malloc(0); // warn119 free(p);120}121</pre></div>122<div class="example"><pre>123void test() {124 int *p = new int[0]; // warn125 delete[] p;126}127</pre></div></div></td>128<td class="aligned"><a href="https://reviews.llvm.org/D6178">129D6178</a></td></tr>130 131</table>132 133<!-- ======================= constructors/destructors ====================== -->134<h3>constructors/destructors</h3>135<table class="checkers">136<col class="namedescr"><col class="example"><col class="progress">137<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>138 139<tr><td><div class="namedescr expandable"><span class="name">140ctordtor.ExptInsideDtor</span><span class="lang">141(C++)</span><div class="descr">142It is dangerous to let an exception leave a destructor.143Using <code>try..catch</code> solves the problem.144<p>Source: Scott Meyers "More Effective C++", item 11: Prevent exceptions from145leaving destructors.</p></div></div></td>146<td><div class="exampleContainer expandable">147<div class="example"><pre>148class A {149 A() {}150 ~A() { throw 1; } // warn151};152</pre></div>153<div class="example"><pre>154void f() throw(int);155 156class A {157 A() {}158 ~A() { f(); } // warn159};160</pre></div></div></td>161<td class="aligned"></td></tr>162 163 164<tr><td><div class="namedescr expandable"><span class="name">165ctordtor.PlacementSelfCopy</span><span class="lang">166(C++11)</span><div class="descr">167For a placement copy or move, it is almost certainly an error if the168constructed object is also the object being copied from.</div></div></td>169<td><div class="exampleContainer expandable">170<div class="example"><pre>171class A {};172 173void test(A *dst, A *src) {174 ::new (dst) A(*dst); // warn (should be 'src')175}176</pre></div></div></td>177<td class="aligned"><!--rdar://problem/13688366--></td></tr>178 179</table>180 181<!-- ============================== exceptions ============================= -->182<h3>exceptions</h3>183<table class="checkers">184<col class="namedescr"><col class="example"><col class="progress">185<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>186 187<tr><td><div class="namedescr expandable"><span class="name">188exceptions.ThrowSpecButNotThrow</span><span class="lang">189(C++)</span><div class="descr">190Function declaration has a <code>throw(<i>type</i>)</code> specifier but the191function do not throw exceptions.</div></div></td>192<td><div class="exampleContainer expandable">193<div class="example"><pre>194void test() throw(int) {195} // warn196</pre></div></div></td>197<td class="aligned"></td></tr>198 199 200<tr><td><div class="namedescr expandable"><span class="name">201exceptions.NoThrowSpecButThrows</span><span class="lang">202(C++)</span><div class="descr">203An exception is throw from a function having a <code>throw()</code>204specifier.</div></div></td>205<td><div class="exampleContainer expandable">206<div class="example"><pre>207void test() throw() {208 throw(1); // warn209}210</pre></div></div></td>211<td class="aligned"></td></tr>212 213 214<tr><td><div class="namedescr expandable"><span class="name">215exceptions.ThrownTypeDiffersSpec</span><span class="lang">216(C++)</span><div class="descr">217The type of a thrown exception differs from those specified in218a <code>throw(<i>type</i>)</code> specifier.</div></div></td>219<td><div class="exampleContainer expandable">220<div class="example"><pre>221struct S{};222 223void test() throw(int) {224 S s;225 throw (s); // warn226}227</pre></div></div></td>228<td class="aligned"></td></tr>229 230</table>231 232<!-- ========================= smart pointers ============================== -->233<h3>smart pointers</h3>234<table class="checkers">235<col class="namedescr"><col class="example"><col class="progress">236<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>237 238<tr><td><div class="namedescr expandable"><span class="name">239smartptr.SmartPtrInit</span><span class="lang">240(C++)</span><div class="descr">241C++03: <code>auto_ptr</code> should store a pointer to an object obtained via242new as allocated memory will be cleaned using <code>delete</code>.<br>243C++11: one should use <code>unique_ptr<<i>type</i>[]></code> to keep a244pointer to memory allocated by <code>new[]</code>.<br>245C++11: to keep a pointer to memory allocated by <code>new[]</code> in246a <code>shared_ptr</code> one should use a custom deleter that calls <code>247delete[].</code>.248<p>Source: C++03 20.4.5p1; C++11 <code>auto_ptr</code> is deprecated (D.10).</p></div></div></td>249<td><div class="exampleContainer expandable">250<div class="example"><pre>251#include <stdlib.h>252#include <memory>253 254void test() {255 std::auto_ptr<int> p1(new int); // Ok256 std::auto_ptr<int> p2(new int[3]); // warn257}258</pre></div>259<div class="example"><pre>260#include <stdlib.h>261#include <memory>262 263void test() {264 std::auto_ptr<int> p((int *)malloc(sizeof(int))); // warn265}266</pre></div></div></td>267<td class="aligned"></td></tr>268 269</table>270 271<!-- ============================== dead code ============================== -->272<h3>dead code</h3>273<table class="checkers">274<col class="namedescr"><col class="example"><col class="progress">275<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>276 277<tr><td><div class="namedescr expandable"><span class="name">278deadcode.UnmodifiedVariable</span><span class="lang">279(C, C++)</span><div class="descr">280A variable is never modified but was not declared const and is not a281reference.<br><br><i>(opt-in checker)</i></div></div></td>282<td><div class="exampleContainer expandable">283<div class="example"><pre>284extern int computeDelta();285 286int test(bool cond) {287 int i = 0;288 if (cond) {289 const int delta = computeDelta();290 // warn: forgot to modify 'i'291 }292 return i;293}294</pre></div></div></td>295<td class="aligned"><a href="https://bugs.llvm.org/show_bug.cgi?id=16890">PR16890</a></td></tr>296 297<tr><td><div class="namedescr expandable"><span class="name">298deadcode.IdempotentOperations</span><span class="lang">299(C)</span><div class="descr">300Warn about idempotent operations.</div></div></td>301<td><div class="exampleContainer expandable">302<div class="example"><pre>303void test() {304 int x = 7;305 x = x; // warn: value is always the same306}307</pre></div>308<div class="example"><pre>309void test() {310 int x = 7;311 x /= x; // warn: value is always 1312}313</pre></div>314<div class="example"><pre>315void test() {316 int x = 7, one = 1;317 x *= one; // warn: right op is always 1318}319</pre></div>320<div class="example"><pre>321void test() {322 int x = 7, zero = 0;323 x = x - zero;324 // warn: the right operand to '-' is always 0325}326</pre></div></div></td>327<td class="aligned">removed from alpha.deadcode.* at328<a href="https://reviews.llvm.org/rL198476">r198476</a></td></tr>329 330</table>331 332<!-- ================================ POSIX ================================ -->333<h3>POSIX</h3>334<table class="checkers">335<col class="namedescr"><col class="example"><col class="progress">336<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>337 338<tr><td><div class="namedescr expandable"><span class="name">339posix.Errno</span><span class="lang">340(C)</span><div class="descr">341Record that <code>errno</code> is non-zero when certain functions342fail.</div></div></td>343<td><div class="exampleContainer expandable">344<div class="example"><pre>345#include <stdlib.h>346 347int readWrapper(int fd, int *count) {348 int lcount = read(fd, globalBuf, sizeof(globalBuf));349 if (lcount < 0)350 return errno;351 *count = lcount;352 return 0;353}354 355void use(int fd) {356 int count;357 if (!readWrapper(fd, &count))358 print("%d", count); // should not warn359}360</pre></div></div></td>361<td class="aligned"><a href="https://bugs.llvm.org/show_bug.cgi?id=18701">PR18701</a></td></tr>362 363</table>364 365<!-- ========================= undefined behavior ========================== -->366<h3>undefined behavior</h3>367<table class="checkers">368<col class="namedescr"><col class="example"><col class="progress">369<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>370 371<tr><td><div class="namedescr expandable"><span class="name">372undefbehavior.ExitInDtor</span><span class="lang">373(C++)</span><div class="descr">374Undefined behavior: <code>std::exit()</code> is called to end the program during375the destruction of an object with static storage duration.376<p>Source: C++11 3.6.1p4.</p></div></div></td>377<td><div class="exampleContainer expandable">378<div class="example"><pre>379#include <cstdlib>380 381class A {382public:383 ~A() {384 std::exit(1); // warn385 }386};387</pre></div></div></td>388<td class="aligned"></td></tr>389 390 391<tr><td><div class="namedescr expandable"><span class="name">392undefbehavior.LocalStaticDestroyed</span><span class="lang">393(C++)</span><div class="descr">394Undefined behavior: function containing a definition of static local object is395called during the destruction of an object with static storage duration so that396flow of control passes through the definition of the previously destroyed397static local object.398<p>Source: C++11 3.6.3p2.</p></div></div></td>399<td><div class="exampleContainer expandable">400<div class="example"><pre>401void f();402 403class A {404public:405 ~A() {406 f(); // warn407 }408};409 410class B {};411 412A a;413 414void f() {415 static B b;416}417</pre></div></div></td>418<td class="aligned"></td></tr>419 420 421<tr><td><div class="namedescr expandable"><span class="name">422undefbehavior.ZeroAllocDereference</span><span class="lang">423(C, C++)</span><div class="descr">424The effect of dereferencing a pointer returned as a request for zero size is425undefined.<br>426Note: possibly an enhancement to <span class="name">427unix.Malloc</span>.428<p>Source: C++03 3.7.3.1p2; C++11 3.7.4.1p2.</p></div></div></td>429<td><div class="exampleContainer expandable">430<div class="example"><pre>431#include <stdlib.h>432 433void test() {434 int *p = (int *)malloc(0);435 *p = 1; // warn436 free(p);437}438</pre></div>439<div class="example"><pre>440void f(int);441 442void test() {443 int *p = new int[0];444 f(*p); // warn445 delete[] p;446}447</pre></div></div></td>448<td class="aligned"><a href="https://reviews.llvm.org/D8273">D8273</a></td></tr>449 450 451<tr><td><div class="namedescr expandable"><span class="name">452undefbehavior.DeadReferenced</span><span class="lang">453(C++)</span><div class="descr">454Undefined behavior: the following usage of the pointer to the object whose455lifetime has ended can result in undefined behavior:<br>456The object will be or was of a class type with a non-trivial destructor and457<ul><li>the pointer is used as the operand of a delete-expression</li></ul>458The object will be or was of a non-POD class type (C++11: any class type) and459<ul><li>the pointer is used to access a non-static data member or call a460non-static member function of the object</li>461<li>the pointer is implicitly converted to a pointer to a base class462type</li>463<li>the pointer is used as the operand of a <code>static_cast</code> (except464when the conversion is to <code>void*</code>, or to <code>void*</code> and465subsequently to <code>char*</code>, or <code>unsigned char*</code>)</li>466<li>the pointer is used as the operand of a <code>dynamic_cast</code></li></ul>467<p>Source: C++03 3.8p5, p7; C++11 3.8p5, p7.</p></div></div></td>468<td><div class="exampleContainer expandable">469<div class="example"><pre>470#include <new>471 472class A {473public:474 ~A();475};476 477class B : public A {};478 479void test() {480 A *a = new A;481 new(a) B;482 delete a; // warn483}484</pre></div>485<div class="example"><pre>486#include <new>487 488class A {489public:490 ~A();491};492 493class B {};494 495void test() {496 A *a = new A;497 new(a) B;498 a->~A();499}500</pre></div>501<div class="example"><pre>502#include <new>503 504class A {505public:506 ~A();507};508 509class B : public A {};510 511class C {};512 513void f(A*);514 515void test() {516 B *b = new B;517 new(b) C;518 f(b); // warn519}520</pre></div>521<div class="example"><pre>522#include <new>523 524class A {525public:526 ~A();527};528 529class B : public A {};530 531class C {};532 533A* test() {534 B *b = new B;535 new(b) C;536 return static_cast<A*>(b); // warn537}538</pre></div>539<div class="example"><pre>540#include <new>541 542class A {543public:544 ~A();545};546 547class B : public A {};548 549class C {};550 551A* test() {552 B *b = new B;553 new(b) C;554 return dynamic_cast<A*>(b); // warn555}556</pre></div></div></td>557<td class="aligned"></td></tr>558 559 560<tr><td><div class="namedescr expandable"><span class="name">561undefbehavior.ObjLocChanges</span><span class="lang">562(C++)</span><div class="descr">563Undefined behavior: the program must ensure that an object occupies the same564storage location when the implicit or explicit destructor call takes place.565<p>Source: C++11 3.8p8.</p></div></div></td>566<td><div class="exampleContainer expandable">567<div class="example"><pre>568#include <new>569 570class A {};571 572class B {573public:574 ~B();575};576 577void test() {578 B b;579 new (&b) A;580} // warn581</pre></div>582<div class="example"><pre>583#include <new>584 585class A {};586 587class B {588public:589 ~B();590};591 592void test() {593 B *b = new B;594 new (b) A;595 delete b; // warn596}597</pre></div></div></td>598<td class="aligned"></td></tr>599 600 601<tr><td><div class="namedescr expandable"><span class="name">602undefbehavior.ExprEvalOrderUndef</span><span class="lang">603(C, C++03)</span><div class="descr">604Undefined behavior: a scalar object shall have its stored value modified at605most once by the evaluation of an expression.<br>606Note: most cases are currently handled by the Clang core (search for 'multiple607unsequenced modifications' warning in Clang tests).608<p>Source: C++03 5p4.</p></div></div></td>609<td><div class="exampleContainer expandable">610<div class="example"><pre>611int test () {612 int i = 0;613 i = ++i + 1; // warn614 return i;615}616</pre></div></div></td>617<td class="aligned"></td></tr>618 619 620<tr><td><div class="namedescr expandable"><span class="name">621undefbehavior.StaticInitReentered</span><span class="lang">622(C++)</span><div class="descr">623Undefined behavior: static declaration is re-entered while the object is being624initialized.625<p>Source: C++11 6.7p4.</p></div></div></td>626<td><div class="exampleContainer expandable">627<div class="example"><pre>628int test(int i) {629 static int s = test(2 * i); // warn630 return i + 1;631}632</pre></div></div></td>633<td class="aligned"></td></tr>634 635 636<tr><td><div class="namedescr expandable"><span class="name">637undefbehavior.ConstModified</span><span class="lang">638(C, C++)</span><div class="descr">639Undefined behavior: const object is being modified.640<p>Source: C++03 7.1.5.1p4, C++11 7.1.6.1p4.</p></div></div></td>641<td><div class="exampleContainer expandable">642<div class="example"><pre>643void test() {644 const int *cp = new const int (0);645 int *p = const_cast<int *>(cp);646 *p = 1; // warn647 delete p;648}649</pre></div>650<div class="example"><pre>651class C {652public :653 int i;654 C();655};656 657void test() {658 const C cb;659 660 C* cp = const_cast<C *>(&cb);661 cp->i = 1; // warn662}663</pre></div></div></td>664<td class="aligned"></td></tr>665 666 667<tr><td><div class="namedescr expandable"><span class="name">668undefbehavior.DeadDestructed</span><span class="lang">669(C++)</span><div class="descr">670Undefined behavior: the destructor is invoked for an object whose lifetime671has ended.672<p>Source: C++11 12.4p14.</p></div></div></td>673<td><div class="exampleContainer expandable">674<div class="example"><pre>675class A {676public:677 void f();678 A();679 ~A();680};681 682void test() {683 A a;684 a.~A();685} // warn686</pre></div></div></td>687<td class="aligned"></td></tr>688 689 690<tr><td><div class="namedescr expandable"><span class="name">691undefbehavior.MethodCallBeforeBaseInit</span><span class="lang">692(C++)</span><div class="descr">693Undefined behavior: calls member function but base not yet initialized.694<p>Source: C++03 12.6.2p8; C++11 12.6.2p13.</p></div></div></td>695<td><div class="exampleContainer expandable">696<div class="example"><pre>697class A {698public :699 A(int);700};701 702class B : public A {703public :704 int f();705 B() : A(f()) {} // warn706};707</pre></div></div></td>708<td class="aligned"></td></tr>709 710 711<tr><td><div class="namedescr expandable"><span class="name">712undefbehavior.MemberOrBaseRefBeforeCtor</span><span class="lang">713(C++)</span><div class="descr">714C++ Undefined behavior: non-static member or base class of non-POD class type715is referred before constructor begins execution.<br>716C++11 Undefined behavior: non-static member or base class of a class with a717non-trivial constructor is referred before constructor begins execution.718<p>Source: C++03 12.7p1; C++11 12.7p1.</p></div></div></td>719<td><div class="exampleContainer expandable">720<div class="example"><pre>721struct non_POD {722 int i;723 non_POD();724};725 726extern non_POD non_pod;727 728int *p = &non_pod.i; // warn729</pre></div>730<div class="example"><pre>731struct POD {732 int i;733};734 735struct non_POD : public POD {736 POD pod;737};738 739extern non_POD non_pod;740 741int *p = &non_pod.pod.i; // warn742</pre></div>743<div class="example"><pre>744struct POD {745 int i;746};747 748struct non_POD : public POD {};749 750extern non_POD non_pod;751 752POD *p = &non_pod; // warn753</pre></div>754<div class="example"><pre>755struct non_POD {756 int i;757 non_POD();758};759 760struct S {761 int *k;762 non_POD non_pod;763 S() : k(&non_pod.i) {} // warn764};765</pre></div></div></td>766<td class="aligned"></td></tr>767 768 769<tr><td><div class="namedescr expandable"><span class="name">770undefbehavior.MemberRefAfterDtor</span><span class="lang">771(C++)</span><div class="descr">772C++03: Undefined behavior: non-static member of non-POD class type is referred773after destructor ends execution.<br>774C++11: Undefined behavior: non-static member of a class with a non-trivial775destructor is referred after destructor ends execution.776<p>Source: C++03 12.7p1; C++11 12.7p1.</p></div></div></td>777<td><div class="exampleContainer expandable">778<div class="example"><pre>779class C {780public:781 C();782 void f();783};784 785void test() {786 C *c = new C();787 c->~C();788 c->f(); // warn789}790</pre></div></div></td>791<td class="aligned"></td></tr>792 793 794<tr><td><div class="namedescr expandable"><span class="name">795undefbehavior.CtorForeignCall</span><span class="lang">796(C++)</span><div class="descr">797Undefined behavior: call to virtual function of an object under construction798whose type is neither the constructors own class or one of its bases.799<p>Source: C++11 12.7p4.</p></div></div></td>800<td><div class="exampleContainer expandable">801<div class="example"><pre>802class A {803public:804 virtual void f() {};805};806 807class B {808public:809 B(A* a) { a->f(); } // warn810};811 812class C : public A, B {813public:814 C() : B((A*)this) {}815};816</pre></div></div></td>817<td class="aligned"></td></tr>818 819 820<tr><td><div class="namedescr expandable"><span class="name">821undefbehavior.CtorForeignTypeid</span><span class="lang">822(C++)</span><div class="descr">823Undefined behavior: the operand of <code>typeid</code> is an object under824construction whose type is neither the constructors own class or one of its825bases.826<p>Source: C++11 12.7p5.</p></div></div></td>827<td><div class="exampleContainer expandable">828<div class="example"><pre>829#include <typeinfo>830 831class A {};832 833class B {834public:835 B(A* a) {836 (void)typeid(*a); // warn837 }838};839 840class C : public A, B {841public:842 C() : B((A*)this) {}843};844</pre></div></div></td>845<td class="aligned"></td></tr>846 847 848<tr><td><div class="namedescr expandable"><span class="name">849undefbehavior.CtorForeignCast</span><span class="lang">850(C++)</span><div class="descr">851Undefined behavior: the operand of <code>dynamic_cast</code> is an object under852construction whose type is neither the constructors own class or one of its853bases.854<p>Source: C++11 12.7p6.</p></div></div></td>855<td><div class="exampleContainer expandable">856<div class="example"><pre>857#include <typeinfo>858 859class A {860public:861 virtual void f() {};862};863 864class B {865public:866 B(A* a) {867 (void)dynamic_cast<B*>(a); //warn868 }869};870 871class C : public A, B {872public:873 C() : B((A*)this) {}874};875</pre></div></div></td>876<td class="aligned"></td></tr>877 878 879<tr><td><div class="namedescr expandable"><span class="name">880undefbehavior.MemberOrBaseRefInCatch</span><span class="lang">881(C++)</span><div class="descr">882Undefined behavior: referring to any non-static member or base class of an883object in the handler for a function-try-block of a constructor or destructor884for that object results in undefined behavior.885<p>Source: C++11 15.3p10.</p></div></div></td>886<td><div class="exampleContainer expandable">887<div class="example"><pre>888void f() { throw 1; }889 890class C {891 int i;892public :893 C()894 try {895 f();896 }897 catch (...) {898 i=2; // warn899 }900};901</pre></div>902<div class="example"><pre>903void f() { throw 1; }904 905class Base {906public:907 int i;908};909 910class C: public Base {911public :912 ~C() try {913 f();914 }915 catch (...) {916 i=2; // warn917 }918};919</pre></div></div></td>920<td class="aligned"></td></tr>921 922 923<tr><td><div class="namedescr expandable"><span class="name">924undefbehavior.ReturnAtCatchEnd</span><span class="lang">925(C++)</span><div class="descr">926Undefined behavior: a function returns when control reaches the end of a927handler. This results in undefined behavior in a value-returning function.928<p>Source: C++11 15.3p10.</p></div></div></td>929<td><div class="exampleContainer expandable">930<div class="example"><pre>931void f() { throw 1; }932 933int test() try {934 f();935 return 1;936}937catch(int) {938} // warn939</pre></div></div></td>940<td class="aligned"></td></tr>941 942 943<tr><td><div class="namedescr expandable"><span class="name">944undefbehavior.AutoptrsOwnSameObj</span><span class="lang">945(C++03)</span><div class="descr">946Undefined behavior: if more than one <code>auto_ptr</code> owns the same object947at the same time the behavior of the program is undefined.948<p>Source: C++03 20.4.5p3; C++11 <code>auto_ptr</code> is deprecated949(D.10).</p></div></div></td>950<td><div class="exampleContainer expandable">951<div class="example"><pre>952#include <memory>953 954void test() {955 int *data = new int;956 std::auto_ptr<int> p(data);957 std::auto_ptr<int> q(data); // warn958}959</pre></div></div></td>960<td class="aligned"></td></tr>961 962 963<tr><td><div class="namedescr expandable"><span class="name">964undefbehavior.BasicStringOutOfBound</span><span class="lang">965(C++03)</span><div class="descr">966Undefined behavior: out-of-bound <code>basic_string</code> access/modification.967<br>Note: possibly an enhancement to <span class="name">968security.ArrayBound</span>.969<p>Source: C++03 21.3.4p1; C++11 behavior is defined970(21.4.5p2).</p></div></div></td>971<td><div class="exampleContainer expandable">972<div class="example"><pre>973#include <string>974 975void test() {976 std::basic_string<char> s;977 char c = s[10]; // warn978}979</pre></div>980<div class="example"><pre>981#include <string>982 983void test() {984 std::basic_string<char> s;985 s[10] = 0; // warn986}987</pre></div></div></td>988<td class="aligned"></td></tr>989 990 991<tr><td><div class="namedescr expandable"><span class="name">992undefbehavior.EosDereference</span><span class="lang">993(C++)</span><div class="descr">994Undefined behavior: the result of <code>operator*()</code> on an end of a995stream is undefined.996<p>Source: C++03 24.5.3p2; C++11 24.6.3p2.</p></div></div></td>997<td><div class="exampleContainer expandable">998<div class="example"><pre>999#include <vector>1000 1001int test() {1002 std::vector<int> v;1003 return *v.end(); // warn1004}1005</pre></div></div></td>1006<td class="aligned"></td></tr>1007 1008 1009<tr><td><div class="namedescr expandable"><span class="name">1010undefbehavior.QsortNonPODNonTrivial</span><span class="lang">1011(C++)</span><div class="descr">1012C++03: Undefined behavior: the objects in the array passed to qsort are of1013non-POD type.<br>1014C++11: Undefined behavior: the objects in the array passed to qsort are of1015non-trivial type.1016<p>Source: C++03 25.4p4; C++11 25.5p4.</p></div></div></td>1017<td><div class="exampleContainer expandable">1018<div class="example"><pre>1019// C++031020#include <cstdlib>1021 1022 1023struct non_POD {1024 non_POD();1025};1026 1027non_POD values[] = { non_POD(), non_POD() };1028 1029int compare(const void *a, const void *b);1030 1031void test() {1032 qsort(values, 2, sizeof(non_POD), compare); // warn1033}1034</pre></div>1035<div class="example"><pre>1036// C++111037#include <cstdlib>1038 1039struct S {};1040 1041struct trivial_non_POD : public S {1042 int i;1043};1044 1045struct non_trivial {1046 int i;1047 non_trivial();1048};1049 1050trivial_non_POD tnp[2];1051non_trivial nt[2];1052 1053int compare1(const void *a, const void *b);1054 1055int compare2(const void *a, const void *b);1056 1057void test() {1058 qsort(tnp, 2, sizeof(trivial_non_POD), compare1); // ok1059 qsort(nt, 2, sizeof(non_trivial), compare2); // warn1060}1061</pre></div></div></td>1062<td class="aligned"></td></tr>1063 1064 1065<tr><td><div class="namedescr expandable"><span class="name">1066undefbehavior.ThrowWhileCopy</span><span class="lang">1067(C++)</span><div class="descr">1068Undefined behavior: copy constructor/assignment operator can throw an exception.1069The effects are undefined if an exception is thrown.</div></div></td>1070<td><div class="exampleContainer expandable">1071<div class="example"><pre>1072class C {1073public:1074 int i, j;1075 C (const C &c) {1076 i = c.i;1077 throw 1; // warn1078 j = c.j;1079 };1080};1081</pre></div>1082<div class="example"><pre>1083class C {1084public:1085 int i, j;1086 C &operator=(const C &c) {1087 i = c.i;1088 throw 1; // warn1089 j = c.j;1090 };1091};1092</pre></div></div></td>1093<td class="aligned"></td></tr>1094 1095 1096<tr><td><div class="namedescr expandable"><span class="name">1097undefbehavior.ValarrayArgBound</span><span class="lang">1098(C++)</span><div class="descr">1099Undefined behavior: the value of the <code><i>n</i></code> argument passed1100to <code>valarray</code> constructor is greater than the number of values1101pointed to by the first argument (source).1102<p>Source: C++03 26.3.2.1p4; C++11 26.6.2.2p4.</p></div></div></td>1103<td><div class="exampleContainer expandable">1104<div class="example"><pre>1105#include <valarray>1106 1107struct S {1108 int i;1109 S(int ii) : i(ii) {};1110};1111 1112void test(void) {1113 S s[] = { S(1), S(2) };1114 std::valarray<S> v(s,3); // warn1115}1116</pre></div></div></td>1117<td class="aligned"></td></tr>1118 1119 1120<tr><td><div class="namedescr expandable"><span class="name">1121undefbehavior.ValarrayLengthDiffer</span><span class="lang">1122(C++)</span><div class="descr">1123Undefined behavior: <code>valarray</code> operands are of different length.1124<p>Source: C++03 26.3.2.2p1, 26.3.2.6p3, 26.3.3.1p3, 26.3.3.2p3;1125C++11 defined (26.6.2.3p1), 26.6.2.7p3, 26.6.3.1p3,112626.6.3.2p3.</p></div></div></td>1127<td><div class="exampleContainer expandable">1128<div class="example"><pre>1129// C++031130#include <valarray>1131 1132void test(void) {1133 std::valarray<int> a(0, 1), b(0, 2);1134 a = b; // warn1135 b.resize(1);1136 a = b; // ok1137}1138</pre></div>1139<div class="example"><pre>1140// C++03, C++111141#include <valarray>1142 1143void test(void) {1144 std::valarray<int> a(0, 1), b(0, 2);1145 a *= b; // warn1146}1147</pre></div>1148<div class="example"><pre>1149// C++03, C++111150#include <valarray>1151 1152void test(void) {1153 std::valarray<int> a(0, 1), b(0, 2);1154 a = a + b; // warn1155}1156</pre></div>1157<div class="example"><pre>1158// C++03, C++111159#include <valarray>1160 1161void test(void) {1162 std::valarray<int> a(0, 1), b(0, 2);1163 std::valarray<bool> c(false, 1);1164 c = a == b; // warn1165}1166</pre></div></div></td>1167<td class="aligned"></td></tr>1168 1169 1170<tr><td><div class="namedescr expandable"><span class="name">1171undefbehavior.ValarrayZeroLength</span><span class="lang">1172(C++)</span><div class="descr">1173Undefined behavior: calling <code>sum()</code>/<code>min()</code>/<code>1174max()</code> methods of a zero length <code>valarray<code> the behavior is1175undefined.1176<p>Source: C++03 26.3.2.7p2, p3, p4; C++11 26.6.2.8p5, p6,1177p7.</p></div></div></td>1178<td><div class="exampleContainer expandable">1179<div class="example"><pre>1180#include <valarray>1181 1182void test(void) {1183 std::valarray<int> v(0, 0);1184 v.sum(); // warn1185}1186</pre></div></div></td>1187<td class="aligned"></td></tr>1188 1189 1190<tr><td><div class="namedescr expandable"><span class="name">1191undefbehavior.ValarrayBadIndirection</span><span class="lang">1192(C++)</span><div class="descr">1193Undefined behavior: element is specified more than once in an indirection.1194<p>Source: C++03 26.3.9.2p2, 26.3.9.3p2; C++11 26.6.9.2p2,119526.6.9.3p2.</p></div></div></td>1196<td><div class="exampleContainer expandable">1197<div class="example"><pre>1198#include <valarray>1199 1200void test() {1201 // '1' is specified more then once1202 size_t addr[] = {0, 1, 1};1203 std::valarray<size_t>indirect(addr, 3);1204 std::valarray<int> a(0, 5), b(1, 3);1205 a[indirect] = b; //warn1206}1207</pre></div>1208<div class="example"><pre>1209#include <valarray>1210 1211void test() {1212 // '1' is specified more then once1213 size_t addr[] = {0, 1, 1};1214 std::valarray<size_t>indirect(addr, 3);1215 std::valarray<int> a(0, 5), b(1, 3);1216 a[indirect] *= b; //warn1217}1218</pre></div></div></td>1219<td class="aligned"></td></tr>1220 1221 1222<tr><td><div class="namedescr expandable"><span class="name">1223undefbehavior.IosBaseDestroyedBeforeInit</span><span class="lang">1224(C++)</span><div class="descr">1225Undefined behavior: <code>ios_base</code> object is destroyed before1226initialization have taken place. <code>basic_ios::init</code> should be call to1227initialize <code>ios_base</code> members.1228<p>Source: C++03 27.4.2.7p1, 27.4.4.1p2; C++11 27.5.3.7p1,122927.5.5.2p2.</p></div></div></td>1230<td><div class="exampleContainer expandable">1231<div class="example"><pre>1232#include <ios>1233 1234using namespace std;1235template <class T, class Traits = std::char_traits<T> >1236class my_stream1 : public std::basic_ios<T, Traits> {1237};1238 1239template <class T, class Traits = std::char_traits<T> >1240class my_stream2 : public std::basic_ios<T, Traits> {1241 class my_streambuf1242 : public std::basic_streambuf<T, Traits> {1243 };1244public:1245 my_stream2() {1246 this->init(new my_streambuf);1247 }1248};1249 1250void test() {1251 my_stream1<char> *p1 = new my_stream1<char>;1252 my_stream2<char> *p2 = new my_stream2<char>;1253 delete p1; // warn1254 delete p2; // ok1255}1256</pre></div></div></td>1257<td class="aligned"></td></tr>1258 1259 1260<tr><td><div class="namedescr expandable"><span class="name">1261undefbehavior.IosBaseUsedBeforeInit</span><span class="lang">1262(C++11)</span><div class="descr">1263Undefined behavior: <code>ios_base</code> object is used before initialization1264have taken place. <code>basic_ios::init</code> should be call to1265initialize <code>ios_base</code> members.1266<p>Source: C++11 27.5.3.7p1, 27.5.5.2p2.</p></div></div></td>1267<td><div class="exampleContainer expandable">1268<div class="example"><pre>1269#include <ios>1270 1271using namespace std;1272template <class T, class Traits = std::char_traits<T> >1273class my_stream1 : public std::basic_ios<T, Traits> {1274};1275 1276template <class T, class Traits = std::char_traits<T> >1277class my_stream2 : public std::basic_ios<T, Traits> {1278 class my_streambuf1279 : public std::basic_streambuf<T, Traits> {1280 };1281public:1282 my_stream2() {1283 this->init(new my_streambuf);1284 }1285};1286 1287void test() {1288 my_stream1<char> *p1 = new my_stream1<char>;1289 my_stream2<char> *p2 = new my_stream2<char>;1290 p1->narrow('a', 'b'); // warn1291 p2->narrow('a', 'b'); // ok1292}1293</pre></div></div></td>1294<td class="aligned"></td></tr>1295 1296 1297<tr><td><div class="namedescr expandable"><span class="name">1298undefbehavior.MinusOnePosType</span><span class="lang">1299(C++)</span><div class="descr">1300Undefined behavior: passing -1 to any <code>streambuf</code>/<code>1301istream</code>/<code>ostream</code> member that accepts a value of1302type <code>traits::pos_type</code> result in undefined behavior.1303<p>Source: C++03 27.4.3.2p3; C++11 27.5.4.2p3.</p></div></div></td>1304<td><div class="exampleContainer expandable">1305<div class="example"><pre>1306#include <fstream>1307 1308class my_streambuf : public std::streambuf {1309 void f() {1310 seekpos(-1); // warn1311 }1312};1313</pre></div>1314<div class="example"><pre>1315#include <fstream>1316 1317void test() {1318 std::filebuf fb;1319 std::istream in(&fb);1320 std::filebuf::off_type pos(-1);1321 in.seekg(pos); // warn1322}1323</pre></div></div></td>1324<td class="aligned"></td></tr>1325 1326</table>1327 1328<!-- ============================ different ================================ -->1329<h3>different</h3>1330<table class="checkers">1331<col class="namedescr"><col class="example"><col class="progress">1332<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr>1333</thead>1334 1335<tr><td><div class="namedescr expandable"><span class="name">1336different.SuccessiveAssign</span><span class="lang">1337(C)</span><div class="descr">1338Successive assign to a variable.</div></div></td>1339<td><div class="exampleContainer expandable">1340<div class="example"><pre>1341int test() {1342 int i;1343 i=1;1344 i=2; // warn1345 return i;1346}1347</pre></div></div></td>1348<td class="aligned"></td></tr>1349 1350 1351<tr><td><div class="namedescr expandable"><span class="name">1352different.NullDerefStmtOrder</span><span class="lang">1353(C)</span><div class="descr">1354Dereferencing of the null pointer might take place. Checking the pointer for1355null should be performed first.1356<br>Note: possibly an enhancement to <span class="name">1357core.NullDereference</span>.</div></div></td>1358<td><div class="exampleContainer expandable">1359<div class="example"><pre>1360struct S {1361 int x;1362};1363 1364struct S* f();1365 1366void test() {1367 struct S *p1 = f();1368 int x1 = p1->x; // warn1369 if (p1) {};1370 1371 struct S *p2 = f();1372 int x2 = p2->x; // ok1373}1374</pre></div></div></td>1375<td class="aligned"></td></tr>1376 1377 1378<tr><td><div class="namedescr expandable"><span class="name">1379different.NullDerefCondOrder</span><span class="lang">1380(C)</span><div class="descr">1381Dereferencing of the null pointer might take place. Checking the pointer for1382null should be performed first.1383<br>Note: possibly an enhancement to <span class="name">1384core.NullDereference</span>.</div></div></td>1385<td><div class="exampleContainer expandable">1386<div class="example"><pre>1387struct S {int i;};1388 1389struct S* f();1390 1391void test() {1392 struct S *p = f();1393 if (p->i && p) {}; // warn1394}1395</pre></div></div></td>1396<td class="aligned"></td></tr>1397 1398 1399<tr><td><div class="namedescr expandable"><span class="name">1400different.MultipleAccessors</span><span class="lang">1401(C++)</span><div class="descr">1402Identical accessor bodies. Possibly a misprint.</div></div></td>1403<td><div class="exampleContainer expandable">1404<div class="example"><pre>1405class A {1406 int i;1407 int j;1408public:1409 int getI() { return i; }1410 int getJ() { return i; } // warn1411};1412</pre></div>1413<div class="example"><pre>1414class A {1415 int i;1416 int j;1417public:1418 void setI(int& ii) { i = ii; }1419 void setJ(int& jj) { i = jj; } // warn1420};1421</pre></div></div></td>1422<td class="aligned"></td></tr>1423 1424 1425<tr><td><div class="namedescr expandable"><span class="name">1426different.AccessorsForPublic</span><span class="lang">1427(C++)</span><div class="descr">1428Accessors exist for a public class field. Should this field really be1429public?</div></div></td>1430<td><div class="exampleContainer expandable">1431<div class="example"><pre>1432class A {1433public:1434 int i; // warn1435 int getI() { return i; }1436 void setI(int& ii) { i = ii; }1437};1438</pre></div></div></td>1439<td class="aligned"></td></tr>1440 1441 1442<tr><td><div class="namedescr expandable"><span class="name">1443different.LibFuncResultUnised</span><span class="lang">1444(C, C++)</span><div class="descr">1445Calling a function ignoring its return value is of no use (create the list of1446known system/library/API functions falling into this category).</div></div></td>1447<td><div class="exampleContainer expandable">1448<div class="example"><pre>1449#include <vector>1450 1451void test() {1452 std::vector<int> v;1453 v.empty(); // warn1454}1455</pre></div></div></td>1456<td class="aligned"></td></tr>1457 1458 1459<tr><td><div class="namedescr expandable"><span class="name">1460different.WrongVarForStmt</span><span class="lang">1461(C, C++)</span><div class="descr">1462Wrong variable is possibly used in the loop/cond-expression of1463the <code>for</code> statement. Did you mean1464'proper_variable_name'?</div></div></td>1465<td><div class="exampleContainer expandable">1466<div class="example"><pre>1467void test() {1468 int i = 0;1469 int j = 0;1470 for (i = 0; i < 3; j += 1); // warn1471}1472</pre></div>1473<div class="example"><pre>1474void test() {1475 int i = 0;1476 int j = 0;1477 for (int j = 0; i < 3; ++j); // warn1478}1479</pre></div></div></td>1480<td class="aligned"></td></tr>1481 1482 1483<tr><td><div class="namedescr expandable"><span class="name">1484different.FloatingCompare</span><span class="lang">1485(C)</span><div class="descr">1486Comparing floating point numbers may be not precise.</div></div></td>1487<td><div class="exampleContainer expandable">1488<div class="example"><pre>1489#include <math.h>1490 1491double test() {1492 double b = sin(M_PI / 6.0);1493 if (b == 0.5) // warn1494 b = 0;1495 return b;1496}1497</pre></div></div></td>1498<td class="aligned"></td></tr>1499 1500 1501<tr><td><div class="namedescr expandable"><span class="name">1502different.BitwiseOpBoolArg</span><span class="lang">1503(C, C++)</span><div class="descr">1504Boolean value met at the left/right part of the bitwise <code>&</code>1505or <code>|</code> operator.1506Did you mean <code>&&</code> (<code>||</code>) ?</div></div></td>1507<td><div class="exampleContainer expandable">1508<div class="example"><pre>1509int f();1510 1511void test() {1512 bool b = true;1513 if (b & f()) {} // warn1514}1515</pre></div></div></td>1516<td class="aligned"></td></tr>1517 1518 1519<tr><td><div class="namedescr expandable"><span class="name">1520different.LabelInsideSwitch</span><span class="lang">1521(C)</span><div class="descr">1522Possibly a misprint: label found inside a <code>switch()</code>1523statement.</div></div></td>1524<td><div class="exampleContainer expandable">1525<div class="example"><pre>1526void test(int c) {1527 switch(c){1528 case 1:1529 c += 1; break;1530 defalt: // warn (did you mean 'default'?)1531 c -= 1; break;1532 }1533}1534</pre></div></div></td>1535<td class="aligned"></td></tr>1536 1537 1538<tr><td><div class="namedescr expandable"><span class="name">1539different.IdenticalCondIfIf</span><span class="lang">1540(C)</span><div class="descr">1541The conditions of two subsequent <code>if</code> statements are1542identical.</div></div></td>1543<td><div class="exampleContainer expandable">1544<div class="example"><pre>1545int test(int c) {1546 if (c > 5)1547 c += 1;1548 if (c > 5) // warn1549 c -= 1;1550 return c;1551}1552</pre></div></div></td>1553<td class="aligned"></td></tr>1554 1555 1556<tr><td><div class="namedescr expandable"><span class="name">1557different.LogicalOpUselessArg</span><span class="lang">1558(C)</span><div class="descr">1559The second operand of a <code>&&</code> operator has no impact on1560expression result.</div></div></td>1561<td><div class="exampleContainer expandable">1562<div class="example"><pre>1563void test(unsigned a) {1564 if (a<7 && a<10) {}; // warn1565}1566</pre></div></div></td>1567<td class="aligned"></td></tr>1568 1569 1570<tr><td><div class="namedescr expandable"><span class="name">1571different.SameResLogicalExpr</span><span class="lang">1572(C)</span><div class="descr">1573An expression is always evaluated to true/false.</div></div></td>1574<td><div class="exampleContainer expandable">1575<div class="example"><pre>1576void test() {1577 int i = 0;1578 if (i != 0) {}; // warn1579}1580</pre></div>1581<div class="example"><pre>1582void test(int i) {1583 if (i == 0 && i == 1) {}; // warn1584}1585</pre></div>1586<div class="example"><pre>1587void test(int i) {1588 if (i < 0 || i >= 0) {}; // warn1589}1590</pre></div></div></td>1591<td class="aligned"></td></tr>1592 1593 1594<tr><td><div class="namedescr expandable"><span class="name">1595different.OpPrecedenceAssignCmp</span><span class="lang">1596(C, C++)</span><div class="descr">1597Comparison operation has higher precedence then assignment. Boolean value is1598assigned to a variable of other type. Parenthesis may bee required around an1599assignment.</div></div></td>1600<td><div class="exampleContainer expandable">1601<div class="example"><pre>1602int f();1603 1604void test(int x, int y) {1605 bool b;1606 if((b = x != y)) {} // ok1607 if((x = f() != y)) {} // warn1608}1609</pre></div></div></td>1610<td class="aligned"></td></tr>1611 1612 1613<tr><td><div class="namedescr expandable"><span class="name">1614different.OpPrecedenceIifShift</span><span class="lang">1615(C, C++)</span><div class="descr">1616<code>?:</code> has lower precedence then <code><<</code>.1617<p>Source: Stephen C. Dewhurst "C++ Gotchas: Avoiding Common Problems in Coding1618and Design", advise 15.</p></div></div></td>1619<td><div class="exampleContainer expandable">1620<div class="example"><pre>1621#include <iostream>1622 1623void test(int a) {1624 std::cout << a ? "a" : "b"; // warn1625}1626</pre></div>1627<div class="example"><pre>1628void test(int a) {1629 a << a > 7 ? 1 : 2; // warn1630}1631</pre></div></div></td>1632<td class="aligned"></td></tr>1633 1634 1635<tr><td><div class="namedescr expandable"><span class="name">1636different.ObjectUnused</span><span class="lang">1637(C++)</span><div class="descr">1638The object was created but is not being used.</div></div></td>1639<td><div class="exampleContainer expandable">1640<div class="example"><pre>1641struct S {1642 int x, y;1643 S(int xx, int yy) : x(xx), y(yy) {}1644 S(int xx) {1645 S(xx, 0); // warn1646 }1647};1648</pre></div>1649<div class="example"><pre>1650#include <exception>1651 1652void test() {1653 std::exception();1654 // warn (did you mean 'throw std::exception()'?)1655}1656</pre></div></div></td>1657<td class="aligned"></td></tr>1658 1659 1660<tr><td><div class="namedescr expandable"><span class="name">1661different.StaticArrayPtrCompare</span><span class="lang">1662(C)</span><div class="descr">1663Pointer to static array is being compared to NULL. May the subscripting is1664missing.</div></div></td>1665<td><div class="exampleContainer expandable">1666<div class="example"><pre>1667void test() {1668 int a[1][1];1669 if (a[0] == 0) {}; // warn1670}1671</pre></div></div></td>1672<td class="aligned"></td></tr>1673 1674 1675<tr><td><div class="namedescr expandable"><span class="name">1676different.ConversionToBool</span><span class="lang">1677(C, C++)</span><div class="descr">1678Odd implicit conversion to boolean.1679<br>Note: possibly merge with <span class="name">1680alpha.core.BoolAssignment</span>.</div></div></td>1681<td><div class="exampleContainer expandable">1682<div class="example"><pre>1683bool test() {1684 return 1.; // warn1685}1686</pre></div>1687<div class="example"><pre>1688bool test() {1689 return ""; // warn1690}1691</pre></div></div></td>1692<td class="aligned"></td></tr>1693 1694 1695<tr><td><div class="namedescr expandable"><span class="name">1696different.StrcpyInputSize</span><span class="lang">1697(C)</span><div class="descr">1698Buffer copy without checking the size of input.1699<br>Note: possibly an enhancement to <span class="name">1700alpha.unix.cstring.OutOfBounds</span>.</div></div></td>1701<td><div class="exampleContainer expandable">1702<div class="example"><pre>1703void test(char* string) {1704 char buf[24];1705 strcpy(buf, string); // warn1706}1707</pre></div></div></td>1708<td class="aligned"></td></tr>1709 1710 1711<tr><td><div class="namedescr expandable"><span class="name">1712different.IntegerOverflow</span><span class="lang">1713(C)</span><div class="descr">1714Integer overflow.1715<br>Note: partially handled by Clang core1716(search for 'overflow in expression' warning in Clang tests).1717<p>Source: <a href="https://cwe.mitre.org/data/definitions/190.html">1718CWE-190</a>.</p></div></div></td>1719<td><div class="exampleContainer expandable">1720<div class="example"><pre>1721#include <limits.h>1722 1723int f(int x);1724 1725void test() {1726 f(INT_MAX + 1); // warn1727}1728</pre></div>1729<div class="example"><pre>1730#include <limits.h>1731 1732int test() {1733 int x = INT_MAX / 2 + 1;1734 return x * 2; // warn1735}1736</pre></div></div></td>1737<td class="aligned"></td></tr>1738 1739 1740<tr><td><div class="namedescr expandable"><span class="name">1741different.SignExtension</span><span class="lang">1742(C)</span><div class="descr">1743Unexpected sign extension might take place.1744<p>Source: <a href="https://cwe.mitre.org/data/definitions/194.html">1745CWE-194</a>.</p></div></div></td>1746<td><div class="exampleContainer expandable">1747<div class="example"><pre>1748unsigned long long test(long long sll) {1749 unsigned long long ull = sll; // warn1750 return ull;1751}1752</pre></div>1753<div class="example"><pre>1754void f(unsigned int i);1755 1756void test(int si) {1757 f(si); // warn1758}1759</pre></div>1760<div class="example"><pre>1761unsigned int test(int i) {1762 return i;1763}1764</pre></div></div></td>1765<td class="aligned"></td></tr>1766 1767 1768<tr><td><div class="namedescr expandable"><span class="name">1769different.NumericTruncation</span><span class="lang">1770(C)</span><div class="descr">1771Numeric truncation might take place.1772<p>Source: <a href="https://cwe.mitre.org/data/definitions/197.html">1773CWE-197</a>.</p></div></div></td>1774<td><div class="exampleContainer expandable">1775<div class="example"><pre>1776unsigned long test(unsigned long long ull) {1777 unsigned long ul = ull; // warn1778 return ul;1779}1780</pre></div>1781<div class="example"><pre>1782void f(int i);1783 1784void test(long long sll) {1785 f(sll); // warn1786}1787</pre></div>1788<div class="example"><pre>1789int f();1790 1791short test(long long sll) {1792 short ss = f();1793 return ss;1794}1795</pre></div></div></td>1796<td class="aligned"></td></tr>1797 1798 1799<tr><td><div class="namedescr expandable"><span class="name">1800different.MissingCopyCtorAssignOp</span><span class="lang">1801(C++)</span><div class="descr">1802A class has dynamically allocated data members but do not define a copy1803constructor/assignment operator.1804<p>Source: Scott Meyers "Effective C++", item 11: Prevent exceptions from1805leaving destructors.</p></div></div></td>1806<td><div class="exampleContainer expandable">1807<div class="example"><pre>1808class C {1809 int *p; // warn1810public:1811 C() { p = new int; }1812 ~C() { delete p; }1813};1814</pre></div></div></td>1815<td class="aligned"></td></tr>1816 1817</table>1818 1819<!-- ============================ WinAPI =================================== -->1820<h3>WinAPI</h3>1821<table class="checkers">1822<col class="namedescr"><col class="example"><col class="progress">1823<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>1824 1825<tr><td><div class="namedescr expandable"><span class="name">1826WinAPI.CreateProcess</span><span class="lang">1827(C)</span><div class="descr">1828<code>CreateProcess()</code>: if the first parameter <code><i>1829lpApplicationName</i></code> is NULL then the executable name must be in the1830white space-delimited string pointed to by <code><i>lpCommandLine</code></i>.1831If the executable or path name has a space in it, there is a risk that a1832different executable could be run because of the way the function parses1833spaces.1834<p>Source: <a href="https://docs.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-createprocessa#security-remarks">1835MSDN: CreateProcess function, Security Remarks</a>.</p></div></div></td>1836<td><div class="exampleContainer expandable">1837<div class="example"><pre>1838#include <windows.h>1839 1840void test() {1841 STARTUPINFO si;1842 PROCESS_INFORMATION pi;1843 CreateProcess(NULL, TEXT("C:\\Program Files\\App -L -S"),1844 NULL, NULL, TRUE, 0, NULL, NULL, &si, &pi);1845 // warn1846}1847</pre></div></div></td>1848<td class="aligned"></td></tr>1849 1850 1851<tr><td><div class="namedescr expandable"><span class="name">1852WinAPI.LoadLibrary</span><span class="lang">1853(C)</span><div class="descr">1854The <code>SearchPath()</code> function is used to retrieve a path to a DLL for1855a subsequent <code>LoadLibrary()</code> call.1856<p>Source: <a href="https://docs.microsoft.com/en-us/windows/win32/api/libloaderapi/nf-libloaderapi-loadlibrarya#security-remarks">1857MSDN: LoadLibrary function, Security Remarks</a>.</p></div></div></td>1858<td><div class="exampleContainer expandable">1859<div class="example"><pre>1860#include <windows.h>1861 1862HINSTANCE test() {1863 char filePath[100];1864 SearchPath(NULL, "file.dll", NULL, 100, filePath, NULL);1865 return LoadLibrary(filePath); // warn1866}1867</pre></div></div></td>1868<td class="aligned"></td></tr>1869 1870 1871<tr><td><div class="namedescr expandable"><span class="name">1872WinAPI.WideCharToMultiByte</span><span class="lang">1873(C)</span><div class="descr">1874Buffer overrun while calling <code>WideCharToMultiByte()</code>. The size of1875the input buffer equals the number of characters in the Unicode string, while1876the size of the output buffer equals the number of bytes.1877<p>Source: <a href="https://docs.microsoft.com/en-us/windows/win32/api/stringapiset/nf-stringapiset-widechartomultibyte">1878MSDN: WideCharToMultiByte function</a>.</p></div></div></td>1879<td><div class="exampleContainer expandable">1880<div class="example"><pre>1881#include <windows.h>1882 1883void test() {1884 wchar_t ws[] = L"abc";1885 char s[3];1886 WideCharToMultiByte(CP_UTF8, 0, ws, -1, s,1887 3, NULL, NULL); // warn1888}1889</pre></div></div></td>1890<td class="aligned"></td></tr>1891 1892 1893</table>1894 1895<!-- =========================== optimization ============================== -->1896<h3>optimization</h3>1897<table class="checkers">1898<col class="namedescr"><col class="example"><col class="progress">1899<thead><tr><td>Name, Description</td><td>Example</td><td>Progress</td></tr></thead>1900 1901<tr><td><div class="namedescr expandable"><span class="name">1902optimization.PassConstObjByValue</span><span class="lang">1903(C, C++)</span><div class="descr">1904Optimization: It is more effective to pass constant parameter by reference to1905avoid unnecessary object copying.</div></div></td>1906<td><div class="exampleContainer expandable">1907<div class="example"><pre>1908struct A {};1909 1910void f(const struct A a); // warn1911</pre></div></div></td>1912<td class="aligned"></td></tr>1913 1914 1915<tr><td><div class="namedescr expandable"><span class="name">1916optimization.PostfixIncIter</span><span class="lang">1917(C++)</span><div class="descr">1918Optimization: It is more effective to use prefix increment operator with1919iterator.1920<p>Source: Scott Meyers "More Effective C++", item 6:1921Distinguish between prefix and postfix forms of increment and decrement1922operators.</p></div></div></td>1923<td><div class="exampleContainer expandable">1924<div class="example"><pre>1925#include <vector>1926 1927void test() {1928 std::vector<int> v;1929 std::vector<int>::const_iterator it;1930 for(it = v.begin();1931 it != v.end(); it++) {}; // warn1932}1933</pre></div></div></td>1934<td class="aligned"></td></tr>1935 1936 1937<tr><td><div class="namedescr expandable"><span class="name">1938optimization.MultipleCallsStrlen</span><span class="lang">1939(C)</span><div class="descr">1940Optimization: multiple calls to <code>strlen()</code> for a string in an1941expression. It is more effective to hold a value returned1942from <code>strlen()</code> in a temporary variable.</div></div></td>1943<td><div class="exampleContainer expandable">1944<div class="example"><pre>1945#include <string.h>1946 1947void test(const char* s) {1948 if (strlen(s) > 0 &&1949 strlen(s) < 7) {}; // warn1950}1951</pre></div></div></td>1952<td class="aligned"></td></tr>1953 1954 1955<tr><td><div class="namedescr expandable"><span class="name">1956optimization.StrLengthCalculation</span><span class="lang">1957(C++)</span><div class="descr">1958Optimization: it is more efficient to use <code>string::length()</code> to1959calculate the length of an <code>std::string</code>.</div></div></td>1960<td><div class="exampleContainer expandable">1961<div class="example"><pre>1962#include <string>1963#include <string.h>1964 1965void test() {1966 std::string s;1967 if (strlen(s.c_str()) != 0) {}; // warn1968}1969</pre></div></div></td>1970<td class="aligned"></td></tr>1971 1972 1973<tr><td><div class="namedescr expandable"><span class="name">1974optimization.EmptyContainerDetect</span><span class="lang">1975(C++)</span><div class="descr">1976Optimization: It is more efficient to use containers <code>empty()</code>1977method to identify an empty container.</div></div></td>1978<td><div class="exampleContainer expandable">1979<div class="example"><pre>1980#include <list>1981 1982void test() {1983 std::list<int> l;1984 if (l.size() != 0) {}; // warn1985}1986</pre></div></div></td>1987<td class="aligned"></td></tr>1988 1989 1990</table>1991 1992<br>1993</div> <!-- page -->1994</div> <!-- content -->1995</body>1996</html>1997