Commit | Line | Data |
---|---|---|
6001596e BF |
1 | If you read this file _as_is_, just ignore the funny characters you |
2 | see. It is written in the POD format (see pod/perlpod.pod) which is | |
3 | specially designed to be readable as is. | |
4 | ||
5 | =head1 NAME | |
6 | ||
7 | perlandroid - Perl under Android | |
8 | ||
9 | =head1 SYNOPSIS | |
10 | ||
fbda5f20 BF |
11 | The first portions of this documents contains instructions |
12 | to cross-compile Perl for Android 2.0 and later, using the | |
13 | binaries provided by Google. The latter portion describes how to build | |
14 | perl native using one of the toolchains available on the Play Store. | |
6001596e BF |
15 | |
16 | =head1 DESCRIPTION | |
17 | ||
18 | This document describes how to set up your host environment when | |
fbda5f20 BF |
19 | attempting to build Perl for Android. |
20 | ||
21 | =head1 Cross-Compiling Perl | |
22 | ||
23 | These instructions assume an Unixish build environment on your host system; | |
24 | they've been tested on Linux and OS X, and may work on Cygwin and MSYS. | |
25 | While Google also provides an NDK for Windows, these steps won't work | |
26 | native there, although it may be possible to cross-compile through different | |
27 | means. | |
6001596e BF |
28 | |
29 | =head2 Get the Android Native Development Kit (NDK) | |
30 | ||
31 | You can download the NDK from L<https://developer.android.com/tools/sdk/ndk/index.html>. | |
32 | You'll want the normal, non-legacy version. | |
33 | ||
34 | =head2 Determine the architecture you'll be cross-compiling for | |
35 | ||
36 | There's three possible options: arm-linux-androideabi for ARM, | |
37 | mipsel-linux-android for MIPS, and simply x86 for x86. | |
38 | As of 2014, most Android devices run on ARM, so that is generally a safe bet. | |
39 | ||
40 | With those two in hand, you should add | |
41 | ||
42 | $ANDROID_NDK/toolchains/$TARGETARCH-4.4.3/prebuilt/`uname | tr '[A-Z]' '[a-z]'`-x86_64/bin | |
43 | ||
44 | to your PATH, where $ANDROID_NDK is the location where you unpacked the | |
45 | NDK, and $TARGETARCH is your target's architecture. | |
46 | ||
47 | =head2 Set up a standalone toolchain | |
48 | ||
49 | This creates a working sysroot that we can feed to Configure later. | |
50 | ||
51 | $ export ANDROID_TOOLCHAIN=/tmp/my-toolchain-$TARGETARCH | |
52 | $ export SYSROOT=$ANDROID_TOOLCHAIN/sysroot | |
53 | $ $ANDROID_NDK/build/tools/make-standalone-toolchain.sh \ | |
54 | --platform=android-9 \ | |
55 | --install-dir=$ANDROID_TOOLCHAIN \ | |
56 | --system=`uname | tr '[A-Z]' '[a-z]'`-x86_64 \ | |
57 | --toolchain=$TARGETARCH-4.4.3 | |
58 | ||
59 | =head2 adb or ssh? | |
60 | ||
61 | adb is the Android Debug Bridge. For our purposes, it's basically a way | |
fbda5f20 BF |
62 | of establishing an ssh connection to an Android device without having to |
63 | install anything on the device itself, as long as the device is either on | |
64 | the same local network as the host, or it is connected to the host through | |
65 | USB. | |
6001596e BF |
66 | Perl can be cross-compiled using either adb or a normal ssh connection; |
67 | in general, if you can connect your device to the host using a USB port, | |
fbda5f20 | 68 | or if you don't feel like installing an sshd app on your device, |
6001596e BF |
69 | you may want to use adb, although you may be forced to switch to ssh if |
70 | your device is not rooted and you're unlucky -- more on that later. | |
71 | Alternatively, if you're cross-compiling for an emulator, you'll have to | |
72 | use adb. | |
73 | ||
74 | =head3 adb | |
75 | ||
76 | To use adb, download the Android SDK from L<https://developer.android.com/sdk/index.html>. | |
77 | The "SDK Tools Only" version should suffice -- if you downloaded the ADT | |
78 | Bundle, you can find the sdk under $ADT_BUNDLE/sdk/. | |
79 | ||
80 | Add $ANDROID_SDK/platform-tools to your PATH, which should give you access | |
81 | to adb. You'll now have to find your device's name using 'adb devices', | |
82 | and later pass that to Configure through '-Dtargethost=$DEVICE'. | |
83 | ||
84 | However, before calling Configure, you need to check if using adb is a | |
85 | viable choice in the first place. Because Android doesn't have a /tmp, | |
86 | nor does it allow executables in the sdcard, we need to find somewhere in | |
87 | the device for Configure to put some files in, as well as for the tests | |
88 | to run in. If your device is rooted, then you're good. Try running these: | |
89 | ||
90 | $ export TARGETDIR=/mnt/asec/perl | |
91 | $ adb -s $DEVICE shell "echo sh -c '\"mkdir $TARGETDIR\"' | su --" | |
92 | ||
93 | Which will create the directory we need, and you can move on to the next | |
94 | step. /mnt/asec is mounted as a tmpfs in Android, but it's only | |
95 | accessible to root. | |
96 | ||
97 | If your device is not rooted, you may still be in luck. Try running this: | |
98 | ||
99 | $ export TARGETDIR=/data/local/tmp/perl | |
100 | $ adb -s $DEVICE shell "mkdir $TARGETDIR" | |
101 | ||
102 | If the command works, you can move to the next step, but beware: | |
103 | B<You'll have to remove the directory from the device once you are done! | |
104 | Unlike /mnt/asec, /data/local/tmp may not get automatically garbage | |
105 | collected once you shut off the phone>. | |
106 | ||
107 | If neither of those work, then you can't use adb to cross-compile to your | |
108 | device. Either try rooting it, or go for the ssh route. | |
109 | ||
110 | =head3 ssh | |
111 | ||
112 | To use ssh, you'll need to install and run a sshd app and set it up | |
113 | properly. There are several paid and free apps that do this rather | |
114 | easily, so you should be able to spot one easily. | |
115 | Remember that Perl requires a passwordless connection, so set up a | |
116 | public key. | |
117 | ||
118 | Note that several apps spew crap to stderr every time you | |
119 | connect, which can throw off Configure. You may need to monkeypatch | |
120 | the part of Configure that creates 'run-ssh' to have it discard stderr. | |
121 | ||
122 | Since you're using ssh, you'll have to pass some extra arguments to | |
123 | Configure: -Dtargetrun=ssh -Dtargethost=$TARGETHOST -Dtargetuser=$TARGETUSER -Dtargetport=$TARGETPORT | |
124 | ||
125 | =head2 Configure and beyond | |
126 | ||
127 | With all of the previous done, you're now ready to call Configure. | |
128 | ||
129 | If using adb, a "basic" Configure line will look like this: | |
130 | ||
131 | $ ./Configure -des -Dusedevel -Dusecrosscompile -Dtargetrun=adb \ | |
132 | -Dcc=$TARGETARCH-gcc \ | |
133 | -Dsysroot=$SYSROOT \ | |
134 | -Dtargetdir=$TARGETDIR \ | |
135 | -Dtargethost=$DEVICE | |
136 | ||
137 | If using ssh, it's not too different -- we just change targetrun to ssh, | |
138 | and pass in targetuser and targetport. It ends up looking like this: | |
139 | ||
140 | $ ./Configure -des -Dusedevel -Dusecrosscompile -Dtargetrun=ssh \ | |
141 | -Dcc=$TARGETARCH-gcc \ | |
142 | -Dsysroot=$SYSROOT \ | |
143 | -Dtargetdir=$TARGETDIR \ | |
144 | -Dtargethost="$TARGETHOST" \ | |
145 | -Dtargetuser=$TARGETUSER \ | |
146 | -Dtargetport=$TARGETPORT | |
147 | ||
148 | Now you're ready to run make and make test! | |
149 | ||
150 | As a final word of warning, if you're using adb, make test may appear to | |
151 | hang; this is because it doesn't output anything until it finishes | |
152 | running all tests. You can check its progress by logging into the | |
153 | device, moving to $TARGETDIR, and looking at the file output.stdout. | |
154 | ||
155 | =head3 Notes | |
156 | ||
157 | =over | |
158 | ||
159 | =item * | |
160 | ||
161 | If you are targetting x86 Android, you will have to change $TARGETARCH-gcc | |
162 | to i686-linux-android-gcc. | |
163 | ||
164 | =item * | |
165 | ||
166 | On some older low-end devices -- think early 2.2 era -- some tests, | |
167 | particularly t/re/uniprops, may crash the phone, causing it to turn | |
168 | itself off once, and then back on again. | |
169 | ||
fbda5f20 BF |
170 | =head1 Native Builds |
171 | ||
172 | While Google doesn't provide a native toolchain for Android, | |
173 | you can still get one from the Play Store; for example, there's the CCTools | |
174 | app which you can get for free. | |
175 | Keep in mind that you want a full | |
176 | toolchain; some apps tend to default to installing only a barebones | |
177 | version without some important utilities, like ar or nm. | |
178 | ||
179 | Once you have the toolchain set up properly, the only | |
180 | remaining hurdle is actually locating where in the device it was installed | |
181 | in. For example, CCTools installs its toolchain in | |
182 | /data/data/com.pdaxrom.cctools/root/cctools. With the path in hand, | |
183 | compiling perl is little more than: | |
184 | ||
185 | export SYSROOT=<location of the native toolchain> | |
186 | export LD_LIBRARY_PATH="$SYSROOT/lib:`pwd`:`pwd`/lib:`pwd`/lib/auto:$LD_LIBRARY_PATH" | |
187 | sh Configure -des -Dsysroot=$SYSROOT -Alibpth="/system/lib /vendor/lib" | |
188 | ||
6001596e BF |
189 | =back |
190 | ||
191 | =head1 AUTHOR | |
192 | ||
193 | Brian Fraser <fraserbn@gmail.com> | |
194 | ||
195 | =cut |