支付宝mpass框架设置代理

支付宝mpass框架设置代理

请求发送流程

image-20230308001214073

image-20230308002003959

image-20230308002041905

image-20230308000728931

image-20230308001318904

设置代理

尝试用以下代码设置代理,无实际效果。。。

1
2
3
4
5
6
7
var CoreHttpManager = Java.use("com.alipay.mobile.common.transport.http.inner.CoreHttpManager");
CoreHttpManager.getHttpClient.overload().implementation = function() {
var client = AndroidHttpClient.newDefaultInstance();
var proxy = HttpHost.$new('192.168.31.111', 8888);
client.getParams().setParameter("http.route.default-proxy", proxy)
return client;
}

分析代码发现每个请求都会调用HttpClientPlannerHelper.determineRoute获取一个路径(路由).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
HttpWorker->determineProxyPlanner (retType: com.alipay.mobile.common.transport.http.inner.HttpProxyWrapper): com.alipay.mobile.common.transport.http.inner.HttpProxyWrapper@4f77c8f
HttpClientPlannerHelper->determineRoute (argType: com.alipay.mobile.common.transport.http.AndroidHttpClient): com.alipay.mobile.common.transport.http.AndroidHttpClient@eca3325
HttpClientPlannerHelper->determineRoute (argType: org.apache.http.HttpHost): https://mobilepaas.abchina.com.cn:441
HttpClientPlannerHelper->determineRoute (argType: org.apache.http.HttpRequest): [object Object]
HttpClientPlannerHelper->determineRoute (argType: org.apache.http.protocol.HttpContext): [object Object]
HttpClientPlannerHelper->determineRoute (retType: org.apache.http.conn.routing.HttpRoute): HttpRoute[{s}->https://mobilepaas.abchina.com.cn:441]
java.lang.Exception
at com.alipay.mobile.common.transport.http.inner.HttpClientPlannerHelper.determineRoute(Native Method)
at com.alipay.mobile.common.transport.http.HttpWorker.executeHttpClientRequest(HttpWorker.java:1584)
at com.alipay.mobile.common.transport.http.HttpWorker.executeRequest(HttpWorker.java:1381)
at com.alipay.mobile.common.transport.http.HttpWorker.call(HttpWorker.java:568)
at com.alipay.mobile.common.transport.http.HttpWorker.call(HttpWorker.java:144)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at com.alipay.mobile.common.transport.concurrent.ZFutureTask.run(ZFutureTask.java:53)
at com.alipay.mobile.common.transport.http.HttpTask.run(HttpTask.java:32)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
at java.lang.Thread.run(Thread.java:919)

image-20230308094414534

image-20230308094452650

因此只需要构造一个HttpRoute对象,就可以实现添加代理的目的。

https://www.javadoc.io/doc/org.apache.httpcomponents/httpclient/4.3.3/org/apache/http/conn/routing/HttpRoute.html

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
// 构造方法参数

HttpRoute(HttpHost target)
Creates a new direct insecure route.

HttpRoute(HttpHost target, HttpHost proxy)
Creates a new plain route through a proxy.

HttpRoute(HttpHost target, InetAddress local, boolean secure)
Creates a new direct route.

HttpRoute(HttpHost target, InetAddress local, HttpHost[] proxies, boolean secure, RouteInfo.TunnelType tunnelled, RouteInfo.LayerType layered)
Creates a new route with all attributes specified explicitly.

HttpRoute(HttpHost target, InetAddress local, HttpHost proxy, boolean secure)
Creates a new route through a proxy.

HttpRoute(HttpHost target, InetAddress local, HttpHost proxy, boolean secure, RouteInfo.TunnelType tunnelled, RouteInfo.LayerType layered)
Creates a new route with at most one proxy.

最终代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
Java.perform(function () {
console.log('start...')

var HttpUrlRequest = Java.use("com.alipay.mobile.common.transport.http.HttpUrlRequest");
HttpUrlRequest.isRpcHttp2.implementation = function () {
return false;
}
var ConnType = Java.use('anet.channel.entity.ConnType')
ConnType.isHttpType.implementation = function () {
return true;
}

var HttpRoute = Java.use('org.apache.http.conn.routing.HttpRoute')
var HttpHost = Java.use('org.apache.http.HttpHost')
HttpRoute.$init.overload('org.apache.http.HttpHost', 'java.net.InetAddress', 'boolean').implementation = function (arg1, arg2, arg3) {
console.log('set proxy...')
var proxy = HttpHost.$new('192.168.31.111', 8080);
return this.$init(arg1, arg2, proxy, arg3)
}

var ArrayList = Java.use("java.util.ArrayList");
var TrustManagerImpl = Java.use('com.android.org.conscrypt.TrustManagerImpl');

TrustManagerImpl.checkTrustedRecursive.implementation = function (a1, a2, a3, a4, a5, a6) {
console.log('Bypassing SSL Pinning');
var arr = ArrayList.$new();
return arr;
}
return
});

使用burp时,需要将默认的HTTP2协议关闭。

image-20240621165118985

其他设置代理的方式

方法1

com.alipay.mobile.common.transport.http.HttpWorker.executeHttpClientRequest()中会调用determineProxyPlanner方法设置代理。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
protected HttpResponse executeHttpClientRequest() {
LogCatUtil.debug("HttpWorker", "By Http/Https to request. operationType=" + this.getOperationType() + " method=" + this.getTargetHttpUriRequest().getMethod() + " url=" + this.getTargetHttpUriRequest().getURI().toString() + " allowRetry=" + this.mOriginRequest.allowRetry);
if(!TextUtils.isEmpty(this.getOperationType())) {
this.mTransportContext.dcList.clear();
}

this.b();
this.getHttpClient().setHttpRequestRetryHandler(HttpWorker.sHttpRequestRetryHandler);
TransportStrategy.fillCurrentReqInfo(true, "https", this.mTransportContext);
if(this.n) {
DataItemsUtil.putDataItem2DataContainer(this.mTransportContext.getCurrentDataContainer(), "RETRY", "T");
}

HttpParams httpParams0 = this.getTargetHttpUriRequest().getParams();
httpParams0.setParameter("http.protocol.element-charset", "utf-8");
this.mTransportContext.getCurrentDataContainer().timeItemDot("ALL_TIME");
HttpEntity httpEntity0 = this.getPostData();
if(httpEntity0 != null) {
this.mLocalContext.setAttribute("alipay_isRepeatable", Boolean.valueOf(httpEntity0.isRepeatable()));
this.mTransportContext.getCurrentDataContainer().putDataItem("REQ_SIZE", httpEntity0.getContentLength());
}

this.putStalledTime();
HttpProxyWrapper httpProxyWrapper0 = this.determineProxyPlanner(httpParams0); //<-----------
HttpUriRequest httpUriRequest0 = this.getTargetHttpUriRequest();
if((httpUriRequest0 instanceof HttpEntityEnclosingRequest)) {
HttpEntity httpEntity1 = ((HttpEntityEnclosingRequest)httpUriRequest0).getEntity();
if((httpEntity1 instanceof ZNetworkHttpEntityWrapper)) {
((ZNetworkHttpEntityWrapper)httpEntity1).setHttpWorker(this);
}
}
else {
this.mLocalContext.setAttribute("alipay_isRepeatable", Boolean.TRUE);
}
// 省略无关代码
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
protected HttpProxyWrapper determineProxyPlanner(HttpParams httpParams0) {
int v1;
HttpProxyWrapper httpProxyWrapper0 = new HttpProxyWrapper();
httpProxyWrapper0.proxy = NetworkUtils.getProxyOfEnhanced(this.mContext);
if(httpProxyWrapper0.proxy == null) {
httpParams0.setParameter("http.route.default-proxy", ConnRouteParams.NO_HOST);
httpProxyWrapper0.proxy = null;
return httpProxyWrapper0;
}

if((this.getOriginRequest().isCapture()) || (MiscUtils.isDebugger(this.mContext))) {
LogCatUtil.info("HttpWorker", "determineProxyPlanner. request capture: " + this.getOriginRequest().isCapture());
this.a(httpProxyWrapper0.proxy);
httpParams0.setParameter("http.route.default-proxy", httpProxyWrapper0.proxy);//<--------------
return httpProxyWrapper0;
}
// 省略无关代码
}
1
2
3
4
5
6
7
8
9
10
11
12
13
public static HttpHost getProxyOfEnhanced(Context context0) {
HttpHost httpHost0 = NetworkUtils.getProxy(context0);
if(httpHost0 == null) {
return null;
}

if((TransportStrategy.isMobileWapProxyIp(httpHost0.getHostName())) && NetworkUtils.getNetworkType(context0) == 3) {
LogCatUtil.warn("NetworkUtils", " The proxy ip is wap = [" + httpHost0.getHostName() + "], but is now wifi network !");
return null;
}

return httpHost0;
}

hook代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
var flag = false
var HttpWorker = Java.use("com.alipay.mobile.common.transport.http.HttpWorker");
HttpWorker.determineProxyPlanner.overload('org.apache.http.params.HttpParams').implementation = function (arg_0) {
var url = this.getOriginRequest().getUrl()
if (url.indexOf('mobilegw.alipay.com') > -1) {
flag = true
}
var retval = this.determineProxyPlanner(arg_0)
flag = false
return retval;
}


var NetworkUtils = Java.use("com.alipay.mobile.common.transport.utils.NetworkUtils");
NetworkUtils.getProxyOfEnhanced.overload('android.content.Context').implementation = function (arg_0) {
if (flag) {
var proxy = HttpHost.$new('192.168.31.111', 8888);
return proxy;
}
var retval = this.getProxyOfEnhanced(arg_0)
return retval;
}

var HttpUrlRequest = Java.use("com.alipay.mobile.common.transport.http.HttpUrlRequest");
HttpUrlRequest.isCapture.overload().implementation = function () {
var url = this.getUrl()
if (url.indexOf('mobilegw.alipay.com') > -1) {
console.log('set proxy...')
return true
}
return false;
}

方法2

将https的url修改成http。再使用iptables将http流量转发到代理服务器。

1
2
3
4
5
6
7
8
9
10
var HttpUrlRequest = Java.use("com.alipay.mobile.common.transport.http.HttpUrlRequest");
HttpUrlRequest.getUrl.overload().implementation = function () {
var retval = this.getUrl()
if (retval.indexOf('https://mobilegw.alipay.com/mgw.htm') > -1) {
console.log("HttpUrlRequest->getUrl (retType: java.lang.String): " + retval)
// return "http://192.168.31.111:5678/mgw.htm"
return "http://mobilegw.alipay.com/mgw.htm"
}
return retval;
}

使用ProxyDroid开启代理服务器后,执行以下命令:

1
2
3
iptables -t nat -F
iptables -t nat -A OUTPUT -p tcp --dport 80 -j REDIRECT --to 8123
iptables -t nat -L

日志

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87

// hook LogCatUtil, 打印错误日志及堆栈
LogCatUtil->error (argType: java.lang.String): HttpWorker
LogCatUtil->error (argType: java.lang.String): processSSLHandshakeException process CertificateException code=15, old exception=javax.net.ssl.SSLHandshakeException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
LogCatUtil->error (argType: java.lang.String): HttpWorker
LogCatUtil->error (argType: java.lang.String): processException,exceptionName = SSLHandshakeException,code=[15] canRetry=[false] e=[java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.]
LogCatUtil->error (argType: java.lang.Throwable): java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
java.lang.Exception
at com.alipay.mobile.common.transport.utils.LogCatUtil.error(Native Method)
at com.alipay.mobile.common.transport.utils.MonitorErrorLogHelper.log(MonitorErrorLogHelper.java:100003)
at com.alipay.mobile.common.transport.http.HttpWorker.monitorErrorLog(HttpWorker.java:100011)
at com.alipay.mobile.common.transport.http.HttpWorker.processException(HttpWorker.java:100363)
at com.alipay.mobile.common.transport.http.HttpWorker.a(HttpWorker.java:100076)
at com.alipay.mobile.common.transport.http.HttpWorker.call(HttpWorker.java:100316)
at com.alipay.mobile.common.transport.http.HttpWorker.__call_stub_private(HttpWorker.java:100000)
at com.alipay.mobile.common.transport.http.HttpWorker.call(Unknown Source:14)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at com.alipay.mobile.common.transport.concurrent.ZFutureTask.__run_stub_private(ZFutureTask.java:100003)
at com.alipay.mobile.common.transport.concurrent.ZFutureTask.run(Unknown Source:14)
at com.alipay.mobile.common.transport.http.HttpTask.__run_stub_private(HttpTask.java:100000)
at com.alipay.mobile.common.transport.http.HttpTask.__run_stub(Unknown Source:0)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100012)
at com.alipay.mobile.framework.aop.TaskMonitorPerfInterceptor.intercept0(TaskMonitorPerfInterceptor.java:100057)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100023)
at com.alipay.dexaop.monitor.chain.interceptors.RunningObjectInterceptor.intercept0(RunningObjectInterceptor.java:100078)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100023)
at com.alipay.dexaop.power.interceptors.BgOnlyInterceptor.intercept0(BgOnlyInterceptor.java:100058)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100023)
at com.alipay.dexaop.DexAOPEntrySettings.bg_java_lang_Runnable_run_proxy(DexAOPEntrySettings.java:100011)
at com.alipay.dexaop.DexAOPEntry.bg_java_lang_Runnable_run_proxy(DexAOPEntry.java:100000)
at com.alipay.mobile.common.transport.http.HttpTask.run(Unknown Source:18)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
at java.lang.Thread.run(Thread.java:919)


// hook java.security.cert.CertPathValidatorException 构造函数
java.lang.Exception
at com.android.org.conscrypt.TrustManagerImpl.verifyChain(TrustManagerImpl.java:674)
at com.android.org.conscrypt.TrustManagerImpl.checkTrustedRecursive(TrustManagerImpl.java:551)
at com.android.org.conscrypt.TrustManagerImpl.checkTrustedRecursive(TrustManagerImpl.java:617)
at com.android.org.conscrypt.TrustManagerImpl.checkTrusted(TrustManagerImpl.java:507)
at com.android.org.conscrypt.TrustManagerImpl.checkServerTrusted(TrustManagerImpl.java:335)
at android.security.net.config.NetworkSecurityTrustManager.checkServerTrusted(NetworkSecurityTrustManager.java:113)
at android.security.net.config.NetworkSecurityTrustManager.checkServerTrusted(NetworkSecurityTrustManager.java:87)
at android.security.net.config.RootTrustManager.checkServerTrusted(RootTrustManager.java:117)
at com.alipay.mobile.common.transport.ssl.ZSSLContextFactory$X509TrustManagerWrapper.checkServerTrusted(ZSSLContextFactory.java:100036)
at com.android.org.conscrypt.Platform.checkServerTrusted(Platform.java:228)
at com.android.org.conscrypt.ConscryptFileDescriptorSocket.verifyCertificateChain(ConscryptFileDescriptorSocket.java:407)
at com.android.org.conscrypt.NativeCrypto.SSL_do_handshake(Native Method)
at com.android.org.conscrypt.NativeSsl.doHandshake(NativeSsl.java:387)
at com.android.org.conscrypt.ConscryptFileDescriptorSocket.startHandshake(ConscryptFileDescriptorSocket.java:226)
at com.alipay.mobile.common.transport.ssl.ZApacheSSLSocketFactory.createSocket(ZApacheSSLSocketFactory.java:100079)
at org.apache.http.impl.conn.DefaultClientConnectionOperator.updateSecureConnection(DefaultClientConnectionOperator.java:242)
at org.apache.http.impl.conn.AbstractPoolEntry.layerProtocol(AbstractPoolEntry.java:307)
at org.apache.http.impl.conn.AbstractPooledConnAdapter.layerProtocol(AbstractPooledConnAdapter.java:151)
at org.apache.http.impl.client.DefaultRequestDirector.establishRoute(DefaultRequestDirector.java:668)
at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:376)
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:560)
at com.alipay.mobile.common.transport.http.AndroidHttpClient.execute(AndroidHttpClient.java:100002)
at com.alipay.mobile.common.transport.http.HttpWorker.doExecuteRequestByHttpClient(HttpWorker.java:100030)
at com.alipay.mobile.common.transport.http.HttpWorker.executeHttpClientRequest(HttpWorker.java:100036)
at com.alipay.mobile.common.transport.http.ResourceHttpWorker.executeHttpClientRequest(ResourceHttpWorker.java:100007)
at com.alipay.mobile.common.transport.http.HttpWorker.executeHttpClientRequest(HttpWorker.java:100252)
at com.alipay.mobile.common.transport.http.ResourceHttpWorker.executeHttpClientRequest(ResourceHttpWorker.java:100001)
at com.alipay.mobile.common.transport.http.HttpWorker.executeRequest(HttpWorker.java:100057)
at com.alipay.mobile.common.transport.http.HttpWorker.call(HttpWorker.java:100161)
at com.alipay.mobile.common.transport.http.HttpWorker.__call_stub_private(HttpWorker.java:100000)
at com.alipay.mobile.common.transport.http.HttpWorker.call(Unknown Source:14)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at com.alipay.mobile.common.transport.concurrent.ZFutureTask.__run_stub_private(ZFutureTask.java:100003)
at com.alipay.mobile.common.transport.concurrent.ZFutureTask.run(Unknown Source:14)
at com.alipay.mobile.common.transport.http.HttpTask.__run_stub_private(HttpTask.java:100000)
at com.alipay.mobile.common.transport.http.HttpTask.__run_stub(Unknown Source:0)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100012)
at com.alipay.mobile.framework.aop.TaskMonitorPerfInterceptor.intercept0(TaskMonitorPerfInterceptor.java:100057) at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100023)
at com.alipay.dexaop.monitor.chain.interceptors.RunningObjectInterceptor.intercept0(RunningObjectInterceptor.java:100078)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100023)
at com.alipay.dexaop.power.interceptors.BgOnlyInterceptor.intercept0(BgOnlyInterceptor.java:100058)
at com.alipay.dexaop.perf.RunnableRunChain.proceed0(RunnableRunChain.java:100023)
at com.alipay.dexaop.DexAOPEntrySettings.bg_java_lang_Runnable_run_proxy(DexAOPEntrySettings.java:100011)
at com.alipay.dexaop.DexAOPEntry.bg_java_lang_Runnable_run_proxy(DexAOPEntry.java:100000)
at com.alipay.mobile.common.transport.http.HttpTask.run(Unknown Source:18)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
at java.lang.Thread.run(Thread.java:919)