❶ android操作系統是基於Linux Kernel是什麼意思
每一個操作系統都有不同的內核。像Windows每個版本的內核都不同,而Mac OX用的是Unix的內核,Linux用的是Linux內核。而Android操作系統的內核是Linux,但是他不是一種Linux操作系統。
❷ android軟體開發的架構
Android以java為編程語言,使介面到功能,都有層出不窮的變化,其中Activity等同於J2ME的MIDlet,一個 Activity 類(class)負責如世御創建視窗(window),一個活動中的Activity就是在 foreground(前景)模式,背景運行的程序叫做Service。兩者之間通過由和AIDL連結,達到復數程序同時運行的效果。如果運行中的 Activity 全部畫面被其他 Activity 取代時,該 Activity 便被停止(stopped),甚至被系統清除(kill)。
View等同於J2ME的Displayable,程序人員可以通過 View 類與「XML layout」檔將UI放置在視窗上,Android 1.5的版本可以利用 View 打造出所謂的 Widgets,其實Widget只是View的一種,所以可以使用xml來設計layout,HTC的Android Hero手機即含有大量的widget。至於ViewGroup 是各種layout 的基礎抽象類(abstract class),ViewGroup之內還可以有ViewGroup。View的構造函數不需要在Activity中調用,但是Displayable的是必須的,在Activity 中,要通過()來從XML 中取得View,Android的View類的顯示很大程度上是從XML中讀取的。View 與事件(event)息息相關,兩者之間通過Listener 結合在一起,每一個渣岩View都可以注冊一個event listener,例如:當View要處理用戶觸碰(touch)的事件時,就要向Android框架注冊View.。另外還有Image等同於J2ME的BitMap。 在模擬器上運行模擬是虛擬設備(AVD),我們需要配置來運行我們的Android應用程序。步驟1、開放的AVD管理步驟2、新的按鈕,點擊添加新設備,並配置您的設備設置。步驟3、會有一個結果窗口顯示所有已配置你上一屏幕選擇。步驟4、按「確定」,你將會看到你的設備列在有你可以關閉此窗口。步驟5、運行你的Android應用程序項目從Eclipse,如果只有一個AVD配置,它會自動部署的應用程序也會出現一個窗口,選擇你的圖片。 模擬器將開始。在設備上運行
Android應用程序可以直接部署在Android設備上,這幾個配置所需要的。步驟1、在調試模式的設置可以設置應用程序:Android的<應用程序>元真可調試屬性。ADT 8這是默認的。步驟2、您的設備上啟用USB調試:Android 3.2或以上轉至設置>應用程序>開發和啟用USB調試。在Android 4更新,這是開發商選擇設置>。註:在Android 4.2更新,開發者選項是默認隱藏。可以,去設定>android的版本號。返回先前屏幕找到開發商選擇。步返敗驟3、安裝USB驅動程序為您的設備,計算機識別你的設備。步驟4、一旦設置和您的設備通過USB連接,從Eclipse菜單欄安裝您的應用程序在設備上選擇運行>運行(或運行>調試)。 操作系統與應用程序的溝通橋梁,並用分為兩層:函數層(Library)和虛擬機(Virtual Machine)。 Bionic是 Android 改良libc的版本。Android 同時包含了Webkit,所謂的Webkit 就是Apple Safari瀏覽器背後的引擎。Surface flinger 是就2D或3D的內容顯示到屏幕上。Android使用工具鏈(Toolchain)為Google自製的Bionic Libc。
Android採用OpenCORE作為基礎多媒體框架。OpenCORE可分7大塊:PVPlayer、PVAuthor、Codec、PacketVideo Multimedia Framework(PVMF)、Operating SystemLibrary(OSCL)、Common、OpenMAX。
Android 使用skia 為核心圖形引擎,搭配OpenGL/ES。skia與Linux Cairo功能相當,但相較於Linux Cairo, skia 功能還只是陽春型的。2005年Skia公司被Google收購,2007年初,Skia GL源碼被公開,Skia 也是Google Chrome 的圖形引擎。
Android的多媒體資料庫採用SQLite資料庫系統。資料庫又分為共用資料庫及私用資料庫。用戶可通過類(Column)取得共用資料庫。
Android的中間層多以Java 實現,並且採用特殊的Dalvik虛擬機(Dalvik Virtual Machine)。Dalvik虛擬機是一種「暫存器型態」(Register Based)的Java虛擬機,變數皆存放於暫存器中,虛擬機的指令相對減少。
Dalvik虛擬機可以有多個實例(instance), 每個Android應用程序都用一個自屬的Dalvik虛擬機來運行,讓系統在運行程序時可達到優化。Dalvik虛擬機並非運行Java位元組碼(Bytecode),而是運行一種稱為.dex格式的文件。 Android 的 HAL(硬體抽像層)是能以封閉源碼形式提供硬體驅動模塊。HAL 的目的是為了把 Android framework 與 Linux kernel 隔開,讓 Android 不至過度依賴 Linux kernel,以達成 kernel independent 的概念,也讓 Android framework 的開發能在不考慮驅動程序實現的前提下進行發展。
HAL stub 是一種代理人(proxy)的概念,stub 是以 *.so 檔的形式存在。Stub 向 HAL「提供」操作函數(operations),並由 Android runtime 向 HAL 取得 stub 的 operations,再 callback 這些操作函數。HAL 里包含了許多的 stub(代理人)。Runtime 只要說明「類型」,即 mole ID,就可以取得操作函數。 Android 是運行於 Linux kernel之上,但並不是GNU/Linux。因為在一般GNU/Linux 里支持的功能,Android 大都沒有支持,包括Cairo、X11、Alsa、FFmpeg、GTK、Pango及Glibc等都被移除掉了。Android又以bionic 取代Glibc、以Skia 取代Cairo、再以opencore 取代FFmpeg 等等。Android 為了達到商業應用,必須移除被GNU GPL授權證所約束的部份,例如Android將驅動程序移到 userspace,使得Linux driver 與 Linux kernel徹底分開。bionic/libc/kernel/ 並非標準的kernel header files。Android 的 kernel header 是利用工具由 Linux kernel header 所產生的,這樣做是為了保留常數、數據結構與宏。
Android 的 Linux kernel控制包括安全(Security),存儲器管理(Memory Managemeat),程序管理(Process Management),網路堆棧(Network Stack),驅動程序模型(Driver Model)等。下載Android源碼之前,先要安裝其構建工具Repo來初始化源碼。Repo 是 Android 用來輔助Git工作的一個工具。
❸ 如何在程序異常退出前輸出當前進程的堆棧信息 Backtraces
列印堆棧是調試的常用方法,一般在系統異常時,我們可以將異常情況下的堆棧列印出來,這樣十分方便錯誤查找。實際上還有另外一個非常有用的功能:分析代碼的行為。android代碼太過龐大復雜了,完全的靜態分析經常是無從下手,因此通過列印堆棧的動態分析也十分必要。
Android列印堆棧的方法,簡單歸類一下
1. zygote的堆棧mp
實際上這個可以同時mp java線程及native線程的堆棧,對於java線程,java堆棧和native堆棧都可以得到。
使用方法很簡單,直接在adb shell或串口中輸入:
[plain] view plain
kill -3 <pid>
輸出的trace會保存在 /data/anr/traces.txt文件中。這個需要注意,如果沒有 /data/anr/這個目錄或/data/anr/traces.txt這個文件,需要手工創建一下,並設置好讀寫許可權。
如果需要在代碼中,更容易控制堆棧的輸出時機,可以用以下命令獲取zygote的core mp:
[java] view plain
Process.sendSignal(pid, Process.SIGNAL_QUIT);
原理和命令行是一樣的。
不過需要注意兩點:
adb shell可能會沒有許可權,需要root。
android 4.2中關閉了native thread的堆棧列印,詳見 dalvik/vm/Thread.cpp的mpNativeThread方法:
[cpp] view plain
dvmPrintDebugMessage(target,
"\"%s\" sysTid=%d nice=%d sched=%d/%d cgrp=%s\n",
name, tid, getpriority(PRIO_PROCESS, tid),
schedStats.policy, schedStats.priority, schedStats.group);
mpSchedStat(target, tid);
// Temporarily disabled collecting native stacks from non-Dalvik
// threads because sometimes they misbehave.
//dvmDumpNativeStack(target, tid);
Native堆棧的列印被關掉了!不過對於大多數情況,可以直接將這個注釋打開。
2. debuggerd的堆棧mp
debuggerd是android的一個daemon進程,負責在進程異常出錯時,將進程的運行時信息mp出來供分析。debuggerd生 成的coremp數據是以文本形式呈現,被保存在 /data/tombstone/ 目錄下(名字取的也很形象,tombstone是墓碑的意思),共可保存10個文件,當超過10個時,會覆蓋重寫最早生成的文件。從4.2版本開 始,debuggerd同時也是一個實用工具:可以在不中斷進程執行的情況下列印當前進程的native堆棧。使用方法是:
[plain] view plain
debuggerd -b <pid>
這可以協助我們分析進程執行行為,但最最有用的地方是:它可以非常簡單的定位到native進程中鎖死或錯誤邏輯引起的死循環的代碼位置。
3. java代碼中列印堆棧
Java代碼列印堆棧比較簡單, 堆棧信息獲取和輸出,都可以通過Throwable類的方法實現。目前通用的做法是在java進程出現需要注意的異常時,列印堆棧,然後再決定退出或挽救。通常的方法是使用exception的printStackTrace()方法:
[java] view plain
try {
...
} catch (RemoteException e) {
e.printStackTrace();
...
}
當然也可以只列印堆棧不退出,這樣就比較方便分析代碼的動態運行情況。Java代碼中插入堆棧列印的方法如下:
[java] view plain
Log.d(TAG,Log.getStackTraceString(new Throwable()));
4. C++代碼中列印堆棧
C++也是支持異常處理的,異常處理庫中,已經包含了獲取backtrace的介面,Android也是利用這個介面來列印堆棧信息的。在Android的C++中,已經集成了一個工具類CallStack,在libutils.so中。使用方法:
[cpp] view plain
#include <utils/CallStack.h>
...
CallStack stack;
stack.update();
stack.mp();
使用方式比較簡單。目前Andoid4.2版本已經將相關信息解析的很到位,符號表查找,demangle,偏移位置校正都做好了。
[plain] view plain
5. C代碼中列印堆棧
C代碼,尤其是底層C庫,想要看到調用的堆棧信息,還是比較麻煩的。 CallStack肯定是不能用,一是因為其實C++寫的,需要重新封裝才能在C中使用,二是底層庫反調上層庫的函數,會造成鏈接器循環依賴而無法鏈接。 不過也不是沒有辦法,可以通過android工具類CallStack實現中使用的unwind調用及符號解析函數來處理。
這里需要注意的是,為解決鏈接問題,最好使用dlopen方式,查找需要用到的介面再直接調用,這樣會比較簡單。如下為相關的實現代碼,只需要在要 列印的文件中插入此部分代碼,然後調用getCallStack()即可,無需包含太多的頭文件和修改Android.mk文件:
[cpp] view plain
#define MAX_DEPTH 31
#define MAX_BACKTRACE_LINE_LENGTH 800
#define PATH "/system/lib/libcorkscrew.so"
typedef ssize_t (*unwindFn)(backtrace_frame_t*, size_t, size_t);
typedef void (*unwindSymbFn)(const backtrace_frame_t*, size_t, backtrace_symbol_t*);
typedef void (*unwindSymbFreeFn)(backtrace_symbol_t*, size_t);
static void *gHandle = NULL;
static int getCallStack(void){
ssize_t i = 0;
ssize_t result = 0;
ssize_t count;
backtrace_frame_t mStack[MAX_DEPTH];
backtrace_symbol_t symbols[MAX_DEPTH];
unwindFn unwind_backtrace = NULL;
unwindSymbFn get_backtrace_symbols = NULL;
unwindSymbFreeFn free_backtrace_symbols = NULL;
// open the so.
if(gHandle == NULL) gHandle = dlopen(PATH, RTLD_NOW);
// get the interface for unwind and symbol analyse
if(gHandle != NULL) unwind_backtrace = (unwindFn)dlsym(gHandle, "unwind_backtrace");
if(gHandle != NULL) get_backtrace_symbols = (unwindSymbFn)dlsym(gHandle, "get_backtrace_symbols");
if(gHandle != NULL) free_backtrace_symbols = (unwindSymbFreeFn)dlsym(gHandle, "free_backtrace_symbols");
if(!gHandle ||!unwind_backtrace ||!get_backtrace_symbols || !free_backtrace_symbols ){
ALOGE("Error! cannot get unwind info: handle:%p %p %p %p",
gHandle, unwind_backtrace, get_backtrace_symbols, free_backtrace_symbols );
return result;
}
count= unwind_backtrace(mStack, 1, MAX_DEPTH);
get_backtrace_symbols(mStack, count, symbols);
for (i = 0; i < count; i++) {
char line[MAX_BACKTRACE_LINE_LENGTH];
const char* mapName = symbols[i].map_name ? symbols[i].map_name : "<unknown>";
const char* symbolName =symbols[i].demangled_name ? symbols[i].demangled_name : symbols[i].symbol_name;
size_t fieldWidth = (MAX_BACKTRACE_LINE_LENGTH - 80) / 2;
if (symbolName) {
uint32_t pc_offset = symbols[i].relative_pc - symbols[i].relative_symbol_addr;
if (pc_offset) {
snprintf(line, MAX_BACKTRACE_LINE_LENGTH, "#%02d pc %08x %.*s (%.*s+%u)",
i, symbols[i].relative_pc, fieldWidth, mapName,
fieldWidth, symbolName, pc_offset);
} else {
snprintf(line, MAX_BACKTRACE_LINE_LENGTH, "#%02d pc %08x %.*s (%.*s)",
i, symbols[i].relative_pc, fieldWidth, mapName,
fieldWidth, symbolName);
}
} else {
snprintf(line, MAX_BACKTRACE_LINE_LENGTH, "#%02d pc %08x %.*s",
i, symbols[i].relative_pc, fieldWidth, mapName);
}
ALOGD("%s", line);
}
free_backtrace_symbols(symbols, count);
return result;
}
對sched_policy.c的堆棧調用分析如下,注意具體是否要列印,在哪裡列印,還可以通過pid、uid、property等來控制一下,這樣就不會被淹死在trace的汪洋大海中。
[plain] view plain
D/SchedPolicy( 1350): #00 pc 0000676c /system/lib/libcutils.so
D/SchedPolicy( 1350): #01 pc 00006b3a /system/lib/libcutils.so (set_sched_policy+49)
D/SchedPolicy( 1350): #02 pc 00010e82 /system/lib/libutils.so (androidSetThreadPriority+61)
D/SchedPolicy( 1350): #03 pc 00068104 /system/lib/libandroid_runtime.so (android_os_Process_setThreadPriority(_JNIEnv*, _jobject*, int, int)+7)
D/SchedPolicy( 1350): #04 pc 0001e510 /system/lib/libdvm.so (dvmPlatformInvoke+112)
D/SchedPolicy( 1350): #05 pc 0004d6aa /system/lib/libdvm.so (dvmCallJNIMethod(unsigned int const*, JValue*, Method const*, Thread*)+417)
D/SchedPolicy( 1350): #06 pc 00027920 /system/lib/libdvm.so
D/SchedPolicy( 1350): #07 pc 0002b7fc /system/lib/libdvm.so (dvmInterpret(Thread*, Method const*, JValue*)+184)
D/SchedPolicy( 1350): #08 pc 00060c30 /system/lib/libdvm.so (dvmCallMethodV(Thread*, Method const*, Object*, bool, JValue*, std::__va_list)+271)
D/SchedPolicy( 1350): #09 pc 0004cd34 /system/lib/libdvm.so
D/SchedPolicy( 1350): #10 pc 00049382 /system/lib/libandroid_runtime.so
D/SchedPolicy( 1350): #11 pc 00065e52 /system/lib/libandroid_runtime.so
D/SchedPolicy( 1350): #12 pc 0001435e /system/lib/libbinder.so (android::BBinder::transact(unsigned int, android::Parcel const&, android::Parcel*, unsigned int)+57)
D/SchedPolicy( 1350): #13 pc 00016f5a /system/lib/libbinder.so (android::IPCThreadState::executeCommand(int)+513)
D/SchedPolicy( 1350): #14 pc 00017380 /system/lib/libbinder.so (android::IPCThreadState::joinThreadPool(bool)+183)
D/SchedPolicy( 1350): #15 pc 0001b160 /system/lib/libbinder.so
D/SchedPolicy( 1350): #16 pc 00011264 /system/lib/libutils.so (android::Thread::_threadLoop(void*)+111)
D/SchedPolicy( 1350): #17 pc 000469bc /system/lib/libandroid_runtime.so (android::AndroidRuntime::javaThreadShell(void*)+63)
D/SchedPolicy( 1350): #18 pc 00010dca /system/lib/libutils.so
D/SchedPolicy( 1350): #19 pc 0000e3d8 /system/lib/libc.so (__thread_entry+72)
D/SchedPolicy( 1350): #20 pc 0000dac4 /system/lib/libc.so (pthread_create+160)
D/SchedPolicy( 1350): #00 pc 0000676c /system/lib/libcutils.so
D/SchedPolicy( 1350): #01 pc 00006b3a /system/lib/libcutils.so (set_sched_policy+49)
D/SchedPolicy( 1350): #02 pc 00016f26 /system/lib/libbinder.so (android::IPCThreadState::executeCommand(int)+461)
D/SchedPolicy( 1350): #03 pc 00017380 /system/lib/libbinder.so (android::IPCThreadState::joinThreadPool(bool)+183)
D/SchedPolicy( 1350): #04 pc 0001b160 /system/lib/libbinder.so
D/SchedPolicy( 1350): #05 pc 00011264 /system/lib/libutils.so (android::Thread::_threadLoop(void*)+111)
D/SchedPolicy( 1350): #06 pc 000469bc /system/lib/libandroid_runtime.so (android::AndroidRuntime::javaThreadShell(void*)+63)
D/SchedPolicy( 1350): #07 pc 00010dca /system/lib/libutils.so
D/SchedPolicy( 1350): #08 pc 0000e3d8 /system/lib/libc.so (__thread_entry+72)
D/SchedPolicy( 1350): #09 pc 0000dac4 /system/lib/libc.so (pthread_create+160)
6. 其它堆棧信息查詢
❹ 求 a stack of 和 a pile of 區別
stack是整齊的一堆。pile是隨便堆放的
1. aumulate
幾乎可用於指任何事物量的增加,側重連續不斷地,一點一滴地聚積。如:
He aumulated a good library.
積累了豐富的藏書。
However, as the evidence began to aumulate, experts from the Zoo felt obliged to investigate.
然而,隨著跡象開始積聚,倫敦動物園的專家們感到有必要進行調查了。
2. amass 強調大量的聚集,常用於財富、資訊、所有物等的聚集,這種積累可能一下子完成,也可能在短期內完成,也可能在比較長的時間內完成,但是數量總是很大的。如:
People tend to amass possessions, sometimes without being aware of doing so.
人們傾向於積攢東西,有的並未意識到這樣做。
3. collect
普通用詞,多用於指物,側重指有區別地作選擇或有安排有計劃地把零散物集中起來。如:
He』s collecting money for the blind.
他在為盲人募款。
Collecting stamps is a hobby of mine.
集郵是我的一個愛好。
All I hope is we can collect more fund for it.
我只希望我們能為此籌集更多資金。
4. gather 普通用詞,指人或物或抽象事物都可用。側重於圍繞一個中心的集合、聚集。如:
We would all gather there on Friday evenings.
星期五晚上我們都在那裡聚會。
The lords and ladies were all gathered at the palace.
貴族老爺和夫人都聚集在皇宮里。
She gathered up her things and left.
她收拾好她的東西就走了。
5. heap 主要指把東西堆集,尤其指沙、石、煤、草、穀物等堆高,不強調整齊。如:
Mother heaped delicious food on the plate.
母親在盤子里堆滿了好吃的東西。
The barn of the used-to-be-poor farmer is now heaped with grain.
過去很貧窮的農民的谷倉里現在堆滿了糧食。
6. pile 著重指比較整齊地把東西堆積在一起。如:
She piled the books on the table.
她把書堆在桌子上。
call stack是函式呼叫堆疊,就是程式執行時函式的呼叫過程,例如A函式呼叫了B函式,那麼程式執行到B函式的時候,call stack里就會有A函式,因為函式呼叫時需要把當前函式入棧,在B函式執行完畢後再從堆疊里將A函式取出,以讓程式指標回到A函式繼續執行。
stack就只是堆疊的意思,在程式里單說stack的時候,是指執行時記憶體里的一塊指定的資料結構空間,用於存放區域性變數,發生函式呼叫時,新建立的區域性變數都會存放在stack里,函式返回時區域性變數需要釋放,就會從stack里被清空。
1.heap是堆,stack是棧。2.stack的空間由作業系統自動分配和釋放,heap的空間是手動申請和釋放的,heap常用new關鍵字來分配。3.stack空間有限,heap的空間是很大的自由區。在Java中,若只是宣告一個物件,則先在棧記憶體中為其分配地址空間,若再new一下,例項化它,則在堆記憶體中為其分配地址。4.舉例:資料型別 變數名;這樣定義的東西在棧區。如:Object a =null; 只在棧記憶體中分配空間new 資料型別();或者malloc(長度); 這樣定義的東西就在堆區如:Object b =new Object(); 則在堆記憶體中分配空間
pack into 英[pæk ˈɪntuː] 美[pæk ˈɪntu]
[詞典] 塞進,擠進;
[例句]I have tried to pack a good deal into a few words.
我盡量言簡意賅。
stack into
堆成
什麼是Android Application?
簡單來說,一個apk檔案就是一個Application。
任何一個Android Application基本上是由一些Activities組成,當用戶與應用程式互動時其所包含的部分Activities具有緊密的邏輯關系,或者各自獨立處理不同的響應。
這些Activities捆綁在一起成為了一個處理特定需求的Application, 並且以「.apk」作為字尾名存在於檔案系統中。
Android平台預設下的應用程式 例如:Email、Calendar、Browser、Maps、Text Message、Contacts、Camera和Dialer等都是一個個獨立的Apps。
就像我們已經知道的,Application基本上是由四個模組組成:Activity、Service、Content Provider 和 Broadcast Receiver,其中Activity是實現應用的主體。
什麼是 Activity Stack?
操作應用程式時,有時需要呼叫多個Activities來完成需求,例如:傳送郵件程式,首先是進入郵件主介面,然後啟動一個新的Activity用於填寫新郵件內容,同時可以調出聯絡人列表用於插入收件人資訊等等。在這個操作過程中 Android平台有一個專門用於管理Activities堆疊的機制,其可以方便的線性記錄Activities例項,當完成某個操作時,可以通過導航功能返回之前的Activity(通過按操作台的「Back」按鈕)。
每次啟動新的Activity都將被新增到Activity Stack。使用者可以方便的返回上一個Activity直到Home Screen,到達Home Screen後,將無法再繼續檢視堆疊記錄(俗話說:到頭了)。如果當前Task被中止(Interrupting the task),返回到系統主介面後啟動了其它操作,當希望返回到前一個Task繼續執行時,只需要再次通過主介面的Application launcher或者快捷方式啟動這個Task的Root Activity便可返回其中止時的狀態繼續執行。
相對於Views、Windows、Menus和Dialogs而言,Activity是唯一可被記錄在History stack中的資料,所以當你所設計的應用程式需要使用者由A介面進入到次一級介面B,當完成操作後需要再次返回A,那麼必須考慮將A看作為 Activity,否則將無法從歷史堆疊中返回。
什麼是Task
當我們需要一個Activity可以啟動另一個Activity,可能另外一個Activity是定義在不同應用程式中的Activity。
例如,假設你想在你的應用中讓使用者顯示一些地方的街景。而這里已經有一個Activity可以做到這一點,因此,你的Activity所需要做的只是在Intent物件中新增必要的資訊,並傳遞給startActivity()。地圖瀏覽將會顯示你的地圖。當用戶按下BACK鍵,你的Activity會再次出現在螢幕上。
對於使用者來說,看起來好像是地圖瀏覽與你的Activity一樣,屬於相同的應用程式,即便是它定義在其它的應用程式里,並執行在那個應用程式的程序里。
Android通過將這兩個Activity儲存在同一個Task里來體現這一使用者體驗。簡單來說,一個Task就是使用者體驗上的一個「應用」。
它將相關的Activity組合在一起,以stack的方式管理(就是前面提到的Activity Stack),這就是Task。
在Android平台上可以將task簡單的理解為幽多個Activity共同協作完成某項應用,而不管Activity具體屬於哪個Application,
什麼是Android Application? 簡單來說,一個apk檔案就是一個Application。 任何一個Android Application基本上是由一些Activities組成,當用戶與應用程式互動時其所包含的部分Activities具有緊密的邏輯關系,或者各自獨立處理不同的響應。
java堆和棧的區別 Java中記憶體分成兩種:一種是棧stack,一種是堆heap。 函式中的一些基本型別的變數(int, float)和物件的引用變數(reference)都在函式的棧中,馬克-to-win,(工作於編譯階段, 生成class檔案之前)分配。存取速度快,稍遜於...
相同點:stack和heap都是記憶體區域
不同點:stack的記憶體區域小,heap的記憶體區域大。stack用於存放變數,地址,heap用於存放物件,是真正的存放物件的地方。
❺ Android什麼意思
android - 以Linux為基礎的操作系統
Android(['ændrɔid])是一個以Linux為基礎的半開源操作系統,主要用於移動設備,由Google和開放手持設備聯盟開發與領導。 Android 系統最初由安迪·魯賓(Andy Rubin)製作,最初主要支持手機。2005年8月17日被Google收購。2007年11月5日,Google與84家硬體製造商、軟體開發商及電信營運商組成開放手持設備聯盟(Open Handset Alliance)來共同研發改良Android系統並生產搭載Android的智慧型手機,並逐漸拓展到平板電腦及其他領域上。隨後,Google以Apache免費開源許可證的授權方式,發布了Android的源代碼。
一、系統介紹
Android是一種以Linux與JAVA為基礎的開放源代碼操作系統,主要使用於便攜設備。中國大陸地區較多人使用「安卓」。Android操作系統最初由Andy Rubin開發,被谷歌收購後則由Google公司和開放手機聯盟領導及開發,主要支持手機與平板。
二、系統特點
【系統內核 】
Android 是運行於 Linux kernel之上,但並不是GNU/Linux。因為在一般GNU/Linux 里支持的功能,Android 大都沒有支持,包括Cairo、X11、Alsa、FFmpeg、GTK、Pango及Glibc等都被移除掉了。
Android又以bionic 取代Glibc、以Skia 取代Cairo、再以opencore 取代FFmpeg 等等。Android 為了達到商業應用,必須移除被GNU GPL授權證所約束的部份,例如Android將驅動程序移到 userspace,使得Linux driver 與 Linux kernel徹底分開。
bionic/libc/kernel/ 並非標準的kernel header files。Android 的 kernel header 是利用工具由 Linux kernel header 所產生的,這樣做是為了保留常數、數據結構與宏。
Android 的 Linux kernel控制包括安全(Security),存儲器管理(Memory Management),程序管理(Process Management),網路堆棧(Network Stack),驅動程序模型(Driver Model)等。下載Android源碼之前,先要安裝其構建工具 Repo來初始化源碼。Repo 是 Android 用來輔助Git工作的一個工具。
【硬體抽象層】
Android 的 HAL(硬體抽像層)是能以封閉源碼形式提供硬體驅動模塊。HAL 的目的是為了把 Android framework 與 Linux kernel 隔開,讓 Android 不至過度依賴 Linux kernel,以達成 kernel independent 的概念,也讓 Android framework 的開發能在不考量驅動程序實現的前提下進行發展。
HAL stub 是一種代理人(proxy)的概念,stub 是以 *.so 檔的形式存在。Stub 向 HAL「提供」操作函數(operations),並由 Android runtime 向 HAL 取得 stub 的 operations,再 callback 這些操作函數。HAL 里包含了許多的 stub(代理人)。Runtime 只要說明「類型」,即 mole ID,就可以取得操作函數。