2016년 11월 14일 월요일

Android workspace widget & shortcut 설정하기


  • 용어설명
- workspace: 안드로이드 바탕화면
- workspace의 아이콘은 앱링크인 App shortscut과, workspace에서 동작하는 appwidget으로 나뉜다.
- Hotseat 영역은 화면의 가장아래 가상버튼위 공간으로 통화버튼이 들어간 자리다.

  • 런처 설정 파일
- Launcher2/res/xml-sw600dp/default_workspace.xml : DB생성 초기 값으로 favorite table에 등록된다. 어느 스크린에 어떤 아이콘이 들어갈지 설정할 수 있으며 shortcut은 favorite xml tag로 표시된다.
 30 <!-- Middle screen [2] --> 31 <!--appwidget 32 launcher:packageName="com.android.deskclock" 33 launcher:className="com.android.alarmclock.AnalogAppWidgetProvider" 34 launcher:screen="2" 35 launcher:x="1" 36 launcher:y="0" 37 launcher:spanX="2" 38 launcher:spanY="2" /> 39 <favorite 40 launcher:packageName="com.android.camera" 41 launcher:className="com.android.camera.Camera" 42 launcher:screen="2" 43 launcher:x="0" 44 launcher:y="3" /-->
- Launcher2/res/values-sw600dp/config.xml : Hotseat 자리 개수, workspace rotation 등 설정파일:
- res/xml/dimens.xml : 아이콘 사이즈, 위치 등 설정파일:

  • 데이터 베이스 확인
sqlite3 /data/data/com.android.launcher/databases/launcher.db

sqlite> .table
android_metadata  favorites       

sqlite> select * from favorites;

1|||-100|2|2|3|2|2|4|2||||||||0    << 아날로그시계 앱위젯
3|갤러리|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.gallery3d/.app.Gallery;end|-100|3|1|3|1|1|0|-1||||||||0
5|설정|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.settings/.Settings;end|-100|3|2|3|1|1|0|-1||||||||0
7|전화|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.dialer/.DialtactsActivity;end|-101|1|1|0|1|1|0|-1||||||||0
9|주소록|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.contacts/.activities.PeopleActivity;end|-101|2|2|0|1|1|0|-1||||||||0
11|메시지|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.mms/.ui.ConversationList;end|-101|4|4|0|1|1|0|-1||||||||0
13|인터넷|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.browser/.BrowserActivity;end|-101|5|5|0|1|1|0|-1||||||||0
14|Dev Tools|#Intent;action=android.intent.action.MAIN;category=android.intent.category.LAUNCHER;launchFlags=0x10200000;component=com.android.development/.Development;end|-100|2|3|2|1|1|0|-1||0|||�PNG|||0

sqlite> delete from favorites where  _id=1  
launcher.db의 favorites 테이블의 모든 행을 지우면 google search bar만 남는다.

  • 코드내 favorite DB 생성명령
302             db.execSQL("CREATE TABLE favorites (" +                             
303                     "_id INTEGER PRIMARY KEY," +                                
304                     "title TEXT," +                                             
305                     "intent TEXT," +                                            
306                     "container INTEGER," +                                      
307                     "screen INTEGER," +                                         
308                     "cellX INTEGER," +                                          
309                     "cellY INTEGER," +                                          
310                     "spanX INTEGER," +                                          
311                     "spanY INTEGER," +                                          
312                     "itemType INTEGER," +                                       
313                     "appWidgetId INTEGER NOT NULL DEFAULT -1," +                
314                     "isShortcut INTEGER," +                                     
315                     "iconType INTEGER," +                                       
316                     "iconPackage TEXT," +                                       
317                     "iconResource TEXT," +                                      
318                     "icon BLOB," +                                              
319                     "uri TEXT," +                                               
320                     "displayMode INTEGER," +                                    
321                     "profileId INTEGER DEFAULT " + userSerialNumber +           
322                     ");");



참조:
https://developer.android.com/guide/practices/ui_guidelines/widget_design.html
https://developer.android.com/guide/topics/appwidgets/index.html



2016년 11월 10일 목요일

플래쉬가 없지만 Quick Settings icon에 flashlight를 표시하는 방법

안드로이드 개발보드에 플래쉬가 없긴하지만 Quick Settings에 Flashlight 아이콘이 나오게 하고 싶다.


결론:
Quick settings에 표시하는 아이콘의 리스트는
/data/data/com.android.providers.settings/databases/settings.db의 secure 테이블에서 sysui_qs_tiles컬럼으로 관리된다.
없을경우 R.string.quick_settings_tiles 에서 표시할 리스트를 가져온다. 여기에 필요한 리스트를 추가하면 된다.
확인 결과 quick settings tile list에 기본값으로 flashlight는 포함된다.
하지만 FlashlightController에서 비활성화 플래그로 인해 표시를 하지않는다. 이 값을 강제로 설정하면 표시는 가능하다.

과정:
Flashlight는 카메라 서비스에서 제공되는 기능으로 카메라 API를 통해서 제어를 할 수있다.
Quick settings icon의 경우 SystemUI에서 관리한다.


//SystemUI 설정 (QSTileHost.java 참조)
1) settings.db 업데이트
   adb shell settings get secure sysui_qs_tiles
   adb shell settings put secure sysui_qs_tiles wifi,bt,inversion,cell,airplane,rotation,flashlight,location,cast,hotspot

settings put을 하면 바로 화면에 적용된다.
위 명령에서 설정값이 없으면 R.string.quick_settings_tiles 에서 리스트를 가져온다.

2)SystemUI/res/values/config.xml
 - R.string.quick_settings_tiles
 - R.string.quick_settings_tiles_default
 - quick settings의 행과 열 설정값.
 - 각종 UI 타이밍 설정값

settings.db의 sysui_qs_tiles의 기본값은 flashlight가 포함되어 있는데, 안나온다.
flashlight 타일의 소스를 보면 HAL포팅이 되어있어야 온/오프 표시가 된다는 것을 알수 있다.

* SystemUI 소스확인
소스위치 : android/frameworks/base/packages/SystemUI
Quick settings 소스 위치: SystemUI/src/com/android/systemui/qs
Status Bar의 명칭 : http://minuhome.tistory.com/13

//타이틀 리스트 생성
 ../systemui/statusbar/phone/QSTileHost.java :
 QSTileHost : recreateTiles()
  { final List<String> tileSpecs = loadTileSpecs();
    createTile(titleSpec)); }

//타이틀 리스트에 따라 퀵세팅 인스턴스생성
 QSTileHost : createTile() { else if (tileSpec.equals("flashlight")) return new FlashlightTile(this); }

//플래쉬 라이트 초기화
src/com/android/systemui/qs/tiles/FlashlightTile.java

//플래쉬상태표시
아래 FlsahController가 활성화 되어 있을경우 표시가된다.
강제로 state.visible=true로 하면 퀵세팅패털에서 플래쉬아이콘을 볼 수 있다.:

handleUpdateState()
state.visible = mWasLastOn != 0 || mFlashlightController.isAvailable();

//개발보드 HAL 로깅메시지
10-06 04:08:22.790 2468-2468/? D/ExynosCameraParameters: [CAM_ID(1)][ParametersFront]-DEBUG(setParameters):strNewFlashMode off


*플래쉬 HAL
각 보드별 특성 설정: android/device/company/products
컴파일 결과물: android/out

HAL Module : out/target/product/mv7420/obj/lib/*.so
HAL Module은 커널의 장치를 제어하는 인터페이스 라이브러리이다.
아래 링크정보를 보고 어떤파일이 컴파일되는 지 확인해 볼수 있다.
HAL Module link 정보:
out/target/product/mv7420/obj/SHARED_LIBRARIES/module_namexxx_intermediates/module_namexxx.P


백라이트 HAL:
Nexus: android/device/lge/liblight
HTC: android/device/htc/flounder/lights
mv7420: device/samsung/smdk_common/liblight/lights.c
센서 HAL
Nexus: android/device/lge/libsensor
HTC: android/device/htc/flounder/sensor_hub/libsensors
mv7420: vendor/invensense/libsensors_HAL_1_1/sensors_mpl.cpp

오디오 HAL
       android/device/samsung/mv7420/audio

카메라 HAL
  libexynoscamera.so  : hardware/samsung_slsi/exynos7420/libcamera/ExynosCameraSensorInfo.cpp
        libcamera_client.so : frameworks/av/camera/*.c
libcamera_metadata.so : system/media/camera/src/*.c
        libcameraservice.so : frameworks/av/services/camera/libcameraservice/*.cpp


1. 카메라 매니져 접근:
 SystemUI/src/com/android/systemui/statusbar/policy/FlashlightController.java :
 mCameraManager = (CameraManager) mContext.getSystemService(Context.CAMERA_SERVICE);
2. 카메라 장치 오픈
 SystemUI/src/com/android/systemui/statusbar/policy/FlashlightController.java :
 mCameraManager.openCamera(getCameraId(), mCameraListener, mHandler);:0:
3. 플래시 명령 전달
 builder.set(CaptureRequest.FLASH_MODE, CameraMetadata.FLASH_MODE_TORCH);




*특정 태크 로깅 설정

Dalvik property 설정:setprop log.tag.<your_log_tag> <level>

$ ./adb shell stop
$ ./adb shell setprop log.tag.QSTileHost DEBUG
$ ./adb shell setprop log.tag.FlashlightController DEBUG
$ ./adb shell start



*파워버튼 두번 누르면 카메라켜기
android/frameworks/base/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java

powerMultiPressAction(..) {
 ...
 case MULTI_PRESS_POWER_LAUNCH_CAMERA:
    Slog.i(TAG, "Launching camera by power button.");
    if (!mCameraLensCoverState != CAMERA_LENS_COVERED) {
        if (!interactive) {
            wakeUpFromPowerKey(eventTime);
        }
        launchCamera();
    }
    break;
...
}

2016년 10월 26일 수요일

Android storage mount configuration

  1. Android storage mount configuration
    1. # cat /init.rc
root@mv7420:/ # cat /init.rc | grep mount
….
   # Create cgroup mount point for cpu accounting
   mount cgroup none /acct cpuacct
….
   # Create cgroup mount point for memory
   mount tmpfs none /sys/fs/cgroup mode=0750,uid=0,gid=1000
   mount cgroup none /sys/fs/cgroup/memory memory
….
   # Secure container public mount points.
   mount tmpfs tmpfs /mnt/asec mode=0755,gid=1000
….
   # Filesystem image public mount points.
   mount tmpfs tmpfs /mnt/obb mode=0755,gid=1000
….
   # memory control cgroup
   mount cgroup none /dev/memcg memory
….
   # Create cgroup mount points for process groups
   mount cgroup none /dev/cpuctl cpu
….
   # pstore/ramoops previous console log
   mount pstore pstore /sys/fs/pstore
….
  # once everything is setup, no need to modify /
   mount rootfs rootfs / ro remount
   # mount shared so changes propagate into child namespaces
   mount rootfs rootfs / shared rec
….

    1. # cat /init.<device>.rc
root@mv7420:/ # cat init.samsungexynos7420.rc
import init.samsungexynos7420.usb.rc

on init
   start watchdogd

   chmod 0701 /mnt/media_rw
   chown root root /mnt/media_rw
….
….

service setup_fs /system/bin/setup_fs mmcblk0p3  mmcblk0p4
   class core
   user root
   group root
   oneshot

service battery_charger /sbin/healthd -c
       user root
       group root
       class charger
       seclabel u:r:healthd:s0

on fs
   mount_all /fstab.samsungexynos7420
   setprop ro.crypto.fuse_sdcard true

# Boost Block I/O Performance
   write /sys/block/sda/queue/read_ahead_kb 512
   write /sys/block/sda/queue/rq_affinity  2
   write /sys/block/sda/queue/iosched/slice_idle 0

# Permissions for ION
   chmod 0660 /sys/class/ion_cma/ion_video_ext/isolated
   chown system system /sys/class/ion_cma/ion_video_ext/isolated

# Permissions for backlight
   chmod 0660 /sys/class/backlight/pwm-backlight.0/brightness
   chown system system /sys/class/backlight/pwm-backlight.0/brightness

# Copy DRM Key
   copy /system/app/wv.keys /factory/wv.keys


    1. External storage is managed by a combination of the vold init service and MountService system service. Mounting of physical external storage volumes is handled by vold, which performs staging operations to prepare the media before exposing it to apps.
      https://source.android.com/devices/storage/config.html
    2. Android 4.2.2 and earlier : /etc/vold.fstab
    3. Android 4.3 and later : /fstab.<device>
      the raw physical device must first be mounted /devices/xxx, then vold will manage the sdcard0, usb1, usb2
      # cat fstab.samsungexynos7420
# Android fstab file.
#<src>                  <mnt_point>         <type>    <mnt_flags and options>
                           <fs_mgr_flags>
# The filesystem that contains the filesystem checker binary (typically /system) cannot
# specify MF_CHECK, and must come before any filesystems that do specify MF_CHECK

/dev/block/platform/15740000.dwmmc0/by-name/system      /system ext4    rowait
/dev/block/platform/15740000.dwmmc0/by-name/cache       /cache  ext4    noatime, nosuid,nodev,nomblk_io_submit,errors=panic      wait
/dev/block/platform/15740000.dwmmc0/by-name/userdata    /data   ext4    noatime,
nosuid,nodev,nomblk_io_submit,discard,noauto_da_alloc,errors=panic    wait,force encrypt=/cache/metadata

# VOLD
/devices/15560000.dwmmc2/mmc_host/mmc2          auto            vfat    default voldmanaged=sdcard0:auto
/devices/15510000.usb                           auto    vfat    default voldmana ged=usb1:auto
/devices/15400000.usb/15400000.dwc3/xhci-hcd    auto    vfat    default voldmana ged=usb2:auto


  1. MMC device partition name
# ls -l /dev/block/platform/15740000.dwmmc0/by-name/
lrwxrwxrwx root     root              2046-11-08 15:37 fat -> /dev/block/mmcblk0p1
lrwxrwxrwx root     root              2046-11-08 15:37 system -> /dev/block/mmcblk0p2
lrwxrwxrwx root     root              2046-11-08 15:37 userdata -> /dev/block/mmcblk0p3
lrwxrwxrwx root     root              2046-11-08 15:37 cache -> /dev/block/mmcblk0p4
lrwxrwxrwx root     root              2046-11-08 15:37 efs -> /dev/block/mmcblk0p5
lrwxrwxrwx root     root              2046-11-08 15:37 kernel -> /dev/block/mmcblk0p6
lrwxrwxrwx root     root              2046-11-08 15:37 ramdisk -> /dev/block/mmcblk0p7
lrwxrwxrwx root     root              2046-11-08 15:37 recovery -> /dev/block/mmcblk0p8
lrwxrwxrwx root     root              2046-11-08 15:37 dtb -> /dev/block/mmcblk0p9
lrwxrwxrwx root     root              2046-11-08 15:37 ldfw -> /dev/block/mmcblk0p10
lrwxrwxrwx root     root              2046-11-08 15:37 bootlogo -> /dev/block/mmcblk0p11
lrwxrwxrwx root     root              2046-11-08 15:37 font -> /dev/block/mmcblk0p12
lrwxrwxrwx root     root              2046-11-08 15:37 engmode -> /dev/block/mmcblk0p13

  1. MMC device partition blocks
# cat /proc/partitions
major minor  #blocks  name
179        0   30535680 mmcblk0
179        1         32 mmcblk0p1
179        2    2662400 mmcblk0p2
179        3   26941360 mmcblk0p3
179        4     819200 mmcblk0p4
179        5      10240 mmcblk0p5
179        6      20480 mmcblk0p6
179        7      26624 mmcblk0p7
259        0      26624 mmcblk0p8
259        1       1024 mmcblk0p9
259        2       2048 mmcblk0p10
259        3      10240 mmcblk0p11
259        4       1024 mmcblk0p12
259        5       2048 mmcblk0p13
179       24       4096 mmcblk0rpmb
179       16       4096 mmcblk0boot1
179        8       4096 mmcblk0boot0
254        0   26941360 dm-0


  1. for MTD and EMMC devices, the  partition layout and name can be retrieved by reading /proc/mtd, /proc/emmc

2016년 10월 17일 월요일

PJSIP 설치

컴파일

2.      컴파일 환경 설정
1) environment-setup-cortexa5hf-vfp-poky-linux-gnueabi
에서 LD = $CC로 수정
2) source /home/albert/Workspace2/VoIP/yocto_gcc/environment-setup-cortexa5hf-vfp-poky-linux-gnueabi (
sama5d31ek_build 문서참조)
3) make distclean &&  make clean
4) ./configure --host=arm-linux
5) pjlib/include/pj/config_site.h
에서 PJ_DEBUG 1, PJ_LOG_MAX_LEVEL 4 로 수정
6) make dep && make

3.      Alsa 라이브러리 설치
rootfs에 라이브러리가 없을 경우 필요한 작업이다.
1) cp –r poky/build-atmel/tmp/sysroots/sama5d3xek/usr/include/alsa  ~/yocto_sdk/sysroots/cortexa5hf-vfp-poky-linux-gnueabi/usr/include;
2) cp poky/build-atmel/tmp /sysroots/sama5d3xek/usr/lib/libasound.so*  ~/yocto_sdk/sysroots/cortexa5hf-vfp-poky-linux-gnueabi/usr/lib

4.      시스템 설정
A.     소켓버퍼 최대 사이즈를 늘린다. 아래처럼 명령을 이용하거나 etc/sysctl.conf에 설정한다. (“net.core.rmem_max=26214400” 형식으로 설정)
                                   i.         $ sysctl -w net.core.rmem_max=26214400
$ sysctl -w net.core.wmem_max=26214400

5.      테스트
pjlib-test: PJLIB 기능테스트, pjlib/bin/pjlib-test-*
pjsip-test: PJSIP
SIP 기능테스트, pjsip/bin/pjsip-test*
pjsystest:
오디오 기능테스트, pjsip-apps/bin/pjsystest-*

 pjsua application on pjsip-apps/bin directory. PJSUA manual can be found in http://www.pjsip.org/pjsua.htm page.

컴파일시 발생 문제해결

문제:
../src/pjmedia-audiodev/alsa_dev.c:37:28: fatal error: alsa/asoundlib.h: No such file or directory
해결: alsa 라이브러리 헤더 추가
cp –r poky/build-atmel/tmp/sysroots/sama5d3xek/usr/include/alsa  ~/yocto_sdk/sysroots/cortexa5hf-vfp-poky-linux-gnueabi/usr/include

문제:
/src/pjmedia-audiodev/alsa_dev.c:317: undefined reference to `snd_lib_error_set_handler'
해결링크옵션에 alsa 라이브러리 추가
cp -l r poky/build-atmel/tmp /sysroots/sama5d3xek/usr/lib/libasound.so*  ~/yocto_sdk/sysroots/cortexa5hf-vfp-poky-linux-gnueabi/usr/lib/

문제:
sphinx-build -b html -d _build/doctrees   . _build/html
make: sphinx-build: Command not found
make: *** [html] Error 127




해결: apt-file 을 설치해서 sphix-build가 어떤 패키지에 있는지 검색 후 설치한다.
1.      sudo apt-get install apt-file
2.      apt-file search sphinx-build
3.      sudo apt-get install python-sphinx

문제: 컴파일 후 타겟에서 실행하면 실행안됨
root@sama5d3xek:/mnt# ls -al pjsip-apps-bin/pjsua-arm-unknown-linux-gnu
-rwxrwxr-x 1 1000 1000 6015936 May 18  2016 pjsip-apps-bin/pjsua-arm-unknown-linux-gnu
root@sama5d3xek:/mnt# ./pjsip-apps-bin/pjsua-arm-unknown-linux-gnu
-sh: ./pjsip-apps-bin/pjsua-arm-unknown-linux-gnu: No such file or directory
해결: source /yocto_sdk/environment-setup-cortexa5hf-vfp-poky-linux-gnueabi 에서
LD = $CC 로 수정한다. 추가로 필요한 링커 옵션은 –Wl 으로 넘긴다.
arm-poky-linux-gnueabi-ld 로 링킹할 경우 스텁코드링킹이 정상적으로 바인딩되지 않는 것 같다.

설정파일

예시1(using-opensip proxy)

--id sip:atmel@192.168.1.220
--registrar sip:192.168.1.220
--proxy sip:192.168.1.220;lr
--realm *
--username atmel
--password atmel
--play-file TheCubanMissileCrisis_8K.wav
--rec-file rec.wav
--add-buddy sip:cisco@192.168.1.220
--add-buddy sip:windows@192.168.1.220
--add-buddy sip:android@192.168.1.220
--auto-answer 200
--log-file log_file.txt
--log-level 4
--app-log-level 4
--ec-tail=400
--ec-opt=1


기능테스트

pjlib-test

- 모든 테스트 성공.

loopbask mic to speaker

 - pjsua: >>>> cc 0 0
 - 노이즈 없이 깨끗하게 잘 들림.

pjsip-test

x86테스트
- x86에 같은버젼의 alsa pjsip를 설치후 pjsip-test를 돌리면 모든 테스트 성공.(26분소요)
10:20:18 ./pjsip/bin/pjsip-test-x86_64-unknown-linux-gnu
(….)
10:46:55.616 Peak memory size=4154504685 MB
10:46:55.621 10:46:55.621 Stack max usage: 0, deepest: :0
10:46:55.621 Looks like everything is okay!..

Running tsx_uas_test(loop-dgram) 실패 : test10
문제:
tsx_uas_tes 10 timeout 실패
해결: 소켓 버퍼의 최대사이즈를 늘린다.
- receive buffer = rmem, send buffer = wmem
$ sysctl -w net.core.rmem_max=26214400
$ sysctl -w net.core.wmem_max=26214400

pjsua

전화걸기:
./pjsua sip:192.168.1.64

전화받기:
>>> a
>>> 200

자동응답:
$ pjsua --play-file /path/PROMPT.WAV --auto-answer 200 --auto-play --auto-loop

RTP 송수신 퍼포먼스 테스트

pc-server: /pjsip-apps/bin/samples/…/streamutil --send-recv --play-file=test.wav --remote=192.168.1.10:4000
target-client: /pjsip-apps/bin/samples/…/streamutil --send-recv --play-file=test.wav --remote=192.168.1.212:4000