Skip to content

Commit 200126b

Browse files
authored
Merge pull request github#6008 from github/tamasvajk/feature/csv-coverage-report
Add timeseries CSV generator script
2 parents 6ca8d69 + 255e422 commit 200126b

File tree

12 files changed

+561
-224
lines changed

12 files changed

+561
-224
lines changed
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
name: Build framework coverage timeseries reports
2+
3+
on:
4+
workflow_dispatch:
5+
6+
jobs:
7+
build:
8+
9+
runs-on: ubuntu-latest
10+
11+
steps:
12+
- name: Clone self (github/codeql)
13+
uses: actions/checkout@v2
14+
with:
15+
path: script
16+
- name: Clone self (github/codeql) for analysis
17+
uses: actions/checkout@v2
18+
with:
19+
path: codeqlModels
20+
fetch-depth: 0
21+
- name: Set up Python 3.8
22+
uses: actions/setup-python@v2
23+
with:
24+
python-version: 3.8
25+
- name: Download CodeQL CLI
26+
env:
27+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
28+
run: |
29+
gh release download --repo "github/codeql-cli-binaries" --pattern "codeql-linux64.zip"
30+
- name: Unzip CodeQL CLI
31+
run: unzip -d codeql-cli codeql-linux64.zip
32+
- name: Build modeled package list
33+
run: |
34+
CLI=$(realpath "codeql-cli/codeql")
35+
echo $CLI
36+
PATH="$PATH:$CLI" python script/misc/scripts/library-coverage/generate-timeseries.py codeqlModels
37+
- name: Upload timeseries CSV
38+
uses: actions/upload-artifact@v2
39+
with:
40+
name: framework-coverage-timeseries
41+
path: framework-coverage-timeseries-*.csv
42+

.github/workflows/csv-coverage.yml

Lines changed: 10 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,11 @@
1-
name: Build/check CSV flow coverage report
1+
name: Build framework coverage reports
22

33
on:
44
workflow_dispatch:
55
inputs:
66
qlModelShaOverride:
77
description: 'github/codeql repo SHA used for looking up the CSV models'
88
required: false
9-
push:
10-
branches:
11-
- main
12-
- 'rc/**'
13-
pull_request:
14-
paths:
15-
- '.github/workflows/csv-coverage.yml'
16-
- '*/ql/src/**/*.ql'
17-
- '*/ql/src/**/*.qll'
18-
- 'misc/scripts/library-coverage/*.py'
19-
# input data files
20-
- '*/documentation/library-coverage/cwe-sink.csv'
21-
- '*/documentation/library-coverage/frameworks.csv'
22-
# coverage report files
23-
- '*/documentation/library-coverage/flow-model-coverage.csv'
24-
- '*/documentation/library-coverage/flow-model-coverage.rst'
259

2610
jobs:
2711
build:
@@ -33,28 +17,20 @@ jobs:
3317
uses: actions/checkout@v2
3418
with:
3519
path: script
36-
- name: Clone self (github/codeql) at a given SHA for analysis
37-
if: github.event.inputs.qlModelShaOverride != ''
38-
uses: actions/checkout@v2
39-
with:
40-
path: codeqlModels
41-
ref: github.event.inputs.qlModelShaOverride
4220
- name: Clone self (github/codeql) for analysis
43-
if: github.event.inputs.qlModelShaOverride == ''
4421
uses: actions/checkout@v2
4522
with:
4623
path: codeqlModels
24+
ref: ${{ github.event.inputs.qlModelShaOverride || github.ref }}
4725
- name: Set up Python 3.8
4826
uses: actions/setup-python@v2
4927
with:
5028
python-version: 3.8
5129
- name: Download CodeQL CLI
52-
uses: dsaltares/fetch-gh-release-asset@aa37ae5c44d3c9820bc12fe675e8670ecd93bd1c
53-
with:
54-
repo: "github/codeql-cli-binaries"
55-
version: "latest"
56-
file: "codeql-linux64.zip"
57-
token: ${{ secrets.GITHUB_TOKEN }}
30+
env:
31+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
32+
run: |
33+
gh release download --repo "github/codeql-cli-binaries" --pattern "codeql-linux64.zip"
5834
- name: Unzip CodeQL CLI
5935
run: unzip -d codeql-cli codeql-linux64.zip
6036
- name: Build modeled package list
@@ -63,15 +39,11 @@ jobs:
6339
- name: Upload CSV package list
6440
uses: actions/upload-artifact@v2
6541
with:
66-
name: csv-flow-model-coverage
67-
path: flow-model-coverage-*.csv
42+
name: framework-coverage-csv
43+
path: framework-coverage-*.csv
6844
- name: Upload RST package list
6945
uses: actions/upload-artifact@v2
7046
with:
71-
name: rst-flow-model-coverage
72-
path: flow-model-coverage-*.rst
73-
# - name: Check coverage files
74-
# if: github.event.pull_request
75-
# run: |
76-
# python script/misc/scripts/library-coverage/compare-files.py codeqlModels
47+
name: framework-coverage-rst
48+
path: framework-coverage-*.rst
7749

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
package,sink,source,summary,sink:bean-validation,sink:create-file,sink:header-splitting,sink:information-leak,sink:jexl,sink:ldap,sink:open-url,sink:set-hostname-verifier,sink:url-open-stream,sink:xpath,sink:xss,source:remote,summary:taint,summary:value
2+
android.util,,16,,,,,,,,,,,,,16,,
3+
android.webkit,3,2,,,,,,,,,,,,3,2,,
4+
com.esotericsoftware.kryo.io,,,1,,,,,,,,,,,,,1,
5+
com.esotericsoftware.kryo5.io,,,1,,,,,,,,,,,,,1,
6+
com.fasterxml.jackson.databind,,,3,,,,,,,,,,,,,3,
7+
com.google.common.base,,,34,,,,,,,,,,,,,28,6
8+
com.google.common.io,6,,73,,,,,,,,,6,,,,72,1
9+
com.unboundid.ldap.sdk,17,,,,,,,,17,,,,,,,,
10+
java.beans,,,1,,,,,,,,,,,,,1,
11+
java.io,3,,20,,3,,,,,,,,,,,20,
12+
java.lang,,,3,,,,,,,,,,,,,1,2
13+
java.net,2,3,4,,,,,,,2,,,,,3,4,
14+
java.nio,10,,2,,10,,,,,,,,,,,2,
15+
java.util,,,283,,,,,,,,,,,,,15,268
16+
javax.naming.directory,1,,,,,,,,1,,,,,,,,
17+
javax.net.ssl,2,,,,,,,,,,2,,,,,,
18+
javax.servlet,4,21,2,,,3,1,,,,,,,,21,2,
19+
javax.validation,1,1,,1,,,,,,,,,,,1,,
20+
javax.ws.rs.core,1,,,,,1,,,,,,,,,,,
21+
javax.xml.transform.sax,,,4,,,,,,,,,,,,,4,
22+
javax.xml.transform.stream,,,2,,,,,,,,,,,,,2,
23+
javax.xml.xpath,3,,,,,,,,,,,,3,,,,
24+
org.apache.commons.codec,,,2,,,,,,,,,,,,,2,
25+
org.apache.commons.io,,,22,,,,,,,,,,,,,22,
26+
org.apache.commons.jexl2,15,,,,,,,15,,,,,,,,,
27+
org.apache.commons.jexl3,15,,,,,,,15,,,,,,,,,
28+
org.apache.commons.lang3,,,370,,,,,,,,,,,,,324,46
29+
org.apache.commons.text,,,272,,,,,,,,,,,,,220,52
30+
org.apache.directory.ldap.client.api,1,,,,,,,,1,,,,,,,,
31+
org.apache.hc.core5.function,,,1,,,,,,,,,,,,,1,
32+
org.apache.hc.core5.http,1,2,39,,,,,,,,,,,1,2,39,
33+
org.apache.hc.core5.net,,,2,,,,,,,,,,,,,2,
34+
org.apache.hc.core5.util,,,24,,,,,,,,,,,,,18,6
35+
org.apache.http,2,3,67,,,,,,,,,,,2,3,59,8
36+
org.dom4j,20,,,,,,,,,,,,20,,,,
37+
org.springframework.ldap.core,14,,,,,,,,14,,,,,,,,
38+
org.springframework.security.web.savedrequest,,6,,,,,,,,,,,,,6,,
39+
org.springframework.web.client,,3,,,,,,,,,,,,,3,,
40+
org.springframework.web.context.request,,8,,,,,,,,,,,,,8,,
41+
org.springframework.web.multipart,,12,,,,,,,,,,,,,12,,
42+
org.xml.sax,,,1,,,,,,,,,,,,,1,
43+
org.xmlpull.v1,,3,,,,,,,,,,,,,3,,
44+
play.mvc,,4,,,,,,,,,,,,,4,,

java/documentation/library-coverage/flow-model-coverage.rst renamed to java/documentation/library-coverage/coverage.rst

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8,12 +8,14 @@ Java framework & library support
88

99
Framework / library,Package,Remote flow sources,Taint & value steps,Sinks (total),`CWE‑022` :sub:`Path injection`,`CWE‑036` :sub:`Path traversal`,`CWE‑079` :sub:`Cross-site scripting`,`CWE‑089` :sub:`SQL injection`,`CWE‑090` :sub:`LDAP injection`,`CWE‑094` :sub:`Code injection`,`CWE‑319` :sub:`Cleartext transmission`
1010
Android,``android.*``,18,,3,,,3,,,,
11-
Apache,``org.apache.*``,5,648,4,,,3,,1,,
1211
`Apache Commons IO <https://commons.apache.org/proper/commons-io/>`_,``org.apache.commons.io``,,22,,,,,,,,
13-
Google,``com.google.common.*``,,97,6,,6,,,,,
14-
Java Standard Library,``java.*``,3,41,15,13,,,,,,2
12+
`Apache Commons Lang <https://commons.apache.org/proper/commons-lang/>`_,``org.apache.commons.lang3``,,370,,,,,,,,
13+
`Apache Commons Text <https://commons.apache.org/proper/commons-text/>`_,``org.apache.commons.text``,,272,,,,,,,,
14+
`Apache HttpComponents <https://hc.apache.org/>`_,"``org.apache.hc.core5.*``, ``org.apache.http``",5,133,3,,,3,,,,
15+
`Google Guava <https://guava.dev/>`_,``com.google.common.*``,,107,6,,6,,,,,
16+
Java Standard Library,``java.*``,3,313,15,13,,,,,,2
1517
Java extensions,``javax.*``,22,8,12,,,,,1,1,
1618
`Spring <https://spring.io/>`_,``org.springframework.*``,29,,14,,,,,14,,
17-
Others,"``com.esotericsoftware.kryo.io``, ``com.esotericsoftware.kryo5.io``, ``com.fasterxml.jackson.databind``, ``com.unboundid.ldap.sdk``, ``org.dom4j``, ``org.xml.sax``, ``org.xmlpull.v1``, ``play.mvc``",7,5,37,,,,,17,,
18-
Totals,,84,821,91,13,6,6,,33,1,2
19+
Others,"``com.esotericsoftware.kryo.io``, ``com.esotericsoftware.kryo5.io``, ``com.fasterxml.jackson.databind``, ``com.unboundid.ldap.sdk``, ``org.apache.commons.codec``, ``org.apache.commons.jexl2``, ``org.apache.commons.jexl3``, ``org.apache.directory.ldap.client.api``, ``org.dom4j``, ``org.xml.sax``, ``org.xmlpull.v1``, ``play.mvc``",7,8,68,,,,,18,,
20+
Totals,,84,1233,121,13,6,6,,33,1,2
1921

java/documentation/library-coverage/flow-model-coverage.csv

Lines changed: 0 additions & 42 deletions
This file was deleted.
Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
1-
Framework name,URL,Package prefix
1+
Framework name,URL,Package prefixes
22
Java Standard Library,,java.*
3-
Google,,com.google.common.*
4-
Apache,,org.apache.*
3+
Java extensions,,javax.*
4+
Google Guava,https://guava.dev/,com.google.common.*
55
Apache Commons IO,https://commons.apache.org/proper/commons-io/,org.apache.commons.io
6+
Apache Commons Lang,https://commons.apache.org/proper/commons-lang/,org.apache.commons.lang3
7+
Apache Commons Text,https://commons.apache.org/proper/commons-text/,org.apache.commons.text
8+
Apache HttpComponents,https://hc.apache.org/,org.apache.hc.core5.* org.apache.http
69
Android,,android.*
7-
Spring,https://spring.io/,org.springframework.*
8-
Java extensions,,javax.*
10+
Spring,https://spring.io/,org.springframework.*
Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
import csv
2+
import sys
3+
import packages
4+
5+
6+
class Framework:
7+
"""
8+
Frameworks are the aggregation units in the RST and timeseries report. These are read from the frameworks.csv file.
9+
"""
10+
11+
def __init__(self, name, url, package_pattern):
12+
self.name = name
13+
self.url = url
14+
self.package_pattern = package_pattern
15+
16+
17+
class FrameworkCollection:
18+
"""
19+
A (sorted) list of frameworks.
20+
"""
21+
22+
def __init__(self, path):
23+
self.frameworks: list[Framework] = []
24+
self.package_patterns = set()
25+
26+
with open(path) as csvfile:
27+
reader = csv.reader(csvfile)
28+
next(reader)
29+
for row in reader:
30+
# row: Hibernate,https://hibernate.org/,org.hibernate
31+
self.__add(Framework(row[0], row[1], row[2]))
32+
self.__sort()
33+
34+
def __add(self, framework: Framework):
35+
if framework.package_pattern not in self.package_patterns:
36+
self.package_patterns.add(framework.package_pattern)
37+
self.frameworks.append(framework)
38+
else:
39+
print("Package pattern already exists: " +
40+
framework.package_pattern, file=sys.stderr)
41+
42+
def __sort(self):
43+
self.frameworks.sort(key=lambda f: f.name)
44+
45+
def get(self, framework_name):
46+
for framework in self.frameworks:
47+
if framework.name == framework_name:
48+
return framework
49+
return None
50+
51+
def get_frameworks(self):
52+
return self.frameworks
53+
54+
def __package_match_single(self, package: packages.Package, pattern):
55+
return (pattern.endswith("*") and package.name.startswith(pattern[:-1])) or (not pattern.endswith("*") and pattern == package.name)
56+
57+
def __package_match(self, package: packages.Package, pattern):
58+
patterns = pattern.split(" ")
59+
return any(self.__package_match_single(package, pattern) for pattern in patterns)
60+
61+
def get_package_filter(self, framework: Framework):
62+
"""
63+
Returns a lambda filter that holds for packages that match the current framework.
64+
65+
The pattern is either full name, such as "org.hibernate", or a prefix, such as "java.*".
66+
Patterns can also contain a space separated list of patterns, such as "java.sql javax.swing".
67+
68+
Package patterns might overlap, in case of 'org.apache.commons.io' and 'org.apache.*', the statistics for
69+
the latter will not include the statistics for the former.
70+
"""
71+
return lambda p: \
72+
self.__package_match(p, framework.package_pattern) and \
73+
all(
74+
len(framework.package_pattern) >= len(pattern) or
75+
not self.__package_match(p, pattern) for pattern in self.package_patterns)

0 commit comments

Comments
 (0)