Icônes SCW
héros bg sans séparateur
Blog

Les erreurs Java : opérateurs bit à bit et opérateurs booléens

Alan Richardson
Publié le 07 février 2021
Dernière mise à jour le 6 mars 2026

Les erreurs Java : opérateurs bit à bit et opérateurs booléens

« Java Gotcha » : un modèle d'erreur courant qui peut être facilement mis en œuvre de manière involontaire.

Une astuce Java assez simple dans laquelle on peut tomber accidentellement consiste à utiliser un opérateur bit à bit au lieu d'un opérateur de comparaison booléen.

Par exemple, une simple erreur de frappe peut entraîner l'écriture de « & » alors que vous souhaitiez réellement écrire « && ».

Une heuristique courante que nous apprenons en révisant le code est la suivante :

Les symboles «&» ou «|» utilisés dans une déclaration conditionnelle ne sont probablement pas intentionnels.

Dans cet article de blog, nous examinerons l'heuristique et identifierons les moyens permettant de détecter et de résoudre ce problème de codage.


Quel est le problème ? Les opérations bit à bit fonctionnent correctement avec les valeurs booléennes.


L'utilisation d'opérateurs bit à bit avec des booléens est tout à fait valide, Java ne signalera donc aucune erreur de syntaxe.

Si nous créons un test JUnit pour explorer une table de vérité à la fois pour Bitwise OR (|) et Bitwise AND (&), nous constaterons que les sorties de l'opérateur Bitwise correspondent à la table de vérité. Compte tenu de cela, nous pourrions penser que l'utilisation d'opérateurs Bitwise ne pose pas de problème.

Tableau de la vérité

Trois colonnes, une avec a, une avec b, et la dernière avec (a^b)


@Test
void BitwiseOperatorsAndTruthTable () {
Assertions.assertEquals (verdadero, verdadero y verdadero);
Assertions.assertEquals (falso, verdadero y falso);
Assertions.assertEquals (falso, falso y verdadero);
Assertions.assertEquals (falso, falso y falso);
}


Le test est réussi, ce Java est parfaitement valide.


Tableau de la vérité


Trois colonnes, une avec a, une avec b, et la dernière avec (a v b)


@Test
anular BitwiseOperatorSorTruthTable () {
Assertions.assertEquals (verdadero, verdadero | verdadero);
Assertions.assertEquals (verdadero, verdadero | falso);
Assertions.assertEquals (verdadero, falso | verdadero);
Assertions.assertEquals (falso, falso | falso);
}


Ce test est également réussi, pourquoi préférons-nous « && » et « || » ?


Les images du tableau de vérité ont été créées à l'aide de l' outil de table de vérité de web.standfor.edu.


Problème : Fonctionnement en court-circuit


Le véritable problème réside dans la différence de comportement entre les opérateurs bit à bit (&, |) et booléens (&&, ||).

Un opérateur booléen est un opérateur de court-circuit et n'évalue que ce qui est nécessaire.

par exemple

si (args! = nulo & args.length () > 23) {
System.out.println (argumentos);
}


Dans le code ci-dessus, les deux conditions booléennes seront évaluées, car l'opérateur Bitwise a été utilisé :

  • arguments ! = nul
  • args.length () > 23

Cela rend mon code vulnérable à une NullPointerException si args est nul, car nous vérifierons toujours args.length, même lorsque args est nul, car les deux conditions booléennes doivent être évaluées.


Évaluation des courts-circuits des opérateurs booléens


Lorsqu'on utilise un &&, par exemple.

si (args! = nulo && args.length () > 23) {
System.out.println (argumentos);
}


Dès que nous savons qu'il s'agit d'un argument = null évalué comme faux, l'évaluation de l'expression conditionnelle s'arrête.

Il n'est pas nécessaire d'évaluer le côté droit.

Quel que soit le résultat de la condition du côté droit, la valeur finale de l'expression booléenne sera fausse.


Cependant, cela ne se produirait jamais dans le code de production.


Il s'agit d'une erreur assez courante et les outils d'analyse statique ne la détectent pas systématiquement.

J'ai utilisé le Google Dork suivant pour voir si je pouvais trouver un exemple public de ce modèle :

Type de fichier : java si « ! = nulo & »
Cette recherche a renvoyé un code Android dans RootWindowContainer
isDocument = intención ! = nulo & intent.isDocument ()


Il s'agit d'un type de code susceptible de passer une révision de code, car nous utilisons souvent des opérateurs bit à bit dans les instructions d'affectation pour masquer les valeurs. Cependant, dans ce cas, le résultat est identique à celui de l'exemple précédent de l'instruction if. Si l'intention est parfois nulle, une NullPointerException sera déclenchée.

Nous parvenons souvent à nos fins avec cette construction, car nous codons souvent de manière défensive et écrivons du code redondant. La vérification « ! = null » peut s'avérer redondante dans la plupart des cas d'utilisation.

Il s'agit d'une erreur commise par les programmeurs dans le code de production.

Je ne sais pas si les résultats de la recherche sont à jour, mais lorsque je l'ai effectuée, les résultats suivants sont apparus : Google, Amazon, Apache... et moi.

Une récente demande d'extraction dans l'un de mes projets open source visait précisément à résoudre cette erreur.

si (escriba! =nulo y escribe.trim () .length () >0) {
Aceptar MediaTypeDefinitionsList.add (type.trim ());
}


Comment trouver ceci


Lorsque j'ai vérifié mon code d'exemple dans certains analyseurs statiques, aucun d'entre eux n'a détecté ce code caché d'autodestruction.

En tant qu'équipe Secure Code Warrior, nous avons élaboré et révisé une recette Sensei simple qui pourrait répondre à cette question.

Étant donné que les opérateurs bit à bit sont parfaitement valides et fréquemment utilisés dans les affectations, nous nous concentrons sur le cas d'utilisation des instructions if et sur l'utilisation de Bitwise & pour identifier le code problématique.

buscar:
expresión:
Cualquiera de:
- en:
condición: {}
valor:
Sensible a mayúsculas y minúsculas: falso
coincidencias: «.* & . *»


Ceci utilise une expression régulière pour correspondre à « & » lorsqu'elle est utilisée comme expression conditionnelle, par exemple dans une instruction if.

Pour résoudre ce problème, nous avons de nouveau utilisé des expressions régulières. Cette fois-ci, nous avons utilisé la fonction sed de QuickFix pour remplacer globalement le & de l'expression par &&.

Correcciones disponibles:
- nombre: «Reemplazar el operador AND bit a bit por el operador AND lógico»
acciones:
- reescribir:
a: «{{#sed}} s/&/&&/g, {{{.}}} {{/sed}}»


Remarques finales

Ceci couvre l'utilisation incorrecte la plus courante d'un opérateur bit à bit, c'est-à-dire lorsque l'on souhaitait en réalité utiliser un opérateur booléen.

Il existe d'autres situations dans lesquelles cela pourrait se produire, par exemple dans le cas d'une tâche, mais lorsque nous rédigeons des recettes, nous devons essayer d'éviter l'identification de faux positifs, sinon les recettes seront ignorées ou désactivées. Nous créons des recettes afin qu'elles correspondent aux occurrences les plus courantes. À mesure que Sensei , il est fort probable que nous ajoutions une spécificité supplémentaire à la fonction de recherche afin de couvrir davantage de conditions correspondantes.

Dans sa forme actuelle, cette recette permettrait d'identifier de nombreux cas d'utilisation actuels, et surtout celui qui a été signalé dans mon projet.

Remarque : Quelques contributeurs ont participé à cet exemple et à la révision des recettes : Charlie Eriksen, Matthieu Calie, Robin Claerhaut, Brysen Ackx, Nathan Desmet et Downey Robersscheuten. Nous vous remercions pour votre aide.


---


Vous pouvez installer Sensei IntelliJ via « Préférences\ Plugins » (Mac) ou « Configuration\ Plugins » (Windows), puis rechercher « code sécurisé de sensei

Nous disposons de nombreux codes sources et modèles pour ces articles de blog (y compris celui-ci) dans le référentiel «sensei » du compte GitHub de Secure Code Warrior.

https://github.com/securecodewarrior/sensei-blog-examples

Pour plus d'informations sur Sensei


Veuillez consulter la ressource
Veuillez consulter la ressource

Dans cet article de blog, nous examinons une erreur courante de codage en Java (l'utilisation d'un opérateur bit à bit au lieu d'un opérateur conditionnel), l'erreur qui rend notre code vulnérable et comment nous pouvons utiliser Sensei corriger et détecter le problème.

Souhaitez-vous en savoir davantage ?

Alan Richardson a plus de vingt ans d'expérience professionnelle dans le domaine des technologies de l'information. Il a travaillé en tant que développeur et à tous les niveaux de la hiérarchie des tests, du testeur au responsable des tests. Responsable des relations avec les développeurs à l'adresse Secure Code Warrior, il travaille directement avec les équipes pour améliorer le développement de codes sécurisés de qualité. Alan est l'auteur de quatre livres, dont "Dear Evil Tester" et "Java For Testers". Alan a également créé une formation en ligne courses pour aider les gens à apprendre les tests techniques sur le Web et Selenium WebDriver avec Java. Alan publie ses écrits et ses vidéos de formation sur SeleniumSimplified.com, EvilTester.com, JavaForTesters.com et CompendiumDev.co.uk.

En savoir plus

Secure Code Warrior là pour aider votre organisation à protéger le code tout au long du cycle de vie du développement logiciel et à créer une culture où la cybersécurité est une priorité. Que vous soyez administrateur AppSec, développeur, CISO ou toute autre personne impliquée dans la sécurité, nous pouvons aider votre organisation à réduire les risques associés à un code non sécurisé.

Veuillez réserver une démonstration.
Partager sur :
marques LinkedInSocialLogo x
auteur
Alan Richardson
Publié le 07 février 2021

Alan Richardson a plus de vingt ans d'expérience professionnelle dans le domaine des technologies de l'information. Il a travaillé en tant que développeur et à tous les niveaux de la hiérarchie des tests, du testeur au responsable des tests. Responsable des relations avec les développeurs à l'adresse Secure Code Warrior, il travaille directement avec les équipes pour améliorer le développement de codes sécurisés de qualité. Alan est l'auteur de quatre livres, dont "Dear Evil Tester" et "Java For Testers". Alan a également créé une formation en ligne courses pour aider les gens à apprendre les tests techniques sur le Web et Selenium WebDriver avec Java. Alan publie ses écrits et ses vidéos de formation sur SeleniumSimplified.com, EvilTester.com, JavaForTesters.com et CompendiumDev.co.uk.

Partager sur :
marques LinkedInSocialLogo x

Les erreurs Java : opérateurs bit à bit et opérateurs booléens

« Java Gotcha » : un modèle d'erreur courant qui peut être facilement mis en œuvre de manière involontaire.

Une astuce Java assez simple dans laquelle on peut tomber accidentellement consiste à utiliser un opérateur bit à bit au lieu d'un opérateur de comparaison booléen.

Par exemple, une simple erreur de frappe peut entraîner l'écriture de « & » alors que vous souhaitiez réellement écrire « && ».

Une heuristique courante que nous apprenons en révisant le code est la suivante :

Les symboles «&» ou «|» utilisés dans une déclaration conditionnelle ne sont probablement pas intentionnels.

Dans cet article de blog, nous examinerons l'heuristique et identifierons les moyens permettant de détecter et de résoudre ce problème de codage.


Quel est le problème ? Les opérations bit à bit fonctionnent correctement avec les valeurs booléennes.


L'utilisation d'opérateurs bit à bit avec des booléens est tout à fait valide, Java ne signalera donc aucune erreur de syntaxe.

Si nous créons un test JUnit pour explorer une table de vérité à la fois pour Bitwise OR (|) et Bitwise AND (&), nous constaterons que les sorties de l'opérateur Bitwise correspondent à la table de vérité. Compte tenu de cela, nous pourrions penser que l'utilisation d'opérateurs Bitwise ne pose pas de problème.

Tableau de la vérité

Trois colonnes, une avec a, une avec b, et la dernière avec (a^b)


@Test
void BitwiseOperatorsAndTruthTable () {
Assertions.assertEquals (verdadero, verdadero y verdadero);
Assertions.assertEquals (falso, verdadero y falso);
Assertions.assertEquals (falso, falso y verdadero);
Assertions.assertEquals (falso, falso y falso);
}


Le test est réussi, ce Java est parfaitement valide.


Tableau de la vérité


Trois colonnes, une avec a, une avec b, et la dernière avec (a v b)


@Test
anular BitwiseOperatorSorTruthTable () {
Assertions.assertEquals (verdadero, verdadero | verdadero);
Assertions.assertEquals (verdadero, verdadero | falso);
Assertions.assertEquals (verdadero, falso | verdadero);
Assertions.assertEquals (falso, falso | falso);
}


Ce test est également réussi, pourquoi préférons-nous « && » et « || » ?


Les images du tableau de vérité ont été créées à l'aide de l' outil de table de vérité de web.standfor.edu.


Problème : Fonctionnement en court-circuit


Le véritable problème réside dans la différence de comportement entre les opérateurs bit à bit (&, |) et booléens (&&, ||).

Un opérateur booléen est un opérateur de court-circuit et n'évalue que ce qui est nécessaire.

par exemple

si (args! = nulo & args.length () > 23) {
System.out.println (argumentos);
}


Dans le code ci-dessus, les deux conditions booléennes seront évaluées, car l'opérateur Bitwise a été utilisé :

  • arguments ! = nul
  • args.length () > 23

Cela rend mon code vulnérable à une NullPointerException si args est nul, car nous vérifierons toujours args.length, même lorsque args est nul, car les deux conditions booléennes doivent être évaluées.


Évaluation des courts-circuits des opérateurs booléens


Lorsqu'on utilise un &&, par exemple.

si (args! = nulo && args.length () > 23) {
System.out.println (argumentos);
}


Dès que nous savons qu'il s'agit d'un argument = null évalué comme faux, l'évaluation de l'expression conditionnelle s'arrête.

Il n'est pas nécessaire d'évaluer le côté droit.

Quel que soit le résultat de la condition du côté droit, la valeur finale de l'expression booléenne sera fausse.


Cependant, cela ne se produirait jamais dans le code de production.


Il s'agit d'une erreur assez courante et les outils d'analyse statique ne la détectent pas systématiquement.

J'ai utilisé le Google Dork suivant pour voir si je pouvais trouver un exemple public de ce modèle :

Type de fichier : java si « ! = nulo & »
Cette recherche a renvoyé un code Android dans RootWindowContainer
isDocument = intención ! = nulo & intent.isDocument ()


Il s'agit d'un type de code susceptible de passer une révision de code, car nous utilisons souvent des opérateurs bit à bit dans les instructions d'affectation pour masquer les valeurs. Cependant, dans ce cas, le résultat est identique à celui de l'exemple précédent de l'instruction if. Si l'intention est parfois nulle, une NullPointerException sera déclenchée.

Nous parvenons souvent à nos fins avec cette construction, car nous codons souvent de manière défensive et écrivons du code redondant. La vérification « ! = null » peut s'avérer redondante dans la plupart des cas d'utilisation.

Il s'agit d'une erreur commise par les programmeurs dans le code de production.

Je ne sais pas si les résultats de la recherche sont à jour, mais lorsque je l'ai effectuée, les résultats suivants sont apparus : Google, Amazon, Apache... et moi.

Une récente demande d'extraction dans l'un de mes projets open source visait précisément à résoudre cette erreur.

si (escriba! =nulo y escribe.trim () .length () >0) {
Aceptar MediaTypeDefinitionsList.add (type.trim ());
}


Comment trouver ceci


Lorsque j'ai vérifié mon code d'exemple dans certains analyseurs statiques, aucun d'entre eux n'a détecté ce code caché d'autodestruction.

En tant qu'équipe Secure Code Warrior, nous avons élaboré et révisé une recette Sensei simple qui pourrait répondre à cette question.

Étant donné que les opérateurs bit à bit sont parfaitement valides et fréquemment utilisés dans les affectations, nous nous concentrons sur le cas d'utilisation des instructions if et sur l'utilisation de Bitwise & pour identifier le code problématique.

buscar:
expresión:
Cualquiera de:
- en:
condición: {}
valor:
Sensible a mayúsculas y minúsculas: falso
coincidencias: «.* & . *»


Ceci utilise une expression régulière pour correspondre à « & » lorsqu'elle est utilisée comme expression conditionnelle, par exemple dans une instruction if.

Pour résoudre ce problème, nous avons de nouveau utilisé des expressions régulières. Cette fois-ci, nous avons utilisé la fonction sed de QuickFix pour remplacer globalement le & de l'expression par &&.

Correcciones disponibles:
- nombre: «Reemplazar el operador AND bit a bit por el operador AND lógico»
acciones:
- reescribir:
a: «{{#sed}} s/&/&&/g, {{{.}}} {{/sed}}»


Remarques finales

Ceci couvre l'utilisation incorrecte la plus courante d'un opérateur bit à bit, c'est-à-dire lorsque l'on souhaitait en réalité utiliser un opérateur booléen.

Il existe d'autres situations dans lesquelles cela pourrait se produire, par exemple dans le cas d'une tâche, mais lorsque nous rédigeons des recettes, nous devons essayer d'éviter l'identification de faux positifs, sinon les recettes seront ignorées ou désactivées. Nous créons des recettes afin qu'elles correspondent aux occurrences les plus courantes. À mesure que Sensei , il est fort probable que nous ajoutions une spécificité supplémentaire à la fonction de recherche afin de couvrir davantage de conditions correspondantes.

Dans sa forme actuelle, cette recette permettrait d'identifier de nombreux cas d'utilisation actuels, et surtout celui qui a été signalé dans mon projet.

Remarque : Quelques contributeurs ont participé à cet exemple et à la révision des recettes : Charlie Eriksen, Matthieu Calie, Robin Claerhaut, Brysen Ackx, Nathan Desmet et Downey Robersscheuten. Nous vous remercions pour votre aide.


---


Vous pouvez installer Sensei IntelliJ via « Préférences\ Plugins » (Mac) ou « Configuration\ Plugins » (Windows), puis rechercher « code sécurisé de sensei

Nous disposons de nombreux codes sources et modèles pour ces articles de blog (y compris celui-ci) dans le référentiel «sensei » du compte GitHub de Secure Code Warrior.

https://github.com/securecodewarrior/sensei-blog-examples

Pour plus d'informations sur Sensei


Veuillez consulter la ressource
Veuillez consulter la ressource

Veuillez remplir le formulaire suivant pour télécharger le rapport.

Nous souhaiterions obtenir votre autorisation pour vous envoyer des informations sur nos produits ou sur des sujets liés au codage sécurisé. Nous traiterons toujours vos données personnelles avec le plus grand soin et ne les vendrons jamais à d'autres entreprises à des fins de marketing.

Envoyer
icône de réussite scw
icône d'erreur scw
Pour envoyer le formulaire, veuillez activer les cookies « d'analyse ». N'hésitez pas à les désactiver à nouveau une fois que vous avez terminé.

Les erreurs Java : opérateurs bit à bit et opérateurs booléens

« Java Gotcha » : un modèle d'erreur courant qui peut être facilement mis en œuvre de manière involontaire.

Une astuce Java assez simple dans laquelle on peut tomber accidentellement consiste à utiliser un opérateur bit à bit au lieu d'un opérateur de comparaison booléen.

Par exemple, une simple erreur de frappe peut entraîner l'écriture de « & » alors que vous souhaitiez réellement écrire « && ».

Une heuristique courante que nous apprenons en révisant le code est la suivante :

Les symboles «&» ou «|» utilisés dans une déclaration conditionnelle ne sont probablement pas intentionnels.

Dans cet article de blog, nous examinerons l'heuristique et identifierons les moyens permettant de détecter et de résoudre ce problème de codage.


Quel est le problème ? Les opérations bit à bit fonctionnent correctement avec les valeurs booléennes.


L'utilisation d'opérateurs bit à bit avec des booléens est tout à fait valide, Java ne signalera donc aucune erreur de syntaxe.

Si nous créons un test JUnit pour explorer une table de vérité à la fois pour Bitwise OR (|) et Bitwise AND (&), nous constaterons que les sorties de l'opérateur Bitwise correspondent à la table de vérité. Compte tenu de cela, nous pourrions penser que l'utilisation d'opérateurs Bitwise ne pose pas de problème.

Tableau de la vérité

Trois colonnes, une avec a, une avec b, et la dernière avec (a^b)


@Test
void BitwiseOperatorsAndTruthTable () {
Assertions.assertEquals (verdadero, verdadero y verdadero);
Assertions.assertEquals (falso, verdadero y falso);
Assertions.assertEquals (falso, falso y verdadero);
Assertions.assertEquals (falso, falso y falso);
}


Le test est réussi, ce Java est parfaitement valide.


Tableau de la vérité


Trois colonnes, une avec a, une avec b, et la dernière avec (a v b)


@Test
anular BitwiseOperatorSorTruthTable () {
Assertions.assertEquals (verdadero, verdadero | verdadero);
Assertions.assertEquals (verdadero, verdadero | falso);
Assertions.assertEquals (verdadero, falso | verdadero);
Assertions.assertEquals (falso, falso | falso);
}


Ce test est également réussi, pourquoi préférons-nous « && » et « || » ?


Les images du tableau de vérité ont été créées à l'aide de l' outil de table de vérité de web.standfor.edu.


Problème : Fonctionnement en court-circuit


Le véritable problème réside dans la différence de comportement entre les opérateurs bit à bit (&, |) et booléens (&&, ||).

Un opérateur booléen est un opérateur de court-circuit et n'évalue que ce qui est nécessaire.

par exemple

si (args! = nulo & args.length () > 23) {
System.out.println (argumentos);
}


Dans le code ci-dessus, les deux conditions booléennes seront évaluées, car l'opérateur Bitwise a été utilisé :

  • arguments ! = nul
  • args.length () > 23

Cela rend mon code vulnérable à une NullPointerException si args est nul, car nous vérifierons toujours args.length, même lorsque args est nul, car les deux conditions booléennes doivent être évaluées.


Évaluation des courts-circuits des opérateurs booléens


Lorsqu'on utilise un &&, par exemple.

si (args! = nulo && args.length () > 23) {
System.out.println (argumentos);
}


Dès que nous savons qu'il s'agit d'un argument = null évalué comme faux, l'évaluation de l'expression conditionnelle s'arrête.

Il n'est pas nécessaire d'évaluer le côté droit.

Quel que soit le résultat de la condition du côté droit, la valeur finale de l'expression booléenne sera fausse.


Cependant, cela ne se produirait jamais dans le code de production.


Il s'agit d'une erreur assez courante et les outils d'analyse statique ne la détectent pas systématiquement.

J'ai utilisé le Google Dork suivant pour voir si je pouvais trouver un exemple public de ce modèle :

Type de fichier : java si « ! = nulo & »
Cette recherche a renvoyé un code Android dans RootWindowContainer
isDocument = intención ! = nulo & intent.isDocument ()


Il s'agit d'un type de code susceptible de passer une révision de code, car nous utilisons souvent des opérateurs bit à bit dans les instructions d'affectation pour masquer les valeurs. Cependant, dans ce cas, le résultat est identique à celui de l'exemple précédent de l'instruction if. Si l'intention est parfois nulle, une NullPointerException sera déclenchée.

Nous parvenons souvent à nos fins avec cette construction, car nous codons souvent de manière défensive et écrivons du code redondant. La vérification « ! = null » peut s'avérer redondante dans la plupart des cas d'utilisation.

Il s'agit d'une erreur commise par les programmeurs dans le code de production.

Je ne sais pas si les résultats de la recherche sont à jour, mais lorsque je l'ai effectuée, les résultats suivants sont apparus : Google, Amazon, Apache... et moi.

Une récente demande d'extraction dans l'un de mes projets open source visait précisément à résoudre cette erreur.

si (escriba! =nulo y escribe.trim () .length () >0) {
Aceptar MediaTypeDefinitionsList.add (type.trim ());
}


Comment trouver ceci


Lorsque j'ai vérifié mon code d'exemple dans certains analyseurs statiques, aucun d'entre eux n'a détecté ce code caché d'autodestruction.

En tant qu'équipe Secure Code Warrior, nous avons élaboré et révisé une recette Sensei simple qui pourrait répondre à cette question.

Étant donné que les opérateurs bit à bit sont parfaitement valides et fréquemment utilisés dans les affectations, nous nous concentrons sur le cas d'utilisation des instructions if et sur l'utilisation de Bitwise & pour identifier le code problématique.

buscar:
expresión:
Cualquiera de:
- en:
condición: {}
valor:
Sensible a mayúsculas y minúsculas: falso
coincidencias: «.* & . *»


Ceci utilise une expression régulière pour correspondre à « & » lorsqu'elle est utilisée comme expression conditionnelle, par exemple dans une instruction if.

Pour résoudre ce problème, nous avons de nouveau utilisé des expressions régulières. Cette fois-ci, nous avons utilisé la fonction sed de QuickFix pour remplacer globalement le & de l'expression par &&.

Correcciones disponibles:
- nombre: «Reemplazar el operador AND bit a bit por el operador AND lógico»
acciones:
- reescribir:
a: «{{#sed}} s/&/&&/g, {{{.}}} {{/sed}}»


Remarques finales

Ceci couvre l'utilisation incorrecte la plus courante d'un opérateur bit à bit, c'est-à-dire lorsque l'on souhaitait en réalité utiliser un opérateur booléen.

Il existe d'autres situations dans lesquelles cela pourrait se produire, par exemple dans le cas d'une tâche, mais lorsque nous rédigeons des recettes, nous devons essayer d'éviter l'identification de faux positifs, sinon les recettes seront ignorées ou désactivées. Nous créons des recettes afin qu'elles correspondent aux occurrences les plus courantes. À mesure que Sensei , il est fort probable que nous ajoutions une spécificité supplémentaire à la fonction de recherche afin de couvrir davantage de conditions correspondantes.

Dans sa forme actuelle, cette recette permettrait d'identifier de nombreux cas d'utilisation actuels, et surtout celui qui a été signalé dans mon projet.

Remarque : Quelques contributeurs ont participé à cet exemple et à la révision des recettes : Charlie Eriksen, Matthieu Calie, Robin Claerhaut, Brysen Ackx, Nathan Desmet et Downey Robersscheuten. Nous vous remercions pour votre aide.


---


Vous pouvez installer Sensei IntelliJ via « Préférences\ Plugins » (Mac) ou « Configuration\ Plugins » (Windows), puis rechercher « code sécurisé de sensei

Nous disposons de nombreux codes sources et modèles pour ces articles de blog (y compris celui-ci) dans le référentiel «sensei » du compte GitHub de Secure Code Warrior.

https://github.com/securecodewarrior/sensei-blog-examples

Pour plus d'informations sur Sensei


Veuillez consulter le webinaire
Commencer
En savoir plus

Veuillez cliquer sur le lien ci-dessous et télécharger le PDF de cette ressource.

Secure Code Warrior là pour aider votre organisation à protéger le code tout au long du cycle de vie du développement logiciel et à créer une culture où la cybersécurité est une priorité. Que vous soyez administrateur AppSec, développeur, CISO ou toute autre personne impliquée dans la sécurité, nous pouvons aider votre organisation à réduire les risques associés à un code non sécurisé.

Veuillez consulter le rapportVeuillez réserver une démonstration.
Télécharger le PDF
Veuillez consulter la ressource
Partager sur :
marques LinkedInSocialLogo x
Souhaitez-vous en savoir davantage ?

Partager sur :
marques LinkedInSocialLogo x
auteur
Alan Richardson
Publié le 07 février 2021

Alan Richardson a plus de vingt ans d'expérience professionnelle dans le domaine des technologies de l'information. Il a travaillé en tant que développeur et à tous les niveaux de la hiérarchie des tests, du testeur au responsable des tests. Responsable des relations avec les développeurs à l'adresse Secure Code Warrior, il travaille directement avec les équipes pour améliorer le développement de codes sécurisés de qualité. Alan est l'auteur de quatre livres, dont "Dear Evil Tester" et "Java For Testers". Alan a également créé une formation en ligne courses pour aider les gens à apprendre les tests techniques sur le Web et Selenium WebDriver avec Java. Alan publie ses écrits et ses vidéos de formation sur SeleniumSimplified.com, EvilTester.com, JavaForTesters.com et CompendiumDev.co.uk.

Partager sur :
marques LinkedInSocialLogo x

Les erreurs Java : opérateurs bit à bit et opérateurs booléens

« Java Gotcha » : un modèle d'erreur courant qui peut être facilement mis en œuvre de manière involontaire.

Une astuce Java assez simple dans laquelle on peut tomber accidentellement consiste à utiliser un opérateur bit à bit au lieu d'un opérateur de comparaison booléen.

Par exemple, une simple erreur de frappe peut entraîner l'écriture de « & » alors que vous souhaitiez réellement écrire « && ».

Une heuristique courante que nous apprenons en révisant le code est la suivante :

Les symboles «&» ou «|» utilisés dans une déclaration conditionnelle ne sont probablement pas intentionnels.

Dans cet article de blog, nous examinerons l'heuristique et identifierons les moyens permettant de détecter et de résoudre ce problème de codage.


Quel est le problème ? Les opérations bit à bit fonctionnent correctement avec les valeurs booléennes.


L'utilisation d'opérateurs bit à bit avec des booléens est tout à fait valide, Java ne signalera donc aucune erreur de syntaxe.

Si nous créons un test JUnit pour explorer une table de vérité à la fois pour Bitwise OR (|) et Bitwise AND (&), nous constaterons que les sorties de l'opérateur Bitwise correspondent à la table de vérité. Compte tenu de cela, nous pourrions penser que l'utilisation d'opérateurs Bitwise ne pose pas de problème.

Tableau de la vérité

Trois colonnes, une avec a, une avec b, et la dernière avec (a^b)


@Test
void BitwiseOperatorsAndTruthTable () {
Assertions.assertEquals (verdadero, verdadero y verdadero);
Assertions.assertEquals (falso, verdadero y falso);
Assertions.assertEquals (falso, falso y verdadero);
Assertions.assertEquals (falso, falso y falso);
}


Le test est réussi, ce Java est parfaitement valide.


Tableau de la vérité


Trois colonnes, une avec a, une avec b, et la dernière avec (a v b)


@Test
anular BitwiseOperatorSorTruthTable () {
Assertions.assertEquals (verdadero, verdadero | verdadero);
Assertions.assertEquals (verdadero, verdadero | falso);
Assertions.assertEquals (verdadero, falso | verdadero);
Assertions.assertEquals (falso, falso | falso);
}


Ce test est également réussi, pourquoi préférons-nous « && » et « || » ?


Les images du tableau de vérité ont été créées à l'aide de l' outil de table de vérité de web.standfor.edu.


Problème : Fonctionnement en court-circuit


Le véritable problème réside dans la différence de comportement entre les opérateurs bit à bit (&, |) et booléens (&&, ||).

Un opérateur booléen est un opérateur de court-circuit et n'évalue que ce qui est nécessaire.

par exemple

si (args! = nulo & args.length () > 23) {
System.out.println (argumentos);
}


Dans le code ci-dessus, les deux conditions booléennes seront évaluées, car l'opérateur Bitwise a été utilisé :

  • arguments ! = nul
  • args.length () > 23

Cela rend mon code vulnérable à une NullPointerException si args est nul, car nous vérifierons toujours args.length, même lorsque args est nul, car les deux conditions booléennes doivent être évaluées.


Évaluation des courts-circuits des opérateurs booléens


Lorsqu'on utilise un &&, par exemple.

si (args! = nulo && args.length () > 23) {
System.out.println (argumentos);
}


Dès que nous savons qu'il s'agit d'un argument = null évalué comme faux, l'évaluation de l'expression conditionnelle s'arrête.

Il n'est pas nécessaire d'évaluer le côté droit.

Quel que soit le résultat de la condition du côté droit, la valeur finale de l'expression booléenne sera fausse.


Cependant, cela ne se produirait jamais dans le code de production.


Il s'agit d'une erreur assez courante et les outils d'analyse statique ne la détectent pas systématiquement.

J'ai utilisé le Google Dork suivant pour voir si je pouvais trouver un exemple public de ce modèle :

Type de fichier : java si « ! = nulo & »
Cette recherche a renvoyé un code Android dans RootWindowContainer
isDocument = intención ! = nulo & intent.isDocument ()


Il s'agit d'un type de code susceptible de passer une révision de code, car nous utilisons souvent des opérateurs bit à bit dans les instructions d'affectation pour masquer les valeurs. Cependant, dans ce cas, le résultat est identique à celui de l'exemple précédent de l'instruction if. Si l'intention est parfois nulle, une NullPointerException sera déclenchée.

Nous parvenons souvent à nos fins avec cette construction, car nous codons souvent de manière défensive et écrivons du code redondant. La vérification « ! = null » peut s'avérer redondante dans la plupart des cas d'utilisation.

Il s'agit d'une erreur commise par les programmeurs dans le code de production.

Je ne sais pas si les résultats de la recherche sont à jour, mais lorsque je l'ai effectuée, les résultats suivants sont apparus : Google, Amazon, Apache... et moi.

Une récente demande d'extraction dans l'un de mes projets open source visait précisément à résoudre cette erreur.

si (escriba! =nulo y escribe.trim () .length () >0) {
Aceptar MediaTypeDefinitionsList.add (type.trim ());
}


Comment trouver ceci


Lorsque j'ai vérifié mon code d'exemple dans certains analyseurs statiques, aucun d'entre eux n'a détecté ce code caché d'autodestruction.

En tant qu'équipe Secure Code Warrior, nous avons élaboré et révisé une recette Sensei simple qui pourrait répondre à cette question.

Étant donné que les opérateurs bit à bit sont parfaitement valides et fréquemment utilisés dans les affectations, nous nous concentrons sur le cas d'utilisation des instructions if et sur l'utilisation de Bitwise & pour identifier le code problématique.

buscar:
expresión:
Cualquiera de:
- en:
condición: {}
valor:
Sensible a mayúsculas y minúsculas: falso
coincidencias: «.* & . *»


Ceci utilise une expression régulière pour correspondre à « & » lorsqu'elle est utilisée comme expression conditionnelle, par exemple dans une instruction if.

Pour résoudre ce problème, nous avons de nouveau utilisé des expressions régulières. Cette fois-ci, nous avons utilisé la fonction sed de QuickFix pour remplacer globalement le & de l'expression par &&.

Correcciones disponibles:
- nombre: «Reemplazar el operador AND bit a bit por el operador AND lógico»
acciones:
- reescribir:
a: «{{#sed}} s/&/&&/g, {{{.}}} {{/sed}}»


Remarques finales

Ceci couvre l'utilisation incorrecte la plus courante d'un opérateur bit à bit, c'est-à-dire lorsque l'on souhaitait en réalité utiliser un opérateur booléen.

Il existe d'autres situations dans lesquelles cela pourrait se produire, par exemple dans le cas d'une tâche, mais lorsque nous rédigeons des recettes, nous devons essayer d'éviter l'identification de faux positifs, sinon les recettes seront ignorées ou désactivées. Nous créons des recettes afin qu'elles correspondent aux occurrences les plus courantes. À mesure que Sensei , il est fort probable que nous ajoutions une spécificité supplémentaire à la fonction de recherche afin de couvrir davantage de conditions correspondantes.

Dans sa forme actuelle, cette recette permettrait d'identifier de nombreux cas d'utilisation actuels, et surtout celui qui a été signalé dans mon projet.

Remarque : Quelques contributeurs ont participé à cet exemple et à la révision des recettes : Charlie Eriksen, Matthieu Calie, Robin Claerhaut, Brysen Ackx, Nathan Desmet et Downey Robersscheuten. Nous vous remercions pour votre aide.


---


Vous pouvez installer Sensei IntelliJ via « Préférences\ Plugins » (Mac) ou « Configuration\ Plugins » (Windows), puis rechercher « code sécurisé de sensei

Nous disposons de nombreux codes sources et modèles pour ces articles de blog (y compris celui-ci) dans le référentiel «sensei » du compte GitHub de Secure Code Warrior.

https://github.com/securecodewarrior/sensei-blog-examples

Pour plus d'informations sur Sensei


Table des matières

Télécharger le PDF
Veuillez consulter la ressource
Souhaitez-vous en savoir davantage ?

Alan Richardson a plus de vingt ans d'expérience professionnelle dans le domaine des technologies de l'information. Il a travaillé en tant que développeur et à tous les niveaux de la hiérarchie des tests, du testeur au responsable des tests. Responsable des relations avec les développeurs à l'adresse Secure Code Warrior, il travaille directement avec les équipes pour améliorer le développement de codes sécurisés de qualité. Alan est l'auteur de quatre livres, dont "Dear Evil Tester" et "Java For Testers". Alan a également créé une formation en ligne courses pour aider les gens à apprendre les tests techniques sur le Web et Selenium WebDriver avec Java. Alan publie ses écrits et ses vidéos de formation sur SeleniumSimplified.com, EvilTester.com, JavaForTesters.com et CompendiumDev.co.uk.

En savoir plus

Secure Code Warrior là pour aider votre organisation à protéger le code tout au long du cycle de vie du développement logiciel et à créer une culture où la cybersécurité est une priorité. Que vous soyez administrateur AppSec, développeur, CISO ou toute autre personne impliquée dans la sécurité, nous pouvons aider votre organisation à réduire les risques associés à un code non sécurisé.

Veuillez réserver une démonstration.Télécharger
Partager sur :
marques LinkedInSocialLogo x
Centre de ressources

Ressources pour débuter

Plus de publications
Centre de ressources

Ressources pour débuter

Plus de publications