2010年6月17日 星期四
修改 Android 系統 platform...
code base: vendor/sample/frameworks/
make com.example.android.platform_library
make com.example.android.platform_library.xml
make libplatform_library_jni
make PlatformLibraryClient
檔案有:
/system/framework/com.example.android.platform_library.jar
/system/etc/permissions/com.example.android.platform_library.xml
/system/lib/libplatform_library_jni.so
adb install PlatformLibraryClient.apk
2009年5月26日 星期二
2009年4月16日 星期四
Android 1.5
Android 1.5 Highlights
April 2009
The Android 1.5 platform introduces many new features for users and developers. The list below provides an overview of the changes.
User interface refinements
- System-wide:
- Refinement of all core UI elements
- Animated window transitions (off by default)
- Accelerometer-based application rotations
- UI polish for:
- In-call experience
- Contacts, Call log, and Favorites
- SMS & MMS
- Browser
- Gmail
- Calendar
- Camera & Gallery
- Application management
Performance improvements
- Faster Camera start-up and image capture
- Much faster acquisition of GPS location (powered by SUPL AGPS)
- Smoother page scrolling in Browser
- Speedier GMail conversation list scrolling
New features
- On-screen soft keyboard
- Works in both portrait and landscape orientation
- Support for user installation of 3rd party keyboards
- User dictionary for custom words
- Home screen
- Widgets
- Bundled home screen widgets include: analog clock, calendar, music player, picture frame, and search
- Live folders
- Camera & Gallery
- Video recording
- Video playback (MPEG-4 & 3GP formats)
- Bluetooth
- Stereo Bluetooth support (A2DP and AVCRP profiles)
- Auto-pairing
- Improved handsfree experience
- Browser
- Updated with latest Webkit browser & Squirrelfish Javascript engines
- Copy 'n paste in browser
- Search within a page
- User-selectable text-encoding
- UI changes include:
- Unified Go and Search box
- Tabbed bookmarks/history/most-visited screen
- Contacts
- Shows user picture for Favorites
- Specific date/time stamp for events in call log
- One-touch access to a contact card from call log event
- System
- New Linux kernel (version 2.6.27)
- SD card filesystem auto-checking and repair
- SIM Application Toolkit 1.0
- Google applications
- View Google Talk friends' status in Contacts, SMS, MMS, GMail, and Email applications
- Batch actions such as archive, delete, and label on Gmail messages
- Upload videos to Youtube
- Upload photos on Picasa
New APIs and developer tools
- UI framework
- Framework for easier background/UI thread interaction
- New SlidingDrawer widget
- Horizontal ScrollView widget
- Home Screen framework
- APIs for creating secure home screen widgets
- APIs for populating live folders with custom content
- Media framework
- Raw audio recording and playback APIs
- Interactive MIDI playback engine
- Video recording APIs for developers (3GP format)
- Video and photo sharing Intents
- Media search Intent
- Input Method framework
- Text prediction engine
- Ability to provide downloadable IMEs to users
- Speech recognition framework
- Support for using speech recognition libraries via Intent
- Misc API additions
- LocationManager - Applications can get location change updates via Intent
- WebView - Touch start/end/move/cancel DOM event support
- SensorManager - redesigned sensor APIs
- GLSurfaceView - convenience framework for creating OpenGL applications
- Broadcast Intent for app update install succeeded - for smoother app upgrade experience
- Developer tools
- Support for multiple versions of Android in a single SDK installation
- Improved JUnit support in ADT
- Easier application performance profiling
2009年4月2日 星期四
2009年3月25日 星期三
2008年6月3日 星期二
sk_buff->cb
sk_buff 這個恐怖的 structure. 其中有個 sk_buff->cb[64] 這個 64 bytes 的
東西, 專門拿來把一些 control information 放進去裡面的, 各層 protocol 都
可以拿來用, 但要小心別互相給蓋掉了...
看一下 definition:
include/linux/skbuff.h:
struct sk_buff {
/* These two members must be first. */
struct sk_buff *next;
struct sk_buff *prev;
:
:
/*
* This is the control buffer. It is free to use for every
* layer. Please put your private variables there. If you
* want to keep them across layers you have to do a skb_clone()
* first. This is owned by whoever has the skb queued ATM.
*/
char cb[64];
:
:
}
再來看一下 TCP layer 裡面有用到的部份...
include/net/tcp.h:
/* This is what the send packet queuing engine uses to pass
* TCP per-packet control information to the transmission
* code. We also store the host-order sequence numbers in
* here too. This is 36 bytes on 32-bit architectures,
* 40 bytes on 64-bit machines, if this grows please adjust
* skbuff.h:skbuff->cb[xxx] size appropriately.
*/
struct tcp_skb_cb {
union {
struct inet_skb_parm h4;
#if defined(CONFIG_IPV6) || defined (CONFIG_IPV6_MODULE)
struct inet6_skb_parm h6;
#endif
} header; /* For incoming frames */
__u32 seq; /* Starting sequence number */
__u32 end_seq; /* SEQ + FIN + SYN + datalen */
__u32 when; /* used to compute rtt's */
__u8 flags; /* TCP header flags. */
/* NOTE: These must match up to the flags byte in a
* real TCP header.
*/
:
:
__u8 sacked; /* State flags for SACK/FACK. */
:
:
__u16 urg_ptr; /* Valid w/URG flags is set. */
__u32 ack_seq; /* Sequence number ACK'd */
};
#define TCP_SKB_CB(__skb) ((struct tcp_skb_cb *)&((__skb)->cb[0]))
struct inet_skb_parm 是啥鬼捏?
include/net/ip.h:
struct inet_skb_parm
{
struct ip_options opt; /* Compiled IP options
unsigned char flags;
:
:
};
哇靠, 又來一個 struct ip_options...
include/linux/ip.h:
struct ip_options {
__u32 faddr; /* Saved first hop address */
unsigned char optlen;
unsigned char srr;
unsigned char rr;
unsigned char ts;
unsigned char is_setbyuser:1, /* Set by setsockopt?
is_data:1, /* Options in __data, rather th
is_strictroute:1, /* Strict source route
srr_is_hit:1, /* Packet destination addr was
is_changed:1, /* IP checksum more not valid
rr_needaddr:1, /* Need to record addr of outgo
ts_needtime:1, /* Need to record timestamp
ts_needaddr:1; /* Need to record addr of outgo
unsigned char router_alert;
unsigned char __pad1;
unsigned char __pad2;
unsigned char __data[0];
};
Total 大約會用到 36 bytes (32bit machine), or 40 bytes (64bit machine)...
事實上在 protocol layer 裡還有其他幾個地方會用到 skb->cb 的咚咚:
[MVL4 include/net]$ grep "cb\[" *
ipx.h:#define IPX_SKB_CB(__skb) ((struct ipx_cb *)&((__skb)->cb[0]))
llc_conn.h: skb->cb[sizeof(skb->cb) - 1] = type;
llc_conn.h: return skb->cb[sizeof(skb->cb) - 1];
tcp.h: * skbuff.h:skbuff->cb[xxx] size appropriately.
tcp.h:#define TCP_SKB_CB(__skb) ((struct tcp_skb_cb *)&((__skb)->cb[0]))
[MVL4 include/linux]$ grep "cb\[" *
if_vlan.h:#define VLAN_TX_SKB_CB(__skb) ((struct vlan_skb_tx_cookie *)&((__skb)->cb[0]))
if_vlan.h: * Puts the VLAN tag in @skb->cb[] and lets the device do the rest
if_vlan.h: * __vlan_hwaccel_get_tag - get the VLAN ID that is in @skb->cb[]
if_vlan.h: * Returns error if @skb->cb[] is not set correctly
llc.h:#define llc_ui_skb_cb(__skb) ((struct sockaddr_llc *)&((__skb)->cb[0]))
所以盡量要使用 skb->cb[] 內容的話, 把它給擺在 cb[36] 以後吧, 反正有 64 bytes 可用...
... 這也難怪了... 先前把東西擺在 cb[0] & cb[1], 老是會不見 @_@ 唉啊, 真是沒看清楚啊~~~
likely & unlikely part II
1.2.9. Compile-Time Optimization for Condition Checks
Most of the time, when the kernel compares a variable against some external value to see whether a given condition is met, the result is extremely likely to be predictable. This is pretty common, for example, with code that enforces sanity checks. The kernel uses the likely and unlikely macros, respectively, to wrap comparisons that are likely to return a true (1) or false (0) result. Those macros take advantage of a feature of the gcc compiler that can optimize the compilation of the code based on that information.
Here is an example. Let's suppose you need to call the do_something function, and that in case of failure, you must handle it with the handle_error function:
err = do_something(x,y,z);
if (err)
handle_error(err);
Under the assumption that do_something rarely fails, you can rewrite the code as follows:
err = do_something(x,y,z);
if (unlikely(err))
handle_error(err);
An example of the optimization made possible by the likely and unlikely macros is in handling options in the IP header. The use of IP options is limited to very specific cases, and the kernel can safely assume that most IP packets do not carry IP options. When the kernel forwards an IP packet, it needs to take care of options according to the rules described in Chapter 18. The last stage of forwarding an IP packet is taken care of by ip_forward_finish. This function uses the unlikely macro to wrap the condition that checks whether there is any IP option to take care of. See the section "ip_forward_finish Function" in Chapter 20.
基本上跟先前的認知是一樣的, 但發覺 ARM, MIPS 跟 PowerPC 用的 GNU crosscompiler 似乎都不會去做這些個 optimization... x86 的就會...
2008年5月8日 星期四
WiMAX 又來了...
WiMax Gets Real
Google, Sprint-Nextel, Intel, Comcast, Clearwire, Time-Warner 跟 Bright house 站出來出 14.55billion(!!) 準備建構 WiMAX 網路, 看來最近 WiMAX 相關類股應該會大漲個幾天才是...
據我所知, 台灣出 WiMAX 最多的是正文, 其他還有 ZyXEL, 東訊跟 AWB (智邦子公司). 喊了好久終於有一點點影子了, 但跟 LTE 的競爭似乎還沒結束, Let's see...
2008年4月1日 星期二
mb(), wmb(), rmb
看到之後翻了翻 Linux device driver, 2nd edition. 喔... 原來是降子的啊... 意思是說用來提醒 compiler 在這些個 mb function 前的 memory operation 要先做完, 之後的動作才可以做... 就是讓 optimization 不要自作主張, 把該先寫進(或讀入) memory 的動作給搬到後面去了...
例如:
writel(addr, val);
wmb()
val = readl(addr);
這樣就會 force compiler 在 wmb() 前的 writel 動作必須先做完, 之後的 readl 才會有意義...
但我卻發現 ARM 的 wmb(), rmb(), mb() 似乎沒有意義?? in include/asm-arm/system.h:
#if __LINUX_ARM_ARCH__ >= 6
#define mb() __asm__ __volatile__ ("mcr p15, 0, %0, c7, c10, 5" \
: : "r" (0) : "memory")
#else
#define mb() __asm__ __volatile__ ("" : : : "memory")
#endif
#define rmb() mb()
#define wmb() mb()
要到 ARMv6 以上的才會透過 coprocessor 15 force flush memory (? 不清楚, 沒用過 ARMv6). 看了一下 MIPS 的 code (include/asm-mips/system.h)
#define __sync() \
__asm__ __volatile__( \
".set push\n\t" \
".set noreorder\n\t" \
".set mips2\n\t" \
"sync\n\t" \
".set pop" \
: /* no output */ \
: /* no input */ \
: "memory")
#define fast_wmb() __sync()
#define fast_rmb() __sync()
#define fast_mb() __sync()
#define wmb() fast_wmb()
#define rmb() fast_rmb()
#define mb() fast_mb()
wmb(), rmb(), mb() 真的會去做 sync 動作...
怪怪的, ARM 的東西好像缺東缺西的... @_@
2008年3月28日 星期五
likely & unlikely
在 kernel include file (include/linux/compiler.h) 裡它們是這樣定義的:
#define likely(x) __builtin_expect(!!(x), 1)
#define unlikely(x) __builtin_expect(!!(x), 0)
這個意思是怎樣呢? 用 google 找了一下, 原來是說當 define likely 時, 預期判斷式的結果會是 x, 這樣 compiler 會把 x 為 true 的內容翻議之後放的比較近一點, 如此一來 instruction cache hit rate 會提高一點; 而 unlikely 就是預期 x 不為真, 這樣的話 compiler 就會把不為 true 的內容擺的比較近一點.
直接看例子比較快, 如以下的 c code:
int main(void)
{
int x, y, z;
x=1;
if (x)
{
y=x+1;
printf("Y: %d\n", y);
}
else
{
y=x+2;
printf("Y: %d\n", y);
}
printf("X: %d, Y: %x\n", x, y);
return 0;
}
我用 arm compiler 去 compile 後看到的 assembly code:
main.o: file format elf32-littlearm
Disassembly of section .text:
00000000
main():
0: e92d4030 stmdb sp!, {r4, r5, lr}
4: e3a04001 mov r4, #1 ; 0x1
8: e0845004 add r5, r4, r4
c: e1a01005 mov r1, r5
10: e59f0018 ldr r0, [pc, #24] ; 30 <.text+0x30>
14: ebfffffe bl 0
18: e1a01004 mov r1, r4
1c: e1a02005 mov r2, r5
20: e59f000c ldr r0, [pc, #12] ; 34 <.text+0x34>
24: ebfffffe bl 0
28: e3a00000 mov r0, #0 ; 0x0
2c: e8bd8030 ldmia sp!, {r4, r5, pc}
30: 00000000 andeq r0, r0, r0
34: 00000008 andeq r0, r0, r8
unlikely:
main3.o: file format elf32-littlearm
Disassembly of section .text:
00000000
main():
0: e92d4010 stmdb sp!, {r4, lr}
4: e3a00001 mov r0, #1 ; 0x1
8: ebfffffe bl 0
c: e3a04002 mov r4, #2 ; 0x2
10: e3500000 cmp r0, #0 ; 0x0
14: e1a01004 mov r1, r4
18: 03a04003 moveq r4, #3 ; 0x3
1c: 01a01004 moveq r1, r4
20: e59f001c ldr r0, [pc, #28] ; 44 <.text+0x44>
24: 059f0018 ldreq r0, [pc, #24] ; 44 <.text+0x44>
28: ebfffffe bl 0
2c: e1a02004 mov r2, r4
30: e3a01001 mov r1, #1 ; 0x1
34: e59f000c ldr r0, [pc, #12] ; 48 <.text+0x48>
38: ebfffffe bl 0
3c: e3a00000 mov r0, #0 ; 0x0
40: e8bd8010 ldmia sp!, {r4, pc}
44: 00000000 andeq r0, r0, r0
48: 00000008 andeq r0, r0, r8
likely:
main2.o: file format elf32-littlearm
Disassembly of section .text:
00000000
main():
0: e92d4010 stmdb sp!, {r4, lr}
4: e3a00001 mov r0, #1 ; 0x1
8: ebfffffe bl 0
c: e3a04002 mov r4, #2 ; 0x2
10: e3500000 cmp r0, #0 ; 0x0
14: e1a01004 mov r1, r4
18: 03a04003 moveq r4, #3 ; 0x3
1c: 01a01004 moveq r1, r4
20: e59f001c ldr r0, [pc, #28] ; 44 <.text+0x44>
24: 059f0018 ldreq r0, [pc, #24] ; 44 <.text+0x44>
28: ebfffffe bl 0
2c: e1a02004 mov r2, r4
30: e3a01001 mov r1, #1 ; 0x1
34: e59f000c ldr r0, [pc, #12] ; 48 <.text+0x48>
38: ebfffffe bl 0
3c: e3a00000 mov r0, #0 ; 0x0
40: e8bd8010 ldmia sp!, {r4, pc}
44: 00000000 andeq r0, r0, r0
48: 00000008 andeq r0, r0, r8
怪怪的, 不管是 likely 或 unlikely 翻出來的 code 幾乎一樣, 後來換用 MIPS 跟 PowerPC compiler 都依樣... 看來 embedded system 的 compiler optimization 都沒做好 !?
