@@ -81,8 +81,34 @@ module Fasthttp {
81
81
}
82
82
}
83
83
84
+ private predicate responseBodyWriterResult ( DataFlow:: Node src ) {
85
+ exists ( Method responseBodyWriter |
86
+ responseBodyWriter .hasQualifiedName ( packagePath ( ) , "Response" , "BodyWriter" ) and
87
+ src = responseBodyWriter .getACall ( ) .getResult ( 0 )
88
+ )
89
+ }
90
+
91
+ private predicate writerSinkAndBody ( DataFlow:: Node sink , DataFlow:: Node body ) {
92
+ exists ( DataFlow:: CallNode writerCall |
93
+ writerCall = any ( Method write | write .hasQualifiedName ( "io" , "Writer" , "Write" ) ) .getACall ( ) and
94
+ sink = writerCall .getReceiver ( ) and
95
+ body = writerCall .getArgument ( 0 )
96
+ )
97
+ or
98
+ exists ( DataFlow:: CallNode writerCall |
99
+ writerCall = any ( Function fprintf | fprintf .hasQualifiedName ( "fmt" , "Fprintf" ) ) .getACall ( ) and
100
+ sink = writerCall .getArgument ( 0 ) and
101
+ body = writerCall .getSyntacticArgument ( any ( int i | i > 1 ) )
102
+ )
103
+ }
104
+
105
+ private predicate writerSink ( DataFlow:: Node sink ) { writerSinkAndBody ( sink , _) }
106
+
107
+ private module ResponseBodyWriterFlow =
108
+ DataFlow:: SimpleGlobal< responseBodyWriterResult / 1 > :: Graph< writerSink / 1 > ;
109
+
84
110
private class ResponseBody extends Http:: ResponseBody:: Range {
85
- DataFlow:: MethodCallNode call ;
111
+ DataFlow:: MethodCallNode responseWriterMethodCall ;
86
112
87
113
ResponseBody ( ) {
88
114
exists ( Method m |
@@ -91,32 +117,24 @@ module Fasthttp {
91
117
"AppendBody" , "AppendBodyString" , "SetBody" , "SetBodyRaw" , "SetBodyStream" ,
92
118
"SetBodyString" , "Success" , "SuccessString"
93
119
] ) and
94
- call = m .getACall ( ) and
95
- this = call .getArgument ( 0 )
120
+ responseWriterMethodCall = m .getACall ( ) and
121
+ this = responseWriterMethodCall .getArgument ( 0 )
96
122
or
97
123
m .hasQualifiedName ( packagePath ( ) , "RequestCtx" , [ "Success" , "SuccessString" ] ) and
98
- call = m .getACall ( ) and
99
- this = call .getArgument ( 1 )
100
- )
101
- or
102
- exists ( Method responseBodyWriter , DataFlow:: CallNode writerCall |
103
- responseBodyWriter .hasQualifiedName ( packagePath ( ) , "Response" , "BodyWriter" ) and
104
- call = responseBodyWriter .getACall ( ) and
105
- writerCall = any ( Method write | write .hasQualifiedName ( "io" , "Writer" , "Write" ) ) .getACall ( ) and
106
- this = writerCall .getArgument ( 0 ) and
107
- DataFlow:: localFlow ( call .getResult ( 0 ) , writerCall .getReceiver ( ) )
124
+ responseWriterMethodCall = m .getACall ( ) and
125
+ this = responseWriterMethodCall .getArgument ( 1 )
108
126
)
109
127
or
110
- exists ( Method responseBodyWriter , DataFlow:: CallNode writerCall |
111
- responseBodyWriter .hasQualifiedName ( packagePath ( ) , "Response" , "BodyWriter" ) and
112
- call = responseBodyWriter .getACall ( ) and
113
- writerCall = any ( Function fprintf | fprintf .hasQualifiedName ( "fmt" , "Fprintf" ) ) .getACall ( ) and
114
- this = writerCall .getSyntacticArgument ( any ( int i | i > 1 ) ) and
115
- DataFlow:: localFlow ( call .getResult ( 0 ) , writerCall .getArgument ( 0 ) )
128
+ exists ( ResponseBodyWriterFlow:: PathNode source , ResponseBodyWriterFlow:: PathNode sink |
129
+ ResponseBodyWriterFlow:: flowPath ( source , sink ) and
130
+ responseWriterMethodCall = source .getNode ( ) and
131
+ writerSinkAndBody ( sink .getNode ( ) , this )
116
132
)
117
133
}
118
134
119
- override Http:: ResponseWriter getResponseWriter ( ) { result .getANode ( ) = call .getReceiver ( ) }
135
+ override Http:: ResponseWriter getResponseWriter ( ) {
136
+ result .getANode ( ) = responseWriterMethodCall .getReceiver ( )
137
+ }
120
138
}
121
139
122
140
/**
0 commit comments