am 9b19d582: am 4f66a14d: Merge "EmuGL: handle NULL data in glBufferData" into ics-mr1

* commit '9b19d582d94a343437aacf962b8b95b83361bc10':
  EmuGL: handle NULL data in glBufferData
diff --git a/build/Android.mk b/build/Android.mk
index e4eeb0a..1cb0653 100644
--- a/build/Android.mk
+++ b/build/Android.mk
@@ -1,3 +1,27 @@
+# ===== SDK source.property files =====
+
+# Add all files to be generated from the source.prop templates to the SDK pre-requisites
+ALL_SDK_FILES += $(patsubst \
+                   $(TOPDIR)development/sdk/%_source.prop_template, \
+                   $(HOST_OUT)/development/sdk/%_source.properties, \
+                   $(wildcard $(TOPDIR)development/sdk/*_source.prop_template))
+
+# Rule to convert a source.prop template into the desired source.property
+# Rewritten variables:
+# - ${PLATFORM_VERSION}          e.g. "1.0"
+# - ${PLATFORM_SDK_VERSION}      e.g. "3", aka the API level
+# - ${PLATFORM_VERSION_CODENAME} e.g. "REL" (transformed into "") or "Cupcake"
+$(HOST_OUT)/development/sdk/%_source.properties : $(TOPDIR)development/sdk/%_source.prop_template
+	@echo Generate $@
+	$(hide) mkdir -p $(dir $@)
+	$(hide) sed -e 's/$${PLATFORM_VERSION}/$(PLATFORM_VERSION)/' \
+		 -e 's/$${PLATFORM_SDK_VERSION}/$(PLATFORM_SDK_VERSION)/' \
+		 -e 's/$${PLATFORM_VERSION_CODENAME}/$(subst REL,,$(PLATFORM_VERSION_CODENAME))/' \
+		 $< > $@
+
+
+# ===== Android Support/Compatibility Library =====
+
 LOCAL_PATH := $(call my-dir)
 
 # The source files for this library are _all_ generated, something we don't do
diff --git a/build/sdk-android-armeabi-v7a.atree b/build/sdk-android-armeabi-v7a.atree
index ddf2f65..603f146 100644
--- a/build/sdk-android-armeabi-v7a.atree
+++ b/build/sdk-android-armeabi-v7a.atree
@@ -18,4 +18,4 @@
 prebuilts/qemu-kernel/${TARGET_ARCH}/kernel-qemu-armv7 system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/kernel-qemu
 
 # version files for the SDK updater, from development.git
-development/sdk/images_armeabi-v7a_source.properties   system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/source.properties
+${HOST_OUT}/development/sdk/images_armeabi-v7a_source.properties system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/source.properties
diff --git a/build/sdk-android-armeabi.atree b/build/sdk-android-armeabi.atree
index 2badd85..f641ee3 100644
--- a/build/sdk-android-armeabi.atree
+++ b/build/sdk-android-armeabi.atree
@@ -17,4 +17,4 @@
 prebuilts/qemu-kernel/${TARGET_ARCH}/kernel-qemu system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/kernel-qemu
 
 # version files for the SDK updater, from development.git
-development/sdk/images_armeabi_source.properties   system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/source.properties
+${HOST_OUT}/development/sdk/images_armeabi_source.properties system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/source.properties
diff --git a/build/sdk-android-x86.atree b/build/sdk-android-x86.atree
index 8425600..9adad9b 100644
--- a/build/sdk-android-x86.atree
+++ b/build/sdk-android-x86.atree
@@ -17,4 +17,4 @@
 prebuilts/qemu-kernel/${TARGET_ARCH}/kernel-qemu system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/kernel-qemu
 
 # version files for the SDK updater, from development.git
-development/sdk/images_x86_source.properties   system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/source.properties
+${HOST_OUT}/development/sdk/images_x86_source.properties system-images/${PLATFORM_NAME}/${TARGET_CPU_ABI}/source.properties
diff --git a/build/sdk.atree b/build/sdk.atree
index 323ffcf..a6f75f3 100644
--- a/build/sdk.atree
+++ b/build/sdk.atree
@@ -61,7 +61,7 @@
 ##############################################################################
 
 # version files for the SDK updater, from development.git
-development/sdk/platform_source.properties    platforms/${PLATFORM_NAME}/source.properties
+${HOST_OUT}/development/sdk/platform_source.properties platforms/${PLATFORM_NAME}/source.properties
 
 # copy build prop from out/.../sdk/
 sdk/sdk-build.prop                            platforms/${PLATFORM_NAME}/build.prop
@@ -132,7 +132,7 @@
 ##############################################################################
 
 # version files for the SDK updater, from sdk.git
-development/sdk/doc_source.properties docs/source.properties
+${HOST_OUT}/development/sdk/doc_source.properties docs/source.properties
 
 # the docs
 docs/offline-sdk docs
diff --git a/build/tools/sdk_repo.mk b/build/tools/sdk_repo.mk
index cc0d1be..a0d93de 100644
--- a/build/tools/sdk_repo.mk
+++ b/build/tools/sdk_repo.mk
@@ -88,10 +88,10 @@
 # $3=package to create, must be "sources"
 #
 define mk-sdk-repo-sources
-$(call sdk-repo-pkg-zip,$(1),$(2),$(3)): $(2) $(TOPDIR)development/sdk/source_source.properties
+$(call sdk-repo-pkg-zip,$(1),$(2),$(3)): $(2) $(HOST_OUT)/development/sdk/source_source.properties
 	@echo "Building SDK sources package"
-	$(hide) $(TOPDIR)development/build/tools/mk_sources_zip.py --exec-zip \
-			$(TOPDIR)development/sdk/source_source.properties \
+	$(hide) $(TOPDIR)development/build/tools/mk_sources_zip.py \
+			$(HOST_OUT)/development/sdk/source_source.properties \
 			$(call sdk-repo-pkg-zip,$(1),$(2),$(3)) \
 			$(TOPDIR).
 $(call dist-for-goals, sdk_repo, $(call sdk-repo-pkg-zip,$(1),$(2),$(3)))
diff --git a/cmds/monkey/src/com/android/commands/monkey/MonkeySourceNetworkViews.java b/cmds/monkey/src/com/android/commands/monkey/MonkeySourceNetworkViews.java
index 5d078c2..c2a1093 100644
--- a/cmds/monkey/src/com/android/commands/monkey/MonkeySourceNetworkViews.java
+++ b/cmds/monkey/src/com/android/commands/monkey/MonkeySourceNetworkViews.java
@@ -378,7 +378,7 @@
             if (command.size() == 2) {
                 String text = command.get(1);
                 List<AccessibilityNodeInfo> nodes = AccessibilityInteractionClient.getInstance()
-                    .findAccessibilityNodeInfosByViewTextInActiveWindow(sConnectionId, text);
+                    .findAccessibilityNodeInfosByTextInActiveWindow(sConnectionId, text);
                 ViewIntrospectionCommand idGetter = new GetAccessibilityIds();
                 List<String> emptyArgs = new ArrayList<String>();
                 StringBuilder ids = new StringBuilder();
diff --git a/host/windows/usb/android_winusb.inf b/host/windows/usb/android_winusb.inf
index 47cf2f7..ab25970 100755
--- a/host/windows/usb/android_winusb.inf
+++ b/host/windows/usb/android_winusb.inf
@@ -6,7 +6,7 @@
 Class               = AndroidUsbDeviceClass

 ClassGuid           = {3F966BD9-FA04-4ec5-991C-D326973B5128}

 Provider            = %ProviderName%

-DriverVer           = 12/06/2010,4.0.0000.00000

+DriverVer           = 10/19/2011,6.0.0000.00000

 CatalogFile.NTx86   = androidwinusb86.cat

 CatalogFile.NTamd64 = androidwinusba64.cat

 

@@ -26,42 +26,33 @@
 %ProviderName% = Google, NTx86, NTamd64

 

 [Google.NTx86]

-; HTC Dream

-%SingleAdbInterface%        = USB_Install, USB\VID_0BB4&PID_0C01

-%CompositeAdbInterface%     = USB_Install, USB\VID_0BB4&PID_0C02&MI_01

-%SingleBootLoaderInterface% = USB_Install, USB\VID_0BB4&PID_0FFF

-; HTC Magic

-%CompositeAdbInterface%     = USB_Install, USB\VID_0BB4&PID_0C03&MI_01

-;

-;Moto Sholes

-%SingleAdbInterface%        = USB_Install, USB\VID_22B8&PID_41DB

-%CompositeAdbInterface%     = USB_Install, USB\VID_22B8&PID_41DB&MI_01

-;

-;Google NexusOne

+

+;Google Nexus One

 %SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_0D02

 %CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_0D02&MI_01

 %SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_4E11

 %CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_4E12&MI_01

+

+;Google Nexus S

+%SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_4E21

 %CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_4E22&MI_01

+%SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_4E23

+%CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_4E24&MI_01

+

 

 [Google.NTamd64]

-; HTC Dream

-%SingleAdbInterface%        = USB_Install, USB\VID_0BB4&PID_0C01

-%CompositeAdbInterface%     = USB_Install, USB\VID_0BB4&PID_0C02&MI_01

-%SingleBootLoaderInterface% = USB_Install, USB\VID_0BB4&PID_0FFF

-; HTC Magic

-%CompositeAdbInterface%     = USB_Install, USB\VID_0BB4&PID_0C03&MI_01

-;

-;Moto Sholes

-%SingleAdbInterface%        = USB_Install, USB\VID_22B8&PID_41DB

-%CompositeAdbInterface%     = USB_Install, USB\VID_22B8&PID_41DB&MI_01

-;

-;Google NexusOne

+

+;Google Nexus One

 %SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_0D02

 %CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_0D02&MI_01

 %SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_4E11

 %CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_4E12&MI_01

+

+;Google Nexus S

+%SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_4E21

 %CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_4E22&MI_01

+%SingleAdbInterface%        = USB_Install, USB\VID_18D1&PID_4E23

+%CompositeAdbInterface%     = USB_Install, USB\VID_18D1&PID_4E24&MI_01

 

 [USB_Install]

 Include = winusb.inf

diff --git a/ndk/platforms/android-11/arch-arm/symbols/libc.so.functions.txt b/ndk/platforms/android-11/arch-arm/symbols/libc.so.functions.txt
new file mode 100644
index 0000000..33f96a7
--- /dev/null
+++ b/ndk/platforms/android-11/arch-arm/symbols/libc.so.functions.txt
@@ -0,0 +1,1083 @@
+MD5_Final
+MD5_Init
+MD5_Update
+SHA1Final
+SHA1Init
+SHA1Transform
+SHA1Update
+_Unwind_Backtrace
+_Unwind_Complete
+_Unwind_DeleteException
+_Unwind_ForcedUnwind
+_Unwind_GetCFA
+_Unwind_GetDataRelBase
+_Unwind_GetLanguageSpecificData
+_Unwind_GetRegionStart
+_Unwind_GetTextRelBase
+_Unwind_RaiseException
+_Unwind_Resume
+_Unwind_Resume_or_Rethrow
+_Unwind_VRS_Get
+_Unwind_VRS_Pop
+_Unwind_VRS_Set
+___Unwind_Backtrace
+___Unwind_ForcedUnwind
+___Unwind_RaiseException
+___Unwind_Resume
+___Unwind_Resume_or_Rethrow
+__adddf3
+__addsf3
+__aeabi_atexit
+__aeabi_cdcmpeq
+__aeabi_cdcmple
+__aeabi_cdrcmple
+__aeabi_d2f
+__aeabi_d2iz
+__aeabi_dadd
+__aeabi_dcmpeq
+__aeabi_dcmpge
+__aeabi_dcmpgt
+__aeabi_dcmple
+__aeabi_dcmplt
+__aeabi_dcmpun
+__aeabi_ddiv
+__aeabi_dmul
+__aeabi_drsub
+__aeabi_dsub
+__aeabi_f2d
+__aeabi_f2iz
+__aeabi_fadd
+__aeabi_fcmpun
+__aeabi_fdiv
+__aeabi_fmul
+__aeabi_frsub
+__aeabi_fsub
+__aeabi_i2d
+__aeabi_i2f
+__aeabi_idiv
+__aeabi_idivmod
+__aeabi_l2d
+__aeabi_l2f
+__aeabi_ldivmod
+__aeabi_lmul
+__aeabi_memclr
+__aeabi_memclr4
+__aeabi_memclr8
+__aeabi_memcpy
+__aeabi_memcpy4
+__aeabi_memcpy8
+__aeabi_memmove
+__aeabi_memmove4
+__aeabi_memmove8
+__aeabi_memset
+__aeabi_memset4
+__aeabi_memset8
+__aeabi_ui2d
+__aeabi_ui2f
+__aeabi_uidiv
+__aeabi_uidivmod
+__aeabi_ul2d
+__aeabi_ul2f
+__aeabi_uldivmod
+__aeabi_unwind_cpp_pr0
+__aeabi_unwind_cpp_pr1
+__aeabi_unwind_cpp_pr2
+__arc4_getbyte
+__assert
+__assert2
+__atexit_register_cleanup
+__atomic_cmpxchg
+__atomic_dec
+__atomic_inc
+__atomic_swap
+__b64_ntop
+__b64_pton
+__bionic_atfork_run_child
+__bionic_atfork_run_parent
+__bionic_atfork_run_prepare
+__bionic_clone
+__bionic_clone_entry
+__bionic_libgcc_compat_hooks
+__brk
+__cmpdf2
+__cxa_atexit
+__cxa_finalize
+__div0
+__divdf3
+__divdi3
+__divsf3
+__divsi3
+__dn_comp
+__dn_count_labels
+__dn_skipname
+__dorand48
+__eqdf2
+__errno
+__evAddTime
+__evCmpTime
+__evConsIovec
+__evConsTime
+__evNowTime
+__evSubTime
+__evTimeSpec
+__evTimeVal
+__evUTCTime
+__extendsfdf2
+__fcntl
+__fcntl64
+__findenv
+__fixdfsi
+__fixsfsi
+__floatdidf
+__floatdisf
+__floatsidf
+__floatsisf
+__floatundidf
+__floatundisf
+__floatunsidf
+__floatunsisf
+__fork
+__fp_nquery
+__fp_query
+__fstatfs64
+__futex_syscall3
+__futex_syscall4
+__futex_wait
+__futex_wait_ex
+__futex_wake
+__futex_wake_ex
+__gedf2
+__get_h_errno
+__get_pc
+__get_res_cache
+__get_sp
+__get_stack_base
+__get_thread
+__getcpu
+__getcwd
+__getpriority
+__gnu_Unwind_Backtrace
+__gnu_Unwind_Find_exidx
+__gnu_Unwind_ForcedUnwind
+__gnu_Unwind_RaiseException
+__gnu_Unwind_Restore_VFP
+__gnu_Unwind_Restore_VFP_D
+__gnu_Unwind_Restore_VFP_D_16_to_31
+__gnu_Unwind_Restore_WMMXC
+__gnu_Unwind_Restore_WMMXD
+__gnu_Unwind_Resume
+__gnu_Unwind_Resume_or_Rethrow
+__gnu_Unwind_Save_VFP
+__gnu_Unwind_Save_VFP_D
+__gnu_Unwind_Save_VFP_D_16_to_31
+__gnu_Unwind_Save_WMMXC
+__gnu_Unwind_Save_WMMXD
+__gnu_ldivmod_helper
+__gnu_uldivmod_helper
+__gnu_unwind_execute
+__gnu_unwind_frame
+__gtdf2
+__hostalias
+__init_tls
+__ioctl
+__ledf2
+__libc_android_log_assert
+__libc_android_log_print
+__libc_android_log_vprint
+__libc_fini
+__libc_init
+__libc_init_common
+__libc_preinit
+__llseek
+__loc_aton
+__loc_ntoa
+__ltdf2
+__memcmp16
+__mmap2
+__muldf3
+__muldi3
+__mulsf3
+__nedf2
+__ns_format_ttl
+__ns_get16
+__ns_get32
+__ns_initparse
+__ns_makecanon
+__ns_msg_getflag
+__ns_name_compress
+__ns_name_ntol
+__ns_name_ntop
+__ns_name_pack
+__ns_name_pton
+__ns_name_rollback
+__ns_name_skip
+__ns_name_uncompress
+__ns_name_unpack
+__ns_parserr
+__ns_put16
+__ns_put32
+__ns_samename
+__ns_skiprr
+__ns_sprintrr
+__ns_sprintrrf
+__open
+__openat
+__p_cdname
+__p_cdnname
+__p_class
+__p_fqname
+__p_fqnname
+__p_option
+__p_query
+__p_rcode
+__p_secstodate
+__p_section
+__p_sockun
+__p_time
+__p_type
+__popcountsi2
+__pthread_cleanup_pop
+__pthread_cleanup_push
+__pthread_clone
+__pthread_cond_timedwait
+__pthread_cond_timedwait_relative
+__ptrace
+__putlong
+__putshort
+__reboot
+__res_close
+__res_dnok
+__res_get_nibblesuffix
+__res_get_nibblesuffix2
+__res_get_state
+__res_get_static
+__res_getservers
+__res_hnok
+__res_hostalias
+__res_isourserver
+__res_mailok
+__res_nameinquery
+__res_nametoclass
+__res_nametotype
+__res_nclose
+__res_ndestroy
+__res_ninit
+__res_nmkquery
+__res_nopt
+__res_nquery
+__res_nquerydomain
+__res_nsearch
+__res_nsend
+__res_opt
+__res_ownok
+__res_pquery
+__res_put_state
+__res_queriesmatch
+__res_querydomain
+__res_randomid
+__res_send
+__res_send_setqhook
+__res_send_setrhook
+__res_setservers
+__res_vinit
+__restore_core_regs
+__rt_sigaction
+__rt_sigprocmask
+__rt_sigtimedwait
+__sched_cpualloc
+__sched_cpucount
+__sched_cpufree
+__sched_getaffinity
+__sclose
+__set_errno
+__set_tls
+__setresuid
+__setreuid
+__setuid
+__sflags
+__sflush
+__sfp
+__sigsuspend
+__sinit
+__smakebuf
+__sread
+__srefill
+__srget
+__sseek
+__stack_chk_fail
+__statfs64
+__subdf3
+__subsf3
+__swbuf
+__swhatbuf
+__swrite
+__swsetup
+__sym_ntop
+__sym_ntos
+__sym_ston
+__sys_clone
+__syslog
+__system_properties_init
+__system_property_find
+__system_property_find_nth
+__system_property_get
+__system_property_read
+__system_property_wait
+__thread_entry
+__timer_create
+__timer_delete
+__timer_getoverrun
+__timer_gettime
+__timer_settime
+__truncdfsf2
+__udivdi3
+__udivsi3
+__unorddf2
+__unordsf2
+__wait4
+__waitid
+_cleanup
+_exit
+_exit_thread
+_exit_with_stack_teardown
+_fwalk
+_getlong
+_getshort
+_init_thread
+_longjmp
+_setjmp
+_thread_created_hook
+abort
+accept
+access
+acct
+alarm
+alphasort
+arc4random
+arc4random_addrandom
+arc4random_buf
+arc4random_stir
+arc4random_uniform
+asctime
+asctime64
+asctime64_r
+asctime_r
+asprintf
+atexit
+atoi
+atol
+atoll
+basename
+basename_r
+bcopy
+bind
+bindresvport
+brk
+bsd_signal
+bsearch
+btowc
+bzero
+cacheflush
+calloc
+capget
+capset
+chdir
+chmod
+chown
+chroot
+clearenv
+clearerr
+clock
+clock_getres
+clock_gettime
+clock_nanosleep
+clock_settime
+clone
+close
+closedir
+closelog
+closelog_r
+connect
+cpuacct_add
+creat
+ctime
+ctime64
+ctime64_r
+ctime_r
+daemon
+delete_module
+difftime
+dirfd
+dirname
+dirname_r
+div
+dlcalloc
+dlfree
+dlindependent_calloc
+dlindependent_comalloc
+dlmallinfo
+dlmalloc
+dlmalloc_footprint
+dlmalloc_max_footprint
+dlmalloc_stats
+dlmalloc_trim
+dlmalloc_usable_size
+dlmalloc_walk_free_pages
+dlmalloc_walk_heap
+dlmallopt
+dlmemalign
+dlpvalloc
+dlrealloc
+dlvalloc
+dn_expand
+drand48
+dup
+dup2
+endpwent
+endservent
+endusershell
+endutent
+epoll_create
+epoll_ctl
+epoll_wait
+erand48
+err
+errx
+ether_aton
+ether_aton_r
+ether_ntoa
+ether_ntoa_r
+eventfd
+eventfd_read
+eventfd_write
+execl
+execle
+execlp
+execv
+execve
+execvp
+exit
+fchdir
+fchmod
+fchmodat
+fchown
+fchownat
+fclose
+fcntl
+fdatasync
+fdopen
+fdopendir
+fdprintf
+feof
+ferror
+fflush
+ffs
+fgetc
+fgetln
+fgetpos
+fgets
+fgetwc
+fgetws
+fileno
+flock
+flockfile
+fnmatch
+fopen
+fork
+fpathconf
+fprintf
+fpurge
+fputc
+fputs
+fputwc
+fputws
+fread
+free
+freeaddrinfo
+freedtoa
+freopen
+fscanf
+fseek
+fseeko
+fsetpos
+fstat
+fstatat
+fstatfs
+fsync
+ftell
+ftello
+ftime
+ftok
+ftruncate
+ftruncate64
+ftrylockfile
+fts_children
+fts_close
+fts_open
+fts_read
+fts_set
+funlockfile
+funopen
+futex
+fwide
+fwprintf
+fwrite
+fwscanf
+gai_strerror
+get_malloc_leak_info
+getaddrinfo
+getc
+getc_unlocked
+getchar
+getchar_unlocked
+getcwd
+getdents
+getdtablesize
+getegid
+getenv
+geteuid
+getgid
+getgrgid
+getgrnam
+getgrouplist
+getgroups
+gethostbyaddr
+gethostbyname
+gethostbyname2
+gethostbyname_r
+gethostent
+gethostname
+getitimer
+getlogin
+getmntent
+getnameinfo
+getnetbyaddr
+getnetbyname
+getopt
+getopt_long
+getopt_long_only
+getpeername
+getpgid
+getpgrp
+getpid
+getppid
+getpriority
+getprotobyname
+getprotobynumber
+getpt
+getpwnam
+getpwuid
+getresgid
+getresuid
+getrlimit
+getrusage
+gets
+getservbyname
+getservbyport
+getservent
+getservent_r
+getsockname
+getsockopt
+gettid
+gettimeofday
+getuid
+getusershell
+getutent
+getwc
+getwchar
+gmtime
+gmtime64
+gmtime64_r
+gmtime_r
+herror
+hstrerror
+if_indextoname
+if_nametoindex
+index
+inet_addr
+inet_aton
+inet_nsap_addr
+inet_nsap_ntoa
+inet_ntoa
+inet_ntop
+inet_pton
+init_module
+initgroups
+inotify_add_watch
+inotify_init
+inotify_rm_watch
+ioctl
+ioprio_get
+ioprio_set
+isalnum
+isalpha
+isascii
+isatty
+isblank
+iscntrl
+isdigit
+isgraph
+islower
+isprint
+ispunct
+issetugid
+isspace
+isupper
+iswalnum
+iswalpha
+iswcntrl
+iswctype
+iswdigit
+iswgraph
+iswlower
+iswprint
+iswpunct
+iswspace
+iswupper
+iswxdigit
+isxdigit
+jrand48
+kill
+killpg
+klogctl
+lchown
+ldexp
+ldiv
+link
+listen
+lldiv
+localtime
+localtime64
+localtime64_r
+localtime_r
+longjmp
+longjmperror
+lrand48
+lseek
+lseek64
+lstat
+madvise
+mallinfo
+malloc
+malloc_debug_init
+mbrlen
+mbrtowc
+mbsinit
+mbsrtowcs
+mbstowcs
+memalign
+memccpy
+memchr
+memcmp
+memcpy
+memmem
+memmove
+memrchr
+memset
+memswap
+mincore
+mkdir
+mkdirat
+mkdtemp
+mknod
+mkstemp
+mkstemps
+mktemp
+mktime
+mktime64
+mlock
+mmap
+mount
+mprotect
+mrand48
+mremap
+msync
+munlock
+munmap
+nanosleep
+nice
+nrand48
+nsdispatch
+open
+openat
+opendir
+openlog
+openlog_r
+pathconf
+pause
+pclose
+perror
+pipe
+pipe2
+poll
+popen
+posix2time
+prctl
+pread
+pread64
+printf
+pselect
+pthread_atfork
+pthread_attr_destroy
+pthread_attr_getdetachstate
+pthread_attr_getguardsize
+pthread_attr_getschedparam
+pthread_attr_getschedpolicy
+pthread_attr_getscope
+pthread_attr_getstack
+pthread_attr_getstackaddr
+pthread_attr_getstacksize
+pthread_attr_init
+pthread_attr_setdetachstate
+pthread_attr_setguardsize
+pthread_attr_setschedparam
+pthread_attr_setschedpolicy
+pthread_attr_setscope
+pthread_attr_setstack
+pthread_attr_setstackaddr
+pthread_attr_setstacksize
+pthread_cond_broadcast
+pthread_cond_destroy
+pthread_cond_init
+pthread_cond_signal
+pthread_cond_timedwait
+pthread_cond_timedwait_monotonic
+pthread_cond_timedwait_monotonic_np
+pthread_cond_timedwait_relative_np
+pthread_cond_timeout_np
+pthread_cond_wait
+pthread_condattr_destroy
+pthread_condattr_getpshared
+pthread_condattr_init
+pthread_condattr_setpshared
+pthread_create
+pthread_detach
+pthread_equal
+pthread_exit
+pthread_getattr_np
+pthread_getcpuclockid
+pthread_getschedparam
+pthread_getspecific
+pthread_join
+pthread_key_create
+pthread_key_delete
+pthread_kill
+pthread_mutex_destroy
+pthread_mutex_init
+pthread_mutex_lock
+pthread_mutex_lock_timeout_np
+pthread_mutex_trylock
+pthread_mutex_unlock
+pthread_mutexattr_destroy
+pthread_mutexattr_getpshared
+pthread_mutexattr_gettype
+pthread_mutexattr_init
+pthread_mutexattr_setpshared
+pthread_mutexattr_settype
+pthread_once
+pthread_rwlock_destroy
+pthread_rwlock_init
+pthread_rwlock_rdlock
+pthread_rwlock_timedrdlock
+pthread_rwlock_timedwrlock
+pthread_rwlock_tryrdlock
+pthread_rwlock_trywrlock
+pthread_rwlock_unlock
+pthread_rwlock_wrlock
+pthread_rwlockattr_destroy
+pthread_rwlockattr_getpshared
+pthread_rwlockattr_init
+pthread_rwlockattr_setpshared
+pthread_self
+pthread_setname_np
+pthread_setschedparam
+pthread_setspecific
+pthread_sigmask
+ptrace
+ptsname
+ptsname_r
+putc
+putc_unlocked
+putchar
+putchar_unlocked
+putenv
+puts
+pututline
+putw
+putwc
+putwchar
+pwrite
+pwrite64
+qsort
+raise
+read
+readdir
+readdir_r
+readlink
+readv
+realloc
+realpath
+reboot
+recv
+recvfrom
+recvmsg
+regcomp
+regerror
+regexec
+regfree
+remove
+rename
+renameat
+res_init
+res_mkquery
+res_query
+res_search
+restore_core_regs
+rewind
+rewinddir
+rmdir
+sbrk
+scandir
+scanf
+sched_get_priority_max
+sched_get_priority_min
+sched_getaffinity
+sched_getcpu
+sched_getparam
+sched_getscheduler
+sched_rr_get_interval
+sched_setaffinity
+sched_setparam
+sched_setscheduler
+sched_yield
+seed48
+select
+sem_close
+sem_destroy
+sem_getvalue
+sem_init
+sem_open
+sem_post
+sem_timedwait
+sem_trywait
+sem_unlink
+sem_wait
+send
+sendfile
+sendmsg
+sendto
+setbuf
+setbuffer
+setegid
+setenv
+seteuid
+setgid
+setgroups
+setitimer
+setjmp
+setlinebuf
+setlocale
+setlogmask
+setlogmask_r
+setpgid
+setpgrp
+setpriority
+setregid
+setresgid
+setresuid
+setreuid
+setrlimit
+setservent
+setsid
+setsockopt
+settimeofday
+setuid
+setusershell
+setutent
+setvbuf
+shutdown
+sigaction
+sigaltstack
+sigblock
+siginterrupt
+siglongjmp
+sigpending
+sigprocmask
+sigsetjmp
+sigsetmask
+sigsuspend
+sigwait
+sleep
+snprintf
+socket
+socketpair
+sprintf
+srand48
+sscanf
+stat
+statfs
+strcasecmp
+strcasestr
+strcat
+strchr
+strcmp
+strcoll
+strcpy
+strcspn
+strdup
+strerror
+strerror_r
+strftime
+strftime_tz
+strlcat
+strlcpy
+strlen
+strncasecmp
+strncat
+strncmp
+strncpy
+strndup
+strnlen
+strntoimax
+strntoumax
+strpbrk
+strptime
+strrchr
+strsep
+strsignal
+strspn
+strstr
+strtod
+strtoimax
+strtok
+strtok_r
+strtol
+strtoll
+strtotimeval
+strtoul
+strtoull
+strtoumax
+strxfrm
+swprintf
+swscanf
+symlink
+sync
+syscall
+sysconf
+sysinfo
+syslog
+syslog_r
+system
+sysv_signal
+tcgetpgrp
+tcsetpgrp
+tempnam
+time
+time2posix
+timegm
+timegm64
+timelocal
+timelocal64
+timer_create
+timer_delete
+timer_getoverrun
+timer_gettime
+timer_settime
+times
+tkill
+tmpfile
+tmpnam
+toascii
+tolower
+toupper
+towlower
+towupper
+truncate
+ttyname
+ttyname_r
+tzset
+umask
+umount
+umount2
+uname
+ungetc
+ungetwc
+unlink
+unlinkat
+unlockpt
+unsetenv
+usleep
+utime
+utimes
+utmpname
+valloc
+vasprintf
+verr
+verrx
+vfdprintf
+vfork
+vfprintf
+vfscanf
+vfwprintf
+vprintf
+vscanf
+vsnprintf
+vsprintf
+vsscanf
+vswprintf
+vsyslog
+vsyslog_r
+vwarn
+vwarnx
+vwprintf
+wait
+wait3
+waitid
+waitpid
+warn
+warnx
+wcpcpy
+wcpncpy
+wcrtomb
+wcscasecmp
+wcscat
+wcschr
+wcscmp
+wcscoll
+wcscpy
+wcscspn
+wcsdup
+wcsftime
+wcslcat
+wcslcpy
+wcslen
+wcsncasecmp
+wcsncat
+wcsncmp
+wcsncpy
+wcsnlen
+wcspbrk
+wcsrchr
+wcsrtombs
+wcsspn
+wcsstr
+wcstod
+wcstok
+wcstol
+wcstombs
+wcstoul
+wcswcs
+wcswidth
+wcsxfrm
+wctob
+wctype
+wcwidth
+wmemchr
+wmemcmp
+wmemcpy
+wmemmove
+wmemset
+wprintf
+write
+writev
+wscanf
diff --git a/ndk/platforms/android-11/arch-arm/symbols/libc.so.variables.txt b/ndk/platforms/android-11/arch-arm/symbols/libc.so.variables.txt
new file mode 100644
index 0000000..ccc33a8
--- /dev/null
+++ b/ndk/platforms/android-11/arch-arm/symbols/libc.so.variables.txt
@@ -0,0 +1,44 @@
+_C_ctype_
+_C_tolower_
+_C_toupper_
+__atexit
+__atexit_invalid
+__bionic_brk
+__evOptMonoTime
+__isthreaded
+__libc_malloc_default_dispatch
+__libc_malloc_dispatch
+__p_cert_syms
+__p_class_syms
+__p_key_syms
+__p_rcode_syms
+__p_type_syms
+__page_shift
+__page_size
+__popcount_tab
+__progname
+__rand48_add
+__rand48_mult
+__rand48_seed
+__sF
+__sdidinit
+__sglue
+__stack_chk_guard
+__system_property_area__
+_ctype_
+_ns_flagdata
+_tolower_tab_
+_toupper_tab_
+daylight
+environ
+h_errlist
+h_nerr
+optarg
+opterr
+optind
+optopt
+optreset
+sys_siglist
+sys_signame
+timezone
+tzname
diff --git a/ndk/platforms/android-11/arch-arm/symbols/libm.so.functions.txt b/ndk/platforms/android-11/arch-arm/symbols/libm.so.functions.txt
new file mode 100644
index 0000000..3911735
--- /dev/null
+++ b/ndk/platforms/android-11/arch-arm/symbols/libm.so.functions.txt
@@ -0,0 +1,211 @@
+__aeabi_cfcmpeq
+__aeabi_cfcmple
+__aeabi_cfrcmple
+__aeabi_d2lz
+__aeabi_d2uiz
+__aeabi_d2ulz
+__aeabi_f2lz
+__aeabi_f2ulz
+__aeabi_fcmpeq
+__aeabi_fcmpge
+__aeabi_fcmpgt
+__aeabi_fcmple
+__aeabi_fcmplt
+__cmpsf2
+__eqsf2
+__exp__D
+__fixdfdi
+__fixsfdi
+__fixunsdfdi
+__fixunsdfsi
+__fixunssfdi
+__fpclassifyd
+__fpclassifyf
+__fpclassifyl
+__gesf2
+__gtsf2
+__ieee754_rem_pio2
+__ieee754_rem_pio2f
+__isfinite
+__isfinitef
+__isfinitel
+__isinf
+__isinff
+__isinfl
+__isnanl
+__isnormal
+__isnormalf
+__isnormall
+__kernel_cos
+__kernel_cosdf
+__kernel_rem_pio2
+__kernel_sin
+__kernel_sindf
+__kernel_tan
+__kernel_tandf
+__lesf2
+__log__D
+__ltsf2
+__nesf2
+__signbit
+__signbitf
+__signbitl
+_scan_nan
+acos
+acosf
+acosh
+acoshf
+asin
+asinf
+asinh
+asinhf
+atan
+atan2
+atan2f
+atanf
+atanh
+atanhf
+cbrt
+cbrtf
+ceil
+ceilf
+ceill
+copysign
+copysignf
+copysignl
+cos
+cosf
+cosh
+coshf
+drem
+dremf
+erf
+erfc
+erfcf
+erff
+exp
+exp2
+exp2f
+expf
+expm1
+expm1f
+fabs
+fabsf
+fabsl
+fdim
+fdimf
+fdiml
+finite
+finitef
+floor
+floorf
+floorl
+fma
+fmaf
+fmax
+fmaxf
+fmaxl
+fmin
+fminf
+fminl
+fmod
+fmodf
+frexp
+frexpf
+gamma
+gamma_r
+gammaf
+gammaf_r
+hypot
+hypotf
+ilogb
+ilogbf
+ilogbl
+isnan
+isnanf
+j0
+j0f
+j1
+j1f
+jn
+jnf
+ldexp
+ldexpf
+ldexpl
+lgamma
+lgamma_r
+lgammaf
+lgammaf_r
+llrint
+llrintf
+llround
+llroundf
+llroundl
+log
+log10
+log10f
+log1p
+log1pf
+logb
+logbf
+logf
+lrint
+lrintf
+lround
+lroundf
+lroundl
+modf
+modff
+nan
+nanf
+nanl
+nearbyint
+nearbyintf
+nextafter
+nextafterf
+nexttowardf
+pow
+powf
+remainder
+remainderf
+remquo
+remquof
+rint
+rintf
+round
+roundf
+roundl
+scalb
+scalbf
+scalbln
+scalblnf
+scalblnl
+scalbn
+scalbnf
+scalbnl
+significand
+significandf
+sin
+sincos
+sincosf
+sincosl
+sinf
+sinh
+sinhf
+sqrt
+sqrtf
+tan
+tanf
+tanh
+tanhf
+tgamma
+tgammaf
+trunc
+truncf
+truncl
+y0
+y0f
+y1
+y1f
+yn
+ynf
diff --git a/ndk/platforms/android-11/arch-arm/symbols/libm.so.variables.txt b/ndk/platforms/android-11/arch-arm/symbols/libm.so.variables.txt
new file mode 100644
index 0000000..a1b63fc
--- /dev/null
+++ b/ndk/platforms/android-11/arch-arm/symbols/libm.so.variables.txt
@@ -0,0 +1,2 @@
+__fe_dfl_env
+signgam
diff --git a/ndk/platforms/android-11/include/pthread.h b/ndk/platforms/android-11/include/pthread.h
new file mode 100644
index 0000000..3b1cf58
--- /dev/null
+++ b/ndk/platforms/android-11/include/pthread.h
@@ -0,0 +1,316 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _PTHREAD_H_
+#define _PTHREAD_H_
+
+#include <time.h>
+#include <signal.h>
+#include <sched.h>
+#include <limits.h>
+#include <sys/types.h>
+
+/*
+ * Types
+ */
+typedef struct
+{
+    int volatile value;
+} pthread_mutex_t;
+
+#define  PTHREAD_MUTEX_INITIALIZER             {0}
+#define  PTHREAD_RECURSIVE_MUTEX_INITIALIZER   {0x4000}
+#define  PTHREAD_ERRORCHECK_MUTEX_INITIALIZER  {0x8000}
+
+enum {
+    PTHREAD_MUTEX_NORMAL = 0,
+    PTHREAD_MUTEX_RECURSIVE = 1,
+    PTHREAD_MUTEX_ERRORCHECK = 2,
+
+    PTHREAD_MUTEX_ERRORCHECK_NP = PTHREAD_MUTEX_ERRORCHECK,
+    PTHREAD_MUTEX_RECURSIVE_NP  = PTHREAD_MUTEX_RECURSIVE,
+
+    PTHREAD_MUTEX_DEFAULT = PTHREAD_MUTEX_NORMAL
+};
+
+
+
+typedef struct
+{
+    int volatile value;
+} pthread_cond_t;
+
+typedef struct
+{
+    uint32_t flags;
+    void * stack_base;
+    size_t stack_size;
+    size_t guard_size;
+    int32_t sched_policy;
+    int32_t sched_priority;
+} pthread_attr_t;
+
+typedef long pthread_mutexattr_t;
+typedef long pthread_condattr_t;
+
+typedef int pthread_key_t;
+typedef long pthread_t;
+
+typedef volatile int  pthread_once_t;
+
+/*
+ * Defines
+ */
+#define PTHREAD_COND_INITIALIZER  {0}
+
+#define PTHREAD_STACK_MIN (2 * PAGE_SIZE)
+
+#define PTHREAD_CREATE_DETACHED  0x00000001
+#define PTHREAD_CREATE_JOINABLE  0x00000000
+
+#define PTHREAD_ONCE_INIT    0
+
+#define PTHREAD_PROCESS_PRIVATE  0
+#define PTHREAD_PROCESS_SHARED   1
+
+#define PTHREAD_SCOPE_SYSTEM     0
+#define PTHREAD_SCOPE_PROCESS    1
+
+/*
+ * Prototypes
+ */
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int pthread_attr_init(pthread_attr_t * attr);
+int pthread_attr_destroy(pthread_attr_t * attr);
+
+int pthread_attr_setdetachstate(pthread_attr_t * attr, int state);
+int pthread_attr_getdetachstate(pthread_attr_t const * attr, int * state);
+
+int pthread_attr_setschedpolicy(pthread_attr_t * attr, int policy);
+int pthread_attr_getschedpolicy(pthread_attr_t const * attr, int * policy);
+
+int pthread_attr_setschedparam(pthread_attr_t * attr, struct sched_param const * param);
+int pthread_attr_getschedparam(pthread_attr_t const * attr, struct sched_param * param);
+
+int pthread_attr_setstacksize(pthread_attr_t * attr, size_t stack_size);
+int pthread_attr_getstacksize(pthread_attr_t const * attr, size_t * stack_size);
+
+int pthread_attr_setstackaddr(pthread_attr_t * attr, void * stackaddr);
+int pthread_attr_getstackaddr(pthread_attr_t const * attr, void ** stackaddr);
+
+int pthread_attr_setstack(pthread_attr_t * attr, void * stackaddr, size_t stack_size);
+int pthread_attr_getstack(pthread_attr_t const * attr, void ** stackaddr, size_t * stack_size);
+
+int pthread_attr_setguardsize(pthread_attr_t * attr, size_t guard_size);
+int pthread_attr_getguardsize(pthread_attr_t const * attr, size_t * guard_size);
+
+int pthread_attr_setscope(pthread_attr_t *attr, int  scope);
+int pthread_attr_getscope(pthread_attr_t const *attr);
+
+int pthread_getattr_np(pthread_t thid, pthread_attr_t * attr);
+
+int pthread_create(pthread_t *thread, pthread_attr_t const * attr,
+                   void *(*start_routine)(void *), void * arg);
+void pthread_exit(void * retval);
+int pthread_join(pthread_t thid, void ** ret_val);
+int pthread_detach(pthread_t  thid);
+
+pthread_t pthread_self(void);
+int pthread_equal(pthread_t one, pthread_t two);
+
+int pthread_getschedparam(pthread_t thid, int * policy,
+                          struct sched_param * param);
+int pthread_setschedparam(pthread_t thid, int poilcy,
+                          struct sched_param const * param);
+
+int pthread_mutexattr_init(pthread_mutexattr_t *attr);
+int pthread_mutexattr_destroy(pthread_mutexattr_t *attr);
+int pthread_mutexattr_gettype(const pthread_mutexattr_t *attr, int *type);
+int pthread_mutexattr_settype(pthread_mutexattr_t *attr, int type);
+int pthread_mutexattr_setpshared(pthread_mutexattr_t *attr, int  pshared);
+int pthread_mutexattr_getpshared(pthread_mutexattr_t *attr, int *pshared);
+
+int pthread_mutex_init(pthread_mutex_t *mutex,
+                       const pthread_mutexattr_t *attr);
+int pthread_mutex_destroy(pthread_mutex_t *mutex);
+int pthread_mutex_lock(pthread_mutex_t *mutex);
+int pthread_mutex_unlock(pthread_mutex_t *mutex);
+int pthread_mutex_trylock(pthread_mutex_t *mutex);
+#if 0 /* MISSING FROM BIONIC */
+int pthread_mutex_timedlock(pthread_mutex_t *mutex, struct timespec*  ts);
+#endif /* MISSING */
+
+int pthread_condattr_init(pthread_condattr_t *attr);
+int pthread_condattr_getpshared(pthread_condattr_t *attr, int *pshared);
+int pthread_condattr_setpshared(pthread_condattr_t* attr, int pshared);
+int pthread_condattr_destroy(pthread_condattr_t *attr);
+
+int pthread_cond_init(pthread_cond_t *cond,
+                      const pthread_condattr_t *attr);
+int pthread_cond_destroy(pthread_cond_t *cond);
+int pthread_cond_broadcast(pthread_cond_t *cond);
+int pthread_cond_signal(pthread_cond_t *cond);
+int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex);
+int pthread_cond_timedwait(pthread_cond_t *cond,
+                           pthread_mutex_t * mutex,
+                           const struct timespec *abstime);
+
+/* BIONIC: same as pthread_cond_timedwait, except the 'abstime' given refers
+ *         to the CLOCK_MONOTONIC clock instead, to avoid any problems when
+ *         the wall-clock time is changed brutally
+ */
+int pthread_cond_timedwait_monotonic_np(pthread_cond_t         *cond,
+                                        pthread_mutex_t        *mutex,
+                                        const struct timespec  *abstime);
+
+/* BIONIC: DEPRECATED. same as pthread_cond_timedwait_monotonic_np()
+ * unfortunately pthread_cond_timedwait_monotonic has shipped already
+ */
+int pthread_cond_timedwait_monotonic(pthread_cond_t         *cond,
+                                     pthread_mutex_t        *mutex,
+                                     const struct timespec  *abstime);
+
+#define HAVE_PTHREAD_COND_TIMEDWAIT_MONOTONIC 1
+
+/* BIONIC: same as pthread_cond_timedwait, except the 'reltime' given refers
+ *         is relative to the current time.
+ */
+int pthread_cond_timedwait_relative_np(pthread_cond_t         *cond,
+                                     pthread_mutex_t        *mutex,
+                                     const struct timespec  *reltime);
+
+#define HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE 1
+
+
+
+int pthread_cond_timeout_np(pthread_cond_t *cond,
+                            pthread_mutex_t * mutex,
+                            unsigned msecs);
+
+/* same as pthread_mutex_lock(), but will wait up to 'msecs' milli-seconds
+ * before returning. same return values than pthread_mutex_trylock though, i.e.
+ * returns EBUSY if the lock could not be acquired after the timeout
+ * expired.
+ */
+int pthread_mutex_lock_timeout_np(pthread_mutex_t *mutex, unsigned msecs);
+
+/* read-write lock support */
+
+typedef int pthread_rwlockattr_t;
+
+typedef struct {
+    pthread_mutex_t  lock;
+    pthread_cond_t   cond;
+    int              numLocks;
+    int              writerThreadId;
+    int              pendingReaders;
+    int              pendingWriters;
+    void*            reserved[4];  /* for future extensibility */
+} pthread_rwlock_t;
+
+#define PTHREAD_RWLOCK_INITIALIZER  { PTHREAD_MUTEX_INITIALIZER, PTHREAD_COND_INITIALIZER, 0, 0, 0, 0, { NULL, NULL, NULL, NULL } }
+
+int pthread_rwlockattr_init(pthread_rwlockattr_t *attr);
+int pthread_rwlockattr_destroy(pthread_rwlockattr_t *attr);
+int pthread_rwlockattr_setpshared(pthread_rwlockattr_t *attr, int  pshared);
+int pthread_rwlockattr_getpshared(pthread_rwlockattr_t *attr, int *pshared);
+
+int pthread_rwlock_init(pthread_rwlock_t *rwlock, const pthread_rwlockattr_t *attr);
+int pthread_rwlock_destroy(pthread_rwlock_t *rwlock);
+
+int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock);
+int pthread_rwlock_tryrdlock(pthread_rwlock_t *rwlock);
+int pthread_rwlock_timedrdlock(pthread_rwlock_t *rwlock, const struct timespec *abs_timeout);
+
+int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock);
+int pthread_rwlock_trywrlock(pthread_rwlock_t *rwlock);
+int pthread_rwlock_timedwrlock(pthread_rwlock_t *rwlock, const struct timespec *abs_timeout);
+
+int pthread_rwlock_unlock(pthread_rwlock_t *rwlock);
+
+
+int pthread_key_create(pthread_key_t *key, void (*destructor_function)(void *));
+int pthread_key_delete (pthread_key_t);
+int pthread_setspecific(pthread_key_t key, const void *value);
+void *pthread_getspecific(pthread_key_t key);
+
+int pthread_kill(pthread_t tid, int sig);
+int pthread_sigmask(int how, const sigset_t *set, sigset_t *oset);
+
+int pthread_getcpuclockid(pthread_t  tid, clockid_t  *clockid);
+
+int pthread_once(pthread_once_t  *once_control, void (*init_routine)(void));
+
+int pthread_setname_np(pthread_t thid, const char *thname);
+
+int pthread_atfork(void (*prepare)(void), void (*parent)(void), void(*child)(void));
+
+typedef void  (*__pthread_cleanup_func_t)(void*);
+
+typedef struct __pthread_cleanup_t {
+    struct __pthread_cleanup_t*   __cleanup_prev;
+    __pthread_cleanup_func_t      __cleanup_routine;
+    void*                         __cleanup_arg;
+} __pthread_cleanup_t;
+
+extern void  __pthread_cleanup_push(__pthread_cleanup_t*      c,
+                                    __pthread_cleanup_func_t  routine,
+                                    void*                     arg);
+
+extern void  __pthread_cleanup_pop(__pthread_cleanup_t*  c,
+                                   int                   execute);
+
+/* Believe or not, the definitions of pthread_cleanup_push and
+ * pthread_cleanup_pop below are correct. Posix states that these
+ * can be implemented as macros that might introduce opening and
+ * closing braces, and that using setjmp/longjmp/return/break/continue
+ * between them results in undefined behaviour.
+ *
+ * And indeed, GLibc and other C libraries use a similar definition
+ */
+#define  pthread_cleanup_push(routine, arg)                      \
+    do {                                                         \
+        __pthread_cleanup_t  __cleanup;                          \
+        __pthread_cleanup_push( &__cleanup, (routine), (arg) );  \
+
+#define  pthread_cleanup_pop(execute)                  \
+        __pthread_cleanup_pop( &__cleanup, (execute)); \
+    } while (0);
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+/************ TO FIX ************/
+
+#define LONG_LONG_MAX __LONG_LONG_MAX__
+#define LONG_LONG_MIN (-__LONG_LONG_MAX__ - 1)
+
+#endif /* _PTHREAD_H_ */
diff --git a/ndk/platforms/android-11/include/sched.h b/ndk/platforms/android-11/include/sched.h
new file mode 100644
index 0000000..ca72da7
--- /dev/null
+++ b/ndk/platforms/android-11/include/sched.h
@@ -0,0 +1,234 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _SCHED_H_
+#define _SCHED_H_
+
+#include <sys/cdefs.h>
+#include <sys/time.h>
+
+__BEGIN_DECLS
+
+#define SCHED_NORMAL            0
+#define SCHED_OTHER             0
+#define SCHED_FIFO              1
+#define SCHED_RR                2
+
+struct sched_param {
+    int sched_priority;
+};
+
+extern int sched_setscheduler(pid_t, int, const struct sched_param *);
+extern int sched_getscheduler(pid_t);
+extern int sched_yield(void);
+extern int sched_get_priority_max(int policy);
+extern int sched_get_priority_min(int policy);
+extern int sched_setparam(pid_t, const struct sched_param *);
+extern int sched_getparam(pid_t, struct sched_param *);
+extern int sched_rr_get_interval(pid_t pid, struct timespec *tp);
+
+#define CLONE_VM             0x00000100
+#define CLONE_FS             0x00000200
+#define CLONE_FILES          0x00000400
+#define CLONE_SIGHAND        0x00000800
+#define CLONE_PTRACE         0x00002000
+#define CLONE_VFORK          0x00004000
+#define CLONE_PARENT         0x00008000
+#define CLONE_THREAD         0x00010000
+#define CLONE_NEWNS          0x00020000
+#define CLONE_SYSVSEM        0x00040000
+#define CLONE_SETTLS         0x00080000
+#define CLONE_PARENT_SETTID  0x00100000
+#define CLONE_CHILD_CLEARTID 0x00200000
+#define CLONE_DETACHED       0x00400000
+#define CLONE_UNTRACED       0x00800000
+#define CLONE_CHILD_SETTID   0x01000000
+#define CLONE_STOPPED        0x02000000
+
+#ifdef _GNU_SOURCE
+extern int clone(int (*fn)(void *), void *child_stack, int flags, void*  arg, ...);
+#endif
+
+/* Support for cpu thread affinity */
+#ifdef _GNU_SOURCE
+
+extern int sched_getcpu(void);
+
+
+/* Our implementation supports up to 32 independent CPUs, which is also
+ * the maximum supported by the kernel at the moment. GLibc uses 1024 by
+ * default.
+ *
+ * If you want to use more than that, you should use CPU_ALLOC() / CPU_FREE()
+ * and the CPU_XXX_S() macro variants.
+ */
+#define CPU_SETSIZE   32
+
+#define __CPU_BITTYPE    unsigned long int  /* mandated by the kernel  */
+#define __CPU_BITSHIFT   5                  /* should be log2(BITTYPE) */
+#define __CPU_BITS       (1 << __CPU_BITSHIFT)
+#define __CPU_ELT(x)     ((x) >> __CPU_BITSHIFT)
+#define __CPU_MASK(x)    ((__CPU_BITTYPE)1 << ((x) & (__CPU_BITS-1)))
+
+typedef struct {
+    __CPU_BITTYPE  __bits[ CPU_SETSIZE / __CPU_BITS ];
+} cpu_set_t;
+
+extern int sched_setaffinity(pid_t pid, size_t setsize, const cpu_set_t* set);
+
+extern int sched_getaffinity(pid_t pid, size_t setsize, cpu_set_t* set);
+
+/* Provide optimized implementation for 32-bit cpu_set_t */
+#if CPU_SETSIZE == __CPU_BITS
+
+#  define CPU_ZERO(set_)   \
+    do{ \
+        (set_)->__bits[0] = 0; \
+    }while(0)
+
+#  define CPU_SET(cpu_,set_) \
+    do {\
+        size_t __cpu = (cpu_); \
+        if (__cpu < CPU_SETSIZE) \
+            (set_)->__bits[0] |= __CPU_MASK(__cpu); \
+    }while (0)
+
+#  define CPU_CLR(cpu_,set_) \
+    do {\
+        size_t __cpu = (cpu_); \
+        if (__cpu < CPU_SETSIZE) \
+            (set_)->__bits[0] &= ~__CPU_MASK(__cpu); \
+    }while (0)
+
+#  define CPU_ISSET(cpu_, set_) \
+    (__extension__({\
+        size_t  __cpu = (cpu_); \
+        (cpu_ < CPU_SETSIZE) \
+            ? ((set_)->__bits[0] & __CPU_MASK(__cpu)) != 0 \
+            : 0; \
+    }))
+
+#  define CPU_EQUAL(set1_, set2_) \
+    ((set1_)->__bits[0] == (set2_)->__bits[0])
+
+#  define __CPU_OP(dst_, set1_, set2_, op_) \
+    do { \
+        (dst_)->__bits[0] = (set1_)->__bits[0] op_ (set2_)->__bits[0]; \
+    } while (0)
+
+#  define CPU_COUNT(set_)  __builtin_popcountl((set_)->__bits[0])
+
+#else /* CPU_SETSIZE != __CPU_BITS */
+
+#  define CPU_ZERO(set_)          CPU_ZERO_S(sizeof(cpu_set_t), set_)
+#  define CPU_SET(cpu_,set_)      CPU_SET_S(cpu_,sizeof(cpu_set_t),set_)
+#  define CPU_CLR(cpu_,set_)      CPU_CLR_S(cpu_,sizeof(cpu_set_t),set_)
+#  define CPU_ISSET(cpu_,set_)    CPU_ISSET_S(cpu_,sizeof(cpu_set_t),set_)
+#  define CPU_COUNT(set_)         CPU_COUNT_S(sizeof(cpu_set_t),set_)
+#  define CPU_EQUAL(set1_,set2_)  CPU_EQUAL_S(sizeof(cpu_set_t),set1_,set2_)
+
+#  define __CPU_OP(dst_,set1_,set2_,op_)  __CPU_OP_S(sizeof(cpu_set_t),dst_,set1_,set2_,op_)
+
+#endif /* CPU_SETSIZE != __CPU_BITS */
+
+#define CPU_AND(set1_,set2_)   __CPU_OP(set1_,set2_,&)
+#define CPU_OR(set1_,set2_)    __CPU_OP(set1_,set2_,|)
+#define CPU_XOR(set1_,set2_)   __CPU_OP(set1_,set2_,^)
+
+/* Support for dynamically-allocated cpu_set_t */
+
+#define CPU_ALLOC_SIZE(count) \
+    __CPU_ELT((count) + (__CPU_BITS-1))*sizeof(__CPU_BITTYPE)
+
+#define CPU_ALLOC(count)   __sched_cpualloc((count));
+#define CPU_FREE(set)      __sched_cpufree((set))
+
+extern cpu_set_t* __sched_cpualloc(size_t count);
+extern void       __sched_cpufree(cpu_set_t* set);
+
+#define CPU_ZERO_S(setsize_,set_)  \
+    do { \
+        size_t __nn = 0; \
+        size_t __nn_max = (setsize_)/sizeof(__CPU_BITTYPE); \
+        for (; __nn < __nn_max; __nn++) \
+            (set_)->__bits[__nn] = 0; \
+    } while (0)
+
+#define CPU_SET_S(cpu_,setsize_,set_) \
+    do { \
+        size_t __cpu = (cpu_); \
+        if (__cpu < 8*(setsize_)) \
+            (set_)->__bits[__CPU_ELT(__cpu)] |= __CPU_MASK(__cpu); \
+    } while (0)
+
+#define CPU_CLR_S(cpu_,setsize_,set_) \
+    do { \
+        size_t __cpu = (cpu_); \
+        if (__cpu < 8*(setsize_)) \
+            (set_)->__bits[__CPU_ELT(__cpu)] &= ~__CPU_MASK(__cpu); \
+    } while (0)
+
+#define CPU_ISSET_S(cpu_, setsize_, set_) \
+    (__extension__ ({ \
+        size_t __cpu = (cpu_); \
+        (__cpu < 8*(setsize_)) \
+          ? ((set_)->__bits[__CPU_ELT(__cpu)] & __CPU_MASK(__cpu)) != 0 \
+          : 0; \
+    }))
+
+#define CPU_EQUAL_S(setsize_, set1_, set2_) \
+    (__extension__ ({ \
+        __const __CPU_BITTYPE* __src1 = (set1_)->__bits; \
+        __const __CPU_BITTYPE* __src2 = (set2_)->__bits; \
+        size_t __nn = 0, __nn_max = (setsize_)/sizeof(__CPU_BITTYPE); \
+        for (; __nn < __nn_max; __nn++) { \
+            if (__src1[__nn] != __src2[__nn]) \
+                break; \
+        } \
+        __nn == __nn_max; \
+    }))
+
+#define __CPU_OP_S(setsize_, dstset_, srcset1_, srcset2_, op) \
+    do { \
+        cpu_set_t* __dst = (dstset); \
+        const __CPU_BITTYPE* __src1 = (srcset1)->__bits; \
+        const __CPU_BITTYPE* __src2 = (srcset2)->__bits; \
+        size_t __nn = 0, __nn_max = (setsize_)/sizeof(__CPU_BITTYPE); \
+        for (; __nn < __nn_max; __nn++) \
+            (__dst)->__bits[__nn] = __src1[__nn] op __src2[__nn]; \
+    } while (0)
+
+#define CPU_COUNT_S(setsize_, set_) \
+    __sched_cpucount((setsize_), (set_))
+
+extern int __sched_cpucount(size_t setsize, cpu_set_t* set);
+
+#endif /* _GNU_SOURCE */
+
+__END_DECLS
+
+#endif /* _SCHED_H_ */
diff --git a/ndk/platforms/android-11/include/stdlib.h b/ndk/platforms/android-11/include/stdlib.h
new file mode 100644
index 0000000..5dc8a87
--- /dev/null
+++ b/ndk/platforms/android-11/include/stdlib.h
@@ -0,0 +1,186 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _STDLIB_H_
+#define _STDLIB_H_
+
+#include <sys/cdefs.h>
+
+/* wchar_t is required in stdlib.h according to POSIX.
+ * note that defining __need_wchar_t prevents stddef.h
+ * to define all other symbols it does normally */
+#define __need_wchar_t
+#include <stddef.h>
+
+#include <stddef.h>
+#include <string.h>
+#include <alloca.h>
+#include <strings.h>
+#include <memory.h>
+
+__BEGIN_DECLS
+
+#define EXIT_FAILURE 1
+#define EXIT_SUCCESS 0
+
+extern __noreturn void exit(int);
+extern __noreturn void abort(void);
+extern int atexit(void (*)(void));
+
+extern char *getenv(const char *);
+extern int putenv(const char *);
+extern int setenv(const char *, const char *, int);
+extern int unsetenv(const char *);
+extern int clearenv(void);
+
+extern char *mkdtemp(char *);
+extern char *mktemp (char *);
+extern int mkstemp (char *);
+
+extern long strtol(const char *, char **, int);
+extern long long strtoll(const char *, char **, int);
+extern unsigned long strtoul(const char *, char **, int);
+extern unsigned long long strtoull(const char *, char **, int);
+extern double strtod(const char *nptr, char **endptr);
+
+static __inline__ float strtof(const char *nptr, char **endptr)
+{
+    return (float)strtod(nptr, endptr);
+}
+
+extern int atoi(const char *);
+extern long atol(const char *);
+extern long long atoll(const char *);
+
+static __inline__ double atof(const char *nptr)
+{
+    return (strtod(nptr, NULL));
+}
+
+static __inline__ int abs(int __n) {
+    return (__n < 0) ? -__n : __n;
+}
+
+static __inline__ long labs(long __n) {
+    return (__n < 0L) ? -__n : __n;
+}
+
+static __inline__ long long llabs(long long __n) {
+    return (__n < 0LL) ? -__n : __n;
+}
+
+extern char * realpath(const char *path, char *resolved);
+extern int system(const char * string);
+
+extern void * bsearch(const void *key, const void *base0,
+	size_t nmemb, size_t size,
+	int (*compar)(const void *, const void *));
+
+extern void qsort(void *, size_t, size_t, int (*)(const void *, const void *));
+
+extern long jrand48(unsigned short *);
+extern long mrand48(void);
+extern long nrand48(unsigned short *);
+extern long lrand48(void);
+extern unsigned short *seed48(unsigned short*);
+extern double erand48(unsigned short xsubi[3]);
+extern double drand48(void);
+extern void srand48(long);
+extern unsigned int arc4random(void);
+extern void arc4random_stir(void);
+extern void arc4random_addrandom(unsigned char *, int);
+
+#define RAND_MAX 0x7fffffff
+static __inline__ int rand(void) {
+    return (int)lrand48();
+}
+static __inline__ void srand(unsigned int __s) {
+    srand48(__s);
+}
+static __inline__ long random(void)
+{
+    return lrand48();
+}
+static __inline__ void srandom(unsigned int __s)
+{
+    srand48(__s);
+}
+
+/* Basic PTY functions.  These only work if devpts is mounted! */
+
+extern int    unlockpt(int);
+extern char*  ptsname(int);
+extern int    ptsname_r(int, char*, size_t);
+extern int    getpt(void);
+
+static __inline__ int grantpt(int __fd __attribute((unused)))
+{
+  (void)__fd;
+  return 0;     /* devpts does this all for us! */
+}
+
+typedef struct {
+    int  quot;
+    int  rem;
+} div_t;
+
+extern div_t   div(int, int);
+
+typedef struct {
+    long int  quot;
+    long int  rem;
+} ldiv_t;
+
+extern ldiv_t   ldiv(long, long);
+
+typedef struct {
+    long long int  quot;
+    long long int  rem;
+} lldiv_t;
+
+extern lldiv_t   lldiv(long long, long long);
+
+#if 1 /* MISSING FROM BIONIC - ENABLED FOR STLPort and libstdc++-v3 */
+/* make STLPort happy */
+extern int      mblen(const char *, size_t);
+extern size_t   mbstowcs(wchar_t *, const char *, size_t);
+extern int      mbtowc(wchar_t *, const char *, size_t);
+
+/* Likewise, make libstdc++-v3 happy.  */
+extern int	wctomb(char *, wchar_t);
+extern size_t	wcstombs(char *, const wchar_t *, size_t);
+#endif /* MISSING */
+
+#define MB_CUR_MAX 1
+
+#if 0 /* MISSING FROM BIONIC */
+extern int on_exit(void (*)(int, void *), void *);
+#endif /* MISSING */
+
+__END_DECLS
+
+#endif /* _STDLIB_H_ */
diff --git a/ndk/platforms/android-11/include/time.h b/ndk/platforms/android-11/include/time.h
new file mode 100644
index 0000000..8867b32
--- /dev/null
+++ b/ndk/platforms/android-11/include/time.h
@@ -0,0 +1,120 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _TIME_H_
+#define _TIME_H_
+
+#include <sys/cdefs.h>
+#include <sys/time.h>
+
+#define __ARCH_SI_UID_T __kernel_uid32_t
+#include <asm/siginfo.h>
+#undef __ARCH_SI_UID_T
+
+__BEGIN_DECLS
+
+extern time_t   time(time_t *);
+extern int      nanosleep(const struct timespec *, struct timespec *);
+
+extern char *strtotimeval(const char *str, struct timeval *tv);
+
+struct tm {
+   int     tm_sec;         /* seconds */
+   int     tm_min;         /* minutes */
+   int     tm_hour;        /* hours */
+   int     tm_mday;        /* day of the month */
+   int     tm_mon;         /* month */
+   int     tm_year;        /* year */
+   int     tm_wday;        /* day of the week */
+   int     tm_yday;        /* day in the year */
+   int     tm_isdst;       /* daylight saving time */
+
+   long int tm_gmtoff;     /* Seconds east of UTC.  */
+   const char *tm_zone;    /* Timezone abbreviation.  */
+
+};
+
+/* defining TM_ZONE indicates that we have a "timezone abbreviation" field in
+ * struct tm, the value should be the field name
+ */
+#define   TM_ZONE   tm_zone
+
+extern char* asctime(const struct tm* a);
+extern char* asctime_r(const struct tm* a, char* buf);
+
+/* Return the difference between TIME1 and TIME0.  */
+extern double difftime (time_t __time1, time_t __time0);
+extern time_t mktime (struct tm *a);
+
+extern struct tm*  localtime(const time_t *t);
+extern struct tm*  localtime_r(const time_t *timep, struct tm *result);
+
+extern struct tm*  gmtime(const time_t *timep);
+extern struct tm*  gmtime_r(const time_t *timep, struct tm *result);
+
+extern char*       strptime(const char *buf, const char *fmt, struct tm *tm);
+extern size_t      strftime(char *s, size_t max, const char *format, const struct tm *tm);
+
+extern char *ctime(const time_t *timep);
+extern char *ctime_r(const time_t *timep, char *buf);
+
+extern void  tzset(void);
+
+/* global includes */
+extern char*     tzname[];
+extern int       daylight;
+extern long int  timezone;
+
+#define CLOCKS_PER_SEC     1000000
+
+extern clock_t   clock(void);
+
+/* BIONIC: extra linux clock goodies */
+extern int clock_getres(int, struct timespec *);
+extern int clock_gettime(int, struct timespec *);
+
+#define CLOCK_REALTIME             0
+#define CLOCK_MONOTONIC            1
+#define CLOCK_PROCESS_CPUTIME_ID   2
+#define CLOCK_THREAD_CPUTIME_ID    3
+#define CLOCK_REALTIME_HR          4
+#define CLOCK_MONOTONIC_HR         5
+
+extern int  timer_create(int, struct sigevent*, timer_t*);
+extern int  timer_delete(timer_t);
+extern int  timer_settime(timer_t timerid, int flags, const struct itimerspec *value, struct itimerspec *ovalue);
+extern int  timer_gettime(timer_t timerid, struct itimerspec *value);
+extern int  timer_getoverrun(timer_t  timerid);
+
+extern time_t timelocal(struct tm *tm);
+extern time_t timegm(struct tm* tm);
+extern time_t time2posix(time_t ti);
+extern time_t posix2time(time_t ti);
+
+__END_DECLS
+
+#endif /* _TIME_H_ */
diff --git a/ndk/platforms/android-11/include/unistd.h b/ndk/platforms/android-11/include/unistd.h
new file mode 100644
index 0000000..d92549f
--- /dev/null
+++ b/ndk/platforms/android-11/include/unistd.h
@@ -0,0 +1,215 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _UNISTD_H_
+#define _UNISTD_H_
+
+#include <stddef.h>
+#include <sys/cdefs.h>
+#include <sys/types.h>
+#include <sys/select.h>
+#include <sys/sysconf.h>
+#include <linux/capability.h>
+#include <pathconf.h>
+
+__BEGIN_DECLS
+
+/* Standard file descriptor numbers. */
+#define STDIN_FILENO	0
+#define STDOUT_FILENO	1
+#define STDERR_FILENO	2
+
+/* Values for whence in fseek and lseek */
+#define SEEK_SET 0
+#define SEEK_CUR 1
+#define SEEK_END 2
+
+extern char **environ;
+extern __noreturn void _exit(int);
+
+extern pid_t  fork(void);
+extern pid_t  vfork(void);
+extern pid_t  getpid(void);
+extern pid_t  gettid(void);
+extern pid_t  getpgid(pid_t);
+extern int    setpgid(pid_t, pid_t);
+extern pid_t  getppid(void);
+extern pid_t  getpgrp(void);
+extern int    setpgrp(void);
+extern pid_t  setsid(void);
+
+extern int execv(const char *, char * const *);
+extern int execvp(const char *, char * const *);
+extern int execve(const char *, char * const *, char * const *);
+extern int execl(const char *, const char *, ...);
+extern int execlp(const char *, const char *, ...);
+extern int execle(const char *, const char *, ...);
+extern int capget(cap_user_header_t hdrp, cap_user_data_t datap);
+extern int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
+
+/* IMPORTANT: See comment under <sys/prctl.h> about this declaration */
+extern int prctl(int  option, ...);
+
+extern int nice(int);
+
+extern int setuid(uid_t);
+extern uid_t getuid(void);
+extern int seteuid(uid_t);
+extern uid_t geteuid(void);
+extern int setgid(gid_t);
+extern gid_t getgid(void);
+extern int setegid(gid_t);
+extern gid_t getegid(void);
+extern int getgroups(int, gid_t *);
+extern int setgroups(size_t, const gid_t *);
+extern int setreuid(uid_t, uid_t);
+extern int setregid(gid_t, gid_t);
+extern int setresuid(uid_t, uid_t, uid_t);
+extern int setresgid(gid_t, gid_t, gid_t);
+extern int getresuid(uid_t *ruid, uid_t *euid, uid_t *suid);
+extern int getresgid(gid_t *rgid, gid_t *egid, gid_t *sgid);
+extern int issetugid(void);
+extern char* getlogin(void);
+extern char* getusershell(void);
+extern void setusershell(void);
+extern void endusershell(void);
+
+
+
+/* Macros for access() */
+#define R_OK  4  /* Read */
+#define W_OK  2  /* Write */
+#define X_OK  1  /* Execute */
+#define F_OK  0  /* Existence */
+
+extern int access(const char *, int);
+extern int link(const char *, const char *);
+extern int unlink(const char *);
+extern int chdir(const char *);
+extern int fchdir(int);
+extern int rmdir(const char *);
+extern int pipe(int *);
+#ifdef _GNU_SOURCE  /* GLibc compatibility */
+extern int pipe2(int *, int);
+#endif
+extern int chroot(const char *);
+extern int symlink(const char *, const char *);
+extern int readlink(const char *, char *, size_t);
+extern int chown(const char *, uid_t, gid_t);
+extern int fchown(int, uid_t, gid_t);
+extern int lchown(const char *, uid_t, gid_t);
+extern int truncate(const char *, off_t);
+extern char *getcwd(char *, size_t);
+
+extern int sync(void);
+
+extern int close(int);
+extern off_t lseek(int, off_t, int);
+extern off64_t lseek64(int, off64_t, int);
+
+extern ssize_t read(int, void *, size_t);
+extern ssize_t write(int, const void *, size_t);
+extern ssize_t pread(int, void *, size_t, off_t);
+extern ssize_t pread64(int, void *, size_t, off64_t);
+extern ssize_t pwrite(int, const void *, size_t, off_t);
+extern ssize_t pwrite64(int, const void *, size_t, off64_t);
+
+extern int dup(int);
+extern int dup2(int, int);
+extern int fcntl(int, int, ...);
+extern int ioctl(int, int, ...);
+extern int flock(int, int);
+extern int fsync(int);
+extern int fdatasync(int);
+extern int ftruncate(int, off_t);
+extern int ftruncate64(int, off64_t);
+
+extern int pause(void);
+extern unsigned int alarm(unsigned int);
+extern unsigned int sleep(unsigned int);
+extern int usleep(unsigned long);
+
+extern int gethostname(char *, size_t);
+
+extern int getdtablesize(void);
+
+extern void *__brk(void *);
+extern int brk(void *);
+extern void *sbrk(ptrdiff_t);
+
+extern int getopt(int, char * const *, const char *);
+extern char *optarg;
+extern int optind, opterr, optopt;
+
+extern int isatty(int);
+extern char* ttyname(int);
+extern int ttyname_r(int, char*, size_t);
+
+extern int  acct(const char*  filepath);
+
+static __inline__ int getpagesize(void) {
+  extern unsigned int __page_size;
+  return __page_size;
+}
+static __inline__ int __getpageshift(void) {
+  extern unsigned int __page_shift;
+  return __page_shift;
+}
+
+extern int sysconf(int  name);
+
+extern int daemon(int, int);
+
+/* A special syscall that is only available on the ARM, not x86 function. */
+extern int cacheflush(long start, long end, long flags);
+
+extern pid_t tcgetpgrp(int fd);
+extern int   tcsetpgrp(int fd, pid_t _pid);
+
+#if 0 /* MISSING FROM BIONIC */
+extern pid_t  getsid(pid_t);
+extern int execvpe(const char *, char * const *, char * const *);
+extern int execlpe(const char *, const char *, ...);
+extern int getfsuid(uid_t);
+extern int setfsuid(uid_t);
+extern int getlogin_r(char* name, size_t namesize);
+extern int sethostname(const char *, size_t);
+extern int getdomainname(char *, size_t);
+extern int setdomainname(const char *, size_t);
+#endif /* MISSING */
+
+/* Used to retry syscalls that can return EINTR. */
+#define TEMP_FAILURE_RETRY(exp) ({         \
+    typeof (exp) _rc;                      \
+    do {                                   \
+        _rc = (exp);                       \
+    } while (_rc == -1 && errno == EINTR); \
+    _rc; })
+
+__END_DECLS
+
+#endif /* _UNISTD_H_ */
diff --git a/ndk/platforms/android-11/include/wchar.h b/ndk/platforms/android-11/include/wchar.h
new file mode 100644
index 0000000..1361ff5
--- /dev/null
+++ b/ndk/platforms/android-11/include/wchar.h
@@ -0,0 +1,159 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _WCHAR_H_
+#define _WCHAR_H_
+
+#include <sys/cdefs.h>
+#include <stdio.h>
+
+/* wchar_t is required in stdlib.h according to POSIX */
+#define __need___wchar_t
+#include <stddef.h>
+
+#include <stdarg.h>
+#include <time.h>
+#include <malloc.h>
+
+#include <stddef.h>
+
+/* IMPORTANT: Any code that relies on wide character support is essentially
+ *            non-portable and/or broken. the only reason this header exist
+ *            is because I'm really a nice guy. However, I'm not nice enough
+ *            to provide you with a real implementation. instead wchar_t == char
+ *            and all wc functions are stubs to their "normal" equivalent...
+ */
+
+__BEGIN_DECLS
+
+typedef int                     wint_t;
+typedef struct { int  dummy; }  mbstate_t;
+
+typedef enum {
+    WC_TYPE_INVALID = 0,
+    WC_TYPE_ALNUM,
+    WC_TYPE_ALPHA,
+    WC_TYPE_BLANK,
+    WC_TYPE_CNTRL,
+    WC_TYPE_DIGIT,
+    WC_TYPE_GRAPH,
+    WC_TYPE_LOWER,
+    WC_TYPE_PRINT,
+    WC_TYPE_PUNCT,
+    WC_TYPE_SPACE,
+    WC_TYPE_UPPER,
+    WC_TYPE_XDIGIT,
+    WC_TYPE_MAX
+} wctype_t;
+
+#define  WCHAR_MAX   INT_MAX
+#define  WCHAR_MIN   INT_MIN
+#define  WEOF        ((wint_t)(-1))
+
+extern wint_t            btowc(int);
+extern int               fwprintf(FILE *, const wchar_t *, ...);
+extern int               fwscanf(FILE *, const wchar_t *, ...);
+extern int               iswalnum(wint_t);
+extern int               iswalpha(wint_t);
+extern int               iswcntrl(wint_t);
+extern int               iswdigit(wint_t);
+extern int               iswgraph(wint_t);
+extern int               iswlower(wint_t);
+extern int               iswprint(wint_t);
+extern int               iswpunct(wint_t);
+extern int               iswspace(wint_t);
+extern int               iswupper(wint_t);
+extern int               iswxdigit(wint_t);
+extern int               iswctype(wint_t, wctype_t);
+extern wint_t            fgetwc(FILE *);
+extern wchar_t          *fgetws(wchar_t *, int, FILE *);
+extern wint_t            fputwc(wchar_t, FILE *);
+extern int               fputws(const wchar_t *, FILE *);
+extern int               fwide(FILE *, int);
+extern wint_t            getwc(FILE *);
+extern wint_t            getwchar(void);
+extern int               mbsinit(const mbstate_t *);
+extern size_t            mbrlen(const char *, size_t, mbstate_t *);
+extern size_t            mbrtowc(wchar_t *, const char *, size_t, mbstate_t *);
+extern size_t            mbsrtowcs(wchar_t *, const char **, size_t, mbstate_t *);
+extern size_t            mbstowcs(wchar_t *, const char *, size_t);
+extern wint_t            putwc(wchar_t, FILE *);
+extern wint_t            putwchar(wchar_t);
+extern int               swprintf(wchar_t *, size_t, const wchar_t *, ...);
+extern int               swscanf(const wchar_t *, const wchar_t *, ...);
+extern wint_t            towlower(wint_t);
+extern wint_t            towupper(wint_t);
+extern wint_t            ungetwc(wint_t, FILE *);
+extern int               vfwprintf(FILE *, const wchar_t *, va_list);
+extern int               vwprintf(const wchar_t *, va_list);
+extern int               vswprintf(wchar_t *, size_t, const wchar_t *, va_list);
+extern size_t            wcrtomb(char *, wchar_t, mbstate_t *);
+extern int               wcscasecmp(const wchar_t *, const wchar_t *);
+extern wchar_t          *wcscat(wchar_t *, const wchar_t *);
+extern wchar_t          *wcschr(const wchar_t *, wchar_t);
+extern int               wcscmp(const wchar_t *, const wchar_t *);
+extern int               wcscoll(const wchar_t *, const wchar_t *);
+extern wchar_t          *wcscpy(wchar_t *, const wchar_t *);
+extern size_t            wcscspn(const wchar_t *, const wchar_t *);
+extern size_t            wcsftime(wchar_t *, size_t, const wchar_t *, const struct tm *);
+extern size_t            wcslen(const wchar_t *);
+extern int               wcsncasecmp(const wchar_t *, const wchar_t *, size_t);
+extern wchar_t          *wcsncat(wchar_t *, const wchar_t *, size_t);
+extern int               wcsncmp(const wchar_t *, const wchar_t *, size_t);
+extern wchar_t          *wcsncpy(wchar_t *, const wchar_t *, size_t);
+extern wchar_t          *wcspbrk(const wchar_t *, const wchar_t *);
+extern wchar_t          *wcsrchr(const wchar_t *, wchar_t);
+extern size_t            wcsrtombs(char *, const wchar_t **, size_t, mbstate_t *);
+extern size_t            wcsspn(const wchar_t *, const wchar_t *);
+extern wchar_t          *wcsstr(const wchar_t *, const wchar_t *);
+extern double            wcstod(const wchar_t *, wchar_t **);
+extern wchar_t          *wcstok(wchar_t *, const wchar_t *, wchar_t **);
+extern long int          wcstol(const wchar_t *, wchar_t **, int);
+extern size_t            wcstombs(char *, const wchar_t *, size_t);
+extern unsigned long int wcstoul(const wchar_t *, wchar_t **, int);
+extern wchar_t          *wcswcs(const wchar_t *, const wchar_t *);
+extern int               wcswidth(const wchar_t *, size_t);
+extern size_t            wcsxfrm(wchar_t *, const wchar_t *, size_t);
+extern int               wctob(wint_t);
+extern wctype_t          wctype(const char *);
+extern int               wcwidth(wchar_t);
+extern wchar_t          *wmemchr(const wchar_t *, wchar_t, size_t);
+extern int               wmemcmp(const wchar_t *, const wchar_t *, size_t);
+extern wchar_t          *wmemcpy(wchar_t *, const wchar_t *, size_t);
+extern wchar_t          *wmemmove(wchar_t *, const wchar_t *, size_t);
+extern wchar_t          *wmemset(wchar_t *, wchar_t, size_t);
+extern int               wprintf(const wchar_t *, ...);
+extern int               wscanf(const wchar_t *, ...);
+
+/* No really supported.  These are just for making libstdc++-v3 happy.  */
+typedef void *wctrans_t;
+extern wint_t		 towctrans(wint_t, wctrans_t);
+extern wctrans_t	 wctrans (const char *);
+
+__END_DECLS
+
+#endif /* _WCHAR_H_ */
diff --git a/ndk/platforms/android-12/arch-arm/symbols/libc.so.functions.txt b/ndk/platforms/android-12/arch-arm/symbols/libc.so.functions.txt
new file mode 100644
index 0000000..6320b24
--- /dev/null
+++ b/ndk/platforms/android-12/arch-arm/symbols/libc.so.functions.txt
@@ -0,0 +1,1088 @@
+MD5_Final
+MD5_Init
+MD5_Update
+SHA1Final
+SHA1Init
+SHA1Transform
+SHA1Update
+_Unwind_Backtrace
+_Unwind_Complete
+_Unwind_DeleteException
+_Unwind_ForcedUnwind
+_Unwind_GetCFA
+_Unwind_GetDataRelBase
+_Unwind_GetLanguageSpecificData
+_Unwind_GetRegionStart
+_Unwind_GetTextRelBase
+_Unwind_RaiseException
+_Unwind_Resume
+_Unwind_Resume_or_Rethrow
+_Unwind_VRS_Get
+_Unwind_VRS_Pop
+_Unwind_VRS_Set
+___Unwind_Backtrace
+___Unwind_ForcedUnwind
+___Unwind_RaiseException
+___Unwind_Resume
+___Unwind_Resume_or_Rethrow
+__adddf3
+__addsf3
+__aeabi_atexit
+__aeabi_cdcmpeq
+__aeabi_cdcmple
+__aeabi_cdrcmple
+__aeabi_d2f
+__aeabi_d2iz
+__aeabi_dadd
+__aeabi_dcmpeq
+__aeabi_dcmpge
+__aeabi_dcmpgt
+__aeabi_dcmple
+__aeabi_dcmplt
+__aeabi_dcmpun
+__aeabi_ddiv
+__aeabi_dmul
+__aeabi_drsub
+__aeabi_dsub
+__aeabi_f2d
+__aeabi_f2iz
+__aeabi_fadd
+__aeabi_fcmpun
+__aeabi_fdiv
+__aeabi_fmul
+__aeabi_frsub
+__aeabi_fsub
+__aeabi_i2d
+__aeabi_i2f
+__aeabi_idiv
+__aeabi_idivmod
+__aeabi_l2d
+__aeabi_l2f
+__aeabi_ldivmod
+__aeabi_lmul
+__aeabi_memclr
+__aeabi_memclr4
+__aeabi_memclr8
+__aeabi_memcpy
+__aeabi_memcpy4
+__aeabi_memcpy8
+__aeabi_memmove
+__aeabi_memmove4
+__aeabi_memmove8
+__aeabi_memset
+__aeabi_memset4
+__aeabi_memset8
+__aeabi_ui2d
+__aeabi_ui2f
+__aeabi_uidiv
+__aeabi_uidivmod
+__aeabi_ul2d
+__aeabi_ul2f
+__aeabi_uldivmod
+__aeabi_unwind_cpp_pr0
+__aeabi_unwind_cpp_pr1
+__aeabi_unwind_cpp_pr2
+__arc4_getbyte
+__assert
+__assert2
+__atexit_register_cleanup
+__atomic_cmpxchg
+__atomic_dec
+__atomic_inc
+__atomic_swap
+__b64_ntop
+__b64_pton
+__bionic_atfork_run_child
+__bionic_atfork_run_parent
+__bionic_atfork_run_prepare
+__bionic_clone
+__bionic_clone_entry
+__bionic_libgcc_compat_hooks
+__brk
+__cmpdf2
+__cxa_atexit
+__cxa_finalize
+__div0
+__divdf3
+__divdi3
+__divsf3
+__divsi3
+__dn_comp
+__dn_count_labels
+__dn_skipname
+__dorand48
+__eqdf2
+__errno
+__evAddTime
+__evCmpTime
+__evConsIovec
+__evConsTime
+__evNowTime
+__evSubTime
+__evTimeSpec
+__evTimeVal
+__evUTCTime
+__extendsfdf2
+__fcntl
+__fcntl64
+__findenv
+__fixdfsi
+__fixsfsi
+__floatdidf
+__floatdisf
+__floatsidf
+__floatsisf
+__floatundidf
+__floatundisf
+__floatunsidf
+__floatunsisf
+__fork
+__fp_nquery
+__fp_query
+__fstatfs64
+__futex_syscall3
+__futex_syscall4
+__futex_wait
+__futex_wait_ex
+__futex_wake
+__futex_wake_ex
+__gedf2
+__get_h_errno
+__get_pc
+__get_res_cache
+__get_sp
+__get_stack_base
+__get_thread
+__getcpu
+__getcwd
+__getpriority
+__gnu_Unwind_Backtrace
+__gnu_Unwind_Find_exidx
+__gnu_Unwind_ForcedUnwind
+__gnu_Unwind_RaiseException
+__gnu_Unwind_Restore_VFP
+__gnu_Unwind_Restore_VFP_D
+__gnu_Unwind_Restore_VFP_D_16_to_31
+__gnu_Unwind_Restore_WMMXC
+__gnu_Unwind_Restore_WMMXD
+__gnu_Unwind_Resume
+__gnu_Unwind_Resume_or_Rethrow
+__gnu_Unwind_Save_VFP
+__gnu_Unwind_Save_VFP_D
+__gnu_Unwind_Save_VFP_D_16_to_31
+__gnu_Unwind_Save_WMMXC
+__gnu_Unwind_Save_WMMXD
+__gnu_ldivmod_helper
+__gnu_uldivmod_helper
+__gnu_unwind_execute
+__gnu_unwind_frame
+__gtdf2
+__hostalias
+__init_tls
+__ioctl
+__ledf2
+__libc_android_log_assert
+__libc_android_log_print
+__libc_android_log_vprint
+__libc_fini
+__libc_init
+__libc_init_common
+__libc_preinit
+__llseek
+__loc_aton
+__loc_ntoa
+__ltdf2
+__memcmp16
+__mmap2
+__muldf3
+__muldi3
+__mulsf3
+__nedf2
+__ns_format_ttl
+__ns_get16
+__ns_get32
+__ns_initparse
+__ns_makecanon
+__ns_msg_getflag
+__ns_name_compress
+__ns_name_ntol
+__ns_name_ntop
+__ns_name_pack
+__ns_name_pton
+__ns_name_rollback
+__ns_name_skip
+__ns_name_uncompress
+__ns_name_unpack
+__ns_parserr
+__ns_put16
+__ns_put32
+__ns_samename
+__ns_skiprr
+__ns_sprintrr
+__ns_sprintrrf
+__open
+__openat
+__p_cdname
+__p_cdnname
+__p_class
+__p_fqname
+__p_fqnname
+__p_option
+__p_query
+__p_rcode
+__p_secstodate
+__p_section
+__p_sockun
+__p_time
+__p_type
+__popcountsi2
+__pthread_cleanup_pop
+__pthread_cleanup_push
+__pthread_clone
+__pthread_cond_timedwait
+__pthread_cond_timedwait_relative
+__ptrace
+__putlong
+__putshort
+__reboot
+__res_close
+__res_dnok
+__res_get_nibblesuffix
+__res_get_nibblesuffix2
+__res_get_state
+__res_get_static
+__res_getservers
+__res_hnok
+__res_hostalias
+__res_isourserver
+__res_mailok
+__res_nameinquery
+__res_nametoclass
+__res_nametotype
+__res_nclose
+__res_ndestroy
+__res_ninit
+__res_nmkquery
+__res_nopt
+__res_nquery
+__res_nquerydomain
+__res_nsearch
+__res_nsend
+__res_opt
+__res_ownok
+__res_pquery
+__res_put_state
+__res_queriesmatch
+__res_querydomain
+__res_randomid
+__res_send
+__res_send_setqhook
+__res_send_setrhook
+__res_setservers
+__res_vinit
+__restore_core_regs
+__rt_sigaction
+__rt_sigprocmask
+__rt_sigtimedwait
+__sched_cpualloc
+__sched_cpucount
+__sched_cpufree
+__sched_getaffinity
+__sclose
+__set_errno
+__set_tls
+__setresuid
+__setreuid
+__setuid
+__sflags
+__sflush
+__sflush_locked
+__sfp
+__sigsuspend
+__sinit
+__smakebuf
+__sread
+__srefill
+__srget
+__sseek
+__stack_chk_fail
+__statfs64
+__subdf3
+__subsf3
+__swbuf
+__swhatbuf
+__swrite
+__swsetup
+__sym_ntop
+__sym_ntos
+__sym_ston
+__sys_clone
+__syslog
+__system_properties_init
+__system_property_find
+__system_property_find_nth
+__system_property_get
+__system_property_read
+__system_property_set
+__system_property_wait
+__thread_entry
+__timer_create
+__timer_delete
+__timer_getoverrun
+__timer_gettime
+__timer_settime
+__truncdfsf2
+__udivdi3
+__udivsi3
+__unorddf2
+__unordsf2
+__vfprintf
+__wait4
+__waitid
+_cleanup
+_exit
+_exit_thread
+_exit_with_stack_teardown
+_fwalk
+_getlong
+_getshort
+_init_thread
+_longjmp
+_memmove_words
+_setjmp
+_thread_created_hook
+abort
+accept
+access
+acct
+alarm
+alphasort
+arc4random
+arc4random_addrandom
+arc4random_buf
+arc4random_stir
+arc4random_uniform
+asctime
+asctime64
+asctime64_r
+asctime_r
+asprintf
+atexit
+atoi
+atol
+atoll
+basename
+basename_r
+bcopy
+bind
+bindresvport
+brk
+bsd_signal
+bsearch
+btowc
+bzero
+cacheflush
+calloc
+capget
+capset
+chdir
+chmod
+chown
+chroot
+clearenv
+clearerr
+clock
+clock_getres
+clock_gettime
+clock_nanosleep
+clock_settime
+clone
+close
+closedir
+closelog
+closelog_r
+connect
+cpuacct_add
+creat
+ctime
+ctime64
+ctime64_r
+ctime_r
+daemon
+delete_module
+difftime
+dirfd
+dirname
+dirname_r
+div
+dlcalloc
+dlfree
+dlindependent_calloc
+dlindependent_comalloc
+dlmallinfo
+dlmalloc
+dlmalloc_footprint
+dlmalloc_max_footprint
+dlmalloc_stats
+dlmalloc_trim
+dlmalloc_usable_size
+dlmalloc_walk_free_pages
+dlmalloc_walk_heap
+dlmallopt
+dlmemalign
+dlpvalloc
+dlrealloc
+dlvalloc
+dn_expand
+drand48
+dup
+dup2
+endpwent
+endservent
+endusershell
+endutent
+epoll_create
+epoll_ctl
+epoll_wait
+erand48
+err
+errx
+ether_aton
+ether_aton_r
+ether_ntoa
+ether_ntoa_r
+eventfd
+eventfd_read
+eventfd_write
+execl
+execle
+execlp
+execv
+execve
+execvp
+exit
+fchdir
+fchmod
+fchmodat
+fchown
+fchownat
+fclose
+fcntl
+fdatasync
+fdopen
+fdopendir
+fdprintf
+feof
+ferror
+fflush
+ffs
+fgetc
+fgetln
+fgetpos
+fgets
+fgetwc
+fgetws
+fileno
+flock
+flockfile
+fnmatch
+fopen
+fork
+fpathconf
+fprintf
+fpurge
+fputc
+fputs
+fputwc
+fputws
+fread
+free
+freeaddrinfo
+freedtoa
+freopen
+fscanf
+fseek
+fseeko
+fsetpos
+fstat
+fstatat
+fstatfs
+fsync
+ftell
+ftello
+ftime
+ftok
+ftruncate
+ftruncate64
+ftrylockfile
+fts_children
+fts_close
+fts_open
+fts_read
+fts_set
+funlockfile
+funopen
+futex
+fwide
+fwprintf
+fwrite
+fwscanf
+gai_strerror
+get_malloc_leak_info
+getaddrinfo
+getc
+getc_unlocked
+getchar
+getchar_unlocked
+getcwd
+getdents
+getdtablesize
+getegid
+getenv
+geteuid
+getgid
+getgrgid
+getgrnam
+getgrouplist
+getgroups
+gethostbyaddr
+gethostbyname
+gethostbyname2
+gethostbyname_r
+gethostent
+gethostname
+getitimer
+getlogin
+getmntent
+getnameinfo
+getnetbyaddr
+getnetbyname
+getopt
+getopt_long
+getopt_long_only
+getpeername
+getpgid
+getpgrp
+getpid
+getppid
+getpriority
+getprotobyname
+getprotobynumber
+getpt
+getpwnam
+getpwuid
+getresgid
+getresuid
+getrlimit
+getrusage
+gets
+getservbyname
+getservbyport
+getservent
+getservent_r
+getsockname
+getsockopt
+gettid
+gettimeofday
+getuid
+getusershell
+getutent
+getwc
+getwchar
+gmtime
+gmtime64
+gmtime64_r
+gmtime_r
+herror
+hstrerror
+if_indextoname
+if_nametoindex
+index
+inet_addr
+inet_aton
+inet_nsap_addr
+inet_nsap_ntoa
+inet_ntoa
+inet_ntop
+inet_pton
+init_module
+initgroups
+inotify_add_watch
+inotify_init
+inotify_rm_watch
+ioctl
+ioprio_get
+ioprio_set
+isalnum
+isalpha
+isascii
+isatty
+isblank
+iscntrl
+isdigit
+isgraph
+islower
+isprint
+ispunct
+issetugid
+isspace
+isupper
+iswalnum
+iswalpha
+iswcntrl
+iswctype
+iswdigit
+iswgraph
+iswlower
+iswprint
+iswpunct
+iswspace
+iswupper
+iswxdigit
+isxdigit
+jrand48
+kill
+killpg
+klogctl
+lchown
+ldexp
+ldiv
+link
+listen
+lldiv
+localtime
+localtime64
+localtime64_r
+localtime_r
+longjmp
+longjmperror
+lrand48
+lseek
+lseek64
+lstat
+madvise
+mallinfo
+malloc
+malloc_debug_init
+mbrlen
+mbrtowc
+mbsinit
+mbsrtowcs
+mbstowcs
+memalign
+memccpy
+memchr
+memcmp
+memcpy
+memmem
+memmove
+memrchr
+memset
+memswap
+mincore
+mkdir
+mkdirat
+mkdtemp
+mknod
+mkstemp
+mkstemps
+mktemp
+mktime
+mktime64
+mlock
+mmap
+mount
+mprotect
+mrand48
+mremap
+msync
+munlock
+munmap
+nanosleep
+nice
+nrand48
+nsdispatch
+open
+openat
+opendir
+openlog
+openlog_r
+pathconf
+pause
+pclose
+perror
+pipe
+pipe2
+poll
+popen
+posix2time
+prctl
+pread
+pread64
+printf
+pselect
+pthread_atfork
+pthread_attr_destroy
+pthread_attr_getdetachstate
+pthread_attr_getguardsize
+pthread_attr_getschedparam
+pthread_attr_getschedpolicy
+pthread_attr_getscope
+pthread_attr_getstack
+pthread_attr_getstackaddr
+pthread_attr_getstacksize
+pthread_attr_init
+pthread_attr_setdetachstate
+pthread_attr_setguardsize
+pthread_attr_setschedparam
+pthread_attr_setschedpolicy
+pthread_attr_setscope
+pthread_attr_setstack
+pthread_attr_setstackaddr
+pthread_attr_setstacksize
+pthread_cond_broadcast
+pthread_cond_destroy
+pthread_cond_init
+pthread_cond_signal
+pthread_cond_timedwait
+pthread_cond_timedwait_monotonic
+pthread_cond_timedwait_monotonic_np
+pthread_cond_timedwait_relative_np
+pthread_cond_timeout_np
+pthread_cond_wait
+pthread_condattr_destroy
+pthread_condattr_getpshared
+pthread_condattr_init
+pthread_condattr_setpshared
+pthread_create
+pthread_detach
+pthread_equal
+pthread_exit
+pthread_getattr_np
+pthread_getcpuclockid
+pthread_getschedparam
+pthread_getspecific
+pthread_join
+pthread_key_create
+pthread_key_delete
+pthread_kill
+pthread_mutex_destroy
+pthread_mutex_init
+pthread_mutex_lock
+pthread_mutex_lock_timeout_np
+pthread_mutex_trylock
+pthread_mutex_unlock
+pthread_mutexattr_destroy
+pthread_mutexattr_getpshared
+pthread_mutexattr_gettype
+pthread_mutexattr_init
+pthread_mutexattr_setpshared
+pthread_mutexattr_settype
+pthread_once
+pthread_rwlock_destroy
+pthread_rwlock_init
+pthread_rwlock_rdlock
+pthread_rwlock_timedrdlock
+pthread_rwlock_timedwrlock
+pthread_rwlock_tryrdlock
+pthread_rwlock_trywrlock
+pthread_rwlock_unlock
+pthread_rwlock_wrlock
+pthread_rwlockattr_destroy
+pthread_rwlockattr_getpshared
+pthread_rwlockattr_init
+pthread_rwlockattr_setpshared
+pthread_self
+pthread_setname_np
+pthread_setschedparam
+pthread_setspecific
+pthread_sigmask
+ptrace
+ptsname
+ptsname_r
+putc
+putc_unlocked
+putchar
+putchar_unlocked
+putenv
+puts
+pututline
+putw
+putwc
+putwchar
+pwrite
+pwrite64
+qsort
+raise
+read
+readdir
+readdir_r
+readlink
+readv
+realloc
+realpath
+reboot
+recv
+recvfrom
+recvmsg
+regcomp
+regerror
+regexec
+regfree
+remove
+rename
+renameat
+res_init
+res_mkquery
+res_query
+res_search
+restore_core_regs
+rewind
+rewinddir
+rmdir
+sbrk
+scandir
+scanf
+sched_get_priority_max
+sched_get_priority_min
+sched_getaffinity
+sched_getcpu
+sched_getparam
+sched_getscheduler
+sched_rr_get_interval
+sched_setaffinity
+sched_setparam
+sched_setscheduler
+sched_yield
+seed48
+select
+sem_close
+sem_destroy
+sem_getvalue
+sem_init
+sem_open
+sem_post
+sem_timedwait
+sem_trywait
+sem_unlink
+sem_wait
+send
+sendfile
+sendmsg
+sendto
+setbuf
+setbuffer
+setegid
+setenv
+seteuid
+setgid
+setgroups
+setitimer
+setjmp
+setlinebuf
+setlocale
+setlogmask
+setlogmask_r
+setpgid
+setpgrp
+setpriority
+setregid
+setresgid
+setresuid
+setreuid
+setrlimit
+setservent
+setsid
+setsockopt
+settimeofday
+setuid
+setusershell
+setutent
+setvbuf
+shutdown
+sigaction
+sigaltstack
+sigblock
+siginterrupt
+siglongjmp
+sigpending
+sigprocmask
+sigsetjmp
+sigsetmask
+sigsuspend
+sigwait
+sleep
+snprintf
+socket
+socketpair
+sprintf
+srand48
+sscanf
+stat
+statfs
+strcasecmp
+strcasestr
+strcat
+strchr
+strcmp
+strcoll
+strcpy
+strcspn
+strdup
+strerror
+strerror_r
+strftime
+strftime_tz
+strlcat
+strlcpy
+strlen
+strncasecmp
+strncat
+strncmp
+strncpy
+strndup
+strnlen
+strntoimax
+strntoumax
+strpbrk
+strptime
+strrchr
+strsep
+strsignal
+strspn
+strstr
+strtod
+strtoimax
+strtok
+strtok_r
+strtol
+strtoll
+strtotimeval
+strtoul
+strtoull
+strtoumax
+strxfrm
+swprintf
+swscanf
+symlink
+sync
+syscall
+sysconf
+sysinfo
+syslog
+syslog_r
+system
+sysv_signal
+tcgetpgrp
+tcsetpgrp
+tempnam
+time
+time2posix
+timegm
+timegm64
+timelocal
+timelocal64
+timer_create
+timer_delete
+timer_getoverrun
+timer_gettime
+timer_settime
+times
+tkill
+tmpfile
+tmpnam
+toascii
+tolower
+toupper
+towlower
+towupper
+truncate
+ttyname
+ttyname_r
+tzset
+umask
+umount
+umount2
+uname
+ungetc
+ungetwc
+unlink
+unlinkat
+unlockpt
+unsetenv
+usleep
+utime
+utimensat
+utimes
+utmpname
+valloc
+vasprintf
+verr
+verrx
+vfdprintf
+vfork
+vfprintf
+vfscanf
+vfwprintf
+vprintf
+vscanf
+vsnprintf
+vsprintf
+vsscanf
+vswprintf
+vsyslog
+vsyslog_r
+vwarn
+vwarnx
+vwprintf
+wait
+wait3
+waitid
+waitpid
+warn
+warnx
+wcpcpy
+wcpncpy
+wcrtomb
+wcscasecmp
+wcscat
+wcschr
+wcscmp
+wcscoll
+wcscpy
+wcscspn
+wcsdup
+wcsftime
+wcslcat
+wcslcpy
+wcslen
+wcsncasecmp
+wcsncat
+wcsncmp
+wcsncpy
+wcsnlen
+wcspbrk
+wcsrchr
+wcsrtombs
+wcsspn
+wcsstr
+wcstod
+wcstok
+wcstol
+wcstombs
+wcstoul
+wcswcs
+wcswidth
+wcsxfrm
+wctob
+wctype
+wcwidth
+wmemchr
+wmemcmp
+wmemcpy
+wmemmove
+wmemset
+wprintf
+write
+writev
+wscanf
diff --git a/ndk/platforms/android-12/arch-arm/symbols/libc.so.variables.txt b/ndk/platforms/android-12/arch-arm/symbols/libc.so.variables.txt
new file mode 100644
index 0000000..ccc33a8
--- /dev/null
+++ b/ndk/platforms/android-12/arch-arm/symbols/libc.so.variables.txt
@@ -0,0 +1,44 @@
+_C_ctype_
+_C_tolower_
+_C_toupper_
+__atexit
+__atexit_invalid
+__bionic_brk
+__evOptMonoTime
+__isthreaded
+__libc_malloc_default_dispatch
+__libc_malloc_dispatch
+__p_cert_syms
+__p_class_syms
+__p_key_syms
+__p_rcode_syms
+__p_type_syms
+__page_shift
+__page_size
+__popcount_tab
+__progname
+__rand48_add
+__rand48_mult
+__rand48_seed
+__sF
+__sdidinit
+__sglue
+__stack_chk_guard
+__system_property_area__
+_ctype_
+_ns_flagdata
+_tolower_tab_
+_toupper_tab_
+daylight
+environ
+h_errlist
+h_nerr
+optarg
+opterr
+optind
+optopt
+optreset
+sys_siglist
+sys_signame
+timezone
+tzname
diff --git a/ndk/platforms/android-12/include/sys/stat.h b/ndk/platforms/android-12/include/sys/stat.h
new file mode 100644
index 0000000..87fcfd0
--- /dev/null
+++ b/ndk/platforms/android-12/include/sys/stat.h
@@ -0,0 +1,112 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#ifndef _SYS_STAT_H_
+#define _SYS_STAT_H_
+
+#include <sys/cdefs.h>
+#include <sys/types.h>
+#include <sys/time.h>
+#include <linux/stat.h>
+
+#include <endian.h>
+
+__BEGIN_DECLS
+
+/* really matches stat64 in the kernel, hence the padding
+ * Note: The kernel zero's the padded region because glibc might read them
+ * in the hope that the kernel has stretched to using larger sizes.
+ */
+struct stat {
+    unsigned long long  st_dev;
+    unsigned char       __pad0[4];
+
+    unsigned long       __st_ino;
+    unsigned int        st_mode;
+    unsigned int        st_nlink;
+
+    unsigned long       st_uid;
+    unsigned long       st_gid;
+
+    unsigned long long  st_rdev;
+    unsigned char       __pad3[4];
+
+    long long           st_size;
+    unsigned long	st_blksize;
+    unsigned long long  st_blocks;
+
+    unsigned long       st_atime;
+    unsigned long       st_atime_nsec;
+
+    unsigned long       st_mtime;
+    unsigned long       st_mtime_nsec;
+
+    unsigned long       st_ctime;
+    unsigned long       st_ctime_nsec;
+
+    unsigned long long  st_ino;
+};
+
+/* For compatibility with GLibc, we provide macro aliases
+ * for the non-Posix nano-seconds accessors.
+ */
+#define  st_atimensec  st_atime_nsec
+#define  st_mtimensec  st_mtime_nsec
+#define  st_ctimensec  st_ctime_nsec
+
+extern int    chmod(const char *, mode_t);
+extern int    fchmod(int, mode_t);
+extern int    mkdir(const char *, mode_t);
+
+extern int    stat(const char *, struct stat *);
+extern int    fstat(int, struct stat *);
+extern int    lstat(const char *, struct stat *);
+extern int    mknod(const char *, mode_t, dev_t);
+extern mode_t umask(mode_t);
+
+#define  stat64    stat
+#define  fstat64   fstat
+#define  lstat64   lstat
+
+static __inline__ int mkfifo(const char *__p, mode_t __m)
+{
+  return mknod(__p, (__m & ~S_IFMT) | S_IFIFO, (dev_t)0);
+}
+
+extern int  fstatat(int dirfd, const char *path, struct stat *buf, int flags);
+extern int  mkdirat(int dirfd, const char *pathname, mode_t mode);
+extern int fchownat(int dirfd, const char *path, uid_t owner, gid_t group, int flags);
+extern int fchmodat(int dirfd, const char *path, mode_t mode, int flags);
+extern int renameat(int olddirfd, const char *oldpath, int newdirfd, const char *newpath);
+
+# define UTIME_NOW      ((1l << 30) - 1l)
+# define UTIME_OMIT     ((1l << 30) - 2l)
+extern int utimensat (int fd, const char *path, const struct timespec times[2], int flags);
+
+__END_DECLS
+
+#endif /* _SYS_STAT_H_ */
diff --git a/ndk/platforms/android-14/arch-arm/symbols/libc.so.functions.txt b/ndk/platforms/android-14/arch-arm/symbols/libc.so.functions.txt
new file mode 100644
index 0000000..2336b9a
--- /dev/null
+++ b/ndk/platforms/android-14/arch-arm/symbols/libc.so.functions.txt
@@ -0,0 +1,1098 @@
+MD5_Final
+MD5_Init
+MD5_Update
+SHA1Final
+SHA1Init
+SHA1Transform
+SHA1Update
+_Unwind_Backtrace
+_Unwind_Complete
+_Unwind_DeleteException
+_Unwind_ForcedUnwind
+_Unwind_GetCFA
+_Unwind_GetDataRelBase
+_Unwind_GetLanguageSpecificData
+_Unwind_GetRegionStart
+_Unwind_GetTextRelBase
+_Unwind_RaiseException
+_Unwind_Resume
+_Unwind_Resume_or_Rethrow
+_Unwind_VRS_Get
+_Unwind_VRS_Pop
+_Unwind_VRS_Set
+___Unwind_Backtrace
+___Unwind_ForcedUnwind
+___Unwind_RaiseException
+___Unwind_Resume
+___Unwind_Resume_or_Rethrow
+__adddf3
+__addsf3
+__aeabi_atexit
+__aeabi_cdcmpeq
+__aeabi_cdcmple
+__aeabi_cdrcmple
+__aeabi_d2f
+__aeabi_d2iz
+__aeabi_dadd
+__aeabi_dcmpeq
+__aeabi_dcmpge
+__aeabi_dcmpgt
+__aeabi_dcmple
+__aeabi_dcmplt
+__aeabi_dcmpun
+__aeabi_ddiv
+__aeabi_dmul
+__aeabi_drsub
+__aeabi_dsub
+__aeabi_f2d
+__aeabi_f2iz
+__aeabi_f2uiz
+__aeabi_fadd
+__aeabi_fcmpun
+__aeabi_fdiv
+__aeabi_fmul
+__aeabi_frsub
+__aeabi_fsub
+__aeabi_i2d
+__aeabi_i2f
+__aeabi_idiv
+__aeabi_idivmod
+__aeabi_l2d
+__aeabi_l2f
+__aeabi_ldivmod
+__aeabi_lmul
+__aeabi_memclr
+__aeabi_memclr4
+__aeabi_memclr8
+__aeabi_memcpy
+__aeabi_memcpy4
+__aeabi_memcpy8
+__aeabi_memmove
+__aeabi_memmove4
+__aeabi_memmove8
+__aeabi_memset
+__aeabi_memset4
+__aeabi_memset8
+__aeabi_ui2d
+__aeabi_ui2f
+__aeabi_uidiv
+__aeabi_uidivmod
+__aeabi_ul2d
+__aeabi_ul2f
+__aeabi_uldivmod
+__aeabi_unwind_cpp_pr0
+__aeabi_unwind_cpp_pr1
+__aeabi_unwind_cpp_pr2
+__arc4_getbyte
+__assert
+__assert2
+__atexit_register_cleanup
+__atomic_cmpxchg
+__atomic_dec
+__atomic_inc
+__atomic_swap
+__b64_ntop
+__b64_pton
+__bionic_atfork_run_child
+__bionic_atfork_run_parent
+__bionic_atfork_run_prepare
+__bionic_clone
+__bionic_clone_entry
+__bionic_libgcc_compat_hooks
+__brk
+__cmpdf2
+__cxa_atexit
+__cxa_finalize
+__div0
+__divdf3
+__divdi3
+__divsf3
+__divsi3
+__dn_comp
+__dn_count_labels
+__dn_skipname
+__dorand48
+__eqdf2
+__errno
+__evAddTime
+__evCmpTime
+__evConsIovec
+__evConsTime
+__evNowTime
+__evSubTime
+__evTimeSpec
+__evTimeVal
+__evUTCTime
+__extendsfdf2
+__fcntl
+__fcntl64
+__findenv
+__fixdfsi
+__fixsfsi
+__fixunssfsi
+__floatdidf
+__floatdisf
+__floatsidf
+__floatsisf
+__floatundidf
+__floatundisf
+__floatunsidf
+__floatunsisf
+__fork
+__fp_nquery
+__fp_query
+__fstatfs64
+__futex_syscall3
+__futex_syscall4
+__futex_wait
+__futex_wait_ex
+__futex_wake
+__futex_wake_ex
+__gedf2
+__get_h_errno
+__get_pc
+__get_res_cache
+__get_sp
+__get_stack_base
+__get_thread
+__getcpu
+__getcwd
+__getpriority
+__gnu_Unwind_Backtrace
+__gnu_Unwind_Find_exidx
+__gnu_Unwind_ForcedUnwind
+__gnu_Unwind_RaiseException
+__gnu_Unwind_Restore_VFP
+__gnu_Unwind_Restore_VFP_D
+__gnu_Unwind_Restore_VFP_D_16_to_31
+__gnu_Unwind_Restore_WMMXC
+__gnu_Unwind_Restore_WMMXD
+__gnu_Unwind_Resume
+__gnu_Unwind_Resume_or_Rethrow
+__gnu_Unwind_Save_VFP
+__gnu_Unwind_Save_VFP_D
+__gnu_Unwind_Save_VFP_D_16_to_31
+__gnu_Unwind_Save_WMMXC
+__gnu_Unwind_Save_WMMXD
+__gnu_ldivmod_helper
+__gnu_uldivmod_helper
+__gnu_unwind_execute
+__gnu_unwind_frame
+__gtdf2
+__hostalias
+__init_tls
+__ioctl
+__ledf2
+__libc_fini
+__libc_init
+__libc_init_common
+__libc_preinit
+__llseek
+__loc_aton
+__loc_ntoa
+__ltdf2
+__memcmp16
+__mmap2
+__muldf3
+__muldi3
+__mulsf3
+__nedf2
+__ns_format_ttl
+__ns_get16
+__ns_get32
+__ns_initparse
+__ns_makecanon
+__ns_msg_getflag
+__ns_name_compress
+__ns_name_ntol
+__ns_name_ntop
+__ns_name_pack
+__ns_name_pton
+__ns_name_rollback
+__ns_name_skip
+__ns_name_uncompress
+__ns_name_unpack
+__ns_parserr
+__ns_put16
+__ns_put32
+__ns_samename
+__ns_skiprr
+__ns_sprintrr
+__ns_sprintrrf
+__open
+__openat
+__p_cdname
+__p_cdnname
+__p_class
+__p_fqname
+__p_fqnname
+__p_option
+__p_query
+__p_rcode
+__p_secstodate
+__p_section
+__p_sockun
+__p_time
+__p_type
+__popcountsi2
+__pthread_cleanup_pop
+__pthread_cleanup_push
+__pthread_clone
+__pthread_cond_timedwait
+__pthread_cond_timedwait_relative
+__pthread_gettid
+__ptrace
+__putlong
+__putshort
+__reboot
+__res_close
+__res_dnok
+__res_get_nibblesuffix
+__res_get_nibblesuffix2
+__res_get_state
+__res_get_static
+__res_getservers
+__res_hnok
+__res_hostalias
+__res_isourserver
+__res_mailok
+__res_nameinquery
+__res_nametoclass
+__res_nametotype
+__res_nclose
+__res_ndestroy
+__res_ninit
+__res_nmkquery
+__res_nopt
+__res_nquery
+__res_nquerydomain
+__res_nsearch
+__res_nsend
+__res_opt
+__res_ownok
+__res_pquery
+__res_put_state
+__res_queriesmatch
+__res_querydomain
+__res_randomid
+__res_send
+__res_send_setqhook
+__res_send_setrhook
+__res_setservers
+__res_vinit
+__restore_core_regs
+__rt_sigaction
+__rt_sigprocmask
+__rt_sigtimedwait
+__sched_cpualloc
+__sched_cpucount
+__sched_cpufree
+__sched_getaffinity
+__sclose
+__set_errno
+__set_tls
+__setresuid
+__setreuid
+__setuid
+__sflags
+__sflush
+__sflush_locked
+__sfp
+__sigsuspend
+__sinit
+__smakebuf
+__sread
+__srefill
+__srget
+__sseek
+__stack_chk_fail
+__statfs64
+__subdf3
+__subsf3
+__swbuf
+__swhatbuf
+__swrite
+__swsetup
+__sym_ntop
+__sym_ntos
+__sym_ston
+__sys_clone
+__syslog
+__system_properties_init
+__system_property_find
+__system_property_find_nth
+__system_property_get
+__system_property_read
+__system_property_set
+__system_property_wait
+__thread_entry
+__timer_create
+__timer_delete
+__timer_getoverrun
+__timer_gettime
+__timer_settime
+__truncdfsf2
+__udivdi3
+__udivsi3
+__unorddf2
+__unordsf2
+__vfprintf
+__wait4
+__waitid
+_cache_get_nameserver_addr
+_cleanup
+_exit
+_exit_thread
+_exit_with_stack_teardown
+_fwalk
+_getlong
+_getshort
+_init_thread
+_longjmp
+_memmove_words
+_resolv_flush_cache_for_default_iface
+_resolv_flush_cache_for_iface
+_resolv_get_addr_of_default_iface
+_resolv_get_addr_of_iface
+_resolv_set_addr_of_iface
+_resolv_set_default_iface
+_resolv_set_nameservers_for_iface
+_setjmp
+_thread_created_hook
+abort
+accept
+access
+acct
+alarm
+alphasort
+arc4random
+arc4random_addrandom
+arc4random_buf
+arc4random_stir
+arc4random_uniform
+asctime
+asctime64
+asctime64_r
+asctime_r
+asprintf
+atexit
+atoi
+atol
+atoll
+basename
+basename_r
+bcopy
+bind
+bindresvport
+brk
+bsd_signal
+bsearch
+btowc
+bzero
+cacheflush
+calloc
+capget
+capset
+chdir
+chmod
+chown
+chroot
+clearenv
+clearerr
+clock
+clock_getres
+clock_gettime
+clock_nanosleep
+clock_settime
+clone
+close
+closedir
+closelog
+closelog_r
+connect
+cpuacct_add
+creat
+ctime
+ctime64
+ctime64_r
+ctime_r
+daemon
+delete_module
+difftime
+dirfd
+dirname
+dirname_r
+div
+dlcalloc
+dlfree
+dlindependent_calloc
+dlindependent_comalloc
+dlmallinfo
+dlmalloc
+dlmalloc_footprint
+dlmalloc_max_footprint
+dlmalloc_stats
+dlmalloc_trim
+dlmalloc_usable_size
+dlmalloc_walk_free_pages
+dlmalloc_walk_heap
+dlmallopt
+dlmemalign
+dlpvalloc
+dlrealloc
+dlvalloc
+dn_expand
+drand48
+dup
+dup2
+endpwent
+endservent
+endusershell
+endutent
+epoll_create
+epoll_ctl
+epoll_wait
+erand48
+err
+errx
+ether_aton
+ether_aton_r
+ether_ntoa
+ether_ntoa_r
+eventfd
+eventfd_read
+eventfd_write
+execl
+execle
+execlp
+execv
+execve
+execvp
+exit
+fchdir
+fchmod
+fchmodat
+fchown
+fchownat
+fclose
+fcntl
+fdatasync
+fdopen
+fdopendir
+fdprintf
+feof
+ferror
+fflush
+ffs
+fgetc
+fgetln
+fgetpos
+fgets
+fgetwc
+fgetws
+fileno
+flock
+flockfile
+fnmatch
+fopen
+fork
+fpathconf
+fprintf
+fpurge
+fputc
+fputs
+fputwc
+fputws
+fread
+free
+freeaddrinfo
+freedtoa
+freopen
+fscanf
+fseek
+fseeko
+fsetpos
+fstat
+fstatat
+fstatfs
+fsync
+ftell
+ftello
+ftime
+ftok
+ftruncate
+ftruncate64
+ftrylockfile
+fts_children
+fts_close
+fts_open
+fts_read
+fts_set
+funlockfile
+funopen
+futex
+fwide
+fwprintf
+fwrite
+fwscanf
+gai_strerror
+get_malloc_leak_info
+getaddrinfo
+getc
+getc_unlocked
+getchar
+getchar_unlocked
+getcwd
+getdents
+getdtablesize
+getegid
+getenv
+geteuid
+getgid
+getgrgid
+getgrnam
+getgrouplist
+getgroups
+gethostbyaddr
+gethostbyname
+gethostbyname2
+gethostbyname_r
+gethostent
+gethostname
+getitimer
+getlogin
+getmntent
+getnameinfo
+getnetbyaddr
+getnetbyname
+getopt
+getopt_long
+getopt_long_only
+getpeername
+getpgid
+getpgrp
+getpid
+getppid
+getpriority
+getprotobyname
+getprotobynumber
+getpt
+getpwnam
+getpwnam_r
+getpwuid
+getpwuid_r
+getresgid
+getresuid
+getrlimit
+getrusage
+gets
+getservbyname
+getservbyport
+getservent
+getservent_r
+getsockname
+getsockopt
+gettid
+gettimeofday
+getuid
+getusershell
+getutent
+getwc
+getwchar
+gmtime
+gmtime64
+gmtime64_r
+gmtime_r
+herror
+hstrerror
+if_indextoname
+if_nametoindex
+index
+inet_addr
+inet_aton
+inet_nsap_addr
+inet_nsap_ntoa
+inet_ntoa
+inet_ntop
+inet_pton
+init_module
+initgroups
+inotify_add_watch
+inotify_init
+inotify_rm_watch
+ioctl
+ioprio_get
+ioprio_set
+isalnum
+isalpha
+isascii
+isatty
+isblank
+iscntrl
+isdigit
+isgraph
+islower
+isprint
+ispunct
+issetugid
+isspace
+isupper
+iswalnum
+iswalpha
+iswcntrl
+iswctype
+iswdigit
+iswgraph
+iswlower
+iswprint
+iswpunct
+iswspace
+iswupper
+iswxdigit
+isxdigit
+jrand48
+kill
+killpg
+klogctl
+lchown
+ldexp
+ldiv
+link
+listen
+lldiv
+localtime
+localtime64
+localtime64_r
+localtime_r
+longjmp
+longjmperror
+lrand48
+lseek
+lseek64
+lstat
+madvise
+mallinfo
+malloc
+malloc_debug_init
+mbrlen
+mbrtowc
+mbsinit
+mbsrtowcs
+mbstowcs
+memalign
+memccpy
+memchr
+memcmp
+memcpy
+memmem
+memmove
+memrchr
+memset
+memswap
+mincore
+mkdir
+mkdirat
+mkdtemp
+mknod
+mkstemp
+mkstemps
+mktemp
+mktime
+mktime64
+mlock
+mmap
+mount
+mprotect
+mrand48
+mremap
+msync
+munlock
+munmap
+nanosleep
+nice
+nrand48
+nsdispatch
+open
+openat
+opendir
+openlog
+openlog_r
+pathconf
+pause
+pclose
+perror
+pipe
+pipe2
+poll
+popen
+posix2time
+prctl
+pread
+pread64
+printf
+pselect
+pthread_atfork
+pthread_attr_destroy
+pthread_attr_getdetachstate
+pthread_attr_getguardsize
+pthread_attr_getschedparam
+pthread_attr_getschedpolicy
+pthread_attr_getscope
+pthread_attr_getstack
+pthread_attr_getstackaddr
+pthread_attr_getstacksize
+pthread_attr_init
+pthread_attr_setdetachstate
+pthread_attr_setguardsize
+pthread_attr_setschedparam
+pthread_attr_setschedpolicy
+pthread_attr_setscope
+pthread_attr_setstack
+pthread_attr_setstackaddr
+pthread_attr_setstacksize
+pthread_cond_broadcast
+pthread_cond_destroy
+pthread_cond_init
+pthread_cond_signal
+pthread_cond_timedwait
+pthread_cond_timedwait_monotonic
+pthread_cond_timedwait_monotonic_np
+pthread_cond_timedwait_relative_np
+pthread_cond_timeout_np
+pthread_cond_wait
+pthread_condattr_destroy
+pthread_condattr_getpshared
+pthread_condattr_init
+pthread_condattr_setpshared
+pthread_create
+pthread_detach
+pthread_equal
+pthread_exit
+pthread_getattr_np
+pthread_getcpuclockid
+pthread_getschedparam
+pthread_getspecific
+pthread_join
+pthread_key_create
+pthread_key_delete
+pthread_kill
+pthread_mutex_destroy
+pthread_mutex_init
+pthread_mutex_lock
+pthread_mutex_lock_timeout_np
+pthread_mutex_trylock
+pthread_mutex_unlock
+pthread_mutexattr_destroy
+pthread_mutexattr_getpshared
+pthread_mutexattr_gettype
+pthread_mutexattr_init
+pthread_mutexattr_setpshared
+pthread_mutexattr_settype
+pthread_once
+pthread_rwlock_destroy
+pthread_rwlock_init
+pthread_rwlock_rdlock
+pthread_rwlock_timedrdlock
+pthread_rwlock_timedwrlock
+pthread_rwlock_tryrdlock
+pthread_rwlock_trywrlock
+pthread_rwlock_unlock
+pthread_rwlock_wrlock
+pthread_rwlockattr_destroy
+pthread_rwlockattr_getpshared
+pthread_rwlockattr_init
+pthread_rwlockattr_setpshared
+pthread_self
+pthread_setname_np
+pthread_setschedparam
+pthread_setspecific
+pthread_sigmask
+ptrace
+ptsname
+ptsname_r
+putc
+putc_unlocked
+putchar
+putchar_unlocked
+putenv
+puts
+pututline
+putw
+putwc
+putwchar
+pwrite
+pwrite64
+qsort
+raise
+read
+readdir
+readdir_r
+readlink
+readv
+realloc
+realpath
+reboot
+recv
+recvfrom
+recvmsg
+regcomp
+regerror
+regexec
+regfree
+remove
+rename
+renameat
+res_init
+res_mkquery
+res_query
+res_search
+restore_core_regs
+rewind
+rewinddir
+rmdir
+sbrk
+scandir
+scanf
+sched_get_priority_max
+sched_get_priority_min
+sched_getaffinity
+sched_getcpu
+sched_getparam
+sched_getscheduler
+sched_rr_get_interval
+sched_setaffinity
+sched_setparam
+sched_setscheduler
+sched_yield
+seed48
+select
+sem_close
+sem_destroy
+sem_getvalue
+sem_init
+sem_open
+sem_post
+sem_timedwait
+sem_trywait
+sem_unlink
+sem_wait
+send
+sendfile
+sendmsg
+sendto
+setbuf
+setbuffer
+setegid
+setenv
+seteuid
+setgid
+setgroups
+setitimer
+setjmp
+setlinebuf
+setlocale
+setlogmask
+setlogmask_r
+setpgid
+setpgrp
+setpriority
+setregid
+setresgid
+setresuid
+setreuid
+setrlimit
+setservent
+setsid
+setsockopt
+settimeofday
+setuid
+setusershell
+setutent
+setvbuf
+shutdown
+sigaction
+sigaltstack
+sigblock
+siginterrupt
+siglongjmp
+sigpending
+sigprocmask
+sigsetjmp
+sigsetmask
+sigsuspend
+sigwait
+sleep
+snprintf
+socket
+socketpair
+sprintf
+srand48
+sscanf
+stat
+statfs
+strcasecmp
+strcasestr
+strcat
+strchr
+strcmp
+strcoll
+strcpy
+strcspn
+strdup
+strerror
+strerror_r
+strftime
+strftime_tz
+strlcat
+strlcpy
+strlen
+strncasecmp
+strncat
+strncmp
+strncpy
+strndup
+strnlen
+strntoimax
+strntoumax
+strpbrk
+strptime
+strrchr
+strsep
+strsignal
+strspn
+strstr
+strtod
+strtoimax
+strtok
+strtok_r
+strtol
+strtoll
+strtotimeval
+strtoul
+strtoull
+strtoumax
+strxfrm
+swprintf
+swscanf
+symlink
+sync
+syscall
+sysconf
+sysinfo
+syslog
+syslog_r
+system
+sysv_signal
+tcgetpgrp
+tcsetpgrp
+tempnam
+time
+time2posix
+timegm
+timegm64
+timelocal
+timelocal64
+timer_create
+timer_delete
+timer_getoverrun
+timer_gettime
+timer_settime
+times
+tkill
+tmpfile
+tmpnam
+toascii
+tolower
+toupper
+towlower
+towupper
+truncate
+ttyname
+ttyname_r
+tzset
+umask
+umount
+umount2
+uname
+ungetc
+ungetwc
+unlink
+unlinkat
+unlockpt
+unsetenv
+usleep
+utime
+utimensat
+utimes
+utmpname
+valloc
+vasprintf
+verr
+verrx
+vfdprintf
+vfork
+vfprintf
+vfscanf
+vfwprintf
+vprintf
+vscanf
+vsnprintf
+vsprintf
+vsscanf
+vswprintf
+vsyslog
+vsyslog_r
+vwarn
+vwarnx
+vwprintf
+wait
+wait3
+waitid
+waitpid
+warn
+warnx
+wcpcpy
+wcpncpy
+wcrtomb
+wcscasecmp
+wcscat
+wcschr
+wcscmp
+wcscoll
+wcscpy
+wcscspn
+wcsdup
+wcsftime
+wcslcat
+wcslcpy
+wcslen
+wcsncasecmp
+wcsncat
+wcsncmp
+wcsncpy
+wcsnlen
+wcspbrk
+wcsrchr
+wcsrtombs
+wcsspn
+wcsstr
+wcstod
+wcstok
+wcstol
+wcstombs
+wcstoul
+wcswcs
+wcswidth
+wcsxfrm
+wctob
+wctype
+wcwidth
+wmemchr
+wmemcmp
+wmemcpy
+wmemmove
+wmemset
+wprintf
+write
+writev
+wscanf
diff --git a/ndk/platforms/android-14/arch-arm/symbols/libc.so.variables.txt b/ndk/platforms/android-14/arch-arm/symbols/libc.so.variables.txt
new file mode 100644
index 0000000..ccc33a8
--- /dev/null
+++ b/ndk/platforms/android-14/arch-arm/symbols/libc.so.variables.txt
@@ -0,0 +1,44 @@
+_C_ctype_
+_C_tolower_
+_C_toupper_
+__atexit
+__atexit_invalid
+__bionic_brk
+__evOptMonoTime
+__isthreaded
+__libc_malloc_default_dispatch
+__libc_malloc_dispatch
+__p_cert_syms
+__p_class_syms
+__p_key_syms
+__p_rcode_syms
+__p_type_syms
+__page_shift
+__page_size
+__popcount_tab
+__progname
+__rand48_add
+__rand48_mult
+__rand48_seed
+__sF
+__sdidinit
+__sglue
+__stack_chk_guard
+__system_property_area__
+_ctype_
+_ns_flagdata
+_tolower_tab_
+_toupper_tab_
+daylight
+environ
+h_errlist
+h_nerr
+optarg
+opterr
+optind
+optopt
+optreset
+sys_siglist
+sys_signame
+timezone
+tzname
diff --git a/ndk/platforms/android-14/arch-x86/symbols/libc.so.functions.txt b/ndk/platforms/android-14/arch-x86/symbols/libc.so.functions.txt
new file mode 100644
index 0000000..7bcd18f
--- /dev/null
+++ b/ndk/platforms/android-14/arch-x86/symbols/libc.so.functions.txt
@@ -0,0 +1,958 @@
+MD5_Final
+MD5_Init
+MD5_Update
+SHA1Final
+SHA1Init
+SHA1Transform
+SHA1Update
+__arc4_getbyte
+__assert
+__assert2
+__atexit_register_cleanup
+__b64_ntop
+__b64_pton
+__bionic_atfork_run_child
+__bionic_atfork_run_parent
+__bionic_atfork_run_prepare
+__brk
+__cxa_atexit
+__cxa_finalize
+__divdi3
+__dn_comp
+__dn_count_labels
+__dn_skipname
+__dorand48
+__errno
+__evAddTime
+__evCmpTime
+__evConsIovec
+__evConsTime
+__evNowTime
+__evSubTime
+__evTimeSpec
+__evTimeVal
+__evUTCTime
+__fcntl
+__fcntl64
+__findenv
+__fork
+__fp_nquery
+__fp_query
+__fstatfs64
+__futex_syscall3
+__futex_syscall4
+__futex_wait
+__futex_wait_ex
+__futex_wake
+__futex_wake_ex
+__get_h_errno
+__get_res_cache
+__get_sp
+__get_stack_base
+__get_thread
+__get_tls
+__getcpu
+__getcwd
+__getpriority
+__hostalias
+__init_tls
+__ioctl
+__libc_fini
+__libc_init
+__libc_init_common
+__libc_preinit
+__llseek
+__loc_aton
+__loc_ntoa
+__mmap2
+__moddi3
+__ns_format_ttl
+__ns_get16
+__ns_get32
+__ns_initparse
+__ns_makecanon
+__ns_msg_getflag
+__ns_name_compress
+__ns_name_ntol
+__ns_name_ntop
+__ns_name_pack
+__ns_name_pton
+__ns_name_rollback
+__ns_name_skip
+__ns_name_uncompress
+__ns_name_unpack
+__ns_parserr
+__ns_put16
+__ns_put32
+__ns_samename
+__ns_skiprr
+__ns_sprintrr
+__ns_sprintrrf
+__open
+__openat
+__p_cdname
+__p_cdnname
+__p_class
+__p_fqname
+__p_fqnname
+__p_option
+__p_query
+__p_rcode
+__p_secstodate
+__p_section
+__p_sockun
+__p_time
+__p_type
+__popcountsi2
+__pthread_cleanup_pop
+__pthread_cleanup_push
+__pthread_clone
+__pthread_cond_timedwait
+__pthread_cond_timedwait_relative
+__pthread_gettid
+__ptrace
+__putlong
+__putshort
+__reboot
+__res_close
+__res_dnok
+__res_get_nibblesuffix
+__res_get_nibblesuffix2
+__res_get_state
+__res_get_static
+__res_getservers
+__res_hnok
+__res_hostalias
+__res_isourserver
+__res_mailok
+__res_nameinquery
+__res_nametoclass
+__res_nametotype
+__res_nclose
+__res_ndestroy
+__res_ninit
+__res_nmkquery
+__res_nopt
+__res_nquery
+__res_nquerydomain
+__res_nsearch
+__res_nsend
+__res_opt
+__res_ownok
+__res_pquery
+__res_put_state
+__res_queriesmatch
+__res_querydomain
+__res_randomid
+__res_send
+__res_send_setqhook
+__res_send_setrhook
+__res_setservers
+__res_vinit
+__rt_sigaction
+__rt_sigprocmask
+__rt_sigtimedwait
+__sched_cpualloc
+__sched_cpucount
+__sched_cpufree
+__sched_getaffinity
+__sclose
+__set_errno
+__set_thread_area
+__set_tls
+__setresuid
+__setreuid
+__setuid
+__sflags
+__sflush
+__sflush_locked
+__sfp
+__sigsuspend
+__sinit
+__smakebuf
+__sread
+__srefill
+__srget
+__sseek
+__stack_chk_fail
+__statfs64
+__swbuf
+__swhatbuf
+__swrite
+__swsetup
+__sym_ntop
+__sym_ntos
+__sym_ston
+__sys_clone
+__syslog
+__system_properties_init
+__system_property_find
+__system_property_find_nth
+__system_property_get
+__system_property_read
+__system_property_set
+__system_property_wait
+__thread_entry
+__timer_create
+__timer_delete
+__timer_getoverrun
+__timer_gettime
+__timer_settime
+__udivdi3
+__umoddi3
+__vfprintf
+__wait4
+__waitid
+_cache_get_nameserver_addr
+_cleanup
+_exit
+_exit_thread
+_exit_with_stack_teardown
+_fwalk
+_getlong
+_getshort
+_init_thread
+_longjmp
+_memmove_words
+_resolv_flush_cache_for_default_iface
+_resolv_flush_cache_for_iface
+_resolv_get_addr_of_default_iface
+_resolv_get_addr_of_iface
+_resolv_set_addr_of_iface
+_resolv_set_default_iface
+_resolv_set_nameservers_for_iface
+_setjmp
+_thread_created_hook
+_waitpid
+abort
+accept
+access
+acct
+alarm
+alphasort
+arc4random
+arc4random_addrandom
+arc4random_buf
+arc4random_stir
+arc4random_uniform
+asctime
+asctime64
+asctime64_r
+asctime_r
+asprintf
+atoi
+atol
+atoll
+basename
+basename_r
+bcopy
+bind
+bindresvport
+brk
+bsd_signal
+bsearch
+btowc
+bzero
+calloc
+capget
+capset
+chdir
+chmod
+chown
+chroot
+clearenv
+clearerr
+clock
+clock_getres
+clock_gettime
+clock_nanosleep
+clock_settime
+close
+closedir
+closelog
+closelog_r
+connect
+cpuacct_add
+creat
+ctime
+ctime64
+ctime64_r
+ctime_r
+daemon
+delete_module
+difftime
+dirfd
+dirname
+dirname_r
+div
+dlcalloc
+dlfree
+dlindependent_calloc
+dlindependent_comalloc
+dlmallinfo
+dlmalloc
+dlmalloc_footprint
+dlmalloc_max_footprint
+dlmalloc_stats
+dlmalloc_trim
+dlmalloc_usable_size
+dlmalloc_walk_free_pages
+dlmalloc_walk_heap
+dlmallopt
+dlmemalign
+dlpvalloc
+dlrealloc
+dlvalloc
+dn_expand
+drand48
+dup
+dup2
+endpwent
+endservent
+endusershell
+endutent
+epoll_create
+epoll_ctl
+epoll_wait
+erand48
+err
+errx
+ether_aton
+ether_aton_r
+ether_ntoa
+ether_ntoa_r
+eventfd
+eventfd_read
+eventfd_write
+execl
+execle
+execlp
+execv
+execve
+execvp
+exit
+fchdir
+fchmod
+fchmodat
+fchown
+fchownat
+fclose
+fcntl
+fdatasync
+fdopen
+fdopendir
+fdprintf
+feof
+ferror
+fflush
+fgetc
+fgetln
+fgetpos
+fgets
+fgetwc
+fgetws
+fileno
+flock
+flockfile
+fnmatch
+fopen
+fork
+fpathconf
+fprintf
+fpurge
+fputc
+fputs
+fputwc
+fputws
+fread
+free
+freeaddrinfo
+freedtoa
+freopen
+fscanf
+fseek
+fseeko
+fsetpos
+fstat
+fstatat
+fstatfs
+fsync
+ftell
+ftello
+ftime
+ftok
+ftruncate
+ftruncate64
+ftrylockfile
+fts_children
+fts_close
+fts_open
+fts_read
+fts_set
+funlockfile
+funopen
+futex
+fwide
+fwprintf
+fwrite
+fwscanf
+gai_strerror
+get_malloc_leak_info
+getaddrinfo
+getc
+getc_unlocked
+getchar
+getchar_unlocked
+getcwd
+getdents
+getdtablesize
+getegid
+getenv
+geteuid
+getgid
+getgrgid
+getgrnam
+getgrouplist
+getgroups
+gethostbyaddr
+gethostbyname
+gethostbyname2
+gethostbyname_r
+gethostent
+gethostname
+getitimer
+getlogin
+getmntent
+getnameinfo
+getnetbyaddr
+getnetbyname
+getopt
+getopt_long
+getopt_long_only
+getpeername
+getpgid
+getpgrp
+getpid
+getppid
+getpriority
+getprotobyname
+getprotobynumber
+getpt
+getpwnam
+getpwnam_r
+getpwuid
+getpwuid_r
+getresgid
+getresuid
+getrlimit
+getrusage
+gets
+getservbyname
+getservbyport
+getservent
+getservent_r
+getsockname
+getsockopt
+gettid
+gettimeofday
+getuid
+getusershell
+getutent
+getwc
+getwchar
+gmtime
+gmtime64
+gmtime64_r
+gmtime_r
+herror
+hstrerror
+if_indextoname
+if_nametoindex
+index
+inet_addr
+inet_aton
+inet_nsap_addr
+inet_nsap_ntoa
+inet_ntoa
+inet_ntop
+inet_pton
+init_module
+initgroups
+inotify_add_watch
+inotify_init
+inotify_rm_watch
+ioctl
+ioprio_get
+ioprio_set
+isalnum
+isalpha
+isascii
+isatty
+isblank
+iscntrl
+isdigit
+isgraph
+islower
+isprint
+ispunct
+issetugid
+isspace
+isupper
+iswalnum
+iswalpha
+iswcntrl
+iswctype
+iswdigit
+iswgraph
+iswlower
+iswprint
+iswpunct
+iswspace
+iswupper
+iswxdigit
+isxdigit
+jrand48
+kill
+killpg
+klogctl
+lchown
+ldexp
+ldiv
+link
+listen
+lldiv
+localtime
+localtime64
+localtime64_r
+localtime_r
+longjmp
+longjmperror
+lrand48
+lseek
+lseek64
+lstat
+madvise
+mallinfo
+malloc
+malloc_debug_init
+mbrlen
+mbrtowc
+mbsinit
+mbsrtowcs
+mbstowcs
+memalign
+memccpy
+memchr
+memcmp
+memcpy
+memmem
+memmove
+memrchr
+memset
+memswap
+mincore
+mkdir
+mkdirat
+mkdtemp
+mknod
+mkstemp
+mkstemps
+mktemp
+mktime
+mktime64
+mlock
+mmap
+mount
+mprotect
+mrand48
+mremap
+msync
+munlock
+munmap
+nanosleep
+nice
+nrand48
+nsdispatch
+open
+openat
+opendir
+openlog
+openlog_r
+pathconf
+pause
+pclose
+perror
+pipe
+pipe2
+poll
+popen
+posix2time
+prctl
+pread
+pread64
+printf
+pselect
+pthread_atfork
+pthread_attr_destroy
+pthread_attr_getdetachstate
+pthread_attr_getguardsize
+pthread_attr_getschedparam
+pthread_attr_getschedpolicy
+pthread_attr_getscope
+pthread_attr_getstack
+pthread_attr_getstackaddr
+pthread_attr_getstacksize
+pthread_attr_init
+pthread_attr_setdetachstate
+pthread_attr_setguardsize
+pthread_attr_setschedparam
+pthread_attr_setschedpolicy
+pthread_attr_setscope
+pthread_attr_setstack
+pthread_attr_setstackaddr
+pthread_attr_setstacksize
+pthread_cond_broadcast
+pthread_cond_destroy
+pthread_cond_init
+pthread_cond_signal
+pthread_cond_timedwait
+pthread_cond_timedwait_monotonic
+pthread_cond_timedwait_monotonic_np
+pthread_cond_timedwait_relative_np
+pthread_cond_timeout_np
+pthread_cond_wait
+pthread_condattr_destroy
+pthread_condattr_getpshared
+pthread_condattr_init
+pthread_condattr_setpshared
+pthread_create
+pthread_detach
+pthread_equal
+pthread_exit
+pthread_getattr_np
+pthread_getcpuclockid
+pthread_getschedparam
+pthread_getspecific
+pthread_join
+pthread_key_create
+pthread_key_delete
+pthread_kill
+pthread_mutex_destroy
+pthread_mutex_init
+pthread_mutex_lock
+pthread_mutex_lock_timeout_np
+pthread_mutex_trylock
+pthread_mutex_unlock
+pthread_mutexattr_destroy
+pthread_mutexattr_getpshared
+pthread_mutexattr_gettype
+pthread_mutexattr_init
+pthread_mutexattr_setpshared
+pthread_mutexattr_settype
+pthread_once
+pthread_rwlock_destroy
+pthread_rwlock_init
+pthread_rwlock_rdlock
+pthread_rwlock_timedrdlock
+pthread_rwlock_timedwrlock
+pthread_rwlock_tryrdlock
+pthread_rwlock_trywrlock
+pthread_rwlock_unlock
+pthread_rwlock_wrlock
+pthread_rwlockattr_destroy
+pthread_rwlockattr_getpshared
+pthread_rwlockattr_init
+pthread_rwlockattr_setpshared
+pthread_self
+pthread_setname_np
+pthread_setschedparam
+pthread_setspecific
+pthread_sigmask
+ptrace
+ptsname
+ptsname_r
+putc
+putc_unlocked
+putchar
+putchar_unlocked
+putenv
+puts
+pututline
+putw
+putwc
+putwchar
+pwrite
+pwrite64
+qsort
+raise
+read
+readdir
+readdir_r
+readlink
+readv
+realloc
+realpath
+reboot
+recv
+recvfrom
+recvmsg
+regcomp
+regerror
+regexec
+regfree
+remove
+rename
+renameat
+res_init
+res_mkquery
+res_query
+res_search
+rewind
+rewinddir
+rmdir
+sbrk
+scandir
+scanf
+sched_get_priority_max
+sched_get_priority_min
+sched_getaffinity
+sched_getcpu
+sched_getparam
+sched_getscheduler
+sched_rr_get_interval
+sched_setaffinity
+sched_setparam
+sched_setscheduler
+sched_yield
+seed48
+select
+sem_close
+sem_destroy
+sem_getvalue
+sem_init
+sem_open
+sem_post
+sem_timedwait
+sem_trywait
+sem_unlink
+sem_wait
+send
+sendfile
+sendmsg
+sendto
+setbuf
+setbuffer
+setegid
+setenv
+seteuid
+setgid
+setgroups
+setitimer
+setjmp
+setlinebuf
+setlocale
+setlogmask
+setlogmask_r
+setpgid
+setpgrp
+setpriority
+setregid
+setresgid
+setresuid
+setreuid
+setrlimit
+setservent
+setsid
+setsockopt
+settimeofday
+setuid
+setusershell
+setutent
+setvbuf
+shutdown
+sigaction
+sigaltstack
+sigblock
+siginterrupt
+siglongjmp
+sigpending
+sigprocmask
+sigsetjmp
+sigsetmask
+sigsuspend
+sigwait
+sleep
+snprintf
+socket
+socketpair
+sprintf
+srand48
+sscanf
+stat
+statfs
+strcasecmp
+strcasestr
+strcat
+strchr
+strcmp
+strcoll
+strcpy
+strcspn
+strdup
+strerror
+strerror_r
+strftime
+strftime_tz
+strlcat
+strlcpy
+strlen
+strncasecmp
+strncat
+strncmp
+strncpy
+strndup
+strnlen
+strntoimax
+strntoumax
+strpbrk
+strptime
+strrchr
+strsep
+strsignal
+strspn
+strstr
+strtod
+strtoimax
+strtok
+strtok_r
+strtol
+strtoll
+strtotimeval
+strtoul
+strtoull
+strtoumax
+strxfrm
+swprintf
+swscanf
+symlink
+sync
+syscall
+sysconf
+sysinfo
+syslog
+syslog_r
+system
+sysv_signal
+tcgetpgrp
+tcsetpgrp
+tempnam
+time
+time2posix
+timegm
+timegm64
+timelocal
+timelocal64
+timer_create
+timer_delete
+timer_getoverrun
+timer_gettime
+timer_settime
+times
+tkill
+tmpfile
+tmpnam
+toascii
+tolower
+toupper
+towlower
+towupper
+truncate
+ttyname
+ttyname_r
+tzset
+umask
+umount
+umount2
+uname
+ungetc
+ungetwc
+unlink
+unlinkat
+unlockpt
+unsetenv
+usleep
+utime
+utimensat
+utimes
+utmpname
+valloc
+vasprintf
+verr
+verrx
+vfdprintf
+vfork
+vfprintf
+vfscanf
+vfwprintf
+vprintf
+vscanf
+vsnprintf
+vsprintf
+vsscanf
+vswprintf
+vsyslog
+vsyslog_r
+vwarn
+vwarnx
+vwprintf
+wait
+wait3
+waitid
+waitpid
+warn
+warnx
+wcpcpy
+wcpncpy
+wcrtomb
+wcscasecmp
+wcscat
+wcschr
+wcscmp
+wcscoll
+wcscpy
+wcscspn
+wcsdup
+wcsftime
+wcslcat
+wcslcpy
+wcslen
+wcsncasecmp
+wcsncat
+wcsncmp
+wcsncpy
+wcsnlen
+wcspbrk
+wcsrchr
+wcsrtombs
+wcsspn
+wcsstr
+wcstod
+wcstok
+wcstol
+wcstombs
+wcstoul
+wcswcs
+wcswidth
+wcsxfrm
+wctob
+wctype
+wcwidth
+wmemchr
+wmemcmp
+wmemcpy
+wmemmove
+wmemset
+wprintf
+write
+writev
+wscanf
diff --git a/ndk/platforms/android-14/arch-x86/symbols/libc.so.variables.txt b/ndk/platforms/android-14/arch-x86/symbols/libc.so.variables.txt
new file mode 100644
index 0000000..ccc33a8
--- /dev/null
+++ b/ndk/platforms/android-14/arch-x86/symbols/libc.so.variables.txt
@@ -0,0 +1,44 @@
+_C_ctype_
+_C_tolower_
+_C_toupper_
+__atexit
+__atexit_invalid
+__bionic_brk
+__evOptMonoTime
+__isthreaded
+__libc_malloc_default_dispatch
+__libc_malloc_dispatch
+__p_cert_syms
+__p_class_syms
+__p_key_syms
+__p_rcode_syms
+__p_type_syms
+__page_shift
+__page_size
+__popcount_tab
+__progname
+__rand48_add
+__rand48_mult
+__rand48_seed
+__sF
+__sdidinit
+__sglue
+__stack_chk_guard
+__system_property_area__
+_ctype_
+_ns_flagdata
+_tolower_tab_
+_toupper_tab_
+daylight
+environ
+h_errlist
+h_nerr
+optarg
+opterr
+optind
+optopt
+optreset
+sys_siglist
+sys_signame
+timezone
+tzname
diff --git a/ndk/platforms/android-14/include/pwd.h b/ndk/platforms/android-14/include/pwd.h
new file mode 100644
index 0000000..4b94ed6
--- /dev/null
+++ b/ndk/platforms/android-14/include/pwd.h
@@ -0,0 +1,128 @@
+/*-
+ * Copyright (c) 1989, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ * (c) UNIX System Laboratories, Inc.
+ * All or some portions of this file are derived from material licensed
+ * to the University of California by American Telephone and Telegraph
+ * Co. or Unix System Laboratories, Inc. and are reproduced herein with
+ * the permission of UNIX System Laboratories, Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ *	@(#)pwd.h	8.2 (Berkeley) 1/21/94
+ */
+
+/*-
+ * Portions Copyright(C) 1995, Jason Downs.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT,
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#ifndef _PWD_H_
+#define _PWD_H_
+
+#include <sys/cdefs.h>
+#include <sys/types.h>
+
+#define _PATH_PASSWD        "/etc/passwd"
+#define _PATH_MASTERPASSWD  "/etc/master.passwd"
+#define _PATH_MASTERPASSWD_LOCK "/etc/ptmp"
+
+#define _PATH_PASSWD_CONF   "/etc/passwd.conf"
+#define _PATH_PASSWDCONF    _PATH_PASSWD_CONF   /* XXX: compat */
+#define _PATH_USERMGMT_CONF "/etc/usermgmt.conf"
+
+#define _PATH_MP_DB     "/etc/pwd.db"
+#define _PATH_SMP_DB        "/etc/spwd.db"
+
+#define _PATH_PWD_MKDB      "/usr/sbin/pwd_mkdb"
+
+#define _PW_KEYBYNAME       '1' /* stored by name */
+#define _PW_KEYBYNUM        '2' /* stored by entry in the "file" */
+#define _PW_KEYBYUID        '3' /* stored by uid */
+
+#define _PASSWORD_EFMT1     '_' /* extended DES encryption format */
+#define _PASSWORD_NONDES    '$' /* non-DES encryption formats */
+
+#define _PASSWORD_LEN       128 /* max length, not counting NUL */
+
+#define _PASSWORD_NOUID     0x01    /* flag for no specified uid. */
+#define _PASSWORD_NOGID     0x02    /* flag for no specified gid. */
+#define _PASSWORD_NOCHG     0x04    /* flag for no specified change. */
+#define _PASSWORD_NOEXP     0x08    /* flag for no specified expire. */
+
+#define _PASSWORD_OLDFMT    0x10    /* flag to expect an old style entry */
+#define _PASSWORD_NOWARN    0x20    /* no warnings for bad entries */
+
+#define _PASSWORD_WARNDAYS  14  /* days to warn about expiry */
+#define _PASSWORD_CHGNOW    -1  /* special day to force password change at next login */
+
+struct passwd
+{
+    char* pw_name;
+    char* pw_passwd;
+    uid_t pw_uid;
+    gid_t pw_gid;
+    char* pw_dir;
+    char* pw_shell;
+};
+
+__BEGIN_DECLS
+
+struct passwd* getpwnam(const char*);
+struct passwd* getpwuid(uid_t);
+
+int getpwnam_r(const char*, struct passwd*, char*, size_t, struct passwd**);
+int getpwuid_r(uid_t, struct passwd*, char*, size_t, struct passwd**);
+
+void endpwent(void);
+
+#if 0 /* MISSING FROM BIONIC */
+struct passwd* getpwent(void);
+int setpwent(void);
+#endif /* MISSING */
+
+__END_DECLS
+
+#endif
diff --git a/ndk/platforms/android-14/samples/native-media/AndroidManifest.xml b/ndk/platforms/android-14/samples/native-media/AndroidManifest.xml
new file mode 100644
index 0000000..07668cf
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/AndroidManifest.xml
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="utf-8"?>
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+      package="com.example.nativemedia">
+
+    <uses-feature android:glEsVersion="0x00020000" />
+
+    <application android:icon="@drawable/icon" android:label="@string/app_name">
+        <activity android:name=".NativeMedia"
+                  android:label="@string/app_name">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="android.intent.category.LAUNCHER" />
+            </intent-filter>
+        </activity>
+
+    </application>
+
+    <uses-sdk android:minSdkVersion="14" />
+
+    <!-- INTERNET is needed to use a URI-based media player, depending on the URI -->
+    <uses-permission android:name="android.permission.INTERNET"></uses-permission>
+
+</manifest>
diff --git a/ndk/platforms/android-14/samples/native-media/NativeMedia.ts b/ndk/platforms/android-14/samples/native-media/NativeMedia.ts
new file mode 100644
index 0000000..d9d54b2
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/NativeMedia.ts
Binary files differ
diff --git a/ndk/platforms/android-14/samples/native-media/README.txt b/ndk/platforms/android-14/samples/native-media/README.txt
index 516698a..f900e31 100644
--- a/ndk/platforms/android-14/samples/native-media/README.txt
+++ b/ndk/platforms/android-14/samples/native-media/README.txt
@@ -1,2 +1,8 @@
-The documentation for Android native media based on OpenMAX AL 1.0.1
-references this directory, but the example is not yet available.
+This sample app requires an MPEG-2 Transport Stream file to be
+placed in /sdcard/NativeMedia.ts and encoded as:
+
+  video: H.264 baseline profile
+  audio: AAC LC stereo
+
+For demonstration purposes we have supplied such a .ts file.
+Any actual stream must be created according to the MPEG-2 specification.
diff --git a/ndk/platforms/android-14/samples/native-media/default.properties b/ndk/platforms/android-14/samples/native-media/default.properties
new file mode 100644
index 0000000..2d69917
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/default.properties
@@ -0,0 +1,4 @@
+# Indicates whether an apk should be generated for each density.
+split.density=false
+# Project target.
+target=android-14
diff --git a/ndk/platforms/android-14/samples/native-media/jni/Android.mk b/ndk/platforms/android-14/samples/native-media/jni/Android.mk
new file mode 100644
index 0000000..369ccf8
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/jni/Android.mk
@@ -0,0 +1,30 @@
+# Copyright (C) 2011 The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#      http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+LOCAL_PATH := $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_MODULE    := native-media-jni
+LOCAL_SRC_FILES := native-media-jni.c
+# for native multimedia
+LOCAL_LDLIBS    += -lOpenMAXAL
+# for logging
+LOCAL_LDLIBS    += -llog
+# for native windows
+LOCAL_LDLIBS    += -landroid
+
+LOCAL_CFLAGS    += -UNDEBUG
+
+include $(BUILD_SHARED_LIBRARY)
diff --git a/ndk/platforms/android-14/samples/native-media/jni/native-media-jni.c b/ndk/platforms/android-14/samples/native-media/jni/native-media-jni.c
new file mode 100644
index 0000000..bdf568a
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/jni/native-media-jni.c
@@ -0,0 +1,526 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* This is a JNI example where we use native methods to play video
+ * using OpenMAX AL. See the corresponding Java source file located at:
+ *
+ *   src/com/example/nativemedia/NativeMedia/NativeMedia.java
+ *
+ * In this example we use assert() for "impossible" error conditions,
+ * and explicit handling and recovery for more likely error conditions.
+ */
+
+#include <assert.h>
+#include <jni.h>
+#include <pthread.h>
+#include <stdio.h>
+#include <string.h>
+
+// for __android_log_print(ANDROID_LOG_INFO, "YourApp", "formatted message");
+#include <android/log.h>
+#define TAG "NativeMedia"
+#define LOGV(...) __android_log_print(ANDROID_LOG_VERBOSE, TAG, __VA_ARGS__)
+
+// for native media
+#include <OMXAL/OpenMAXAL.h>
+#include <OMXAL/OpenMAXAL_Android.h>
+
+// for native window JNI
+#include <android/native_window_jni.h>
+
+// engine interfaces
+static XAObjectItf engineObject = NULL;
+static XAEngineItf engineEngine = NULL;
+
+// output mix interfaces
+static XAObjectItf outputMixObject = NULL;
+
+// streaming media player interfaces
+static XAObjectItf             playerObj = NULL;
+static XAPlayItf               playerPlayItf = NULL;
+static XAAndroidBufferQueueItf playerBQItf = NULL;
+static XAStreamInformationItf  playerStreamInfoItf = NULL;
+static XAVolumeItf             playerVolItf = NULL;
+
+// number of required interfaces for the MediaPlayer creation
+#define NB_MAXAL_INTERFACES 3 // XAAndroidBufferQueueItf, XAStreamInformationItf and XAPlayItf
+
+// video sink for the player
+static ANativeWindow* theNativeWindow;
+
+// number of buffers in our buffer queue, an arbitrary number
+#define NB_BUFFERS 8
+
+// we're streaming MPEG-2 transport stream data, operate on transport stream block size
+#define MPEG2_TS_PACKET_SIZE 188
+
+// number of MPEG-2 transport stream blocks per buffer, an arbitrary number
+#define PACKETS_PER_BUFFER 10
+
+// determines how much memory we're dedicating to memory caching
+#define BUFFER_SIZE (PACKETS_PER_BUFFER*MPEG2_TS_PACKET_SIZE)
+
+// where we cache in memory the data to play
+// note this memory is re-used by the buffer queue callback
+static char dataCache[BUFFER_SIZE * NB_BUFFERS];
+
+// handle of the file to play
+static FILE *file;
+
+// has the app reached the end of the file
+static jboolean reachedEof = JNI_FALSE;
+
+// constant to identify a buffer context which is the end of the stream to decode
+static const int kEosBufferCntxt = 1980; // a magic value we can compare against
+
+// For mutual exclusion between callback thread and application thread(s).
+// The mutex protects reachedEof, discontinuity,
+// The condition is signalled when a discontinuity is acknowledged.
+
+static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
+static pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
+
+// whether a discontinuity is in progress
+static jboolean discontinuity = JNI_FALSE;
+
+static jboolean enqueueInitialBuffers(jboolean discontinuity);
+
+// AndroidBufferQueueItf callback to supply MPEG-2 TS packets to the media player
+static XAresult AndroidBufferQueueCallback(
+        XAAndroidBufferQueueItf caller,
+        void *pCallbackContext,        /* input */
+        void *pBufferContext,          /* input */
+        void *pBufferData,             /* input */
+        XAuint32 dataSize,             /* input */
+        XAuint32 dataUsed,             /* input */
+        const XAAndroidBufferItem *pItems,/* input */
+        XAuint32 itemsLength           /* input */)
+{
+    XAresult res;
+    int ok;
+
+    // pCallbackContext was specified as NULL at RegisterCallback and is unused here
+    assert(NULL == pCallbackContext);
+
+    // note there is never any contention on this mutex unless a discontinuity request is active
+    ok = pthread_mutex_lock(&mutex);
+    assert(0 == ok);
+
+    // was a discontinuity requested?
+    if (discontinuity) {
+        // Note: can't rewind after EOS, which we send when reaching EOF
+        // (don't send EOS if you plan to play more content through the same player)
+        if (!reachedEof) {
+            // clear the buffer queue
+            res = (*playerBQItf)->Clear(playerBQItf);
+            assert(XA_RESULT_SUCCESS == res);
+            // rewind the data source so we are guaranteed to be at an appropriate point
+            rewind(file);
+            // Enqueue the initial buffers, with a discontinuity indicator on first buffer
+            (void) enqueueInitialBuffers(JNI_TRUE);
+        }
+        // acknowledge the discontinuity request
+        discontinuity = JNI_FALSE;
+        ok = pthread_cond_signal(&cond);
+        assert(0 == ok);
+        goto exit;
+    }
+
+    if ((pBufferData == NULL) && (pBufferContext != NULL)) {
+        const int processedCommand = *(int *)pBufferContext;
+        if (kEosBufferCntxt == processedCommand) {
+            LOGV("EOS was processed\n");
+            // our buffer with the EOS message has been consumed
+            assert(0 == dataSize);
+            goto exit;
+        }
+    }
+
+    // pBufferData is a pointer to a buffer that we previously Enqueued
+    assert((dataSize > 0) && ((dataSize % MPEG2_TS_PACKET_SIZE) == 0));
+    assert(dataCache <= (char *) pBufferData && (char *) pBufferData <
+            &dataCache[BUFFER_SIZE * NB_BUFFERS]);
+    assert(0 == (((char *) pBufferData - dataCache) % BUFFER_SIZE));
+
+    // don't bother trying to read more data once we've hit EOF
+    if (reachedEof) {
+        goto exit;
+    }
+
+    size_t nbRead;
+    // note we do call fread from multiple threads, but never concurrently
+    size_t bytesRead;
+    bytesRead = fread(pBufferData, 1, BUFFER_SIZE, file);
+    if (bytesRead > 0) {
+        if ((bytesRead % MPEG2_TS_PACKET_SIZE) != 0) {
+            LOGV("Dropping last packet because it is not whole");
+        }
+        size_t packetsRead = bytesRead / MPEG2_TS_PACKET_SIZE;
+        size_t bufferSize = packetsRead * MPEG2_TS_PACKET_SIZE;
+        res = (*caller)->Enqueue(caller, NULL /*pBufferContext*/,
+                pBufferData /*pData*/,
+                bufferSize /*dataLength*/,
+                NULL /*pMsg*/,
+                0 /*msgLength*/);
+        assert(XA_RESULT_SUCCESS == res);
+    } else {
+        // EOF or I/O error, signal EOS
+        XAAndroidBufferItem msgEos[1];
+        msgEos[0].itemKey = XA_ANDROID_ITEMKEY_EOS;
+        msgEos[0].itemSize = 0;
+        // EOS message has no parameters, so the total size of the message is the size of the key
+        //   plus the size if itemSize, both XAuint32
+        res = (*caller)->Enqueue(caller, (void *)&kEosBufferCntxt /*pBufferContext*/,
+                NULL /*pData*/, 0 /*dataLength*/,
+                msgEos /*pMsg*/,
+                sizeof(XAuint32)*2 /*msgLength*/);
+        assert(XA_RESULT_SUCCESS == res);
+        reachedEof = JNI_TRUE;
+    }
+
+exit:
+    ok = pthread_mutex_unlock(&mutex);
+    assert(0 == ok);
+    return XA_RESULT_SUCCESS;
+}
+
+
+// callback invoked whenever there is new or changed stream information
+static void StreamChangeCallback(XAStreamInformationItf caller,
+        XAuint32 eventId,
+        XAuint32 streamIndex,
+        void * pEventData,
+        void * pContext )
+{
+    LOGV("StreamChangeCallback called for stream %u", streamIndex);
+    // pContext was specified as NULL at RegisterStreamChangeCallback and is unused here
+    assert(NULL == pContext);
+    switch (eventId) {
+      case XA_STREAMCBEVENT_PROPERTYCHANGE: {
+        /** From spec 1.0.1:
+            "This event indicates that stream property change has occurred.
+            The streamIndex parameter identifies the stream with the property change.
+            The pEventData parameter for this event is not used and shall be ignored."
+         */
+
+        XAresult res;
+        XAuint32 domain;
+        res = (*caller)->QueryStreamType(caller, streamIndex, &domain);
+        assert(XA_RESULT_SUCCESS == res);
+        switch (domain) {
+          case XA_DOMAINTYPE_VIDEO: {
+            XAVideoStreamInformation videoInfo;
+            res = (*caller)->QueryStreamInformation(caller, streamIndex, &videoInfo);
+            assert(XA_RESULT_SUCCESS == res);
+            LOGV("Found video size %u x %u, codec ID=%u, frameRate=%u, bitRate=%u, duration=%u ms",
+                        videoInfo.width, videoInfo.height, videoInfo.codecId, videoInfo.frameRate,
+                        videoInfo.bitRate, videoInfo.duration);
+          } break;
+          default:
+            fprintf(stderr, "Unexpected domain %u\n", domain);
+            break;
+        }
+      } break;
+      default:
+        fprintf(stderr, "Unexpected stream event ID %u\n", eventId);
+        break;
+    }
+}
+
+
+// create the engine and output mix objects
+void Java_com_example_nativemedia_NativeMedia_createEngine(JNIEnv* env, jclass clazz)
+{
+    XAresult res;
+
+    // create engine
+    res = xaCreateEngine(&engineObject, 0, NULL, 0, NULL, NULL);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // realize the engine
+    res = (*engineObject)->Realize(engineObject, XA_BOOLEAN_FALSE);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // get the engine interface, which is needed in order to create other objects
+    res = (*engineObject)->GetInterface(engineObject, XA_IID_ENGINE, &engineEngine);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // create output mix
+    res = (*engineEngine)->CreateOutputMix(engineEngine, &outputMixObject, 0, NULL, NULL);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // realize the output mix
+    res = (*outputMixObject)->Realize(outputMixObject, XA_BOOLEAN_FALSE);
+    assert(XA_RESULT_SUCCESS == res);
+
+}
+
+
+// Enqueue the initial buffers, and optionally signal a discontinuity in the first buffer
+static jboolean enqueueInitialBuffers(jboolean discontinuity)
+{
+
+    /* Fill our cache.
+     * We want to read whole packets (integral multiples of MPEG2_TS_PACKET_SIZE).
+     * fread returns units of "elements" not bytes, so we ask for 1-byte elements
+     * and then check that the number of elements is a multiple of the packet size.
+     */
+    size_t bytesRead;
+    bytesRead = fread(dataCache, 1, BUFFER_SIZE * NB_BUFFERS, file);
+    if (bytesRead <= 0) {
+        // could be premature EOF or I/O error
+        return JNI_FALSE;
+    }
+    if ((bytesRead % MPEG2_TS_PACKET_SIZE) != 0) {
+        LOGV("Dropping last packet because it is not whole");
+    }
+    size_t packetsRead = bytesRead / MPEG2_TS_PACKET_SIZE;
+    LOGV("Initially queueing %u packets", packetsRead);
+
+    /* Enqueue the content of our cache before starting to play,
+       we don't want to starve the player */
+    size_t i;
+    for (i = 0; i < NB_BUFFERS && packetsRead > 0; i++) {
+        // compute size of this buffer
+        size_t packetsThisBuffer = packetsRead;
+        if (packetsThisBuffer > PACKETS_PER_BUFFER) {
+            packetsThisBuffer = PACKETS_PER_BUFFER;
+        }
+        size_t bufferSize = packetsThisBuffer * MPEG2_TS_PACKET_SIZE;
+        XAresult res;
+        if (discontinuity) {
+            // signal discontinuity
+            XAAndroidBufferItem items[1];
+            items[0].itemKey = XA_ANDROID_ITEMKEY_DISCONTINUITY;
+            items[0].itemSize = 0;
+            // DISCONTINUITY message has no parameters,
+            //   so the total size of the message is the size of the key
+            //   plus the size if itemSize, both XAuint32
+            res = (*playerBQItf)->Enqueue(playerBQItf, NULL /*pBufferContext*/,
+                    dataCache + i*BUFFER_SIZE, bufferSize, items /*pMsg*/,
+                    sizeof(XAuint32)*2 /*msgLength*/);
+            discontinuity = JNI_FALSE;
+        } else {
+            res = (*playerBQItf)->Enqueue(playerBQItf, NULL /*pBufferContext*/,
+                    dataCache + i*BUFFER_SIZE, bufferSize, NULL, 0);
+        }
+        assert(XA_RESULT_SUCCESS == res);
+        packetsRead -= packetsThisBuffer;
+    }
+
+    return JNI_TRUE;
+}
+
+
+// create streaming media player
+jboolean Java_com_example_nativemedia_NativeMedia_createStreamingMediaPlayer(JNIEnv* env,
+        jclass clazz, jstring filename)
+{
+    XAresult res;
+
+    // convert Java string to UTF-8
+    const char *utf8 = (*env)->GetStringUTFChars(env, filename, NULL);
+    assert(NULL != utf8);
+
+    // open the file to play
+    file = fopen(utf8, "rb");
+    if (file == NULL) {
+        return JNI_FALSE;
+    }
+
+    // configure data source
+    XADataLocator_AndroidBufferQueue loc_abq = { XA_DATALOCATOR_ANDROIDBUFFERQUEUE, NB_BUFFERS };
+    XADataFormat_MIME format_mime = {
+            XA_DATAFORMAT_MIME, XA_ANDROID_MIME_MP2TS, XA_CONTAINERTYPE_MPEG_TS };
+    XADataSource dataSrc = {&loc_abq, &format_mime};
+
+    // configure audio sink
+    XADataLocator_OutputMix loc_outmix = { XA_DATALOCATOR_OUTPUTMIX, outputMixObject };
+    XADataSink audioSnk = { &loc_outmix, NULL };
+
+    // configure image video sink
+    XADataLocator_NativeDisplay loc_nd = {
+            XA_DATALOCATOR_NATIVEDISPLAY,        // locatorType
+            // the video sink must be an ANativeWindow created from a Surface or SurfaceTexture
+            (void*)theNativeWindow,              // hWindow
+            // must be NULL
+            NULL                                 // hDisplay
+    };
+    XADataSink imageVideoSink = {&loc_nd, NULL};
+
+    // declare interfaces to use
+    XAboolean     required[NB_MAXAL_INTERFACES]
+                           = {XA_BOOLEAN_TRUE, XA_BOOLEAN_TRUE,           XA_BOOLEAN_TRUE};
+    XAInterfaceID iidArray[NB_MAXAL_INTERFACES]
+                           = {XA_IID_PLAY,     XA_IID_ANDROIDBUFFERQUEUESOURCE,
+                                               XA_IID_STREAMINFORMATION};
+
+    // create media player
+    res = (*engineEngine)->CreateMediaPlayer(engineEngine, &playerObj, &dataSrc,
+            NULL, &audioSnk, &imageVideoSink, NULL, NULL,
+            NB_MAXAL_INTERFACES /*XAuint32 numInterfaces*/,
+            iidArray /*const XAInterfaceID *pInterfaceIds*/,
+            required /*const XAboolean *pInterfaceRequired*/);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // release the Java string and UTF-8
+    (*env)->ReleaseStringUTFChars(env, filename, utf8);
+
+    // realize the player
+    res = (*playerObj)->Realize(playerObj, XA_BOOLEAN_FALSE);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // get the play interface
+    res = (*playerObj)->GetInterface(playerObj, XA_IID_PLAY, &playerPlayItf);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // get the stream information interface (for video size)
+    res = (*playerObj)->GetInterface(playerObj, XA_IID_STREAMINFORMATION, &playerStreamInfoItf);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // get the volume interface
+    res = (*playerObj)->GetInterface(playerObj, XA_IID_VOLUME, &playerVolItf);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // get the Android buffer queue interface
+    res = (*playerObj)->GetInterface(playerObj, XA_IID_ANDROIDBUFFERQUEUESOURCE, &playerBQItf);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // specify which events we want to be notified of
+    res = (*playerBQItf)->SetCallbackEventsMask(playerBQItf, XA_ANDROIDBUFFERQUEUEEVENT_PROCESSED);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // register the callback from which OpenMAX AL can retrieve the data to play
+    res = (*playerBQItf)->RegisterCallback(playerBQItf, AndroidBufferQueueCallback, NULL);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // we want to be notified of the video size once it's found, so we register a callback for that
+    res = (*playerStreamInfoItf)->RegisterStreamChangeCallback(playerStreamInfoItf,
+            StreamChangeCallback, NULL);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // enqueue the initial buffers
+    if (!enqueueInitialBuffers(JNI_FALSE)) {
+        return JNI_FALSE;
+    }
+
+    // prepare the player
+    res = (*playerPlayItf)->SetPlayState(playerPlayItf, XA_PLAYSTATE_PAUSED);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // set the volume
+    res = (*playerVolItf)->SetVolumeLevel(playerVolItf, 0);
+    assert(XA_RESULT_SUCCESS == res);
+
+    // start the playback
+    res = (*playerPlayItf)->SetPlayState(playerPlayItf, XA_PLAYSTATE_PLAYING);
+        assert(XA_RESULT_SUCCESS == res);
+
+    return JNI_TRUE;
+}
+
+
+// set the playing state for the streaming media player
+void Java_com_example_nativemedia_NativeMedia_setPlayingStreamingMediaPlayer(JNIEnv* env,
+        jclass clazz, jboolean isPlaying)
+{
+    XAresult res;
+
+    // make sure the streaming media player was created
+    if (NULL != playerPlayItf) {
+
+        // set the player's state
+        res = (*playerPlayItf)->SetPlayState(playerPlayItf, isPlaying ?
+            XA_PLAYSTATE_PLAYING : XA_PLAYSTATE_PAUSED);
+        assert(XA_RESULT_SUCCESS == res);
+
+    }
+
+}
+
+
+// shut down the native media system
+void Java_com_example_nativemedia_NativeMedia_shutdown(JNIEnv* env, jclass clazz)
+{
+    // destroy streaming media player object, and invalidate all associated interfaces
+    if (playerObj != NULL) {
+        (*playerObj)->Destroy(playerObj);
+        playerObj = NULL;
+        playerPlayItf = NULL;
+        playerBQItf = NULL;
+        playerStreamInfoItf = NULL;
+        playerVolItf = NULL;
+    }
+
+    // destroy output mix object, and invalidate all associated interfaces
+    if (outputMixObject != NULL) {
+        (*outputMixObject)->Destroy(outputMixObject);
+        outputMixObject = NULL;
+    }
+
+    // destroy engine object, and invalidate all associated interfaces
+    if (engineObject != NULL) {
+        (*engineObject)->Destroy(engineObject);
+        engineObject = NULL;
+        engineEngine = NULL;
+    }
+
+    // close the file
+    if (file != NULL) {
+        fclose(file);
+        file = NULL;
+    }
+
+    // make sure we don't leak native windows
+    if (theNativeWindow != NULL) {
+        ANativeWindow_release(theNativeWindow);
+        theNativeWindow = NULL;
+    }
+}
+
+
+// set the surface
+void Java_com_example_nativemedia_NativeMedia_setSurface(JNIEnv *env, jclass clazz, jobject surface)
+{
+    // obtain a native window from a Java surface
+    theNativeWindow = ANativeWindow_fromSurface(env, surface);
+}
+
+
+// rewind the streaming media player
+void Java_com_example_nativemedia_NativeMedia_rewindStreamingMediaPlayer(JNIEnv *env, jclass clazz)
+{
+    XAresult res;
+
+    // make sure the streaming media player was created
+    if (NULL != playerBQItf && NULL != file) {
+        // first wait for buffers currently in queue to be drained
+        int ok;
+        ok = pthread_mutex_lock(&mutex);
+        assert(0 == ok);
+        discontinuity = JNI_TRUE;
+        // wait for discontinuity request to be observed by buffer queue callback
+        // Note: can't rewind after EOS, which we send when reaching EOF
+        // (don't send EOS if you plan to play more content through the same player)
+        while (discontinuity && !reachedEof) {
+            ok = pthread_cond_wait(&cond, &mutex);
+            assert(0 == ok);
+        }
+        ok = pthread_mutex_unlock(&mutex);
+        assert(0 == ok);
+    }
+
+}
diff --git a/ndk/platforms/android-14/samples/native-media/project.properties b/ndk/platforms/android-14/samples/native-media/project.properties
new file mode 100644
index 0000000..8f51418
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/project.properties
@@ -0,0 +1,13 @@
+# This file is automatically generated by Android Tools.
+# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
+#
+# This file must be checked in Version Control Systems.
+#
+# To customize properties used by the Ant build system use,
+# "ant.properties", and override values to adapt the script to your
+# project structure.
+
+# Indicates whether an apk should be generated for each density.
+split.density=false
+# Project target.
+target=android-14
diff --git a/ndk/platforms/android-14/samples/native-media/res/drawable/icon.png b/ndk/platforms/android-14/samples/native-media/res/drawable/icon.png
new file mode 100644
index 0000000..a07c69f
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/res/drawable/icon.png
Binary files differ
diff --git a/ndk/platforms/android-14/samples/native-media/res/layout/main.xml b/ndk/platforms/android-14/samples/native-media/res/layout/main.xml
new file mode 100644
index 0000000..0e41339
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/res/layout/main.xml
@@ -0,0 +1,133 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:orientation="vertical"
+    android:layout_width="fill_parent"
+    android:layout_height="fill_parent"
+    >
+<TextView
+    android:layout_width="fill_parent"
+    android:layout_height="wrap_content"
+    android:text="@string/hello"
+    />
+<TextView
+    android:layout_width="fill_parent"
+    android:layout_height="wrap_content"
+    android:text="@string/source_select"
+    />
+<Spinner
+    android:id="@+id/source_spinner"
+    android:layout_width="fill_parent"
+    android:layout_height="wrap_content"
+    android:text="@string/source_prompt"
+    />
+<TextView
+    android:layout_width="fill_parent"
+    android:layout_height="wrap_content"
+    android:text="@string/sink_select"
+    />
+<Spinner
+    android:id="@+id/sink_spinner"
+    android:layout_width="fill_parent"
+    android:layout_height="wrap_content"
+    android:text="@string/sink_prompt"
+    />
+
+<LinearLayout
+    android:orientation="horizontal"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    >
+    <Button
+        android:id="@+id/start_java"
+        android:text="@string/start_java"
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        />
+    <Button
+        android:id="@+id/start_native"
+        android:text="@string/start_native"
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        />
+    <Button
+        android:id="@+id/finish"
+        android:text="@string/finish"
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        />
+</LinearLayout>
+
+<LinearLayout
+    android:orientation="horizontal"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    >
+    <Button
+        android:id="@+id/rewind_java"
+        android:text="@string/rewind_java"
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        />
+    <Button
+        android:id="@+id/rewind_native"
+        android:text="@string/rewind_native"
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        />
+</LinearLayout>
+
+<LinearLayout
+    android:orientation="horizontal"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    >
+    <TextView
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        android:text="S1"
+        />
+    <SurfaceView
+        android:id="@+id/surfaceview1"
+        android:layout_width="320px"
+        android:layout_height="240px"
+        />
+    <TextView
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        android:text="S2"
+        />
+    <SurfaceView
+        android:id="@+id/surfaceview2"
+        android:layout_width="400px"
+        android:layout_height="224px"
+        />
+</LinearLayout>
+
+<LinearLayout
+    android:orientation="horizontal"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    >
+    <TextView
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        android:text="ST1"
+        />
+    <com.example.nativemedia.MyGLSurfaceView
+        android:id="@+id/glsurfaceview1"
+        android:layout_width="320px"
+        android:layout_height="240px"
+        />
+    <TextView
+        android:layout_width="fill_parent"
+        android:layout_height="wrap_content"
+        android:text="ST2"
+        />
+    <com.example.nativemedia.MyGLSurfaceView
+        android:id="@+id/glsurfaceview2"
+        android:layout_width="320px"
+        android:layout_height="240px"
+        />
+</LinearLayout>
+
+</LinearLayout>
diff --git a/ndk/platforms/android-14/samples/native-media/res/values/strings.xml b/ndk/platforms/android-14/samples/native-media/res/values/strings.xml
new file mode 100644
index 0000000..32a9a8e
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/res/values/strings.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="utf-8"?>
+<resources>
+    <string name="hello">Hello, Android, using native media!</string>
+    <string name="app_name">NativeMedia</string>
+
+    <string name="start_java">Start/Pause\nJava MediaPlayer</string>
+    <string name="start_native">Start/Pause\nnative MediaPlayer</string>
+    <string name="finish">Finish</string>
+
+    <string name="rewind_java">Rewind\nJava MediaPlayer</string>
+    <string name="rewind_native">Rewind\nnative MediaPlayer</string>
+
+    <string name="source_select">Please select the media source</string>
+    <string name="source_prompt">Media source</string>
+    <string-array name="source_array">
+        <item>/sdcard/NativeMedia.ts</item>
+    </string-array>
+
+    <string name="sink_select">Please select the video sink</string>
+    <string name="sink_prompt">Video sink</string>
+    <string-array name="sink_array">
+        <item>Surface 1</item>
+        <item>Surface 2</item>
+        <item>SurfaceTexture 1</item>
+        <item>SurfaceTexture 2</item>
+    </string-array>
+
+</resources>
diff --git a/ndk/platforms/android-14/samples/native-media/src/com/example/nativemedia/MyGLSurfaceView.java b/ndk/platforms/android-14/samples/native-media/src/com/example/nativemedia/MyGLSurfaceView.java
new file mode 100644
index 0000000..39a7ecf
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/src/com/example/nativemedia/MyGLSurfaceView.java
@@ -0,0 +1,336 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.nativemedia;
+
+import android.graphics.SurfaceTexture;
+import android.util.Log;
+
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.FloatBuffer;
+
+import javax.microedition.khronos.egl.EGLConfig;
+import javax.microedition.khronos.opengles.GL10;
+
+import android.content.Context;
+
+import android.opengl.GLES20;
+import android.opengl.GLSurfaceView;
+import android.opengl.Matrix;
+
+import android.util.AttributeSet;
+
+public class MyGLSurfaceView extends GLSurfaceView {
+
+    MyRenderer mRenderer;
+
+    public MyGLSurfaceView(Context context) {
+        this(context, null);
+    }
+
+    public MyGLSurfaceView(Context context, AttributeSet attributeSet) {
+        super(context, attributeSet);
+        init();
+    }
+
+    private void init() {
+        setEGLContextClientVersion(2);
+        mRenderer = new MyRenderer();
+        setRenderer(mRenderer);
+    }
+
+    @Override
+    public void onPause() {
+        super.onPause();
+    }
+
+    @Override
+    public void onResume() {
+        super.onResume();
+    }
+
+    public SurfaceTexture getSurfaceTexture() {
+        return mRenderer.getSurfaceTexture();
+    }
+}
+
+class MyRenderer implements GLSurfaceView.Renderer, SurfaceTexture.OnFrameAvailableListener {
+
+    public MyRenderer() {
+        mVertices = ByteBuffer.allocateDirect(mVerticesData.length
+                * FLOAT_SIZE_BYTES).order(ByteOrder.nativeOrder()).asFloatBuffer();
+        mVertices.put(mVerticesData).position(0);
+
+        Matrix.setIdentityM(mSTMatrix, 0);
+        Matrix.setIdentityM(mMMatrix, 0);
+        Matrix.rotateM(mMMatrix, 0, 20, 0, 1, 0);
+    }
+
+    public void onDrawFrame(GL10 glUnused) {
+        synchronized(this) {
+            if (updateSurface) {
+                mSurface.updateTexImage();
+
+                mSurface.getTransformMatrix(mSTMatrix);
+                updateSurface = false;
+            }
+        }
+
+        // Ignore the passed-in GL10 interface, and use the GLES20
+        // class's static methods instead.
+        GLES20.glClear( GLES20.GL_DEPTH_BUFFER_BIT | GLES20.GL_COLOR_BUFFER_BIT);
+        GLES20.glUseProgram(mProgram);
+        checkGlError("glUseProgram");
+
+        GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
+        GLES20.glBindTexture(GL_TEXTURE_EXTERNAL_OES, mTextureID);
+
+        mVertices.position(VERTICES_DATA_POS_OFFSET);
+        GLES20.glVertexAttribPointer(maPositionHandle, 3, GLES20.GL_FLOAT, false,
+                VERTICES_DATA_STRIDE_BYTES, mVertices);
+        checkGlError("glVertexAttribPointer maPosition");
+        GLES20.glEnableVertexAttribArray(maPositionHandle);
+        checkGlError("glEnableVertexAttribArray maPositionHandle");
+
+        mVertices.position(VERTICES_DATA_UV_OFFSET);
+        GLES20.glVertexAttribPointer(maTextureHandle, 3, GLES20.GL_FLOAT, false,
+                VERTICES_DATA_STRIDE_BYTES, mVertices);
+        checkGlError("glVertexAttribPointer maTextureHandle");
+        GLES20.glEnableVertexAttribArray(maTextureHandle);
+        checkGlError("glEnableVertexAttribArray maTextureHandle");
+
+        Matrix.multiplyMM(mMVPMatrix, 0, mVMatrix, 0, mMMatrix, 0);
+        Matrix.multiplyMM(mMVPMatrix, 0, mProjMatrix, 0, mMVPMatrix, 0);
+
+        GLES20.glUniformMatrix4fv(muMVPMatrixHandle, 1, false, mMVPMatrix, 0);
+        GLES20.glUniformMatrix4fv(muSTMatrixHandle, 1, false, mSTMatrix, 0);
+
+        GLES20.glDrawArrays(GLES20.GL_TRIANGLE_STRIP, 0, 4);
+        checkGlError("glDrawArrays");
+    }
+
+    public void onSurfaceChanged(GL10 glUnused, int width, int height) {
+        // Ignore the passed-in GL10 interface, and use the GLES20
+        // class's static methods instead.
+        GLES20.glViewport(0, 0, width, height);
+        mRatio = (float) width / height;
+        Matrix.frustumM(mProjMatrix, 0, -mRatio, mRatio, -1, 1, 3, 7);
+    }
+
+    public void onSurfaceCreated(GL10 glUnused, EGLConfig config) {
+        // Ignore the passed-in GL10 interface, and use the GLES20
+        // class's static methods instead.
+
+        /* Set up alpha blending and an Android background color */
+        GLES20.glEnable(GLES20.GL_BLEND);
+        GLES20.glBlendFunc(GLES20.GL_SRC_ALPHA, GLES20.GL_ONE_MINUS_SRC_ALPHA);
+        GLES20.glClearColor(0.643f, 0.776f, 0.223f, 1.0f);
+
+        /* Set up shaders and handles to their variables */
+        mProgram = createProgram(mVertexShader, mFragmentShader);
+        if (mProgram == 0) {
+            return;
+        }
+        maPositionHandle = GLES20.glGetAttribLocation(mProgram, "aPosition");
+        checkGlError("glGetAttribLocation aPosition");
+        if (maPositionHandle == -1) {
+            throw new RuntimeException("Could not get attrib location for aPosition");
+        }
+        maTextureHandle = GLES20.glGetAttribLocation(mProgram, "aTextureCoord");
+        checkGlError("glGetAttribLocation aTextureCoord");
+        if (maTextureHandle == -1) {
+            throw new RuntimeException("Could not get attrib location for aTextureCoord");
+        }
+
+        muMVPMatrixHandle = GLES20.glGetUniformLocation(mProgram, "uMVPMatrix");
+        checkGlError("glGetUniformLocation uMVPMatrix");
+        if (muMVPMatrixHandle == -1) {
+            throw new RuntimeException("Could not get attrib location for uMVPMatrix");
+        }
+
+        muSTMatrixHandle = GLES20.glGetUniformLocation(mProgram, "uSTMatrix");
+        checkGlError("glGetUniformLocation uSTMatrix");
+        if (muMVPMatrixHandle == -1) {
+            throw new RuntimeException("Could not get attrib location for uSTMatrix");
+        }
+
+        checkGlError("glGetUniformLocation uCRatio");
+        if (muMVPMatrixHandle == -1) {
+            throw new RuntimeException("Could not get attrib location for uCRatio");
+        }
+
+        /*
+         * Create our texture. This has to be done each time the
+         * surface is created.
+         */
+
+        int[] textures = new int[1];
+        GLES20.glGenTextures(1, textures, 0);
+
+        mTextureID = textures[0];
+        GLES20.glBindTexture(GL_TEXTURE_EXTERNAL_OES, mTextureID);
+        checkGlError("glBindTexture mTextureID");
+
+        // Can't do mipmapping with camera source
+        GLES20.glTexParameterf(GL_TEXTURE_EXTERNAL_OES, GLES20.GL_TEXTURE_MIN_FILTER,
+                GLES20.GL_NEAREST);
+        GLES20.glTexParameterf(GL_TEXTURE_EXTERNAL_OES, GLES20.GL_TEXTURE_MAG_FILTER,
+                GLES20.GL_LINEAR);
+        // Clamp to edge is the only option
+        GLES20.glTexParameteri(GL_TEXTURE_EXTERNAL_OES, GLES20.GL_TEXTURE_WRAP_S,
+                GLES20.GL_CLAMP_TO_EDGE);
+        GLES20.glTexParameteri(GL_TEXTURE_EXTERNAL_OES, GLES20.GL_TEXTURE_WRAP_T,
+                GLES20.GL_CLAMP_TO_EDGE);
+        checkGlError("glTexParameteri mTextureID");
+
+        /*
+         * Create the SurfaceTexture that will feed this textureID, and pass it to the camera
+         */
+
+        mSurface = new SurfaceTexture(mTextureID);
+        mSurface.setOnFrameAvailableListener(this);
+
+        Matrix.setLookAtM(mVMatrix, 0, 0, 0, 4f, 0f, 0f, 0f, 0f, 1.0f, 0.0f);
+
+        synchronized(this) {
+            updateSurface = false;
+        }
+    }
+
+    synchronized public void onFrameAvailable(SurfaceTexture surface) {
+        /* For simplicity, SurfaceTexture calls here when it has new
+         * data available.  Call may come in from some random thread,
+         * so let's be safe and use synchronize. No OpenGL calls can be done here.
+         */
+        updateSurface = true;
+        //Log.v(TAG, "onFrameAvailable " + surface.getTimestamp());
+    }
+
+    private int loadShader(int shaderType, String source) {
+        int shader = GLES20.glCreateShader(shaderType);
+        if (shader != 0) {
+            GLES20.glShaderSource(shader, source);
+            GLES20.glCompileShader(shader);
+            int[] compiled = new int[1];
+            GLES20.glGetShaderiv(shader, GLES20.GL_COMPILE_STATUS, compiled, 0);
+            if (compiled[0] == 0) {
+                Log.e(TAG, "Could not compile shader " + shaderType + ":");
+                Log.e(TAG, GLES20.glGetShaderInfoLog(shader));
+                GLES20.glDeleteShader(shader);
+                shader = 0;
+            }
+        }
+        return shader;
+    }
+
+    private int createProgram(String vertexSource, String fragmentSource) {
+        int vertexShader = loadShader(GLES20.GL_VERTEX_SHADER, vertexSource);
+        if (vertexShader == 0) {
+            return 0;
+        }
+        int pixelShader = loadShader(GLES20.GL_FRAGMENT_SHADER, fragmentSource);
+        if (pixelShader == 0) {
+            return 0;
+        }
+
+        int program = GLES20.glCreateProgram();
+        if (program != 0) {
+            GLES20.glAttachShader(program, vertexShader);
+            checkGlError("glAttachShader");
+            GLES20.glAttachShader(program, pixelShader);
+            checkGlError("glAttachShader");
+            GLES20.glLinkProgram(program);
+            int[] linkStatus = new int[1];
+            GLES20.glGetProgramiv(program, GLES20.GL_LINK_STATUS, linkStatus, 0);
+            if (linkStatus[0] != GLES20.GL_TRUE) {
+                Log.e(TAG, "Could not link program: ");
+                Log.e(TAG, GLES20.glGetProgramInfoLog(program));
+                GLES20.glDeleteProgram(program);
+                program = 0;
+            }
+        }
+        return program;
+    }
+
+    private void checkGlError(String op) {
+        int error;
+        while ((error = GLES20.glGetError()) != GLES20.GL_NO_ERROR) {
+            Log.e(TAG, op + ": glError " + error);
+            throw new RuntimeException(op + ": glError " + error);
+        }
+    }
+
+    private static final int FLOAT_SIZE_BYTES = 4;
+    private static final int VERTICES_DATA_STRIDE_BYTES = 5 * FLOAT_SIZE_BYTES;
+    private static final int VERTICES_DATA_POS_OFFSET = 0;
+    private static final int VERTICES_DATA_UV_OFFSET = 3;
+    private final float[] mVerticesData = {
+        // X, Y, Z, U, V
+        -1.0f, -1.0f, 0, 0.f, 0.f,
+        1.0f, -1.0f, 0, 1.f, 0.f,
+        -1.0f,  1.0f, 0, 0.f, 1.f,
+        1.0f,   1.0f, 0, 1.f, 1.f,
+    };
+
+    private FloatBuffer mVertices;
+
+    private final String mVertexShader =
+        "uniform mat4 uMVPMatrix;\n" +
+        "uniform mat4 uSTMatrix;\n" +
+        "attribute vec4 aPosition;\n" +
+        "attribute vec4 aTextureCoord;\n" +
+        "varying vec2 vTextureCoord;\n" +
+        "void main() {\n" +
+        "  gl_Position = uMVPMatrix * aPosition;\n" +
+        "  vTextureCoord = (uSTMatrix * aTextureCoord).xy;\n" +
+        "}\n";
+
+    private final String mFragmentShader =
+        "#extension GL_OES_EGL_image_external : require\n" +
+        "precision mediump float;\n" +
+        "varying vec2 vTextureCoord;\n" +
+        "uniform samplerExternalOES sTexture;\n" +
+        "void main() {\n" +
+        "  gl_FragColor = texture2D(sTexture, vTextureCoord);\n" +
+        "}\n";
+
+    private float[] mMVPMatrix = new float[16];
+    private float[] mProjMatrix = new float[16];
+    private float[] mMMatrix = new float[16];
+    private float[] mVMatrix = new float[16];
+    private float[] mSTMatrix = new float[16];
+
+    private int mProgram;
+    private int mTextureID;
+    private int muMVPMatrixHandle;
+    private int muSTMatrixHandle;
+    private int maPositionHandle;
+    private int maTextureHandle;
+
+    private float mRatio = 1.0f;
+    private SurfaceTexture mSurface;
+    private boolean updateSurface = false;
+
+    private static final String TAG = "MyRenderer";
+
+    // Magic key
+    private static final int GL_TEXTURE_EXTERNAL_OES = 0x8D65;
+
+    public SurfaceTexture getSurfaceTexture() {
+        return mSurface;
+    }
+}
diff --git a/ndk/platforms/android-14/samples/native-media/src/com/example/nativemedia/NativeMedia.java b/ndk/platforms/android-14/samples/native-media/src/com/example/nativemedia/NativeMedia.java
new file mode 100644
index 0000000..3b5f49b
--- /dev/null
+++ b/ndk/platforms/android-14/samples/native-media/src/com/example/nativemedia/NativeMedia.java
@@ -0,0 +1,407 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.nativemedia;
+
+import android.app.Activity;
+import android.graphics.SurfaceTexture;
+import android.media.MediaPlayer;
+import android.os.Bundle;
+import android.util.Log;
+import android.view.Surface;
+import android.view.SurfaceHolder;
+import android.view.SurfaceView;
+import android.view.View;
+import android.widget.AdapterView;
+import android.widget.ArrayAdapter;
+import android.widget.Button;
+import android.widget.Spinner;
+import java.io.IOException;
+
+public class NativeMedia extends Activity {
+    static final String TAG = "NativeMedia";
+
+    String mSourceString = null;
+    String mSinkString = null;
+
+    // member variables for Java media player
+    MediaPlayer mMediaPlayer;
+    boolean mMediaPlayerIsPrepared = false;
+    SurfaceView mSurfaceView1;
+    SurfaceHolder mSurfaceHolder1;
+
+    // member variables for native media player
+    boolean mIsPlayingStreaming = false;
+    SurfaceView mSurfaceView2;
+    SurfaceHolder mSurfaceHolder2;
+
+    VideoSink mSelectedVideoSink;
+    VideoSink mJavaMediaPlayerVideoSink;
+    VideoSink mNativeMediaPlayerVideoSink;
+
+    SurfaceHolderVideoSink mSurfaceHolder1VideoSink, mSurfaceHolder2VideoSink;
+    GLViewVideoSink mGLView1VideoSink, mGLView2VideoSink;
+
+    /** Called when the activity is first created. */
+    @Override
+    public void onCreate(Bundle icicle) {
+        super.onCreate(icicle);
+        setContentView(R.layout.main);
+
+        mGLView1 = (MyGLSurfaceView) findViewById(R.id.glsurfaceview1);
+        mGLView2 = (MyGLSurfaceView) findViewById(R.id.glsurfaceview2);
+
+        // initialize native media system
+        createEngine();
+
+        // set up the Surface 1 video sink
+        mSurfaceView1 = (SurfaceView) findViewById(R.id.surfaceview1);
+        mSurfaceHolder1 = mSurfaceView1.getHolder();
+
+        mSurfaceHolder1.addCallback(new SurfaceHolder.Callback() {
+
+            public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
+                Log.v(TAG, "surfaceChanged format=" + format + ", width=" + width + ", height="
+                        + height);
+            }
+
+            public void surfaceCreated(SurfaceHolder holder) {
+                Log.v(TAG, "surfaceCreated");
+                setSurface(holder.getSurface());
+            }
+
+            public void surfaceDestroyed(SurfaceHolder holder) {
+                Log.v(TAG, "surfaceDestroyed");
+            }
+
+        });
+
+        // set up the Surface 2 video sink
+        mSurfaceView2 = (SurfaceView) findViewById(R.id.surfaceview2);
+        mSurfaceHolder2 = mSurfaceView2.getHolder();
+
+        mSurfaceHolder2.addCallback(new SurfaceHolder.Callback() {
+
+            public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
+                Log.v(TAG, "surfaceChanged format=" + format + ", width=" + width + ", height="
+                        + height);
+            }
+
+            public void surfaceCreated(SurfaceHolder holder) {
+                Log.v(TAG, "surfaceCreated");
+                setSurface(holder.getSurface());
+            }
+
+            public void surfaceDestroyed(SurfaceHolder holder) {
+                Log.v(TAG, "surfaceDestroyed");
+            }
+
+        });
+
+        // create Java media player
+        mMediaPlayer = new MediaPlayer();
+
+        // set up Java media player listeners
+        mMediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
+
+            public void onPrepared(MediaPlayer mediaPlayer) {
+                int width = mediaPlayer.getVideoWidth();
+                int height = mediaPlayer.getVideoHeight();
+                Log.v(TAG, "onPrepared width=" + width + ", height=" + height);
+                if (width != 0 && height != 0 && mJavaMediaPlayerVideoSink != null) {
+                    mJavaMediaPlayerVideoSink.setFixedSize(width, height);
+                }
+                mMediaPlayerIsPrepared = true;
+                mediaPlayer.start();
+            }
+
+        });
+
+        mMediaPlayer.setOnVideoSizeChangedListener(new MediaPlayer.OnVideoSizeChangedListener() {
+
+            public void onVideoSizeChanged(MediaPlayer mediaPlayer, int width, int height) {
+                Log.v(TAG, "onVideoSizeChanged width=" + width + ", height=" + height);
+                if (width != 0 && height != 0 && mJavaMediaPlayerVideoSink != null) {
+                    mJavaMediaPlayerVideoSink.setFixedSize(width, height);
+                }
+            }
+
+        });
+
+        // initialize content source spinner
+        Spinner sourceSpinner = (Spinner) findViewById(R.id.source_spinner);
+        ArrayAdapter<CharSequence> sourceAdapter = ArrayAdapter.createFromResource(
+                this, R.array.source_array, android.R.layout.simple_spinner_item);
+        sourceAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
+        sourceSpinner.setAdapter(sourceAdapter);
+        sourceSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
+
+            public void onItemSelected(AdapterView<?> parent, View view, int pos, long id) {
+                mSourceString = parent.getItemAtPosition(pos).toString();
+                Log.v(TAG, "onItemSelected " + mSourceString);
+            }
+
+            public void onNothingSelected(AdapterView parent) {
+                Log.v(TAG, "onNothingSelected");
+                mSourceString = null;
+            }
+
+        });
+
+        // initialize video sink spinner
+        Spinner sinkSpinner = (Spinner) findViewById(R.id.sink_spinner);
+        ArrayAdapter<CharSequence> sinkAdapter = ArrayAdapter.createFromResource(
+                this, R.array.sink_array, android.R.layout.simple_spinner_item);
+        sinkAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
+        sinkSpinner.setAdapter(sinkAdapter);
+        sinkSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
+
+            public void onItemSelected(AdapterView<?> parent, View view, int pos, long id) {
+                mSinkString = parent.getItemAtPosition(pos).toString();
+                Log.v(TAG, "onItemSelected " + mSinkString);
+                if ("Surface 1".equals(mSinkString)) {
+                    if (mSurfaceHolder1VideoSink == null) {
+                        mSurfaceHolder1VideoSink = new SurfaceHolderVideoSink(mSurfaceHolder1);
+                    }
+                    mSelectedVideoSink = mSurfaceHolder1VideoSink;
+                } else if ("Surface 2".equals(mSinkString)) {
+                    if (mSurfaceHolder2VideoSink == null) {
+                        mSurfaceHolder2VideoSink = new SurfaceHolderVideoSink(mSurfaceHolder2);
+                    }
+                    mSelectedVideoSink = mSurfaceHolder2VideoSink;
+                } else if ("SurfaceTexture 1".equals(mSinkString)) {
+                    if (mGLView1VideoSink == null) {
+                        mGLView1VideoSink = new GLViewVideoSink(mGLView1);
+                    }
+                    mSelectedVideoSink = mGLView1VideoSink;
+                } else if ("SurfaceTexture 2".equals(mSinkString)) {
+                    if (mGLView2VideoSink == null) {
+                        mGLView2VideoSink = new GLViewVideoSink(mGLView2);
+                    }
+                    mSelectedVideoSink = mGLView2VideoSink;
+                }
+            }
+
+            public void onNothingSelected(AdapterView parent) {
+                Log.v(TAG, "onNothingSelected");
+                mSinkString = null;
+                mSelectedVideoSink = null;
+            }
+
+        });
+
+        // initialize button click handlers
+
+        // Java MediaPlayer start/pause
+
+        ((Button) findViewById(R.id.start_java)).setOnClickListener(new View.OnClickListener() {
+
+            public void onClick(View view) {
+                if (mJavaMediaPlayerVideoSink == null) {
+                    if (mSelectedVideoSink == null) {
+                        return;
+                    }
+                    mSelectedVideoSink.useAsSinkForJava(mMediaPlayer);
+                    mJavaMediaPlayerVideoSink = mSelectedVideoSink;
+                }
+                if (!mMediaPlayerIsPrepared) {
+                    if (mSourceString != null) {
+                        try {
+                            mMediaPlayer.setDataSource(mSourceString);
+                        } catch (IOException e) {
+                            Log.e(TAG, "IOException " + e);
+                        }
+                        mMediaPlayer.prepareAsync();
+                    }
+                } else if (mMediaPlayer.isPlaying()) {
+                    mMediaPlayer.pause();
+                } else {
+                    mMediaPlayer.start();
+                }
+            }
+
+        });
+
+        // native MediaPlayer start/pause
+
+        ((Button) findViewById(R.id.start_native)).setOnClickListener(new View.OnClickListener() {
+
+            boolean created = false;
+            public void onClick(View view) {
+                if (!created) {
+                    if (mNativeMediaPlayerVideoSink == null) {
+                        if (mSelectedVideoSink == null) {
+                            return;
+                        }
+                        mSelectedVideoSink.useAsSinkForNative();
+                        mNativeMediaPlayerVideoSink = mSelectedVideoSink;
+                    }
+                    if (mSourceString != null) {
+                        created = createStreamingMediaPlayer(mSourceString);
+                    }
+                }
+                if (created) {
+                    mIsPlayingStreaming = !mIsPlayingStreaming;
+                    setPlayingStreamingMediaPlayer(mIsPlayingStreaming);
+                }
+            }
+
+        });
+
+        // finish
+
+        ((Button) findViewById(R.id.finish)).setOnClickListener(new View.OnClickListener() {
+
+            public void onClick(View view) {
+                finish();
+            }
+
+        });
+
+        // Java MediaPlayer rewind
+
+        ((Button) findViewById(R.id.rewind_java)).setOnClickListener(new View.OnClickListener() {
+
+            public void onClick(View view) {
+                if (mMediaPlayerIsPrepared) {
+                    mMediaPlayer.seekTo(0);
+                }
+            }
+
+        });
+
+        // native MediaPlayer rewind
+
+        ((Button) findViewById(R.id.rewind_native)).setOnClickListener(new View.OnClickListener() {
+
+            public void onClick(View view) {
+                if (mNativeMediaPlayerVideoSink != null) {
+                    rewindStreamingMediaPlayer();
+                }
+            }
+
+        });
+
+    }
+
+    /** Called when the activity is about to be paused. */
+    @Override
+    protected void onPause()
+    {
+        mIsPlayingStreaming = false;
+        setPlayingStreamingMediaPlayer(false);
+        mGLView1.onPause();
+        mGLView2.onPause();
+        super.onPause();
+    }
+
+    @Override
+    protected void onResume() {
+        super.onResume();
+        mGLView1.onResume();
+        mGLView2.onResume();
+    }
+
+    /** Called when the activity is about to be destroyed. */
+    @Override
+    protected void onDestroy()
+    {
+        shutdown();
+        super.onDestroy();
+    }
+
+    private MyGLSurfaceView mGLView1, mGLView2;
+
+    /** Native methods, implemented in jni folder */
+    public static native void createEngine();
+    public static native boolean createStreamingMediaPlayer(String filename);
+    public static native void setPlayingStreamingMediaPlayer(boolean isPlaying);
+    public static native void shutdown();
+    public static native void setSurface(Surface surface);
+    public static native void rewindStreamingMediaPlayer();
+
+    /** Load jni .so on initialization */
+    static {
+         System.loadLibrary("native-media-jni");
+    }
+
+    // VideoSink abstracts out the difference between Surface and SurfaceTexture
+    // aka SurfaceHolder and GLSurfaceView
+    static abstract class VideoSink {
+
+        abstract void setFixedSize(int width, int height);
+        abstract void useAsSinkForJava(MediaPlayer mediaPlayer);
+        abstract void useAsSinkForNative();
+
+    }
+
+    static class SurfaceHolderVideoSink extends VideoSink {
+
+        private final SurfaceHolder mSurfaceHolder;
+
+        SurfaceHolderVideoSink(SurfaceHolder surfaceHolder) {
+            mSurfaceHolder = surfaceHolder;
+        }
+
+        void setFixedSize(int width, int height) {
+            mSurfaceHolder.setFixedSize(width, height);
+        }
+
+        void useAsSinkForJava(MediaPlayer mediaPlayer) {
+            // Use the newer MediaPlayer.setSurface(Surface) since API level 14
+            // instead of MediaPlayer.setDisplay(mSurfaceHolder) since API level 1,
+            // because setSurface also works with a Surface derived from a SurfaceTexture.
+            Surface s = mSurfaceHolder.getSurface();
+            mediaPlayer.setSurface(s);
+            s.release();
+        }
+
+        void useAsSinkForNative() {
+            Surface s = mSurfaceHolder.getSurface();
+            setSurface(s);
+            s.release();
+        }
+
+    }
+
+    static class GLViewVideoSink extends VideoSink {
+
+        private final MyGLSurfaceView mMyGLSurfaceView;
+
+        GLViewVideoSink(MyGLSurfaceView myGLSurfaceView) {
+            mMyGLSurfaceView = myGLSurfaceView;
+        }
+
+        void setFixedSize(int width, int height) {
+        }
+
+        void useAsSinkForJava(MediaPlayer mediaPlayer) {
+            SurfaceTexture st = mMyGLSurfaceView.getSurfaceTexture();
+            Surface s = new Surface(st);
+            mediaPlayer.setSurface(s);
+            s.release();
+        }
+
+        void useAsSinkForNative() {
+            SurfaceTexture st = mMyGLSurfaceView.getSurfaceTexture();
+            Surface s = new Surface(st);
+            setSurface(s);
+            s.release();
+        }
+
+    }
+
+}
diff --git a/ndk/platforms/android-3/arch-arm/include/asm/ptrace.h b/ndk/platforms/android-3/arch-arm/include/asm/ptrace.h
index c6dfea1..a04eec3 100644
--- a/ndk/platforms/android-3/arch-arm/include/asm/ptrace.h
+++ b/ndk/platforms/android-3/arch-arm/include/asm/ptrace.h
@@ -29,6 +29,9 @@
 #define PTRACE_GETCRUNCHREGS 25
 #define PTRACE_SETCRUNCHREGS 26
 
+#define PTRACE_GETVFPREGS 27
+#define PTRACE_SETVFPREGS 28
+
 #define USR26_MODE 0x00000000
 #define FIQ26_MODE 0x00000001
 #define IRQ26_MODE 0x00000002
diff --git a/ndk/platforms/android-3/arch-arm/include/asm/user.h b/ndk/platforms/android-3/arch-arm/include/asm/user.h
index 5f25850..d0baecd 100644
--- a/ndk/platforms/android-3/arch-arm/include/asm/user.h
+++ b/ndk/platforms/android-3/arch-arm/include/asm/user.h
@@ -58,4 +58,15 @@
 #define HOST_TEXT_START_ADDR (u.start_code)
 #define HOST_STACK_END_ADDR (u.start_stack + u.u_ssize * NBPG)
 
+struct user_vfp {
+ unsigned long long fpregs[32];
+ unsigned long fpscr;
+};
+
+struct user_vfp_exc {
+ unsigned long fpexc;
+ unsigned long fpinst;
+ unsigned long fpinst2;
+};
+
 #endif
diff --git a/ndk/platforms/android-3/include/asm-generic/resource.h b/ndk/platforms/android-3/include/asm-generic/resource.h
index a7f7dec..3106473 100644
--- a/ndk/platforms/android-3/include/asm-generic/resource.h
+++ b/ndk/platforms/android-3/include/asm-generic/resource.h
@@ -43,8 +43,9 @@
 #define RLIMIT_MSGQUEUE 12  
 #define RLIMIT_NICE 13  
 #define RLIMIT_RTPRIO 14  
+#define RLIMIT_RTTIME 15  
 
-#define RLIM_NLIMITS 15
+#define RLIM_NLIMITS 16
 
 #ifndef RLIM_INFINITY
 #define RLIM_INFINITY (~0UL)
diff --git a/ndk/platforms/android-3/include/linux/ipv6.h b/ndk/platforms/android-3/include/linux/ipv6.h
new file mode 100644
index 0000000..f4ee9a1
--- /dev/null
+++ b/ndk/platforms/android-3/include/linux/ipv6.h
@@ -0,0 +1,133 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ ***   This header was automatically generated from a Linux kernel header
+ ***   of the same name, to make information necessary for userspace to
+ ***   call into the kernel available to libc.  It contains only constants,
+ ***   structures, and macros generated from the original header, and thus,
+ ***   contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _IPV6_H
+#define _IPV6_H
+
+#include <linux/types.h>
+#include <linux/in6.h>
+#include <asm/byteorder.h>
+
+#define IPV6_MIN_MTU 1280
+
+struct in6_pktinfo {
+ struct in6_addr ipi6_addr;
+ int ipi6_ifindex;
+};
+
+struct ip6_mtuinfo {
+ struct sockaddr_in6 ip6m_addr;
+ __u32 ip6m_mtu;
+};
+
+struct in6_ifreq {
+ struct in6_addr ifr6_addr;
+ __u32 ifr6_prefixlen;
+ int ifr6_ifindex;
+};
+
+#define IPV6_SRCRT_STRICT 0x01  
+#define IPV6_SRCRT_TYPE_0 0  
+#define IPV6_SRCRT_TYPE_2 2  
+
+struct ipv6_rt_hdr {
+ __u8 nexthdr;
+ __u8 hdrlen;
+ __u8 type;
+ __u8 segments_left;
+
+};
+
+struct ipv6_opt_hdr {
+ __u8 nexthdr;
+ __u8 hdrlen;
+
+} __attribute__((packed));
+
+#define ipv6_destopt_hdr ipv6_opt_hdr
+#define ipv6_hopopt_hdr ipv6_opt_hdr
+
+struct rt0_hdr {
+ struct ipv6_rt_hdr rt_hdr;
+ __u32 reserved;
+ struct in6_addr addr[0];
+
+#define rt0_type rt_hdr.type
+};
+
+struct rt2_hdr {
+ struct ipv6_rt_hdr rt_hdr;
+ __u32 reserved;
+ struct in6_addr addr;
+
+#define rt2_type rt_hdr.type
+};
+
+struct ipv6_destopt_hao {
+ __u8 type;
+ __u8 length;
+ struct in6_addr addr;
+} __attribute__((packed));
+
+struct ipv6hdr {
+#ifdef __LITTLE_ENDIAN_BITFIELD
+ __u8 priority:4,
+ version:4;
+#elif defined(__BIG_ENDIAN_BITFIELD)
+ __u8 version:4,
+ priority:4;
+#else
+#error "Please fix <asm/byteorder.h>"
+#endif
+ __u8 flow_lbl[3];
+
+ __be16 payload_len;
+ __u8 nexthdr;
+ __u8 hop_limit;
+
+ struct in6_addr saddr;
+ struct in6_addr daddr;
+};
+
+enum {
+ DEVCONF_FORWARDING = 0,
+ DEVCONF_HOPLIMIT,
+ DEVCONF_MTU6,
+ DEVCONF_ACCEPT_RA,
+ DEVCONF_ACCEPT_REDIRECTS,
+ DEVCONF_AUTOCONF,
+ DEVCONF_DAD_TRANSMITS,
+ DEVCONF_RTR_SOLICITS,
+ DEVCONF_RTR_SOLICIT_INTERVAL,
+ DEVCONF_RTR_SOLICIT_DELAY,
+ DEVCONF_USE_TEMPADDR,
+ DEVCONF_TEMP_VALID_LFT,
+ DEVCONF_TEMP_PREFERED_LFT,
+ DEVCONF_REGEN_MAX_RETRY,
+ DEVCONF_MAX_DESYNC_FACTOR,
+ DEVCONF_MAX_ADDRESSES,
+ DEVCONF_FORCE_MLD_VERSION,
+ DEVCONF_ACCEPT_RA_DEFRTR,
+ DEVCONF_ACCEPT_RA_PINFO,
+ DEVCONF_ACCEPT_RA_RTR_PREF,
+ DEVCONF_RTR_PROBE_INTERVAL,
+ DEVCONF_ACCEPT_RA_RT_INFO_MAX_PLEN,
+ DEVCONF_PROXY_NDP,
+ DEVCONF_OPTIMISTIC_DAD,
+ DEVCONF_ACCEPT_SOURCE_ROUTE,
+ DEVCONF_MC_FORWARDING,
+ DEVCONF_DISABLE_IPV6,
+ DEVCONF_ACCEPT_DAD,
+ DEVCONF_FORCE_TLLAO,
+ DEVCONF_MAX
+};
+
+#endif
diff --git a/ndk/platforms/android-9/arch-x86/include/sys/atomics.h b/ndk/platforms/android-3/include/net/ethernet.h
similarity index 62%
rename from ndk/platforms/android-9/arch-x86/include/sys/atomics.h
rename to ndk/platforms/android-3/include/net/ethernet.h
index 7aed3ae..b1b88dd 100644
--- a/ndk/platforms/android-9/arch-x86/include/sys/atomics.h
+++ b/ndk/platforms/android-3/include/net/ethernet.h
@@ -25,41 +25,8 @@
  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  * SUCH DAMAGE.
  */
-#ifndef _SYS_ATOMICS_H
-#define _SYS_ATOMICS_H
-
-#include <sys/cdefs.h>
-#include <sys/time.h>
-
-__BEGIN_DECLS
-
-static inline __attribute__((always_inline)) int
-__atomic_cmpxchg(int old, int _new, volatile int *ptr)
-{
-  return !__sync_bool_compare_and_swap (ptr, old, _new);
-}
-
-static inline __attribute__((always_inline)) int
-__atomic_swap(int _new, volatile int *ptr)
-{
-  return __sync_lock_test_and_set(ptr, _new);
-}
-
-static inline __attribute__((always_inline)) int
-__atomic_dec(volatile int *ptr)
-{
-  return __sync_fetch_and_sub (ptr, 1);
-}
-
-static inline __attribute__((always_inline)) int
-__atomic_inc(volatile int *ptr)
-{
-  return __sync_fetch_and_add (ptr, 1);
-}
-
-int __futex_wait(volatile void *ftx, int val, const struct timespec *timeout);
-int __futex_wake(volatile void *ftx, int count);
-
-__END_DECLS
-
-#endif /* _SYS_ATOMICS_H */
+#ifndef _NET_ETHERNET_H_
+#define _NET_IF_ETHERNET_H_
+#include <linux/if_ether.h>
+#include <net/if_ether.h>
+#endif /* !_NET_ETHERNET_H_ */
diff --git a/ndk/platforms/android-3/include/net/if_ether.h b/ndk/platforms/android-3/include/net/if_ether.h
index 121f9ac..8daa16b 100644
--- a/ndk/platforms/android-3/include/net/if_ether.h
+++ b/ndk/platforms/android-3/include/net/if_ether.h
@@ -34,6 +34,8 @@
 #ifndef _NET_IF_ETHER_H_
 #define _NET_IF_ETHER_H_
 
+#include <sys/types.h>
+
 #ifdef _KERNEL
 #ifdef _KERNEL_OPT
 #include "opt_mbuftrace.h"
diff --git a/ndk/platforms/android-3/include/netdb.h b/ndk/platforms/android-3/include/netdb.h
index 8d3996a..f48052d 100644
--- a/ndk/platforms/android-3/include/netdb.h
+++ b/ndk/platforms/android-3/include/netdb.h
@@ -137,10 +137,7 @@
 /*
  * Error return codes from getaddrinfo()
  */
-#if 0
-/* obsoleted */
 #define	EAI_ADDRFAMILY	 1	/* address family for hostname not supported */
-#endif
 #define	EAI_AGAIN	 2	/* temporary failure in name resolution */
 #define	EAI_BADFLAGS	 3	/* invalid value for ai_flags */
 #define	EAI_FAIL	 4	/* non-recoverable failure in name resolution */
diff --git a/ndk/platforms/android-3/include/netinet/icmp6.h b/ndk/platforms/android-3/include/netinet/icmp6.h
new file mode 100644
index 0000000..fbc8234
--- /dev/null
+++ b/ndk/platforms/android-3/include/netinet/icmp6.h
@@ -0,0 +1,730 @@
+/*	$NetBSD: icmp6.h,v 1.40 2009/10/31 22:32:17 christos Exp $	*/
+/*	$KAME: icmp6.h,v 1.84 2003/04/23 10:26:51 itojun Exp $	*/
+
+
+/*
+ * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the project nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+/*
+ * Copyright (c) 1982, 1986, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ *	@(#)ip_icmp.h	8.1 (Berkeley) 6/10/93
+ */
+
+#ifndef _NETINET_ICMP6_H_
+#define _NETINET_ICMP6_H_
+
+#define ICMPV6_PLD_MAXLEN	1232	/* IPV6_MMTU - sizeof(struct ip6_hdr)
+					   - sizeof(struct icmp6_hdr) */
+
+struct icmp6_hdr {
+	u_int8_t	icmp6_type;	/* type field */
+	u_int8_t	icmp6_code;	/* code field */
+	u_int16_t	icmp6_cksum;	/* checksum field */
+	union {
+		u_int32_t	icmp6_un_data32[1]; /* type-specific field */
+		u_int16_t	icmp6_un_data16[2]; /* type-specific field */
+		u_int8_t	icmp6_un_data8[4];  /* type-specific field */
+	} icmp6_dataun;
+} __packed;
+
+#define icmp6_data32	icmp6_dataun.icmp6_un_data32
+#define icmp6_data16	icmp6_dataun.icmp6_un_data16
+#define icmp6_data8	icmp6_dataun.icmp6_un_data8
+#define icmp6_pptr	icmp6_data32[0]		/* parameter prob */
+#define icmp6_mtu	icmp6_data32[0]		/* packet too big */
+#define icmp6_id	icmp6_data16[0]		/* echo request/reply */
+#define icmp6_seq	icmp6_data16[1]		/* echo request/reply */
+#define icmp6_maxdelay	icmp6_data16[0]		/* mcast group membership */
+
+#define ICMP6_DST_UNREACH		1	/* dest unreachable, codes: */
+#define ICMP6_PACKET_TOO_BIG		2	/* packet too big */
+#define ICMP6_TIME_EXCEEDED		3	/* time exceeded, code: */
+#define ICMP6_PARAM_PROB		4	/* ip6 header bad */
+
+#define ICMP6_ECHO_REQUEST		128	/* echo service */
+#define ICMP6_ECHO_REPLY		129	/* echo reply */
+#define MLD_LISTENER_QUERY		130 	/* multicast listener query */
+#define MLD_LISTENER_REPORT		131	/* multicast listener report */
+#define MLD_LISTENER_DONE		132	/* multicast listener done */
+
+/* RFC2292 decls */
+#define ICMP6_MEMBERSHIP_QUERY		130	/* group membership query */
+#define ICMP6_MEMBERSHIP_REPORT		131	/* group membership report */
+#define ICMP6_MEMBERSHIP_REDUCTION	132	/* group membership termination */
+
+#ifndef _KERNEL
+/* the followings are for backward compatibility to old KAME apps. */
+#define MLD6_LISTENER_QUERY	MLD_LISTENER_QUERY
+#define MLD6_LISTENER_REPORT	MLD_LISTENER_REPORT
+#define MLD6_LISTENER_DONE	MLD_LISTENER_DONE
+#endif
+
+#define ND_ROUTER_SOLICIT		133	/* router solicitation */
+#define ND_ROUTER_ADVERT		134	/* router advertisement */
+#define ND_NEIGHBOR_SOLICIT		135	/* neighbor solicitation */
+#define ND_NEIGHBOR_ADVERT		136	/* neighbor advertisement */
+#define ND_REDIRECT			137	/* redirect */
+
+#define ICMP6_ROUTER_RENUMBERING	138	/* router renumbering */
+
+#define ICMP6_WRUREQUEST		139	/* who are you request */
+#define ICMP6_WRUREPLY			140	/* who are you reply */
+#define ICMP6_FQDN_QUERY		139	/* FQDN query */
+#define ICMP6_FQDN_REPLY		140	/* FQDN reply */
+#define ICMP6_NI_QUERY			139	/* node information request */
+#define ICMP6_NI_REPLY			140	/* node information reply */
+
+/* The definitions below are experimental. TBA */
+#define MLD_MTRACE_RESP			200	/* mtrace response(to sender) */
+#define MLD_MTRACE			201	/* mtrace messages */
+
+#ifndef _KERNEL
+/* the followings are for backward compatibility to old KAME apps. */
+#define MLD6_MTRACE_RESP	MLD_MTRACE_RESP
+#define MLD6_MTRACE		MLD_MTRACE
+#endif
+
+#define ICMP6_MAXTYPE			201
+
+#define ICMP6_DST_UNREACH_NOROUTE	0	/* no route to destination */
+#define ICMP6_DST_UNREACH_ADMIN	 	1	/* administratively prohibited */
+#define ICMP6_DST_UNREACH_NOTNEIGHBOR	2	/* not a neighbor(obsolete) */
+#define ICMP6_DST_UNREACH_BEYONDSCOPE	2	/* beyond scope of source address */
+#define ICMP6_DST_UNREACH_ADDR		3	/* address unreachable */
+#define ICMP6_DST_UNREACH_NOPORT	4	/* port unreachable */
+
+#define ICMP6_TIME_EXCEED_TRANSIT 	0	/* ttl==0 in transit */
+#define ICMP6_TIME_EXCEED_REASSEMBLY	1	/* ttl==0 in reass */
+
+#define ICMP6_PARAMPROB_HEADER 	 	0	/* erroneous header field */
+#define ICMP6_PARAMPROB_NEXTHEADER	1	/* unrecognized next header */
+#define ICMP6_PARAMPROB_OPTION		2	/* unrecognized option */
+
+#define ICMP6_INFOMSG_MASK		0x80	/* all informational messages */
+
+#define ICMP6_NI_SUBJ_IPV6	0	/* Query Subject is an IPv6 address */
+#define ICMP6_NI_SUBJ_FQDN	1	/* Query Subject is a Domain name */
+#define ICMP6_NI_SUBJ_IPV4	2	/* Query Subject is an IPv4 address */
+
+#define ICMP6_NI_SUCCESS	0	/* node information successful reply */
+#define ICMP6_NI_REFUSED	1	/* node information request is refused */
+#define ICMP6_NI_UNKNOWN	2	/* unknown Qtype */
+
+#define ICMP6_ROUTER_RENUMBERING_COMMAND  0	/* rr command */
+#define ICMP6_ROUTER_RENUMBERING_RESULT   1	/* rr result */
+#define ICMP6_ROUTER_RENUMBERING_SEQNUM_RESET   255	/* rr seq num reset */
+
+/* Used in kernel only */
+#define ND_REDIRECT_ONLINK	0	/* redirect to an on-link node */
+#define ND_REDIRECT_ROUTER	1	/* redirect to a better router */
+
+/*
+ * Multicast Listener Discovery
+ */
+struct mld_hdr {
+	struct icmp6_hdr	mld_icmp6_hdr;
+	struct in6_addr		mld_addr; /* multicast address */
+} __packed;
+
+/* definitions to provide backward compatibility to old KAME applications */
+#ifndef _KERNEL
+#define mld6_hdr	mld_hdr
+#define mld6_type	mld_type
+#define mld6_code	mld_code
+#define mld6_cksum	mld_cksum
+#define mld6_maxdelay	mld_maxdelay
+#define mld6_reserved	mld_reserved
+#define mld6_addr	mld_addr
+#endif
+
+/* shortcut macro definitions */
+#define mld_type	mld_icmp6_hdr.icmp6_type
+#define mld_code	mld_icmp6_hdr.icmp6_code
+#define mld_cksum	mld_icmp6_hdr.icmp6_cksum
+#define mld_maxdelay	mld_icmp6_hdr.icmp6_data16[0]
+#define mld_reserved	mld_icmp6_hdr.icmp6_data16[1]
+
+#define MLD_MINLEN			24
+
+/*
+ * Neighbor Discovery
+ */
+
+struct nd_router_solicit {	/* router solicitation */
+	struct icmp6_hdr 	nd_rs_hdr;
+	/* could be followed by options */
+} __packed;
+
+#define nd_rs_type	nd_rs_hdr.icmp6_type
+#define nd_rs_code	nd_rs_hdr.icmp6_code
+#define nd_rs_cksum	nd_rs_hdr.icmp6_cksum
+#define nd_rs_reserved	nd_rs_hdr.icmp6_data32[0]
+
+struct nd_router_advert {	/* router advertisement */
+	struct icmp6_hdr	nd_ra_hdr;
+	u_int32_t		nd_ra_reachable;	/* reachable time */
+	u_int32_t		nd_ra_retransmit;	/* retransmit timer */
+	/* could be followed by options */
+} __packed;
+
+#define nd_ra_type		nd_ra_hdr.icmp6_type
+#define nd_ra_code		nd_ra_hdr.icmp6_code
+#define nd_ra_cksum		nd_ra_hdr.icmp6_cksum
+#define nd_ra_curhoplimit	nd_ra_hdr.icmp6_data8[0]
+#define nd_ra_flags_reserved	nd_ra_hdr.icmp6_data8[1]
+#define ND_RA_FLAG_MANAGED	0x80
+#define ND_RA_FLAG_OTHER	0x40
+#define ND_RA_FLAG_HOME_AGENT	0x20
+
+/*
+ * Router preference values based on RFC4199.
+ */
+#define ND_RA_FLAG_RTPREF_MASK	0x18 /* 00011000 */
+
+#define ND_RA_FLAG_RTPREF_HIGH	0x08 /* 00001000 */
+#define ND_RA_FLAG_RTPREF_MEDIUM	0x00 /* 00000000 */
+#define ND_RA_FLAG_RTPREF_LOW	0x18 /* 00011000 */
+#define ND_RA_FLAG_RTPREF_RSV	0x10 /* 00010000 */
+
+#define nd_ra_router_lifetime	nd_ra_hdr.icmp6_data16[1]
+
+struct nd_neighbor_solicit {	/* neighbor solicitation */
+	struct icmp6_hdr	nd_ns_hdr;
+	struct in6_addr		nd_ns_target;	/*target address */
+	/* could be followed by options */
+} __packed;
+
+#define nd_ns_type		nd_ns_hdr.icmp6_type
+#define nd_ns_code		nd_ns_hdr.icmp6_code
+#define nd_ns_cksum		nd_ns_hdr.icmp6_cksum
+#define nd_ns_reserved		nd_ns_hdr.icmp6_data32[0]
+
+struct nd_neighbor_advert {	/* neighbor advertisement */
+	struct icmp6_hdr	nd_na_hdr;
+	struct in6_addr		nd_na_target;	/* target address */
+	/* could be followed by options */
+} __packed;
+
+#define nd_na_type		nd_na_hdr.icmp6_type
+#define nd_na_code		nd_na_hdr.icmp6_code
+#define nd_na_cksum		nd_na_hdr.icmp6_cksum
+#define nd_na_flags_reserved	nd_na_hdr.icmp6_data32[0]
+#if BYTE_ORDER == BIG_ENDIAN
+#define ND_NA_FLAG_ROUTER		0x80000000
+#define ND_NA_FLAG_SOLICITED		0x40000000
+#define ND_NA_FLAG_OVERRIDE		0x20000000
+#else
+#if BYTE_ORDER == LITTLE_ENDIAN
+#define ND_NA_FLAG_ROUTER		0x80
+#define ND_NA_FLAG_SOLICITED		0x40
+#define ND_NA_FLAG_OVERRIDE		0x20
+#endif
+#endif
+
+struct nd_redirect {		/* redirect */
+	struct icmp6_hdr	nd_rd_hdr;
+	struct in6_addr		nd_rd_target;	/* target address */
+	struct in6_addr		nd_rd_dst;	/* destination address */
+	/* could be followed by options */
+} __packed;
+
+#define nd_rd_type		nd_rd_hdr.icmp6_type
+#define nd_rd_code		nd_rd_hdr.icmp6_code
+#define nd_rd_cksum		nd_rd_hdr.icmp6_cksum
+#define nd_rd_reserved		nd_rd_hdr.icmp6_data32[0]
+
+struct nd_opt_hdr {		/* Neighbor discovery option header */
+	u_int8_t	nd_opt_type;
+	u_int8_t	nd_opt_len;
+	/* followed by option specific data*/
+} __packed;
+
+#define ND_OPT_SOURCE_LINKADDR		1
+#define ND_OPT_TARGET_LINKADDR		2
+#define ND_OPT_PREFIX_INFORMATION	3
+#define ND_OPT_REDIRECTED_HEADER	4
+#define ND_OPT_MTU			5
+#define ND_OPT_ADVINTERVAL		7
+#define ND_OPT_HOMEAGENT_INFO		8
+#define ND_OPT_SOURCE_ADDRLIST		9
+#define ND_OPT_TARGET_ADDRLIST		10
+#define ND_OPT_RDNSS			25
+/* draft-ietf-ipngwg-router-preference, not officially assigned yet */
+#define ND_OPT_ROUTE_INFO		200
+/* draft-ietf-mobileip-hmipv6, not officially assigned yet */
+#define ND_OPT_MAP			201
+
+struct nd_opt_route_info {	/* route info */
+	u_int8_t	nd_opt_rti_type;
+	u_int8_t	nd_opt_rti_len;
+	u_int8_t	nd_opt_rti_prefixlen;
+	u_int8_t	nd_opt_rti_flags;
+	u_int32_t	nd_opt_rti_lifetime;
+	/* prefix follows */
+};
+
+struct nd_opt_prefix_info {	/* prefix information */
+	u_int8_t	nd_opt_pi_type;
+	u_int8_t	nd_opt_pi_len;
+	u_int8_t	nd_opt_pi_prefix_len;
+	u_int8_t	nd_opt_pi_flags_reserved;
+	u_int32_t	nd_opt_pi_valid_time;
+	u_int32_t	nd_opt_pi_preferred_time;
+	u_int32_t	nd_opt_pi_reserved2;
+	struct in6_addr	nd_opt_pi_prefix;
+} __packed;
+
+#define ND_OPT_PI_FLAG_ONLINK		0x80
+#define ND_OPT_PI_FLAG_AUTO		0x40
+
+struct nd_opt_rd_hdr {		/* redirected header */
+	u_int8_t	nd_opt_rh_type;
+	u_int8_t	nd_opt_rh_len;
+	u_int16_t	nd_opt_rh_reserved1;
+	u_int32_t	nd_opt_rh_reserved2;
+	/* followed by IP header and data */
+} __packed;
+
+struct nd_opt_mtu {		/* MTU option */
+	u_int8_t	nd_opt_mtu_type;
+	u_int8_t	nd_opt_mtu_len;
+	u_int16_t	nd_opt_mtu_reserved;
+	u_int32_t	nd_opt_mtu_mtu;
+} __packed;
+
+struct nd_opt_rdnss {		/* RDNSS option RFC 5006 */
+	u_int8_t	nd_opt_rdnss_type;
+	u_int8_t	nd_opt_rdnss_len;
+	u_int16_t	nd_opt_rdnss_reserved;
+	u_int32_t	nd_opt_rdnss_lifetime;
+	/* followed by list of IP prefixes */
+} __packed;
+
+/*
+ * icmp6 namelookup
+ */
+
+struct icmp6_namelookup {
+	struct icmp6_hdr 	icmp6_nl_hdr;
+	u_int8_t	icmp6_nl_nonce[8];
+	int32_t		icmp6_nl_ttl;
+#if 0
+	u_int8_t	icmp6_nl_len;
+	u_int8_t	icmp6_nl_name[3];
+#endif
+	/* could be followed by options */
+} __packed;
+
+/*
+ * icmp6 node information
+ */
+struct icmp6_nodeinfo {
+	struct icmp6_hdr icmp6_ni_hdr;
+	u_int8_t icmp6_ni_nonce[8];
+	/* could be followed by reply data */
+} __packed;
+
+#define ni_type		icmp6_ni_hdr.icmp6_type
+#define ni_code		icmp6_ni_hdr.icmp6_code
+#define ni_cksum	icmp6_ni_hdr.icmp6_cksum
+#define ni_qtype	icmp6_ni_hdr.icmp6_data16[0]
+#define ni_flags	icmp6_ni_hdr.icmp6_data16[1]
+
+#define NI_QTYPE_NOOP		0 /* NOOP  */
+#define NI_QTYPE_SUPTYPES	1 /* Supported Qtypes */
+#define NI_QTYPE_FQDN		2 /* FQDN (draft 04) */
+#define NI_QTYPE_DNSNAME	2 /* DNS Name */
+#define NI_QTYPE_NODEADDR	3 /* Node Addresses */
+#define NI_QTYPE_IPV4ADDR	4 /* IPv4 Addresses */
+
+#if BYTE_ORDER == BIG_ENDIAN
+#define NI_SUPTYPE_FLAG_COMPRESS	0x1
+#define NI_FQDN_FLAG_VALIDTTL		0x1
+#elif BYTE_ORDER == LITTLE_ENDIAN
+#define NI_SUPTYPE_FLAG_COMPRESS	0x0100
+#define NI_FQDN_FLAG_VALIDTTL		0x0100
+#endif
+
+#ifdef NAME_LOOKUPS_04
+#if BYTE_ORDER == BIG_ENDIAN
+#define NI_NODEADDR_FLAG_LINKLOCAL	0x1
+#define NI_NODEADDR_FLAG_SITELOCAL	0x2
+#define NI_NODEADDR_FLAG_GLOBAL		0x4
+#define NI_NODEADDR_FLAG_ALL		0x8
+#define NI_NODEADDR_FLAG_TRUNCATE	0x10
+#define NI_NODEADDR_FLAG_ANYCAST	0x20 /* just experimental. not in spec */
+#elif BYTE_ORDER == LITTLE_ENDIAN
+#define NI_NODEADDR_FLAG_LINKLOCAL	0x0100
+#define NI_NODEADDR_FLAG_SITELOCAL	0x0200
+#define NI_NODEADDR_FLAG_GLOBAL		0x0400
+#define NI_NODEADDR_FLAG_ALL		0x0800
+#define NI_NODEADDR_FLAG_TRUNCATE	0x1000
+#define NI_NODEADDR_FLAG_ANYCAST	0x2000 /* just experimental. not in spec */
+#endif
+#else  /* draft-ietf-ipngwg-icmp-name-lookups-05 (and later?) */
+#if BYTE_ORDER == BIG_ENDIAN
+#define NI_NODEADDR_FLAG_TRUNCATE	0x1
+#define NI_NODEADDR_FLAG_ALL		0x2
+#define NI_NODEADDR_FLAG_COMPAT		0x4
+#define NI_NODEADDR_FLAG_LINKLOCAL	0x8
+#define NI_NODEADDR_FLAG_SITELOCAL	0x10
+#define NI_NODEADDR_FLAG_GLOBAL		0x20
+#define NI_NODEADDR_FLAG_ANYCAST	0x40 /* just experimental. not in spec */
+#elif BYTE_ORDER == LITTLE_ENDIAN
+#define NI_NODEADDR_FLAG_TRUNCATE	0x0100
+#define NI_NODEADDR_FLAG_ALL		0x0200
+#define NI_NODEADDR_FLAG_COMPAT		0x0400
+#define NI_NODEADDR_FLAG_LINKLOCAL	0x0800
+#define NI_NODEADDR_FLAG_SITELOCAL	0x1000
+#define NI_NODEADDR_FLAG_GLOBAL		0x2000
+#define NI_NODEADDR_FLAG_ANYCAST	0x4000 /* just experimental. not in spec */
+#endif
+#endif
+
+struct ni_reply_fqdn {
+	u_int32_t ni_fqdn_ttl;	/* TTL */
+	u_int8_t ni_fqdn_namelen; /* length in octets of the FQDN */
+	u_int8_t ni_fqdn_name[3]; /* XXX: alignment */
+} __packed;
+
+/*
+ * Router Renumbering. as router-renum-08.txt
+ */
+struct icmp6_router_renum {	/* router renumbering header */
+	struct icmp6_hdr	rr_hdr;
+	u_int8_t	rr_segnum;
+	u_int8_t	rr_flags;
+	u_int16_t	rr_maxdelay;
+	u_int32_t	rr_reserved;
+} __packed;
+
+#define ICMP6_RR_FLAGS_TEST		0x80
+#define ICMP6_RR_FLAGS_REQRESULT	0x40
+#define ICMP6_RR_FLAGS_FORCEAPPLY	0x20
+#define ICMP6_RR_FLAGS_SPECSITE		0x10
+#define ICMP6_RR_FLAGS_PREVDONE		0x08
+
+#define rr_type		rr_hdr.icmp6_type
+#define rr_code		rr_hdr.icmp6_code
+#define rr_cksum	rr_hdr.icmp6_cksum
+#define rr_seqnum 	rr_hdr.icmp6_data32[0]
+
+struct rr_pco_match {		/* match prefix part */
+	u_int8_t	rpm_code;
+	u_int8_t	rpm_len;
+	u_int8_t	rpm_ordinal;
+	u_int8_t	rpm_matchlen;
+	u_int8_t	rpm_minlen;
+	u_int8_t	rpm_maxlen;
+	u_int16_t	rpm_reserved;
+	struct	in6_addr	rpm_prefix;
+} __packed;
+
+#define RPM_PCO_ADD		1
+#define RPM_PCO_CHANGE		2
+#define RPM_PCO_SETGLOBAL	3
+#define RPM_PCO_MAX		4
+
+struct rr_pco_use {		/* use prefix part */
+	u_int8_t	rpu_uselen;
+	u_int8_t	rpu_keeplen;
+	u_int8_t	rpu_ramask;
+	u_int8_t	rpu_raflags;
+	u_int32_t	rpu_vltime;
+	u_int32_t	rpu_pltime;
+	u_int32_t	rpu_flags;
+	struct	in6_addr rpu_prefix;
+} __packed;
+#define ICMP6_RR_PCOUSE_RAFLAGS_ONLINK	0x80
+#define ICMP6_RR_PCOUSE_RAFLAGS_AUTO	0x40
+
+#if BYTE_ORDER == BIG_ENDIAN
+#define ICMP6_RR_PCOUSE_FLAGS_DECRVLTIME     0x80000000
+#define ICMP6_RR_PCOUSE_FLAGS_DECRPLTIME     0x40000000
+#elif BYTE_ORDER == LITTLE_ENDIAN
+#define ICMP6_RR_PCOUSE_FLAGS_DECRVLTIME     0x80
+#define ICMP6_RR_PCOUSE_FLAGS_DECRPLTIME     0x40
+#endif
+
+struct rr_result {		/* router renumbering result message */
+	u_int16_t	rrr_flags;
+	u_int8_t	rrr_ordinal;
+	u_int8_t	rrr_matchedlen;
+	u_int32_t	rrr_ifid;
+	struct	in6_addr rrr_prefix;
+} __packed;
+#if BYTE_ORDER == BIG_ENDIAN
+#define ICMP6_RR_RESULT_FLAGS_OOB		0x0002
+#define ICMP6_RR_RESULT_FLAGS_FORBIDDEN		0x0001
+#elif BYTE_ORDER == LITTLE_ENDIAN
+#define ICMP6_RR_RESULT_FLAGS_OOB		0x0200
+#define ICMP6_RR_RESULT_FLAGS_FORBIDDEN		0x0100
+#endif
+
+/*
+ * icmp6 filter structures.
+ */
+
+struct icmp6_filter {
+	u_int32_t icmp6_filt[8];
+};
+
+#define	ICMP6_FILTER_SETPASSALL(filterp) \
+	(void)memset(filterp, 0xff, sizeof(struct icmp6_filter))
+#define	ICMP6_FILTER_SETBLOCKALL(filterp) \
+	(void)memset(filterp, 0x00, sizeof(struct icmp6_filter))
+#define	ICMP6_FILTER_SETPASS(type, filterp) \
+	(((filterp)->icmp6_filt[(type) >> 5]) |= (1 << ((type) & 31)))
+#define	ICMP6_FILTER_SETBLOCK(type, filterp) \
+	(((filterp)->icmp6_filt[(type) >> 5]) &= ~(1 << ((type) & 31)))
+#define	ICMP6_FILTER_WILLPASS(type, filterp) \
+	((((filterp)->icmp6_filt[(type) >> 5]) & (1 << ((type) & 31))) != 0)
+#define	ICMP6_FILTER_WILLBLOCK(type, filterp) \
+	((((filterp)->icmp6_filt[(type) >> 5]) & (1 << ((type) & 31))) == 0)
+
+/*
+ * Variables related to this implementation
+ * of the internet control message protocol version 6.
+ */
+
+/*
+ * IPv6 ICMP statistics.
+ * Each counter is an unsigned 64-bit value.
+ */
+#define	ICMP6_STAT_ERROR	0	/* # of calls to icmp6_error */
+#define	ICMP6_STAT_CANTERROR	1	/* no error (old was icmp) */
+#define	ICMP6_STAT_TOOFREQ	2	/* no error (rate limitation) */
+#define	ICMP6_STAT_OUTHIST	3	/* # of output messages */
+		/* space for 256 counters */
+#define	ICMP6_STAT_BADCODE	259	/* icmp6_code out of range */
+#define	ICMP6_STAT_TOOSHORT	260	/* packet < sizeof(struct icmp6_hdr) */
+#define	ICMP6_STAT_CHECKSUM	261	/* bad checksum */
+#define	ICMP6_STAT_BADLEN	262	/* calculated bound mismatch */
+	/*
+	 * number of responses; this member is inherited from the netinet code,
+	 * but for netinet6 code, it is already available in outhist[].
+	 */
+#define	ICMP6_STAT_REFLECT	263
+#define	ICMP6_STAT_INHIST	264	/* # of input messages */
+		/* space for 256 counters */
+#define	ICMP6_STAT_ND_TOOMANYOPT 520	/* too many ND options */
+#define	ICMP6_STAT_OUTERRHIST	521
+		/* space for 13 counters */
+#define	ICMP6_STAT_PMTUCHG	534	/* path MTU changes */
+#define	ICMP6_STAT_ND_BADOPT	535	/* bad ND options */
+#define	ICMP6_STAT_BADNS	536	/* bad neighbor solicititation */
+#define	ICMP6_STAT_BADNA	537	/* bad neighbor advertisement */
+#define	ICMP6_STAT_BADRS	538	/* bad router solicitiation */
+#define	ICMP6_STAT_BADRA	539	/* bad router advertisement */
+#define	ICMP6_STAT_BADREDIRECT	540	/* bad redirect message */
+
+#define	ICMP6_NSTATS		541
+
+#define	ICMP6_ERRSTAT_DST_UNREACH_NOROUTE	0
+#define	ICMP6_ERRSTAT_DST_UNREACH_ADMIN		1
+#define	ICMP6_ERRSTAT_DST_UNREACH_BEYONDSCOPE	2
+#define	ICMP6_ERRSTAT_DST_UNREACH_ADDR		3
+#define	ICMP6_ERRSTAT_DST_UNREACH_NOPORT	4
+#define	ICMP6_ERRSTAT_PACKET_TOO_BIG		5
+#define	ICMP6_ERRSTAT_TIME_EXCEED_TRANSIT	6
+#define	ICMP6_ERRSTAT_TIME_EXCEED_REASSEMBLY	7
+#define	ICMP6_ERRSTAT_PARAMPROB_HEADER		8
+#define	ICMP6_ERRSTAT_PARAMPROB_NEXTHEADER	9
+#define	ICMP6_ERRSTAT_PARAMPROB_OPTION		10
+#define	ICMP6_ERRSTAT_REDIRECT			11
+#define	ICMP6_ERRSTAT_UNKNOWN			12
+
+/*
+ * Names for ICMP sysctl objects
+ */
+#define ICMPV6CTL_STATS		1
+#define ICMPV6CTL_REDIRACCEPT	2	/* accept/process redirects */
+#define ICMPV6CTL_REDIRTIMEOUT	3	/* redirect cache time */
+#if 0	/*obsoleted*/
+#define ICMPV6CTL_ERRRATELIMIT	5	/* ICMPv6 error rate limitation */
+#endif
+#define ICMPV6CTL_ND6_PRUNE	6
+#define ICMPV6CTL_ND6_DELAY	8
+#define ICMPV6CTL_ND6_UMAXTRIES	9
+#define ICMPV6CTL_ND6_MMAXTRIES		10
+#define ICMPV6CTL_ND6_USELOOPBACK	11
+/*#define ICMPV6CTL_ND6_PROXYALL	12	obsoleted, do not reuse here */
+#define ICMPV6CTL_NODEINFO	13
+#define ICMPV6CTL_ERRPPSLIMIT	14	/* ICMPv6 error pps limitation */
+#define ICMPV6CTL_ND6_MAXNUDHINT	15
+#define ICMPV6CTL_MTUDISC_HIWAT	16
+#define ICMPV6CTL_MTUDISC_LOWAT	17
+#define ICMPV6CTL_ND6_DEBUG	18
+#define ICMPV6CTL_ND6_DRLIST	19
+#define ICMPV6CTL_ND6_PRLIST	20
+#define	ICMPV6CTL_ND6_MAXQLEN	24
+#define ICMPV6CTL_MAXID		25
+
+#define ICMPV6CTL_NAMES { \
+	{ 0, 0 }, \
+	{ 0, 0 }, \
+	{ "rediraccept", CTLTYPE_INT }, \
+	{ "redirtimeout", CTLTYPE_INT }, \
+	{ 0, 0 }, \
+	{ 0, 0 }, \
+	{ "nd6_prune", CTLTYPE_INT }, \
+	{ 0, 0 }, \
+	{ "nd6_delay", CTLTYPE_INT }, \
+	{ "nd6_umaxtries", CTLTYPE_INT }, \
+	{ "nd6_mmaxtries", CTLTYPE_INT }, \
+	{ "nd6_useloopback", CTLTYPE_INT }, \
+	{ 0, 0 }, \
+	{ "nodeinfo", CTLTYPE_INT }, \
+	{ "errppslimit", CTLTYPE_INT }, \
+	{ "nd6_maxnudhint", CTLTYPE_INT }, \
+	{ "mtudisc_hiwat", CTLTYPE_INT }, \
+	{ "mtudisc_lowat", CTLTYPE_INT }, \
+	{ "nd6_debug", CTLTYPE_INT }, \
+	{ 0, 0 }, \
+	{ 0, 0 }, \
+	{ 0, 0 }, \
+	{ 0, 0 }, \
+	{ 0, 0 }, \
+	{ "nd6_maxqueuelen", CTLTYPE_INT }, \
+}
+
+#define RTF_PROBEMTU	RTF_PROTO1
+
+#ifdef _KERNEL
+struct	rtentry;
+struct	rttimer;
+struct	in6_multi;
+
+void	icmp6_init(void);
+void	icmp6_paramerror(struct mbuf *, int);
+void	icmp6_error(struct mbuf *, int, int, int);
+void	icmp6_error2(struct mbuf *, int, int, int, struct ifnet *);
+int	icmp6_input(struct mbuf **, int *, int);
+void	icmp6_fasttimo(void);
+void	icmp6_reflect(struct mbuf *, size_t);
+void	icmp6_prepare(struct mbuf *);
+void	icmp6_redirect_input(struct mbuf *, int);
+void	icmp6_redirect_output(struct mbuf *, struct rtentry *);
+int	icmp6_sysctl(int *, u_int, void *, size_t *, void *, size_t);
+
+void	icmp6_statinc(u_int);
+
+struct	ip6ctlparam;
+void	icmp6_mtudisc_update(struct ip6ctlparam *, int);
+void	icmp6_mtudisc_callback_register(void (*)(struct in6_addr *));
+
+/* XXX: is this the right place for these macros? */
+#define icmp6_ifstat_inc(ifp, tag) \
+do {								\
+	if (ifp)						\
+		((struct in6_ifextra *)((ifp)->if_afdata[AF_INET6]))->icmp6_ifstat->tag++; \
+} while (/*CONSTCOND*/ 0)
+
+#define icmp6_ifoutstat_inc(ifp, type, code) \
+do { \
+		icmp6_ifstat_inc(ifp, ifs6_out_msg); \
+		switch(type) { \
+		 case ICMP6_DST_UNREACH: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_dstunreach); \
+			 if (code == ICMP6_DST_UNREACH_ADMIN) \
+				 icmp6_ifstat_inc(ifp, ifs6_out_adminprohib); \
+			 break; \
+		 case ICMP6_PACKET_TOO_BIG: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_pkttoobig); \
+			 break; \
+		 case ICMP6_TIME_EXCEEDED: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_timeexceed); \
+			 break; \
+		 case ICMP6_PARAM_PROB: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_paramprob); \
+			 break; \
+		 case ICMP6_ECHO_REQUEST: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_echo); \
+			 break; \
+		 case ICMP6_ECHO_REPLY: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_echoreply); \
+			 break; \
+		 case MLD_LISTENER_QUERY: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_mldquery); \
+			 break; \
+		 case MLD_LISTENER_REPORT: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_mldreport); \
+			 break; \
+		 case MLD_LISTENER_DONE: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_mlddone); \
+			 break; \
+		 case ND_ROUTER_SOLICIT: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_routersolicit); \
+			 break; \
+		 case ND_ROUTER_ADVERT: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_routeradvert); \
+			 break; \
+		 case ND_NEIGHBOR_SOLICIT: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_neighborsolicit); \
+			 break; \
+		 case ND_NEIGHBOR_ADVERT: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_neighboradvert); \
+			 break; \
+		 case ND_REDIRECT: \
+			 icmp6_ifstat_inc(ifp, ifs6_out_redirect); \
+			 break; \
+		} \
+} while (/*CONSTCOND*/ 0)
+
+extern int	icmp6_rediraccept;	/* accept/process redirects */
+extern int	icmp6_redirtimeout;	/* cache time for redirect routes */
+#endif /* _KERNEL */
+
+#endif /* !_NETINET_ICMP6_H_ */
diff --git a/ndk/platforms/android-3/include/netinet/in.h b/ndk/platforms/android-3/include/netinet/in.h
index 7a4b6c7..01bf58e 100644
--- a/ndk/platforms/android-3/include/netinet/in.h
+++ b/ndk/platforms/android-3/include/netinet/in.h
@@ -32,6 +32,7 @@
 #include <linux/socket.h>
 #include <linux/in.h>
 #include <linux/in6.h>
+#include <linux/ipv6.h>
 #include <netinet/in6.h>
 
 __BEGIN_DECLS
diff --git a/ndk/platforms/android-3/include/netinet/in6.h b/ndk/platforms/android-3/include/netinet/in6.h
index e756583..eaf3c34 100644
--- a/ndk/platforms/android-3/include/netinet/in6.h
+++ b/ndk/platforms/android-3/include/netinet/in6.h
@@ -60,6 +60,10 @@
 #define IN6_IS_ADDR_SITELOCAL(a)	\
 	(((a)->s6_addr[0] == 0xfe) && (((a)->s6_addr[1] & 0xc0) == 0xc0))
 
+/* RFC 4193. */
+#define IN6_IS_ADDR_ULA(a)	\
+	(((a)->s6_addr[0] & 0xfe) == 0xfc)
+
 #define IN6_IS_ADDR_MULTICAST(a)	\
 	(((__const uint8_t *) (a))[0] == 0xff)
 
diff --git a/ndk/platforms/android-3/include/netinet/ip.h b/ndk/platforms/android-3/include/netinet/ip.h
index 541905c..629ed77 100644
--- a/ndk/platforms/android-3/include/netinet/ip.h
+++ b/ndk/platforms/android-3/include/netinet/ip.h
@@ -83,7 +83,7 @@
 #define	IPTOS_LOWDELAY		0x10
 #define	IPTOS_THROUGHPUT	0x08
 #define	IPTOS_RELIABILITY	0x04
-/*	IPTOS_LOWCOST		0x02 XXX */
+#define	IPTOS_MINCOST		0x02
 #if 1
 /* ECN RFC3168 obsoletes RFC2481, and these will be deprecated soon. */
 #define IPTOS_CE		0x01	/* congestion experienced */
diff --git a/ndk/platforms/android-3/include/netinet/ip6.h b/ndk/platforms/android-3/include/netinet/ip6.h
new file mode 100644
index 0000000..aa816c2
--- /dev/null
+++ b/ndk/platforms/android-3/include/netinet/ip6.h
@@ -0,0 +1,319 @@
+/*	$NetBSD: ip6.h,v 1.23 2007/12/25 18:33:46 perry Exp $	*/
+/*	$KAME: ip6.h,v 1.45 2003/06/05 04:46:38 keiichi Exp $	*/
+
+/*
+ * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the project nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+/*
+ * Copyright (c) 1982, 1986, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ *	@(#)ip.h	8.1 (Berkeley) 6/10/93
+ */
+
+#ifndef _NETINET_IP6_H_
+#define _NETINET_IP6_H_
+
+/*
+ * Definition for internet protocol version 6.
+ * RFC 2460
+ */
+
+struct ip6_hdr {
+	union {
+		struct ip6_hdrctl {
+			u_int32_t ip6_un1_flow;	/* 20 bits of flow-ID */
+			u_int16_t ip6_un1_plen;	/* payload length */
+			u_int8_t  ip6_un1_nxt;	/* next header */
+			u_int8_t  ip6_un1_hlim;	/* hop limit */
+		} ip6_un1;
+		u_int8_t ip6_un2_vfc;	/* 4 bits version, top 4 bits class */
+	} ip6_ctlun;
+	struct in6_addr ip6_src;	/* source address */
+	struct in6_addr ip6_dst;	/* destination address */
+} __packed;
+
+#define ip6_vfc		ip6_ctlun.ip6_un2_vfc
+#define ip6_flow	ip6_ctlun.ip6_un1.ip6_un1_flow
+#define ip6_plen	ip6_ctlun.ip6_un1.ip6_un1_plen
+#define ip6_nxt		ip6_ctlun.ip6_un1.ip6_un1_nxt
+#define ip6_hlim	ip6_ctlun.ip6_un1.ip6_un1_hlim
+#define ip6_hops	ip6_ctlun.ip6_un1.ip6_un1_hlim
+
+#define IPV6_VERSION		0x60
+#define IPV6_VERSION_MASK	0xf0
+
+#if BYTE_ORDER == BIG_ENDIAN
+#define IPV6_FLOWINFO_MASK	0x0fffffff	/* flow info (28 bits) */
+#define IPV6_FLOWLABEL_MASK	0x000fffff	/* flow label (20 bits) */
+#else
+#if BYTE_ORDER == LITTLE_ENDIAN
+#define IPV6_FLOWINFO_MASK	0xffffff0f	/* flow info (28 bits) */
+#define IPV6_FLOWLABEL_MASK	0xffff0f00	/* flow label (20 bits) */
+#endif /* LITTLE_ENDIAN */
+#endif
+#if 1
+/* ECN bits proposed by Sally Floyd */
+#define IP6TOS_CE		0x01	/* congestion experienced */
+#define IP6TOS_ECT		0x02	/* ECN-capable transport */
+#endif
+
+#ifdef _KERNEL
+/*
+ * for IPv6 pseudo header checksum
+ * XXX nonstandard
+ */
+struct ip6_hdr_pseudo {
+	struct in6_addr ip6ph_src;
+	struct in6_addr ip6ph_dst;
+	u_int32_t	ip6ph_len;
+	u_int8_t	ip6ph_zero[3];
+	u_int8_t	ip6ph_nxt;
+} __packed;
+#endif
+
+/*
+ * Extension Headers
+ */
+
+struct	ip6_ext {
+	u_int8_t ip6e_nxt;
+	u_int8_t ip6e_len;
+} __packed;
+
+/* Hop-by-Hop options header */
+/* XXX should we pad it to force alignment on an 8-byte boundary? */
+struct ip6_hbh {
+	u_int8_t ip6h_nxt;	/* next header */
+	u_int8_t ip6h_len;	/* length in units of 8 octets */
+	/* followed by options */
+} __packed;
+
+/* Destination options header */
+/* XXX should we pad it to force alignment on an 8-byte boundary? */
+struct ip6_dest {
+	u_int8_t ip6d_nxt;	/* next header */
+	u_int8_t ip6d_len;	/* length in units of 8 octets */
+	/* followed by options */
+} __packed;
+
+/* Option types and related macros */
+#define IP6OPT_PAD1		0x00	/* 00 0 00000 */
+#define IP6OPT_PADN		0x01	/* 00 0 00001 */
+#define IP6OPT_JUMBO		0xC2	/* 11 0 00010 = 194 */
+#define IP6OPT_NSAP_ADDR	0xC3	/* 11 0 00011 */
+#define IP6OPT_TUNNEL_LIMIT	0x04	/* 00 0 00100 */
+#define IP6OPT_RTALERT		0x05	/* 00 0 00101 (KAME definition) */
+#define IP6OPT_ROUTER_ALERT	0x05	/* (RFC3542 def, recommended) */
+
+#define IP6OPT_RTALERT_LEN	4
+#define IP6OPT_RTALERT_MLD	0	/* Datagram contains an MLD message */
+#define IP6OPT_RTALERT_RSVP	1	/* Datagram contains an RSVP message */
+#define IP6OPT_RTALERT_ACTNET	2 	/* contains an Active Networks msg */
+#define IP6OPT_MINLEN		2
+
+#define IP6OPT_TYPE(o)		((o) & 0xC0)
+#define IP6OPT_TYPE_SKIP	0x00
+#define IP6OPT_TYPE_DISCARD	0x40
+#define IP6OPT_TYPE_FORCEICMP	0x80
+#define IP6OPT_TYPE_ICMP	0xC0
+
+#define IP6OPT_MUTABLE		0x20
+
+/* IPv6 options: common part */
+struct ip6_opt {
+	u_int8_t ip6o_type;
+	u_int8_t ip6o_len;
+} __packed;
+
+/* Jumbo Payload Option */
+struct ip6_opt_jumbo {
+	u_int8_t ip6oj_type;
+	u_int8_t ip6oj_len;
+	u_int8_t ip6oj_jumbo_len[4];
+} __packed;
+#define IP6OPT_JUMBO_LEN 6
+
+/* NSAP Address Option */
+struct ip6_opt_nsap {
+	u_int8_t ip6on_type;
+	u_int8_t ip6on_len;
+	u_int8_t ip6on_src_nsap_len;
+	u_int8_t ip6on_dst_nsap_len;
+	/* followed by source NSAP */
+	/* followed by destination NSAP */
+} __packed;
+
+/* Tunnel Limit Option */
+struct ip6_opt_tunnel {
+	u_int8_t ip6ot_type;
+	u_int8_t ip6ot_len;
+	u_int8_t ip6ot_encap_limit;
+} __packed;
+
+/* Router Alert Option */
+struct ip6_opt_router {
+	u_int8_t ip6or_type;
+	u_int8_t ip6or_len;
+	u_int8_t ip6or_value[2];
+} __packed;
+/* Router alert values (in network byte order) */
+#if BYTE_ORDER == BIG_ENDIAN
+#define IP6_ALERT_MLD	0x0000
+#define IP6_ALERT_RSVP	0x0001
+#define IP6_ALERT_AN	0x0002
+#else
+#if BYTE_ORDER == LITTLE_ENDIAN
+#define IP6_ALERT_MLD	0x0000
+#define IP6_ALERT_RSVP	0x0100
+#define IP6_ALERT_AN	0x0200
+#endif /* LITTLE_ENDIAN */
+#endif
+
+/* Routing header */
+struct ip6_rthdr {
+	u_int8_t  ip6r_nxt;	/* next header */
+	u_int8_t  ip6r_len;	/* length in units of 8 octets */
+	u_int8_t  ip6r_type;	/* routing type */
+	u_int8_t  ip6r_segleft;	/* segments left */
+	/* followed by routing type specific data */
+} __packed;
+
+/* Type 0 Routing header */
+struct ip6_rthdr0 {
+	u_int8_t  ip6r0_nxt;		/* next header */
+	u_int8_t  ip6r0_len;		/* length in units of 8 octets */
+	u_int8_t  ip6r0_type;		/* always zero */
+	u_int8_t  ip6r0_segleft;	/* segments left */
+	u_int32_t ip6r0_reserved;	/* reserved field */
+} __packed;
+
+/* Fragment header */
+struct ip6_frag {
+	u_int8_t  ip6f_nxt;		/* next header */
+	u_int8_t  ip6f_reserved;	/* reserved field */
+	u_int16_t ip6f_offlg;		/* offset, reserved, and flag */
+	u_int32_t ip6f_ident;		/* identification */
+} __packed;
+
+#if BYTE_ORDER == BIG_ENDIAN
+#define IP6F_OFF_MASK		0xfff8	/* mask out offset from _offlg */
+#define IP6F_RESERVED_MASK	0x0006	/* reserved bits in ip6f_offlg */
+#define IP6F_MORE_FRAG		0x0001	/* more-fragments flag */
+#else /* BYTE_ORDER == LITTLE_ENDIAN */
+#define IP6F_OFF_MASK		0xf8ff	/* mask out offset from _offlg */
+#define IP6F_RESERVED_MASK	0x0600	/* reserved bits in ip6f_offlg */
+#define IP6F_MORE_FRAG		0x0100	/* more-fragments flag */
+#endif /* BYTE_ORDER == LITTLE_ENDIAN */
+
+/*
+ * Internet implementation parameters.
+ */
+#define IPV6_MAXHLIM	255	/* maximum hoplimit */
+#define IPV6_DEFHLIM	64	/* default hlim */
+#define IPV6_FRAGTTL	120	/* ttl for fragment packets, in slowtimo tick */
+#define IPV6_HLIMDEC	1	/* subtracted when forwarding */
+
+#define IPV6_MMTU	1280	/* minimal MTU and reassembly. 1024 + 256 */
+#define IPV6_MAXPACKET	65535	/* ip6 max packet size without Jumbo payload*/
+
+#ifdef _KERNEL
+/*
+ * IP6_EXTHDR_GET ensures that intermediate protocol header (from "off" to
+ * "len") is located in single mbuf, on contiguous memory region.
+ * The pointer to the region will be returned to pointer variable "val",
+ * with type "typ".
+ * IP6_EXTHDR_GET0 does the same, except that it aligns the structure at the
+ * very top of mbuf.  GET0 is likely to make memory copy than GET.
+ *
+ * XXX we're now testing this, needs m_pulldown()
+ */
+#define IP6_EXTHDR_GET(val, typ, m, off, len) \
+do {									\
+	struct mbuf *_t;						\
+	int _tmp;							\
+	if ((m)->m_len >= (off) + (len))				\
+		(val) = (typ)(mtod((m), char *) + (off));		\
+	else {								\
+		_t = m_pulldown((m), (off), (len), &_tmp);		\
+		if (_t) {						\
+			if (_t->m_len < _tmp + (len))			\
+				panic("m_pulldown malfunction");	\
+			(val) = (typ)(mtod(_t, char *) + _tmp);	\
+		} else {						\
+			(val) = (typ)NULL;				\
+			(m) = NULL;					\
+		}							\
+	}								\
+} while (/*CONSTCOND*/ 0)
+
+#define IP6_EXTHDR_GET0(val, typ, m, off, len) \
+do {									\
+	struct mbuf *_t;						\
+	if ((off) == 0 && (m)->m_len >= len)				\
+		(val) = (typ)mtod((m), void *);			\
+	else {								\
+		_t = m_pulldown((m), (off), (len), NULL);		\
+		if (_t) {						\
+			if (_t->m_len < (len))				\
+				panic("m_pulldown malfunction");	\
+			(val) = (typ)mtod(_t, void *);			\
+		} else {						\
+			(val) = (typ)NULL;				\
+			(m) = NULL;					\
+		}							\
+	}								\
+} while (/*CONSTCOND*/ 0)
+#endif /*_KERNEL*/
+
+#endif /* !_NETINET_IP6_H_ */
diff --git a/ndk/platforms/android-3/include/pthread.h b/ndk/platforms/android-3/include/pthread.h
index e3afdae..2a6029d 100644
--- a/ndk/platforms/android-3/include/pthread.h
+++ b/ndk/platforms/android-3/include/pthread.h
@@ -103,7 +103,7 @@
 /*
  * Prototypes
  */
-#if __cplusplus
+#ifdef __cplusplus
 extern "C" {
 #endif
 
@@ -231,7 +231,7 @@
         __pthread_cleanup_pop( &__cleanup, (execute)); \
     } while (0);
 
-#if __cplusplus
+#ifdef __cplusplus
 } /* extern "C" */
 #endif
 
@@ -240,4 +240,4 @@
 #define LONG_LONG_MAX __LONG_LONG_MAX__
 #define LONG_LONG_MIN (-__LONG_LONG_MAX__ - 1)
 
-#endif // _PTHREAD_H_
+#endif /* _PTHREAD_H_ */
diff --git a/ndk/platforms/android-3/include/signal.h b/ndk/platforms/android-3/include/signal.h
index 5540847..0bfd550 100644
--- a/ndk/platforms/android-3/include/signal.h
+++ b/ndk/platforms/android-3/include/signal.h
@@ -42,12 +42,15 @@
 
 typedef int sig_atomic_t;
 
-/* crepy NIG / _NSIG handling, just to be safe */
-#ifndef NSIG
-#  define NSIG  _NSIG
-#endif
+/* _NSIG is used by the SIGRTMAX definition under <asm/signal.h>, however
+ * its definition is part of a #if __KERNEL__ .. #endif block in the original
+ * kernel headers and is thus not part of our cleaned-up versions.
+ *
+ * Looking at the current kernel sources, it is defined as 64 for all
+ * architectures except for the 'mips' one which set it to 128.
+ */
 #ifndef _NSIG
-#  define _NSIG  NSIG
+#  define _NSIG  64
 #endif
 
 extern const char * const sys_siglist[];
diff --git a/ndk/platforms/android-3/include/sys/atomics.h b/ndk/platforms/android-3/include/sys/atomics.h
index d3fa145..3ada8de 100644
--- a/ndk/platforms/android-3/include/sys/atomics.h
+++ b/ndk/platforms/android-3/include/sys/atomics.h
@@ -33,10 +33,48 @@
 
 __BEGIN_DECLS
 
-extern int __atomic_cmpxchg(int old, int _new, volatile int *ptr);
-extern int __atomic_swap(int _new, volatile int *ptr);
-extern int __atomic_dec(volatile int *ptr);
-extern int __atomic_inc(volatile int *ptr);
+/* Note: atomic operations that were exported by the C library didn't
+ *       provide any memory barriers, which created potential issues on
+ *       multi-core devices. We now define them as inlined calls to
+ *       GCC sync builtins, which always provide a full barrier.
+ *
+ *       NOTE: The C library still exports atomic functions by the same
+ *              name to ensure ABI stability for existing NDK machine code.
+ *
+ *       If you are an NDK developer, we encourage you to rebuild your
+ *       unmodified sources against this header as soon as possible.
+ */
+#define __ATOMIC_INLINE__ static __inline__ __attribute__((always_inline))
+
+__ATOMIC_INLINE__ int
+__atomic_cmpxchg(int old, int _new, volatile int *ptr)
+{
+    /* We must return 0 on success */
+    return __sync_val_compare_and_swap(ptr, old, _new) != old;
+}
+
+__ATOMIC_INLINE__ int
+__atomic_swap(int _new, volatile int *ptr)
+{
+    int prev;
+    do {
+        prev = *ptr;
+    } while (__sync_val_compare_and_swap(ptr, prev, _new) != prev);
+    return prev;
+}
+
+__ATOMIC_INLINE__ int
+__atomic_dec(volatile int *ptr)
+{
+  return __sync_fetch_and_sub (ptr, 1);
+}
+
+__ATOMIC_INLINE__ int
+__atomic_inc(volatile int *ptr)
+{
+  return __sync_fetch_and_add (ptr, 1);
+}
+
 
 int __futex_wait(volatile void *ftx, int val, const struct timespec *timeout);
 int __futex_wake(volatile void *ftx, int count);
diff --git a/ndk/platforms/android-3/include/sys/cdefs.h b/ndk/platforms/android-3/include/sys/cdefs.h
index 2389437..27c575c 100644
--- a/ndk/platforms/android-3/include/sys/cdefs.h
+++ b/ndk/platforms/android-3/include/sys/cdefs.h
@@ -85,7 +85,7 @@
 #define	___STRING(x)	__STRING(x)
 #define	___CONCAT(x,y)	__CONCAT(x,y)
 
-#if __STDC__ || defined(__cplusplus)
+#if defined(__STDC__) || defined(__cplusplus)
 #define	__P(protos)	protos		/* full-blown ANSI C */
 #define	__CONCAT(x,y)	x ## y
 #define	__STRING(x)	#x
@@ -219,7 +219,7 @@
  * C99 defines the restrict type qualifier keyword, which was made available
  * in GCC 2.92.
  */
-#if __STDC_VERSION__ >= 199901L
+#if defined(__STDC__VERSION__) && __STDC_VERSION__ >= 199901L
 #define	__restrict	restrict
 #else
 #if !__GNUC_PREREQ__(2, 92)
@@ -231,7 +231,7 @@
  * C99 defines __func__ predefined identifier, which was made available
  * in GCC 2.95.
  */
-#if !(__STDC_VERSION__ >= 199901L)
+#if !defined(__STDC_VERSION__) || !(__STDC_VERSION__ >= 199901L)
 #if __GNUC_PREREQ__(2, 6)
 #define	__func__	__PRETTY_FUNCTION__
 #elif __GNUC_PREREQ__(2, 4)
@@ -503,5 +503,6 @@
 #endif
 
 #define  __BIONIC__   1
+#include <android/api-level.h>
 
 #endif /* !_SYS_CDEFS_H_ */
diff --git a/ndk/platforms/android-3/include/sys/cdefs_elf.h b/ndk/platforms/android-3/include/sys/cdefs_elf.h
index e051b1d..1e57470 100644
--- a/ndk/platforms/android-3/include/sys/cdefs_elf.h
+++ b/ndk/platforms/android-3/include/sys/cdefs_elf.h
@@ -95,6 +95,10 @@
 	__asm__(".section _sec\n\t.asciz _str\n\t.previous")
 #endif
 
+/* GCC visibility helper macro */
+#define __LIBC_HIDDEN__							\
+	__attribute__ ((visibility ("hidden")))
+
 #define	__IDSTRING(_n,_s)		__SECTIONSTRING(.ident,_s)
 
 #define	__RCSID(_s)			__IDSTRING(rcsid,_s)
diff --git a/ndk/platforms/android-3/include/sys/prctl.h b/ndk/platforms/android-3/include/sys/prctl.h
index ce85bf7..359d684 100644
--- a/ndk/platforms/android-3/include/sys/prctl.h
+++ b/ndk/platforms/android-3/include/sys/prctl.h
@@ -32,8 +32,13 @@
 
 __BEGIN_DECLS
 
-extern int prctl(int option, unsigned long arg2, unsigned long arg3 , unsigned
-               long arg4, unsigned long arg5);
+/* IMPORTANT NOTE: This function is declared as taking a variable number
+ *                 of arguments to match the GLibc definition. However
+ *                 its declaration inside SYSCALLS.TXT *must* make it
+ *                 take 6 arguments to ensure consistency with the kernel
+ *                 implementation.
+ */
+extern int prctl(int option, ...);
 
 __END_DECLS
 
diff --git a/ndk/platforms/android-3/include/unistd.h b/ndk/platforms/android-3/include/unistd.h
index 25fc334..53088d4 100644
--- a/ndk/platforms/android-3/include/unistd.h
+++ b/ndk/platforms/android-3/include/unistd.h
@@ -70,8 +70,9 @@
 extern int execle(const char *, const char *, ...);
 extern int capget(cap_user_header_t hdrp, cap_user_data_t datap);
 extern int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
-extern int prctl(int  option,  unsigned long arg2, unsigned long arg3,
-                 unsigned long arg4, unsigned long arg5);
+
+/* IMPORTANT: See comment under <sys/prctl.h> about this declaration */
+extern int prctl(int  option, ...);
 
 extern int nice(int);
 
@@ -121,7 +122,7 @@
 
 extern int close(int);
 extern off_t lseek(int, off_t, int);
-extern loff_t lseek64(int, loff_t, int);
+extern off64_t lseek64(int, off64_t, int);
 
 extern ssize_t read(int, void *, size_t);
 extern ssize_t write(int, const void *, size_t);
diff --git a/ndk/platforms/android-5/include/pthread.h b/ndk/platforms/android-5/include/pthread.h
index 6603b3f..a20a52d 100644
--- a/ndk/platforms/android-5/include/pthread.h
+++ b/ndk/platforms/android-5/include/pthread.h
@@ -103,7 +103,7 @@
 /*
  * Prototypes
  */
-#if __cplusplus
+#ifdef __cplusplus
 extern "C" {
 #endif
 
@@ -258,7 +258,7 @@
         __pthread_cleanup_pop( &__cleanup, (execute)); \
     } while (0);
 
-#if __cplusplus
+#ifdef __cplusplus
 } /* extern "C" */
 #endif
 
@@ -267,4 +267,4 @@
 #define LONG_LONG_MAX __LONG_LONG_MAX__
 #define LONG_LONG_MIN (-__LONG_LONG_MAX__ - 1)
 
-#endif // _PTHREAD_H_
+#endif /* _PTHREAD_H_ */
diff --git a/ndk/platforms/android-8/include/dlfcn.h b/ndk/platforms/android-8/include/dlfcn.h
index f84d1d1..7daa8f7 100644
--- a/ndk/platforms/android-8/include/dlfcn.h
+++ b/ndk/platforms/android-8/include/dlfcn.h
@@ -47,7 +47,7 @@
 extern int          dlclose(void*  handle);
 extern const char*  dlerror(void);
 extern void*        dlsym(void*  handle, const char*  symbol);
-extern int          dladdr(void* addr, Dl_info *info);
+extern int          dladdr(const void* addr, Dl_info *info);
 
 enum {
   RTLD_NOW  = 0,
diff --git a/ndk/platforms/android-8/include/pthread.h b/ndk/platforms/android-8/include/pthread.h
index eb2d169..f7a596a 100644
--- a/ndk/platforms/android-8/include/pthread.h
+++ b/ndk/platforms/android-8/include/pthread.h
@@ -103,7 +103,7 @@
 /*
  * Prototypes
  */
-#if __cplusplus
+#ifdef __cplusplus
 extern "C" {
 #endif
 
@@ -263,7 +263,7 @@
         __pthread_cleanup_pop( &__cleanup, (execute)); \
     } while (0);
 
-#if __cplusplus
+#ifdef __cplusplus
 } /* extern "C" */
 #endif
 
@@ -272,4 +272,4 @@
 #define LONG_LONG_MAX __LONG_LONG_MAX__
 #define LONG_LONG_MIN (-__LONG_LONG_MAX__ - 1)
 
-#endif // _PTHREAD_H_
+#endif /* _PTHREAD_H_ */
diff --git a/ndk/platforms/android-8/include/signal.h b/ndk/platforms/android-8/include/signal.h
index 4401164..91c3b00 100644
--- a/ndk/platforms/android-8/include/signal.h
+++ b/ndk/platforms/android-8/include/signal.h
@@ -42,12 +42,15 @@
 
 typedef int sig_atomic_t;
 
-/* crepy NIG / _NSIG handling, just to be safe */
-#ifndef NSIG
-#  define NSIG  _NSIG
-#endif
+/* _NSIG is used by the SIGRTMAX definition under <asm/signal.h>, however
+ * its definition is part of a #if __KERNEL__ .. #endif block in the original
+ * kernel headers and is thus not part of our cleaned-up versions.
+ *
+ * Looking at the current kernel sources, it is defined as 64 for all
+ * architectures except for the 'mips' one which set it to 128.
+ */
 #ifndef _NSIG
-#  define _NSIG  NSIG
+#  define _NSIG  64
 #endif
 
 extern const char * const sys_siglist[];
diff --git a/ndk/platforms/android-8/include/unistd.h b/ndk/platforms/android-8/include/unistd.h
index 863d56d..ab8aee2 100644
--- a/ndk/platforms/android-8/include/unistd.h
+++ b/ndk/platforms/android-8/include/unistd.h
@@ -70,8 +70,9 @@
 extern int execle(const char *, const char *, ...);
 extern int capget(cap_user_header_t hdrp, cap_user_data_t datap);
 extern int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
-extern int prctl(int  option,  unsigned long arg2, unsigned long arg3,
-                 unsigned long arg4, unsigned long arg5);
+
+/* IMPORTANT: See comment under <sys/prctl.h> about this declaration */
+extern int prctl(int  option, ...);
 
 extern int nice(int);
 
@@ -125,7 +126,7 @@
 
 extern int close(int);
 extern off_t lseek(int, off_t, int);
-extern loff_t lseek64(int, loff_t, int);
+extern off64_t lseek64(int, off64_t, int);
 
 extern ssize_t read(int, void *, size_t);
 extern ssize_t write(int, const void *, size_t);
diff --git a/ndk/platforms/android-9/include/android/native_activity.h b/ndk/platforms/android-9/include/android/native_activity.h
index d89bc8b..52997bf 100644
--- a/ndk/platforms/android-9/include/android/native_activity.h
+++ b/ndk/platforms/android-9/include/android/native_activity.h
@@ -60,7 +60,14 @@
     JNIEnv* env;
 
     /**
-     * The NativeActivity Java class.
+     * The NativeActivity object handle.
+     *
+     * IMPORTANT NOTE: This member is mis-named. It should really be named
+     * 'activity' instead of 'clazz', since it's a reference to the
+     * NativeActivity instance created by the system for you.
+     *
+     * We unfortunately cannot change this without breaking NDK
+     * source-compatibility.
      */
     jobject clazz;
 
diff --git a/ndk/platforms/android-9/include/pthread.h b/ndk/platforms/android-9/include/pthread.h
index 5e87043..4baf82f 100644
--- a/ndk/platforms/android-9/include/pthread.h
+++ b/ndk/platforms/android-9/include/pthread.h
@@ -103,7 +103,7 @@
 /*
  * Prototypes
  */
-#if __cplusplus
+#ifdef __cplusplus
 extern "C" {
 #endif
 
@@ -302,7 +302,7 @@
         __pthread_cleanup_pop( &__cleanup, (execute)); \
     } while (0);
 
-#if __cplusplus
+#ifdef __cplusplus
 } /* extern "C" */
 #endif
 
@@ -311,4 +311,4 @@
 #define LONG_LONG_MAX __LONG_LONG_MAX__
 #define LONG_LONG_MIN (-__LONG_LONG_MAX__ - 1)
 
-#endif // _PTHREAD_H_
+#endif /* _PTHREAD_H_ */
diff --git a/ndk/platforms/android-9/arch-x86/include/sys/atomics.h b/ndk/platforms/android-9/include/sys/eventfd.h
similarity index 62%
copy from ndk/platforms/android-9/arch-x86/include/sys/atomics.h
copy to ndk/platforms/android-9/include/sys/eventfd.h
index 7aed3ae..19244a5 100644
--- a/ndk/platforms/android-9/arch-x86/include/sys/atomics.h
+++ b/ndk/platforms/android-9/include/sys/eventfd.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2011 The Android Open Source Project
+ * Copyright (C) 2008 The Android Open Source Project
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -25,41 +25,26 @@
  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  * SUCH DAMAGE.
  */
-#ifndef _SYS_ATOMICS_H
-#define _SYS_ATOMICS_H
+#ifndef _SYS_EVENTFD_H
+#define _SYS_EVENTFD_H
 
 #include <sys/cdefs.h>
-#include <sys/time.h>
+#include <fcntl.h>
 
 __BEGIN_DECLS
 
-static inline __attribute__((always_inline)) int
-__atomic_cmpxchg(int old, int _new, volatile int *ptr)
-{
-  return !__sync_bool_compare_and_swap (ptr, old, _new);
-}
+#define  EFD_CLOEXEC   O_CLOEXEC
+#define  EFD_NONBLOCK  O_NONBLOCK
 
-static inline __attribute__((always_inline)) int
-__atomic_swap(int _new, volatile int *ptr)
-{
-  return __sync_lock_test_and_set(ptr, _new);
-}
+/* type of event counter */
+typedef uint64_t  eventfd_t;
 
-static inline __attribute__((always_inline)) int
-__atomic_dec(volatile int *ptr)
-{
-  return __sync_fetch_and_sub (ptr, 1);
-}
+extern int eventfd(unsigned int initval, int flags);
 
-static inline __attribute__((always_inline)) int
-__atomic_inc(volatile int *ptr)
-{
-  return __sync_fetch_and_add (ptr, 1);
-}
-
-int __futex_wait(volatile void *ftx, int val, const struct timespec *timeout);
-int __futex_wake(volatile void *ftx, int count);
+/* Compatibility with GLibc */
+extern int eventfd_read(int fd, eventfd_t *counter);
+extern int eventfd_write(int fd, const eventfd_t counter);
 
 __END_DECLS
 
-#endif /* _SYS_ATOMICS_H */
+#endif /* _SYS_EVENTFD_H */
diff --git a/ndk/platforms/android-9/include/unistd.h b/ndk/platforms/android-9/include/unistd.h
index 21154ad..f92ec10 100644
--- a/ndk/platforms/android-9/include/unistd.h
+++ b/ndk/platforms/android-9/include/unistd.h
@@ -70,8 +70,9 @@
 extern int execle(const char *, const char *, ...);
 extern int capget(cap_user_header_t hdrp, cap_user_data_t datap);
 extern int capset(cap_user_header_t hdrp, const cap_user_data_t datap);
-extern int prctl(int  option,  unsigned long arg2, unsigned long arg3,
-                 unsigned long arg4, unsigned long arg5);
+
+/* IMPORTANT: See comment under <sys/prctl.h> about this declaration */
+extern int prctl(int  option, ...);
 
 extern int nice(int);
 
@@ -128,7 +129,7 @@
 
 extern int close(int);
 extern off_t lseek(int, off_t, int);
-extern loff_t lseek64(int, loff_t, int);
+extern off64_t lseek64(int, off64_t, int);
 
 extern ssize_t read(int, void *, size_t);
 extern ssize_t write(int, const void *, size_t);
diff --git a/ndk/sources/android/native_app_glue/android_native_app_glue.c b/ndk/sources/android/native_app_glue/android_native_app_glue.c
index 3069f17..82fc030 100644
--- a/ndk/sources/android/native_app_glue/android_native_app_glue.c
+++ b/ndk/sources/android/native_app_glue/android_native_app_glue.c
@@ -26,6 +26,14 @@
 #include <android/log.h>
 
 #define LOGI(...) ((void)__android_log_print(ANDROID_LOG_INFO, "threaded_app", __VA_ARGS__))
+#define LOGE(...) ((void)__android_log_print(ANDROID_LOG_ERROR, "threaded_app", __VA_ARGS__))
+
+/* For debug builds, always enable the debug traces in this library */
+#ifndef NDEBUG
+#  define LOGV(...)  ((void)__android_log_print(ANDROID_LOG_VERBOSE, "threaded_app", __VA_ARGS__))
+#else
+#  define LOGV(...)  ((void)0)
+#endif
 
 static void free_saved_state(struct android_app* android_app) {
     pthread_mutex_lock(&android_app->mutex);
@@ -47,7 +55,7 @@
         }
         return cmd;
     } else {
-        LOGI("No data on command pipe!");
+        LOGE("No data on command pipe!");
     }
     return -1;
 }
@@ -57,7 +65,7 @@
     AConfiguration_getLanguage(android_app->config, lang);
     AConfiguration_getCountry(android_app->config, country);
 
-    LOGI("Config: mcc=%d mnc=%d lang=%c%c cnt=%c%c orien=%d touch=%d dens=%d "
+    LOGV("Config: mcc=%d mnc=%d lang=%c%c cnt=%c%c orien=%d touch=%d dens=%d "
             "keys=%d nav=%d keysHid=%d navHid=%d sdk=%d size=%d long=%d "
             "modetype=%d modenight=%d",
             AConfiguration_getMcc(android_app->config),
@@ -80,14 +88,14 @@
 void android_app_pre_exec_cmd(struct android_app* android_app, int8_t cmd) {
     switch (cmd) {
         case APP_CMD_INPUT_CHANGED:
-            LOGI("APP_CMD_INPUT_CHANGED\n");
+            LOGV("APP_CMD_INPUT_CHANGED\n");
             pthread_mutex_lock(&android_app->mutex);
             if (android_app->inputQueue != NULL) {
                 AInputQueue_detachLooper(android_app->inputQueue);
             }
             android_app->inputQueue = android_app->pendingInputQueue;
             if (android_app->inputQueue != NULL) {
-                LOGI("Attaching input queue to looper");
+                LOGV("Attaching input queue to looper");
                 AInputQueue_attachLooper(android_app->inputQueue,
                         android_app->looper, LOOPER_ID_INPUT, NULL,
                         &android_app->inputPollSource);
@@ -97,7 +105,7 @@
             break;
 
         case APP_CMD_INIT_WINDOW:
-            LOGI("APP_CMD_INIT_WINDOW\n");
+            LOGV("APP_CMD_INIT_WINDOW\n");
             pthread_mutex_lock(&android_app->mutex);
             android_app->window = android_app->pendingWindow;
             pthread_cond_broadcast(&android_app->cond);
@@ -105,7 +113,7 @@
             break;
 
         case APP_CMD_TERM_WINDOW:
-            LOGI("APP_CMD_TERM_WINDOW\n");
+            LOGV("APP_CMD_TERM_WINDOW\n");
             pthread_cond_broadcast(&android_app->cond);
             break;
 
@@ -113,7 +121,7 @@
         case APP_CMD_START:
         case APP_CMD_PAUSE:
         case APP_CMD_STOP:
-            LOGI("activityState=%d\n", cmd);
+            LOGV("activityState=%d\n", cmd);
             pthread_mutex_lock(&android_app->mutex);
             android_app->activityState = cmd;
             pthread_cond_broadcast(&android_app->cond);
@@ -121,14 +129,14 @@
             break;
 
         case APP_CMD_CONFIG_CHANGED:
-            LOGI("APP_CMD_CONFIG_CHANGED\n");
+            LOGV("APP_CMD_CONFIG_CHANGED\n");
             AConfiguration_fromAssetManager(android_app->config,
                     android_app->activity->assetManager);
             print_cur_config(android_app);
             break;
 
         case APP_CMD_DESTROY:
-            LOGI("APP_CMD_DESTROY\n");
+            LOGV("APP_CMD_DESTROY\n");
             android_app->destroyRequested = 1;
             break;
     }
@@ -137,7 +145,7 @@
 void android_app_post_exec_cmd(struct android_app* android_app, int8_t cmd) {
     switch (cmd) {
         case APP_CMD_TERM_WINDOW:
-            LOGI("APP_CMD_TERM_WINDOW\n");
+            LOGV("APP_CMD_TERM_WINDOW\n");
             pthread_mutex_lock(&android_app->mutex);
             android_app->window = NULL;
             pthread_cond_broadcast(&android_app->cond);
@@ -145,7 +153,7 @@
             break;
 
         case APP_CMD_SAVE_STATE:
-            LOGI("APP_CMD_SAVE_STATE\n");
+            LOGV("APP_CMD_SAVE_STATE\n");
             pthread_mutex_lock(&android_app->mutex);
             android_app->stateSaved = 1;
             pthread_cond_broadcast(&android_app->cond);
@@ -163,7 +171,7 @@
 }
 
 static void android_app_destroy(struct android_app* android_app) {
-    LOGI("android_app_destroy!");
+    LOGV("android_app_destroy!");
     free_saved_state(android_app);
     pthread_mutex_lock(&android_app->mutex);
     if (android_app->inputQueue != NULL) {
@@ -179,7 +187,7 @@
 static void process_input(struct android_app* app, struct android_poll_source* source) {
     AInputEvent* event = NULL;
     if (AInputQueue_getEvent(app->inputQueue, &event) >= 0) {
-        LOGI("New input event: type=%d\n", AInputEvent_getType(event));
+        LOGV("New input event: type=%d\n", AInputEvent_getType(event));
         if (AInputQueue_preDispatchEvent(app->inputQueue, event)) {
             return;
         }
@@ -187,7 +195,7 @@
         if (app->onInputEvent != NULL) handled = app->onInputEvent(app, event);
         AInputQueue_finishEvent(app->inputQueue, event, handled);
     } else {
-        LOGI("Failure reading next input event: %s\n", strerror(errno));
+        LOGE("Failure reading next input event: %s\n", strerror(errno));
     }
 }
 
@@ -250,7 +258,8 @@
 
     int msgpipe[2];
     if (pipe(msgpipe)) {
-        LOGI("could not create pipe: %s", strerror(errno));
+        LOGE("could not create pipe: %s", strerror(errno));
+        return NULL;
     }
     android_app->msgread = msgpipe[0];
     android_app->msgwrite = msgpipe[1];
@@ -272,7 +281,7 @@
 
 static void android_app_write_cmd(struct android_app* android_app, int8_t cmd) {
     if (write(android_app->msgwrite, &cmd, sizeof(cmd)) != sizeof(cmd)) {
-        LOGI("Failure writing android_app cmd: %s\n", strerror(errno));
+        LOGE("Failure writing android_app cmd: %s\n", strerror(errno));
     }
 }
 
@@ -326,17 +335,17 @@
 }
 
 static void onDestroy(ANativeActivity* activity) {
-    LOGI("Destroy: %p\n", activity);
+    LOGV("Destroy: %p\n", activity);
     android_app_free((struct android_app*)activity->instance);
 }
 
 static void onStart(ANativeActivity* activity) {
-    LOGI("Start: %p\n", activity);
+    LOGV("Start: %p\n", activity);
     android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_START);
 }
 
 static void onResume(ANativeActivity* activity) {
-    LOGI("Resume: %p\n", activity);
+    LOGV("Resume: %p\n", activity);
     android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_RESUME);
 }
 
@@ -344,7 +353,7 @@
     struct android_app* android_app = (struct android_app*)activity->instance;
     void* savedState = NULL;
 
-    LOGI("SaveInstanceState: %p\n", activity);
+    LOGV("SaveInstanceState: %p\n", activity);
     pthread_mutex_lock(&android_app->mutex);
     android_app->stateSaved = 0;
     android_app_write_cmd(android_app, APP_CMD_SAVE_STATE);
@@ -365,56 +374,56 @@
 }
 
 static void onPause(ANativeActivity* activity) {
-    LOGI("Pause: %p\n", activity);
+    LOGV("Pause: %p\n", activity);
     android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_PAUSE);
 }
 
 static void onStop(ANativeActivity* activity) {
-    LOGI("Stop: %p\n", activity);
+    LOGV("Stop: %p\n", activity);
     android_app_set_activity_state((struct android_app*)activity->instance, APP_CMD_STOP);
 }
 
 static void onConfigurationChanged(ANativeActivity* activity) {
     struct android_app* android_app = (struct android_app*)activity->instance;
-    LOGI("ConfigurationChanged: %p\n", activity);
+    LOGV("ConfigurationChanged: %p\n", activity);
     android_app_write_cmd(android_app, APP_CMD_CONFIG_CHANGED);
 }
 
 static void onLowMemory(ANativeActivity* activity) {
     struct android_app* android_app = (struct android_app*)activity->instance;
-    LOGI("LowMemory: %p\n", activity);
+    LOGV("LowMemory: %p\n", activity);
     android_app_write_cmd(android_app, APP_CMD_LOW_MEMORY);
 }
 
 static void onWindowFocusChanged(ANativeActivity* activity, int focused) {
-    LOGI("WindowFocusChanged: %p -- %d\n", activity, focused);
+    LOGV("WindowFocusChanged: %p -- %d\n", activity, focused);
     android_app_write_cmd((struct android_app*)activity->instance,
             focused ? APP_CMD_GAINED_FOCUS : APP_CMD_LOST_FOCUS);
 }
 
 static void onNativeWindowCreated(ANativeActivity* activity, ANativeWindow* window) {
-    LOGI("NativeWindowCreated: %p -- %p\n", activity, window);
+    LOGV("NativeWindowCreated: %p -- %p\n", activity, window);
     android_app_set_window((struct android_app*)activity->instance, window);
 }
 
 static void onNativeWindowDestroyed(ANativeActivity* activity, ANativeWindow* window) {
-    LOGI("NativeWindowDestroyed: %p -- %p\n", activity, window);
+    LOGV("NativeWindowDestroyed: %p -- %p\n", activity, window);
     android_app_set_window((struct android_app*)activity->instance, NULL);
 }
 
 static void onInputQueueCreated(ANativeActivity* activity, AInputQueue* queue) {
-    LOGI("InputQueueCreated: %p -- %p\n", activity, queue);
+    LOGV("InputQueueCreated: %p -- %p\n", activity, queue);
     android_app_set_input((struct android_app*)activity->instance, queue);
 }
 
 static void onInputQueueDestroyed(ANativeActivity* activity, AInputQueue* queue) {
-    LOGI("InputQueueDestroyed: %p -- %p\n", activity, queue);
+    LOGV("InputQueueDestroyed: %p -- %p\n", activity, queue);
     android_app_set_input((struct android_app*)activity->instance, NULL);
 }
 
 void ANativeActivity_onCreate(ANativeActivity* activity,
         void* savedState, size_t savedStateSize) {
-    LOGI("Creating: %p\n", activity);
+    LOGV("Creating: %p\n", activity);
     activity->callbacks->onDestroy = onDestroy;
     activity->callbacks->onStart = onStart;
     activity->callbacks->onResume = onResume;
diff --git a/samples/ApiDemos/AndroidManifest.xml b/samples/ApiDemos/AndroidManifest.xml
index 9cd9d95..240eac5 100644
--- a/samples/ApiDemos/AndroidManifest.xml
+++ b/samples/ApiDemos/AndroidManifest.xml
@@ -885,6 +885,16 @@
             </intent-filter>
         </activity>
 
+        <!-- Accessibility Samples -->
+        <activity android:name=".accessibility.AccessibilityNodeProviderActivity"
+                android:label="@string/accessibility_node_provider"
+                android:enabled="@bool/atLeastIceCreamSandwich">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="android.intent.category.SAMPLE_CODE" />
+            </intent-filter>
+        </activity>
+
         <!-- Application Updating Samples -->
 
 <!-- BEGIN_INCLUDE(app_update_declaration) -->
diff --git a/samples/ApiDemos/_index.html b/samples/ApiDemos/_index.html
index 3c45843..421eca6 100644
--- a/samples/ApiDemos/_index.html
+++ b/samples/ApiDemos/_index.html
@@ -1,19 +1,19 @@
-<p>The API Demos application includes a variety of small applications 
+<p>The API Demos application includes a variety of small applications
 that illustrate the use of various Android APIs. It includes samples of:
 </p>
 <ul>
-  <li>Notifications</li>  
-  <li>Alarms</li>  
-  <li>Progress Dialogs</li>  
-  <li>Intents</li>  
-  <li>Menus</li>  
-  <li>Search</li>  
-  <li>Persistent application state</li>  
-  <li>Preferences</li>  
-  <li>Background Services</li>  
-  <li>App Widgets</li>  
-  <li>Voice Recognition</li>  
-  <li>And many many more...</li>  
+  <li>Notifications</li>
+  <li>Alarms</li>
+  <li>Progress Dialogs</li>
+  <li>Intents</li>
+  <li>Menus</li>
+  <li>Search</li>
+  <li>Persistent application state</li>
+  <li>Preferences</li>
+  <li>Background Services</li>
+  <li>App Widgets</li>
+  <li>Voice Recognition</li>
+  <li>And many many more...</li>
 </ul>
 
 <div class="note">
@@ -36,6 +36,7 @@
 <li><a href="src/com/example/android/apis/graphics/TouchPaint.html">Stylus and hover
 support</a></li>
 <li><a href="src/com/example/android/apis/view/Switches.html">Switch widget</a></li>
+<li><a href="src/com/example/android/apis/accessibility/AccessibilityNodeProviderActivity.html">Accessibility Node Provider</a></li>
 <li><a
   href="src/com/example/android/apis/accessibility/TaskBackService.html">Window
   Querying Accessibility Service</a></li>
diff --git a/samples/ApiDemos/res/layout/accessibility_node_provider.xml b/samples/ApiDemos/res/layout/accessibility_node_provider.xml
new file mode 100644
index 0000000..cc10c9c
--- /dev/null
+++ b/samples/ApiDemos/res/layout/accessibility_node_provider.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2011 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    android:orientation="vertical">
+
+    <TextView
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginBottom="50dip"
+        android:text="@string/accessibility_node_provider_instructions">
+    </TextView>
+
+    <view
+        class="com.example.android.apis.accessibility.AccessibilityNodeProviderActivity$VirtualSubtreeRootView"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content" >
+    </view>
+
+</LinearLayout>
diff --git a/samples/ApiDemos/res/values/strings.xml b/samples/ApiDemos/res/values/strings.xml
index 99e2463..4e675e1 100644
--- a/samples/ApiDemos/res/values/strings.xml
+++ b/samples/ApiDemos/res/values/strings.xml
@@ -1290,6 +1290,10 @@
     <!--  Accessibility examples strings  -->
     <!-- ============================ -->
 
+    <string name="accessibility_node_provider">Accessibility/Accessibility Node Provider</string>
+    <string name="accessibility_node_provider_instructions">Enable TalkBack and Explore-by-touch from accessibility
+        settings. Then touch the colored squares.</string>
+
     <string name="accessibility_service">Accessibility/Accessibility Service</string>
     <string name="accessibility_service_label">ClockBack</string>
     <string name="accessibility_service_instructions">
diff --git a/samples/ApiDemos/src/com/example/android/apis/accessibility/AccessibilityNodeProviderActivity.java b/samples/ApiDemos/src/com/example/android/apis/accessibility/AccessibilityNodeProviderActivity.java
new file mode 100644
index 0000000..16914c7
--- /dev/null
+++ b/samples/ApiDemos/src/com/example/android/apis/accessibility/AccessibilityNodeProviderActivity.java
@@ -0,0 +1,484 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.android.apis.accessibility;
+
+import com.example.android.apis.R;
+
+import android.app.Activity;
+import android.app.Service;
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.Rect;
+import android.os.Bundle;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.accessibility.AccessibilityEvent;
+import android.view.accessibility.AccessibilityManager;
+import android.view.accessibility.AccessibilityNodeInfo;
+import android.view.accessibility.AccessibilityNodeProvider;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * This sample demonstrates how a View can expose a virtual view sub-tree
+ * rooted at it. A virtual sub-tree is composed of imaginary Views
+ * that are reported as a part of the view hierarchy for accessibility
+ * purposes. This enables custom views that draw complex content to report
+ * them selves as a tree of virtual views, thus conveying their logical
+ * structure.
+ * <p>
+ * For example, a View may draw a monthly calendar as a grid of days while
+ * each such day may contains some events. From a perspective of the View
+ * hierarchy the calendar is composed of a single View but an accessibility
+ * service would benefit of traversing the logical structure of the calendar
+ * by examining each day and each event on that day.
+ * </p>
+ */
+public class AccessibilityNodeProviderActivity extends Activity {
+    /** Called when the activity is first created. */
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        setContentView(R.layout.accessibility_node_provider);
+    }
+
+   /**
+    * This class presents a View that is composed of three virtual children
+    * each of which is drawn with a different color and represents a region
+    * of the View that has different semantics compared to other such regions.
+    * While the virtual view tree exposed by this class is one level deep
+    * for simplicity, there is no bound on the complexity of that virtual
+    * sub-tree.
+    */
+    public static class VirtualSubtreeRootView extends View {
+
+        /** Paint object for drawing the virtual sub-tree */
+        private final Paint mPaint = new Paint();
+
+        /** Temporary rectangle to minimize object creation. */
+        private final Rect mTempRect = new Rect();
+
+        /** Handle to the system accessibility service. */
+        private final AccessibilityManager mAccessibilityManager;
+
+        /** The virtual children of this View. */
+        private final List<VirtualView> mChildren = new ArrayList<VirtualView>();
+
+        /** The instance of the node provider for the virtual tree - lazily instantiated. */
+        private AccessibilityNodeProvider mAccessibilityNodeProvider;
+
+        /** The last hovered child used for event dispatching. */
+        private VirtualView mLastHoveredChild;
+
+        public VirtualSubtreeRootView(Context context, AttributeSet attrs) {
+            super(context, attrs);
+            mAccessibilityManager = (AccessibilityManager) context.getSystemService(
+                    Service.ACCESSIBILITY_SERVICE);
+            createVirtualChildren();
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public AccessibilityNodeProvider getAccessibilityNodeProvider() {
+            // Instantiate the provide only when requested. Since the system
+            // will call this method multiple times it is a good practice to
+            // cache the provider instance.
+            if (mAccessibilityNodeProvider == null) {
+                mAccessibilityNodeProvider = new VirtualDescendantsProvider();
+            }
+            return mAccessibilityNodeProvider;
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public boolean dispatchHoverEvent(MotionEvent event) {
+            // This implementation assumes that the virtual children
+            // cannot overlap and are always visible. Do NOT use this
+            // code as a reference of how to implement hover event
+            // dispatch. Instead, refer to ViewGroup#dispatchHoverEvent.
+            boolean handled = false;
+            List<VirtualView> children = mChildren;
+            final int childCount = children.size();
+            for (int i = 0; i < childCount; i++) {
+                VirtualView child = children.get(i);
+                Rect childBounds = child.mBounds;
+                final int childCoordsX = (int) event.getX() + getScrollX();
+                final int childCoordsY = (int) event.getY() + getScrollY();
+                if (!childBounds.contains(childCoordsX, childCoordsY)) {
+                    continue;
+                }
+                final int action = event.getAction();
+                switch (action) {
+                    case MotionEvent.ACTION_HOVER_ENTER: {
+                        mLastHoveredChild = child;
+                        handled |= onHoverVirtualView(child, event);
+                        event.setAction(action);
+                    } break;
+                    case MotionEvent.ACTION_HOVER_MOVE: {
+                        if (child == mLastHoveredChild) {
+                            handled |= onHoverVirtualView(child, event);
+                            event.setAction(action);
+                        } else {
+                            MotionEvent eventNoHistory = event.getHistorySize() > 0
+                                ? MotionEvent.obtainNoHistory(event) : event;
+                            eventNoHistory.setAction(MotionEvent.ACTION_HOVER_EXIT);
+                            onHoverVirtualView(mLastHoveredChild, eventNoHistory);
+                            eventNoHistory.setAction(MotionEvent.ACTION_HOVER_ENTER);
+                            onHoverVirtualView(child, eventNoHistory);
+                            mLastHoveredChild = child;
+                            eventNoHistory.setAction(MotionEvent.ACTION_HOVER_MOVE);
+                            handled |= onHoverVirtualView(child, eventNoHistory);
+                            if (eventNoHistory != event) {
+                                eventNoHistory.recycle();
+                            } else {
+                                event.setAction(action);
+                            }
+                        }
+                    } break;
+                    case MotionEvent.ACTION_HOVER_EXIT: {
+                        mLastHoveredChild = null;
+                        handled |= onHoverVirtualView(child, event);
+                        event.setAction(action);
+                    } break;
+                }
+            }
+            if (!handled) {
+                handled |= onHoverEvent(event);
+            }
+            return handled;
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+            // The virtual children are ordered horizontally next to
+            // each other and take the entire space of this View.
+            int offsetX = 0;
+            List<VirtualView> children = mChildren;
+            final int childCount = children.size();
+            for (int i = 0; i < childCount; i++) {
+                VirtualView child = children.get(i);
+                Rect childBounds = child.mBounds;
+                childBounds.set(offsetX, 0, offsetX + childBounds.width(), childBounds.height());
+                offsetX += childBounds.width();
+            }
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+            // The virtual children are ordered horizontally next to
+            // each other and take the entire space of this View.
+            int width = 0;
+            int height = 0;
+            List<VirtualView> children = mChildren;
+            final int childCount = children.size();
+            for (int i = 0; i < childCount; i++) {
+                VirtualView child = children.get(i);
+                width += child.mBounds.width();
+                height = Math.max(height, child.mBounds.height());
+            }
+            setMeasuredDimension(width, height);
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        protected void onDraw(Canvas canvas) {
+            // Draw the virtual children with the reusable Paint object
+            // and with the bounds and color which are child specific.
+            Rect drawingRect = mTempRect;
+            List<VirtualView> children = mChildren;
+            final int childCount = children.size();
+            for (int i = 0; i < childCount; i++) {
+                VirtualView child = children.get(i);
+                drawingRect.set(child.mBounds);
+                mPaint.setColor(child.mColor);
+                mPaint.setAlpha(child.mAlpha);
+                canvas.drawRect(drawingRect, mPaint);
+            }
+        }
+
+        /**
+         * Creates the virtual children of this View.
+         */
+        private void createVirtualChildren() {
+            // The virtual portion of the tree is one level deep. Note
+            // that implementations can use any way of representing and
+            // drawing virtual view.
+            VirtualView firstChild = new VirtualView(0, new Rect(0, 0, 150, 150), Color.RED,
+                    "Virtual view 1");
+            mChildren.add(firstChild);
+            VirtualView secondChild = new VirtualView(1, new Rect(0, 0, 150, 150), Color.GREEN,
+                    "Virtual view 2");
+            mChildren.add(secondChild);
+            VirtualView thirdChild = new VirtualView(2, new Rect(0, 0, 150, 150), Color.BLUE,
+                    "Virtual view 3");
+            mChildren.add(thirdChild);
+        }
+
+        /**
+         * Set the selected state of a virtual view.
+         *
+         * @param virtualView The virtual view whose selected state to set.
+         * @param selected Whether the virtual view is selected.
+         */
+        private void setVirtualViewSelected(VirtualView virtualView, boolean selected) {
+            virtualView.mAlpha = selected ? VirtualView.ALPHA_SELECTED : VirtualView.ALPHA_NOT_SELECTED;
+        }
+
+        /**
+         * Handle a hover over a virtual view.
+         *
+         * @param virtualView The virtual view over which is hovered.
+         * @param event The event to dispatch.
+         * @return Whether the event was handled.
+         */
+        private boolean onHoverVirtualView(VirtualView virtualView, MotionEvent event) {
+            // The implementation of hover event dispatch can be implemented
+            // in any way that is found suitable. However, each virtual View
+            // should fire a corresponding accessibility event whose source
+            // is that virtual view. Accessibility services get the event source
+            // as the entry point of the APIs for querying the window content.
+            final int action = event.getAction();
+            switch (action) {
+                case MotionEvent.ACTION_HOVER_ENTER: {
+                    sendAccessibilityEventForVirtualView(virtualView,
+                            AccessibilityEvent.TYPE_VIEW_HOVER_ENTER);
+                } break;
+                case MotionEvent.ACTION_HOVER_EXIT: {
+                    sendAccessibilityEventForVirtualView(virtualView,
+                            AccessibilityEvent.TYPE_VIEW_HOVER_EXIT);
+                } break;
+            }
+            return true;
+        }
+
+        /**
+         * Sends a properly initialized accessibility event for a virtual view..
+         *
+         * @param virtualView The virtual view.
+         * @param eventType The type of the event to send.
+         */
+        private void sendAccessibilityEventForVirtualView(VirtualView virtualView, int eventType) {
+            // If touch exploration, i.e. the user gets feedback while touching
+            // the screen, is enabled we fire accessibility events.
+            if (mAccessibilityManager.isTouchExplorationEnabled()) {
+                AccessibilityEvent event = AccessibilityEvent.obtain(eventType);
+                event.setPackageName(getContext().getPackageName());
+                event.setClassName(virtualView.getClass().getName());
+                event.setSource(VirtualSubtreeRootView.this, virtualView.mId);
+                event.getText().add(virtualView.mText);
+                getParent().requestSendAccessibilityEvent(VirtualSubtreeRootView.this, event);
+            }
+        }
+
+        /**
+         * Finds a virtual view given its id.
+         *
+         * @param id The virtual view id.
+         * @return The found virtual view.
+         */
+        private VirtualView findVirtualViewById(int id) {
+            List<VirtualView> children = mChildren;
+            final int childCount = children.size();
+            for (int i = 0; i < childCount; i++) {
+                VirtualView child = children.get(i);
+                if (child.mId == id) {
+                    return child;
+                }
+            }
+            return null;
+        }
+
+        /**
+         * Represents a virtual View.
+         */
+        private class VirtualView {
+            public static final int ALPHA_SELECTED = 255;
+            public static final int ALPHA_NOT_SELECTED = 127;
+
+            public final int mId;
+            public final int mColor;
+            public final Rect mBounds;
+            public final String mText;
+            public int mAlpha;
+
+            public VirtualView(int id, Rect bounds, int color, String text) {
+                mId = id;
+                mColor = color;
+                mBounds = bounds;
+                mText = text;
+                mAlpha = ALPHA_NOT_SELECTED;
+            }
+        }
+
+        /**
+         * This is the provider that exposes the virtual View tree to accessibility
+         * services. From the perspective of an accessibility service the
+         * {@link AccessibilityNodeInfo}s it receives while exploring the sub-tree
+         * rooted at this View will be the same as the ones it received while
+         * exploring a View containing a sub-tree composed of real Views.
+         */
+        private class VirtualDescendantsProvider extends AccessibilityNodeProvider {
+
+            /**
+             * {@inheritDoc}
+             */
+            @Override
+            public AccessibilityNodeInfo createAccessibilityNodeInfo(int virtualViewId) {
+                AccessibilityNodeInfo info = null;
+                if (virtualViewId == View.NO_ID) {
+                    // We are requested to create an AccessibilityNodeInfo describing
+                    // this View, i.e. the root of the virtual sub-tree. Note that the
+                    // host View has an AccessibilityNodeProvider which means that this
+                    // provider is responsible for creating the node info for that root.
+                    info = AccessibilityNodeInfo.obtain(VirtualSubtreeRootView.this);
+                    onInitializeAccessibilityNodeInfo(info);
+                    // Add the virtual children of the root View.
+                    List<VirtualView> children = mChildren;
+                    final int childCount = children.size();
+                    for (int i = 0; i < childCount; i++) {
+                        VirtualView child = children.get(i);
+                        info.addChild(VirtualSubtreeRootView.this, child.mId);
+                    }
+                } else {
+                    // Find the view that corresponds to the given id.
+                    VirtualView virtualView = findVirtualViewById(virtualViewId);
+                    if (virtualView == null) {
+                        return null;
+                    }
+                    // Obtain and initialize an AccessibilityNodeInfo with
+                    // information about the virtual view.
+                    info = AccessibilityNodeInfo.obtain();
+                    info.addAction(AccessibilityNodeInfo.ACTION_SELECT);
+                    info.addAction(AccessibilityNodeInfo.ACTION_CLEAR_SELECTION);
+                    info.setPackageName(getContext().getPackageName());
+                    info.setClassName(virtualView.getClass().getName());
+                    info.setSource(VirtualSubtreeRootView.this, virtualViewId);
+                    info.setBoundsInParent(virtualView.mBounds);
+                    info.setParent(VirtualSubtreeRootView.this);
+                    info.setText(virtualView.mText);
+                }
+                return info;
+            }
+
+            /**
+             * {@inheritDoc}
+             */
+            @Override
+            public List<AccessibilityNodeInfo> findAccessibilityNodeInfosByText(String searched,
+                    int virtualViewId) {
+                if (TextUtils.isEmpty(searched)) {
+                    return Collections.emptyList();
+                }
+                String searchedLowerCase = searched.toLowerCase();
+                List<AccessibilityNodeInfo> result = null;
+                if (virtualViewId == View.NO_ID) {
+                    // If the search is from the root, i.e. this View, go over the virtual
+                    // children and look for ones that contain the searched string since
+                    // this View does not contain text itself.
+                    List<VirtualView> children = mChildren;
+                    final int childCount = children.size();
+                    for (int i = 0; i < childCount; i++) {
+                        VirtualView child = children.get(i);
+                        String textToLowerCase = child.mText.toLowerCase();
+                        if (textToLowerCase.contains(searchedLowerCase)) {
+                            if (result == null) {
+                                result = new ArrayList<AccessibilityNodeInfo>();
+                            }
+                            result.add(createAccessibilityNodeInfo(child.mId));
+                        }
+                    }
+                } else {
+                    // If the search is from a virtual view, find the view. Since the tree
+                    // is one level deep we add a node info for the child to the result if
+                    // the child contains the searched text.
+                    VirtualView virtualView = findVirtualViewById(virtualViewId);
+                    if (virtualView != null) {
+                        String textToLowerCase = virtualView.mText.toLowerCase();
+                        if (textToLowerCase.contains(searchedLowerCase)) {
+                            result = new ArrayList<AccessibilityNodeInfo>();
+                            result.add(createAccessibilityNodeInfo(virtualViewId));
+                        }
+                    }
+                }
+                if (result == null) {
+                    return Collections.emptyList();
+                }
+                return result;
+            }
+
+            /**
+             * {@inheritDoc}
+             */
+            @Override
+            public boolean performAccessibilityAction(int action, int virtualViewId) {
+                if (virtualViewId == View.NO_ID) {
+                    // Perform the action on the host View.
+                    switch (action) {
+                        case AccessibilityNodeInfo.ACTION_SELECT:
+                            if (!isSelected()) {
+                                setSelected(true);
+                                return isSelected();
+                            }
+                            break;
+                        case AccessibilityNodeInfo.ACTION_CLEAR_SELECTION:
+                            if (isSelected()) {
+                                setSelected(false);
+                                return !isSelected();
+                            }
+                            break;
+                    }
+                } else {
+                    // Find the view that corresponds to the given id.
+                    VirtualView child = findVirtualViewById(virtualViewId);
+                    if (child == null) {
+                        return false;
+                    }
+                    // Perform the action on a virtual view.
+                    switch (action) {
+                        case AccessibilityNodeInfo.ACTION_SELECT:
+                            setVirtualViewSelected(child, true);
+                            invalidate();
+                            return true;
+                        case AccessibilityNodeInfo.ACTION_CLEAR_SELECTION:
+                            setVirtualViewSelected(child, false);
+                            invalidate();
+                            return true;
+                    }
+                }
+                return false;
+            }
+        }
+    }
+}
diff --git a/samples/ApiDemos/src/com/example/android/apis/accessibility/_index.html b/samples/ApiDemos/src/com/example/android/apis/accessibility/_index.html
index 713d913..df54e96 100644
--- a/samples/ApiDemos/src/com/example/android/apis/accessibility/_index.html
+++ b/samples/ApiDemos/src/com/example/android/apis/accessibility/_index.html
@@ -1,3 +1,4 @@
+<h3 id="Accessibility">Accessibility</h3>
 <dl>
   <dt><a href="ClockBackService.html">Accessibility Service</a></dt>
   <dd>
@@ -20,6 +21,12 @@
     xml files, and adding additional information to AccessibilityEvents using
     AccessibilityRecords.
   </dd>
+  <dt><a href="AccessibilityNodeProviderActivity.html">Accessibility Node Provider</a></dt>
+  <dd>Demonstrates how to develop an accessibility node provider which manages a virtual
+    View tree reported to accessibility services. The virtual subtree is rooted at a View
+    that draws complex content and reports itself as a tree of virtual views, thus conveying
+    its logical structure.
+  </dd>
 </dl>
 
 <dl>
diff --git a/samples/SimpleJNI/jni/native.cpp b/samples/SimpleJNI/jni/native.cpp
index 4d2e4e0..853c3d9 100644
--- a/samples/SimpleJNI/jni/native.cpp
+++ b/samples/SimpleJNI/jni/native.cpp
@@ -24,7 +24,7 @@
 static jint
 add(JNIEnv *env, jobject thiz, jint a, jint b) {
 int result = a + b;
-    LOGI("%d + %d = %d", a, b, result);
+    ALOGI("%d + %d = %d", a, b, result);
     return result;
 }
 
@@ -44,11 +44,11 @@
 
     clazz = env->FindClass(className);
     if (clazz == NULL) {
-        LOGE("Native registration unable to find class '%s'", className);
+        ALOGE("Native registration unable to find class '%s'", className);
         return JNI_FALSE;
     }
     if (env->RegisterNatives(clazz, gMethods, numMethods) < 0) {
-        LOGE("RegisterNatives failed for '%s'", className);
+        ALOGE("RegisterNatives failed for '%s'", className);
         return JNI_FALSE;
     }
 
@@ -89,16 +89,16 @@
     jint result = -1;
     JNIEnv* env = NULL;
     
-    LOGI("JNI_OnLoad");
+    ALOGI("JNI_OnLoad");
 
     if (vm->GetEnv(&uenv.venv, JNI_VERSION_1_4) != JNI_OK) {
-        LOGE("ERROR: GetEnv failed");
+        ALOGE("ERROR: GetEnv failed");
         goto bail;
     }
     env = uenv.env;
 
     if (registerNatives(env) != JNI_TRUE) {
-        LOGE("ERROR: registerNatives failed");
+        ALOGE("ERROR: registerNatives failed");
         goto bail;
     }
     
diff --git a/samples/Support4Demos/AndroidManifest.xml b/samples/Support4Demos/AndroidManifest.xml
index 6d71b03..cb34be2 100644
--- a/samples/Support4Demos/AndroidManifest.xml
+++ b/samples/Support4Demos/AndroidManifest.xml
@@ -242,5 +242,26 @@
             </intent-filter>
         </activity>
 
+        <activity android:name=".app.SharingSupport"
+                  android:label="@string/sharing_support_title">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+                <category android:name="com.example.android.supportv4.SUPPORT4_SAMPLE_CODE" />
+            </intent-filter>
+        </activity>
+
+        <activity android:name=".app.SharingReceiverSupport"
+                  android:label="@string/sharing_receiver_title">
+            <intent-filter>
+                <action android:name="android.intent.action.SEND" />
+                <action android:name="android.intent.action.SEND_MULTIPLE" />
+                <data android:mimeType="text/plain" />
+                <category android:name="android.intent.category.DEFAULT" />
+            </intent-filter>
+        </activity>
+
+        <provider android:authorities="com.example.supportv4.content.sharingsupportprovider"
+                  android:name=".content.SharingSupportProvider" />
+
     </application>
 </manifest>
diff --git a/samples/Support4Demos/res/layout/sharing_receiver_support.xml b/samples/Support4Demos/res/layout/sharing_receiver_support.xml
new file mode 100644
index 0000000..a7b4c38
--- /dev/null
+++ b/samples/Support4Demos/res/layout/sharing_receiver_support.xml
@@ -0,0 +1,31 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2011 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+              android:orientation="vertical"
+              android:padding="16dp"
+              android:layout_width="match_parent"
+              android:layout_height="match_parent">
+    <TextView android:id="@+id/app_info"
+              android:layout_width="match_parent"
+              android:layout_height="wrap_content"
+              android:gravity="center_vertical"/>
+    <ScrollView android:layout_width="match_parent"
+                android:layout_height="match_parent">
+        <TextView android:id="@+id/text"
+                  android:layout_width="match_parent"
+                  android:layout_height="wrap_content" />
+    </ScrollView>
+</LinearLayout>
diff --git a/samples/Support4Demos/res/layout/sharing_support.xml b/samples/Support4Demos/res/layout/sharing_support.xml
new file mode 100644
index 0000000..8b88dca
--- /dev/null
+++ b/samples/Support4Demos/res/layout/sharing_support.xml
@@ -0,0 +1,36 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2011 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+              android:orientation="vertical"
+              android:padding="16dp"
+              android:layout_width="match_parent"
+              android:layout_height="match_parent">
+    <Button android:id="@+id/share_text"
+            android:text="@string/share_text"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:onClick="onShareTextClick" />
+    <Button android:id="@+id/share_file"
+            android:text="@string/share_file"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:onClick="onShareFileClick" />
+    <Button android:id="@+id/share_multiple_file"
+            android:text="@string/share_multiple_file"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:onClick="onShareMultipleFileClick" />
+</LinearLayout>
diff --git a/samples/Support4Demos/res/values/strings.xml b/samples/Support4Demos/res/values/strings.xml
index 8f70fd3..4738c44 100644
--- a/samples/Support4Demos/res/values/strings.xml
+++ b/samples/Support4Demos/res/values/strings.xml
@@ -122,4 +122,10 @@
     <string name="accessibility_delegate_button">Button</string>
     <string name="accessibility_delegate_custom_text_added">Custom text added via an accessibility delegate.</string>
 
+    <string name="share_text">Share some text</string>
+    <string name="share_file">Share a file</string>
+    <string name="share_multiple_file">Share multiple files</string>
+    <string name="sharing_support_title">ShareCompat Demo</string>
+    <string name="sharing_receiver_title">ShareCompat Receiver</string>
+
 </resources>
diff --git a/samples/Support4Demos/src/com/example/android/supportv4/app/SharingReceiverSupport.java b/samples/Support4Demos/src/com/example/android/supportv4/app/SharingReceiverSupport.java
new file mode 100644
index 0000000..d1efa2d
--- /dev/null
+++ b/samples/Support4Demos/src/com/example/android/supportv4/app/SharingReceiverSupport.java
@@ -0,0 +1,90 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.android.supportv4.app;
+
+import com.example.android.supportv4.R;
+
+import android.app.Activity;
+import android.graphics.drawable.Drawable;
+import android.net.Uri;
+import android.os.Bundle;
+import android.support.v4.app.ShareCompat;
+import android.util.Log;
+import android.widget.TextView;
+
+import java.io.BufferedReader;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStreamReader;
+
+/**
+ * This example shows a simple way to handle data shared with your app through the
+ * use of the support library's ShareCompat features. It will display shared text
+ * content as well as the application label and icon of the app that shared the content.
+ */
+public class SharingReceiverSupport extends Activity {
+    private static final String TAG = "SharingReceiverSupport";
+    private static final int ICON_SIZE = 32; // dip
+
+    @Override
+    protected void onCreate(Bundle b) {
+        super.onCreate(b);
+        setContentView(R.layout.sharing_receiver_support);
+
+        final float density = getResources().getDisplayMetrics().density;
+        final int iconSize = (int) (ICON_SIZE * density + 0.5f);
+
+        ShareCompat.IntentReader intentReader = ShareCompat.IntentReader.from(this);
+
+        // The following provides attribution for the app that shared the data with us.
+        TextView info = (TextView) findViewById(R.id.app_info);
+        Drawable d = intentReader.getCallingActivityIcon();
+        d.setBounds(0, 0, iconSize, iconSize);
+        info.setCompoundDrawables(d, null, null, null);
+        info.setText(intentReader.getCallingApplicationLabel());
+
+        TextView tv = (TextView) findViewById(R.id.text);
+        StringBuilder txt = new StringBuilder("Received share!\nText was: ");
+
+        txt.append(intentReader.getText());
+        txt.append("\n");
+
+        txt.append("Streams included:\n");
+        final int N = intentReader.getStreamCount();
+        for (int i = 0; i < N; i++) {
+            Uri uri = intentReader.getStream(i);
+            txt.append("Share included stream " + i + ": " + uri + "\n");
+            try {
+                BufferedReader reader = new BufferedReader(new InputStreamReader(
+                        getContentResolver().openInputStream(uri)));
+                try {
+                    txt.append(reader.readLine() + "\n");
+                } catch (IOException e) {
+                    Log.e(TAG, "Reading stream threw exception", e);
+                } finally {
+                    reader.close();
+                }
+            } catch (FileNotFoundException e) {
+                Log.e(TAG, "File not found from share.", e);
+            } catch (IOException e) {
+                Log.d(TAG, "I/O Error", e);
+            }
+        }
+
+        tv.setText(txt.toString());
+    }
+}
diff --git a/samples/Support4Demos/src/com/example/android/supportv4/app/SharingSupport.java b/samples/Support4Demos/src/com/example/android/supportv4/app/SharingSupport.java
new file mode 100644
index 0000000..68eb0f2
--- /dev/null
+++ b/samples/Support4Demos/src/com/example/android/supportv4/app/SharingSupport.java
@@ -0,0 +1,113 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.android.supportv4.app;
+
+import com.example.android.supportv4.R;
+import com.example.android.supportv4.content.SharingSupportProvider;
+
+import android.app.Activity;
+import android.net.Uri;
+import android.os.Bundle;
+import android.support.v4.app.ShareCompat;
+import android.support.v4.view.MenuItemCompat;
+import android.view.Menu;
+import android.view.MenuItem;
+import android.view.View;
+
+import java.io.FileNotFoundException;
+import java.io.FileWriter;
+import java.io.IOException;
+
+/**
+ * This example illustrates the use of the ShareCompat feature of the support library.
+ * ShareCompat offers several pieces of functionality to assist in sharing content between
+ * apps and is especially suited for sharing content to social apps that the user has installed.
+ *
+ * <p>Two other classes are relevant to this code sample: {@link SharingReceiverSupport} is
+ * an activity that has been configured to receive ACTION_SEND and ACTION_SEND_MULTIPLE
+ * sharing intents with a type of text/plain. It provides an example of writing a sharing
+ * target using ShareCompat features. {@link SharingSupportProvider} is a simple
+ * {@link android.content.ContentProvider} that provides access to two text files
+ * created by this app to share as content streams.</p>
+ */
+public class SharingSupport extends Activity {
+    @Override
+    protected void onCreate(Bundle b) {
+        super.onCreate(b);
+        setContentView(R.layout.sharing_support);
+    }
+
+    @Override
+    public boolean onCreateOptionsMenu(Menu menu) {
+        ShareCompat.IntentBuilder b = ShareCompat.IntentBuilder.from(this);
+        b.setType("text/plain").setText("Share from menu");
+        MenuItem item = menu.add("Share");
+        ShareCompat.configureMenuItem(item, b);
+        MenuItemCompat.setShowAsAction(item, MenuItemCompat.SHOW_AS_ACTION_IF_ROOM);
+        return true;
+    }
+
+    public void onShareTextClick(View v) {
+        ShareCompat.IntentBuilder.from(this)
+                .setType("text/plain")
+                .setText("I'm sharing!")
+                .startChooserForResult();
+    }
+
+    public void onShareFileClick(View v) {
+        try {
+            // This file will be accessed by the target of the share through
+            // the ContentProvider SharingSupportProvider.
+            FileWriter fw = new FileWriter(getFilesDir() + "/foo.txt");
+            fw.write("This is a file share");
+            fw.close();
+
+            ShareCompat.IntentBuilder.from(this)
+                    .setType("text/plain")
+                    .setStream(Uri.parse(SharingSupportProvider.CONTENT_URI + "/foo.txt"))
+                    .startChooserForResult();
+        } catch (FileNotFoundException e) {
+            e.printStackTrace();
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+    }
+
+    public void onShareMultipleFileClick(View v) {
+        try {
+            // These files will be accessed by the target of the share through
+            // the ContentProvider SharingSupportProvider.
+            FileWriter fw = new FileWriter(getFilesDir() + "/foo.txt");
+            fw.write("This is a file share");
+            fw.close();
+
+            fw = new FileWriter(getFilesDir() + "/bar.txt");
+            fw.write("This is another file share");
+            fw.close();
+
+            ShareCompat.IntentBuilder.from(this)
+                    .setType("text/plain")
+                    .addStream(Uri.parse(SharingSupportProvider.CONTENT_URI + "/foo.txt"))
+                    .addStream(Uri.parse(SharingSupportProvider.CONTENT_URI + "/bar.txt"))
+                    .startChooserForResult();
+        } catch (FileNotFoundException e) {
+            e.printStackTrace();
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+    }
+}
diff --git a/samples/Support4Demos/src/com/example/android/supportv4/content/SharingSupportProvider.java b/samples/Support4Demos/src/com/example/android/supportv4/content/SharingSupportProvider.java
new file mode 100644
index 0000000..596fd6c
--- /dev/null
+++ b/samples/Support4Demos/src/com/example/android/supportv4/content/SharingSupportProvider.java
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.example.android.supportv4.content;
+
+import android.content.ContentProvider;
+import android.content.ContentValues;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.ParcelFileDescriptor;
+import android.util.Log;
+
+import java.io.File;
+import java.io.FileNotFoundException;
+
+/**
+ * This simple ContentProvider provides access to the two example files shared
+ * by the ShareCompat example {@link com.example.android.supportv4.app.SharingSupport}.
+ */
+public class SharingSupportProvider extends ContentProvider {
+    public static final Uri CONTENT_URI =
+            Uri.parse("content://com.example.supportv4.content.sharingsupportprovider");
+
+    private static final String TAG = "SharingSupportProvider";
+
+    @Override
+    public boolean onCreate() {
+        return true;
+    }
+
+    @Override
+    public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs,
+            String sortOrder) {
+        return null;
+    }
+
+    @Override
+    public String getType(Uri uri) {
+        if (uri.equals(Uri.withAppendedPath(CONTENT_URI, "foo.txt")) ||
+                uri.equals(Uri.withAppendedPath(CONTENT_URI, "bar.txt"))) {
+            return "text/plain";
+        }
+        return null;
+    }
+
+    @Override
+    public Uri insert(Uri uri, ContentValues values) {
+        return null;
+    }
+
+    @Override
+    public int delete(Uri uri, String selection, String[] selectionArgs) {
+        return 0;
+    }
+
+    @Override
+    public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
+        return 0;
+    }
+
+    @Override
+    public ParcelFileDescriptor openFile(Uri uri, String mode) {
+        String path = uri.getPath();
+        if (mode.equals("r") &&
+                (path.equals("/foo.txt") || path.equals("/bar.txt"))) {
+            try {
+                return ParcelFileDescriptor.open(
+                        new File(getContext().getFilesDir() + path),
+                        ParcelFileDescriptor.MODE_READ_ONLY);
+            } catch (FileNotFoundException e) {
+                Log.e(TAG, "Bad file " + uri);
+            }
+        }
+        return null;
+    }
+}
diff --git a/sdk/doc_source.prop_template b/sdk/doc_source.prop_template
new file mode 100644
index 0000000..d3cdfd5
--- /dev/null
+++ b/sdk/doc_source.prop_template
@@ -0,0 +1,4 @@
+Pkg.UserSrc=false
+Pkg.Revision=1
+AndroidVersion.ApiLevel=${PLATFORM_SDK_VERSION}
+AndroidVersion.CodeName=${PLATFORM_VERSION_CODENAME}
diff --git a/sdk/doc_source.properties b/sdk/doc_source.properties
deleted file mode 100644
index 5b3dce6..0000000
--- a/sdk/doc_source.properties
+++ /dev/null
@@ -1,5 +0,0 @@
-Pkg.UserSrc=false
-Pkg.Revision=1
-AndroidVersion.ApiLevel=15
-#AndroidVersion.CodeName=
-
diff --git a/sdk/images_armeabi-v7a_source.prop_template b/sdk/images_armeabi-v7a_source.prop_template
new file mode 100644
index 0000000..ae67647
--- /dev/null
+++ b/sdk/images_armeabi-v7a_source.prop_template
@@ -0,0 +1,6 @@
+Pkg.Desc=Android SDK Platform ${PLATFORM_VERSION}
+Pkg.UserSrc=false
+Pkg.Revision=1
+AndroidVersion.ApiLevel=${PLATFORM_SDK_VERSION}
+AndroidVersion.CodeName=${PLATFORM_VERSION_CODENAME}
+SystemImage.Abi=armeabi-v7a
diff --git a/sdk/images_armeabi-v7a_source.properties b/sdk/images_armeabi-v7a_source.properties
deleted file mode 100644
index 2392a00..0000000
--- a/sdk/images_armeabi-v7a_source.properties
+++ /dev/null
@@ -1,6 +0,0 @@
-Pkg.Desc=Android SDK Platform 4.0.3
-Pkg.UserSrc=false
-Pkg.Revision=1
-AndroidVersion.ApiLevel=15
-#AndroidVersion.CodeName=
-SystemImage.Abi=armeabi-v7a
diff --git a/sdk/images_armeabi_source.prop_template b/sdk/images_armeabi_source.prop_template
new file mode 100644
index 0000000..b100e53
--- /dev/null
+++ b/sdk/images_armeabi_source.prop_template
@@ -0,0 +1,6 @@
+Pkg.Desc=Android SDK Platform ${PLATFORM_VERSION}
+Pkg.UserSrc=false
+Pkg.Revision=1
+AndroidVersion.ApiLevel=${PLATFORM_SDK_VERSION}
+AndroidVersion.CodeName=${PLATFORM_VERSION_CODENAME}
+SystemImage.Abi=armeabi
diff --git a/sdk/images_armeabi_source.properties b/sdk/images_armeabi_source.properties
deleted file mode 100644
index 4af4b5d..0000000
--- a/sdk/images_armeabi_source.properties
+++ /dev/null
@@ -1,6 +0,0 @@
-Pkg.Desc=Android SDK Platform 4.0.3
-Pkg.UserSrc=false
-Pkg.Revision=1
-AndroidVersion.ApiLevel=15
-#AndroidVersion.CodeName=
-SystemImage.Abi=armeabi
diff --git a/sdk/images_x86_source.prop_template b/sdk/images_x86_source.prop_template
new file mode 100644
index 0000000..62e2e0d
--- /dev/null
+++ b/sdk/images_x86_source.prop_template
@@ -0,0 +1,6 @@
+Pkg.Desc=Android SDK Platform ${PLATFORM_VERSION}
+Pkg.UserSrc=false
+Pkg.Revision=1
+AndroidVersion.ApiLevel=${PLATFORM_SDK_VERSION}
+AndroidVersion.CodeName=${PLATFORM_VERSION_CODENAME}
+SystemImage.Abi=x86
diff --git a/sdk/images_x86_source.properties b/sdk/images_x86_source.properties
deleted file mode 100644
index 7a17964..0000000
--- a/sdk/images_x86_source.properties
+++ /dev/null
@@ -1,6 +0,0 @@
-Pkg.Desc=Android SDK Platform 4.0.3
-Pkg.UserSrc=false
-Pkg.Revision=1
-AndroidVersion.ApiLevel=15
-#AndroidVersion.CodeName=
-SystemImage.Abi=x86
diff --git a/sdk/platform_source.prop_template b/sdk/platform_source.prop_template
new file mode 100644
index 0000000..17a5e4e
--- /dev/null
+++ b/sdk/platform_source.prop_template
@@ -0,0 +1,9 @@
+Pkg.Desc=Android SDK Platform ${PLATFORM_VERSION}
+Pkg.UserSrc=false
+Platform.Version=${PLATFORM_VERSION}
+Pkg.Revision=1
+AndroidVersion.ApiLevel=${PLATFORM_SDK_VERSION}
+AndroidVersion.CodeName=${PLATFORM_VERSION_CODENAME}
+Layoutlib.Api=7
+Layoutlib.Revision=1
+Platform.MinToolsRev=15
diff --git a/sdk/platform_source.properties b/sdk/platform_source.properties
deleted file mode 100644
index 785bdc1..0000000
--- a/sdk/platform_source.properties
+++ /dev/null
@@ -1,9 +0,0 @@
-Pkg.Desc=Android SDK Platform 4.0.3
-Pkg.UserSrc=false
-Platform.Version=4.0.3
-Pkg.Revision=2
-AndroidVersion.ApiLevel=15
-#AndroidVersion.CodeName=
-Layoutlib.Api=7
-Layoutlib.Revision=1
-Platform.MinToolsRev=15
diff --git a/sdk/source_source.prop_template b/sdk/source_source.prop_template
new file mode 100644
index 0000000..d3cdfd5
--- /dev/null
+++ b/sdk/source_source.prop_template
@@ -0,0 +1,4 @@
+Pkg.UserSrc=false
+Pkg.Revision=1
+AndroidVersion.ApiLevel=${PLATFORM_SDK_VERSION}
+AndroidVersion.CodeName=${PLATFORM_VERSION_CODENAME}
diff --git a/sdk/source_source.properties b/sdk/source_source.properties
deleted file mode 100644
index d0b390b..0000000
--- a/sdk/source_source.properties
+++ /dev/null
@@ -1,4 +0,0 @@
-Pkg.UserSrc=false
-Pkg.Revision=1
-AndroidVersion.ApiLevel=15
-#AndroidVersion.CodeName=
diff --git a/sdk/support_source.properties b/sdk/support_source.properties
index 32bdbe3..85af1a7 100644
--- a/sdk/support_source.properties
+++ b/sdk/support_source.properties
@@ -3,4 +3,3 @@
 Extra.Vendor=android
 Extra.Path=support
 Extra.OldPaths=compatibility
-
diff --git a/testrunner/runtest.py b/testrunner/runtest.py
index 6226350..1691c16 100755
--- a/testrunner/runtest.py
+++ b/testrunner/runtest.py
@@ -233,8 +233,11 @@
     self._TurnOffVerifier(tests)
     self._DoFullBuild(tests)
 
-    target_set = Set()
-    extra_args_set = Set()
+    target_set = []
+    if self._IsCtsTests(tests):
+      target_set.append("cts/CtsBuild.mk")
+
+    extra_args_set = []
     for test_suite in tests:
       self._AddBuildTarget(test_suite, target_set, extra_args_set)
 
@@ -260,8 +263,8 @@
           logger.Log(cmd)
           run_command.RunCommand(cmd, return_output=False)
 
-      target_build_string = " ".join(list(target_set))
-      extra_args_string = " ".join(list(extra_args_set))
+      target_build_string = " ".join(target_set)
+      extra_args_string = " ".join(extra_args_set)
 
       # mmm cannot be used from python, so perform a similar operation using
       # ONE_SHOT_MAKEFILE
@@ -315,7 +318,7 @@
     if not test_suite.IsFullMake():
       build_dir = test_suite.GetBuildPath()
       if self._AddBuildTargetPath(build_dir, target_set):
-        extra_args_set.add(test_suite.GetExtraBuildArgs())
+        extra_args_set.append(test_suite.GetExtraBuildArgs())
       for path in test_suite.GetBuildDependencies(self._options):
         self._AddBuildTargetPath(path, target_set)
 
@@ -323,7 +326,7 @@
     if build_dir is not None:
       build_file_path = os.path.join(build_dir, "Android.mk")
       if os.path.isfile(os.path.join(self._root_path, build_file_path)):
-        target_set.add(build_file_path)
+        target_set.append(build_file_path)
         return True
       else:
         logger.Log("%s has no Android.mk, skipping" % build_dir)
diff --git a/tools/a3dconvert/SimpleMesh.h b/tools/a3dconvert/SimpleMesh.h
index c87bb7d..91b4823 100644
--- a/tools/a3dconvert/SimpleMesh.h
+++ b/tools/a3dconvert/SimpleMesh.h
@@ -106,13 +106,18 @@
             uint32_t vertexPos = i*vertexSize;
             float *vertexPtr = dataPtr + vertexPos;
 
+            uint32_t elemIndex = 0;
             for (uint32_t c = 0; c < mChannels.size(); c ++) {
                 // Skip empty channels
                 if (mChannels[c].mData.size() == 0) {
                     continue;
                 }
+                // This will address vector element alignment issues
+                uint32_t elemlOffset = vertexDataElem->getFieldOffsetBytes(elemIndex)/sizeof(float);
+                elemIndex ++;
+                float *channelPtr = vertexPtr + elemlOffset;
                 for (uint32_t cStride = 0; cStride < mChannels[c].mStride; cStride ++) {
-                    *(vertexPtr++) = mChannels[c].mData[i * mChannels[c].mStride + cStride];
+                    *(channelPtr++) = mChannels[c].mData[i * mChannels[c].mStride + cStride];
                 }
             }
         }
diff --git a/tools/a3dconvert/a3dconvert.cpp b/tools/a3dconvert/a3dconvert.cpp
index 3535b17..4e48642 100644
--- a/tools/a3dconvert/a3dconvert.cpp
+++ b/tools/a3dconvert/a3dconvert.cpp
@@ -44,21 +44,11 @@
 
 // We only care to implement allocation memory initialization and destruction
 // because we need no other renderscript hal features for serialization
-static RsdHalFunctions FunctionTable = {
-    NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-    { NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,NULL },
-    {
-        rsdAllocationInit,
-        rsdAllocationDestroy,
-        NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
-    },
-    { NULL, NULL, NULL }, { NULL, NULL, NULL }, { NULL, NULL, NULL },
-    { NULL, NULL, NULL }, { NULL, NULL, NULL }, { NULL, NULL },
-    { NULL, NULL, NULL},
-};
-
-// No-op initizlizer for rs context hal since we only
+static RsdHalFunctions FunctionTable;
 bool rsdHalInit(Context *rsc, uint32_t version_major, uint32_t version_minor) {
+    memset(&FunctionTable, 0, sizeof(FunctionTable));
+    FunctionTable.allocation.init = rsdAllocationInit;
+    FunctionTable.allocation.destroy = rsdAllocationDestroy;
     rsc->mHal.funcs = FunctionTable;
     return true;
 }
diff --git a/tools/emulator/opengl/host/tools/emugen/ApiGen.cpp b/tools/emulator/opengl/host/tools/emugen/ApiGen.cpp
index 4265301..7c83364 100644
--- a/tools/emulator/opengl/host/tools/emugen/ApiGen.cpp
+++ b/tools/emulator/opengl/host/tools/emugen/ApiGen.cpp
@@ -462,7 +462,8 @@
     size_t n = size();
 
     // unsupport printout
-    fprintf(fp, "static void enc_unsupported()\n{\n\tLOGE(\"Function is unsupported\\n\");\n}\n\n");
+    fprintf(fp,
+            "static void enc_unsupported()\n{\n\tALOGE(\"Function is unsupported\\n\");\n}\n\n");
 
     // entry points;
     for (size_t i = 0; i < n; i++) {
diff --git a/tools/emulator/opengl/shared/OpenglCodecCommon/ErrorLog.h b/tools/emulator/opengl/shared/OpenglCodecCommon/ErrorLog.h
index 5e9c7b3..6f41fd7 100644
--- a/tools/emulator/opengl/shared/OpenglCodecCommon/ErrorLog.h
+++ b/tools/emulator/opengl/shared/OpenglCodecCommon/ErrorLog.h
@@ -18,9 +18,9 @@
 
 #if (HAVE_ANDROID_OS == 1)
 #    include <cutils/log.h>
-#    define ERR(...)    LOGE(__VA_ARGS__)
+#    define ERR(...)    ALOGE(__VA_ARGS__)
 #    ifdef EMUGL_DEBUG
-#        define DBG(...)    LOGD(__VA_ARGS__)
+#        define DBG(...)    ALOGD(__VA_ARGS__)
 #    else
 #        define DBG(...)    ((void)0)
 #    endif
diff --git a/tools/emulator/opengl/system/GLESv1/gl.cpp b/tools/emulator/opengl/system/GLESv1/gl.cpp
index 07afade..cd1b055 100644
--- a/tools/emulator/opengl/system/GLESv1/gl.cpp
+++ b/tools/emulator/opengl/system/GLESv1/gl.cpp
@@ -23,12 +23,12 @@
 #define DEFINE_AND_VALIDATE_HOST_CONNECTION(ret) \
     HostConnection *hostCon = HostConnection::get(); \
     if (!hostCon) { \
-        LOGE("egl: Failed to get host connection\n"); \
+        ALOGE("egl: Failed to get host connection\n"); \
         return ret; \
     } \
     renderControl_encoder_context_t *rcEnc = hostCon->rcEncoder(); \
     if (!rcEnc) { \
-        LOGE("egl: Failed to get renderControl encoder context\n"); \
+        ALOGE("egl: Failed to get renderControl encoder context\n"); \
         return ret; \
     }
 
diff --git a/tools/emulator/opengl/system/GLESv1_enc/GLEncoder.cpp b/tools/emulator/opengl/system/GLESv1_enc/GLEncoder.cpp
index dc7c527..6636117 100644
--- a/tools/emulator/opengl/system/GLESv1_enc/GLEncoder.cpp
+++ b/tools/emulator/opengl/system/GLESv1_enc/GLEncoder.cpp
@@ -30,14 +30,14 @@
 static GLubyte *gExtensionsString= (GLubyte *) ""; // no extensions at this point;
 
 #define SET_ERROR_IF(condition,err) if((condition)) {                            \
-        LOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
+        ALOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
         ctx->setError(err);                                    \
         return;                                                  \
     }
 
 
 #define RET_AND_SET_ERROR_IF(condition,err,ret) if((condition)) {                \
-        LOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
+        ALOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
         ctx->setError(err);                                    \
         return ret;                                              \
     }
@@ -258,7 +258,7 @@
 {
     GLEncoder *ctx = (GLEncoder *)self;
     ctx->m_glPixelStorei_enc(ctx, param, value);
-    LOG_ASSERT(ctx->m_state, "GLEncoder::s_glPixelStorei");
+    ALOG_ASSERT(ctx->m_state, "GLEncoder::s_glPixelStorei");
     ctx->m_state->setPixelStore(param, value);
 }
 
@@ -537,7 +537,7 @@
     }
 
     if (!has_immediate_arrays && !has_indirect_arrays) {
-        LOGE("glDrawElements: no data bound to the command - ignoring\n");
+        ALOGE("glDrawElements: no data bound to the command - ignoring\n");
         return;
     }
 
@@ -580,7 +580,7 @@
             }
             break;
         default:
-            LOGE("unsupported index buffer type %d\n", type);
+            ALOGE("unsupported index buffer type %d\n", type);
         }
         if (has_indirect_arrays || 1) {
             ctx->sendVertexData(minIndex, maxIndex - minIndex + 1);
@@ -588,12 +588,12 @@
                                       count * glSizeof(type));
             // XXX - OPTIMIZATION (see the other else branch) should be implemented
             if(!has_indirect_arrays) {
-                //LOGD("unoptimized drawelements !!!\n");
+                //ALOGD("unoptimized drawelements !!!\n");
             }
         } else {
             // we are all direct arrays and immidate mode index array -
             // rebuild the arrays and the index array;
-            LOGE("glDrawElements: direct index & direct buffer data - will be implemented in later versions;\n");
+            ALOGE("glDrawElements: direct index & direct buffer data - will be implemented in later versions;\n");
         }
     }
 }
@@ -605,7 +605,7 @@
     GLenum err;
 
     if ((err = state->setActiveTextureUnit(texture)) != GL_NO_ERROR) {
-        LOGE("%s:%s:%d GL error %#x\n", __FILE__, __FUNCTION__, __LINE__, err);
+        ALOGE("%s:%s:%d GL error %#x\n", __FILE__, __FUNCTION__, __LINE__, err);
         ctx->setError(err);
         return;
     }
@@ -621,7 +621,7 @@
 
     GLboolean firstUse;
     if ((err = state->bindTexture(target, texture, &firstUse)) != GL_NO_ERROR) {
-        LOGE("%s:%s:%d GL error %#x\n", __FILE__, __FUNCTION__, __LINE__, err);
+        ALOGE("%s:%s:%d GL error %#x\n", __FILE__, __FUNCTION__, __LINE__, err);
         ctx->setError(err);
         return;
     }
diff --git a/tools/emulator/opengl/system/GLESv2/gl2.cpp b/tools/emulator/opengl/system/GLESv2/gl2.cpp
index a014c1a..2c8938b 100644
--- a/tools/emulator/opengl/system/GLESv2/gl2.cpp
+++ b/tools/emulator/opengl/system/GLESv2/gl2.cpp
@@ -23,12 +23,12 @@
 #define DEFINE_AND_VALIDATE_HOST_CONNECTION(ret) \
     HostConnection *hostCon = HostConnection::get(); \
     if (!hostCon) { \
-        LOGE("egl: Failed to get host connection\n"); \
+        ALOGE("egl: Failed to get host connection\n"); \
         return ret; \
     } \
     renderControl_encoder_context_t *rcEnc = hostCon->rcEncoder(); \
     if (!rcEnc) { \
-        LOGE("egl: Failed to get renderControl encoder context\n"); \
+        ALOGE("egl: Failed to get renderControl encoder context\n"); \
         return ret; \
     }
 
diff --git a/tools/emulator/opengl/system/GLESv2_enc/GL2Encoder.cpp b/tools/emulator/opengl/system/GLESv2_enc/GL2Encoder.cpp
index 59fe1a2..d57c223 100644
--- a/tools/emulator/opengl/system/GLESv2_enc/GL2Encoder.cpp
+++ b/tools/emulator/opengl/system/GLESv2_enc/GL2Encoder.cpp
@@ -8,14 +8,14 @@
 static GLubyte *gExtensionsString= (GLubyte *) ""; // no extensions at this point;
 
 #define SET_ERROR_IF(condition,err) if((condition)) {                            \
-        LOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
+        ALOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
         ctx->setError(err);                                    \
         return;                                                  \
     }
 
 
 #define RET_AND_SET_ERROR_IF(condition,err,ret) if((condition)) {                \
-        LOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
+        ALOGE("%s:%s:%d GL error 0x%x\n", __FILE__, __FUNCTION__, __LINE__, err); \
         ctx->setError(err);                                    \
         return ret;                                              \
     }
@@ -355,7 +355,7 @@
     }
 
     if (!has_immediate_arrays && !has_indirect_arrays) {
-        LOGE("glDrawElements: no data bound to the command - ignoring\n");
+        ALOGE("glDrawElements: no data bound to the command - ignoring\n");
         return;
     }
 
@@ -398,7 +398,7 @@
             }
             break;
         default:
-            LOGE("unsupported index buffer type %d\n", type);
+            ALOGE("unsupported index buffer type %d\n", type);
         }
         if (has_indirect_arrays || 1) {
             ctx->sendVertexAttributes(minIndex, maxIndex - minIndex + 1);
@@ -406,12 +406,12 @@
                                     count * glSizeof(type));
             // XXX - OPTIMIZATION (see the other else branch) should be implemented
             if(!has_indirect_arrays) {
-                //LOGD("unoptimized drawelements !!!\n");
+                //ALOGD("unoptimized drawelements !!!\n");
             }
         } else {
             // we are all direct arrays and immidate mode index array -
             // rebuild the arrays and the index array;
-            LOGE("glDrawElements: direct index & direct buffer data - will be implemented in later versions;\n");
+            ALOGE("glDrawElements: direct index & direct buffer data - will be implemented in later versions;\n");
         }
     }
 }
diff --git a/tools/emulator/opengl/system/OpenglSystemCommon/HostConnection.cpp b/tools/emulator/opengl/system/OpenglSystemCommon/HostConnection.cpp
index 3355d9f..940f5ae 100644
--- a/tools/emulator/opengl/system/OpenglSystemCommon/HostConnection.cpp
+++ b/tools/emulator/opengl/system/OpenglSystemCommon/HostConnection.cpp
@@ -63,12 +63,12 @@
         if (useQemuPipe) {
             QemuPipeStream *stream = new QemuPipeStream(STREAM_BUFFER_SIZE);
             if (!stream) {
-                LOGE("Failed to create QemuPipeStream for host connection!!!\n");
+                ALOGE("Failed to create QemuPipeStream for host connection!!!\n");
                 delete con;
                 return NULL;
             }
             if (stream->connect() < 0) {
-                LOGE("Failed to connect to host (QemuPipeStream)!!!\n");
+                ALOGE("Failed to connect to host (QemuPipeStream)!!!\n");
                 delete stream;
                 delete con;
                 return NULL;
@@ -79,13 +79,13 @@
         {
             TcpStream *stream = new TcpStream(STREAM_BUFFER_SIZE);
             if (!stream) {
-                LOGE("Failed to create TcpStream for host connection!!!\n");
+                ALOGE("Failed to create TcpStream for host connection!!!\n");
                 delete con;
                 return NULL;
             }
 
             if (stream->connect("10.0.2.2", STREAM_PORT_NUM) < 0) {
-                LOGE("Failed to connect to host (TcpStream)!!!\n");
+                ALOGE("Failed to connect to host (TcpStream)!!!\n");
                 delete stream;
                 delete con;
                 return NULL;
@@ -99,7 +99,7 @@
         *pClientFlags = 0;
         con->m_stream->commitBuffer(sizeof(unsigned int));
 
-        LOGD("HostConnection::get() New Host Connection established %p, tid %d\n", con, gettid());
+        ALOGD("HostConnection::get() New Host Connection established %p, tid %d\n", con, gettid());
         tinfo->hostConn = con;
     }
 
diff --git a/tools/emulator/opengl/system/egl/egl.cpp b/tools/emulator/opengl/system/egl/egl.cpp
index 93f8681..fcd7720 100644
--- a/tools/emulator/opengl/system/egl/egl.cpp
+++ b/tools/emulator/opengl/system/egl/egl.cpp
@@ -65,12 +65,12 @@
 
 #define setErrorReturn(error, retVal)     \
     {                                                \
-        LOGE("tid %d: %s(%d): error 0x%x (%s)", gettid(), __FUNCTION__, __LINE__, error, eglStrError(error));     \
+        ALOGE("tid %d: %s(%d): error 0x%x (%s)", gettid(), __FUNCTION__, __LINE__, error, eglStrError(error));     \
         return setErrorFunc(error, retVal);            \
     }
 
 #define RETURN_ERROR(ret,err)           \
-    LOGE("tid %d: %s(%d): error 0x%x (%s)", gettid(), __FUNCTION__, __LINE__, err, eglStrError(err));    \
+    ALOGE("tid %d: %s(%d): error 0x%x (%s)", gettid(), __FUNCTION__, __LINE__, err, eglStrError(err));    \
     getEGLThreadInfo()->eglError = err;    \
     return ret;
 
@@ -107,12 +107,12 @@
 #define DEFINE_AND_VALIDATE_HOST_CONNECTION(ret) \
     HostConnection *hostCon = HostConnection::get(); \
     if (!hostCon) { \
-        LOGE("egl: Failed to get host connection\n"); \
+        ALOGE("egl: Failed to get host connection\n"); \
         return ret; \
     } \
     renderControl_encoder_context_t *rcEnc = hostCon->rcEncoder(); \
     if (!rcEnc) { \
-        LOGE("egl: Failed to get renderControl encoder context\n"); \
+        ALOGE("egl: Failed to get renderControl encoder context\n"); \
         return ret; \
     }
 
@@ -282,7 +282,7 @@
     DEFINE_AND_VALIDATE_HOST_CONNECTION(EGL_FALSE);
     rcSurface = rcEnc->rcCreateWindowSurface(rcEnc, (uint32_t)config, getWidth(), getHeight());
     if (!rcSurface) {
-        LOGE("rcCreateWindowSurface returned 0");
+        ALOGE("rcCreateWindowSurface returned 0");
         return EGL_FALSE;
     }
     valid = EGL_TRUE;
@@ -292,7 +292,7 @@
 EGLBoolean egl_window_surface_t::rcDestroy()
 {
     if (!rcSurface) {
-        LOGE("rcDestroy called on invalid rcSurface");
+        ALOGE("rcDestroy called on invalid rcSurface");
         return EGL_FALSE;
     }
 
@@ -395,12 +395,12 @@
     DEFINE_AND_VALIDATE_HOST_CONNECTION(EGL_FALSE);
     rcSurface = rcEnc->rcCreateWindowSurface(rcEnc, (uint32_t)config, getWidth(), getHeight());
     if (!rcSurface) {
-        LOGE("rcCreateWindowSurface returned 0");
+        ALOGE("rcCreateWindowSurface returned 0");
         return EGL_FALSE;
     }
     rcColorBuffer = rcEnc->rcCreateColorBuffer(rcEnc, getWidth(), getHeight(), format);
     if (!rcColorBuffer) {
-        LOGE("rcCreateColorBuffer returned 0");
+        ALOGE("rcCreateColorBuffer returned 0");
         return EGL_FALSE;
     }
 
@@ -411,7 +411,7 @@
 EGLBoolean egl_pbuffer_surface_t::rcDestroy()
 {
     if ((!rcSurface)||(!rcColorBuffer)) {
-        LOGE("destroyRc called on invalid rcSurface");
+        ALOGE("destroyRc called on invalid rcSurface");
         return EGL_FALSE;
     }
 
@@ -782,7 +782,7 @@
             break;
         //TODO: complete other attributes
         default:
-            LOGE("eglQuerySurface %x  EGL_BAD_ATTRIBUTE", attribute);
+            ALOGE("eglQuerySurface %x  EGL_BAD_ATTRIBUTE", attribute);
             ret = setErrorFunc(EGL_BAD_ATTRIBUTE, EGL_FALSE);
             break;
     }
@@ -819,14 +819,14 @@
 EGLSurface eglCreatePbufferFromClientBuffer(EGLDisplay dpy, EGLenum buftype, EGLClientBuffer buffer, EGLConfig config, const EGLint *attrib_list)
 {
     //TODO
-    LOGW("%s not implemented", __FUNCTION__);
+    ALOGW("%s not implemented", __FUNCTION__);
     return 0;
 }
 
 EGLBoolean eglSurfaceAttrib(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint value)
 {
     //TODO
-    LOGW("%s not implemented", __FUNCTION__);
+    ALOGW("%s not implemented", __FUNCTION__);
     return 0;
 }
 
@@ -864,7 +864,7 @@
 EGLBoolean eglReleaseTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer)
 {
     //TODO
-    LOGW("%s not implemented", __FUNCTION__);
+    ALOGW("%s not implemented", __FUNCTION__);
     return 0;
 }
 
@@ -900,7 +900,7 @@
     DEFINE_AND_VALIDATE_HOST_CONNECTION(EGL_NO_CONTEXT);
     uint32_t rcContext = rcEnc->rcCreateContext(rcEnc, (uint32_t)config, rcShareCtx, version);
     if (!rcContext) {
-        LOGE("rcCreateContext returned 0");
+        ALOGE("rcCreateContext returned 0");
         setErrorReturn(EGL_BAD_ALLOC, EGL_NO_CONTEXT);
     }
 
@@ -972,7 +972,7 @@
 
     DEFINE_AND_VALIDATE_HOST_CONNECTION(EGL_FALSE);
     if (rcEnc->rcMakeCurrent(rcEnc, ctxHandle, drawHandle, readHandle) == EGL_FALSE) {
-        LOGE("rcMakeCurrent returned EGL_FALSE");
+        ALOGE("rcMakeCurrent returned EGL_FALSE");
         setErrorReturn(EGL_BAD_CONTEXT, EGL_FALSE);
     }
 
@@ -1098,7 +1098,7 @@
                 *value = EGL_BACK_BUFFER; //single buffer not supported
             break;
         default:
-            LOGE("eglQueryContext %x  EGL_BAD_ATTRIBUTE", attribute);
+            ALOGE("eglQueryContext %x  EGL_BAD_ATTRIBUTE", attribute);
             setErrorReturn(EGL_BAD_ATTRIBUTE, EGL_FALSE);
             break;
     }
diff --git a/tools/emulator/opengl/system/egl/eglDisplay.cpp b/tools/emulator/opengl/system/egl/eglDisplay.cpp
index 7beeb8e..2497548 100644
--- a/tools/emulator/opengl/system/egl/eglDisplay.cpp
+++ b/tools/emulator/opengl/system/egl/eglDisplay.cpp
@@ -88,7 +88,7 @@
                                          &s_gles_lib);
         if (!m_gles_iface) {
             pthread_mutex_unlock(&m_lock);
-            LOGE("Failed to load gles1 iface");
+            ALOGE("Failed to load gles1 iface");
             return false;
         }
 
@@ -106,7 +106,7 @@
         HostConnection *hcon = HostConnection::get();
         if (!hcon) {
             pthread_mutex_unlock(&m_lock);
-            LOGE("Failed to establish connection with the host\n");
+            ALOGE("Failed to establish connection with the host\n");
             return false;
         }
 
@@ -116,7 +116,7 @@
         renderControl_encoder_context_t *rcEnc = hcon->rcEncoder();
         if (!rcEnc) {
             pthread_mutex_unlock(&m_lock);
-            LOGE("Failed to get renderControl encoder instance");
+            ALOGE("Failed to get renderControl encoder instance");
             return false;
         }
 
@@ -228,13 +228,13 @@
 {
     void *lib = dlopen(libName, RTLD_NOW);
     if (!lib) {
-        LOGE("Failed to dlopen %s", libName);
+        ALOGE("Failed to dlopen %s", libName);
         return NULL;
     }
 
     init_emul_gles_t init_gles_func = (init_emul_gles_t)dlsym(lib,"init_emul_gles");
     if (!init_gles_func) {
-        LOGE("Failed to find init_emul_gles");
+        ALOGE("Failed to find init_emul_gles");
         dlclose((void*)lib);
         return NULL;
     }
@@ -385,7 +385,7 @@
         return m_extensionString;
     }
     else {
-        LOGE("[%s] Unknown name %d\n", __FUNCTION__, name);
+        ALOGE("[%s] Unknown name %d\n", __FUNCTION__, name);
         return NULL;
     }
 }
@@ -397,7 +397,7 @@
 {
     if (attribIdx == ATTRIBUTE_NONE)
     {
-        LOGE("[%s] Bad attribute idx\n", __FUNCTION__);
+        ALOGE("[%s] Bad attribute idx\n", __FUNCTION__);
         return EGL_FALSE;
     }
     *value = *(m_configs + (int)config*m_numConfigAttribs + attribIdx);
@@ -430,7 +430,7 @@
 {
     if (attribIdx == ATTRIBUTE_NONE)
     {
-        LOGE("[%s] Bad attribute idx\n", __FUNCTION__);
+        ALOGE("[%s] Bad attribute idx\n", __FUNCTION__);
         return EGL_FALSE;
     }
     *(m_configs + (int)config*m_numConfigAttribs + attribIdx) = value;
@@ -456,7 +456,7 @@
         getAttribValue(config, m_attribs.valueFor(EGL_GREEN_SIZE), &greenSize) &&
         getAttribValue(config, m_attribs.valueFor(EGL_ALPHA_SIZE), &alphaSize)) )
     {
-        LOGE("Couldn't find value for one of the pixel format attributes");
+        ALOGE("Couldn't find value for one of the pixel format attributes");
         return EGL_FALSE;
     }
 
@@ -480,7 +480,7 @@
         getAttribValue(config, m_attribs.valueFor(EGL_GREEN_SIZE), &greenSize) &&
         getAttribValue(config, m_attribs.valueFor(EGL_ALPHA_SIZE), &alphaSize)) )
     {
-        LOGE("Couldn't find value for one of the pixel format attributes");
+        ALOGE("Couldn't find value for one of the pixel format attributes");
         return EGL_FALSE;
     }
 
diff --git a/tools/emulator/opengl/system/gralloc/gralloc.cpp b/tools/emulator/opengl/system/gralloc/gralloc.cpp
index b27eaa3..0d5bb6e 100644
--- a/tools/emulator/opengl/system/gralloc/gralloc.cpp
+++ b/tools/emulator/opengl/system/gralloc/gralloc.cpp
@@ -35,13 +35,13 @@
 #define DEBUG  0
 
 #if DEBUG >= 1
-#  define D(...)   LOGD(__VA_ARGS__)
+#  define D(...)   ALOGD(__VA_ARGS__)
 #else
 #  define D(...)   ((void)0)
 #endif
 
 #if DEBUG >= 2
-#  define DD(...)  LOGD(__VA_ARGS__)
+#  define DD(...)  ALOGD(__VA_ARGS__)
 #else
 #  define DD(...)  ((void)0)
 #endif
@@ -113,12 +113,12 @@
 #define DEFINE_AND_VALIDATE_HOST_CONNECTION \
     HostConnection *hostCon = HostConnection::get(); \
     if (!hostCon) { \
-        LOGE("gralloc: Failed to get host connection\n"); \
+        ALOGE("gralloc: Failed to get host connection\n"); \
         return -EIO; \
     } \
     renderControl_encoder_context_t *rcEnc = hostCon->rcEncoder(); \
     if (!rcEnc) { \
-        LOGE("gralloc: Failed to get renderControl encoder context\n"); \
+        ALOGE("gralloc: Failed to get renderControl encoder context\n"); \
         return -EIO; \
     }
 
@@ -209,7 +209,7 @@
 
         fd = ashmem_create_region("gralloc-buffer", ashmem_size);
         if (fd < 0) {
-            LOGE("gralloc_alloc failed to create ashmem region: %s\n", strerror(errno));
+            ALOGE("gralloc_alloc failed to create ashmem region: %s\n", strerror(errno));
             return -errno;
         }
     }
@@ -503,7 +503,7 @@
     private_module_t *gr = (private_module_t *)module;
     cb_handle_t *cb = (cb_handle_t *)handle;
     if (!gr || !cb_handle_t::validate(cb)) {
-        LOGE("gralloc_lock bad handle\n");
+        ALOGE("gralloc_lock bad handle\n");
         return -EINVAL;
     }
 
@@ -522,7 +522,7 @@
          (!sw_read && !sw_write) ||
          (sw_read && !sw_read_allowed) ||
          (sw_write && !sw_write_allowed) ) {
-        LOGE("gralloc_lock usage mismatch usage=0x%x cb->usage=0x%x\n", usage, cb->usage);
+        ALOGE("gralloc_lock usage mismatch usage=0x%x cb->usage=0x%x\n", usage, cb->usage);
         return -EINVAL;
     }
 
@@ -559,7 +559,7 @@
         if (hostSyncStatus < 0) {
             // host failed the color buffer sync - probably since it was already
             // locked for write access. fail the lock.
-            LOGE("gralloc_lock cacheFlush failed postCount=%d sw_read=%d\n",
+            ALOGE("gralloc_lock cacheFlush failed postCount=%d sw_read=%d\n",
                  postCount, sw_read);
             return -EBUSY;
         }
@@ -669,7 +669,7 @@
         // return error if connection with host can not be established
         HostConnection *hostCon = HostConnection::get();
         if (!hostCon) {
-            LOGE("gralloc: failed to get host connection while opening %s\n", name);
+            ALOGE("gralloc: failed to get host connection while opening %s\n", name);
             return -EIO;
         }
 
@@ -805,7 +805,7 @@
     if (atoi(prop) > 0) {
         return;
     }
-    LOGD("Emulator without GPU emulation detected.");
+    ALOGD("Emulator without GPU emulation detected.");
     module = dlopen("/system/lib/hw/gralloc.default.so", RTLD_LAZY|RTLD_LOCAL);
     if (module != NULL) {
         sFallback = reinterpret_cast<gralloc_module_t*>(dlsym(module, HAL_MODULE_INFO_SYM_AS_STR));
@@ -814,6 +814,6 @@
         }
     }
     if (sFallback == NULL) {
-        LOGE("Could not find software fallback module!?");
+        ALOGE("Could not find software fallback module!?");
     }
 }
diff --git a/tools/emulator/opengl/tests/gles_android_wrapper/ServerConnection.cpp b/tools/emulator/opengl/tests/gles_android_wrapper/ServerConnection.cpp
index 1204264..ff4e390 100644
--- a/tools/emulator/opengl/tests/gles_android_wrapper/ServerConnection.cpp
+++ b/tools/emulator/opengl/tests/gles_android_wrapper/ServerConnection.cpp
@@ -83,7 +83,7 @@
         QemuPipeStream*  pipeStream = new QemuPipeStream(bufsize);
 
         if (pipeStream->connect() < 0) {
-            LOGE("couldn't connect to host server\n");
+            ALOGE("couldn't connect to host server\n");
             delete pipeStream;
             return -1;
         }
@@ -102,7 +102,7 @@
         }
 
         if (tcpStream->connect(hostname, CODEC_SERVER_PORT) < 0) {
-            LOGE("couldn't connect to %s\n", hostname);
+            ALOGE("couldn't connect to %s\n", hostname);
             free(hostname);
             delete tcpStream;
             return -1;
diff --git a/tools/emulator/opengl/tests/gles_android_wrapper/egl.cpp b/tools/emulator/opengl/tests/gles_android_wrapper/egl.cpp
index 1ee2b6a..1e2e456 100644
--- a/tools/emulator/opengl/tests/gles_android_wrapper/egl.cpp
+++ b/tools/emulator/opengl/tests/gles_android_wrapper/egl.cpp
@@ -58,7 +58,7 @@
 {
     void *driverLib = dlopen(driverLibName, RTLD_NOW | RTLD_LOCAL);
     if (driverLib == NULL) {
-        LOGE("failed to load %s : %s\n", driverLibName, dlerror());
+        ALOGE("failed to load %s : %s\n", driverLibName, dlerror());
         return -1;
     }
 
@@ -66,13 +66,13 @@
     createFcn_t createFcn;
     createFcn = (createFcn_t) dlsym(driverLib, "createFromLib");
     if (createFcn == NULL) {
-        LOGE("failed to load createFromLib constructor function\n");
+        ALOGE("failed to load createFromLib constructor function\n");
         return -1;
     }
 
     void *implLib = dlopen(implLibName, RTLD_NOW | RTLD_LOCAL);
     if (implLib == NULL) {
-        LOGE("couldn't open %s", implLibName);
+        ALOGE("couldn't open %s", implLibName);
         return -2;
     }
     *dispatchTable = createFcn(implLib, accessor);
@@ -85,7 +85,7 @@
 
     // XXX - we do not dlclose the driver library, so its not initialized when
     // later loaded by android - is this required?
-    LOGD("loading %s into %s complete\n", implLibName, driverLibName);
+    ALOGD("loading %s into %s complete\n", implLibName, driverLibName);
     return 0;
 
 }
@@ -112,20 +112,20 @@
             // we need to obtain our process name from the command line;
             FILE *fp = fopen("/proc/self/cmdline", "rt");
             if (fp == NULL) {
-                LOGE("couldn't open /proc/self/cmdline\n");
+                ALOGE("couldn't open /proc/self/cmdline\n");
                 return NULL;
             }
 
             char line[1000];
             if (fgets(line, sizeof(line), fp) == NULL) {
-                LOGE("couldn't read the self cmdline from \n");
+                ALOGE("couldn't read the self cmdline from \n");
                 fclose(fp);
                 return NULL;
             }
             fclose(fp);
 
             if (line[0] == '\0') {
-                LOGE("cmdline is empty\n");
+                ALOGE("cmdline is empty\n");
                 return NULL;
             }
 
@@ -155,11 +155,11 @@
 {
     const char *procname = getProcName();
     if (procname == NULL) return false;
-    LOGD("isNeedEncode? for %s\n", procname);
+    ALOGD("isNeedEncode? for %s\n", procname);
     // check on our whitelist
     FILE *fp = fopen(GLES_EMUL_TARGETS_FILE, "rt");
     if (fp == NULL) {
-        LOGE("couldn't open %s\n", GLES_EMUL_TARGETS_FILE);
+        ALOGE("couldn't open %s\n", GLES_EMUL_TARGETS_FILE);
         return false;
     }
 
@@ -173,7 +173,7 @@
             char c = line[procnameLen];
             if (c == '\0' || c == ' ' || c == '\t' || c == '\n') {
                 found = true;
-                LOGD("should use encoder for %s\n", procname);
+                ALOGD("should use encoder for %s\n", procname);
                 break;
             }
         }
@@ -187,7 +187,7 @@
     //
     // Load our back-end implementation of EGL/GLES
     //
-    LOGD("Loading egl dispatch for %s\n", getProcName());
+    ALOGD("Loading egl dispatch for %s\n", getProcName());
 
     void *gles_android = dlopen("/system/lib/egl/libGLES_android.so", RTLD_NOW | RTLD_LOCAL);
     if (!gles_android) {
@@ -213,7 +213,7 @@
         // initialize a connection to the server, and the GLESv1/v2 encoders;
         ServerConnection * connection = ServerConnection::s_getServerConnection();
         if (connection == NULL) {
-            LOGE("couldn't create server connection\n");
+            ALOGE("couldn't create server connection\n");
             s_needEncode = false;
         }
     }
@@ -231,7 +231,7 @@
     }
 
     if (!s_needEncode) {
-        LOGD("Initializing native opengl for %s\n", getProcName());
+        ALOGD("Initializing native opengl for %s\n", getProcName());
         initApi<gl_wrapper_context_t>(GLESv1_DRIVER, GLES_android_LIB, &g_gl_dispatch, getGLContext);
         // try to initialize gl2 from GLES, though its probably going to fail
         initApi<gl2_wrapper_context_t>(GLESv2_DRIVER, GLES_android_LIB, &g_gl2_dispatch, getGL2Context);
@@ -313,7 +313,7 @@
             if (attribs[i + 1] & EGL_OPENGL_ES2_BIT) {
                 attribs[i + 1] &= ~EGL_OPENGL_ES2_BIT;
                 attribs[i + 1] |= EGL_OPENGL_ES_BIT;
-                LOGD("removing ES2 bit 0x%x\n", attribs[i + 1]);
+                ALOGD("removing ES2 bit 0x%x\n", attribs[i + 1]);
                 if (isES2 != NULL) *isES2 = true;
             }
         }
@@ -331,11 +331,11 @@
                                               configs,
                                               config_size,
                                               num_config);
-        LOGD("eglChooseConfig: %d configs found\n", *num_config);
+        ALOGD("eglChooseConfig: %d configs found\n", *num_config);
         if (*num_config == 0 && attribs != NULL) {
-            LOGD("requested attributes:\n");
+            ALOGD("requested attributes:\n");
             for (int i = 0; attribs[i] != EGL_NONE; i++) {
-                LOGD("%d: 0x%x\n", i, attribs[i]);
+                ALOGD("%d: 0x%x\n", i, attribs[i]);
             }
         }
 
diff --git a/tools/emulator/opengl/tests/gles_android_wrapper/gles.cpp b/tools/emulator/opengl/tests/gles_android_wrapper/gles.cpp
index f0a22aa..c0949c8 100644
--- a/tools/emulator/opengl/tests/gles_android_wrapper/gles.cpp
+++ b/tools/emulator/opengl/tests/gles_android_wrapper/gles.cpp
@@ -27,7 +27,7 @@
 {
     s_dispatch = create_gles_dispatch(gles_android);
     if (s_dispatch == NULL) {
-        LOGE("failed to create gles dispatch\n");
+        ALOGE("failed to create gles dispatch\n");
     }
 }
 
diff --git a/tools/emulator/system/camera/CallbackNotifier.cpp b/tools/emulator/system/camera/CallbackNotifier.cpp
index f974b86..41ea0f8 100755
--- a/tools/emulator/system/camera/CallbackNotifier.cpp
+++ b/tools/emulator/system/camera/CallbackNotifier.cpp
@@ -80,7 +80,7 @@
     const char* strs[lCameraMessagesNum];
     const int translated = GetMessageStrings(msg, strs, lCameraMessagesNum);
     for (int n = 0; n < translated; n++) {
-        LOGV("    %s", strs[n]);
+        ALOGV("    %s", strs[n]);
     }
 }
 
@@ -113,7 +113,7 @@
                                     camera_request_memory get_memory,
                                     void* user)
 {
-    LOGV("%s: %p, %p, %p, %p (%p)",
+    ALOGV("%s: %p, %p, %p, %p (%p)",
          __FUNCTION__, notify_cb, data_cb, data_cb_timestamp, get_memory, user);
 
     Mutex::Autolock locker(&mObjectLock);
@@ -126,29 +126,29 @@
 
 void CallbackNotifier::enableMessage(uint msg_type)
 {
-    LOGV("%s: msg_type = 0x%x", __FUNCTION__, msg_type);
+    ALOGV("%s: msg_type = 0x%x", __FUNCTION__, msg_type);
     PrintMessages(msg_type);
 
     Mutex::Autolock locker(&mObjectLock);
     mMessageEnabler |= msg_type;
-    LOGV("**** Currently enabled messages:");
+    ALOGV("**** Currently enabled messages:");
     PrintMessages(mMessageEnabler);
 }
 
 void CallbackNotifier::disableMessage(uint msg_type)
 {
-    LOGV("%s: msg_type = 0x%x", __FUNCTION__, msg_type);
+    ALOGV("%s: msg_type = 0x%x", __FUNCTION__, msg_type);
     PrintMessages(msg_type);
 
     Mutex::Autolock locker(&mObjectLock);
     mMessageEnabler &= ~msg_type;
-    LOGV("**** Currently enabled messages:");
+    ALOGV("**** Currently enabled messages:");
     PrintMessages(mMessageEnabler);
 }
 
 status_t CallbackNotifier::enableVideoRecording(int fps)
 {
-    LOGV("%s: FPS = %d", __FUNCTION__, fps);
+    ALOGV("%s: FPS = %d", __FUNCTION__, fps);
 
     Mutex::Autolock locker(&mObjectLock);
     mVideoRecEnabled = true;
@@ -160,7 +160,7 @@
 
 void CallbackNotifier::disableVideoRecording()
 {
-    LOGV("%s:", __FUNCTION__);
+    ALOGV("%s:", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     mVideoRecEnabled = false;
@@ -215,7 +215,7 @@
             mDataCBTimestamp(timestamp, CAMERA_MSG_VIDEO_FRAME,
                                cam_buff, 0, mCBOpaque);
         } else {
-            LOGE("%s: Memory failure in CAMERA_MSG_VIDEO_FRAME", __FUNCTION__);
+            ALOGE("%s: Memory failure in CAMERA_MSG_VIDEO_FRAME", __FUNCTION__);
         }
     }
 
@@ -227,7 +227,7 @@
             mDataCB(CAMERA_MSG_PREVIEW_FRAME, cam_buff, 0, NULL, mCBOpaque);
             cam_buff->release(cam_buff);
         } else {
-            LOGE("%s: Memory failure in CAMERA_MSG_PREVIEW_FRAME", __FUNCTION__);
+            ALOGE("%s: Memory failure in CAMERA_MSG_PREVIEW_FRAME", __FUNCTION__);
         }
     }
 
@@ -261,10 +261,10 @@
                     mDataCB(CAMERA_MSG_COMPRESSED_IMAGE, jpeg_buff, 0, NULL, mCBOpaque);
                     jpeg_buff->release(jpeg_buff);
                 } else {
-                    LOGE("%s: Memory failure in CAMERA_MSG_VIDEO_FRAME", __FUNCTION__);
+                    ALOGE("%s: Memory failure in CAMERA_MSG_VIDEO_FRAME", __FUNCTION__);
                 }
             } else {
-                LOGE("%s: Compression failure in CAMERA_MSG_VIDEO_FRAME", __FUNCTION__);
+                ALOGE("%s: Compression failure in CAMERA_MSG_VIDEO_FRAME", __FUNCTION__);
             }
         }
     }
diff --git a/tools/emulator/system/camera/EmulatedCamera.cpp b/tools/emulator/system/camera/EmulatedCamera.cpp
index 02b4683..d54d7b4 100755
--- a/tools/emulator/system/camera/EmulatedCamera.cpp
+++ b/tools/emulator/system/camera/EmulatedCamera.cpp
@@ -28,7 +28,7 @@
 #include <cutils/log.h>
 #include <ui/Rect.h>
 #include "EmulatedCamera.h"
-#include "EmulatedFakeCameraDevice.h"
+//#include "EmulatedFakeCameraDevice.h"
 #include "Converters.h"
 
 /* Defines whether we should trace parameter changes. */
@@ -99,12 +99,8 @@
      * Fake required parameters.
      */
 
-    mParameters.set(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES,
-                    "320x240,0x0");
-    mParameters.set(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION, "6");
-    mParameters.set(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION, "-6");
-    mParameters.set(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP, "0.5");
-    mParameters.set(CameraParameters::KEY_EXPOSURE_COMPENSATION, "0");
+    mParameters.set(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES, "320x240,0x0");
+
     mParameters.set(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH, "512");
     mParameters.set(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT, "384");
     mParameters.set(CameraParameters::KEY_JPEG_QUALITY, "90");
@@ -137,10 +133,36 @@
                     CameraParameters::PIXEL_FORMAT_JPEG);
     mParameters.setPictureFormat(CameraParameters::PIXEL_FORMAT_JPEG);
 
-    /*
-     * Not supported features
-     */
+    /* Set exposure compensation. */
+    mParameters.set(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION, "6");
+    mParameters.set(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION, "-6");
+    mParameters.set(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP, "0.5");
+    mParameters.set(CameraParameters::KEY_EXPOSURE_COMPENSATION, "0");
 
+    /* Sets the white balance modes and the device-dependent scale factors. */
+    char supported_white_balance[1024];
+    snprintf(supported_white_balance, sizeof(supported_white_balance),
+             "%s,%s,%s,%s",
+             CameraParameters::WHITE_BALANCE_AUTO,
+             CameraParameters::WHITE_BALANCE_INCANDESCENT,
+             CameraParameters::WHITE_BALANCE_DAYLIGHT,
+             CameraParameters::WHITE_BALANCE_TWILIGHT);
+    mParameters.set(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE,
+                    supported_white_balance);
+    mParameters.set(CameraParameters::KEY_WHITE_BALANCE,
+                    CameraParameters::WHITE_BALANCE_AUTO);
+    getCameraDevice()->initializeWhiteBalanceModes(
+            CameraParameters::WHITE_BALANCE_AUTO, 1.0f, 1.0f);
+    getCameraDevice()->initializeWhiteBalanceModes(
+            CameraParameters::WHITE_BALANCE_INCANDESCENT, 1.38f, 0.60f);
+    getCameraDevice()->initializeWhiteBalanceModes(
+            CameraParameters::WHITE_BALANCE_DAYLIGHT, 1.09f, 0.92f);
+    getCameraDevice()->initializeWhiteBalanceModes(
+            CameraParameters::WHITE_BALANCE_TWILIGHT, 0.92f, 1.22f);
+    getCameraDevice()->setWhiteBalanceMode(CameraParameters::WHITE_BALANCE_AUTO);
+
+    /* Not supported features
+     */
     mParameters.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
                     CameraParameters::FOCUS_MODE_FIXED);
     mParameters.set(CameraParameters::KEY_FOCUS_MODE,
@@ -172,11 +194,11 @@
 
 status_t EmulatedCamera::connectCamera(hw_device_t** device)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     status_t res = EINVAL;
     EmulatedCameraDevice* const camera_dev = getCameraDevice();
-    LOGE_IF(camera_dev == NULL, "%s: No camera device instance.", __FUNCTION__);
+    ALOGE_IF(camera_dev == NULL, "%s: No camera device instance.", __FUNCTION__);
 
     if (camera_dev != NULL) {
         /* Connect to the camera device. */
@@ -191,14 +213,14 @@
 
 status_t EmulatedCamera::closeCamera()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     return cleanupCamera();
 }
 
 status_t EmulatedCamera::getCameraInfo(struct camera_info* info)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     const char* valstr = NULL;
 
@@ -301,7 +323,7 @@
 
 status_t EmulatedCamera::setAutoFocus()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     /* TODO: Future enhancements. */
     return NO_ERROR;
@@ -309,7 +331,7 @@
 
 status_t EmulatedCamera::cancelAutoFocus()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     /* TODO: Future enhancements. */
     return NO_ERROR;
@@ -317,7 +339,7 @@
 
 status_t EmulatedCamera::takePicture()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     status_t res;
     int width, height;
@@ -336,7 +358,7 @@
         /* We only have JPEG converted for NV21 format. */
         org_fmt = V4L2_PIX_FMT_NV21;
     } else {
-        LOGE("%s: Unsupported pixel format %s", __FUNCTION__, pix_fmt);
+        ALOGE("%s: Unsupported pixel format %s", __FUNCTION__, pix_fmt);
         return EINVAL;
     }
     /* Get JPEG quality. */
@@ -359,7 +381,7 @@
      * enabled. */
     EmulatedCameraDevice* const camera_dev = getCameraDevice();
     if (camera_dev->isStarted()) {
-        LOGW("%s: Camera device is started", __FUNCTION__);
+        ALOGW("%s: Camera device is started", __FUNCTION__);
         camera_dev->stopDeliveringFrames();
         camera_dev->stopDevice();
     }
@@ -369,7 +391,7 @@
      */
 
     /* Start camera device for the picture frame. */
-    LOGD("Starting camera for picture: %.4s(%s)[%dx%d]",
+    ALOGD("Starting camera for picture: %.4s(%s)[%dx%d]",
          reinterpret_cast<const char*>(&org_fmt), pix_fmt, width, height);
     res = camera_dev->startDevice(width, height, org_fmt);
     if (res != NO_ERROR) {
@@ -394,20 +416,23 @@
 
 status_t EmulatedCamera::cancelPicture()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     return NO_ERROR;
 }
 
 status_t EmulatedCamera::setParameters(const char* parms)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
     PrintParamDiff(mParameters, parms);
 
     CameraParameters new_param;
     String8 str8_param(parms);
     new_param.unflatten(str8_param);
 
+    /*
+     * Check for new exposure compensation parameter.
+     */
     int new_exposure_compensation = new_param.getInt(
             CameraParameters::KEY_EXPOSURE_COMPENSATION);
     const int min_exposure_compensation = new_param.getInt(
@@ -435,6 +460,24 @@
                     exposure_value);
         }
     }
+
+    const char* new_white_balance = new_param.get(
+            CameraParameters::KEY_WHITE_BALANCE);
+    const char* supported_white_balance = new_param.get(
+            CameraParameters::KEY_SUPPORTED_WHITE_BALANCE);
+
+    if ((supported_white_balance != NULL) && (new_white_balance != NULL) &&
+        (strstr(supported_white_balance, new_white_balance) != NULL)) {
+
+        const char* current_white_balance = mParameters.get(
+                CameraParameters::KEY_WHITE_BALANCE);
+        if ((current_white_balance == NULL) ||
+            (strcmp(current_white_balance, new_white_balance) != 0)) {
+            ALOGV("Setting white balance to %s", new_white_balance);
+            getCameraDevice()->setWhiteBalanceMode(new_white_balance);
+        }
+    }
+
     mParameters = new_param;
 
     return NO_ERROR;
@@ -453,7 +496,7 @@
         strncpy(ret_str, params.string(), params.length()+1);
         return ret_str;
     } else {
-        LOGE("%s: Unable to allocate string for %s", __FUNCTION__, params.string());
+        ALOGE("%s: Unable to allocate string for %s", __FUNCTION__, params.string());
         /* Apparently, we can't return NULL fron this routine. */
         return &lNoParam;
     }
@@ -469,7 +512,7 @@
 
 status_t EmulatedCamera::sendCommand(int32_t cmd, int32_t arg1, int32_t arg2)
 {
-    LOGV("%s: cmd = %d, arg1 = %d, arg2 = %d", __FUNCTION__, cmd, arg1, arg2);
+    ALOGV("%s: cmd = %d, arg1 = %d, arg2 = %d", __FUNCTION__, cmd, arg1, arg2);
 
     /* TODO: Future enhancements. */
     return 0;
@@ -477,14 +520,14 @@
 
 void EmulatedCamera::releaseCamera()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     cleanupCamera();
 }
 
 status_t EmulatedCamera::dumpCamera(int fd)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     /* TODO: Future enhancements. */
     return -EINVAL;
@@ -496,7 +539,7 @@
 
 status_t EmulatedCamera::doStartPreview()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     EmulatedCameraDevice* camera_dev = getCameraDevice();
     if (camera_dev->isStarted()) {
@@ -547,7 +590,7 @@
         pix_fmt = mParameters.getPreviewFormat();
     }
     if (pix_fmt == NULL) {
-        LOGE("%s: Unable to obtain video format", __FUNCTION__);
+        ALOGE("%s: Unable to obtain video format", __FUNCTION__);
         mPreviewWindow.stopPreview();
         return EINVAL;
     }
@@ -561,11 +604,11 @@
     } else if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_YUV420SP) == 0) {
         org_fmt = V4L2_PIX_FMT_NV21;
     } else {
-        LOGE("%s: Unsupported pixel format %s", __FUNCTION__, pix_fmt);
+        ALOGE("%s: Unsupported pixel format %s", __FUNCTION__, pix_fmt);
         mPreviewWindow.stopPreview();
         return EINVAL;
     }
-    LOGD("Starting camera: %dx%d -> %.4s(%s)",
+    ALOGD("Starting camera: %dx%d -> %.4s(%s)",
          width, height, reinterpret_cast<const char*>(&org_fmt), pix_fmt);
     res = camera_dev->startDevice(width, height, org_fmt);
     if (res != NO_ERROR) {
@@ -584,7 +627,7 @@
 
 status_t EmulatedCamera::doStopPreview()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     status_t res = NO_ERROR;
     if (mPreviewWindow.isPreviewEnabled()) {
@@ -652,7 +695,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->setPreviewWindow(window);
@@ -668,7 +711,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->setCallbacks(notify_cb, data_cb, data_cb_timestamp, get_memory, user);
@@ -678,7 +721,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->enableMsgType(msg_type);
@@ -688,7 +731,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->disableMsgType(msg_type);
@@ -698,7 +741,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->isMsgTypeEnabled(msg_type);
@@ -708,7 +751,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->startPreview();
@@ -718,7 +761,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->stopPreview();
@@ -728,7 +771,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->isPreviewEnabled();
@@ -739,7 +782,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->storeMetaDataInBuffers(enable);
@@ -749,7 +792,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->startRecording();
@@ -759,7 +802,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->stopRecording();
@@ -769,7 +812,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->isRecordingEnabled();
@@ -780,7 +823,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->releaseRecordingFrame(opaque);
@@ -790,7 +833,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->setAutoFocus();
@@ -800,7 +843,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->cancelAutoFocus();
@@ -810,7 +853,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->takePicture();
@@ -820,7 +863,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->cancelPicture();
@@ -830,7 +873,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->setParameters(parms);
@@ -840,7 +883,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return NULL;
     }
     return ec->getParameters();
@@ -850,7 +893,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->putParameters(params);
@@ -863,7 +906,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->sendCommand(cmd, arg1, arg2);
@@ -873,7 +916,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return;
     }
     ec->releaseCamera();
@@ -883,7 +926,7 @@
 {
     EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->dumpCamera(fd);
@@ -894,7 +937,7 @@
     EmulatedCamera* ec =
         reinterpret_cast<EmulatedCamera*>(reinterpret_cast<struct camera_device*>(device)->priv);
     if (ec == NULL) {
-        LOGE("%s: Unexpected NULL camera device", __FUNCTION__);
+        ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
         return -EINVAL;
     }
     return ec->closeCamera();
@@ -954,7 +997,7 @@
     const size_t len1 = strlen(param);
     const size_t len2 = strlen(val);
     char* ret = reinterpret_cast<char*>(malloc(len1 + len2 + 2));
-    LOGE_IF(ret == NULL, "%s: Memory failure", __FUNCTION__);
+    ALOGE_IF(ret == NULL, "%s: Memory failure", __FUNCTION__);
     if (ret != NULL) {
         memcpy(ret, param, len1);
         ret[len1] = ',';
@@ -986,13 +1029,13 @@
             const char* in_current = current.get(tmp);
             if (in_current != NULL) {
                 if (strcmp(in_current, val)) {
-                    LOGD("=== Value changed: %s: %s -> %s", tmp, in_current, val);
+                    ALOGD("=== Value changed: %s: %s -> %s", tmp, in_current, val);
                 }
             } else {
-                LOGD("+++ New parameter: %s=%s", tmp, val);
+                ALOGD("+++ New parameter: %s=%s", tmp, val);
             }
         } else {
-            LOGW("No value separator in %s", tmp);
+            ALOGW("No value separator in %s", tmp);
         }
         wrk = next + 1;
         next = strchr(wrk, ';');
diff --git a/tools/emulator/system/camera/EmulatedCameraCommon.h b/tools/emulator/system/camera/EmulatedCameraCommon.h
index 907985a..c1d575c 100755
--- a/tools/emulator/system/camera/EmulatedCameraCommon.h
+++ b/tools/emulator/system/camera/EmulatedCameraCommon.h
@@ -34,12 +34,12 @@
     /* Constructor that prints an "entry" trace message. */
     explicit HWERoutineTracker(const char* name)
             : mName(name) {
-        LOGV("Entering %s", mName);
+        ALOGV("Entering %s", mName);
     }
 
     /* Destructor that prints a "leave" trace message. */
     ~HWERoutineTracker() {
-        LOGV("Leaving %s", mName);
+        ALOGV("Leaving %s", mName);
     }
 
 private:
diff --git a/tools/emulator/system/camera/EmulatedCameraDevice.cpp b/tools/emulator/system/camera/EmulatedCameraDevice.cpp
index 71464d2..5c52808 100755
--- a/tools/emulator/system/camera/EmulatedCameraDevice.cpp
+++ b/tools/emulator/system/camera/EmulatedCameraDevice.cpp
@@ -29,25 +29,33 @@
 #include <sys/select.h>
 #include <cmath>
 #include "EmulatedCameraDevice.h"
-#include "Converters.h"
 
 namespace android {
 
+const float GAMMA_CORRECTION = 2.2f;
 EmulatedCameraDevice::EmulatedCameraDevice(EmulatedCamera* camera_hal)
     : mObjectLock(),
       mCurFrameTimestamp(0),
       mCameraHAL(camera_hal),
       mCurrentFrame(NULL),
       mExposureCompensation(1.0f),
+      mWhiteBalanceScale(NULL),
+      mSupportedWhiteBalanceScale(),
       mState(ECDS_CONSTRUCTED)
 {
 }
 
 EmulatedCameraDevice::~EmulatedCameraDevice()
 {
+    ALOGV("EmulatedCameraDevice destructor");
     if (mCurrentFrame != NULL) {
         delete[] mCurrentFrame;
     }
+    for (int i = 0; i < mSupportedWhiteBalanceScale.size(); ++i) {
+        if (mSupportedWhiteBalanceScale.valueAt(i) != NULL) {
+            delete[] mSupportedWhiteBalanceScale.valueAt(i);
+        }
+    }
 }
 
 /****************************************************************************
@@ -57,7 +65,7 @@
 status_t EmulatedCameraDevice::Initialize()
 {
     if (isInitialized()) {
-        LOGW("%s: Emulated camera device is already initialized: mState = %d",
+        ALOGW("%s: Emulated camera device is already initialized: mState = %d",
              __FUNCTION__, mState);
         return NO_ERROR;
     }
@@ -65,7 +73,7 @@
     /* Instantiate worker thread object. */
     mWorkerThread = new WorkerThread(this);
     if (getWorkerThread() == NULL) {
-        LOGE("%s: Unable to instantiate worker thread object", __FUNCTION__);
+        ALOGE("%s: Unable to instantiate worker thread object", __FUNCTION__);
         return ENOMEM;
     }
 
@@ -76,52 +84,85 @@
 
 status_t EmulatedCameraDevice::startDeliveringFrames(bool one_burst)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     if (!isStarted()) {
-        LOGE("%s: Device is not started", __FUNCTION__);
+        ALOGE("%s: Device is not started", __FUNCTION__);
         return EINVAL;
     }
 
     /* Frames will be delivered from the thread routine. */
     const status_t res = startWorkerThread(one_burst);
-    LOGE_IF(res != NO_ERROR, "%s: startWorkerThread failed", __FUNCTION__);
+    ALOGE_IF(res != NO_ERROR, "%s: startWorkerThread failed", __FUNCTION__);
     return res;
 }
 
 status_t EmulatedCameraDevice::stopDeliveringFrames()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     if (!isStarted()) {
-        LOGW("%s: Device is not started", __FUNCTION__);
+        ALOGW("%s: Device is not started", __FUNCTION__);
         return NO_ERROR;
     }
 
     const status_t res = stopWorkerThread();
-    LOGE_IF(res != NO_ERROR, "%s: startWorkerThread failed", __FUNCTION__);
+    ALOGE_IF(res != NO_ERROR, "%s: startWorkerThread failed", __FUNCTION__);
     return res;
 }
 
 void EmulatedCameraDevice::setExposureCompensation(const float ev) {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     if (!isStarted()) {
-        LOGW("%s: Fake camera device is not started.", __FUNCTION__);
+        ALOGW("%s: Fake camera device is not started.", __FUNCTION__);
     }
 
-    mExposureCompensation = std::pow(2.0f, ev);
-    LOGV("New exposure compensation is %f", mExposureCompensation);
+    mExposureCompensation = std::pow(2.0f, ev / GAMMA_CORRECTION);
+    ALOGV("New exposure compensation is %f", mExposureCompensation);
+}
+
+void EmulatedCameraDevice::initializeWhiteBalanceModes(const char* mode,
+                                                       const float r_scale,
+                                                       const float b_scale) {
+    ALOGV("%s with %s, %f, %f", __FUNCTION__, mode, r_scale, b_scale);
+    float* value = new float[3];
+    value[0] = r_scale; value[1] = 1.0f; value[2] = b_scale;
+    mSupportedWhiteBalanceScale.add(String8(mode), value);
+}
+
+void EmulatedCameraDevice::setWhiteBalanceMode(const char* mode) {
+    ALOGV("%s with white balance %s", __FUNCTION__, mode);
+    mWhiteBalanceScale =
+            mSupportedWhiteBalanceScale.valueFor(String8(mode));
+}
+
+/* Computes the pixel value after adjusting the white balance to the current
+ * one. The input the y, u, v channel of the pixel and the adjusted value will
+ * be stored in place. The adjustment is done in RGB space.
+ */
+void EmulatedCameraDevice::changeWhiteBalance(uint8_t& y,
+                                              uint8_t& u,
+                                              uint8_t& v) const {
+    float r_scale = mWhiteBalanceScale[0];
+    float b_scale = mWhiteBalanceScale[2];
+    int r = static_cast<float>(YUV2R(y, u, v)) / r_scale;
+    int g = YUV2G(y, u, v);
+    int b = static_cast<float>(YUV2B(y, u, v)) / b_scale;
+
+    y = RGB2Y(r, g, b);
+    u = RGB2U(r, g, b);
+    v = RGB2V(r, g, b);
 }
 
 status_t EmulatedCameraDevice::getCurrentPreviewFrame(void* buffer)
 {
     if (!isStarted()) {
-        LOGE("%s: Device is not started", __FUNCTION__);
+        ALOGE("%s: Device is not started", __FUNCTION__);
         return EINVAL;
     }
     if (mCurrentFrame == NULL || buffer == NULL) {
-        LOGE("%s: No framebuffer", __FUNCTION__);
+        ALOGE("%s: No framebuffer", __FUNCTION__);
         return EINVAL;
     }
 
@@ -141,7 +182,7 @@
             return NO_ERROR;
 
         default:
-            LOGE("%s: Unknown pixel format %.4s",
+            ALOGE("%s: Unknown pixel format %.4s",
                  __FUNCTION__, reinterpret_cast<const char*>(&mPixelFormat));
             return EINVAL;
     }
@@ -165,7 +206,7 @@
             break;
 
         default:
-            LOGE("%s: Unknown pixel format %.4s",
+            ALOGE("%s: Unknown pixel format %.4s",
                  __FUNCTION__, reinterpret_cast<const char*>(&pix_fmt));
             return EINVAL;
     }
@@ -179,10 +220,10 @@
     /* Allocate framebuffer. */
     mCurrentFrame = new uint8_t[mFrameBufferSize];
     if (mCurrentFrame == NULL) {
-        LOGE("%s: Unable to allocate framebuffer", __FUNCTION__);
+        ALOGE("%s: Unable to allocate framebuffer", __FUNCTION__);
         return ENOMEM;
     }
-    LOGV("%s: Allocated %p %d bytes for %d pixels in %.4s[%dx%d] frame",
+    ALOGV("%s: Allocated %p %d bytes for %d pixels in %.4s[%dx%d] frame",
          __FUNCTION__, mCurrentFrame, mFrameBufferSize, mTotalPixels,
          reinterpret_cast<const char*>(&mPixelFormat), mFrameWidth, mFrameHeight);
     return NO_ERROR;
@@ -205,29 +246,29 @@
 
 status_t EmulatedCameraDevice::startWorkerThread(bool one_burst)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     if (!isInitialized()) {
-        LOGE("%s: Emulated camera device is not initialized", __FUNCTION__);
+        ALOGE("%s: Emulated camera device is not initialized", __FUNCTION__);
         return EINVAL;
     }
 
     const status_t res = getWorkerThread()->startThread(one_burst);
-    LOGE_IF(res != NO_ERROR, "%s: Unable to start worker thread", __FUNCTION__);
+    ALOGE_IF(res != NO_ERROR, "%s: Unable to start worker thread", __FUNCTION__);
     return res;
 }
 
 status_t EmulatedCameraDevice::stopWorkerThread()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     if (!isInitialized()) {
-        LOGE("%s: Emulated camera device is not initialized", __FUNCTION__);
+        ALOGE("%s: Emulated camera device is not initialized", __FUNCTION__);
         return EINVAL;
     }
 
     const status_t res = getWorkerThread()->stopThread();
-    LOGE_IF(res != NO_ERROR, "%s: Unable to stop worker thread", __FUNCTION__);
+    ALOGE_IF(res != NO_ERROR, "%s: Unable to stop worker thread", __FUNCTION__);
     return res;
 }
 
@@ -244,19 +285,19 @@
 
 status_t EmulatedCameraDevice::WorkerThread::readyToRun()
 {
-    LOGV("Starting emulated camera device worker thread...");
+    ALOGV("Starting emulated camera device worker thread...");
 
-    LOGW_IF(mThreadControl >= 0 || mControlFD >= 0,
+    ALOGW_IF(mThreadControl >= 0 || mControlFD >= 0,
             "%s: Thread control FDs are opened", __FUNCTION__);
     /* Create a pair of FDs that would be used to control the thread. */
     int thread_fds[2];
     if (pipe(thread_fds) == 0) {
         mThreadControl = thread_fds[1];
         mControlFD = thread_fds[0];
-        LOGV("Emulated device's worker thread has been started.");
+        ALOGV("Emulated device's worker thread has been started.");
         return NO_ERROR;
     } else {
-        LOGE("%s: Unable to create thread control FDs: %d -> %s",
+        ALOGE("%s: Unable to create thread control FDs: %d -> %s",
              __FUNCTION__, errno, strerror(errno));
         return errno;
     }
@@ -264,7 +305,7 @@
 
 status_t EmulatedCameraDevice::WorkerThread::stopThread()
 {
-    LOGV("Stopping emulated camera device's worker thread...");
+    ALOGV("Stopping emulated camera device's worker thread...");
 
     status_t res = EINVAL;
     if (mThreadControl >= 0) {
@@ -285,18 +326,18 @@
                     close(mControlFD);
                     mControlFD = -1;
                 }
-                LOGV("Emulated camera device's worker thread has been stopped.");
+                ALOGV("Emulated camera device's worker thread has been stopped.");
             } else {
-                LOGE("%s: requestExitAndWait failed: %d -> %s",
+                ALOGE("%s: requestExitAndWait failed: %d -> %s",
                      __FUNCTION__, res, strerror(-res));
             }
         } else {
-            LOGE("%s: Unable to send THREAD_STOP message: %d -> %s",
+            ALOGE("%s: Unable to send THREAD_STOP message: %d -> %s",
                  __FUNCTION__, errno, strerror(errno));
             res = errno ? errno : EINVAL;
         }
     } else {
-        LOGE("%s: Thread control FDs are not opened", __FUNCTION__);
+        ALOGE("%s: Thread control FDs are not opened", __FUNCTION__);
     }
 
     return res;
@@ -322,7 +363,7 @@
     }
     int res = TEMP_FAILURE_RETRY(select(fd_num, fds, NULL, NULL, tvp));
     if (res < 0) {
-        LOGE("%s: select returned %d and failed: %d -> %s",
+        ALOGE("%s: select returned %d and failed: %d -> %s",
              __FUNCTION__, res, errno, strerror(errno));
         return ERROR;
     } else if (res == 0) {
@@ -333,21 +374,21 @@
         ControlMessage msg;
         res = TEMP_FAILURE_RETRY(read(mControlFD, &msg, sizeof(msg)));
         if (res != sizeof(msg)) {
-            LOGE("%s: Unexpected message size %d, or an error %d -> %s",
+            ALOGE("%s: Unexpected message size %d, or an error %d -> %s",
                  __FUNCTION__, res, errno, strerror(errno));
             return ERROR;
         }
         /* THREAD_STOP is the only message expected here. */
         if (msg == THREAD_STOP) {
-            LOGV("%s: THREAD_STOP message is received", __FUNCTION__);
+            ALOGV("%s: THREAD_STOP message is received", __FUNCTION__);
             return EXIT_THREAD;
         } else {
-            LOGE("Unknown worker thread message %d", msg);
+            ALOGE("Unknown worker thread message %d", msg);
             return ERROR;
         }
     } else {
         /* Must be an FD. */
-        LOGW_IF(fd < 0 || !FD_ISSET(fd, fds), "%s: Undefined 'select' result",
+        ALOGW_IF(fd < 0 || !FD_ISSET(fd, fds), "%s: Undefined 'select' result",
                 __FUNCTION__);
         return READY;
     }
diff --git a/tools/emulator/system/camera/EmulatedCameraDevice.h b/tools/emulator/system/camera/EmulatedCameraDevice.h
index 357c9e6..b7cdcb7 100755
--- a/tools/emulator/system/camera/EmulatedCameraDevice.h
+++ b/tools/emulator/system/camera/EmulatedCameraDevice.h
@@ -27,7 +27,10 @@
  */
 
 #include <utils/threads.h>
+#include <utils/KeyedVector.h>
+#include <utils/String8.h>
 #include "EmulatedCameraCommon.h"
+#include "Converters.h"
 
 namespace android {
 
@@ -116,6 +119,21 @@
      */
     virtual status_t Initialize();
 
+    /* Initializes the white balance modes parameters.
+     * The parameters are passed by each individual derived camera API to
+     * represent that different camera manufacturers may have different
+     * preferences on the white balance parameters. Green channel in the RGB
+     * color space is fixed to keep the luminance to be reasonably constant.
+     *
+     * Param:
+     * mode the text describing the current white balance mode
+     * r_scale the scale factor for the R channel in RGB space
+     * b_scale the scale factor for the B channel in RGB space.
+     */
+    void initializeWhiteBalanceModes(const char* mode,
+                                     const float r_scale,
+                                     const float b_scale);
+
     /* Starts delivering frames captured from the camera device.
      * This method will start the worker thread that would be pulling frames from
      * the camera device, and will deliver the pulled frames back to the emulated
@@ -145,7 +163,11 @@
 
     /* Sets the exposure compensation for the camera device.
      */
-    virtual void setExposureCompensation(const float ev);
+    void setExposureCompensation(const float ev);
+
+    /* Sets the white balance mode for the device.
+     */
+    void setWhiteBalanceMode(const char* mode);
 
     /* Gets current framebuffer, converted into preview frame format.
      * This method must be called on a connected instance of this class with a
@@ -170,7 +192,7 @@
      */
     inline int getFrameWidth() const
     {
-        LOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
+        ALOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
         return mFrameWidth;
     }
 
@@ -182,7 +204,7 @@
      */
     inline int getFrameHeight() const
     {
-        LOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
+        ALOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
         return mFrameHeight;
     }
 
@@ -193,7 +215,7 @@
      */
     inline size_t getFrameBufferSize() const
     {
-        LOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
+        ALOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
         return mFrameBufferSize;
     }
 
@@ -204,7 +226,7 @@
      */
     inline int getPixelNum() const
     {
-        LOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
+        ALOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
         return mTotalPixels;
     }
 
@@ -230,7 +252,7 @@
      */
     inline uint32_t getOriginalPixelFormat() const
     {
-        LOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
+        ALOGE_IF(!isStarted(), "%s: Device is not started", __FUNCTION__);
         return mPixelFormat;
     }
 
@@ -269,6 +291,24 @@
      */
     virtual void commonStopDevice();
 
+    /** Computes a luminance value after taking the exposure compensation.
+     * value into account.
+     *
+     * Param:
+     * inputY - The input luminance value.
+     * Return:
+     * The luminance value after adjusting the exposure compensation.
+     */
+    inline uint8_t changeExposure(const uint8_t& inputY) const {
+        return static_cast<uint8_t>(clamp(static_cast<float>(inputY) *
+                                    mExposureCompensation));
+    }
+
+    /** Computes the pixel value in YUV space after adjusting to the current
+     * white balance mode.
+     */
+    void changeWhiteBalance(uint8_t& y, uint8_t& u, uint8_t& v) const;
+
     /****************************************************************************
      * Worker thread management.
      * Typicaly when emulated camera device starts capturing frames from the
@@ -332,7 +372,7 @@
 
             inline ~WorkerThread()
             {
-                LOGW_IF(mThreadControl >= 0 || mControlFD >= 0,
+                ALOGW_IF(mThreadControl >= 0 || mControlFD >= 0,
                         "%s: Control FDs are opened in the destructor",
                         __FUNCTION__);
                 if (mThreadControl >= 0) {
@@ -478,6 +518,10 @@
     /* Exposure compensation value */
     float                       mExposureCompensation;
 
+    float*                      mWhiteBalanceScale;
+
+    DefaultKeyedVector<String8, float*>      mSupportedWhiteBalanceScale;
+
     /* Defines possible states of the emulated camera device object.
      */
     enum EmulatedCameraDeviceState {
diff --git a/tools/emulator/system/camera/EmulatedCameraFactory.cpp b/tools/emulator/system/camera/EmulatedCameraFactory.cpp
index 5c5c5de..a805418 100755
--- a/tools/emulator/system/camera/EmulatedCameraFactory.cpp
+++ b/tools/emulator/system/camera/EmulatedCameraFactory.cpp
@@ -61,7 +61,7 @@
         if (mEmulatedCameras == NULL) {
             mEmulatedCameras = new EmulatedCamera*[mEmulatedCameraNum];
             if (mEmulatedCameras == NULL) {
-                LOGE("%s: Unable to allocate emulated camera array for %d entries",
+                ALOGE("%s: Unable to allocate emulated camera array for %d entries",
                      __FUNCTION__, mEmulatedCameraNum);
                 return;
             }
@@ -80,13 +80,13 @@
         } else {
             mEmulatedCameras--;
             mFakeCameraID = -1;
-            LOGE("%s: Unable to instantiate fake camera class", __FUNCTION__);
+            ALOGE("%s: Unable to instantiate fake camera class", __FUNCTION__);
         }
     } else {
-        LOGD("Fake camera emulation is disabled.");
+        ALOGD("Fake camera emulation is disabled.");
     }
 
-    LOGV("%d cameras are being emulated. Fake camera ID is %d",
+    ALOGV("%d cameras are being emulated. Fake camera ID is %d",
          mEmulatedCameraNum, mFakeCameraID);
 
     mConstructedOK = true;
@@ -114,17 +114,17 @@
 
 int EmulatedCameraFactory::cameraDeviceOpen(int camera_id, hw_device_t** device)
 {
-    LOGV("%s: id = %d", __FUNCTION__, camera_id);
+    ALOGV("%s: id = %d", __FUNCTION__, camera_id);
 
     *device = NULL;
 
     if (!isConstructedOK()) {
-        LOGE("%s: EmulatedCameraFactory has failed to initialize", __FUNCTION__);
+        ALOGE("%s: EmulatedCameraFactory has failed to initialize", __FUNCTION__);
         return -EINVAL;
     }
 
     if (camera_id < 0 || camera_id >= getEmulatedCameraNum()) {
-        LOGE("%s: Camera id %d is out of bounds (%d)",
+        ALOGE("%s: Camera id %d is out of bounds (%d)",
              __FUNCTION__, camera_id, getEmulatedCameraNum());
         return -EINVAL;
     }
@@ -134,15 +134,15 @@
 
 int EmulatedCameraFactory::getCameraInfo(int camera_id, struct camera_info* info)
 {
-    LOGV("%s: id = %d", __FUNCTION__, camera_id);
+    ALOGV("%s: id = %d", __FUNCTION__, camera_id);
 
     if (!isConstructedOK()) {
-        LOGE("%s: EmulatedCameraFactory has failed to initialize", __FUNCTION__);
+        ALOGE("%s: EmulatedCameraFactory has failed to initialize", __FUNCTION__);
         return -EINVAL;
     }
 
     if (camera_id < 0 || camera_id >= getEmulatedCameraNum()) {
-        LOGE("%s: Camera id %d is out of bounds (%d)",
+        ALOGE("%s: Camera id %d is out of bounds (%d)",
              __FUNCTION__, camera_id, getEmulatedCameraNum());
         return -EINVAL;
     }
@@ -164,12 +164,12 @@
      */
 
     if (module != &HAL_MODULE_INFO_SYM.common) {
-        LOGE("%s: Invalid module %p expected %p",
+        ALOGE("%s: Invalid module %p expected %p",
              __FUNCTION__, module, &HAL_MODULE_INFO_SYM.common);
         return -EINVAL;
     }
     if (name == NULL) {
-        LOGE("%s: NULL name is not expected here", __FUNCTION__);
+        ALOGE("%s: NULL name is not expected here", __FUNCTION__);
         return -EINVAL;
     }
 
@@ -233,7 +233,7 @@
      * one more entry for the fake camera emulation. */
     mEmulatedCameras = new EmulatedCamera*[num + 1];
     if (mEmulatedCameras == NULL) {
-        LOGE("%s: Unable to allocate emulated camera array for %d entries",
+        ALOGE("%s: Unable to allocate emulated camera array for %d entries",
              __FUNCTION__, num + 1);
         free(camera_list);
         return;
@@ -292,11 +292,11 @@
                     delete qemu_cam;
                 }
             } else {
-                LOGE("%s: Unable to instantiate EmulatedQemuCamera",
+                ALOGE("%s: Unable to instantiate EmulatedQemuCamera",
                      __FUNCTION__);
             }
         } else {
-            LOGW("%s: Bad camera information: %s", __FUNCTION__, cur_entry);
+            ALOGW("%s: Bad camera information: %s", __FUNCTION__, cur_entry);
         }
 
         cur_entry = next_entry;
diff --git a/tools/emulator/system/camera/EmulatedFakeCamera.cpp b/tools/emulator/system/camera/EmulatedFakeCamera.cpp
index 86b9d08..461af28 100755
--- a/tools/emulator/system/camera/EmulatedFakeCamera.cpp
+++ b/tools/emulator/system/camera/EmulatedFakeCamera.cpp
@@ -55,7 +55,7 @@
     const char* facing = prop;
 
     mParameters.set(EmulatedCamera::FACING_KEY, facing);
-    LOGD("%s: Fake camera is facing %s", __FUNCTION__, facing);
+    ALOGD("%s: Fake camera is facing %s", __FUNCTION__, facing);
 
     mParameters.set(EmulatedCamera::ORIENTATION_KEY,
                     gEmulatedCameraFactory.getFakeCameraOrientation());
diff --git a/tools/emulator/system/camera/EmulatedFakeCameraDevice.cpp b/tools/emulator/system/camera/EmulatedFakeCameraDevice.cpp
index 3666827..0bc4c54 100755
--- a/tools/emulator/system/camera/EmulatedFakeCameraDevice.cpp
+++ b/tools/emulator/system/camera/EmulatedFakeCameraDevice.cpp
@@ -46,11 +46,11 @@
 {
     // Makes the image with the original exposure compensation darker.
     // So the effects of changing the exposure compensation can be seen.
-    mBlackYUV.Y = mBlackYUV.Y / 4;
-    mWhiteYUV.Y = mWhiteYUV.Y / 4;
-    mRedYUV.Y = mRedYUV.Y / 4;
-    mGreenYUV.Y = mGreenYUV.Y / 4;
-    mBlueYUV.Y = mBlueYUV.Y / 4;
+    mBlackYUV.Y = mBlackYUV.Y / 2;
+    mWhiteYUV.Y = mWhiteYUV.Y / 2;
+    mRedYUV.Y = mRedYUV.Y / 2;
+    mGreenYUV.Y = mGreenYUV.Y / 2;
+    mBlueYUV.Y = mBlueYUV.Y / 2;
 }
 
 EmulatedFakeCameraDevice::~EmulatedFakeCameraDevice()
@@ -63,15 +63,15 @@
 
 status_t EmulatedFakeCameraDevice::connectDevice()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isInitialized()) {
-        LOGE("%s: Fake camera device is not initialized.", __FUNCTION__);
+        ALOGE("%s: Fake camera device is not initialized.", __FUNCTION__);
         return EINVAL;
     }
     if (isConnected()) {
-        LOGW("%s: Fake camera device is already connected.", __FUNCTION__);
+        ALOGW("%s: Fake camera device is already connected.", __FUNCTION__);
         return NO_ERROR;
     }
 
@@ -83,15 +83,15 @@
 
 status_t EmulatedFakeCameraDevice::disconnectDevice()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isConnected()) {
-        LOGW("%s: Fake camera device is already disconnected.", __FUNCTION__);
+        ALOGW("%s: Fake camera device is already disconnected.", __FUNCTION__);
         return NO_ERROR;
     }
     if (isStarted()) {
-        LOGE("%s: Cannot disconnect from the started device.", __FUNCTION__);
+        ALOGE("%s: Cannot disconnect from the started device.", __FUNCTION__);
         return EINVAL;
     }
 
@@ -105,15 +105,15 @@
                                                int height,
                                                uint32_t pix_fmt)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isConnected()) {
-        LOGE("%s: Fake camera device is not connected.", __FUNCTION__);
+        ALOGE("%s: Fake camera device is not connected.", __FUNCTION__);
         return EINVAL;
     }
     if (isStarted()) {
-        LOGE("%s: Fake camera device is already started.", __FUNCTION__);
+        ALOGE("%s: Fake camera device is already started.", __FUNCTION__);
         return EINVAL;
     }
 
@@ -154,7 +154,7 @@
                 break;
 
             default:
-                LOGE("%s: Unknown pixel format %.4s", __FUNCTION__,
+                ALOGE("%s: Unknown pixel format %.4s", __FUNCTION__,
                      reinterpret_cast<const char*>(&mPixelFormat));
                 return EINVAL;
         }
@@ -162,7 +162,7 @@
         mUVInRow = (width / 2) * mUVStep;
         mState = ECDS_STARTED;
     } else {
-        LOGE("%s: commonStartDevice failed", __FUNCTION__);
+        ALOGE("%s: commonStartDevice failed", __FUNCTION__);
     }
 
     return res;
@@ -170,11 +170,11 @@
 
 status_t EmulatedFakeCameraDevice::stopDevice()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isStarted()) {
-        LOGW("%s: Fake camera device is not started.", __FUNCTION__);
+        ALOGW("%s: Fake camera device is not started.", __FUNCTION__);
         return NO_ERROR;
     }
 
@@ -195,7 +195,7 @@
     WorkerThread::SelectRes res =
         getWorkerThread()->Select(-1, 1000000 / mEmulatedFPS);
     if (res == WorkerThread::EXIT_THREAD) {
-        LOGV("%s: Worker thread has been terminated.", __FUNCTION__);
+        ALOGV("%s: Worker thread has been terminated.", __FUNCTION__);
         return false;
     }
 
@@ -256,6 +256,9 @@
     uint8_t* U = U_pos;
     uint8_t* V = V_pos;
 
+    YUVPixel adjustedWhite = YUVPixel(mWhiteYUV);
+    changeWhiteBalance(adjustedWhite.Y, adjustedWhite.U, adjustedWhite.V);
+
     for(int y = 0; y < mFrameHeight; y++) {
         int countx = checkxremainder;
         bool current = black;
@@ -263,7 +266,7 @@
             if (current) {
                 mBlackYUV.get(Y, U, V);
             } else {
-                mWhiteYUV.get(Y, U, V);
+                adjustedWhite.get(Y, U, V);
             }
             *Y = changeExposure(*Y);
             Y[1] = *Y;
@@ -309,6 +312,9 @@
     const int square_ystop = min(mFrameHeight, y + size);
     uint8_t* Y_pos = mCurrentFrame + y * mFrameWidth + x;
 
+    YUVPixel adjustedColor = *color;
+    changeWhiteBalance(adjustedColor.Y, adjustedColor.U, adjustedColor.V);
+
     // Draw the square.
     for (; y < square_ystop; y++) {
         const int iUV = (y / 2) * mUVInRow + (x / 2) * mUVStep;
@@ -316,7 +322,7 @@
         uint8_t* sqV = mFrameV + iUV;
         uint8_t* sqY = Y_pos;
         for (int i = x; i < square_xstop; i += 2) {
-            color->get(sqY, sqU, sqV);
+            adjustedColor.get(sqY, sqU, sqV);
             *sqY = changeExposure(*sqY);
             sqY[1] = *sqY;
             sqY += 2; sqU += mUVStep; sqV += mUVStep;
@@ -329,8 +335,11 @@
 
 void EmulatedFakeCameraDevice::drawSolid(YUVPixel* color)
 {
+    YUVPixel adjustedColor = *color;
+    changeWhiteBalance(adjustedColor.Y, adjustedColor.U, adjustedColor.V);
+
     /* All Ys are the same. */
-    memset(mCurrentFrame, changeExposure(color->Y), mTotalPixels);
+    memset(mCurrentFrame, changeExposure(adjustedColor.Y), mTotalPixels);
 
     /* Fill U, and V panes. */
     uint8_t* U = mFrameU;
@@ -364,6 +373,7 @@
             /* And the blue stripe at the bottom. */
             color = &mBlueYUV;
         }
+        changeWhiteBalance(color->Y, color->U, color->V);
 
         /* All Ys at the row are the same. */
         memset(pY, changeExposure(color->Y), mFrameWidth);
@@ -389,26 +399,26 @@
             mCurrentFrameType = 0;
         }
         if (mCurrentFrameType == 2) {
-            LOGD("********** Rotated to the SOLID COLOR frame **********");
+            ALOGD("********** Rotated to the SOLID COLOR frame **********");
             /* Solid color: lets rotate color too. */
             if (mCurrentColor == &mWhiteYUV) {
-                LOGD("----- Painting a solid RED frame -----");
+                ALOGD("----- Painting a solid RED frame -----");
                 mCurrentColor = &mRedYUV;
             } else if (mCurrentColor == &mRedYUV) {
-                LOGD("----- Painting a solid GREEN frame -----");
+                ALOGD("----- Painting a solid GREEN frame -----");
                 mCurrentColor = &mGreenYUV;
             } else if (mCurrentColor == &mGreenYUV) {
-                LOGD("----- Painting a solid BLUE frame -----");
+                ALOGD("----- Painting a solid BLUE frame -----");
                 mCurrentColor = &mBlueYUV;
             } else {
                 /* Back to white. */
-                LOGD("----- Painting a solid WHITE frame -----");
+                ALOGD("----- Painting a solid WHITE frame -----");
                 mCurrentColor = &mWhiteYUV;
             }
         } else if (mCurrentFrameType == 0) {
-            LOGD("********** Rotated to the CHECKERBOARD frame **********");
-        } else {
-            LOGD("********** Rotated to the STRIPED frame **********");
+            ALOGD("********** Rotated to the CHECKERBOARD frame **********");
+        } else if (mCurrentFrameType == 1) {
+            ALOGD("********** Rotated to the STRIPED frame **********");
         }
     }
 
diff --git a/tools/emulator/system/camera/EmulatedFakeCameraDevice.h b/tools/emulator/system/camera/EmulatedFakeCameraDevice.h
index 383118b..f66f076 100755
--- a/tools/emulator/system/camera/EmulatedFakeCameraDevice.h
+++ b/tools/emulator/system/camera/EmulatedFakeCameraDevice.h
@@ -99,6 +99,7 @@
      ***************************************************************************/
 
 private:
+
     /* Draws a black and white checker board in the current frame buffer. */
     void drawCheckerboard();
 
@@ -110,10 +111,6 @@
      */
     void drawSquare(int x, int y, int size, const YUVPixel* color);
 
-    inline uint8_t changeExposure(uint8_t inputY) {
-        return static_cast<uint8_t>(static_cast<float>(inputY) *
-                                    mExposureCompensation);
-    }
 #if EFCD_ROTATE_FRAME
     void drawSolid(YUVPixel* color);
     void drawStripes();
diff --git a/tools/emulator/system/camera/EmulatedQemuCamera.cpp b/tools/emulator/system/camera/EmulatedQemuCamera.cpp
index 611b6b5..af1e324 100755
--- a/tools/emulator/system/camera/EmulatedQemuCamera.cpp
+++ b/tools/emulator/system/camera/EmulatedQemuCamera.cpp
@@ -45,7 +45,7 @@
                                         const char* frame_dims,
                                         const char* facing_dir)
 {
-    LOGV("%s:\n   Name=%s\n   Facing '%s'\n   Dimensions=%s",
+    ALOGV("%s:\n   Name=%s\n   Facing '%s'\n   Dimensions=%s",
          __FUNCTION__, device_name, facing_dir, frame_dims);
     /* Save dimensions. */
     mFrameDims = frame_dims;
@@ -94,7 +94,7 @@
     /* Width and height are separated with 'x' */
     char* sep = strchr(first_dim, 'x');
     if (sep == NULL) {
-        LOGE("%s: Invalid first dimension format in %s",
+        ALOGE("%s: Invalid first dimension format in %s",
              __FUNCTION__, frame_dims);
         return EINVAL;
     }
@@ -105,7 +105,7 @@
     mParameters.setPreviewSize(x, y);
     mParameters.setPictureSize(x, y);
 
-    LOGV("%s: Qemu camera %s is initialized. Current frame is %dx%d",
+    ALOGV("%s: Qemu camera %s is initialized. Current frame is %dx%d",
          __FUNCTION__, device_name, x, y);
 
     return NO_ERROR;
diff --git a/tools/emulator/system/camera/EmulatedQemuCameraDevice.cpp b/tools/emulator/system/camera/EmulatedQemuCameraDevice.cpp
index 57dbc98..07837af 100755
--- a/tools/emulator/system/camera/EmulatedQemuCameraDevice.cpp
+++ b/tools/emulator/system/camera/EmulatedQemuCameraDevice.cpp
@@ -58,7 +58,7 @@
     /* Initialize base class. */
     res = EmulatedCameraDevice::Initialize();
     if (res == NO_ERROR) {
-        LOGV("%s: Connected to the emulated camera service '%s'",
+        ALOGV("%s: Connected to the emulated camera service '%s'",
              __FUNCTION__, device_name);
         mDeviceName = device_name;
     } else {
@@ -74,15 +74,15 @@
 
 status_t EmulatedQemuCameraDevice::connectDevice()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isInitialized()) {
-        LOGE("%s: Qemu camera device is not initialized.", __FUNCTION__);
+        ALOGE("%s: Qemu camera device is not initialized.", __FUNCTION__);
         return EINVAL;
     }
     if (isConnected()) {
-        LOGW("%s: Qemu camera device '%s' is already connected.",
+        ALOGW("%s: Qemu camera device '%s' is already connected.",
              __FUNCTION__, (const char*)mDeviceName);
         return NO_ERROR;
     }
@@ -90,11 +90,11 @@
     /* Connect to the camera device via emulator. */
     const status_t res = mQemuClient.queryConnect();
     if (res == NO_ERROR) {
-        LOGV("%s: Connected to device '%s'",
+        ALOGV("%s: Connected to device '%s'",
              __FUNCTION__, (const char*)mDeviceName);
         mState = ECDS_CONNECTED;
     } else {
-        LOGE("%s: Connection to device '%s' failed",
+        ALOGE("%s: Connection to device '%s' failed",
              __FUNCTION__, (const char*)mDeviceName);
     }
 
@@ -103,16 +103,16 @@
 
 status_t EmulatedQemuCameraDevice::disconnectDevice()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isConnected()) {
-        LOGW("%s: Qemu camera device '%s' is already disconnected.",
+        ALOGW("%s: Qemu camera device '%s' is already disconnected.",
              __FUNCTION__, (const char*)mDeviceName);
         return NO_ERROR;
     }
     if (isStarted()) {
-        LOGE("%s: Cannot disconnect from the started device '%s.",
+        ALOGE("%s: Cannot disconnect from the started device '%s.",
              __FUNCTION__, (const char*)mDeviceName);
         return EINVAL;
     }
@@ -120,11 +120,11 @@
     /* Disconnect from the camera device via emulator. */
     const status_t res = mQemuClient.queryDisconnect();
     if (res == NO_ERROR) {
-        LOGV("%s: Disonnected from device '%s'",
+        ALOGV("%s: Disonnected from device '%s'",
              __FUNCTION__, (const char*)mDeviceName);
         mState = ECDS_INITIALIZED;
     } else {
-        LOGE("%s: Disconnection from device '%s' failed",
+        ALOGE("%s: Disconnection from device '%s' failed",
              __FUNCTION__, (const char*)mDeviceName);
     }
 
@@ -135,23 +135,23 @@
                                                int height,
                                                uint32_t pix_fmt)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isConnected()) {
-        LOGE("%s: Qemu camera device '%s' is not connected.",
+        ALOGE("%s: Qemu camera device '%s' is not connected.",
              __FUNCTION__, (const char*)mDeviceName);
         return EINVAL;
     }
     if (isStarted()) {
-        LOGW("%s: Qemu camera device '%s' is already started.",
+        ALOGW("%s: Qemu camera device '%s' is already started.",
              __FUNCTION__, (const char*)mDeviceName);
         return NO_ERROR;
     }
 
     status_t res = EmulatedCameraDevice::commonStartDevice(width, height, pix_fmt);
     if (res != NO_ERROR) {
-        LOGE("%s: commonStartDevice failed", __FUNCTION__);
+        ALOGE("%s: commonStartDevice failed", __FUNCTION__);
         return res;
     }
 
@@ -160,7 +160,7 @@
      * RGB32 only.*/
     mPreviewFrame = new uint32_t[mTotalPixels];
     if (mPreviewFrame == NULL) {
-        LOGE("%s: Unable to allocate %d bytes for preview frame",
+        ALOGE("%s: Unable to allocate %d bytes for preview frame",
              __FUNCTION__, mTotalPixels);
         return ENOMEM;
     }
@@ -168,13 +168,13 @@
     /* Start the actual camera device. */
     res = mQemuClient.queryStart(mPixelFormat, mFrameWidth, mFrameHeight);
     if (res == NO_ERROR) {
-        LOGV("%s: Qemu camera device '%s' is started for %.4s[%dx%d] frames",
+        ALOGV("%s: Qemu camera device '%s' is started for %.4s[%dx%d] frames",
              __FUNCTION__, (const char*)mDeviceName,
              reinterpret_cast<const char*>(&mPixelFormat),
              mFrameWidth, mFrameHeight);
         mState = ECDS_STARTED;
     } else {
-        LOGE("%s: Unable to start device '%s' for %.4s[%dx%d] frames",
+        ALOGE("%s: Unable to start device '%s' for %.4s[%dx%d] frames",
              __FUNCTION__, (const char*)mDeviceName,
              reinterpret_cast<const char*>(&pix_fmt), width, height);
     }
@@ -184,11 +184,11 @@
 
 status_t EmulatedQemuCameraDevice::stopDevice()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     if (!isStarted()) {
-        LOGW("%s: Qemu camera device '%s' is not started.",
+        ALOGW("%s: Qemu camera device '%s' is not started.",
              __FUNCTION__, (const char*)mDeviceName);
         return NO_ERROR;
     }
@@ -202,10 +202,10 @@
         }
         EmulatedCameraDevice::commonStopDevice();
         mState = ECDS_CONNECTED;
-        LOGV("%s: Qemu camera device '%s' is stopped",
+        ALOGV("%s: Qemu camera device '%s' is stopped",
              __FUNCTION__, (const char*)mDeviceName);
     } else {
-        LOGE("%s: Unable to stop device '%s'",
+        ALOGE("%s: Unable to stop device '%s'",
              __FUNCTION__, (const char*)mDeviceName);
     }
 
@@ -218,7 +218,7 @@
 
 status_t EmulatedQemuCameraDevice::getCurrentPreviewFrame(void* buffer)
 {
-    LOGW_IF(mPreviewFrame == NULL, "%s: No preview frame", __FUNCTION__);
+    ALOGW_IF(mPreviewFrame == NULL, "%s: No preview frame", __FUNCTION__);
     if (mPreviewFrame != NULL) {
         memcpy(buffer, mPreviewFrame, mTotalPixels * 4);
         return 0;
@@ -237,21 +237,25 @@
     WorkerThread::SelectRes res =
         getWorkerThread()->Select(-1, 1000000 / mEmulatedFPS);
     if (res == WorkerThread::EXIT_THREAD) {
-        LOGV("%s: Worker thread has been terminated.", __FUNCTION__);
+        ALOGV("%s: Worker thread has been terminated.", __FUNCTION__);
         return false;
     }
 
     /* Query frames from the service. */
     status_t query_res = mQemuClient.queryFrame(mCurrentFrame, mPreviewFrame,
                                                  mFrameBufferSize,
-                                                 mTotalPixels * 4);
+                                                 mTotalPixels * 4,
+                                                 mWhiteBalanceScale[0],
+                                                 mWhiteBalanceScale[1],
+                                                 mWhiteBalanceScale[2],
+                                                 mExposureCompensation);
     if (query_res == NO_ERROR) {
         /* Timestamp the current frame, and notify the camera HAL. */
         mCurFrameTimestamp = systemTime(SYSTEM_TIME_MONOTONIC);
         mCameraHAL->onNextFrameAvailable(mCurrentFrame, mCurFrameTimestamp, this);
         return true;
     } else {
-        LOGE("%s: Unable to get current video frame: %s",
+        ALOGE("%s: Unable to get current video frame: %s",
              __FUNCTION__, strerror(query_res));
         mCameraHAL->onCameraDeviceError(CAMERA_ERROR_SERVER_DIED);
         return false;
diff --git a/tools/emulator/system/camera/JpegCompressor.cpp b/tools/emulator/system/camera/JpegCompressor.cpp
index 0e538a1..8eec52d 100644
--- a/tools/emulator/system/camera/JpegCompressor.cpp
+++ b/tools/emulator/system/camera/JpegCompressor.cpp
@@ -44,7 +44,7 @@
                                               int height,
                                               int quality)
 {
-    LOGV("%s: %p[%dx%d]", __FUNCTION__, image, width, height);
+    ALOGV("%s: %p[%dx%d]", __FUNCTION__, image, width, height);
     void* pY = const_cast<void*>(image);
     int offsets[2];
     offsets[0] = 0;
@@ -52,11 +52,11 @@
     mStrides[0] = width;
     mStrides[1] = width;
     if (encode(&mStream, pY, width, height, offsets, quality)) {
-        LOGV("%s: Compressed JPEG: %d[%dx%d] -> %d bytes",
+        ALOGV("%s: Compressed JPEG: %d[%dx%d] -> %d bytes",
              __FUNCTION__, (width * height * 12) / 8, width, height, mStream.getOffset());
         return NO_ERROR;
     } else {
-        LOGE("%s: JPEG compression failed", __FUNCTION__);
+        ALOGE("%s: JPEG compression failed", __FUNCTION__);
         return errno ? errno : EINVAL;
     }
 }
diff --git a/tools/emulator/system/camera/PreviewWindow.cpp b/tools/emulator/system/camera/PreviewWindow.cpp
index fb708d5..eac3586 100755
--- a/tools/emulator/system/camera/PreviewWindow.cpp
+++ b/tools/emulator/system/camera/PreviewWindow.cpp
@@ -49,7 +49,7 @@
 status_t PreviewWindow::setPreviewWindow(struct preview_stream_ops* window,
                                          int preview_fps)
 {
-    LOGV("%s: current: %p -> new: %p", __FUNCTION__, mPreviewWindow, window);
+    ALOGV("%s: current: %p -> new: %p", __FUNCTION__, mPreviewWindow, window);
 
     status_t res = NO_ERROR;
     Mutex::Autolock locker(&mObjectLock);
@@ -70,7 +70,7 @@
         } else {
             window = NULL;
             res = -res; // set_usage returns a negative errno.
-            LOGE("%s: Error setting preview window usage %d -> %s",
+            ALOGE("%s: Error setting preview window usage %d -> %s",
                  __FUNCTION__, res, strerror(res));
         }
     }
@@ -81,7 +81,7 @@
 
 status_t PreviewWindow::startPreview()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     mPreviewEnabled = true;
@@ -91,7 +91,7 @@
 
 void PreviewWindow::stopPreview()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     Mutex::Autolock locker(&mObjectLock);
     mPreviewEnabled = false;
@@ -117,7 +117,7 @@
         /* Need to set / adjust buffer geometry for the preview window.
          * Note that in the emulator preview window uses only RGB for pixel
          * formats. */
-        LOGV("%s: Adjusting preview windows %p geometry to %dx%d",
+        ALOGV("%s: Adjusting preview windows %p geometry to %dx%d",
              __FUNCTION__, mPreviewWindow, mPreviewFrameWidth,
              mPreviewFrameHeight);
         res = mPreviewWindow->set_buffers_geometry(mPreviewWindow,
@@ -125,7 +125,7 @@
                                                    mPreviewFrameHeight,
                                                    HAL_PIXEL_FORMAT_RGBA_8888);
         if (res != NO_ERROR) {
-            LOGE("%s: Error in set_buffers_geometry %d -> %s",
+            ALOGE("%s: Error in set_buffers_geometry %d -> %s",
                  __FUNCTION__, -res, strerror(-res));
             return;
         }
@@ -140,7 +140,7 @@
     int stride = 0;
     res = mPreviewWindow->dequeue_buffer(mPreviewWindow, &buffer, &stride);
     if (res != NO_ERROR || buffer == NULL) {
-        LOGE("%s: Unable to dequeue preview window buffer: %d -> %s",
+        ALOGE("%s: Unable to dequeue preview window buffer: %d -> %s",
             __FUNCTION__, -res, strerror(-res));
         return;
     }
@@ -148,7 +148,7 @@
     /* Let the preview window to lock the buffer. */
     res = mPreviewWindow->lock_buffer(mPreviewWindow, buffer);
     if (res != NO_ERROR) {
-        LOGE("%s: Unable to lock preview window buffer: %d -> %s",
+        ALOGE("%s: Unable to lock preview window buffer: %d -> %s",
              __FUNCTION__, -res, strerror(-res));
         mPreviewWindow->cancel_buffer(mPreviewWindow, buffer);
         return;
@@ -161,7 +161,7 @@
     GraphicBufferMapper& grbuffer_mapper(GraphicBufferMapper::get());
     res = grbuffer_mapper.lock(*buffer, GRALLOC_USAGE_SW_WRITE_OFTEN, rect, &img);
     if (res != NO_ERROR) {
-        LOGE("%s: grbuffer_mapper.lock failure: %d -> %s",
+        ALOGE("%s: grbuffer_mapper.lock failure: %d -> %s",
              __FUNCTION__, res, strerror(res));
         mPreviewWindow->cancel_buffer(mPreviewWindow, buffer);
         return;
@@ -174,7 +174,7 @@
         /* Show it. */
         mPreviewWindow->enqueue_buffer(mPreviewWindow, buffer);
     } else {
-        LOGE("%s: Unable to obtain preview frame: %d", __FUNCTION__, res);
+        ALOGE("%s: Unable to obtain preview frame: %d", __FUNCTION__, res);
         mPreviewWindow->cancel_buffer(mPreviewWindow, buffer);
     }
     grbuffer_mapper.unlock(*buffer);
diff --git a/tools/emulator/system/camera/QemuClient.cpp b/tools/emulator/system/camera/QemuClient.cpp
index fd49585..17e6f98 100755
--- a/tools/emulator/system/camera/QemuClient.cpp
+++ b/tools/emulator/system/camera/QemuClient.cpp
@@ -27,7 +27,7 @@
 
 #define LOG_QUERIES 0
 #if LOG_QUERIES
-#define LOGQ(...)   LOGD(__VA_ARGS__)
+#define LOGQ(...)   ALOGD(__VA_ARGS__)
 #else
 #define LOGQ(...)   (void(0))
 
@@ -86,7 +86,7 @@
 
     /* Query name cannot be NULL or an empty string. */
     if (name == NULL || *name == '\0') {
-        LOGE("%s: NULL or an empty string is passed as query name.",
+        ALOGE("%s: NULL or an empty string is passed as query name.",
              __FUNCTION__);
         mQueryDeliveryStatus = EINVAL;
         return EINVAL;
@@ -100,7 +100,7 @@
         /* Preallocated buffer was too small. Allocate a bigger query buffer. */
         mQuery = new char[required];
         if (mQuery == NULL) {
-            LOGE("%s: Unable to allocate %d bytes for query buffer",
+            ALOGE("%s: Unable to allocate %d bytes for query buffer",
                  __FUNCTION__, required);
             mQueryDeliveryStatus = ENOMEM;
             return ENOMEM;
@@ -131,7 +131,7 @@
      * with a ':'. If there is no more data in the reply, the prefix will be
      * zero-terminated, and the terminator will be inculded in the reply. */
     if (mReplyBuffer == NULL || mReplySize < 3) {
-        LOGE("%s: Invalid reply to the query", __FUNCTION__);
+        ALOGE("%s: Invalid reply to the query", __FUNCTION__);
         mQueryDeliveryStatus = EINVAL;
         return EINVAL;
     }
@@ -142,7 +142,7 @@
     } else if (!memcmp(mReplyBuffer, "ko", 2)) {
         mReplyStatus = 0;
     } else {
-        LOGE("%s: Invalid query reply: '%s'", __FUNCTION__, mReplyBuffer);
+        ALOGE("%s: Invalid query reply: '%s'", __FUNCTION__, mReplyBuffer);
         mQueryDeliveryStatus = EINVAL;
         return EINVAL;
     }
@@ -152,7 +152,7 @@
         /* There are extra data. Make sure they are separated from the status
          * with a ':' */
         if (mReplyBuffer[2] != ':') {
-            LOGE("%s: Invalid query reply: '%s'", __FUNCTION__, mReplyBuffer);
+            ALOGE("%s: Invalid query reply: '%s'", __FUNCTION__, mReplyBuffer);
             mQueryDeliveryStatus = EINVAL;
             return EINVAL;
         }
@@ -162,7 +162,7 @@
         /* Make sure reply buffer containing just 'ok'/'ko' ends with
          * zero-terminator. */
         if (mReplyBuffer[2] != '\0') {
-            LOGE("%s: Invalid query reply: '%s'", __FUNCTION__, mReplyBuffer);
+            ALOGE("%s: Invalid query reply: '%s'", __FUNCTION__, mReplyBuffer);
             mQueryDeliveryStatus = EINVAL;
             return EINVAL;
         }
@@ -212,11 +212,11 @@
 
 status_t QemuClient::connectClient(const char* param)
 {
-    LOGV("%s: '%s'", __FUNCTION__, param ? param : "");
+    ALOGV("%s: '%s'", __FUNCTION__, param ? param : "");
 
     /* Make sure that client is not connected already. */
     if (mPipeFD >= 0) {
-        LOGE("%s: Qemu client is already connected", __FUNCTION__);
+        ALOGE("%s: Qemu client is already connected", __FUNCTION__);
         return EINVAL;
     }
 
@@ -237,7 +237,7 @@
         delete[] connection_str;
     }
     if (mPipeFD < 0) {
-        LOGE("%s: Unable to connect to the camera service '%s': %s",
+        ALOGE("%s: Unable to connect to the camera service '%s': %s",
              __FUNCTION__, param ? param : "Factory", strerror(errno));
         return errno ? errno : EINVAL;
     }
@@ -247,7 +247,7 @@
 
 void QemuClient::disconnectClient()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     if (mPipeFD >= 0) {
         close(mPipeFD);
@@ -258,7 +258,7 @@
 status_t QemuClient::sendMessage(const void* data, size_t data_size)
 {
     if (mPipeFD < 0) {
-        LOGE("%s: Qemu client is not connected", __FUNCTION__);
+        ALOGE("%s: Qemu client is not connected", __FUNCTION__);
         return EINVAL;
     }
 
@@ -270,7 +270,7 @@
     if (written == data_size) {
         return NO_ERROR;
     } else {
-        LOGE("%s: Error sending data via qemu pipe: '%s'",
+        ALOGE("%s: Error sending data via qemu pipe: '%s'",
              __FUNCTION__, strerror(errno));
         return errno ? errno : EIO;
     }
@@ -282,7 +282,7 @@
     *data_size = 0;
 
     if (mPipeFD < 0) {
-        LOGE("%s: Qemu client is not connected", __FUNCTION__);
+        ALOGE("%s: Qemu client is not connected", __FUNCTION__);
         return EINVAL;
     }
 
@@ -294,7 +294,7 @@
     char payload_size_str[9];
     int rd_res = qemud_fd_read(mPipeFD, payload_size_str, 8);
     if (rd_res != 8) {
-        LOGE("%s: Unable to obtain payload size: %s",
+        ALOGE("%s: Unable to obtain payload size: %s",
              __FUNCTION__, strerror(errno));
         return errno ? errno : EIO;
     }
@@ -304,14 +304,14 @@
     payload_size_str[8] = '\0';
     payload_size = strtol(payload_size_str, NULL, 16);
     if (errno) {
-        LOGE("%s: Invalid payload size '%s'", __FUNCTION__, payload_size_str);
+        ALOGE("%s: Invalid payload size '%s'", __FUNCTION__, payload_size_str);
         return EIO;
     }
 
     /* Allocate payload data buffer, and read the payload there. */
     *data = malloc(payload_size);
     if (*data == NULL) {
-        LOGE("%s: Unable to allocate %d bytes payload buffer",
+        ALOGE("%s: Unable to allocate %d bytes payload buffer",
              __FUNCTION__, payload_size);
         return ENOMEM;
     }
@@ -320,7 +320,7 @@
         *data_size = payload_size;
         return NO_ERROR;
     } else {
-        LOGE("%s: Read size %d doesnt match expected payload size %d: %s",
+        ALOGE("%s: Read size %d doesnt match expected payload size %d: %s",
              __FUNCTION__, rd_res, payload_size, strerror(errno));
         free(*data);
         *data = NULL;
@@ -332,7 +332,7 @@
 {
     /* Make sure that query has been successfuly constructed. */
     if (query->mQueryDeliveryStatus != NO_ERROR) {
-        LOGE("%s: Query is invalid", __FUNCTION__);
+        ALOGE("%s: Query is invalid", __FUNCTION__);
         return query->mQueryDeliveryStatus;
     }
 
@@ -348,17 +348,17 @@
             LOGQ("Response to query '%s': Status = '%.2s', %d bytes in response",
                  query->mQuery, query->mReplyBuffer, query->mReplySize);
         } else {
-            LOGE("%s Response to query '%s' has failed: %s",
+            ALOGE("%s Response to query '%s' has failed: %s",
                  __FUNCTION__, query->mQuery, strerror(res));
         }
     } else {
-        LOGE("%s: Send query '%s' failed: %s",
+        ALOGE("%s: Send query '%s' failed: %s",
              __FUNCTION__, query->mQuery, strerror(res));
     }
 
     /* Complete the query, and return its completion handling status. */
     const status_t res1 = query->completeQuery(res);
-    LOGE_IF(res1 != NO_ERROR && res1 != res,
+    ALOGE_IF(res1 != NO_ERROR && res1 != res,
             "%s: Error %d in query '%s' completion",
             __FUNCTION__, res1, query->mQuery);
     return res1;
@@ -386,18 +386,18 @@
 
 status_t FactoryQemuClient::listCameras(char** list)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     QemuQuery query(mQueryList);
     if (doQuery(&query) || !query.isQuerySucceeded()) {
-        LOGE("%s: List cameras query failed: %s", __FUNCTION__,
+        ALOGE("%s: List cameras query failed: %s", __FUNCTION__,
              query.mReplyData ? query.mReplyData : "No error message");
         return query.getCompletionStatus();
     }
 
     /* Make sure there is a list returned. */
     if (query.mReplyDataSize == 0) {
-        LOGE("%s: No camera list is returned.", __FUNCTION__);
+        ALOGE("%s: No camera list is returned.", __FUNCTION__);
         return EINVAL;
     }
 
@@ -405,10 +405,10 @@
     *list = (char*)malloc(query.mReplyDataSize);
     if (*list != NULL) {
         memcpy(*list, query.mReplyData, query.mReplyDataSize);
-        LOGD("Emulated camera list: %s", *list);
+        ALOGD("Emulated camera list: %s", *list);
         return NO_ERROR;
     } else {
-        LOGE("%s: Unable to allocate %d bytes",
+        ALOGE("%s: Unable to allocate %d bytes",
              __FUNCTION__, query.mReplyDataSize);
         return ENOMEM;
     }
@@ -445,12 +445,12 @@
 
 status_t CameraQemuClient::queryConnect()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     QemuQuery query(mQueryConnect);
     doQuery(&query);
     const status_t res = query.getCompletionStatus();
-    LOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
+    ALOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
             __FUNCTION__, query.mReplyData ? query.mReplyData :
                                              "No error message");
     return res;
@@ -458,12 +458,12 @@
 
 status_t CameraQemuClient::queryDisconnect()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     QemuQuery query(mQueryDisconnect);
     doQuery(&query);
     const status_t res = query.getCompletionStatus();
-    LOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
+    ALOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
             __FUNCTION__, query.mReplyData ? query.mReplyData :
                                              "No error message");
     return res;
@@ -473,7 +473,7 @@
                                       int width,
                                       int height)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     char query_str[256];
     snprintf(query_str, sizeof(query_str), "%s dim=%dx%d pix=%d",
@@ -481,7 +481,7 @@
     QemuQuery query(query_str);
     doQuery(&query);
     const status_t res = query.getCompletionStatus();
-    LOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
+    ALOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
             __FUNCTION__, query.mReplyData ? query.mReplyData :
                                              "No error message");
     return res;
@@ -489,12 +489,12 @@
 
 status_t CameraQemuClient::queryStop()
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     QemuQuery query(mQueryStop);
     doQuery(&query);
     const status_t res = query.getCompletionStatus();
-    LOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
+    ALOGE_IF(res != NO_ERROR, "%s: Query failed: %s",
             __FUNCTION__, query.mReplyData ? query.mReplyData :
                                              "No error message");
     return res;
@@ -503,19 +503,24 @@
 status_t CameraQemuClient::queryFrame(void* vframe,
                                       void* pframe,
                                       size_t vframe_size,
-                                      size_t pframe_size)
+                                      size_t pframe_size,
+                                      float r_scale,
+                                      float g_scale,
+                                      float b_scale,
+                                      float exposure_comp)
 {
-    LOGV("%s", __FUNCTION__);
+    ALOGV("%s", __FUNCTION__);
 
     char query_str[256];
-    snprintf(query_str, sizeof(query_str), "%s video=%d preview=%d",
+    snprintf(query_str, sizeof(query_str), "%s video=%d preview=%d whiteb=%g,%g,%g expcomp=%g",
              mQueryFrame, (vframe && vframe_size) ? vframe_size : 0,
-                           (pframe && pframe_size) ? pframe_size : 0);
+             (pframe && pframe_size) ? pframe_size : 0, r_scale, g_scale, b_scale,
+             exposure_comp);
     QemuQuery query(query_str);
     doQuery(&query);
     const status_t res = query.getCompletionStatus();
     if( res != NO_ERROR) {
-        LOGE("%s: Query failed: %s",
+        ALOGE("%s: Query failed: %s",
              __FUNCTION__, query.mReplyData ? query.mReplyData :
                                               "No error message");
         return res;
@@ -531,7 +536,7 @@
             memcpy(vframe, frame, vframe_size);
             cur_offset += vframe_size;
         } else {
-            LOGE("%s: Reply %d bytes is to small to contain %d bytes video frame",
+            ALOGE("%s: Reply %d bytes is to small to contain %d bytes video frame",
                  __FUNCTION__, query.mReplyDataSize - cur_offset, vframe_size);
             return EINVAL;
         }
@@ -542,7 +547,7 @@
             memcpy(pframe, frame + cur_offset, pframe_size);
             cur_offset += pframe_size;
         } else {
-            LOGE("%s: Reply %d bytes is to small to contain %d bytes preview frame",
+            ALOGE("%s: Reply %d bytes is to small to contain %d bytes preview frame",
                  __FUNCTION__, query.mReplyDataSize - cur_offset, pframe_size);
             return EINVAL;
         }
diff --git a/tools/emulator/system/camera/QemuClient.h b/tools/emulator/system/camera/QemuClient.h
index c0b8e61..1644321 100755
--- a/tools/emulator/system/camera/QemuClient.h
+++ b/tools/emulator/system/camera/QemuClient.h
@@ -401,13 +401,19 @@
      *  pframe, pframe_size - Define buffer, allocated to receive a preview frame.
      *      Any of these parameters can be 0, indicating that the caller is
      *      interested only in video frame.
+     *  r_scale, g_scale, b_scale - White balance scale.
+     *  exposure_comp - Expsoure compensation.
      * Return:
      *  NO_ERROR on success, or an appropriate error status on failure.
      */
     status_t queryFrame(void* vframe,
                         void* pframe,
                         size_t vframe_size,
-                        size_t pframe_size);
+                        size_t pframe_size,
+                        float r_scale,
+                        float g_scale,
+                        float b_scale,
+                        float exposure_comp);
 
     /****************************************************************************
      * Names of the queries available for the emulated camera.
diff --git a/tools/emulator/system/gps/gps_qemu.c b/tools/emulator/system/gps/gps_qemu.c
index a4699d3..78e0bf2 100644
--- a/tools/emulator/system/gps/gps_qemu.c
+++ b/tools/emulator/system/gps/gps_qemu.c
@@ -42,7 +42,7 @@
 #define  GPS_DEBUG  0
 
 #if GPS_DEBUG
-#  define  D(...)   LOGD(__VA_ARGS__)
+#  define  D(...)   ALOGD(__VA_ARGS__)
 #else
 #  define  D(...)   ((void)0)
 #endif
@@ -686,13 +686,13 @@
         nevents = epoll_wait( epoll_fd, events, 2, -1 );
         if (nevents < 0) {
             if (errno != EINTR)
-                LOGE("epoll_wait() unexpected error: %s", strerror(errno));
+                ALOGE("epoll_wait() unexpected error: %s", strerror(errno));
             continue;
         }
         D("gps thread received %d events", nevents);
         for (ne = 0; ne < nevents; ne++) {
             if ((events[ne].events & (EPOLLERR|EPOLLHUP)) != 0) {
-                LOGE("EPOLLERR or EPOLLHUP after epoll_wait() !?");
+                ALOGE("EPOLLERR or EPOLLHUP after epoll_wait() !?");
                 return;
             }
             if ((events[ne].events & EPOLLIN) != 0) {
@@ -738,7 +738,7 @@
                             if (errno == EINTR)
                                 continue;
                             if (errno != EWOULDBLOCK)
-                                LOGE("error while reading from gps daemon socket: %s:", strerror(errno));
+                                ALOGE("error while reading from gps daemon socket: %s:", strerror(errno));
                             break;
                         }
                         D("received %d bytes: %.*s", ret, ret, buff);
@@ -749,7 +749,7 @@
                 }
                 else
                 {
-                    LOGE("epoll_wait() returned unkown fd %d ?", fd);
+                    ALOGE("epoll_wait() returned unkown fd %d ?", fd);
                 }
             }
         }
@@ -775,14 +775,14 @@
     D("gps emulation will read from '%s' qemud channel", QEMU_CHANNEL_NAME );
 
     if ( socketpair( AF_LOCAL, SOCK_STREAM, 0, state->control ) < 0 ) {
-        LOGE("could not create thread control socket pair: %s", strerror(errno));
+        ALOGE("could not create thread control socket pair: %s", strerror(errno));
         goto Fail;
     }
 
     state->thread = callbacks->create_thread_cb( "gps_state_thread", gps_state_thread, state );
 
     if ( !state->thread ) {
-        LOGE("could not create gps thread: %s", strerror(errno));
+        ALOGE("could not create gps thread: %s", strerror(errno));
         goto Fail;
     }
 
diff --git a/tools/emulator/system/lights/lights_qemu.c b/tools/emulator/system/lights/lights_qemu.c
index d6576a0..839154a 100644
--- a/tools/emulator/system/lights/lights_qemu.c
+++ b/tools/emulator/system/lights/lights_qemu.c
@@ -44,12 +44,12 @@
 /* Set to 1 to enable debug messages to the log */
 #define DEBUG 0
 #if DEBUG
-# define D(...) LOGD(__VA_ARGS__)
+# define D(...) ALOGD(__VA_ARGS__)
 #else
 # define D(...) do{}while(0)
 #endif
 
-#define  E(...)  LOGE(__VA_ARGS__)
+#define  E(...)  ALOGE(__VA_ARGS__)
 
 /* Get brightness(0~255) from state. */
 static int
diff --git a/tools/emulator/system/qemu-props/qemu-props.c b/tools/emulator/system/qemu-props/qemu-props.c
index 3f086a1..56d510f 100644
--- a/tools/emulator/system/qemu-props/qemu-props.c
+++ b/tools/emulator/system/qemu-props/qemu-props.c
@@ -28,7 +28,7 @@
 
 #if DEBUG
 #  include <cutils/log.h>
-#  define  DD(...)    LOGI(__VA_ARGS__)
+#  define  DD(...)    ALOGI(__VA_ARGS__)
 #else
 #  define  DD(...)    ((void)0)
 #endif
diff --git a/tools/emulator/system/qemud/qemud.c b/tools/emulator/system/qemud/qemud.c
index dc04de8..e836376 100644
--- a/tools/emulator/system/qemud/qemud.c
+++ b/tools/emulator/system/qemud/qemud.c
@@ -87,7 +87,7 @@
 #if DEBUG
 #  define LOG_TAG  "qemud"
 #  include <cutils/log.h>
-#  define  D(...)   LOGD(__VA_ARGS__)
+#  define  D(...)   ALOGD(__VA_ARGS__)
 #else
 #  define  D(...)  ((void)0)
 #  define  T(...)  ((void)0)
diff --git a/tools/emulator/system/sensors/sensors_qemu.c b/tools/emulator/system/sensors/sensors_qemu.c
index 9a776c7..33fa516 100644
--- a/tools/emulator/system/sensors/sensors_qemu.c
+++ b/tools/emulator/system/sensors/sensors_qemu.c
@@ -39,12 +39,12 @@
 #include <hardware/sensors.h>
 
 #if 0
-#define  D(...)  LOGD(__VA_ARGS__)
+#define  D(...)  ALOGD(__VA_ARGS__)
 #else
 #define  D(...)  ((void)0)
 #endif
 
-#define  E(...)  LOGE(__VA_ARGS__)
+#define  E(...)  ALOGE(__VA_ARGS__)
 
 #include <hardware/qemud.h>
 
@@ -206,7 +206,7 @@
 }
 
 static int
-control__close(struct hw_device_t *dev) 
+control__close(struct hw_device_t *dev)
 {
     SensorPoll*  ctl = (void*)dev;
     close(ctl->fd);
@@ -281,7 +281,7 @@
             return i;
         }
     }
-    LOGE("No sensor to return!!! pendingSensors=%08x", data->pendingSensors);
+    ALOGE("No sensor to return!!! pendingSensors=%08x", data->pendingSensors);
     // we may end-up in a busy loop, slow things down, just in case.
     usleep(100000);
     return -EINVAL;
@@ -350,7 +350,7 @@
         }
 
         /* "temperature:<celsius>" */
-        if (sscanf(buff, "temperature:%g", params+0) == 2) {
+        if (sscanf(buff, "temperature:%g", params+0) == 1) {
             new_sensors |= SENSORS_TEMPERATURE;
             data->sensors[ID_TEMPERATURE].temperature = params[0];
             continue;
@@ -397,12 +397,12 @@
 }
 
 static int
-data__close(struct hw_device_t *dev) 
+data__close(struct hw_device_t *dev)
 {
     SensorPoll* data = (SensorPoll*)dev;
     if (data) {
         if (data->events_fd >= 0) {
-            //LOGD("(device close) about to close fd=%d", data->events_fd);
+            //ALOGD("(device close) about to close fd=%d", data->events_fd);
             close(data->events_fd);
         }
         free(data);
@@ -545,7 +545,7 @@
 static struct sensor_t  sSensorList[MAX_NUM_SENSORS];
 
 static int sensors__get_sensors_list(struct sensors_module_t* module,
-        struct sensor_t const** list) 
+        struct sensor_t const** list)
 {
     int  fd = qemud_channel_open(SENSORS_SERVICE_NAME);
     char buffer[12];
diff --git a/tools/mkstubs/.classpath b/tools/mkstubs/.classpath
index 49a6d6c..1b7d34b 100644
--- a/tools/mkstubs/.classpath
+++ b/tools/mkstubs/.classpath
@@ -1,9 +1,9 @@
-<?xml version="1.0" encoding="UTF-8"?>

-<classpath>

-	<classpathentry kind="src" path="src"/>

-	<classpathentry kind="src" path="tests"/>

-	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.5"/>

-	<classpathentry kind="con" path="org.eclipse.jdt.junit.JUNIT_CONTAINER/4"/>

-	<classpathentry kind="var" path="ANDROID_SRC/prebuilt/common/asm/asm-3.1.jar"/>

-	<classpathentry kind="output" path="bin"/>

-</classpath>

+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+	<classpathentry kind="src" path="src"/>
+	<classpathentry kind="src" path="tests"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J2SE-1.5"/>
+	<classpathentry kind="con" path="org.eclipse.jdt.junit.JUNIT_CONTAINER/4"/>
+	<classpathentry kind="var" path="ANDROID_SRC/prebuilt/common/asm/asm-4.0.jar"/>
+	<classpathentry kind="output" path="bin"/>
+</classpath>
diff --git a/tools/mkstubs/Android.mk b/tools/mkstubs/Android.mk
index a12bf18..3e46a1d 100644
--- a/tools/mkstubs/Android.mk
+++ b/tools/mkstubs/Android.mk
@@ -20,7 +20,7 @@
 
 LOCAL_JAR_MANIFEST := manifest.txt
 LOCAL_STATIC_JAVA_LIBRARIES := \
-	asm-3.1
+	asm-4.0
 
 LOCAL_MODULE := mkstubs
 
diff --git a/tools/mkstubs/src/com/android/mkstubs/FilterClassAdapter.java b/tools/mkstubs/src/com/android/mkstubs/FilterClassAdapter.java
index 6f570c7..e875f10 100644
--- a/tools/mkstubs/src/com/android/mkstubs/FilterClassAdapter.java
+++ b/tools/mkstubs/src/com/android/mkstubs/FilterClassAdapter.java
@@ -20,7 +20,6 @@
 
 import org.objectweb.asm.AnnotationVisitor;
 import org.objectweb.asm.Attribute;
-import org.objectweb.asm.ClassAdapter;
 import org.objectweb.asm.ClassVisitor;
 import org.objectweb.asm.FieldVisitor;
 import org.objectweb.asm.MethodVisitor;
@@ -30,14 +29,14 @@
  * A class visitor that filters out all members (fields, methods and inner classes) that are
  * either private, default-access or rejected by the {@link Filter}.
  */
-class FilterClassAdapter extends ClassAdapter {
+class FilterClassAdapter extends ClassVisitor {
 
     private final Logger mLog;
     private final Filter mFilter;
     private String mClassName;
 
     public FilterClassAdapter(ClassVisitor writer, Filter filter, Logger log) {
-        super(writer);
+        super(Opcodes.ASM4, writer);
         mFilter = filter;
         mLog = log;
     }
diff --git a/tools/mkstubs/src/com/android/mkstubs/sourcer/AnnotationSourcer.java b/tools/mkstubs/src/com/android/mkstubs/sourcer/AnnotationSourcer.java
index d2843a8..ea3ca67 100644
--- a/tools/mkstubs/src/com/android/mkstubs/sourcer/AnnotationSourcer.java
+++ b/tools/mkstubs/src/com/android/mkstubs/sourcer/AnnotationSourcer.java
@@ -17,11 +17,12 @@
 package com.android.mkstubs.sourcer;
 
 import org.objectweb.asm.AnnotationVisitor;
+import org.objectweb.asm.Opcodes;
 
 /**
  * An annotation visitor that generates Java source for an annotation.
  */
-class AnnotationSourcer implements AnnotationVisitor {
+class AnnotationSourcer extends AnnotationVisitor {
 
     private final String mOpenChar;
     private final String mCloseChar;
@@ -33,11 +34,13 @@
     }
 
     public AnnotationSourcer(Output output, boolean isArray) {
+        super(Opcodes.ASM4);
         mOutput = output;
         mOpenChar = isArray ? "[" : "(";
         mCloseChar = isArray ? "]" : ")";
     }
 
+    @Override
     public void visit(String name, Object value) {
         startOpen();
 
@@ -56,6 +59,7 @@
         }
     }
 
+    @Override
     public void visitEnd() {
         if (mNeedClose) {
             mOutput.write(mCloseChar);
@@ -63,18 +67,21 @@
         mOutput.write("\n");
     }
 
+    @Override
     public AnnotationVisitor visitAnnotation(String name, String desc) {
         startOpen();
-        
+
         mOutput.write("@%s", name);
         return this;
     }
 
+    @Override
     public AnnotationVisitor visitArray(String name) {
         startOpen();
         return new AnnotationSourcer(mOutput, true /*isArray*/);
     }
 
+    @Override
     public void visitEnum(String name, String desc, String value) {
         mOutput.write("/* annotation enum not supported: %s */\n", name);
     }
diff --git a/tools/mkstubs/src/com/android/mkstubs/sourcer/ClassSourcer.java b/tools/mkstubs/src/com/android/mkstubs/sourcer/ClassSourcer.java
index 3d95039..c005b0c 100644
--- a/tools/mkstubs/src/com/android/mkstubs/sourcer/ClassSourcer.java
+++ b/tools/mkstubs/src/com/android/mkstubs/sourcer/ClassSourcer.java
@@ -27,23 +27,25 @@
 /**
  * A class visitor that writes a java source.
  */
-public class ClassSourcer implements ClassVisitor {
+public class ClassSourcer extends ClassVisitor {
 
     private final Output mOutput;
     private final AccessSourcer mAccessSourcer;
     private String mClassName;
 
     public ClassSourcer(Output output) {
+        super(Opcodes.ASM4);
         mOutput = output;
         mAccessSourcer = new AccessSourcer(mOutput);
     }
-    
+
     /* Examples:
      * name = com/foo/MyClass
      * signature = null (if not generic)
      * superName = java/lang/Object
      * interfaces = [ java/lang/Runnable ... ]
      */
+    @Override
     public void visit(int version, int access, String name, String signature,
             String superName, String[] interfaces) {
 
@@ -63,13 +65,13 @@
             SignatureReader sigReader = new SignatureReader(signature);
             SignatureSourcer sigSourcer = new SignatureSourcer();
             sigReader.accept(sigSourcer);
-            
+
             if (sigSourcer.hasFormalsContent()) {
                 mOutput.write(sigSourcer.formalsToString());
             }
 
             mOutput.write(" extends %s", sigSourcer.getSuperClass().toString());
-            
+
         } else {
             // write non-generic super type
             mOutput.write(" extends %s", superName.replace('/', '.'));
@@ -87,35 +89,40 @@
                 need_sep = true;
             }
         }
-        
+
         // open class body
         mOutput.write(" {\n");
     }
 
+    @Override
     public void visitEnd() {
         mOutput.write("}\n");
     }
 
+    @Override
     public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
         mOutput.write("@%s", desc);
         return new AnnotationSourcer(mOutput);
     }
 
+    @Override
     public void visitAttribute(Attribute attr) {
         mOutput.write("%s /* non-standard class attribute */ ", attr.type);
     }
 
 
+    @Override
     public FieldVisitor visitField(int access, String name, String desc, String signature,
             Object value) {
         // skip synthetic fields
         if ((access & Opcodes.ACC_SYNTHETIC) != 0) {
             return null;
         }
-        
+
         return new FieldSourcer(mOutput, access, name, desc, signature);
     }
 
+    @Override
     public MethodVisitor visitMethod(int access, String name, String desc, String signature,
             String[] exceptions) {
 
@@ -123,15 +130,18 @@
         return new MethodSourcer(mOutput, mClassName, access, name, desc, signature, exceptions);
     }
 
+    @Override
     public void visitInnerClass(String name, String outerName, String innerName, int access) {
         // Skip inner classes. This just indicates there's an inner class definition but
         // they are visited at the top level as separate classes.
     }
 
+    @Override
     public void visitOuterClass(String owner, String name, String desc) {
         // Skip outer classes.
     }
 
+    @Override
     public void visitSource(String source, String debug) {
         // Skip source information.
     }
diff --git a/tools/mkstubs/src/com/android/mkstubs/sourcer/FieldSourcer.java b/tools/mkstubs/src/com/android/mkstubs/sourcer/FieldSourcer.java
index 7f30a24..68eae71 100644
--- a/tools/mkstubs/src/com/android/mkstubs/sourcer/FieldSourcer.java
+++ b/tools/mkstubs/src/com/android/mkstubs/sourcer/FieldSourcer.java
@@ -19,13 +19,14 @@
 import org.objectweb.asm.AnnotationVisitor;
 import org.objectweb.asm.Attribute;
 import org.objectweb.asm.FieldVisitor;
+import org.objectweb.asm.Opcodes;
 import org.objectweb.asm.Type;
 import org.objectweb.asm.signature.SignatureReader;
 
 /**
- * A field visitor that generates Java source defining a field. 
+ * A field visitor that generates Java source defining a field.
  */
-class FieldSourcer implements FieldVisitor {
+class FieldSourcer extends FieldVisitor {
 
     private final Output mOutput;
     private final int mAccess;
@@ -34,6 +35,7 @@
     private final String mSignature;
 
     public FieldSourcer(Output output, int access, String name, String desc, String signature) {
+        super(Opcodes.ASM4);
         mOutput = output;
         mAccess = access;
         mName = name;
@@ -41,21 +43,24 @@
         mSignature = signature;
     }
 
+    @Override
     public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
         mOutput.write("@%s", desc);
         return new AnnotationSourcer(mOutput);
     }
 
+    @Override
     public void visitAttribute(Attribute attr) {
         mOutput.write("%s /* non-standard attribute */ ", attr.type);
     }
 
+    @Override
     public void visitEnd() {
         // Need to write type and field name after the annotations and attributes.
 
         AccessSourcer as = new AccessSourcer(mOutput);
         as.write(mAccess, AccessSourcer.IS_FIELD);
-        
+
         if (mSignature == null) {
             mOutput.write(" %s", Type.getType(mDesc).getClassName());
         } else {
diff --git a/tools/mkstubs/src/com/android/mkstubs/sourcer/MethodSourcer.java b/tools/mkstubs/src/com/android/mkstubs/sourcer/MethodSourcer.java
index f58de32..26e8870 100644
--- a/tools/mkstubs/src/com/android/mkstubs/sourcer/MethodSourcer.java
+++ b/tools/mkstubs/src/com/android/mkstubs/sourcer/MethodSourcer.java
@@ -20,15 +20,16 @@
 import org.objectweb.asm.Attribute;
 import org.objectweb.asm.Label;
 import org.objectweb.asm.MethodVisitor;
+import org.objectweb.asm.Opcodes;
 import org.objectweb.asm.Type;
 import org.objectweb.asm.signature.SignatureReader;
 
 import java.util.ArrayList;
 
 /**
- * A method visitor that generates the Java source for a whole method. 
+ * A method visitor that generates the Java source for a whole method.
  */
-class MethodSourcer implements MethodVisitor {
+class MethodSourcer extends MethodVisitor {
 
     private final Output mOutput;
     private final int mAccess;
@@ -42,6 +43,7 @@
 
     public MethodSourcer(Output output, String className, int access, String name,
             String desc, String signature, String[] exceptions) {
+        super(Opcodes.ASM4);
         mOutput = output;
         mClassName = className;
         mAccess = access;
@@ -49,16 +51,16 @@
         mDesc = desc;
         mSignature = signature;
         mExceptions = exceptions;
-        
+
         mNeedDeclaration = true;
         mIsConstructor = "<init>".equals(name);
     }
-    
-    private void writeHeader() {        
+
+    private void writeHeader() {
         if (!mNeedDeclaration) {
             return;
         }
-        
+
         AccessSourcer as = new AccessSourcer(mOutput);
         as.write(mAccess, AccessSourcer.IS_METHOD);
 
@@ -68,19 +70,19 @@
             SignatureReader sigReader = new SignatureReader(mSignature);
             sigSourcer = new SignatureSourcer();
             sigReader.accept(sigSourcer);
-            
+
             if (sigSourcer.hasFormalsContent()) {
                 // dump formal template parameter definitions
                 mOutput.write(" %s", sigSourcer.formalsToString());
             }
         }
-        
+
         // output return type (constructor have no return type)
         if (!mIsConstructor) {
             // The signature overrides desc, if present
             if (sigSourcer == null || sigSourcer.getReturnType() == null) {
                 mOutput.write(" %s", Type.getReturnType(mDesc).getClassName());
-                
+
             } else {
                 mOutput.write(" %s", sigSourcer.getReturnType().toString());
             }
@@ -88,11 +90,11 @@
 
         // output name
         mOutput.write(" %s(", mIsConstructor ? mClassName : mName);
-            
+
         // output arguments. The signature overrides desc, if present
         if (mSignature == null) {
             Type[] types = Type.getArgumentTypes(mDesc);
-            
+
             for(int i = 0; i < types.length; i++) {
                 if (i > 0) {
                     mOutput.write(", ");
@@ -101,7 +103,7 @@
             }
         } else {
             ArrayList<SignatureSourcer> params = sigSourcer.getParameters();
-            
+
             for(int i = 0; i < params.size(); i++) {
                 if (i > 0) {
                     mOutput.write(", ");
@@ -114,7 +116,7 @@
         // output throwable exceptions
         if (mExceptions != null && mExceptions.length > 0) {
             mOutput.write(" throws ");
-            
+
             for (int i = 0; i < mExceptions.length; i++) {
                 if (i > 0) {
                     mOutput.write(", ");
@@ -128,106 +130,130 @@
         mNeedDeclaration = false;
     }
 
+    @Override
     public void visitCode() {
         writeHeader();
-        
+
         // write the stub itself
         mOutput.write("throw new RuntimeException(\"Stub\");");
     }
 
+    @Override
     public void visitEnd() {
         writeHeader();
         mOutput.write("\n}\n");
     }
 
+    @Override
     public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
         mOutput.write("@%s", desc);
         return new AnnotationSourcer(mOutput);
     }
 
+    @Override
     public AnnotationVisitor visitAnnotationDefault() {
         // pass
         return null;
     }
 
+    @Override
     public void visitAttribute(Attribute attr) {
         mOutput.write("%s /* non-standard method attribute */ ", attr.type);
     }
 
+    @Override
     public void visitFieldInsn(int opcode, String owner, String name, String desc) {
         // pass
     }
 
+    @Override
     public void visitFrame(int type, int local, Object[] local2, int stack, Object[] stack2) {
         // pass
     }
 
+    @Override
     public void visitIincInsn(int var, int increment) {
         // pass
     }
 
+    @Override
     public void visitInsn(int opcode) {
         // pass
     }
 
+    @Override
     public void visitIntInsn(int opcode, int operand) {
         // pass
     }
 
+    @Override
     public void visitJumpInsn(int opcode, Label label) {
         // pass
     }
 
+    @Override
     public void visitLabel(Label label) {
         // pass
     }
 
+    @Override
     public void visitLdcInsn(Object cst) {
         // pass
     }
 
+    @Override
     public void visitLineNumber(int line, Label start) {
         // pass
     }
 
+    @Override
     public void visitLocalVariable(String name, String desc, String signature,
             Label start, Label end, int index) {
         // pass
     }
 
+    @Override
     public void visitLookupSwitchInsn(Label dflt, int[] keys, Label[] labels) {
         // pass
     }
 
+    @Override
     public void visitMaxs(int maxStack, int maxLocals) {
         // pass
     }
 
+    @Override
     public void visitMethodInsn(int opcode, String owner, String name, String desc) {
         // pass
     }
 
+    @Override
     public void visitMultiANewArrayInsn(String desc, int dims) {
         // pass
     }
 
+    @Override
     public AnnotationVisitor visitParameterAnnotation(int parameter, String desc, boolean visible) {
         // pass
         return null;
     }
 
+    @Override
     public void visitTableSwitchInsn(int min, int max, Label dflt, Label[] labels) {
         // pass
     }
 
+    @Override
     public void visitTryCatchBlock(Label start, Label end, Label handler, String type) {
         // pass
     }
 
+    @Override
     public void visitTypeInsn(int opcode, String type) {
         // pass
     }
 
+    @Override
     public void visitVarInsn(int opcode, int var) {
         // pass
     }
diff --git a/tools/mkstubs/src/com/android/mkstubs/sourcer/SignatureSourcer.java b/tools/mkstubs/src/com/android/mkstubs/sourcer/SignatureSourcer.java
index 7805d7d..ab90945 100644
--- a/tools/mkstubs/src/com/android/mkstubs/sourcer/SignatureSourcer.java
+++ b/tools/mkstubs/src/com/android/mkstubs/sourcer/SignatureSourcer.java
@@ -16,6 +16,7 @@
 
 package com.android.mkstubs.sourcer;
 
+import org.objectweb.asm.Opcodes;
 import org.objectweb.asm.Type;
 import org.objectweb.asm.signature.SignatureReader;
 import org.objectweb.asm.signature.SignatureVisitor;
@@ -36,12 +37,12 @@
  * <p/>
  * Note: When processing a method's signature, the signature order is the reverse of the source
  * order, e.g. the signature is written as "(parameters)return-type" where we want to generate
- * "return-type method-name (parameters)". To hanlde this case, the return-type and parameters
+ * "return-type method-name (parameters)". To handle this case, the return-type and parameters
  * are <em>not</em> output directly but are instead accumulated in internal variables that you can
  * get later using {@link #getReturnType()}, {@link #getParameters()}, {@link #getSuperClass()}
  * and {@link #formalsToString()}.
  */
-class SignatureSourcer implements SignatureVisitor {
+class SignatureSourcer extends SignatureVisitor {
 
     /**
      * Buffer used to construct the signature.
@@ -85,13 +86,14 @@
     private ArrayList<SignatureSourcer> mParameters = new ArrayList<SignatureSourcer>();
 
 
-    
+
     /**
      * Constructs a new {@link SignatureWriter} object.
      */
     public SignatureSourcer() {
+        super(Opcodes.ASM4);
     }
-    
+
     private StringBuilder getBuf() {
         if (mWritingFormals) {
             return mFormalsBuf;
@@ -117,7 +119,7 @@
     public SignatureSourcer getReturnType() {
         return mReturnType;
     }
-    
+
     /**
      * Will be non-empty if a parameters were processed
      * by {@link SignatureReader#accept(SignatureVisitor)}
@@ -125,19 +127,19 @@
     public ArrayList<SignatureSourcer> getParameters() {
         return mParameters;
     }
-    
+
     /**
-     * True if the signature contains formal type parameters, which are available 
+     * True if the signature contains formal type parameters, which are available
      * via {@link #formalsToString()} after calling {@link SignatureReader#accept(SignatureVisitor)}
      */
     public boolean hasFormalsContent() {
         return mFormalsBuf.length() > 0;
     }
-    
+
     public String formalsToString() {
         return mFormalsBuf.toString();
     }
-    
+
     /**
      * Will be non-null if a super class was processed
      * by {@link SignatureReader#accept(SignatureVisitor)}
@@ -150,6 +152,7 @@
     // Implementation of the SignatureVisitor interface
     // ------------------------------------------------------------------------
 
+    @Override
     public void visitFormalTypeParameter(final String name) {
         if (!mWritingFormals) {
             mWritingFormals = true;
@@ -161,16 +164,19 @@
         getBuf().append(" extends ");
     }
 
+    @Override
     public SignatureVisitor visitClassBound() {
-        // we don't differentiate between visiting a sub class or interface type 
+        // we don't differentiate between visiting a sub class or interface type
         return this;
     }
 
+    @Override
     public SignatureVisitor visitInterfaceBound() {
-        // we don't differentiate between visiting a sub class or interface type 
+        // we don't differentiate between visiting a sub class or interface type
         return this;
     }
 
+    @Override
     public SignatureVisitor visitSuperclass() {
         endFormals();
         SignatureSourcer sourcer = new SignatureSourcer();
@@ -179,10 +185,12 @@
         return sourcer;
     }
 
+    @Override
     public SignatureVisitor visitInterface() {
         return this;
     }
 
+    @Override
     public SignatureVisitor visitParameterType() {
         endFormals();
         SignatureSourcer sourcer = new SignatureSourcer();
@@ -190,6 +198,7 @@
         return sourcer;
     }
 
+    @Override
     public SignatureVisitor visitReturnType() {
         endFormals();
         SignatureSourcer sourcer = new SignatureSourcer();
@@ -198,29 +207,35 @@
         return sourcer;
     }
 
+    @Override
     public SignatureVisitor visitExceptionType() {
         getBuf().append('^');
         return this;
     }
 
+    @Override
     public void visitBaseType(final char descriptor) {
         getBuf().append(Type.getType(Character.toString(descriptor)).getClassName());
     }
 
+    @Override
     public void visitTypeVariable(final String name) {
         getBuf().append(name.replace('/', '.'));
     }
 
+    @Override
     public SignatureVisitor visitArrayType() {
         getBuf().append('[');
         return this;
     }
 
+    @Override
     public void visitClassType(final String name) {
         getBuf().append(name.replace('/', '.'));
         mArgumentStack *= 2;
     }
 
+    @Override
     public void visitInnerClassType(final String name) {
         endArguments();
         getBuf().append('.');
@@ -228,6 +243,7 @@
         mArgumentStack *= 2;
     }
 
+    @Override
     public void visitTypeArgument() {
         if (mArgumentStack % 2 == 0) {
             ++mArgumentStack;
@@ -238,6 +254,7 @@
         getBuf().append('*');
     }
 
+    @Override
     public SignatureVisitor visitTypeArgument(final char wildcard) {
         if (mArgumentStack % 2 == 0) {
             ++mArgumentStack;
@@ -258,6 +275,7 @@
         return this;
     }
 
+    @Override
     public void visitEnd() {
         endArguments();
     }
diff --git a/tools/mkstubs/src/com/android/mkstubs/stubber/ClassStubber.java b/tools/mkstubs/src/com/android/mkstubs/stubber/ClassStubber.java
index 8f9ae11..f66c7a7 100644
--- a/tools/mkstubs/src/com/android/mkstubs/stubber/ClassStubber.java
+++ b/tools/mkstubs/src/com/android/mkstubs/stubber/ClassStubber.java
@@ -18,19 +18,19 @@
 
 import org.objectweb.asm.AnnotationVisitor;
 import org.objectweb.asm.Attribute;
-import org.objectweb.asm.ClassAdapter;
 import org.objectweb.asm.ClassVisitor;
 import org.objectweb.asm.FieldVisitor;
 import org.objectweb.asm.MethodVisitor;
+import org.objectweb.asm.Opcodes;
 
 /**
  * A class visitor that generates stubs for all methods of the visited class.
  * Everything else is passed as-is.
  */
-public class ClassStubber extends ClassAdapter {
+public class ClassStubber extends ClassVisitor {
 
     public ClassStubber(ClassVisitor cv) {
-        super(cv);
+        super(Opcodes.ASM4, cv);
     }
 
     @Override
@@ -41,45 +41,45 @@
             String[] interfaces) {
         super.visit(version, access, name, signature, superName, interfaces);
     }
-    
+
     @Override
     public void visitEnd() {
         super.visitEnd();
     }
-    
+
     @Override
     public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
         return super.visitAnnotation(desc, visible);
     }
-    
+
     @Override
     public void visitAttribute(Attribute attr) {
         super.visitAttribute(attr);
     }
-    
+
     @Override
     public MethodVisitor visitMethod(int access, String name, String desc, String signature,
             String[] exceptions) {
         MethodVisitor mw = super.visitMethod(access, name, desc, signature, exceptions);
         return new MethodStubber(mw, access, name, desc, signature, exceptions);
     }
-    
+
     @Override
     public FieldVisitor visitField(int access, String name, String desc, String signature,
             Object value) {
         return super.visitField(access, name, desc, signature, value);
     }
-    
+
     @Override
     public void visitInnerClass(String name, String outerName, String innerName, int access) {
         super.visitInnerClass(name, outerName, innerName, access);
     }
-    
+
     @Override
     public void visitOuterClass(String owner, String name, String desc) {
         super.visitOuterClass(owner, name, desc);
     }
-    
+
     @Override
     public void visitSource(String source, String debug) {
         super.visitSource(source, debug);
diff --git a/tools/mkstubs/src/com/android/mkstubs/stubber/MethodStubber.java b/tools/mkstubs/src/com/android/mkstubs/stubber/MethodStubber.java
index 1617809..89aa221 100644
--- a/tools/mkstubs/src/com/android/mkstubs/stubber/MethodStubber.java
+++ b/tools/mkstubs/src/com/android/mkstubs/stubber/MethodStubber.java
@@ -19,7 +19,6 @@
 import org.objectweb.asm.AnnotationVisitor;
 import org.objectweb.asm.Attribute;
 import org.objectweb.asm.Label;
-import org.objectweb.asm.MethodAdapter;
 import org.objectweb.asm.MethodVisitor;
 import org.objectweb.asm.Opcodes;
 
@@ -32,13 +31,13 @@
  * Note that constructors rewritten this way will probably fail with the runtime bytecode
  * verifier since no call to <code>super</code> is generated.
  */
-public class MethodStubber extends MethodAdapter {
+public class MethodStubber extends MethodVisitor {
 
     public MethodStubber(MethodVisitor mw,
             int access, String name, String desc, String signature, String[] exceptions) {
-        super(mw);
+        super(Opcodes.ASM4, mw);
     }
-    
+
     @Override
     public void visitCode() {
         Label l0 = new Label();
@@ -64,7 +63,7 @@
                 0);                                             // index
         mv.visitMaxs(3, 1); // maxStack, maxLocals
     }
-    
+
     @Override
     public void visitEnd() {
         super.visitEnd();
@@ -74,110 +73,110 @@
     public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
         return super.visitAnnotation(desc, visible);
     }
-    
+
     @Override
     public AnnotationVisitor visitAnnotationDefault() {
         return super.visitAnnotationDefault();
     }
- 
+
     @Override
     public void visitAttribute(Attribute attr) {
         super.visitAttribute(attr);
     }
-    
+
     @Override
     public AnnotationVisitor visitParameterAnnotation(int parameter, String desc, boolean visible) {
         return super.visitParameterAnnotation(parameter, desc, visible);
     }
 
     // -- stuff that gets skipped
-    
+
     @Override
     public void visitFieldInsn(int opcode, String owner, String name, String desc) {
         // skip
     }
-    
+
     @Override
     public void visitFrame(int type, int local, Object[] local2, int stack, Object[] stack2) {
         // skip
     }
-    
+
     @Override
     public void visitIincInsn(int var, int increment) {
         // skip
     }
-    
+
     @Override
     public void visitInsn(int opcode) {
         // skip
     }
-    
+
     @Override
     public void visitIntInsn(int opcode, int operand) {
         // skip
     }
-    
+
     @Override
     public void visitJumpInsn(int opcode, Label label) {
         // skip
     }
-    
+
     @Override
     public void visitLabel(Label label) {
         // skip
     }
-    
+
     @Override
     public void visitLdcInsn(Object cst) {
         // skip
     }
-    
+
     @Override
     public void visitLineNumber(int line, Label start) {
         // skip
     }
-    
+
     @Override
     public void visitLocalVariable(String name, String desc, String signature,
             Label start, Label end, int index) {
         // skip
     }
-    
+
     @Override
     public void visitLookupSwitchInsn(Label dflt, int[] keys, Label[] labels) {
         // skip
     }
-    
+
     @Override
     public void visitMaxs(int maxStack, int maxLocals) {
         // skip
     }
-    
+
     @Override
     public void visitMethodInsn(int opcode, String owner, String name, String desc) {
         // skip
     }
-    
+
     @Override
     public void visitMultiANewArrayInsn(String desc, int dims) {
         // skip
     }
-    
+
     @Override
     public void visitTableSwitchInsn(int min, int max, Label dflt, Label[] labels) {
         // skip
     }
-    
+
     @Override
     public void visitTryCatchBlock(Label start, Label end, Label handler, String type) {
         // skip
     }
-    
+
     @Override
     public void visitTypeInsn(int opcode, String type) {
         // skip
     }
-    
+
     @Override
     public void visitVarInsn(int opcode, int var) {
         // skip