﻿# New diagnostic rules in PVS\-Studio 7\.34

The PVS\-Studio 7\.34 release has introduced a bunch of new diagnostic rules into the analyzer: taint analysis for Java, Unity\-specific diagnostic rules for C\#, deep dive into OWASP, and much more\! This article will cover them all\.

![1202_New_Diagnostics/image1.png](https://import.viva64.com/docx/blog/1202_New_Diagnostics/image1.png)

## C\+\+

In this release, the C\+\+ team focused on General\-Analysis diagnostic rules and the support for various software development standards\. 

But hold onto your hat, this is just the beginning\! The team plans to cover even more [MISRA standard](https://pvs-studio.com/en/pvs-studio/sast/misra/) diagnostic rules, so stay tuned for more news :\)

And for now, let's go through the main rules in the 7\.34 release\. 

### V1116

#### Creating an exception object without an explanatory message may result in insufficient logging\.

This diagnostic rule is designed to detect exceptions created without explanatory messages\. 

The absence of a message may hinder the process of error detection and fixing, as well as the overall code readability\. 

Here is an example of code that makes the PVS\-Studio analyzer generate a warning: 

```cpp
void SomeCheck(const char *val)
{
  if (!val) throw std::runtime_error { "" };
  ....
}

void Foo()
{
  const char *val = ....;
  try
  {
    SomeCheck(val);              // <=
  }
  catch(std::runtime_error &err)
  {
    std::cerr << err.what() << std::endl;
  }
}
```

If an error occurs, the `SomeCheck` function throws an exception with an empty message, which will be handled in the `Foo` function\. During processing, `std::cerr` is expected to contain information about the reason for the exception, but it does not\.

By writing code in this way, a developer sends wishes of "happy debugging" to colleagues\. This impedes the understanding what exactly caused the failure\.  

The rule works for a [standard exception](https://en.cppreference.com/w/cpp/error/exception#Standard_exceptions)\. You can use the [custom annotation mechanism](https://pvs-studio.com/en/docs/manual/6743/#exception_annotation) to issue warnings for custom exceptions\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v1116/\) for more details on this diagnostic rule\\\.



### V1117 \[For the C language\]

#### The declared function type is cv\-qualified\. The behavior when using this type is undefined\.

This diagnostic rule applies only to the C language\.

It aims to detect cases of function type definitions that use `const` or `volatile` qualifiers\.  

According to the C23 standard \([10th point of paragraph 6\.7\.4\.1](https://open-std.org/JTC1/SC22/WG14/www/docs/n3301.pdf#page=138)\), using these types leads to undefined behavior\.

An example of code that makes the PVS\-Studio analyzer generate a warning: 

```cpp
typedef int fun_t(void);

typedef const fun_t const_qual_fun_t;          // <=

typedef const fun_t * ptr_to_const_qual_fun_t; // <=

void foo()
{
  const fun_t c_fun_t;       // <=
  const fun_t * ptr_c_fun_t; // <=
}
```


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v1117/\) for more details on this diagnostic rule\\\.



### V2022 \[For the C language\]

#### Implicit type conversion from integer type to enum type\.

Another diagnostic rule for the C language that can help when refactoring and debugging\.

This rule enables the analyzer to detect implicit casts of integer types to enum types\. 

A code example with the PVS\-Studio warning: 

```cpp
Orientation GetOrientation (bool b)
{
  int posOne = 1;
  int posTwo = 2;
  return b ? posOne : posTwo;    // V2022
}
```

This code uses the conditional operator \(?:\) to choose between two integer variables `posOne` and `posTwo`, resulting in an implicit cast\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v2022/\) for more details on this diagnostic rule\\\.



### V5014 \[OWASP Standard\]

#### OWASP\. Cryptographic function is deprecated\. Its use can lead to security issues\. Consider switching to an equivalent newer function\.

Here's a new diagnostic rule focused on security, aligned with SAST principles\.

This rule was designed according to the [OWASP](https://pvs-studio.com/en/pvs-studio/sast/owasp/) security verification standard\.

It aims to detect calls of obsolete cryptographic functions\. Their use can cause critical software security problems\.

A code example with the PVS\-Studio warning: 

```cpp
BOOL ImportKey(HCRYPTPROV hProv, LPBYTE pbKeyBlob, DWORD dwBlobLen)
{
  HCRYPTKEY hPubKey;
  if (!CryptImportKey(hProv, pbKeyBlob, dwBlobLen, 0, 0, &hPubKey))
  {
    return FALSE;
  }
  if (!CryptDestroyKey(hPubKey))
  {
    return FALSE;
  }
  return TRUE;
}
```

According to Microsoft documentation, the [CryptoImportKey](https://learn.microsoft.com/en-us/windows/win32/api/wincrypt/nf-wincrypt-cryptimportkey) and [CryptoDestroyKey](https://learn.microsoft.com/en-us/windows/win32/api/wincrypt/nf-wincrypt-cryptdestroykey) functions are deprecated\. These should be replaced with secure counterparts from [Cryptography Next Generation](https://learn.microsoft.com/en-us/windows/win32/seccng/cng-portal) \([BCryptoImportKey](https://learn.microsoft.com/en-us/windows/win32/api/bcrypt/nf-bcrypt-bcryptimportkey) and [BCryptoDestroyKey](https://learn.microsoft.com/en-us/windows/win32/api/bcrypt/nf-bcrypt-bcryptdestroykey)\)\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v5014/\) for more details on this diagnostic rule\\\.



But that's just a warm up\! The C and C\+\+ team plans to cover even more diagnostic rules on various software development standards\. Special attention will be paid to the [MISRA](https://pvs-studio.com/en/pvs-studio/sast/misra/) standard\. So, wait for the news :\)

## C\#

In the new PVS\-Studio [7\.34](https://pvs-studio.com/en/whatsnew/) release, the C\# team focused on creating Unity\-specific diagnostic rules but didn't forget about General\-Analysis rules either\. 

Let's start with the latter\.

### V3207

#### The 'not A or B' logical pattern may not work as expected\. The 'not' pattern is matched only to the first expression from the 'or' pattern\.

This new diagnostic rule aims to detect incorrect use of the `not A or B` pattern\. The problem stems from developers' confusion about the operation precedence\.

A code example with the PVS\-Studio warning: 

```cpp
private void ShowWordDetails(string key)
{
  if (key is not "" or null)
  {
    PanelReferenceBox.Controls.Clear();

    CurrentWord = Words.Find(x => x.Name == key);
    ....
  }
}
```

At the beginning of the method, the input parameter `key` is checked for an empty string or `null`\.

But there is an error in the logic of the conditional expression\. The priority of the `not` operator is higher than that of the `or` operator\. As a result, negation doesn't apply to the right\-hand side of the expression\. Also, if `key` is set to `null`, the condition will be `true`\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v3207/\) for more details on this diagnostic rule\\\.



### V3208 \[Unity Engine\]

#### Unity Engine\. Using 'WeakReference' with 'UnityEngine\.Object' is not supported\. GC will not reclaim the object's memory because it is linked to a native object\.

This is the first diagnostic rule in a new series of Unity\-specific rules\.

It aims at detecting uses of `UnityEngine.Object` \(or other objects inherited from it\) together with `System.WeakReference`\. 

Due to the implicit use of the instance by the engine itself, the behavior of a weak reference may differ from what is expected\.

A code example with the PVS\-Studio warning: 

```cpp
WeakReference<GameObject> _goWeakRef;
void UnityObjectWeakReference()
{
  var go = new GameObject();
  _goWeakRef = new WeakReference<GameObject>(go);
}
```

In the example, we can see a weak reference to an object of the `GameObject` class\. Even if an author hasn't created strong references to this object, the garbage collector will not be able to clean it up\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v3208/\) for more details on this diagnostic rule\\\.



### V3209 \[Unity Engine\]

#### Unity Engine\. Using await on 'Awaitable' object more than once can lead to exception or deadlock, as such objects are returned to the pool after being awaited\.

In another diagnostic rule for Unity, the analyzer searches for places with multiple uses of the same [`UnityEngine.Awaitable`](https://docs.unity3d.com/6000.0/Documentation/Manual/async-awaitable-introduction.html) object with the `await` operator\. 

Objects are stored in an object pool for optimization purposes\. 

On await\-call, the `Awaitable` object is returned to the pool\. After that if `await` is applied to the same object again, we get an exception\. In some cases, a [deadlock](https://pvs-studio.com/en/blog/terms/0013/) is also possible\.

A code example with the PVS\-Studio warning: 

```cpp
async Awaitable<bool> AwaitableFoo() { .... }

async Awaitable ExampleFoo()
{
  Awaitable<bool> awaitable = AwaitableFoo();
  if (await awaitable)
  {
    var result = await awaitable;
    ....
  }
}
```

In this code, we get an exception or a deadlock\. Let me explain why\. We get a value using the`await` call of `awaitable`\. Then we initialize the `result` variable with this value\. The deadlock occurs, as `await` has previously been applied to `awaitable` in a conditional construction\.




> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v3209/\) for more details on this diagnostic rule\\\.





### V3210 \[Unity Engine\]

#### Unity Engine\. Unity does not allow removing the 'Transform' component using 'Destroy' or 'DestroyImmediate' methods\. The method call will be ignored\.

This diagnostic rule aims at detecting anomalies related to calls of the `Destroy` or `DestroyImmediate` methods of the `UnityEngine.Object` class\. 

The problem occurs in a situation when an argument of the `UnityEngine.Transform` type is used\. This causes an error during the method call\. Removing the `Transform` component from a game object is not allowed in Unity\.

A code example with the PVS\-Studio warning: 



```cpp
using UnityEngine;

class Projectile : MonoBehaviour
{
  public void Update() 
  {
    if (....)
    {
      Destroy(transform);
    }
    ....
  }
}
```

The `transform` property from the `MonoBehaviour` base class returns an instance of the `Transform` class, which is passed as an argument to the `Destroy` method\. 

When calling the method in this way, Unity will give an error message, but the component itself won't be destroyed\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v3210/\) for more details on this diagnostic rule\\\.



### V4007 \[Unity Engine\]

#### Unity Engine\. Avoid creating and destroying UnityEngine objects in performance\-sensitive context\. Consider activating and deactivating them instead\.

This diagnostic rule targets a different range of errors—performance issues\.




> If you are interested in how static analysis can help optimise Unity projects, I invite you to read \[this article\]\(https://pvs\-studio\.com/en/blog/posts/csharp/1071/\)\\\.



The purpose of this rule is to help the analyzer detect the creation of Unity objects in a frequently executed method\. 



Regular creation/destruction of game objects not only loads the CPU, but also leads to an increased frequency of garbage collector calls\. This affects the performance\. 



A code example with the PVS\-Studio warning: 



```cpp
CustomObject _instance;

void Update()
{
  if (....)
  {
     CreateCustomObject();
     ....
  }
  else if (....)
  {
    ....
    Destroy(_instance.gameObject);       // <=
  }
}

void CreateCustomObject()
{
  var go = new GameObject();             // <=
  _instance = go.AddComponent<CustomObject>();
  ....
}
```

Here in the `Update` method, a game object `_instance` is created and destroyed\. Since `Update` is executed every time the frames are updated, it is recommended to avoid these operations in it if possible\.  


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v4007/\) for more details on this diagnostic rule\\\.



By the way, other Unity\-diagnostics are yet to come\! Get ready for good news from our team :\)

### One more thing\.\.\.

We cannot but tell you about one important enhancement in the C\# analyzer—tracking changes of the method return value between calls\. What does it change? Let's break it down\.

Check out this example:

```cpp
void Example()
{
  if (Foo() != null)
  {
    var value = Foo().Value;
  }
}

Value Foo()
{
  if (_condition)
  {
    ....
    return value;
  }
  return null;
}
```

The `Example()` method checks the return value of `Foo()` for `null`\. The `Foo()` method is then called again in the body of the condition, and its return value is dereferenced\.

Earlier, the analyzer would generate a warning in this case because it didn't consider the context of an invocation, focusing only on the code of its declaration\. The analyzer used to imply that `null` could be returned\.

Now the analyzer understands that `Foo()` returns the same value in both cases and there will be no warning\.

But let's look at an example with slightly modified code\.\.\.

```cpp
void Example()
{
  if (Foo() != null)
  {
    _condition = false;      // <=
    var value = Foo().Value;
  }
}

Value Foo()
{
  if (_condition)
  {
    ....
    return value;
  }
  return null;
}
```

From the `Foo()` method declaration, we can get that when `_condition == true`, the method returns not `null`\.

The analyzer will see the `_condition` field change before the second invocation and will make an assumption: if the field used inside `Foo()` has changed, the return value of `Foo()` might have changed too\.

As a result, warnings of a potential dereference will remain\.


> The C\\\# analyzer now supports analysis of \\\.NET 9 projects\\\! Learn more about these and other new features in PVS\\\-Studio 7\\\.34 \[here\]\(https://pvs\-studio\.com/en/whats\-new/\)\\\.



## Java

With the release of PVS\-Studio [7\.34](https://pvs-studio.com/en/whatsnew/), the Java analyzer now has a mechanism for [taint analysis](https://pvs-studio.com/en/blog/terms/6496/)\!

This mechanism became the basis for the first diagnostic rule—search for SQL injections\. Future updates of the Java analyzer will focus on SAST, the [OWASP Top\-10](https://pvs-studio.com/en/blog/terms/6458/) list of the most common potential vulnerabilities, and other taint\-related diagnostic rules\.

Right now, let's start with some new General Analysis rules, as they are also worthwhile\.

### V6123

#### Modified value of the operand is not used after the increment/decrement operation\.

This new diagnostic rule highlights areas in code where values of postfix operations are not used\. 

The problem is that either an operation is redundant or, more seriously, operations got mixed up and a developer wanted to use the prefix one\.

A code example with the PVS\-Studio warning: 



```cpp
int calculateSomething() {
  int value = getSomething();
  ....
  return value++;
}
```

The `++` operator won't affect the value that the `calculateSomething` method will return\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v6123/\) for more details on this diagnostic rule\\\.

  

### V6124

#### Converting an integer literal to the type with a smaller value range will result in overflow\.

As you can see from the name of this diagnostic rule, it detects possible overflow\.

A code example with the PVS\-Studio warning: 

```cpp
public static void test() {
  byte a = (byte) 256;       // a = 0
  short b = (short) 32768;   // b = -32768
  int c = (int) 2147483648L; // c = -2147483648
}
```

An integer type variable has been assigned a value out of the valid range, which will cause an overflow\.

Variables will obviously store different values than the ones the developer tried to assign\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v6124/\) for more details on this diagnostic rule\\\.



### V6125

#### Calling the 'wait', 'notify', and 'notifyAll' methods outside of synchronized context will lead to 'IllegalMonitorStateException'\.

This diagnostic helps identify synchronization problems\.

A code example with the PVS\-Studio warning: 

```cpp
public void someMethod() {
    notify();
}

public void anotherMethod() throws InterruptedException {
    wait();
}
```

The analyzer spots `wait`, `notify`, and `notifyAll` methods, as they may be called in an unsynchronized context\. They [operate](https://docs.oracle.com/en/java/javase/22/docs/api/java.base/java/lang/Object.html#notify()) with the monitor of the object by which the synchronization occurs\. That is, their invocation is correct only in the synchronized context and only on the object by which synchronization occurs\.

If `wait`, `notify` or `notifyAll` methods are called in an unsynchronized context or on the wrong object, we get the `IllegalMonitorStateException` exception\.


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v6124/\) for more details on this diagnostic rule\\\.



### V5309 \[OWASP standard\]

#### OWASP\. Possible SQL injection\. Potentially tainted data is used to create SQL command\.

The first taint\-related diagnostic rule of the Java analyzer\! More specifically, the analyzer can now detect potential SQL injections\.

SQL injection is a vulnerability that allows an attacker to inject their code into an SQL query\. If the query uses external data, without validating it correctly, one risks the integrity and confidentiality of the information stored in a database\.

```cpp
@Autowired
private JdbcTemplate template;

@GetMapping("/get_all_secret_data")
public void getEndpoint(@RequestParam String param) {
    var sql = "SELECT * FROM Users WHERE id = '" + param + "'";
    template.execute(sql);
    ....
}
```

In case the user turns out to be malicious and the value of `param` is approximately the following:\- "111' or 1\=1; drop table users; select ' ",—you can say goodbye to the `users` table\. Therefore, it is important to check the external data\. 


> Check out the \[documentation\]\(https://pvs\-studio\.com/en/docs/warnings/v5309/\) for more details on this diagnostic rule\\\.



Thanks for reading\!

If you have requests for articles or questions, don't hesitate to send them via the [feedback form](https://pvs-studio.com/en/about-feedback/?is_question_form_open=true)\. Last but not least, we'd love to hear your thoughts in the comments:\)