A static analysis tool for security

Overview

progpilot

A static analyzer for security purposes
Only PHP language is currently supported

Build Status Packagist Packagist

Installation

Option 1: use standalone phar

  • Download the latest phar archive from the releases page.
  • Place the file somewhere in your path and make it executable:
chmod +x progpilot_vX.Y.Z.phar
sudo mv progpilot_vX.Y.Z.phar /usr/local/bin/progpilot

Option 2: build phar from source code

phar-composer.phar should be located in a directory listed in the $PATH environment variable before starting the build:

git clone https://github.com/designsecurity/progpilot
cd progpilot
./build.sh

The resulting phar archive will be located in the builds folder at the root of this project.

Option 3: use composer

Use Composer to install progpilot:

composer require --dev designsecurity/progpilot

Configuration

Use a yaml configuration file (look at this example) to configure and customize the progpilot analysis otherwise the default configuration will be used with, in particular the standard taint configuration data.

Usage

CLI example

The progpilot command takes as arguments the path to the files and folders to be analyzed and optionally a configuration file:

# without config file
progpilot example1.php example2.php folder1/ folder2/
# with a config file
progpilot --configuration configuration.yml example1.php example2.php folder1/ folder2/

If you installed it with composer, the program will be located at vendor/bin/progpilot.

Library example

It is also possible to use progpilot inside PHP code. For more information look at the API documentation.

Use this code to analyze source_code1.php:

<?php
require_once './vendor/autoload.php';

$context = new \progpilot\Context;
$analyzer = new \progpilot\Analyzer;

$context->inputs->setFile("source_code1.php");

try {
  $analyzer->run($context);
} catch (Exception $e) {
   echo "Exception : ".$e->getMessage()."\n";
}  
  
$results = $context->outputs->getResults();

var_dump($results);

When source_code1.php contains this code:

<?php
$var7 = $_GET["p"];
$var4 = $var7;
echo "$var4";

The simplified output will be:

array(1) {
  [0]=>
  array(11) {
    ["source_name"]=>
    array(1) {
      [0]=>
      string(5) "$var4"
    }
    ["source_line"]=>
    array(1) {
      [0]=>
      int(4)
    }
    ["sink_name"]=>
    string(4) "echo"
    ["sink_line"]=>
    int(5)
    ["vuln_name"]=>
    string(3) "xss"
  }
}

All files (composer.json, example1.php, source_code1.php) used in this example are in the projects/example folder. For more examples look also at this page.

Specify an analysis

It is strongly recommended to customize the taint analysis configuration (the definitions of sinks, sources, sanitizers and validators) according to the context of the application to be analyzed. In the following specification, superglobals variables _GET, _POST or _COOKIE are defined as untrusted and also the return of the shell_exec() function:

{
    "sources": [
        {"name": "_GET", "is_array": true, "language": "php"},
        {"name": "_POST", "is_array": true, "language": "php"},
        {"name": "_COOKIE", "is_array": true, "language": "php"},
        {"name": "shell_exec", "is_function": true, "language": "php"}
    ]
}

See available settings in the corresponding chapter about specifying an analysis.
Custom rules can be created too, see the corresponding chapter about custom rules.

Development

Learn more about the development of Progpilot.

Faq

Here

Comments
  • Unknown node error

    Unknown node error

    Some node types are not handle, I tried to run progpilot on some projects using nullable type or group use and I have those errors:

    • Unknown Stmt Node Encountered : Stmt_GroupUse
    • Unknown Expr Type NullableType
    opened by BafS 16
  • Excluded file still processed if explicitly passed

    Excluded file still processed if explicitly passed

    If you add a file to the "exclude_files" section of a configuration file but then pass that file to be processed the file is still processed instead of being excluded.

    My case: I have a VERY large project and for some reason there are a few files within the project that causes Progpilot to crash. For now I want to exclude those files to be able to still process everything else. My issue is that I am doing a diff between my current working branch to the master branch to get a list of files that have been changed, then pass those filenames to progpilot to be processed. Mind you this way saves processing time but it still takes over 30 minutes to run, as opposed to 3-4 hours (I told you it was a large project).

    opened by wpenton-itc 8
  • Call to a member function get_name() on null in phar

    Call to a member function get_name() on null in phar

    I'm just trying to run this with out a configuration file: php progpilot.phar someFile.php

    This is the result I get: PHP Fatal error: Uncaught Error: Call to a member function get_name() on null in phar:///home/centos/progpilot/progpilot.phar/vendor/progpilot/package/src/progpilot/Inputs/MyInputs.php:310 Stack trace: #0 phar:///home/centos/progpilot/progpilot.phar/vendor/progpilot/package/src/progpilot/Analysis/SecurityAnalysis.php(93): progpilot\Inputs\MyInputs->get_sink_byname(Object(progpilot\Context), Array, Object(progpilot\Objects\MyFunction), NULL) #1 phar:///home/centos/progpilot/progpilot.phar/vendor/progpilot/package/src/progpilot/Analysis/TaintAnalysis.php(40): progpilot\Analysis\SecurityAnalysis::funccall(Array, Object(progpilot\Context), Object(progpilot\Code\MyInstruction), NULL) #2 phar:///home/centos/progpilot/progpilot.phar/vendor/progpilot/package/src/progpilot/Analysis/VisitorAnalysis.php(461): progpilot\Analysis\TaintAnalysis::funccall_specify_analysis(NULL, Array, Object(progpilot\Context), Array, NULL, Object(progpilot\Objects\MyFunction), false, Object(progpilot\Code\MyInstruction), Object(progpilot\Code\MyCode), 858) in phar:///home/centos/progpilot/progpilot.phar/vendor/progpilot/package/src/progpilot/Inputs/MyInputs.php on line 310

    opened by the6thBook 8
  • trace   function

    trace function

    hi, Sir,I used the progpilot to analyze my php project ,It works well,but It seem that taint flow do not work,there is no taint trace info,only exits source and sink. Can you give me some suggestion?

    opened by tiandiyixian 8
  • Illegal offset type

    Illegal offset type

    I got 'Illegal offset type' error on fresh installation via composer. It is not just a notice. Class method analysis failed. nikic/php-parser v4.0.2 35b8caf75e791ba1b2d24fec1552168d72692b12 php v7.0 Solved by type casting to string

    diff --git a/package/src/progpilot/Transformations/Php/Transform.php 
    -        $this->context->get_functions()->add_function($myfunction->get_name(), $myfunction);
    +        $this->context->get_functions()->add_function((string)$myfunction->get_name(), $myfunction);
    -        $myfunction = $this->context->get_functions()->get_function($func->name, $class_name);
    +        $myfunction = $this->context->get_functions()->get_function((string)$func->name, $class_name);
    
    opened by eapunk 7
  • [Bug BLOCKER] Ignoring vuln_id with a json file doesn't work.

    [Bug BLOCKER] Ignoring vuln_id with a json file doesn't work.

    Hello,

    Thanks for providing to us this nice security package.

    I use last phar version, and set the config file like this: setFalsePositives: "./tests/php/progpilot-false-positive.json"

    and the json files with reported false positive:

    {
      "false_positives": [
        {
    	  "vuln_id": "fcfa05bd72416786bcbf09289f64dad31d0afe89145421d42f2023f0198550ad",
    	  "vuln_id": "14fad770072acbb70eebdf1aeba31c032d63c6806c2cc94de1c97266d2fea41a"
    	}
      ]
    }
    

    I tryed with just one:

    {
      "false_positives": [
        {
    	  "vuln_id": "fcfa05bd72416786bcbf09289f64dad31d0afe89145421d42f2023f0198550ad"
    	}
      ]
    }
    

    ,and like this too:

    {
      "false_positives": [
        {
    	  "vuln_id": "fcfa05bd72416786bcbf09289f64dad31d0afe89145421d42f2023f0198550ad"
    	},
        {
    	  "vuln_id": "14fad770072acbb70eebdf1aeba31c032d63c6806c2cc94de1c97266d2fea41a"
    	}
      ]
    }
    

    But problem are always displayed when i run the phar file : ( The json config is well parsed by progpilot because if the format is not good i got an error message, so the config and the json file is well loaded in progpilot. Is it a bug or i missed something ? Actually I cannot use it because some false positive are reported and i would like to silent them.

    When several vuln_id, which is the good format from my 2 examples ?

    Thanks a lot!

    opened by Yivan 4
  • Syntax Error Standalone Build

    Syntax Error Standalone Build

    Hey there,

    I've found the closed #10 issue that seems really close to mine, the only difference is that i'm running a Debian machine.

    php's version :

    $ php -v PHP 7.0.30-0+deb9u1 (cli) (built: Jun 14 2018 13:50:25) ( NTS )

    What I Did

    $ wget https://github.com/designsecurity/progpilot/releases/download/v0.4.0/progpilot_v0.4.0.phar $ php progpilot_v0.4.0.phar

    What I Got

    PHP Parse error: syntax error, unexpected '?', expecting variable (T_VARIABLE) in phar:///.../progpilot_v0.4.0.phar/vendor/symfony/console/Output/Output.php on line 40

    Did I do something obviously wrong ?

    opened by aza-rian 4
  • Improve the build.sh script

    Improve the build.sh script

    • User /usr/bin/env instead of hardcoded path for bash
    • Check if command is in $PATH instead of hardcoding it in the script
    • Exit early if the command is not found
    • Use modern $() syntax instead of backticks
    • Group the cleanup commands together
    • Merge the mkdir commands in one with -p flag
    • Add -f to rm composer.lock command so it doesn't complain if file is not here
    • Script is now passing shellcheck with no errors
    • Add verbose flag to final move
    • Add phar builds to .gitignore
    opened by NicolasCARPi 3
  • Trying to access array offset on value of type int

    Trying to access array offset on value of type int

    Hello, I found a case where progpilot is failing when it encounters integers in the file. It can be replicated even with the default configuration

    PHP version - 7.4.3 Progpilot version - v0.6.0 Configuration of progpilot - default File trying to analyze:

    <?php
    
    
    ini_set('allow_url_fopen',1);
    
    
    function get_client_ip() {
        $ipaddress = '';
        if (getenv('HTTP_CLIENT_IP'))
            $ipaddress = getenv('HTTP_CLIENT_IP');
        else if(getenv('HTTP_X_FORWARDED_FOR'))
            $ipaddress = getenv('HTTP_X_FORWARDED_FOR');
        else if(getenv('HTTP_X_FORWARDED'))
            $ipaddress = getenv('HTTP_X_FORWARDED');
        else if(getenv('HTTP_FORWARDED_FOR'))
            $ipaddress = getenv('HTTP_FORWARDED_FOR');
        else if(getenv('HTTP_FORWARDED'))
            $ipaddress = getenv('HTTP_FORWARDED');
        else if(getenv('REMOTE_ADDR'))
            $ipaddress = getenv('REMOTE_ADDR');
        else
            $ipaddress = 'UNKNOWN';
        return $ipaddress;
    }
    
    $IP = get_client_ip();
    
    $settings = include '../../../settings/settings.php';
    
    $message = "********** [ INFORMATION ] **********\n";
    $message .= "# IP ADDRESS : {$IP}\n";
    $message .= "**********************************************\n";
    
    $to = $settings['email'];
    $headers = "Content-type:text/plain;charset=UTF-8\r\n";
    $headers .= "From: REDACTED\r\n";
    $subject = "REDACTED";
    mail($to,$subject,$msg,$headers);
    
    $data = $message;
    $send = ['REDACTED'=>$data];
    $website = "REDACTED";
    $ch = curl_init($website . '/somePath');
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_POST, 1);
    curl_setopt($ch, CURLOPT_POSTFIELDS, ($send));
    curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
    $result = curl_exec($ch);
    curl_close($ch);
    
    ?>
    

    Error - Multiple lines of:

    PHP Notice:  Trying to access array offset on value of type int in /home/**/vendor/designsecurity/progpilot/package/src/progpilot/Transformations/Php/Expr.php on line 36
    

    Removing lines with integers passed to functions, like the two curl_setopt lines and the ini_set line, it works fine and matches the custom rule used in default progpilot config for security misconfiguration.

    I wasn't able to trace back the exact trace that calls Expr::setChars with a number passed to it, although it is possible that the $name generated using mt_rand() can also possibly cause this in general.

    opened by TheComputeGuy 2
  • I can't install Progpilot on PHP < 7.4

    I can't install Progpilot on PHP < 7.4

    The documentation says:

    The minimum version of PHP needed to run Progpilot is 7.0.25

    However, due to the library requiring ircmaxell/php-cfg (which is requiring PHP 7.4) it's impossible to install the library with versions of PHP older than 7.4.

    As I'm dealing with legacy code which for which we must provide support for older 7.* versions of PHP, I'm unable to use this library to scan for security issue.

    opened by andreasciamanna 2
  • Issue with setcookie

    Issue with setcookie

    With the new released version, I can now try this software :)

    There is an issue with setcookie() because it can also take an array of options as a third parameter, and the code is only taking into account the other way to specify options.

    This code: 2020-03-22-144947_384x134_scrot

    Should not trigger this warning:

    2020-03-22-145018_668x174_scrot

    Cheers :) ~Nico

    opened by NicolasCARPi 2
  • Bump acorn from 5.7.3 to 5.7.4 in /package/src/progpilot/Transformations/Js

    Bump acorn from 5.7.3 to 5.7.4 in /package/src/progpilot/Transformations/Js

    Bumps acorn from 5.7.3 to 5.7.4.

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    • @dependabot use these labels will set the current labels as the default for future PRs for this repo and language
    • @dependabot use these reviewers will set the current reviewers as the default for future PRs for this repo and language
    • @dependabot use these assignees will set the current assignees as the default for future PRs for this repo and language
    • @dependabot use this milestone will set the current milestone as the default for future PRs for this repo and language

    You can disable automated security fix PRs for this repo from the Security Alerts page.

    dependencies 
    opened by dependabot[bot] 1
  • How to define the most strict configuration possible for  Progpilot ?

    How to define the most strict configuration possible for Progpilot ?

    I’m collaborating in a opensource project :

    https://bitbucket.org/AliasAPI/damnp/src/master/etc/progpilot/run_progpilot.sh

    And i am finding trouble configuring Progpilot in the most sensitive way possible, so it would detected every generally undesired line of code. If anyone has any tips, it would be very welcome.

    opened by vic131 0
  • Unknown Expr Type Expr_YieldFrom

    Unknown Expr Type Expr_YieldFrom

    Using yield from in PHP code causes an error: Unknown Expr Type Expr_YieldFrom.

    PHP version: 7.4.3 progpilot version: 0.7.0 Configuration: default Code I'm trying to analyze:

    function test() {
            yield from ['foo' => 123];
    }
    
    Raw log
    > progpilot --version
    progpilot 0.7.0
    > php --version
    PHP 7.4.3 (cli) (built: Mar  2 2022 15:36:52) ( NTS )
    Copyright (c) The PHP Group
    Zend Engine v3.4.0, Copyright (c) Zend Technologies
        with Zend OPcache v7.4.3, Copyright (c), by Zend Technologies
    richard@richardspc ~> progpilot --version
    progpilot 0.7.0
    > cat test.php
    <?php
    function test() {
            yield from ['foo' => 123];
    }
    foreach (test() as $key => $value) {
            echo "$key: $value\n";
    }
    > php test.php
    foo: 123
    > progpilot test.php
    
    
    Unknown Expr Type Expr_YieldFrom
    
    
    
    
    
    opened by rigrig 1
  • Unknown type node: UnionType

    Unknown type node: UnionType

    Hi,

    When I try to analyze some code I get Unknown type node: UnionType as a result. I can´t really figure out what this means. There must be something wrong with Main.php but can't figure out what : <?php require('../../sys/classes/Main.php');

    opened by chogberg 1
  • After try to install with composer get error

    After try to install with composer get error "Your requirements could not be resolved to an installable set of packages."

    After i try to install with composer i get error this is full error from terminal. Your requirements could not be resolved to an installable set of packages.

    Problem 1 - Root composer.json requires designsecurity/progpilot ^0.8.0 -> satisfiable by designsecurity/progpilot[v0.8.0]. - designsecurity/progpilot v0.8.0 requires ircmaxell/php-cfg 1.0.x-dev -> found ircmaxell/php-cfg[v1.0.x-dev] but it does not match your minimum-stability.

    Installation failed, deleting ./composer.json.

    opened by r00t3r5 2
  • exists a paper on the implemented analysis?

    exists a paper on the implemented analysis?

    Thank you for the great work. Is there a corresponding paper on the implemented basics, i.e. analysis lattice, transfer functions, soundness, that can be cited?

    opened by MBcom 0
Releases(v1.0.0)
Owner
null
Beautiful and understandable static analysis tool for PHP

PhpMetrics PhpMetrics provides metrics about PHP project and classes, with beautiful and readable HTML report. Documentation | Twitter | Contributing

PhpMetrics 2.3k Dec 22, 2022
A static php code analysis tool using the Graph Theory

Mondrian Ok guyz, you have a master degree in Graph Theory, you follow Law of Demeter and you live on S.O.L.I.D principles ? Let's have some Fun ! (^ω

Florent Genette 391 Nov 30, 2022
A static analysis tool for finding errors in PHP applications

Psalm Psalm is a static analysis tool for finding errors in PHP applications. Installation To get started, check out the installation guide. Live Demo

Vimeo 5k Jan 2, 2023
Deptrac is a static code analysis tool for PHP that helps you communicate, visualize and enforce architectural decisions in your projects

Deptrac is a static code analysis tool for PHP that helps you communicate, visualize and enforce architectural decisions in your projects. You can freely define your architectural layers over classes and which rules should apply to them.

QOSSMIC GmbH 2.2k Dec 30, 2022
A project to add Psalm support for Drupal for security testing, focused only on taint analysis.

psalm-plugin-drupal A Drupal integration for Psalm focused on security scanning (SAST) taint analysis. Features Stubs for sinks, sources, and sanitize

Samuel Mortenson 38 Aug 29, 2022
Static code analysis to find violations in a dependency graph

PhpDependencyAnalysis PhpDependencyAnalysis is an extendable static code analysis for object-oriented PHP-Projects to generate dependency graphs from

Marco Muths 546 Dec 7, 2022
Performs advanced static analysis on PHP code

PHP Analyzer Please report bugs or feature requests via our website support system ? in bottom right or by emailing [email protected]. Contri

Continuous Inspection 443 Sep 23, 2022
The Exakat Engine : smart static analysis for PHP

Exakat The Exakat Engine is an automated code reviewing engine for PHP. Installation Installation with the phar Phar is the recommended installation p

Exakat 370 Dec 28, 2022
Static Analysis Results Baseliner

Static Analysis Results Baseliner (SARB) Why SARB Requirements Installing Using SARB Examples Further reading Why SARB? If you've tried to introduce a

Dave Liddament 151 Jan 3, 2023
Infection Static Analysis Plugin

Static analysis on top of mutation testing - prevents escaped mutants from being invalid according to static analysis

Roave, LLC 108 Jan 2, 2023
phpcs-security-audit is a set of PHP_CodeSniffer rules that finds vulnerabilities and weaknesses related to security in PHP code

phpcs-security-audit v3 About phpcs-security-audit is a set of PHP_CodeSniffer rules that finds vulnerabilities and weaknesses related to security in

Floe design + technologies 655 Jan 3, 2023
Parse: A Static Security Scanner

Parse: A PHP Security Scanner PLEASE NOTE: This tool is still in a very early stage. The work continues... The Parse scanner is a static scanning tool

psec.io 342 Jan 2, 2023
A set of tools for lexical and syntactical analysis written in pure PHP.

Welcome to Dissect! master - this branch always contains the last stable version. develop - the unstable development branch. Dissect is a set of tools

Jakub Lédl 221 Nov 29, 2022
Phan is a static analyzer for PHP. Phan prefers to avoid false-positives and attempts to prove incorrectness rather than correctness.

Phan is a static analyzer for PHP that prefers to minimize false-positives. Phan attempts to prove incorrectness rather than correctness. Phan looks f

null 5.4k Jan 7, 2023
A static analyzer for PHP version migration

PHP Migration Readme in Chinese 中文 This is a static analyzer for PHP version migration and compatibility checking. It can suppose your current code ru

Yuchen Wang 194 Sep 27, 2022
SonarPHP: PHP static analyzer for SonarQube & SonarLint

Code Quality and Security for PHP This SonarSource project is a static code analyser for PHP language used as an extension for the SonarQube platform.

SonarSource 343 Dec 25, 2022
A tool to automatically fix PHP Coding Standards issues

PHP Coding Standards Fixer The PHP Coding Standards Fixer (PHP CS Fixer) tool fixes your code to follow standards; whether you want to follow PHP codi

null 11.6k Jan 3, 2023
A PHP code-quality tool

GrumPHP Sick and tired of defending code quality over and over again? GrumPHP will do it for you! This composer plugin will register some git hooks in

PHPro 3.9k Jan 1, 2023
A tool for quickly measuring the size of a PHP project.

PHPLOC phploc is a tool for quickly measuring the size and analyzing the structure of a PHP project. Installation This tool is distributed as a PHP Ar

Sebastian Bergmann 2.3k Jan 4, 2023