File tree Expand file tree Collapse file tree 4 files changed +108
-0
lines changed
test/library-tests/MemberRefExpr Expand file tree Collapse file tree 4 files changed +108
-0
lines changed Original file line number Diff line number Diff line change @@ -1225,6 +1225,27 @@ class MemberRefExpr extends FunctionalExpr, @memberref {
1225
1225
*/
1226
1226
override Method asMethod ( ) { result = getAnonymousClass ( ) .getAMethod ( ) }
1227
1227
1228
+ /**
1229
+ * Gets the receiver type whose member this expression refers to. The result might not be
1230
+ * the type which actually declares the member (makes a difference for inherited non-overridden
1231
+ * methods).
1232
+ */
1233
+ RefType getReceiverType ( ) {
1234
+ exists ( Stmt stmt , Expr resultExpr |
1235
+ stmt = asMethod ( ) .getBody ( ) .( SingletonBlock ) .getStmt ( ) and
1236
+ (
1237
+ resultExpr = stmt .( ReturnStmt ) .getResult ( )
1238
+ or
1239
+ // Note: Currently never an ExprStmt, but might change once https://github.com/github/codeql/issues/3605 is fixed
1240
+ resultExpr = stmt .( ExprStmt ) .getExpr ( )
1241
+ )
1242
+ |
1243
+ result = resultExpr .( MethodAccess ) .getReceiverType ( ) or
1244
+ result = resultExpr .( ClassInstanceExpr ) .getConstructedType ( ) or
1245
+ result = resultExpr .( ArrayCreationExpr ) .getType ( )
1246
+ )
1247
+ }
1248
+
1228
1249
/**
1229
1250
* Gets the method or constructor referenced by this member reference expression.
1230
1251
*/
Original file line number Diff line number Diff line change
1
+ | Test.java:24:26:24:51 | ...::... | Inner<>.Inner<> | Test$Generic$Inner.class:0:0:0:0 | Inner<> |
2
+ | Test.java:38:29:38:42 | ...::... | Object.toString | Test.java:1:7:1:10 | Test |
3
+ | Test.java:39:29:39:42 | ...::... | Object.hashCode | Test.java:1:7:1:10 | Test |
4
+ | Test.java:40:29:40:39 | ...::... | Object.clone | Test.java:1:7:1:10 | Test |
5
+ | Test.java:41:40:41:64 | ...::... | Object.toString | Test$Generic.class:0:0:0:0 | Generic<String> |
6
+ | Test.java:43:23:43:36 | ...::... | Object.toString | Test.java:1:7:1:10 | Test |
7
+ | Test.java:44:23:44:36 | ...::... | Object.hashCode | Test.java:1:7:1:10 | Test |
8
+ | Test.java:45:23:45:33 | ...::... | Object.clone | Test.java:1:7:1:10 | Test |
9
+ | Test.java:48:22:48:35 | ...::... | Object.toString | Test.java:1:7:1:10 | Test |
10
+ | Test.java:51:13:51:21 | ...::... | Test.Test | Test.java:1:7:1:10 | Test |
11
+ | Test.java:52:13:52:32 | ...::... | Generic<String>.Generic<String> | Test$Generic.class:0:0:0:0 | Generic<String> |
12
+ | Test.java:56:13:56:22 | ...::... | | file://:0:0:0:0 | int[] |
13
+ | Test.java:57:13:57:26 | ...::... | | file://:0:0:0:0 | Generic<>[] |
14
+ | Test.java:61:31:61:47 | ...::... | Test.doSomething | Test.java:1:7:1:10 | Test |
Original file line number Diff line number Diff line change
1
+ import java
2
+
3
+ string getReferencedCallable ( MemberRefExpr e ) {
4
+ if exists ( e .getReferencedCallable ( ) )
5
+ then result = e .getReferencedCallable ( ) .getQualifiedName ( )
6
+ else result = ""
7
+ }
8
+
9
+ from MemberRefExpr e
10
+ select e , getReferencedCallable ( e ) , e .getReceiverType ( )
Original file line number Diff line number Diff line change
1
+ class Test {
2
+ interface Function <T > {
3
+ Object apply (T o ) throws Exception ;
4
+ }
5
+
6
+ interface IntFunction {
7
+ Object apply (int i );
8
+ }
9
+
10
+ interface Supplier {
11
+ Object get () throws Exception ;
12
+ }
13
+
14
+ public Test () { }
15
+
16
+ static class Generic <T > {
17
+ public Generic () { }
18
+
19
+ class Inner {
20
+ public Inner () { }
21
+ }
22
+
23
+ void test () {
24
+ Supplier s = Generic <Number >.Inner ::new ;
25
+ }
26
+ }
27
+
28
+ void doSomething () { }
29
+
30
+ static class Sub extends Test {
31
+ }
32
+
33
+ interface SubtypeConsumer {
34
+ void consume (Sub s );
35
+ }
36
+
37
+ void test () {
38
+ Function <Test > f0 = Test ::toString ;
39
+ Function <Test > f1 = Test ::hashCode ;
40
+ Function <Test > f2 = Test ::clone ;
41
+ Function <Generic <String >> f3 = Generic <String >::toString ;
42
+
43
+ Supplier s0 = this ::toString ;
44
+ Supplier s1 = this ::hashCode ;
45
+ Supplier s2 = this ::clone ;
46
+
47
+ // Discards result of method call
48
+ Runnable r = this ::toString ;
49
+
50
+ Supplier [] classInstances = {
51
+ Test ::new ,
52
+ Generic <String >::new ,
53
+ };
54
+
55
+ IntFunction [] arrays = {
56
+ int []::new ,
57
+ Generic []::new ,
58
+ };
59
+
60
+ // SubtypeConsumer has `Sub` as parameter type, but receiver here is `Test` (supertype)
61
+ SubtypeConsumer sub = Test ::doSomething ;
62
+ }
63
+ }
You can’t perform that action at this time.
0 commit comments