@@ -59,8 +59,8 @@ private predicate isFileConstructorArgument(Expr expSource, Expr exprDest) {
5959 */
6060private class TaintFollowingFileMethod extends Method {
6161 TaintFollowingFileMethod ( ) {
62- getDeclaringType ( ) instanceof TypeFile and
63- hasName ( [ "getAbsoluteFile" , "getCanonicalFile" ] )
62+ this . getDeclaringType ( ) instanceof TypeFile and
63+ this . hasName ( [ "getAbsoluteFile" , "getCanonicalFile" ] )
6464 }
6565}
6666
@@ -80,3 +80,50 @@ predicate isAdditionalFileTaintStep(DataFlow::Node node1, DataFlow::Node node2)
8080 isFileConstructorArgument ( node1 .asExpr ( ) , node2 .asExpr ( ) ) or
8181 isTaintPropagatingFileTransformation ( node1 .asExpr ( ) , node2 .asExpr ( ) )
8282}
83+
84+ /**
85+ * A method call to `java.io.File::setReadable`.
86+ */
87+ private class FileSetRedableMethodAccess extends MethodAccess {
88+ FileSetRedableMethodAccess ( ) {
89+ exists ( Method m | this .getMethod ( ) = m |
90+ m .getDeclaringType ( ) instanceof TypeFile and
91+ m .hasName ( "setReadable" )
92+ )
93+ }
94+
95+ predicate isCallWithArguments ( boolean arg1 , boolean arg2 ) {
96+ this .isCallWithArgument ( 0 , arg1 ) and this .isCallToSecondArgumentWithValue ( arg2 )
97+ }
98+
99+ private predicate isCallToSecondArgumentWithValue ( boolean value ) {
100+ this .getMethod ( ) .getNumberOfParameters ( ) = 1 and value = true
101+ or
102+ isCallWithArgument ( 1 , value )
103+ }
104+
105+ private predicate isCallWithArgument ( int index , boolean arg ) {
106+ DataFlow:: localExprFlow ( any ( CompileTimeConstantExpr e | e .getBooleanValue ( ) = arg ) ,
107+ this .getArgument ( index ) )
108+ }
109+ }
110+
111+ /**
112+ * Hold's if temporary directory's use is protected if there is an explicit call to
113+ * `setReadable(false, false)`, then `setRedabale(true, true)`.
114+ */
115+ predicate isPermissionsProtectedTempDirUse ( DataFlow:: Node sink ) {
116+ exists ( FileSetRedableMethodAccess setReadable1 , FileSetRedableMethodAccess setReadable2 |
117+ setReadable1 .isCallWithArguments ( false , false ) and
118+ setReadable2 .isCallWithArguments ( true , true )
119+ |
120+ exists ( DataFlow:: Node setReadableNode1 , DataFlow:: Node setReadableNode2 |
121+ setReadableNode1 .asExpr ( ) = setReadable1 .getQualifier ( ) and
122+ setReadableNode2 .asExpr ( ) = setReadable2 .getQualifier ( )
123+ |
124+ DataFlow:: localFlow ( sink , setReadableNode1 ) and // Flow from sink to setReadable(false, false)
125+ DataFlow:: localFlow ( sink , setReadableNode2 ) and // Flow from sink to setReadable(true, true)
126+ DataFlow:: localFlow ( setReadableNode1 , setReadableNode2 ) // Flow from setReadable(false, false) to setReadable(true, true)
127+ )
128+ )
129+ }
0 commit comments