Skip to content

Commit 6a15212

Browse files
authored
Add android lecture (#49)
1 parent 9def82d commit 6a15212

2 files changed

Lines changed: 370 additions & 0 deletions

File tree

Lines changed: 254 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,254 @@
1+
\documentclass{beamer}
2+
3+
% Theme choice
4+
\usetheme{Madrid}
5+
6+
% Optional packages
7+
\usepackage[utf8]{inputenc}
8+
\usepackage[T1]{fontenc}
9+
\usepackage[english]{babel}
10+
\usepackage{graphicx} % For including images
11+
\usepackage{amsmath} % For math symbols and formulas
12+
\usepackage{hyperref} % For hyperlinks
13+
\usepackage{listings} % For code snippets
14+
15+
\lstset{
16+
basicstyle=\ttfamily\footnotesize,
17+
breaklines=true,
18+
columns=fullflexible,
19+
keepspaces=true
20+
}
21+
22+
\title[OpenVINO on Android]{OpenVINO on Android: quick guide}
23+
\author{Obolenskiy Arseniy, Nesterov Alexander}
24+
\institute{ITLab}
25+
\date{\today}
26+
27+
% Redefine the footline to display both the short title and the org name
28+
\setbeamertemplate{footline}{
29+
\leavevmode%
30+
\hbox{%
31+
\begin{beamercolorbox}[wd=.45\paperwidth,ht=2.5ex,dp=1ex,leftskip=1em,center]{author in head/foot}%
32+
\usebeamerfont{author in head/foot}\insertshortinstitute%
33+
\end{beamercolorbox}%
34+
\begin{beamercolorbox}[wd=.45\paperwidth,ht=2.5ex,dp=1ex,leftskip=1em,center]{author in head/foot}%
35+
\usebeamerfont{author in head/foot}\insertshorttitle%
36+
\end{beamercolorbox}%
37+
\begin{beamercolorbox}[wd=.1\paperwidth,ht=2.5ex,dp=1ex,rightskip=1em,center]{author in head/foot}%
38+
\usebeamerfont{author in head/foot}\insertframenumber{} / \inserttotalframenumber%
39+
\end{beamercolorbox}}%
40+
\vskip0pt%
41+
}
42+
43+
\AtBeginSection[]{
44+
\begin{frame}
45+
\centering
46+
\Huge\insertsection%
47+
\end{frame}
48+
}
49+
50+
\begin{document}
51+
52+
\begin{frame}
53+
\titlepage%
54+
\end{frame}
55+
56+
\section{Platform}
57+
\begin{frame}{Android stack (bottom to top)}
58+
\begin{itemize}
59+
\item Linux kernel: drivers, memory, threading and security primitives.
60+
\item HAL layer gives stable APIs to diverse chips; keeps upper layers portable
61+
\item ART runtime executes app bytecode/Dex
62+
\item Native C/C++ libs: media/graphics; we hook via NDK for speed.
63+
\item Java/Kotlin API framework + services: usual app layer on top.
64+
\item Takeaway: we can reach native performance while staying compatible.
65+
\end{itemize}
66+
\end{frame}
67+
68+
\section{Tools}
69+
\begin{frame}{SDK vs NDK}
70+
\begin{itemize}
71+
\item SDK stack: Java/Kotlin UI + app logic; produces APKs
72+
\item NDK toolkit builds C/C++ \texttt{.so}; OpenVINO core is C++ so NDK is mandatory
73+
\item Workflow: cross-compile on host for target ABI (ARM/x86\_64) via NDK toolchain.
74+
\end{itemize}
75+
\end{frame}
76+
77+
\begin{frame}{What to install}
78+
\begin{itemize}
79+
\item Android NDK (e.g., r28c) --- includes \texttt{android.toolchain.cmake}.
80+
\item Platform Tools (ADB) --- push binaries, run shell, grab logs.
81+
\item CMake + Ninja on host --- configure/build quickly; any modern CMake works.
82+
\item Optional: Android Studio only if you plan to package an APK later.
83+
\end{itemize}
84+
\end{frame}
85+
86+
\begin{frame}{What is ADB}
87+
\begin{itemize}
88+
\item Android Debug Bridge = client/server/daemon trio for device control over USB/Wi‑Fi.
89+
\item Core uses: file transfer (\texttt{adb push/pull}), remote shell (\texttt{adb shell}), install/uninstall APKs, logcat, port forwarding.
90+
\item ADB must see the device: enable Developer options + USB debugging; check with \texttt{adb devices}.
91+
\item For our flow: we use it to copy OpenVINO libs/tools and run \texttt{benchmark\_app} on-device.
92+
\end{itemize}
93+
\end{frame}
94+
95+
\begin{frame}[fragile]{No device? Use an emulator (CLI)}
96+
\begin{itemize}
97+
\item Install Android SDK command-line tools; add \texttt{sdkmanager}, \texttt{avdmanager}, \texttt{emulator} to \texttt{PATH}.
98+
\item Download image (example): \texttt{sdkmanager ``system-images;android-35;google\_apis;x86\_64''}.
99+
\item Create an AVD using \texttt{avdmanager create avd -n ov-emul -k ``system-images;android-35;google\_apis;x86\_64''}
100+
\item Run emulator headless: \texttt{emulator -avd ov-emul -no-window -gpu swiftshader\_indirect}.
101+
\item Verify ADB sees it: \texttt{adb devices} should list the virtual device; then use the same push/run steps as for hardware
102+
\end{itemize}
103+
\end{frame}
104+
105+
\section{Hello World (native)}
106+
\begin{frame}[fragile]{Build a tiny C++ binary}
107+
\begin{itemize}
108+
\item Minimal source:
109+
\end{itemize}
110+
\begin{lstlisting}
111+
// hello.cpp
112+
#include <iostream>
113+
int main() { std::cout << "Hello Android!\n"; }
114+
\end{lstlisting}
115+
\vspace{0.5em}
116+
\begin{lstlisting}
117+
cmake -B build -G Ninja \
118+
-DANDROID_ABI=$CURRENT_ANDROID_ABI \
119+
-DANDROID_PLATFORM=$CURRENT_ANDROID_PLATFORM \
120+
-DCMAKE_TOOLCHAIN_FILE=$CURRENT_CMAKE_TOOLCHAIN_FILE \
121+
-DCMAKE_BUILD_TYPE=Release
122+
cmake --build build --parallel
123+
\end{lstlisting}
124+
\begin{itemize}
125+
\item Result: \texttt{build/hello} ELF for the target ABI.\@
126+
\end{itemize}
127+
\end{frame}
128+
129+
\begin{frame}[fragile]{Run Hello World on device}
130+
\begin{itemize}
131+
\item Push and execute via ADB (commands below).\@
132+
\end{itemize}
133+
\begin{lstlisting}
134+
adb push build/hello /data/local/tmp/
135+
adb shell "chmod +x /data/local/tmp/hello && /data/local/tmp/hello"
136+
\end{lstlisting}
137+
\begin{itemize}
138+
\item Expect stdout: \texttt{Hello Android!}
139+
\item If it fails: check ABI/API level and \texttt{LD\_LIBRARY\_PATH} (for libc++ if dynamically linked).
140+
\end{itemize}
141+
\end{frame}
142+
143+
\section{Homework}
144+
\begin{frame}{HW — Hello Android}
145+
\begin{itemize}
146+
\item Prepare env: install NDK + Platform Tools, set \texttt{CURRENT\_ANDROID\_*}; emulator allowed if no device.
147+
\item Build \texttt{hello.cpp} via CMake/NDK (recipe in slides); get \texttt{build/hello} for your ABI/API level.
148+
\item Run on device/emulator: \texttt{adb push}, \texttt{chmod +x}, execute; expect \texttt{Hello Android!} on stdout.
149+
\item Submit: short note (ABI + API level, commands used, screenshot/log of output); if something failed, describe it separately.
150+
\item Bonus: static link (\texttt{ANDROID\_STL=c++\_static}) or wrap the binary into a minimal APK via Android Studio.
151+
\end{itemize}
152+
\end{frame}
153+
154+
\section{Environment}
155+
\begin{frame}{Key variables}
156+
\begin{itemize}
157+
\item \texttt{ANDROID\_NDK\_PATH}, \texttt{ANDROID\_TOOLS\_PATH}.
158+
\item \texttt{CURRENT\_ANDROID\_ABI} (typically \texttt{arm64-v8a}; must match device).
159+
\item \texttt{CURRENT\_ANDROID\_PLATFORM} (API level, e.g., 35; not higher than device).
160+
\item \texttt{CURRENT\_ANDROID\_STL} (\texttt{c++\_shared} for shared libc++).
161+
\item \texttt{CURRENT\_CMAKE\_TOOLCHAIN\_FILE} (\ldots/android.toolchain.cmake) to enable cross-build.
162+
\item Wrong values \textrightarrow{} link/runtime errors; double-check before configuring.
163+
\end{itemize}
164+
\end{frame}
165+
166+
\begin{frame}{Supported ABIs}
167+
\begin{itemize}
168+
\item \texttt{arm64-v8a}, \texttt{armeabi-v7a}, \texttt{x86\_64}, \texttt{riscv64} (experimental).
169+
\item Detect on device: \texttt{adb shell getprop ro.product.cpu.abi}.
170+
\item Build only what you need (faster builds, smaller artifact set).
171+
\end{itemize}
172+
\end{frame}
173+
174+
\section{Build}
175+
\begin{frame}[fragile]{oneTBB}
176+
\begin{itemize}
177+
\item Clone the oneTBB repo (threading backend OpenVINO depends on).
178+
\item Configure with Android toolchain; disable tests to speed up.
179+
\item CMake example:
180+
\end{itemize}
181+
\begin{lstlisting}
182+
cmake -B build -G Ninja \
183+
-DANDROID_ABI=arm64-v8a \
184+
-DANDROID_PLATFORM=35 \
185+
-DANDROID_STL=c++_shared \
186+
-DCMAKE_TOOLCHAIN_FILE=$CURRENT_CMAKE_TOOLCHAIN_FILE \
187+
-DCMAKE_BUILD_TYPE=Release \
188+
-DTBB_TEST=OFF
189+
cmake --build build --parallel
190+
cmake --install build --prefix $PWD/install
191+
\end{lstlisting}
192+
\end{frame}
193+
194+
\begin{frame}[fragile]{OpenVINO}
195+
\begin{lstlisting}
196+
cmake -B build -G Ninja \
197+
-DANDROID_ABI=$CURRENT_ANDROID_ABI \
198+
-DANDROID_PLATFORM=$CURRENT_ANDROID_PLATFORM \
199+
-DANDROID_STL=$CURRENT_ANDROID_STL \
200+
-DCMAKE_TOOLCHAIN_FILE=$CURRENT_CMAKE_TOOLCHAIN_FILE \
201+
-DTBB_DIR=/path/to/oneTBB/install/lib/cmake/TBB \
202+
-DCMAKE_BUILD_TYPE=Release
203+
cmake --build build --parallel
204+
cmake --install build --prefix $PWD/install
205+
\end{lstlisting}
206+
\vspace{0.5em}
207+
\begin{itemize}
208+
\item Outputs: OpenVINO \texttt{.so}, plugins, \texttt{benchmark\_app} for target ABI.\@
209+
\item Keep install dir; you will push these binaries to the device.
210+
\end{itemize}
211+
\end{frame}
212+
213+
\section{Deploy \& run}
214+
\begin{frame}{Push to device}
215+
\begin{itemize}
216+
\item Enable developer mode + USB debugging; connect the device.
217+
\item \texttt{adb push} oneTBB \& OpenVINO \texttt{.so}, \texttt{libc++\_shared.so}, \texttt{benchmark\_app}, model into \texttt{/data/local/tmp}.
218+
\item Keep everything in one directory to simplify library lookup.
219+
\end{itemize}
220+
\end{frame}
221+
222+
\begin{frame}[fragile]{Run inference}
223+
\begin{lstlisting}
224+
adb shell "LD_LIBRARY_PATH=/data/local/tmp \
225+
/data/local/tmp/benchmark_app \
226+
-m /data/local/tmp/model.xml -hint latency"
227+
\end{lstlisting}
228+
\begin{itemize}
229+
\item \texttt{LD\_LIBRARY\_PATH} points to pushed libs; \texttt{-m} sets model; \texttt{-hint latency} optimizes for response time.
230+
\item Watch stdout for latency/FPS and any missing-library errors.
231+
\end{itemize}
232+
\end{frame}
233+
234+
\section{Tuning}
235+
\begin{frame}{Performance tips}
236+
\begin{itemize}
237+
\item Prefer FP16/INT8 models to reduce compute and bandwidth.
238+
\item Tune thread count (\texttt{-nthreads}) for each device.
239+
\item Balance load against thermals when picking thread count.
240+
\item Try AUTO/NNAPI plugins if the device supports them.
241+
\item Always ship \texttt{libc++\_shared.so} alongside your binaries.
242+
\end{itemize}
243+
\end{frame}
244+
245+
\section{Wrap up}
246+
\begin{frame}{What next}
247+
\begin{itemize}
248+
\item We built OpenVINO + oneTBB for Android and ran the demo binary.
249+
\item Next: package the \texttt{.so} into APK/AAB and call via JNI from app code.
250+
\item Check official OpenVINO Android guide for sample apps and plugin notes.
251+
\end{itemize}
252+
\end{frame}
253+
254+
\end{document}
Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
# Домашнее задание: Hello World на Android (NDK)
2+
3+
Подробная инструкция, чтобы собрать и запустить нативный `hello` под Android и сдать результат.
4+
5+
## Что нужно установить
6+
1) **Android SDK command-line tools** (sdkmanager/avdmanager/emulator) — нужны и для эмулятора, и чтобы ставить NDK.
7+
2) **Android NDK** (например, r28c). Пусть в переменной `ANDROID_NDK_PATH`.
8+
3) **Platform Tools (ADB)**. Положите `adb` в PATH или задайте `ANDROID_TOOLS_PATH`.
9+
4) **CMake + Ninja** на хосте (Linux/macOS/Windows WSL).
10+
5) (Опционально) **Эмулятор** из Android SDK, если нет физического устройства.
11+
12+
### Установка SDK/NDK на Linux (через command-line tools)
13+
```bash
14+
# 1. Скачайте command-line tools
15+
wget https://dl.google.com/android/repository/commandlinetools-linux-11076708_latest.zip -O cmd-tools.zip
16+
mkdir -p $HOME/Android/cmdline-tools
17+
unzip -q cmd-tools.zip -d $HOME/Android/cmdline-tools
18+
mv $HOME/Android/cmdline-tools/cmdline-tools $HOME/Android/cmdline-tools/latest
19+
20+
# 2. Пути и sdkmanager
21+
export ANDROID_SDK_ROOT=$HOME/Android
22+
export PATH="$ANDROID_SDK_ROOT/cmdline-tools/latest/bin:$ANDROID_SDK_ROOT/platform-tools:$PATH"
23+
24+
# 3. Примите лицензии (один раз)
25+
yes | sdkmanager --licenses
26+
27+
# 4. Ставим нужное
28+
sdkmanager "platform-tools" \
29+
"ndk;28.0.12433566" \ # r28c, можно выбрать иную версию
30+
"cmake;3.31.1" \
31+
"emulator" \
32+
"system-images;android-35;google_apis;x86_64"
33+
34+
# 5. Пути для задания
35+
export ANDROID_NDK_PATH="$ANDROID_SDK_ROOT/ndk/28.0.12433566"
36+
export ANDROID_TOOLS_PATH="$ANDROID_SDK_ROOT/platform-tools"
37+
```
38+
Теперь можно продолжать по инструкции ниже.
39+
40+
## Переменные окружения (пропишите в шелле)
41+
```bash
42+
export ANDROID_NDK_PATH=/path/to/android-ndk-r28c
43+
export ANDROID_TOOLS_PATH=/path/to/platform-tools
44+
export PATH="$ANDROID_TOOLS_PATH:$PATH"
45+
46+
# выберите под ваше устройство/эмулятор
47+
export CURRENT_ANDROID_ABI=arm64-v8a # или armeabi-v7a, x86_64
48+
export CURRENT_ANDROID_PLATFORM=35 # не выше API устройства
49+
export CURRENT_ANDROID_STL=c++_shared # можно c++_static для бонуса
50+
export CURRENT_CMAKE_TOOLCHAIN_FILE=$ANDROID_NDK_PATH/build/cmake/android.toolchain.cmake
51+
```
52+
53+
Проверки:
54+
- `adb devices` должен показать устройство/эмулятор.
55+
- `adb shell getprop ro.product.cpu.abi` — узнать ABI, чтобы не промахнуться.
56+
57+
## Исходник
58+
Сохраните в `hello.cpp`:
59+
```cpp
60+
#include <iostream>
61+
int main() { std::cout << "Hello Android!\n"; }
62+
```
63+
64+
## Сборка (host → Android)
65+
```bash
66+
cmake -B build -G Ninja \
67+
-DANDROID_ABI=$CURRENT_ANDROID_ABI \
68+
-DANDROID_PLATFORM=$CURRENT_ANDROID_PLATFORM \
69+
-DANDROID_STL=$CURRENT_ANDROID_STL \
70+
-DCMAKE_TOOLCHAIN_FILE=$CURRENT_CMAKE_TOOLCHAIN_FILE \
71+
-DCMAKE_BUILD_TYPE=Release
72+
73+
cmake --build build --parallel
74+
```
75+
Результат: `build/hello` — ELF под целевую ABI.
76+
77+
## Запуск на устройстве / эмуляторе
78+
```bash
79+
adb push build/hello /data/local/tmp/
80+
adb shell "chmod +x /data/local/tmp/hello && /data/local/tmp/hello"
81+
```
82+
Ожидаемый вывод: `Hello Android!`
83+
84+
Если видите ошибки:
85+
- `exec format error` — ABI не совпадает.
86+
- `not found` / `linker` — проверьте `ANDROID_PLATFORM` и `c++_shared`. Можно пушнуть `libc++_shared.so` из `$ANDROID_NDK_PATH/toolchains/llvm/prebuilt/.../sysroot/usr/lib/<abi>/`.
87+
88+
## Быстрый подъём эмулятора (CLI)
89+
Если нет устройства, можно пройти задание на эмуляторе.
90+
91+
1) Убедитесь, что в PATH есть `sdkmanager`, `avdmanager`, `emulator` (ставятся через Android SDK command-line tools).
92+
2) Скачайте системный образ (пример: API 35, x86_64, Google APIs):
93+
```bash
94+
sdkmanager "system-images;android-35;google_apis;x86_64"
95+
```
96+
3) Создайте виртуальное устройство:
97+
```bash
98+
avdmanager create avd -n ov-emul -k "system-images;android-35;google_apis;x86_64"
99+
```
100+
4) Запустите headless:
101+
```bash
102+
emulator -avd ov-emul -no-window -gpu swiftshader_indirect
103+
```
104+
5) Проверьте подключение:
105+
```bash
106+
adb devices
107+
```
108+
Должна появиться строка `emulator-5554 device`.
109+
6) Дальше используйте те же команды `adb push/chmod/run`, что и для физического устройства.
110+
111+
## Сдача
112+
В одном сообщении прикрепите:
113+
1) ABI и API level, на которые собирали (например, `arm64-v8a`, API 33).
114+
2) Команды, которые запускали (коротко, можно скопировать из терминала).
115+
3) Скриншот или лог вывода `Hello Android!`.
116+
4) Если что-то не заработало — что именно и какие действия пробовали.

0 commit comments

Comments
 (0)