Checking for vulnerabilities in transitive NuGet dependencies with OWASP Dependency-Check
Dependency-Check is a tool for checking for publically disclosed vulnerabilities in the libraries you are using. Free, backed by OWASP, integrated with SonarQube and plugins available for pretty much all pipeline platforms, Dependency-Check is a great choice for checking your NuGet package references.
But have you ever wondered if your dependency scanning is checking for vulnerabilities beyond your immediate package references? In the .Net world many tools don't!
Let's take a look at this problem using Dependency-Check and find a workaround for checking out those transitive dependencies.
If you want to follow along, this is the sample application I am checking. I am using this docker image for Dependency-Check, but you could use the Dependency-Check executable or run it as a task in your preferred pipeline platform.
I am running on Windows and will be using Powershell, so be prepared to adapt if your environment differs from mine.
Also, I will be referencing some folders I have set up on my local system, so just be aware that you would have to create those yourself.
First, I'm going to just target one .csproj file with some package references
Let's just quickly break down the arguments in this docker run command:
--volume C:\repos\eShopOnContainers/src:/src Map my local source code to /src on the container
--volume C:\temp\data:/usr/share/dependency-check/data Give a location for vulnerability database to be saved locally so does not need to be pulled in each run
--volume C:\repos\eShopOnContainers/odc-reports:/report Map location where report will be saved on my local system
--scan /src/Services/Basket/Basket.API/Basket.API.csproj Give Dependency-Check the instruction on what to check
--out /report Tell Dependency-Check where to save the report
Looking at the report, I see it found some dependencies, but not vulnerabilities. Excellent, a clean bill of health. Or are we are missing something?
Using the Assembly scanner
Alright, so after building the Basket.API project I was looking at, let's run a scan on everything to see what it finds if it also looks at the DLLs.
We have a hit!
Hmm, lets look a little closer here. ASP Project Management 1.0 vulnerability from 2009. I think we have a false positive.
If we want to check the packages our immediate NuGet references brings in, but we want to reduce false positives caused by assembly scanning, what do we do?
We need to get Dependency-Check a complete list of all the NuGet packages. I'm sure there are many workarounds and methods that could be done here, so I'm just going to show you one of them.
NuGet has support for a lock file but I'm going to work with what we already have. After building I have a
Inside we have an overwhelming amount of information about the libraries being used, but most importantly we havethe name and version number.
Dependency-Check does support packages.config and .nuspec, but today we are going to convert to a .csproj. Well, kinda. It doesn't require an actual valid .csproj file. It just needs a valid xml document with PackageReference elements with the appropriate attributes. I'm going to go ahead and do some quick powershell to make a pseudo .csproj out of our projects.assets.json.
Now time to run Dependency-Check one more time.
And one last look at the report. Seems like we caught some actual vulnerabilities in the transitive dependencies that we were not aware of.
Of course when you add your workaround to your build pipeline you are going to want to loop over all the project's project.assets.json. My recommendation is to always save the pseudo .csproj within the same project so it can be easy to see within the OWASP Dependency-Check report which project the vulnerabilities came from.
Post a Comment