从网络上回来的数据是如何被webkit接收的?
在framework/…/net/http/EventHandler.java 中定义了一些接口, 比如:
public void data(byte[] data, int len);
public void headers(Headers headers);
public void error(int id, String description);
这个接口被framework/…/webkit/LoadListener.java 实现, 重写EventHandler接口中的方法.
被重写的这3个方法大致的思路是: 通过sendMessageInternal api, 把数据包装成message, 发给LoadLisenter所在的线程, 在Handler.handleMessage(Message msg)处理.
class LoadListener extends Handler implements EventHandler { //所以LoadListener在架构中就当成一个Handler使用.
* IMPORTANT: as this is called from network thread, can't call native
* directlypublic void data(byte[] data, int length) {
boolean sendMessage = false;
synchronized (mDataBuilder) {
sendMessage = mDataBuilder.isEmpty();
mDataBuilder.append(data, 0, length);
}
if (sendMessage) {
sendMessageInternal(obtainMessage(MSG_CONTENT_DATA));
}
}public void headers(Headers headers) {
sendMessageInternal(obtainMessage(MSG_CONTENT_HEADERS, headers));
}public void error(int id, String description) {
sendMessageInternal(obtainMessage(MSG_CONTENT_ERROR, id, 0, description));
}
}
/*
* This message handler is to facilitate communication between the network
* thread and the browser thread.
*/
public void handleMessage(Message msg) {
switch (msg.what) {
case MSG_CONTENT_HEADERS:
handleHeaders((Headers) msg.obj);
break;
case MSG_CONTENT_DATA:
commitLoad();
break;
case MSG_CONTENT_ERROR:
handleError(msg.arg1, (String) msg.obj);
break;
}
}
打断点跟, 哪个thread call headers(), 哪个thread call handleHeaders().
可以看到是http thread执行的LoadListener.java ---> headers().
是WebViewCoreThread 执行的LoadListener.java ---> handleHeaders().
打断点跟, 数据是怎么从http thread 到 browser thread的.
http thread 执行LoadListener.java ---> data(byte[] data, int length).
WebViewCoreThread 执行commitLoad().
private void commitLoad() {
// Give the data to WebKit now.
ByteArrayBuilder.Chunk c;
while (true) {
c = mDataBuilder.getFirstChunk();
if (c == null) break;
if (c.mLength != 0) {
nativeAddData(c.mArray, c.mLength);
} else {
c.release();
}
}
}
调用jni接口nativeAddData(byte[] data, int length); 把mDataBuilder中的数据传给webkit做底层的处理.
2011年最后一天, 做个技术上的收尾.