mirror of
https://github.com/github/codeql.git
synced 2025-12-24 04:36:35 +01:00
add queries for more popular libs
This commit is contained in:
@@ -5,7 +5,6 @@
|
||||
<overview>
|
||||
<p>Extracting Compressed files with any compression algorithm like gzip can cause to denial of service attacks.</p>
|
||||
<p>Attackers can compress a huge file which created by repeated similiar byte and convert it to a small compressed file.</p>
|
||||
|
||||
</overview>
|
||||
<recommendation>
|
||||
|
||||
@@ -25,8 +24,13 @@ An Unsafe Approach can be this example which we don't check for uncompressed siz
|
||||
<sample src="example_bad.cpp" />
|
||||
|
||||
</example>
|
||||
|
||||
<references>
|
||||
|
||||
<li>
|
||||
<a href="https://zlib.net/manual.html">Zlib Documentation</a>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<a href="https://www.bamsoftware.com/hacks/zipbomb/">A great research to gain more impact by this kind of attacks</a>
|
||||
</li>
|
||||
|
||||
@@ -0,0 +1,107 @@
|
||||
/**
|
||||
* @name User-controlled file decompression
|
||||
* @description User-controlled data that flows into decompression library APIs without checking the compression rate is dangerous
|
||||
* @kind path-problem
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression-brotli
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
*/
|
||||
|
||||
// https://github.com/google/brotli
|
||||
import cpp
|
||||
import semmle.code.cpp.ir.dataflow.TaintTracking
|
||||
import semmle.code.cpp.security.FlowSources
|
||||
import semmle.code.cpp.commons.File
|
||||
|
||||
/**
|
||||
* A Pointer Variable is used in Flow source
|
||||
*/
|
||||
private class PointerVar extends VariableAccess {
|
||||
PointerVar() { this.getType() instanceof PointerType }
|
||||
}
|
||||
|
||||
/**
|
||||
* A Pointer Variable is used in Flow source
|
||||
*/
|
||||
private class Uint8Var extends VariableAccess {
|
||||
Uint8Var() { this.getType() instanceof UInt8_t }
|
||||
}
|
||||
|
||||
/**
|
||||
* A ZSTD_inBuffer Variable is used in Flow source
|
||||
*/
|
||||
private class ZSTDinBufferVar extends VariableAccess {
|
||||
ZSTDinBufferVar() { this.getType().hasName("ZSTD_inBuffer") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `ZSTD_decompress_usingDDict` function is used in Flow sink
|
||||
* Ref: https://www.brotli.org/decode.html#af68
|
||||
*/
|
||||
private class BrotliDecoderDecompressFunction extends Function {
|
||||
BrotliDecoderDecompressFunction() { this.hasGlobalName(["BrotliDecoderDecompress"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `BrotliDecoderDecompressStream` function is used in Flow sink
|
||||
* Ref: https://www.brotli.org/decode.html#a234
|
||||
*/
|
||||
private class BrotliDecoderDecompressStreamFunction extends Function {
|
||||
BrotliDecoderDecompressStreamFunction() { this.hasGlobalName(["BrotliDecoderDecompressStream"]) }
|
||||
}
|
||||
|
||||
module BrotliTaintConfig implements DataFlow::StateConfigSig {
|
||||
class FlowState = DataFlow::FlowState;
|
||||
|
||||
predicate isSource(DataFlow::Node source, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof AllocationFunction |
|
||||
fc = source.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fopenCall(fc) |
|
||||
fc = source.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
source.asExpr() instanceof PointerVar and
|
||||
state = ""
|
||||
or
|
||||
source.asExpr() instanceof Uint8Var and
|
||||
state = ""
|
||||
}
|
||||
|
||||
predicate isSink(DataFlow::Node sink, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof BrotliDecoderDecompressStreamFunction |
|
||||
fc.getArgument(2) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof BrotliDecoderDecompressFunction |
|
||||
fc.getArgument(1) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, DataFlow::FlowState state1, DataFlow::Node node2,
|
||||
DataFlow::FlowState state2
|
||||
) {
|
||||
none()
|
||||
}
|
||||
|
||||
predicate isBarrier(DataFlow::Node node, DataFlow::FlowState state) { none() }
|
||||
}
|
||||
|
||||
module BrotliTaint = TaintTracking::GlobalWithState<BrotliTaintConfig>;
|
||||
|
||||
import BrotliTaint::PathGraph
|
||||
|
||||
from BrotliTaint::PathNode source, BrotliTaint::PathNode sink
|
||||
where BrotliTaint::flowPath(source, sink)
|
||||
select sink.getNode(), source, sink, "This Decompression depends on a $@.", source.getNode(),
|
||||
"potentially untrusted source"
|
||||
@@ -0,0 +1,126 @@
|
||||
/**
|
||||
* @name User-controlled file decompression
|
||||
* @description User-controlled data that flows into decompression library APIs without checking the compression rate is dangerous
|
||||
* @kind path-problem
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression-bzip2
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
*/
|
||||
|
||||
import cpp
|
||||
import semmle.code.cpp.ir.dataflow.TaintTracking
|
||||
import semmle.code.cpp.security.FlowSources
|
||||
import semmle.code.cpp.commons.File
|
||||
|
||||
/**
|
||||
* A `bz_stream` Variable as a Flow source
|
||||
*/
|
||||
private class BzStreamVar extends VariableAccess {
|
||||
BzStreamVar() { this.getType().hasName("bz_stream") }
|
||||
}
|
||||
|
||||
/**
|
||||
* A `BZFILE` Variable as a Flow source
|
||||
*/
|
||||
private class BZFILEVar extends VariableAccess {
|
||||
BZFILEVar() { this.getType().hasName("BZFILE") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `BZ2_bzopen`,`BZ2_bzdopen` functions as a Flow source
|
||||
*/
|
||||
private class BZ2BzopenFunction extends Function {
|
||||
BZ2BzopenFunction() { this.hasGlobalName(["BZ2_bzopen", "BZ2_bzdopen"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `BZ2_bzDecompress` function as a Flow source
|
||||
*/
|
||||
private class BZ2BzDecompressFunction extends Function {
|
||||
BZ2BzDecompressFunction() { this.hasGlobalName(["BZ2_bzDecompress"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `BZ2_bzReadOpen` function
|
||||
*/
|
||||
private class BZ2BzReadOpenFunction extends Function {
|
||||
BZ2BzReadOpenFunction() { this.hasGlobalName(["BZ2_bzReadOpen"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `BZ2_bzRead` function is used in Flow sink
|
||||
*/
|
||||
private class BZ2BzReadFunction extends Function {
|
||||
BZ2BzReadFunction() { this.hasGlobalName("BZ2_bzRead") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `BZ2_bzRead` function is used in Flow sink
|
||||
*/
|
||||
private class BZ2BzBuffToBuffDecompressFunction extends Function {
|
||||
BZ2BzBuffToBuffDecompressFunction() { this.hasGlobalName("BZ2_bzBuffToBuffDecompress") }
|
||||
}
|
||||
|
||||
/**
|
||||
* https://www.sourceware.org/bzip2/manual/manual.html
|
||||
*/
|
||||
module Bzip2TaintConfig implements DataFlow::StateConfigSig {
|
||||
class FlowState = DataFlow::FlowState;
|
||||
|
||||
predicate isSource(DataFlow::Node source, DataFlow::FlowState state) {
|
||||
source.asExpr() instanceof BzStreamVar and
|
||||
state = ""
|
||||
or
|
||||
source.asExpr() instanceof BZFILEVar and
|
||||
state = ""
|
||||
or
|
||||
// will flow into BZ2BzReadOpenFunction
|
||||
exists(FunctionCall fc | fopenCall(fc) |
|
||||
fc = source.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
}
|
||||
|
||||
predicate isSink(DataFlow::Node sink, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof BZ2BzDecompressFunction |
|
||||
fc.getArgument(0) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof BZ2BzReadFunction |
|
||||
fc.getArgument(1) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof BZ2BzBuffToBuffDecompressFunction |
|
||||
fc.getArgument(2) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, DataFlow::FlowState state1, DataFlow::Node node2,
|
||||
DataFlow::FlowState state2
|
||||
) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof BZ2BzReadOpenFunction |
|
||||
node1.asExpr() = fc.getArgument(1) and
|
||||
node2.asExpr() = fc and
|
||||
state1 = "" and
|
||||
state2 = ""
|
||||
)
|
||||
}
|
||||
|
||||
predicate isBarrier(DataFlow::Node node, DataFlow::FlowState state) { none() }
|
||||
}
|
||||
|
||||
module Bzip2Taint = TaintTracking::GlobalWithState<Bzip2TaintConfig>;
|
||||
|
||||
import Bzip2Taint::PathGraph
|
||||
|
||||
from Bzip2Taint::PathNode source, Bzip2Taint::PathNode sink
|
||||
where Bzip2Taint::flowPath(source, sink)
|
||||
select sink.getNode(), source, sink, "This Decompressiondepends on a $@.", source.getNode(),
|
||||
"potentially untrusted source"
|
||||
@@ -0,0 +1,102 @@
|
||||
/**
|
||||
* @name User-controlled file decompression
|
||||
* @description User-controlled data that flows into decompression library APIs without checking the compression rate is dangerous
|
||||
* @kind path-problem
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression-minizip
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
*/
|
||||
|
||||
import cpp
|
||||
import semmle.code.cpp.ir.dataflow.TaintTracking
|
||||
import semmle.code.cpp.security.FlowSources
|
||||
|
||||
/**
|
||||
* A `unzFile` Variable as a Flow source
|
||||
*/
|
||||
private class UnzFileVar extends VariableAccess {
|
||||
UnzFileVar() { this.getType().hasName("unzFile") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `UnzOpen` function as a Flow source
|
||||
*/
|
||||
private class UnzOpenFunction extends Function {
|
||||
UnzOpenFunction() { this.hasGlobalName(["UnzOpen", "unzOpen64", "unzOpen2", "unzOpen2_64"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `mz_stream_open` function is used in Flow source
|
||||
*/
|
||||
private class MzStreamOpenFunction extends Function {
|
||||
MzStreamOpenFunction() { this.hasGlobalName("mz_stream_open") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `unzReadCurrentFile` function is used in Flow sink
|
||||
*/
|
||||
private class UnzReadCurrentFileFunction extends Function {
|
||||
UnzReadCurrentFileFunction() { this.hasGlobalName(["unzReadCurrentFile"]) }
|
||||
}
|
||||
|
||||
module MiniZipTaintConfig implements DataFlow::StateConfigSig {
|
||||
class FlowState = DataFlow::FlowState;
|
||||
|
||||
predicate isSource(DataFlow::Node source, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof UnzOpenFunction |
|
||||
fc.getArgument(0) = source.asExpr() and
|
||||
state = "unzFile"
|
||||
)
|
||||
or
|
||||
source.asExpr() instanceof UnzFileVar and
|
||||
state = "unzFile"
|
||||
or
|
||||
// TO Check
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof MzStreamOpenFunction |
|
||||
fc.getArgument(0).getEnclosingVariable() = source.asVariable() and
|
||||
state = "MzStream"
|
||||
)
|
||||
or
|
||||
// TO Check
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof MzStreamOpenFunction |
|
||||
fc.getArgument(0).getEnclosingVariable() = source.asVariable() and
|
||||
state = "MzStream"
|
||||
)
|
||||
}
|
||||
|
||||
predicate isSink(DataFlow::Node sink, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof UnzReadCurrentFileFunction |
|
||||
fc.getArgument(0) = sink.asExpr() and
|
||||
state = "unzFile"
|
||||
// and not sanitizer(fc)
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, DataFlow::FlowState state1, DataFlow::Node node2,
|
||||
DataFlow::FlowState state2
|
||||
) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof UnzOpenFunction |
|
||||
node1.asExpr() = fc.getArgument(0) and
|
||||
node2.asExpr() = fc and
|
||||
state1 = "" and
|
||||
state2 = "unzFile"
|
||||
)
|
||||
}
|
||||
|
||||
predicate isBarrier(DataFlow::Node node, DataFlow::FlowState state) { none() }
|
||||
}
|
||||
|
||||
|
||||
module MiniZipTaint = TaintTracking::GlobalWithState<MiniZipTaintConfig>;
|
||||
|
||||
import MiniZipTaint::PathGraph
|
||||
|
||||
from MiniZipTaint::PathNode source, MiniZipTaint::PathNode sink
|
||||
where MiniZipTaint::flowPath(source, sink)
|
||||
select sink.getNode(), source, sink, "This Decompressiondepends on a $@.", source.getNode(),
|
||||
"potentially untrusted source"
|
||||
@@ -0,0 +1,100 @@
|
||||
/**
|
||||
* @name User-controlled file decompression
|
||||
* @description User-controlled data that flows into decompression library APIs without checking the compression rate is dangerous
|
||||
* @kind path-problem
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression-xz
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
*/
|
||||
|
||||
import cpp
|
||||
import semmle.code.cpp.ir.dataflow.TaintTracking
|
||||
import semmle.code.cpp.security.FlowSources
|
||||
|
||||
/**
|
||||
* A Pointer Variable as a Flow source
|
||||
*/
|
||||
private class Uint8Var extends VariableAccess {
|
||||
Uint8Var() { this.getType() instanceof UInt8_t }
|
||||
}
|
||||
|
||||
/**
|
||||
* A `lzma_stream` Variable as a Flow source
|
||||
*/
|
||||
private class LzmaStreamVar extends VariableAccess {
|
||||
LzmaStreamVar() { this.getType().hasName("lzma_stream") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `lzma_*_decoder` function is used as a required condition for decompression
|
||||
*/
|
||||
private class LzmaDecoderFunction extends Function {
|
||||
LzmaDecoderFunction() {
|
||||
this.hasGlobalName(["lzma_stream_decoder", "lzma_auto_decoder", "lzma_alone_decoder"])
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The `lzma_code` function is used in Flow sink
|
||||
*/
|
||||
private class LzmaCodeFunction extends Function {
|
||||
LzmaCodeFunction() { this.hasGlobalName(["lzma_code"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `lzma_stream_buffer_decode` function is used in Flow sink
|
||||
*/
|
||||
private class LzmaStreamBufferDecodeFunction extends Function {
|
||||
LzmaStreamBufferDecodeFunction() { this.hasGlobalName(["lzma_stream_buffer_decode"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* https://github.com/tukaani-project/xz
|
||||
*/
|
||||
module XzTaintConfig implements DataFlow::StateConfigSig {
|
||||
class FlowState = DataFlow::FlowState;
|
||||
|
||||
predicate isSource(DataFlow::Node source, DataFlow::FlowState state) {
|
||||
source.asExpr() instanceof LzmaStreamVar and
|
||||
state = ""
|
||||
or
|
||||
source.asExpr() instanceof Uint8Var and
|
||||
state = ""
|
||||
// and not exists(FunctionCall fc | fc.getTarget() instanceof LzmaStreamDecoderFunction)
|
||||
}
|
||||
|
||||
predicate isSink(DataFlow::Node sink, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof LzmaStreamBufferDecodeFunction |
|
||||
fc.getArgument(1) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof LzmaCodeFunction |
|
||||
fc.getArgument(0) = sink.asExpr() and
|
||||
state = ""
|
||||
) and
|
||||
exists(FunctionCall fc2 | fc2.getTarget() instanceof LzmaDecoderFunction)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, DataFlow::FlowState state1, DataFlow::Node node2,
|
||||
DataFlow::FlowState state2
|
||||
) {
|
||||
none()
|
||||
}
|
||||
|
||||
predicate isBarrier(DataFlow::Node node, DataFlow::FlowState state) { none() }
|
||||
}
|
||||
|
||||
module XzTaint = TaintTracking::GlobalWithState<XzTaintConfig>;
|
||||
|
||||
import XzTaint::PathGraph
|
||||
|
||||
from XzTaint::PathNode source, XzTaint::PathNode sink
|
||||
where XzTaint::flowPath(source, sink)
|
||||
select sink.getNode(), source, sink, "This Decompressiondepends on a $@.", source.getNode(),
|
||||
"potentially untrusted source"
|
||||
@@ -0,0 +1,140 @@
|
||||
/**
|
||||
* @name User-controlled file decompression
|
||||
* @description User-controlled data that flows into decompression library APIs without checking the compression rate is dangerous
|
||||
* @kind path-problem
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression-zstd
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
*/
|
||||
|
||||
// https://github.com/facebook/zstd/blob/dev/examples/streaming_decompression.c
|
||||
import cpp
|
||||
import semmle.code.cpp.ir.dataflow.TaintTracking
|
||||
import semmle.code.cpp.security.FlowSources
|
||||
import semmle.code.cpp.commons.File
|
||||
|
||||
// /**
|
||||
// * A Pointer Variable as a Flow source
|
||||
// */
|
||||
// private class PointerVar extends VariableAccess {
|
||||
// PointerVar() { this.getType() instanceof PointerType }
|
||||
// }
|
||||
/**
|
||||
* A ZSTD_inBuffer Variable as a Flow source
|
||||
*/
|
||||
private class ZSTDinBufferVar extends VariableAccess {
|
||||
ZSTDinBufferVar() { this.getType().hasName("ZSTD_inBuffer") }
|
||||
}
|
||||
|
||||
/**
|
||||
* A ZSTD_inBuffer_s Variable as a Flow source
|
||||
*/
|
||||
private class ZSTDinBufferSVar extends VariableAccess {
|
||||
ZSTDinBufferSVar() { this.getType().hasName("ZSTD_inBuffer_s") }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `ZSTD_decompress` function is used in Flow sink
|
||||
*/
|
||||
private class ZSTDDecompressFunction extends Function {
|
||||
ZSTDDecompressFunction() { this.hasGlobalName(["ZSTD_decompress"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `ZSTD_decompressDCtx` function is used in Flow sink
|
||||
*/
|
||||
private class ZSTDDecompressDCtxFunction extends Function {
|
||||
ZSTDDecompressDCtxFunction() { this.hasGlobalName(["ZSTD_decompressDCtx"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `ZSTD_decompressStream` function is used in Flow sink
|
||||
*/
|
||||
private class ZSTDDecompressStreamFunction extends Function {
|
||||
ZSTDDecompressStreamFunction() { this.hasGlobalName(["ZSTD_decompressStream"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `ZSTD_decompress_usingDDict` function is used in Flow sink
|
||||
*/
|
||||
private class ZSTDDecompressUsingDictFunction extends Function {
|
||||
ZSTDDecompressUsingDictFunction() { this.hasGlobalName(["ZSTD_decompress_usingDDict"]) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The `ZSTD_decompress_usingDDict` function is used in Flow sink
|
||||
*/
|
||||
private class ZSTDDecompressUsingDDictFunction extends Function {
|
||||
ZSTDDecompressUsingDDictFunction() { this.hasGlobalName(["ZSTD_decompress_usingDDict"]) }
|
||||
}
|
||||
|
||||
module ZstdTaintConfig implements DataFlow::StateConfigSig {
|
||||
class FlowState = DataFlow::FlowState;
|
||||
|
||||
predicate isSource(DataFlow::Node source, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof AllocationFunction |
|
||||
fc = source.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fopenCall(fc) |
|
||||
fc = source.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
source.asExpr() instanceof ZSTDinBufferSVar and
|
||||
state = ""
|
||||
or
|
||||
source.asExpr() instanceof ZSTDinBufferVar and
|
||||
state = ""
|
||||
}
|
||||
|
||||
predicate isSink(DataFlow::Node sink, DataFlow::FlowState state) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof ZSTDDecompressFunction |
|
||||
fc.getArgument(2) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof ZSTDDecompressDCtxFunction |
|
||||
fc.getArgument(3) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof ZSTDDecompressStreamFunction |
|
||||
fc.getArgument(2) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof ZSTDDecompressUsingDictFunction |
|
||||
fc.getArgument(3) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
or
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof ZSTDDecompressUsingDDictFunction |
|
||||
fc.getArgument(3) = sink.asExpr() and
|
||||
state = ""
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, DataFlow::FlowState state1, DataFlow::Node node2,
|
||||
DataFlow::FlowState state2
|
||||
) {
|
||||
none()
|
||||
}
|
||||
|
||||
predicate isBarrier(DataFlow::Node node, DataFlow::FlowState state) { none() }
|
||||
}
|
||||
|
||||
module ZstdTaint = TaintTracking::GlobalWithState<ZstdTaintConfig>;
|
||||
|
||||
import ZstdTaint::PathGraph
|
||||
|
||||
from ZstdTaint::PathNode source, ZstdTaint::PathNode sink
|
||||
where ZstdTaint::flowPath(source, sink)
|
||||
select sink.getNode(), source, sink, "This Decompression depends on a $@.", source.getNode(),
|
||||
"potentially untrusted source"
|
||||
@@ -5,7 +5,7 @@
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression1
|
||||
* @id cpp/user-controlled-file-zlibgz
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
@@ -5,7 +5,7 @@
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression2
|
||||
* @id cpp/user-controlled-file-zlibinflator
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
@@ -41,13 +41,6 @@ module ZlibTaintConfig implements DataFlow::ConfigSig {
|
||||
fc.getArgument(0) = sink.asExpr()
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(DataFlow::Node node1, DataFlow::Node node2) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof InflateFunction |
|
||||
node1.asExpr() = fc.getArgument(0) and
|
||||
node2.asExpr() = fc
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
module ZlibTaint = TaintTracking::Global<ZlibTaintConfig>;
|
||||
@@ -5,7 +5,7 @@
|
||||
* @problem.severity error
|
||||
* @security-severity 7.8
|
||||
* @precision high
|
||||
* @id cpp/user-controlled-file-decompression3
|
||||
* @id cpp/user-controlled-file-zlibuncompress
|
||||
* @tags security
|
||||
* experimental
|
||||
* external/cwe/cwe-409
|
||||
@@ -37,13 +37,6 @@ module ZlibTaintConfig implements DataFlow::ConfigSig {
|
||||
fc.getArgument(0) = sink.asExpr()
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(DataFlow::Node node1, DataFlow::Node node2) {
|
||||
exists(FunctionCall fc | fc.getTarget() instanceof UncompressFunction |
|
||||
node1.asExpr() = fc.getArgument(0) and
|
||||
node2.asExpr() = fc
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
module ZlibTaint = TaintTracking::Global<ZlibTaintConfig>;
|
||||
@@ -1,3 +1,8 @@
|
||||
#include <iostream>
|
||||
#include <vector>
|
||||
#include "zlib.h"
|
||||
#include <cstdio>
|
||||
#include <cstring>
|
||||
|
||||
int UnsafeInflate(int argc, char *argv[]) {
|
||||
// original string len = 36
|
||||
|
||||
@@ -1,3 +1,8 @@
|
||||
#include <iostream>
|
||||
#include <vector>
|
||||
#include "zlib.h"
|
||||
#include <cstdio>
|
||||
#include <cstring>
|
||||
|
||||
int SafeGzread() {
|
||||
std::cout << "enter compressed file name!\n" << std::endl;
|
||||
|
||||
Reference in New Issue
Block a user