Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit9aa5e21

Browse files
committed
RULE-8-2-2 - NoCStyleOrFunctionalCasts
Detects C-style casts and functional notation casts that should bereplaced with explicit cast operators. Prevents unsafe type conversionsthat lack clear intent and proper type checking constraints. [a]
1 parent9b9a68c commit9aa5e21

File tree

4 files changed

+199
-0
lines changed

4 files changed

+199
-0
lines changed
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
/**
2+
* @id cpp/misra/no-c-style-or-functional-casts
3+
* @name RULE-8-2-2: C-style casts and functional notation casts shall not be used
4+
* @description Using C-style casts or functional notation casts allows unsafe type conversions and
5+
* makes code harder to maintain compared to using named casts like const_cast,
6+
* dynamic_cast, static_cast and reinterpret_cast.
7+
* @kind problem
8+
* @precision very-high
9+
* @problem.severity error
10+
* @tags external/misra/id/rule-8-2-2
11+
* scope/single-translation-unit
12+
* external/misra/enforcement/decidable
13+
* external/misra/obligation/required
14+
*/
15+
16+
import cpp
17+
import codingstandards.cpp.misra
18+
import codingstandards.cpp.CStyleCasts
19+
import codingstandards.cpp.AlertReporting
20+
21+
classMISRACPPProhibitedCStyleCastsextendsExplicitUserDefinedCStyleCast{
22+
MISRACPPProhibitedCStyleCasts(){
23+
// MISRA C++ permits casts to void types
24+
notgetType()instanceofVoidType
25+
}
26+
}
27+
28+
fromElementreportingElement,MISRACPPProhibitedCStyleCastsc
29+
where
30+
notisExcluded(c, Conversions2Package::noCStyleOrFunctionalCastsQuery())and
31+
reportingElement= MacroUnwrapper<MISRACPPProhibitedCStyleCasts>::unwrapElement(c)and
32+
exists(reportingElement.getFile().getRelativePath())// within user code - validated during testing
33+
selectreportingElement,"Use of explicit c-style cast to "+c.getType().getName()+"."
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
| test.cpp:8:22:8:37 | (uint32_t)... | Use of explicit c-style cast to uint32_t. |
2+
| test.cpp:9:22:9:32 | (unsigned int)... | Use of explicit c-style cast to unsigned int. |
3+
| test.cpp:70:1:70:31 | #define ADD_ONE(x) ((int)x) + 1 | Use of explicit c-style cast to int. |
4+
| test.cpp:83:19:83:26 | (int)... | Use of explicit c-style cast to int. |
5+
| test.cpp:84:27:84:34 | (int)... | Use of explicit c-style cast to int. |
6+
| test.cpp:112:10:112:13 | (int)... | Use of explicit c-style cast to int. |
7+
| test.cpp:147:12:147:26 | (unsigned int)... | Use of explicit c-style cast to unsigned int. |
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
rules/RULE-8-2-2/NoCStyleOrFunctionalCasts.ql
Lines changed: 158 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,158 @@
1+
#include<cstdint>
2+
#include<string>
3+
#include<utility>
4+
intfoo() {return1; }
5+
// A copy of A5-2-2 test.cpp, but with different cases compliant/non-compliant
6+
voidtest_c_style_cast() {
7+
double f =3.14;
8+
std::uint32_t n1 = (std::uint32_t)f;// NON_COMPLIANT - C-style cast
9+
std::uint32_t n2 =unsigned(f);// NON_COMPLIANT - functional notation
10+
11+
std::uint8_t n3 =1;
12+
std::uint8_t n4 =1;
13+
std::uint8_t n5 = n3 + n4;// ignored, implicit casts
14+
15+
(void)foo();// COMPLIANT - permitted by MISRA C++
16+
}
17+
18+
classA {
19+
public:
20+
virtualvoidf1() {}
21+
};
22+
23+
classB : A {
24+
public:
25+
virtualvoidf1() {}
26+
};
27+
28+
classC {
29+
voidf1() {}
30+
};
31+
32+
voidtest_cpp_style_cast() {
33+
// These cases may contravene other rules, but are marked as COMPLIANT for
34+
// this rule
35+
A a1;
36+
const A *a2 = &a1;
37+
A *a3 =const_cast<A *>(a2);// COMPLIANT
38+
B *b =dynamic_cast<B *>(a3);// COMPLIANT
39+
C *c =reinterpret_cast<C *>(a3);// COMPLIANT
40+
std::int16_t n8 =0;
41+
std::int32_t n9 =static_cast<std::int32_t>(n8);// COMPLIANT
42+
static_cast<void>(foo());// COMPLIANT
43+
}
44+
45+
classA5_2_2a {
46+
public:
47+
template<typename... As>
48+
staticvoidFoo(const std::string &name, As &&...rest) {
49+
Fun(Log(std::forward<As>(
50+
rest)...));// COMPLIANT - previously reported as a false positive
51+
}
52+
53+
template<typename... As>static std::stringLog(As &&...tail) {
54+
returnstd::string();
55+
}
56+
57+
staticvoidFun(const std::string &message) {}
58+
};
59+
60+
classA5_2_2final {
61+
public:
62+
voidf(const std::string &s)const {A5_2_2a::Foo("name","x","y","z"); }
63+
};
64+
65+
voida5_2_2_test() {
66+
A5_2_2 a;
67+
a.f("");
68+
}
69+
70+
#defineADD_ONE(x) ((int)x) +1// NON_COMPLIANT
71+
#defineNESTED_ADD_ONE(x) ADD_ONE(x)// Not reported - reported at ADD_ONE
72+
#defineNO_CAST_ADD_ONE(x) x +1// COMPLIANT
73+
74+
#include"macro_c_style_casts.h"
75+
76+
voidtest_macro_cast() {
77+
ADD_ONE(1);// Reported at macro definition site
78+
NESTED_ADD_ONE(1);// reported at macro definition site
79+
LIBRARY_ADD_TWO(1);// COMPLIANT - macro generating the cast is defined in a
80+
// library, and is not modifiable by the user
81+
LIBRARY_NESTED_ADD_TWO(1);// COMPLIANT - macro generating the cast is defined
82+
// in a library, and is not modifiable by the user
83+
NO_CAST_ADD_ONE((int)1.0);// NON_COMPLIANT - cast in argument to macro
84+
LIBRARY_NO_CAST_ADD_TWO((int)1.0);// NON_COMPLIANT - library macro with
85+
// c-style cast in argument, written by
86+
// user so should be reported
87+
}
88+
89+
classD {
90+
public:
91+
D(int x) : fx(x), fy(0) {}
92+
D(int x,int y) : fx(x), fy(y) {}
93+
94+
private:
95+
int fx;
96+
int fy;
97+
};
98+
99+
DtestNonFunctionalCast() {
100+
return (D)1;// COMPLIANT
101+
}
102+
103+
DtestFunctionalCast() {
104+
returnD(1);// COMPLIANT
105+
}
106+
107+
DtestFunctionalCastMulti() {
108+
returnD(1,2);// COMPLIANT
109+
}
110+
111+
template<typename T> TtestFunctionalCastTemplate() {
112+
returnT(1);// NON_COMPLIANT - used with an int
113+
}
114+
115+
template<typename T> TtestFunctionalCastTemplateMulti() {
116+
returnT(1,2);// COMPLIANT
117+
}
118+
119+
voidtestFunctionalCastTemplateUse() {
120+
testFunctionalCastTemplate<D>();
121+
testFunctionalCastTemplate<int>();
122+
testFunctionalCastTemplateMulti<D>();
123+
}
124+
125+
template<typename T>classE {
126+
public:
127+
classF {
128+
public:
129+
F(int x) : fx(x), fy(0) {}
130+
F(int x,int y) : fx(x), fy(y) {}
131+
132+
private:
133+
int fx;
134+
int fy;
135+
};
136+
137+
Ff() {
138+
returnF(1);// COMPLIANT
139+
}
140+
141+
Dd() {
142+
returnD(1);// COMPLIANT
143+
}
144+
145+
inti() {
146+
double f =3.14;
147+
return (unsignedint)f;// NON_COMPLIANT
148+
}
149+
};
150+
151+
classG {};
152+
153+
voidtestE() {
154+
E<G> e;
155+
e.f();
156+
e.d();
157+
e.i();
158+
}

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp