[clang-tools-extra] 512767e - Add CppCoreGuidelines I.2 "Avoid non-const global variables" check

Aaron Ballman via cfe-commits cfe-commits at lists.llvm.org
Fri Mar 13 07:06:14 PDT 2020


Author: Kim Viggedal
Date: 2020-03-13T10:05:13-04:00
New Revision: 512767eb3fe9c34c655a480d034147c54f1d4f85

URL: https://github.com/llvm/llvm-project/commit/512767eb3fe9c34c655a480d034147c54f1d4f85
DIFF: https://github.com/llvm/llvm-project/commit/512767eb3fe9c34c655a480d034147c54f1d4f85.diff

LOG: Add CppCoreGuidelines I.2 "Avoid non-const global variables" check

Cpp Core Guideline I.2, a.k.a "Avoid non-const global variables"
For detailed documentation, see:
https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#i2-avoid-non-const-global-variables

Added: 
    clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.cpp
    clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.h
    clang-tools-extra/docs/clang-tidy/checks/cppcoreguidelines-avoid-non-const-global-variables.rst
    clang-tools-extra/test/clang-tidy/checkers/cppcoreguidelines-avoid-non-const-global-variables.cpp

Modified: 
    clang-tools-extra/clang-tidy/cppcoreguidelines/CMakeLists.txt
    clang-tools-extra/clang-tidy/cppcoreguidelines/CppCoreGuidelinesTidyModule.cpp
    clang-tools-extra/docs/ReleaseNotes.rst
    clang-tools-extra/docs/clang-tidy/checks/list.rst

Removed: 
    


################################################################################
diff  --git a/clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.cpp b/clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.cpp
new file mode 100644
index 000000000000..da94ac03ae19
--- /dev/null
+++ b/clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.cpp
@@ -0,0 +1,67 @@
+//===--- AvoidNonConstGlobalVariablesCheck.cpp - clang-tidy ---------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "AvoidNonConstGlobalVariablesCheck.h"
+#include "clang/AST/ASTContext.h"
+#include "clang/ASTMatchers/ASTMatchFinder.h"
+#include "clang/ASTMatchers/ASTMatchers.h"
+
+using namespace clang::ast_matchers;
+
+namespace clang {
+namespace tidy {
+namespace cppcoreguidelines {
+
+void AvoidNonConstGlobalVariablesCheck::registerMatchers(MatchFinder *Finder) {
+  auto GlobalVariable = varDecl(
+      hasGlobalStorage(),
+      unless(anyOf(
+          isConstexpr(), hasType(isConstQualified()),
+          hasType(referenceType())))); // References can't be changed, only the
+                                       // data they reference can be changed.
+
+  auto GlobalReferenceToNonConst =
+      varDecl(hasGlobalStorage(), hasType(referenceType()),
+              unless(hasType(references(qualType(isConstQualified())))));
+
+  auto GlobalPointerToNonConst =
+      varDecl(hasGlobalStorage(),
+              hasType(pointerType(pointee(unless(isConstQualified())))));
+
+  Finder->addMatcher(GlobalVariable.bind("non-const_variable"), this);
+  Finder->addMatcher(GlobalReferenceToNonConst.bind("indirection_to_non-const"),
+                     this);
+  Finder->addMatcher(GlobalPointerToNonConst.bind("indirection_to_non-const"),
+                     this);
+}
+
+void AvoidNonConstGlobalVariablesCheck::check(
+    const MatchFinder::MatchResult &Result) {
+
+  if (const auto *Variable =
+          Result.Nodes.getNodeAs<VarDecl>("non-const_variable")) {
+    diag(Variable->getLocation(), "variable %0 is non-const and globally "
+                                  "accessible, consider making it const")
+        << Variable; // FIXME: Add fix-it hint to Variable
+    // Don't return early, a non-const variable may also be a pointer or
+    // reference to non-const data.
+  }
+
+  if (const auto *VD =
+          Result.Nodes.getNodeAs<VarDecl>("indirection_to_non-const")) {
+    diag(VD->getLocation(),
+         "variable %0 provides global access to a non-const object; consider "
+         "making the %select{referenced|pointed-to}1 data 'const'")
+        << VD
+        << VD->getType()->isPointerType(); // FIXME: Add fix-it hint to Variable
+  }
+}
+
+} // namespace cppcoreguidelines
+} // namespace tidy
+} // namespace clang

diff  --git a/clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.h b/clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.h
new file mode 100644
index 000000000000..4f5a2a025033
--- /dev/null
+++ b/clang-tools-extra/clang-tidy/cppcoreguidelines/AvoidNonConstGlobalVariablesCheck.h
@@ -0,0 +1,35 @@
+//===--- AvoidNonConstGlobalVariablesCheck.h - clang-tidy -------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CPPCOREGUIDELINES_AVOIDNONCONSTGLOBALVARIABLESCHECK_H
+#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CPPCOREGUIDELINES_AVOIDNONCONSTGLOBALVARIABLESCHECK_H
+
+#include "../ClangTidyCheck.h"
+
+namespace clang {
+namespace tidy {
+namespace cppcoreguidelines {
+
+/// Non-const global variables hide dependencies and make the dependencies
+/// subject to unpredictable changes.
+///
+/// For the user-facing documentation see:
+/// http://clang.llvm.org/extra/clang-tidy/checks/cppcoreguidelines-avoid-non-const-global-variables.html
+class AvoidNonConstGlobalVariablesCheck : public ClangTidyCheck {
+public:
+  AvoidNonConstGlobalVariablesCheck(StringRef Name, ClangTidyContext *Context)
+      : ClangTidyCheck(Name, Context) {}
+  void registerMatchers(ast_matchers::MatchFinder *Finder) override;
+  void check(const ast_matchers::MatchFinder::MatchResult &Result) override;
+};
+
+} // namespace cppcoreguidelines
+} // namespace tidy
+} // namespace clang
+
+#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_CPPCOREGUIDELINES_AVOIDNONCONSTGLOBALVARIABLESCHECK_H

diff  --git a/clang-tools-extra/clang-tidy/cppcoreguidelines/CMakeLists.txt b/clang-tools-extra/clang-tidy/cppcoreguidelines/CMakeLists.txt
index 13c15bc9d227..5c27538d3487 100644
--- a/clang-tools-extra/clang-tidy/cppcoreguidelines/CMakeLists.txt
+++ b/clang-tools-extra/clang-tidy/cppcoreguidelines/CMakeLists.txt
@@ -2,6 +2,7 @@ set(LLVM_LINK_COMPONENTS support)
 
 add_clang_library(clangTidyCppCoreGuidelinesModule
   AvoidGotoCheck.cpp
+  AvoidNonConstGlobalVariablesCheck.cpp
   CppCoreGuidelinesTidyModule.cpp
   InitVariablesCheck.cpp
   InterfacesGlobalInitCheck.cpp

diff  --git a/clang-tools-extra/clang-tidy/cppcoreguidelines/CppCoreGuidelinesTidyModule.cpp b/clang-tools-extra/clang-tidy/cppcoreguidelines/CppCoreGuidelinesTidyModule.cpp
index 8886eb833795..4cb5022888d3 100644
--- a/clang-tools-extra/clang-tidy/cppcoreguidelines/CppCoreGuidelinesTidyModule.cpp
+++ b/clang-tools-extra/clang-tidy/cppcoreguidelines/CppCoreGuidelinesTidyModule.cpp
@@ -15,6 +15,7 @@
 #include "../modernize/UseOverrideCheck.h"
 #include "../readability/MagicNumbersCheck.h"
 #include "AvoidGotoCheck.h"
+#include "AvoidNonConstGlobalVariablesCheck.h"
 #include "InitVariablesCheck.h"
 #include "InterfacesGlobalInitCheck.h"
 #include "MacroUsageCheck.h"
@@ -48,6 +49,8 @@ class CppCoreGuidelinesModule : public ClangTidyModule {
         "cppcoreguidelines-avoid-goto");
     CheckFactories.registerCheck<readability::MagicNumbersCheck>(
         "cppcoreguidelines-avoid-magic-numbers");
+    CheckFactories.registerCheck<AvoidNonConstGlobalVariablesCheck>(
+        "cppcoreguidelines-avoid-non-const-global-variables");
     CheckFactories.registerCheck<modernize::UseOverrideCheck>(
         "cppcoreguidelines-explicit-virtual-functions");
     CheckFactories.registerCheck<InitVariablesCheck>(

diff  --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index 95afaf3b659a..3b9212f6723c 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -75,6 +75,10 @@ New module
 
 New checks
 ^^^^^^^^^^
+- New :doc:`cppcoreguidelines-avoid-non-const-global-variables
+  <clang-tidy/checks/cppcoreguidelines-avoid-non-const-global-variables>` check.
+  Finds non-const global variables as described in check I.2 of C++ Core
+  Guidelines.
 
 - New :doc:`bugprone-misplaced-pointer-arithmetic-in-alloc
   <clang-tidy/checks/bugprone-misplaced-pointer-arithmetic-in-alloc>` check.

diff  --git a/clang-tools-extra/docs/clang-tidy/checks/cppcoreguidelines-avoid-non-const-global-variables.rst b/clang-tools-extra/docs/clang-tidy/checks/cppcoreguidelines-avoid-non-const-global-variables.rst
new file mode 100644
index 000000000000..4d1ffde62dbb
--- /dev/null
+++ b/clang-tools-extra/docs/clang-tidy/checks/cppcoreguidelines-avoid-non-const-global-variables.rst
@@ -0,0 +1,38 @@
+.. title:: clang-tidy - cppcoreguidelines-avoid-non-const-global-variables
+
+cppcoreguidelines-avoid-non-const-global-variables
+==================================================
+
+Finds non-const global variables as described in `I.2 of C++ Core Guidelines <https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#Ri-global>` .
+As `R.6 of C++ Core Guidelines <https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#Rr-global>` is a duplicate of rule I.2 it also covers that rule.
+
+.. code-block:: c++
+
+    char a;  // Warns!
+    const char b =  0;
+
+    namespace some_namespace
+    {
+        char c;  // Warns!
+        const char d = 0;
+    }
+
+    char * c_ptr1 = &some_namespace::c;  // Warns!
+    char *const c_const_ptr = &some_namespace::c;  // Warns!
+    char & c_reference = some_namespace::c;  // Warns!
+
+    class Foo  // No Warnings inside Foo, only namespace scope is covered
+    {
+    public:
+        char e = 0;
+        const char f = 0;
+    protected:
+        char g = 0;
+    private:
+        char h = 0;
+    };
+
+Variables: ``a``, ``c``, ``c_ptr1``, ``c_ptr2``, ``c_const_ptr`` and
+``c_reference``, will all generate warnings since they are either:
+a globally accessible variable and non-const, a pointer or reference providing
+global access to non-const data or both.

diff  --git a/clang-tools-extra/docs/clang-tidy/checks/list.rst b/clang-tools-extra/docs/clang-tidy/checks/list.rst
index 36ad51feff32..5e943c5003f0 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/list.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/list.rst
@@ -380,6 +380,7 @@ Clang-Tidy Checks
    `clang-analyzer-unix.cstring.NullArg <clang-analyzer-unix.cstring.NullArg.html>`_, `Clang Static Analyzer <https://clang.llvm.org/docs/analyzer/checkers.html>`_,
    `cppcoreguidelines-avoid-c-arrays <cppcoreguidelines-avoid-c-arrays.html>`_, `modernize-avoid-c-arrays <modernize-avoid-c-arrays.html>`_,
    `cppcoreguidelines-avoid-magic-numbers <cppcoreguidelines-avoid-magic-numbers.html>`_, `readability-magic-numbers <readability-magic-numbers.html>`_,
+   `cppcoreguidelines-avoid-non-const-global-variables <cppcoreguidelines-avoid-non-const-global-variables.html>`_, , , ""
    `cppcoreguidelines-c-copy-assignment-signature <cppcoreguidelines-c-copy-assignment-signature.html>`_, `misc-unconventional-assign-operator <misc-unconventional-assign-operator.html>`_,
    `cppcoreguidelines-explicit-virtual-functions <cppcoreguidelines-explicit-virtual-functions.html>`_, `modernize-use-override <modernize-use-override.html>`_, "Yes"
    `cppcoreguidelines-non-private-member-variables-in-classes <cppcoreguidelines-non-private-member-variables-in-classes.html>`_, `misc-non-private-member-variables-in-classes <misc-non-private-member-variables-in-classes.html>`_,
@@ -413,3 +414,4 @@ Clang-Tidy Checks
    `hicpp-use-override <hicpp-use-override.html>`_, `modernize-use-override <modernize-use-override.html>`_, "Yes"
    `hicpp-vararg <hicpp-vararg.html>`_, `cppcoreguidelines-pro-type-vararg <cppcoreguidelines-pro-type-vararg.html>`_,
    `llvm-qualified-auto <llvm-qualified-auto.html>`_, `readability-qualified-auto <readability-qualified-auto.html>`_, "Yes"
+

diff  --git a/clang-tools-extra/test/clang-tidy/checkers/cppcoreguidelines-avoid-non-const-global-variables.cpp b/clang-tools-extra/test/clang-tidy/checkers/cppcoreguidelines-avoid-non-const-global-variables.cpp
new file mode 100644
index 000000000000..1e554d6e59da
--- /dev/null
+++ b/clang-tools-extra/test/clang-tidy/checkers/cppcoreguidelines-avoid-non-const-global-variables.cpp
@@ -0,0 +1,237 @@
+// RUN: %check_clang_tidy %s cppcoreguidelines-avoid-non-const-global-variables %t
+
+int nonConstInt = 0;
+// CHECK-MESSAGES: :[[@LINE-1]]:5: warning: variable 'nonConstInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+int &nonConstIntReference = nonConstInt;
+// CHECK-MESSAGES: :[[@LINE-1]]:6: warning: variable 'nonConstIntReference' provides global access to a non-const object; consider making the referenced data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+int *pointerToNonConstInt = &nonConstInt;
+// CHECK-MESSAGES: :[[@LINE-1]]:6: warning: variable 'pointerToNonConstInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+// CHECK-MESSAGES: :[[@LINE-2]]:6: warning: variable 'pointerToNonConstInt' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+int *const constPointerToNonConstInt = &nonConstInt;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'constPointerToNonConstInt' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+namespace namespace_name {
+int nonConstNamespaceInt = 0;
+// CHECK-MESSAGES: :[[@LINE-1]]:5: warning: variable 'nonConstNamespaceInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const int constNamespaceInt = 0;
+} // namespace namespace_name
+
+const int constInt = 0;
+
+const int *pointerToConstInt = &constInt;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'pointerToConstInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const int *const constPointerToConstInt = &constInt;
+
+const int &constReferenceToConstInt = constInt;
+
+constexpr int constexprInt = 0;
+
+int function() {
+  int nonConstReturnValue = 0;
+  return nonConstReturnValue;
+}
+
+namespace {
+int nonConstAnonymousNamespaceInt = 0;
+// CHECK-MESSAGES: :[[@LINE-1]]:5: warning: variable 'nonConstAnonymousNamespaceInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+} // namespace
+
+class DummyClass {
+public:
+  int nonConstPublicMemberVariable = 0;
+  const int constPublicMemberVariable = 0;
+
+private:
+  int nonConstPrivateMemberVariable = 0;
+  const int constPrivateMemberVariable = 0;
+};
+
+DummyClass nonConstClassInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'nonConstClassInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyClass *pointerToNonConstDummyClass = &nonConstClassInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: variable 'pointerToNonConstDummyClass' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+// CHECK-MESSAGES: :[[@LINE-2]]:13: warning: variable 'pointerToNonConstDummyClass' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyClass &referenceToNonConstDummyClass = nonConstClassInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: variable 'referenceToNonConstDummyClass' provides global access to a non-const object; consider making the referenced data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+int *nonConstPointerToMember = &nonConstClassInstance.nonConstPublicMemberVariable;
+// CHECK-MESSAGES: :[[@LINE-1]]:6: warning: variable 'nonConstPointerToMember' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+// CHECK-MESSAGES: :[[@LINE-2]]:6: warning: variable 'nonConstPointerToMember' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+int *const constPointerToNonConstMember = &nonConstClassInstance.nonConstPublicMemberVariable;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'constPointerToNonConstMember' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyClass constClassInstance;
+
+DummyClass *const constPointerToNonConstDummyClass = &nonConstClassInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:19: warning: variable 'constPointerToNonConstDummyClass' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyClass *nonConstPointerToConstDummyClass = &constClassInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:19: warning: variable 'nonConstPointerToConstDummyClass' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyClass *const constPointerToConstDummyClass = &constClassInstance;
+
+const int *const constPointerToConstMember = &constClassInstance.nonConstPublicMemberVariable;
+
+const DummyClass &constReferenceToDummyClass = constClassInstance;
+
+namespace namespace_name {
+DummyClass nonConstNamespaceClassInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'nonConstNamespaceClassInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyClass constDummyClassInstance;
+} // namespace namespace_name
+
+// CHECKING FOR NON-CONST GLOBAL ENUM /////////////////////////////////////////
+enum DummyEnum {
+  first,
+  second
+};
+
+DummyEnum nonConstDummyEnumInstance = DummyEnum::first;
+// CHECK-MESSAGES: :[[@LINE-1]]:11: warning: variable 'nonConstDummyEnumInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyEnum *pointerToNonConstDummyEnum = &nonConstDummyEnumInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'pointerToNonConstDummyEnum' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+// CHECK-MESSAGES: :[[@LINE-2]]:12: warning: variable 'pointerToNonConstDummyEnum' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyEnum &referenceToNonConstDummyEnum = nonConstDummyEnumInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'referenceToNonConstDummyEnum' provides global access to a non-const object; consider making the referenced data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyEnum *const constPointerToNonConstDummyEnum = &nonConstDummyEnumInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:18: warning: variable 'constPointerToNonConstDummyEnum' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyEnum constDummyEnumInstance = DummyEnum::first;
+
+const DummyEnum *nonConstPointerToConstDummyEnum = &constDummyEnumInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:18: warning: variable 'nonConstPointerToConstDummyEnum' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyEnum *const constPointerToConstDummyEnum = &constDummyEnumInstance;
+
+const DummyEnum &referenceToConstDummyEnum = constDummyEnumInstance;
+
+namespace namespace_name {
+DummyEnum nonConstNamespaceEnumInstance = DummyEnum::first;
+// CHECK-MESSAGES: :[[@LINE-1]]:11: warning: variable 'nonConstNamespaceEnumInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyEnum constNamespaceEnumInstance = DummyEnum::first;
+} // namespace namespace_name
+
+namespace {
+DummyEnum nonConstAnonymousNamespaceEnumInstance = DummyEnum::first;
+}
+// CHECK-MESSAGES: :[[@LINE-2]]:11: warning: variable 'nonConstAnonymousNamespaceEnumInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+// CHECKING FOR NON-CONST GLOBAL STRUCT ///////////////////////////////////////
+struct DummyStruct {
+public:
+  int structIntElement = 0;
+  const int constStructIntElement = 0;
+
+private:
+  int privateStructIntElement = 0;
+};
+
+DummyStruct nonConstDummyStructInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: variable 'nonConstDummyStructInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyStruct *pointerToNonConstDummyStruct = &nonConstDummyStructInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:14: warning: variable 'pointerToNonConstDummyStruct' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+// CHECK-MESSAGES: :[[@LINE-2]]:14: warning: variable 'pointerToNonConstDummyStruct' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyStruct &referenceToNonConstDummyStruct = nonConstDummyStructInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:14: warning: variable 'referenceToNonConstDummyStruct' provides global access to a non-const object; consider making the referenced data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+DummyStruct *const constPointerToNonConstDummyStruct = &nonConstDummyStructInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:20: warning: variable 'constPointerToNonConstDummyStruct' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyStruct constDummyStructInstance;
+
+const DummyStruct *nonConstPointerToConstDummyStruct = &constDummyStructInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:20: warning: variable 'nonConstPointerToConstDummyStruct' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyStruct *const constPointerToConstDummyStruct = &constDummyStructInstance;
+
+const DummyStruct &referenceToConstDummyStruct = constDummyStructInstance;
+
+namespace namespace_name {
+DummyStruct nonConstNamespaceDummyStructInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: variable 'nonConstNamespaceDummyStructInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyStruct constNamespaceDummyStructInstance;
+} // namespace namespace_name
+
+namespace {
+DummyStruct nonConstAnonymousNamespaceStructInstance;
+}
+// CHECK-MESSAGES: :[[@LINE-2]]:13: warning: variable 'nonConstAnonymousNamespaceStructInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+// CHECKING FOR NON-CONST GLOBAL UNION ////////////////////////////////////////
+union DummyUnion {
+  int unionInteger;
+  char unionChar;
+};
+
+DummyUnion nonConstUnionIntInstance = {0x0};
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'nonConstUnionIntInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyUnion *nonConstPointerToNonConstUnionInt = &nonConstUnionIntInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: variable 'nonConstPointerToNonConstUnionInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+// CHECK-MESSAGES: :[[@LINE-2]]:13: warning: variable 'nonConstPointerToNonConstUnionInt' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyUnion *const constPointerToNonConstUnionInt = &nonConstUnionIntInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:19: warning: variable 'constPointerToNonConstUnionInt' provides global access to a non-const object; consider making the pointed-to data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+DummyUnion &referenceToNonConstUnionInt = nonConstUnionIntInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:13: warning: variable 'referenceToNonConstUnionInt' provides global access to a non-const object; consider making the referenced data 'const' [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyUnion constUnionIntInstance = {0x0};
+
+const DummyUnion *nonConstPointerToConstUnionInt = &constUnionIntInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:19: warning: variable 'nonConstPointerToConstUnionInt' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyUnion *const constPointerToConstUnionInt = &constUnionIntInstance;
+
+const DummyUnion &referenceToConstUnionInt = constUnionIntInstance;
+
+namespace namespace_name {
+DummyUnion nonConstNamespaceDummyUnionInstance;
+// CHECK-MESSAGES: :[[@LINE-1]]:12: warning: variable 'nonConstNamespaceDummyUnionInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+const DummyUnion constNamespaceDummyUnionInstance = {0x0};
+} // namespace namespace_name
+
+namespace {
+DummyUnion nonConstAnonymousNamespaceUnionInstance = {0x0};
+}
+// CHECK-MESSAGES: :[[@LINE-2]]:12: warning: variable 'nonConstAnonymousNamespaceUnionInstance' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+// CHECKING FOR NON-CONST GLOBAL FUNCTION POINTER /////////////////////////////
+int dummyFunction() {
+  return 0;
+}
+
+typedef int (*functionPointer)();
+functionPointer fp1 = &dummyFunction;
+// CHECK-MESSAGES: :[[@LINE-1]]:17: warning: variable 'fp1' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+typedef int (*const functionConstPointer)();
+functionPointer fp2 = &dummyFunction;
+// CHECK-MESSAGES: :[[@LINE-1]]:17: warning: variable 'fp2' is non-const and globally accessible, consider making it const [cppcoreguidelines-avoid-non-const-global-variables]
+
+// CHECKING FOR NON-CONST GLOBAL TEMPLATE VARIABLE ////////////////////////////
+template <class T>
+constexpr T templateVariable = T(0L);
+
+// CHECKING AGAINST FALSE POSITIVES INSIDE FUNCTION SCOPE /////////////////////
+int main() {
+  for (int i = 0; i < 3; ++i) {
+    int nonConstLoopVariable = 42;
+    nonConstInt = nonConstLoopVariable + i;
+  }
+}


        


More information about the cfe-commits mailing list