@@ -67,14 +67,20 @@ module EventEmitter {
6767 /** Gets the name of the channel if possible. */
6868 abstract string getChannel ( ) ;
6969
70- /** Gets the `i`th parameter in the callback registered as the event handler. */
71- abstract DataFlow:: Node getCallbackParameter ( int i ) ;
70+ /** Gets the `i`th parameter in the event handler. */
71+ abstract DataFlow:: Node getEventHandlerParameter ( int i ) ;
7272
7373 /**
74- * Gets a value that is returned by the event handler to the `dispatch` where the event was dispatched .
74+ * Gets a value that is returned by the event handler.
7575 * The default implementation is that no value can be returned.
7676 */
77- DataFlow:: Node getAReturnedValue ( EventDispatch dispatch ) { none ( ) }
77+ DataFlow:: Node getAReturnedValue ( ) { none ( ) }
78+
79+ /**
80+ * Holds if this event handler can return a value to the given `dispatch`.
81+ * The default implementation is that there exists no such dispatch.
82+ */
83+ predicate canReturnTo ( EventDispatch dispatch ) { none ( ) }
7884 }
7985
8086 /**
@@ -117,16 +123,17 @@ module EventEmitter {
117123 override predicate step ( DataFlow:: Node pred , DataFlow:: Node succ ) {
118124 exists ( int i | i >= 0 |
119125 pred = dispatch .getDispatchedArgument ( i ) and
120- succ = reg .getCallbackParameter ( i )
126+ succ = reg .getEventHandlerParameter ( i )
121127 )
122128 or
123- pred = reg .getAReturnedValue ( dispatch ) and
129+ reg .canReturnTo ( dispatch ) and
130+ pred = reg .getAReturnedValue ( ) and
124131 succ = dispatch
125132 }
126133 }
127134
128135 /**
129- * Concrete classes for modelling EventEmitter in NodeJS.
136+ * Concrete classes for modeling EventEmitter in NodeJS.
130137 */
131138 private module NodeJSEventEmitter {
132139 private class NodeJSEventEmitter extends EventEmitter {
@@ -141,20 +148,16 @@ module EventEmitter {
141148 }
142149
143150 private class EventEmitterRegistration extends EventRegistration , DataFlow:: MethodCallNode {
144- override EventEmitter emitter ;
145-
146151 EventEmitterRegistration ( ) { this = emitter .ref ( ) .getAMethodCall ( EventEmitter:: on ( ) ) }
147152
148153 override string getChannel ( ) { this .getArgument ( 0 ) .mayHaveStringValue ( result ) }
149154
150- override DataFlow:: Node getCallbackParameter ( int i ) {
155+ override DataFlow:: Node getEventHandlerParameter ( int i ) {
151156 result = this .( DataFlow:: MethodCallNode ) .getABoundCallbackParameter ( 1 , i )
152157 }
153158 }
154159
155160 private class EventEmitterDispatch extends EventDispatch , DataFlow:: MethodCallNode {
156- override EventEmitter emitter ;
157-
158161 EventEmitterDispatch ( ) {
159162 this = emitter .ref ( ) .getAMethodCall ( "emit" )
160163 }
0 commit comments