Skip to content

Commit 9c8b1ae

Browse files
committed
add modern dubbo support
1 parent 8219898 commit 9c8b1ae

File tree

16 files changed

+308
-100
lines changed

16 files changed

+308
-100
lines changed

dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/asm/AsmMethods.java

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -140,9 +140,7 @@ static Method getAsmMethod(final Class<?> clazz,
140140
SpyDispatcher.class,
141141
"leaveDubbo",
142142
Object.class,
143-
Object.class,
144-
Object.class,
145-
byte.class
143+
Object.class
146144
);
147145
Method SPY$isFirstLevelDubbo = InnerHelper.getAsmMethod(
148146
SpyDispatcher.class,
@@ -175,6 +173,13 @@ static Method getAsmMethod(final Class<?> clazz,
175173
String.class
176174
);
177175

176+
Method SPY$collectDubboResponse = InnerHelper.getAsmMethod(
177+
SpyDispatcher.class,
178+
"collectDubboResponse",
179+
Object.class,
180+
byte.class
181+
);
182+
178183
Method SPY$enterSource = InnerHelper.getAsmMethod(
179184
SpyDispatcher.class,
180185
"enterSource"

dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/DispatchDubbo.java

Lines changed: 21 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,20 +6,32 @@
66
import org.objectweb.asm.ClassVisitor;
77

88
public class DispatchDubbo implements DispatchPlugin {
9-
public static final String LEGACY_DUBBO_SYNC_HANDLER = " com.alibaba.dubbo.rpc.listener.ListenerInvokerWrapper".substring(1);
10-
public static final String LEGACY_DUBBO_EXCHANGE_HANDLER = " com.alibaba.dubbo.remoting.exchange.support.header.HeaderExchangeHandler".substring(1);
11-
public static final String LEGACY_DUBBO_PROXY_HANDLER = " com.alibaba.dubbo.rpc.proxy.AbstractProxyInvoker".substring(1);
9+
public static final String ALIBABA_DUBBO_SYNC_HANDLER = " com.alibaba.dubbo.rpc.listener.ListenerInvokerWrapper".substring(1);
10+
public static final String APACHE_DUBBO_SYNC_HANDLER = " org.apache.dubbo.rpc.listener.ListenerInvokerWrapper".substring(1);
11+
public static final String ALIBABA_DUBBO_EXCHANGE_HANDLER = " com.alibaba.dubbo.remoting.exchange.support.header.HeaderExchangeHandler".substring(1);
12+
public static final String APACHE_DUBBO_EXCHANGE_HANDLER = " org.apache.dubbo.remoting.exchange.support.header.HeaderExchangeHandler".substring(1);
13+
public static final String APACHE_DUBBO_EXCHANGE_CHANNEL = " org.apache.dubbo.remoting.exchange.support.header.HeaderExchangeChannel".substring(1);
14+
public static final String ALIBABA_DUBBO_PROXY_HANDLER = " com.alibaba.dubbo.rpc.proxy.AbstractProxyInvoker".substring(1);
15+
public static final String APACHE_DUBBO_PROXY_HANDLER = " org.apache.dubbo.rpc.proxy.AbstractProxyInvoker".substring(1);
1216

1317
@Override
1418
public ClassVisitor dispatch(ClassVisitor classVisitor, ClassContext context, Policy policy) {
1519
String className = context.getClassName();
1620

17-
if (LEGACY_DUBBO_SYNC_HANDLER.equals(className)) {
18-
classVisitor = new LegacyDubboSyncHandlerAdapter(classVisitor, context);
19-
} else if (LEGACY_DUBBO_EXCHANGE_HANDLER.equals(className)) {
20-
classVisitor = new LegacyDubboExchangeHandlerAdapter(classVisitor, context);
21-
} else if (LEGACY_DUBBO_PROXY_HANDLER.equals(className)) {
22-
classVisitor = new LegacyDubboProxyHandlerAdapter(classVisitor, context);
21+
if (ALIBABA_DUBBO_SYNC_HANDLER.equals(className)) {
22+
classVisitor = new DubboSyncHandlerAdapter(classVisitor, context, " com.alibaba".substring(1));
23+
} else if (APACHE_DUBBO_SYNC_HANDLER.equals(className)) {
24+
classVisitor = new DubboSyncHandlerAdapter(classVisitor, context, " org.apache".substring(1));
25+
} else if (ALIBABA_DUBBO_EXCHANGE_HANDLER.equals(className)) {
26+
classVisitor = new DubboExchangeHandlerAdapter(classVisitor, context, " com.alibaba".substring(1));
27+
} else if (APACHE_DUBBO_EXCHANGE_HANDLER.equals(className)) {
28+
classVisitor = new DubboExchangeHandlerAdapter(classVisitor, context, " org.apache".substring(1));
29+
} else if (APACHE_DUBBO_EXCHANGE_CHANNEL.equals(className)) {
30+
classVisitor = new DubboExchangeChannelAdapter(classVisitor, context, " org.apache".substring(1));
31+
} else if (ALIBABA_DUBBO_PROXY_HANDLER.equals(className)) {
32+
classVisitor = new DubboProxyHandlerAdapter(classVisitor, context, " com.alibaba".substring(1));
33+
} else if (APACHE_DUBBO_PROXY_HANDLER.equals(className)) {
34+
classVisitor = new DubboProxyHandlerAdapter(classVisitor, context, " org.apache".substring(1));
2335
}
2436

2537
return classVisitor;
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
package io.dongtai.iast.core.bytecode.enhance.plugin.framework.dubbo;
2+
3+
import io.dongtai.iast.core.bytecode.enhance.ClassContext;
4+
import io.dongtai.iast.core.bytecode.enhance.plugin.AbstractClassVisitor;
5+
import io.dongtai.iast.core.utils.AsmUtils;
6+
import io.dongtai.log.DongTaiLog;
7+
import org.objectweb.asm.ClassVisitor;
8+
import org.objectweb.asm.MethodVisitor;
9+
10+
public class DubboExchangeChannelAdapter extends AbstractClassVisitor {
11+
public static final String DUBBO_EXCHANGE_CHANNEL_SEND = "{package}.dubbo.remoting.exchange.support.header.HeaderExchangeChannel.send(java.lang.Object)";
12+
13+
private final String packageName;
14+
private final String sendSign;
15+
16+
public DubboExchangeChannelAdapter(ClassVisitor classVisitor, ClassContext context, String packageName) {
17+
super(classVisitor, context);
18+
this.packageName = packageName;
19+
this.sendSign = DUBBO_EXCHANGE_CHANNEL_SEND.replace("{package}", this.packageName);
20+
}
21+
22+
@Override
23+
public MethodVisitor visitMethod(final int access, final String name, final String desc, final String signature, final String[] exceptions) {
24+
MethodVisitor mv = super.visitMethod(access, name, desc, signature, exceptions);
25+
String signCode = AsmUtils.buildSignature(context.getClassName(), name, desc);
26+
27+
if (this.sendSign.equals(signCode)) {
28+
DongTaiLog.debug("Adding dubbo provider response tracking by {}", signCode);
29+
mv = new DubboExchangeChannelSendAdviceAdapter(mv, access, name, desc, signCode,
30+
this.context, this.packageName);
31+
setTransformed();
32+
}
33+
return mv;
34+
}
35+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
package io.dongtai.iast.core.bytecode.enhance.plugin.framework.dubbo;
2+
3+
import io.dongtai.iast.core.bytecode.enhance.ClassContext;
4+
import io.dongtai.iast.core.bytecode.enhance.plugin.AbstractAdviceAdapter;
5+
import org.objectweb.asm.*;
6+
import org.objectweb.asm.commons.Method;
7+
8+
public class DubboExchangeChannelSendAdviceAdapter extends AbstractAdviceAdapter {
9+
private static final Method GET_RESULT_METHOD = Method.getMethod("java.lang.Object getResult()");
10+
private static final Method GET_STATUS_METHOD = Method.getMethod("byte getStatus()");
11+
12+
private final String packageName;
13+
private final Type objectType;
14+
private final Type responseType;
15+
16+
protected DubboExchangeChannelSendAdviceAdapter(MethodVisitor mv, int access, String name, String desc,
17+
String signature, ClassContext context, String packageName) {
18+
super(mv, access, name, desc, context, "dubbo", signature);
19+
this.packageName = packageName;
20+
String packageDesc = packageName.replace(".", "/");
21+
this.responseType = Type.getObjectType(packageDesc + "/dubbo/remoting/exchange/Response");
22+
this.objectType = Type.getObjectType("java/lang/Object");
23+
}
24+
25+
@Override
26+
protected void before() {
27+
mark(tryLabel);
28+
Label elseLabel = new Label();
29+
30+
isFirstLevelDubbo();
31+
mv.visitJumpInsn(EQ, elseLabel);
32+
33+
collectDubboResponse();
34+
35+
mark(elseLabel);
36+
}
37+
38+
@Override
39+
protected void after(int opcode) {
40+
}
41+
42+
private void isFirstLevelDubbo() {
43+
invokeStatic(ASM_TYPE_SPY_HANDLER, SPY_HANDLER$getDispatcher);
44+
invokeInterface(ASM_TYPE_SPY_DISPATCHER, SPY$isFirstLevelDubbo);
45+
}
46+
47+
private void collectDubboResponse() {
48+
Label tryL = new Label();
49+
Label catchL = new Label();
50+
Label exHandlerL = new Label();
51+
visitTryCatchBlock(tryL, catchL, exHandlerL, ASM_TYPE_THROWABLE.getInternalName());
52+
visitLabel(tryL);
53+
54+
55+
int respLocal = newLocal(this.responseType);
56+
loadArg(0);
57+
checkCast(this.responseType);
58+
storeLocal(respLocal);
59+
60+
invokeStatic(ASM_TYPE_SPY_HANDLER, SPY_HANDLER$getDispatcher);
61+
loadLocal(respLocal);
62+
invokeVirtual(this.responseType, GET_RESULT_METHOD);
63+
loadLocal(respLocal);
64+
invokeVirtual(this.responseType, GET_STATUS_METHOD);
65+
invokeInterface(ASM_TYPE_SPY_DISPATCHER, SPY$collectDubboResponse);
66+
67+
visitLabel(catchL);
68+
Label endL = new Label();
69+
visitJumpInsn(GOTO, endL);
70+
visitLabel(exHandlerL);
71+
visitVarInsn(ASTORE, this.nextLocal);
72+
visitLabel(endL);
73+
}
74+
}

dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/LegacyDubboExchangeHandleRequestAdviceAdapter.java renamed to dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/DubboExchangeHandleRequestAdviceAdapter.java

Lines changed: 49 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,7 @@
55
import org.objectweb.asm.*;
66
import org.objectweb.asm.commons.Method;
77

8-
public class LegacyDubboExchangeHandleRequestAdviceAdapter extends AbstractAdviceAdapter {
9-
private static final Method GET_URL_METHOD = Method.getMethod(" com.alibaba.dubbo.common.URL getUrl()".substring(1));
8+
public class DubboExchangeHandleRequestAdviceAdapter extends AbstractAdviceAdapter {
109
private static final Method URL_TO_STRING_METHOD = Method.getMethod("java.lang.String toString()");
1110
private static final Method GET_REMOTE_ADDRESS_METHOD = Method.getMethod("java.net.InetSocketAddress getRemoteAddress()");
1211
private static final Method IS_TWO_WAY_METHOD = Method.getMethod("boolean isTwoWay()");
@@ -16,19 +15,31 @@ public class LegacyDubboExchangeHandleRequestAdviceAdapter extends AbstractAdvic
1615
private static final Method GET_RESULT_METHOD = Method.getMethod("java.lang.Object getResult()");
1716
private static final Method GET_STATUS_METHOD = Method.getMethod("byte getStatus()");
1817

18+
private final String packageName;
1919
private final Type endpointType;
2020
private final Type urlType;
2121
private final Type channelType;
2222
private final Type requestType;
2323
private final Type responseType;
24+
private final Method getUrlMethod;
2425

25-
protected LegacyDubboExchangeHandleRequestAdviceAdapter(MethodVisitor mv, int access, String name, String desc, String signature, ClassContext context) {
26+
protected DubboExchangeHandleRequestAdviceAdapter(MethodVisitor mv, int access, String name, String desc,
27+
String signature, ClassContext context, String packageName) {
2628
super(mv, access, name, desc, context, "dubbo", signature);
27-
this.endpointType = Type.getObjectType(" com/alibaba/dubbo/remoting/Endpoint".substring(1));
28-
this.urlType = Type.getObjectType(" com/alibaba/dubbo/common/URL".substring(1));
29-
this.channelType = Type.getObjectType(" com/alibaba/dubbo/remoting/Channel".substring(1));
30-
this.requestType = Type.getObjectType(" com/alibaba/dubbo/remoting/exchange/Request".substring(1));
31-
this.responseType = Type.getObjectType(" com/alibaba/dubbo/remoting/exchange/Response".substring(1));
29+
this.packageName = packageName;
30+
String packageDesc = packageName.replace(".", "/");
31+
this.endpointType = Type.getObjectType(packageDesc + "/dubbo/remoting/Endpoint");
32+
this.urlType = Type.getObjectType(packageDesc + "/dubbo/common/URL");
33+
this.channelType = Type.getObjectType(packageDesc + "/dubbo/remoting/Channel");
34+
this.requestType = Type.getObjectType(packageDesc + "/dubbo/remoting/exchange/Request");
35+
if (" com.alibaba".substring(1).equals(packageName)) {
36+
this.responseType = Type.getObjectType(packageDesc + "/dubbo/remoting/exchange/Response");
37+
} else {
38+
// org.apache.dubbo use HeaderExchangeChannel to track response
39+
this.responseType = null;
40+
}
41+
42+
this.getUrlMethod = Method.getMethod(packageName + ".dubbo.common.URL getUrl()");
3243
}
3344

3445
@Override
@@ -47,13 +58,13 @@ protected void before() {
4758

4859
@Override
4960
protected void after(int opcode) {
50-
// if (opcode != ATHROW) {
51-
// Label elseLabel = new Label();
52-
// isFirstLevelDubbo();
53-
// mv.visitJumpInsn(EQ, elseLabel);
54-
// collectDubboResponse(opcode);
55-
// mark(elseLabel);
56-
// }
61+
if (this.responseType != null && opcode != ATHROW) {
62+
Label elseLabel = new Label();
63+
isFirstLevelDubbo();
64+
mv.visitJumpInsn(EQ, elseLabel);
65+
collectDubboResponse(opcode);
66+
mark(elseLabel);
67+
}
5768

5869
leaveDubbo(opcode);
5970
}
@@ -64,26 +75,9 @@ private void enterDubbo() {
6475
}
6576

6677
private void leaveDubbo(int opcode) {
67-
int retLocal = newLocal(ASM_TYPE_OBJECT);
68-
if (!isThrow(opcode)) {
69-
loadReturn(opcode);
70-
} else {
71-
pushNull();
72-
}
73-
storeLocal(retLocal);
7478
invokeStatic(ASM_TYPE_SPY_HANDLER, SPY_HANDLER$getDispatcher);
79+
loadArg(0);
7580
loadArg(1);
76-
loadLocal(retLocal);
77-
if (!isThrow(opcode)) {
78-
loadLocal(retLocal);
79-
invokeVirtual(this.responseType, GET_RESULT_METHOD);
80-
loadLocal(retLocal);
81-
invokeVirtual(this.responseType, GET_STATUS_METHOD);
82-
} else {
83-
pushNull();
84-
byte b = 0;
85-
push(b);
86-
}
8781
invokeInterface(ASM_TYPE_SPY_DISPATCHER, SPY$leaveDubbo);
8882
}
8983

@@ -104,7 +98,7 @@ private void collectDubboRequest() {
10498
loadArg(0);
10599
loadArg(1);
106100
loadArg(0);
107-
invokeInterface(this.endpointType, GET_URL_METHOD);
101+
invokeInterface(this.endpointType, this.getUrlMethod);
108102
invokeVirtual(this.urlType, URL_TO_STRING_METHOD);
109103
loadArg(0);
110104
invokeInterface(this.channelType, GET_REMOTE_ADDRESS_METHOD);
@@ -122,7 +116,27 @@ private void collectDubboRequest() {
122116
Label endL = new Label();
123117
visitJumpInsn(GOTO, endL);
124118
visitLabel(exHandlerL);
125-
visitVarInsn(ASTORE, this.nextLocal);
119+
int nextL = newLocal(ASM_TYPE_OBJECT);
120+
storeLocal(nextL);
126121
visitLabel(endL);
127122
}
123+
124+
private void collectDubboResponse(int opcode) {
125+
int retLocal = newLocal(ASM_TYPE_OBJECT);
126+
loadReturn(opcode);
127+
storeLocal(retLocal);
128+
129+
Label nonNullLabel = new Label();
130+
loadLocal(retLocal);
131+
ifNull(nonNullLabel);
132+
133+
invokeStatic(ASM_TYPE_SPY_HANDLER, SPY_HANDLER$getDispatcher);
134+
loadLocal(retLocal);
135+
invokeVirtual(this.responseType, GET_RESULT_METHOD);
136+
loadLocal(retLocal);
137+
invokeVirtual(this.responseType, GET_STATUS_METHOD);
138+
invokeInterface(ASM_TYPE_SPY_DISPATCHER, SPY$collectDubboResponse);
139+
140+
mark(nonNullLabel);
141+
}
128142
}

dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/LegacyDubboExchangeHandlerAdapter.java renamed to dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/DubboExchangeHandlerAdapter.java

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -7,21 +7,27 @@
77
import org.objectweb.asm.ClassVisitor;
88
import org.objectweb.asm.MethodVisitor;
99

10-
public class LegacyDubboExchangeHandlerAdapter extends AbstractClassVisitor {
11-
public static final String LEGACY_DUBBO_EXCHANGE_HANDLE_REQUEST = " com.alibaba.dubbo.remoting.exchange.support.header.HeaderExchangeHandler.handleRequest(com.alibaba.dubbo.remoting.exchange.ExchangeChannel,com.alibaba.dubbo.remoting.exchange.Request)".substring(1);
10+
public class DubboExchangeHandlerAdapter extends AbstractClassVisitor {
11+
public static final String DUBBO_EXCHANGE_HANDLE_REQUEST = "{package}.dubbo.remoting.exchange.support.header.HeaderExchangeHandler.handleRequest({package}.dubbo.remoting.exchange.ExchangeChannel,{package}.dubbo.remoting.exchange.Request)";
1212

13-
public LegacyDubboExchangeHandlerAdapter(ClassVisitor classVisitor, ClassContext context) {
13+
private final String packageName;
14+
private final String handleRequestSign;
15+
16+
public DubboExchangeHandlerAdapter(ClassVisitor classVisitor, ClassContext context, String packageName) {
1417
super(classVisitor, context);
18+
this.packageName = packageName;
19+
this.handleRequestSign = DUBBO_EXCHANGE_HANDLE_REQUEST.replace("{package}", this.packageName);
1520
}
1621

1722
@Override
1823
public MethodVisitor visitMethod(final int access, final String name, final String desc, final String signature, final String[] exceptions) {
1924
MethodVisitor mv = super.visitMethod(access, name, desc, signature, exceptions);
2025
String signCode = AsmUtils.buildSignature(context.getClassName(), name, desc);
2126

22-
if (LEGACY_DUBBO_EXCHANGE_HANDLE_REQUEST.equals(signCode)) {
27+
if (this.handleRequestSign.equals(signCode)) {
2328
DongTaiLog.debug("Adding dubbo provider tracking by {}", signCode);
24-
mv = new LegacyDubboExchangeHandleRequestAdviceAdapter(mv, access, name, desc, signCode, this.context);
29+
mv = new DubboExchangeHandleRequestAdviceAdapter(mv, access, name, desc, signCode,
30+
this.context, this.packageName);
2531
setTransformed();
2632
}
2733
return mv;

dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/LegacyDubboProxyHandlerAdapter.java renamed to dongtai-core/src/main/java/io/dongtai/iast/core/bytecode/enhance/plugin/framework/dubbo/DubboProxyHandlerAdapter.java

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -7,21 +7,27 @@
77
import org.objectweb.asm.ClassVisitor;
88
import org.objectweb.asm.MethodVisitor;
99

10-
public class LegacyDubboProxyHandlerAdapter extends AbstractClassVisitor {
11-
public static final String LEGACY_DUBBO_PROXY_HANDLER_INVOKE = " com.alibaba.dubbo.rpc.proxy.AbstractProxyInvoker.invoke(com.alibaba.dubbo.rpc.Invocation)".substring(1);
10+
public class DubboProxyHandlerAdapter extends AbstractClassVisitor {
11+
public static final String DUBBO_PROXY_HANDLER_INVOKE = "{package}.dubbo.rpc.proxy.AbstractProxyInvoker.invoke({package}.dubbo.rpc.Invocation)";
1212

13-
public LegacyDubboProxyHandlerAdapter(ClassVisitor classVisitor, ClassContext context) {
13+
private final String packageName;
14+
private final String fullSign;
15+
16+
public DubboProxyHandlerAdapter(ClassVisitor classVisitor, ClassContext context, String packageName) {
1417
super(classVisitor, context);
18+
this.packageName = packageName;
19+
this.fullSign = DUBBO_PROXY_HANDLER_INVOKE.replace("{package}", this.packageName);
1520
}
1621

1722
@Override
1823
public MethodVisitor visitMethod(final int access, final String name, final String desc, final String signature, final String[] exceptions) {
1924
MethodVisitor mv = super.visitMethod(access, name, desc, signature, exceptions);
2025
String signCode = AsmUtils.buildSignature(context.getClassName(), name, desc);
2126

22-
if (LEGACY_DUBBO_PROXY_HANDLER_INVOKE.equals(signCode)) {
27+
if (this.fullSign.equals(signCode)) {
2328
DongTaiLog.debug("Adding dubbo provider source tracking by {}", signCode);
24-
mv = new LegacyDubboProxyHandlerInvokeAdviceAdapter(mv, access, name, desc, signCode, this.context);
29+
mv = new DubboProxyHandlerInvokeAdviceAdapter(mv, access, name, desc, signCode,
30+
this.context, this.packageName);
2531
setTransformed();
2632
}
2733
return mv;

0 commit comments

Comments
 (0)