PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps
Nous continuons à faciliter l'utilisation de PVS-Studio. Désormais, notre analyseur est disponible dans Chocolatey, le gestionnaire de paquets pour Windows. Nous pensons que cela simplifiera le déploiement de PVS-Studio, notamment dans les services cloud. Pour ne pas aller loin, vérifions le code source de Chocolatey. Azure DevOps servira de systÚme CI.

Voici une liste de nos autres articles sur l'intégration avec des systÚmes cloud :

Je vous conseille de prĂȘter attention au premier article sur l'intĂ©gration avec Azure DevOps, car certains points y sont omis pour Ă©viter les doublons.

Ainsi, les héros de cet article sont :

PVS-Studio — un outil d'analyse statique du code, conçu pour identifier les erreurs et les vulnĂ©rabilitĂ©s potentielles dans des programmes Ă©crits en C, C++, C# et Java. Il fonctionne sur des systĂšmes 64 bits sous Windows, Linux et macOS, et peut analyser du code destinĂ© aux plateformes ARM 32 bits, 64 bits et embarquĂ©es. Si vous essayez l'analyse statique du code pour la premiĂšre fois sur vos projets, nous vous recommandons de consulter mais la syntaxe des requĂȘtes y est ancienne, il faut en tenir compte. sur la façon de visualiser rapidement les avertissements intĂ©ressants de PVS-Studio et d'Ă©valuer les capacitĂ©s de cet outil.

Azure DevOps — un ensemble de services cloud qui couvre tout le processus de dĂ©veloppement. Cette plateforme comprend des outils tels que Azure Pipelines, Azure Boards, Azure Artifacts, Azure Repos, et Azure Test Plans, permettant d'accĂ©lĂ©rer le processus de crĂ©ation de logiciels et d'en amĂ©liorer la qualitĂ©.

Chocolatey – un gestionnaire de paquets open source pour Windows. L'objectif du projet est d'automatiser l'ensemble du cycle de vie des logiciels, de l'installation à la mise à jour et à la suppression, sous les systùmes d'exploitation Windows.

Sur l'utilisation de Chocolatey

Vous pouvez voir comment installer le gestionnaire de paquets lui-mĂȘme Ă  partir de cette le lien. La documentation complĂšte sur l'installation de l'analyseur est disponible le lien dans la section « Installation Ă  l'aide du gestionnaire de paquets Chocolatey ». Je vais briĂšvement rappeler certains points de lĂ -bas.

Commande pour installer la derniĂšre version de l'analyseur :

choco install pvs-studio

Commande pour installer une version spécifique du paquet PVS-Studio :

choco install pvs-studio --version=7.05.35617.2075

Par dĂ©faut, seul le noyau de l'analyseur - le composant Core - est installĂ©. Tous les autres indicateurs (Standalone, JavaCore, IDEA, MSVS2010, MSVS2012, MSVS2013, MSVS2015, MSVS2017, MSVS2019) peuvent ĂȘtre passĂ©s Ă  l'aide de —package-parameters.

Voici un exemple de commande qui installera l'analyseur avec le plugin pour Visual Studio 2019 :

choco install pvs-studio --package-parameters="'\/MSVS2019'"

Voyons maintenant un exemple d'utilisation pratique de l'analyseur sous Azure DevOps.

Configuration

Je rappelle que des points comme l'enregistrement d'un compte, la création d'un pipeline de construction et la synchronisation du compte avec le projet dans le dépÎt sur GitHub sont abordés dans un document séparé. article. Notre configuration commencera directement par l'écriture du fichier de configuration.

Pour commencer, configurons le déclencheur d'exécution en indiquant que nous ne lançons que pour les modifications dans master la branche :

trigger:
- master

Ensuite, nous devons choisir une machine virtuelle. Pour le moment, ce sera un agent hébergé par Microsoft avec Windows Server 2019 et Visual Studio 2019 :

pool:
  vmImage: 'windows-latest'

Passons au corps du fichier de configuration (bloc steps). Bien qu'il ne soit pas possible d'installer des logiciels arbitraires sur la machine virtuelle, je n'ai pas ajoutĂ© de conteneur Docker. Nous pouvons ajouter Chocolatey en tant qu'extension pour Azure DevOps. Pour cela, allons Ă  le lien. Cliquez sur Get it free. Ensuite, si vous ĂȘtes dĂ©jĂ  connectĂ©, il vous suffit de choisir votre compte, sinon, suivez la mĂȘme procĂ©dure aprĂšs vous ĂȘtre connectĂ©.

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

Ici, vous devez choisir oĂč nous ajouterons l'extension, puis appuyer sur le bouton Installer.

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

AprÚs l'installation réussie, cliquons sur Proceed to organization:

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

Vous pouvez maintenant voir le modĂšle de tĂąche Chocolatey dans la fenĂȘtre tasks lors de l'Ă©dition du fichier de configuration azure-pipelines.yml :

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

Cliquons sur Chocolatey et verrons la liste des champs :

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

Ici, nous devons sélectionner install dans le champ des commandes. Dans Nuspec File Name nous spécifions le nom du package souhaité - pvs-studio. Si nous ne spécifions pas de version, c'est la derniÚre qui sera installée, ce qui nous convient parfaitement. Cliquons sur le bouton add et nous verrons la tùche générée dans le fichier de configuration.

steps:
- task: ChocolateyCommand@0
  inputs:
    command: 'install'
    installPackageId: 'pvs-studio'

Passons maintenant Ă  la partie principale de notre fichier :

- task: CmdLine@2
  inputs:
    script : 

Nous devons maintenant crĂ©er un fichier avec la licence de l'analyseur. Ici PVSNAME et PVSKEY – sont les noms des variables dont nous spĂ©cifions les valeurs dans les paramĂštres. Elles stockeront le login et la clĂ© de licence de PVS-Studio. Pour dĂ©finir leurs valeurs, ouvrons le menu Variables->New variable. CrĂ©ons des variables PVSNAME pour le login et PVSKEY pour la clĂ© de l'analyseur. N'oubliez pas de cocher la case Gardez cette valeur secrĂšte pour PVSKEY. Code de la commande :

call "C:Program Files (x86)PVS-StudioPVS-Studio_Cmd.exe" credentials 
–u $(PVSNAME) –n $(PVSKEY)

Nous allons rassembler le projet à l'aide du fichier bat situé dans le référentiel :

call build.bat

CrĂ©ons un dossier oĂč seront stockĂ©s les fichiers contenant les rĂ©sultats du travail de l'analyseur :

call mkdir PVSTestResults

Lançons l'analyse du projet :

call "C:Program Files (x86)PVS-StudioPVS-Studio_Cmd.exe" 
–t .srcchocolatey.sln –o .PVSTestResultsChoco.plog 

Convertissons notre rapport au format html en utilisant l'utilitaire PlogConverter :

call "C:Program Files (x86)PVS-StudioPlogConverter.exe" 
–t html –o PVSTestResults .PVSTestResultsChoco.plog

Nous devons maintenant créer une tùche afin de pouvoir télécharger le rapport.

- task: PublishBuildArtifacts@1
  inputs:
    pathToPublish: PVSTestResults
    artifactName: PVSTestResults
    condition: always()

Le fichier de configuration complet ressemble Ă  ceci :

trigger:
- master

pool:
  vmImage: 'windows-latest'

steps:
- task: ChocolateyCommand@0
  inputs:
    command: 'install'
    installPackageId: 'pvs-studio'

- task: CmdLine@2
  inputs:
    script: |
      call "C:Program Files (x86)PVS-StudioPVS-Studio_Cmd.exe" 
      credentials –u $(PVSNAME) –n $(PVSKEY)
      call build.bat
      call mkdir PVSTestResults
      call "C:Program Files (x86)PVS-StudioPVS-Studio_Cmd.exe" 
      –t .srcchocolatey.sln –o .PVSTestResultsChoco.plog
      call "C:Program Files (x86)PVS-StudioPlogConverter.exe" 
      –t html –o .PVSTestResults .PVSTestResultsChoco.plog

- task: PublishBuildArtifacts@1
  inputs:
    pathToPublish: PVSTestResults
    artifactName: PVSTestResults
    condition: always()

Cliquez sur Enregistrer->Enregistrer->Exécuter pour exécuter la tùche. Nous téléchargerons le rapport en accédant à l'onglet des tùches.

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

Le projet Chocolatey contient un total de 37615 lignes de code C#. Examinons certaines des erreurs trouvées.

Résultats de l'analyse

Avertissement N1

Avertissement de l'analyseur : V3005 La variable ‘Provider’ est assignĂ©e Ă  elle-mĂȘme. CrytpoHashProviderSpecs.cs 38

public abstract class CrytpoHashProviderSpecsBase : TinySpec
{
  ....
  protected CryptoHashProvider Provider;
  ....
  public override void Context()
  {
    Provider = Provider = new CryptoHashProvider(FileSystem.Object);
  }
}

L'analyseur a dĂ©tectĂ© qu'une variable est assignĂ©e Ă  elle-mĂȘme, ce qui n'a pas de sens. Il est probable qu'Ă  la place de l'une de ces variables, une autre devrait ĂȘtre utilisĂ©e. Ou alors, c'est une faute de frappe, et l'assignation superflue peut tout simplement ĂȘtre supprimĂ©e.

Avertissement N2

Avertissement de l'analyseur : V3093 [CWE-480] L'opĂ©rateur ‘&’ Ă©value les deux opĂ©randes. Peut-ĂȘtre qu'un opĂ©rateur ‘&&’ Ă  court-circuit devrait ĂȘtre utilisĂ© Ă  la place. Platform.cs 64

public static PlatformType get_platform()
{
  switch (Environment.OSVersion.Platform)
  {
    case PlatformID.MacOSX:
    {
      ....
    }
    case PlatformID.Unix:
    if(file_system.directory_exists("/Applications")
      & file_system.directory_exists("/System")
      & file_system.directory_exists("/Users")
      & file_system.directory_exists("/Volumes"))
      {
        return PlatformType.Mac;
      }
        else
          return PlatformType.Linux;
    default:
      return PlatformType.Windows;
  }
}

La diffĂ©rence entre l'opĂ©rateur & et l'opĂ©rateur && rĂ©side dans le fait que si la partie gauche de l'expression — faux, cela calculera tout de mĂȘme la partie droite, ce qui dans ce cas implique des appels de mĂ©thode inutiles. system.directory_exists.

Dans le fragment examinĂ©, c'est un petit dĂ©tail. Oui, cette condition peut ĂȘtre optimisĂ©e en remplaçant l'opĂ©rateur & par l'opĂ©rateur &&, mais d'un point de vue pratique, cela n'a aucune influence. Cependant, dans d'autres cas, la confusion entre & et && peut provoquer de graves problĂšmes lorsque la partie droite de l'expression traite des valeurs incorrectes ou non autorisĂ©es. Par exemple, dans notre collection d'erreurs, dĂ©tectĂ©es par le diagnostic V3093, il y a ce cas :

if ((k < nct) && (s[k] != 0.0))

MĂȘme si l'index k est incorrect, il sera utilisĂ© pour accĂ©der Ă  l'Ă©lĂ©ment du tableau. Cela gĂ©nĂ©rera une exception IndexOutOfRangeException.

Avertissements N3, N4

Avertissement de l'analyseur : V3022 [CWE-571] L'expression ‘shortPrompt’ est toujours vraie. InteractivePrompt.cs 101
Avertissement de l'analyseur : V3022 [CWE-571] L'expression ‘shortPrompt’ est toujours vraie. InteractivePrompt.cs 105

public static string 
prompt_for_confirmation(.... bool shortPrompt = false, ....)
{
  ....
  if (shortPrompt)
  {
    var choicePrompt = choice.is_equal_to(defaultChoice) //1
    ?
    shortPrompt //2
    ?
    "[[{0}]{1}]".format_with(choice.Substring(0, 1).ToUpperInvariant(), //3
    choice.Substring(1,choice.Length - 1))
    :
    "[{0}]".format_with(choice.ToUpperInvariant()) //0
    : 
    shortPrompt //4
    ? 
    "[{0}]{1}".format_with(choice.Substring(0,1).ToUpperInvariant(), //5
    choice.Substring(1,choice.Length - 1)) 
    :
    choice; //0
    ....
  }
  ....
}

Dans ce cas, il y a une logique Ă©trange dans le fonctionnement de l'opĂ©rateur ternaire. Examinons plus en dĂ©tail : si la condition marquĂ©e par le chiffre 1 se rĂ©alise, nous passerons Ă  la condition 2, qui est toujours true, ce qui signifie que la ligne 3 sera exĂ©cutĂ©e. Si la condition 1 s'avĂšre fausse, nous passerons Ă  la ligne marquĂ©e par le chiffre 4, dont la condition est Ă©galement toujours true, ce qui signifie que la ligne 5 sera exĂ©cutĂ©e. Ainsi, les conditions marquĂ©es par le commentaire 0 ne seront jamais exĂ©cutĂ©es, ce qui peut ne pas correspondre Ă  la logique que le programmeur avait en tĂȘte.

Avertissement N5

Avertissement de l'analyseur : V3123 [CWE-783] Peut-ĂȘtre que l'opĂ©rateur ‘?:’ fonctionne diffĂ©remment de ce qui Ă©tait attendu. Sa prioritĂ© est infĂ©rieure Ă  celle d'autres opĂ©rateurs dans sa condition. Options.cs 1019

private static string GetArgumentName (...., string description)
{
  string[] nameStart;
  if (maxIndex == 1)
  {
    nameStart = new string[]{"{0:", "{"};
  }
  else
  {
    nameStart = new string[]{"{" + index + ":"};
  }
  for (int i = 0; i = 0 && j != 0 ? description [j++ - 1] == '{' : false);
    ....
    return maxIndex == 1 ? "VALUE" : "VALUE" + (index + 1);
  }
}

Le diagnostic a été déclenché sur la ligne :

while (start >= 0 && j != 0 ? description [j++ - 1] == '{' : false)

Étant donnĂ© que la variable j plus haut, il est initialisĂ© Ă  zĂ©ro, l'opĂ©rateur ternaire retournera une valeur faux. En raison de cette condition, le corps de la boucle ne s'exĂ©cutera qu'une seule fois. Je pense que ce fragment de code fonctionne tout Ă  fait diffĂ©remment de ce que le programmeur avait prĂ©vu.

Avertissement N6

Avertissement de l'analyseur : V3022 [CWE-571] L'expression 'installedPackageVersions.Count != 1' est toujours vraie. NugetService.cs 1405

private void remove_nuget_cache_for_package(....)
{
  if (!config.AllVersions && installedPackageVersions.Count > 1)
  {
    const string allVersionsChoice = "Toutes versions";
    if (installedPackageVersions.Count != 1)
    {
      choices.Add(allVersionsChoice);
    }
    ....
  }
  ....
}

Il y a une condition imbriquée étrange ici : installedPackageVersions.Count != 1, qui sera toujours true. Souvent, ce genre d'avertissement signale une erreur logique dans le code, ou parfois juste une vérification redondante.

Avertissement N7

Avertissement de l'analyseur : V3001 Il y a des sous-expressions identiques 'commandArguments.contains("-apikey")' à gauche et à droite de l'opérateur '||'. ArgumentsUtility.cs 42

public static bool arguments_contain_sensitive_information(string
 commandArguments)
{
  return commandArguments.contains("-install-arguments-sensitive")
  || commandArguments.contains("-package-parameters-sensitive")
  || commandArguments.contains("apikey ")
  || commandArguments.contains("config ")
  || commandArguments.contains("push ")
  || commandArguments.contains("-p ")
  || commandArguments.contains("-p=")
  || commandArguments.contains("-password")
  || commandArguments.contains("-cp ")
  || commandArguments.contains("-cp=")
  || commandArguments.contains("-certpassword")
  || commandArguments.contains("-k ")
  || commandArguments.contains("-k=")
  || commandArguments.contains("-key ")
  || commandArguments.contains("-key=")
  || commandArguments.contains("-apikey")
  || commandArguments.contains("-api-key")
  || commandArguments.contains("-apikey")
  || commandArguments.contains("-api-key");
}

Le programmeur qui a Ă©crit ce bout de code a copiĂ©-collĂ© les deux derniĂšres lignes et a oubliĂ© de les modifier. En consĂ©quence, les utilisateurs de Chocolatey n'ont pas pu appliquer le paramĂštre apikey d'autres maniĂšres Ă©galement. De la mĂȘme maniĂšre que les paramĂštres ci-dessus, je peux proposer les options suivantes :

commandArguments.contains("-apikey=");
commandArguments.contains("-api-key=");

Les erreurs de copie-coller ont de grandes chances d'apparaĂźtre tĂŽt ou tard dans tout projet avec beaucoup de code source, et l'un des meilleurs moyens de lutter contre cela est l'analyse statique.

P.S. Et comme toujours, cette erreur a tendance Ă  apparaĂźtre Ă  la fin d'une condition multi-ligne :). Voir la publication "L'effet de la derniĂšre ligne".

Avertissement N8

Avertissement de l'analyseur : V3095 [CWE-476] L'objet 'installedPackage' a été utilisé avant d'avoir été vérifié contre null. Vérifiez les lignes : 910, 917. NugetService.cs 910

public virtual ConcurrentDictionary get_outdated(....)
{
  ....
  var pinnedPackageResult = outdatedPackages.GetOrAdd(
    packageName, 
    new PackageResult(installedPackage, 
                      _fileSystem.combine_paths(
                        ApplicationParameters.PackagesLocation, 
                        installedPackage.Id)));
  ....
  if (   installedPackage != null
      && !string.IsNullOrWhiteSpace(installedPackage.Version.SpecialVersion) 
      && !config.UpgradeCommand.ExcludePrerelease)
  {
    ....
  }
  ....
}

Erreur classique : l'objet est utilisĂ© avant d'ĂȘtre vĂ©rifiĂ© installedPackage Cela indique l'une des deux problĂšmes dans le programme : soit nulln'est jamais Ă©gal Ă  installedPackage , ce qui est douteux, et donc la vĂ©rification est superflue, soit nous pouvons potentiellement rencontrer une grave erreur dans le code – une tentative d'accĂšs par un pointeur nul. nullVoilĂ , nous avons encore fait un petit pas – utiliser PVS-Studio est devenu encore plus simple et pratique. Je tiens Ă©galement Ă  dire que Chocolatey est un bon gestionnaire de paquets avec peu d'erreurs dans le code, qui pourraient encore diminuer avec l'utilisation de PVS-Studio.

Conclusion

et essayez PVS-Studio. L'utilisation réguliÚre de l'analyseur statique améliorera la qualité et la fiabilité du code développé par votre équipe et aidera à prévenir de nombreuses

Nous vous invitons télécharger vulnérabilités de type zero-day Avant publication, nous avons envoyé l'article aux développeurs de Chocolatey, et ils l'ont bien accueilli. Rien de critique n'a été trouvé par nos soins, mais ils ont, par exemple, apprécié l'erreur que nous avons trouvée concernant la clé « api-key »..

P.S.

PVS-Studio est maintenant intégré à Chocolatey : Vérification de Chocolatey sous Azure DevOps

PVS-Studio est maintenant disponible sur Chocolatey : vérification de Chocolatey via Azure DevOps

Si vous souhaitez partager cet article avec un public anglophone, veuillez utiliser le lien vers la traduction : Vladislav Stolyarov. Nous continuons..

Source : habr.com

Acheter un hĂ©bergement fiable pour les sites avec protection DDoS, serveurs VPS VDS đŸ”„ Acheter un hĂ©bergement fiable pour les sites avec protection DDoS, serveurs VPS VDS | ProHoster