summaryrefslogtreecommitdiff
path: root/cross
diff options
context:
space:
mode:
authorPo Lu <luangruo@yahoo.com>2023-03-02 18:31:35 +0800
committerPo Lu <luangruo@yahoo.com>2023-03-02 18:31:35 +0800
commit960230d88d3c063ad51f91de076dd2b4a7b88ca1 (patch)
tree5a9c421aa3709a76e9351ba7c40ed0f52a2ab923 /cross
parent951bdd021f51959649bf0bff9b16fde00c23f1a7 (diff)
downloademacs-960230d88d3c063ad51f91de076dd2b4a7b88ca1.tar.gz
Summary: Update Android port
* INSTALL: Document where to find Android installation instructions. * configure.ac (CHECK_LISP_OBJECT_TYPE): Pacify -Wsuggest-attribute=noreturn only on Android. * cross/ndk-build/README: New file. * doc/emacs/android.texi (Android): * doc/emacs/emacs.texi (Top): * doc/emacs/input.texi (Other Input Devices): Untabify menus. * etc/NEWS: Move INSTALL.android to java/INSTALL. * java/INSTALL: New file. * java/README: * src/coding.c (from_unicode_buffer): Make Android specific code only build on Android.
Diffstat (limited to 'cross')
-rw-r--r--cross/ndk-build/README352
1 files changed, 352 insertions, 0 deletions
diff --git a/cross/ndk-build/README b/cross/ndk-build/README
new file mode 100644
index 00000000000..9c4ffdf437a
--- /dev/null
+++ b/cross/ndk-build/README
@@ -0,0 +1,352 @@
+NDK BUILD SYSTEM IMPLEMENTATION
+
+Copyright (C) 2023 Free Software Foundation, Inc.
+See the end of the file for license conditions.
+
+Emacs implements ndk-build itself, because the version that comes with
+the Android NDK is not easy to use from another Makefile, and keeps
+accumulating incompatible changes.
+
+The Emacs implementation of ndk-build consists of one m4 file:
+
+ m4/ndk-build.m4
+
+four Makefiles in build-aux, run during configure:
+
+ build-aux/ndk-build-helper-1.mk
+ build-aux/ndk-build-helper-2.mk
+ build-aux/ndk-build-helper-3.mk
+ build-aux/ndk-build-helper.mk
+
+one awk script in build-awx, run during configure:
+
+ build-aux/ndk-module-extract.awk
+
+seven Makefiles in cross/ndk-build,
+
+ cross/ndk-build/ndk-build-shared-library.mk
+ cross/ndk-build/ndk-build-static-library.mk
+ cross/ndk-build/ndk-build-executable.mk
+ cross/ndk-build/ndk-clear-vars.mk
+ cross/ndk-build/ndk-prebuilt-shared-library.mk
+ cross/ndk-build/ndk-prebuilt-static-library.mk
+ cross/ndk-build/ndk-resolve.mk
+
+and finally, two more Makefiles in cross/ndk-build, generated by
+configure:
+
+ cross/ndk-build/Makefile (generated from cross/ndk-build/Makefile.in)
+ cross/ndk-build/ndk-build.mk (generated from cross/ndk-build/ndk-build.mk.in)
+
+m4/ndk-build.m4 is a collection of macros which are used by the
+configure script to set up the ndk-build system, look for modules, add
+the appropriate options to LIBS and CFLAGS, and generate the Makefiles
+necessary to build the rest of Emacs.
+
+Immediately after determining the list of directories in which to look
+for ``Android.mk'' files, the version and type of Android system being
+built for, configure calls:
+
+ ndk_INIT([$android_abi], [$ANDROID_SDK], [cross/ndk-build])
+
+This expands to a sequence of shell script that enumerates all of the
+Android.mk files specified in "$with_ndk_path", sets up some shell
+functions used by the rest of the ndk-build code run by the configure
+script, and teaches the ndk-build system that the Makefiles to be
+generated are found in the directory "cross/ndk-build/Makefile".
+
+When configure is cross-compiling for Android, the macro
+EMACS_CHECK_MODULES will expand to the macro ndk_CHECK_MODULES,
+instead of pkg-config.m4's PKG_CHECK_MODULES. Thus, the following
+code:
+
+ EMACS_CHECK_MODULES([PNG], [libpng >= 1.0.0])
+
+will actually expand to:
+
+ ndk_CHECK_MODULES([PNG], [libpng >= 1.0.0], [HAVE_PNG=yes],
+ [HAVE_PNG=no])
+
+which in turn expands to a sequence shell script that first invokes:
+
+ make -f build-aux/ndk-build-helper.mk
+
+for each ``Android.mk'' file found by ndk_INIT, with the following
+variables given to Make:
+
+ EMACS_SRCDIR=. # the source directory (in which configure is running)
+ EMACS_ABI=$ndk_ABI # this is the $android_abi given to ndk_INIT
+ ANDROID_MAKEFILE="/opt/android/libpng/Android.mk"
+ ANDROID_MODULE_DIRECTORY="/opt/android/libpng"
+ NDK_BUILD_DIR="$ndk_DIR" # this is the directory given as to ndk_INIT
+
+build-aux/ndk-build-helper.mk will then evaluate the contents
+$(ANDROID_MAKEFILE), the ``Android.mk'' file, for the first time. The
+purpose of this evaluation is to establish a list of packages (or
+modules) provided by the ``Android.mk'' file, and the corresponding
+Makefile targets and compiler and linker flags required to build and
+link to those tagets.
+
+Before doing so, build-aux/ndk-build-helper.mk will define several
+variables and functions required by all ``Android.mk'' files. The
+most important of these are:
+
+ my-dir # the directory containing the Android.mk file.
+ BUILD_SHARED_LIBRARY # build-aux/ndk-build-helper-1.mk
+ BUILD_STATIC_LIBRARY # build-aux/ndk-build-helper-2.mk
+ BUILD_EXECUTABLE # build-aux/ndk-build-helper-3.mk
+ CLEAR_VARS # build-aux/ndk-build-helper-4.mk
+
+Then, ``Android.mk'' will include $(CLEAN_VARS), possibly other
+``Android.mk'' files, (to clear variables previously set), set several
+variables describing each module to the ndk-build system, and include
+one of $(BUILD_SHARED_LIBRARY), $(BUILD_STATIC_LIBRARY) and
+$(BUILD_EXECUTABLE).
+
+Each one of those three scripts will then read from the variables set
+by ``Android.mk'', resolve dependencies, and print out some text
+describing the module to Emacs. For example, the shared library
+module "libpng" results in the following text being printed:
+
+Building shared
+libpng
+/opt/android/libpng/png.c /opt/android/libpng/pngerror.c /opt/android/libpng/pngget.c /opt/android/libpng/pngmem.c /opt/android/libpng/pngpread.c /opt/android/libpng/pngread.c /opt/android/libpng/pngrio.c /opt/android/libpng/pngrtran.c /opt/android/libpng/pngrutil.c /opt/android/libpng/pngset.c /opt/android/libpng/pngtrans.c /opt/android/libpng/pngwio.c /opt/android/libpng/pngwrite.c /opt/android/libpng/pngwtran.c /opt/android/libpng/pngwutil.c
+-I/opt/android/libpng
+
+ -L/opt/emacs/cross/ndk-build -l:libpng_emacs.so
+libpng_emacs.so
+End
+
+The output is arranged as follows:
+
+ - The first line consists of the word ``Building'', followed by
+ either ``shared'', ``static'', or ``executable'', depending on
+ what type of module being built.
+
+ - The second line consists of the name of the module currently being
+ built.
+
+ - The third line consists of all of the source code files comprising
+ the module.
+
+ - The fourth line consists of the text that has to be added to
+ CFLAGS in order to find the includes associated with the module.
+
+ - The fifth line consists of the text that has to be added to LIBS
+ in order to link with this module and all of its dependencies.
+
+ - The sixth line consists of the Make targets (more on this later)
+ that will build the final shared object or library archive of this
+ module, along with all of its dependencies.
+
+ - The seventh line is either empty, or the name of a dependency on
+ the C++ standard library. This is used to determine whether or
+ not Emacs will include the C++ standard library in the application
+ package.
+
+The output from Make is given to an awk script,
+build-aux/ndk-module-extract.awk. This is responsible for parsing the
+that output and filtering out modules other than what is being built:
+
+ awk -f build-aux/ndk-module-extract.awk MODULE=libpng
+
+eventually generating this section of shell script:
+
+module_name=libpng
+module_kind=shared
+module_src="/opt/android/libpng/png.c /opt/android/libpng/pngerror.c /opt/android/libpng/pngget.c /opt/android/libpng/pngmem.c /opt/android/libpng/pngpread.c /opt/android/libpng/pngread.c /opt/android/libpng/pngrio.c /opt/android/libpng/pngrtran.c /opt/android/libpng/pngrutil.c /opt/android/libpng/pngset.c /opt/android/libpng/pngtrans.c /opt/android/libpng/pngwio.c /opt/android/libpng/pngwrite.c /opt/android/libpng/pngwtran.c /opt/android/libpng/pngwutil.c"
+module_includes="-I/opt/android/libpng"
+module_cflags=""
+module_ldflags=" -L/opt/emacs/cross/ndk-build -l:libpng_emacs.so"
+module_target="libpng_emacs.so"
+module_cxx_deps=""
+module_imports=""
+
+which is then evaluated by `configure'. Once the variable
+`module_name' is set, configure apends the remaining
+$(module_includes), $(module_cflags) and $(module_ldflags) to the
+module's CFLAGS and LIBS variables, and appends the list of Makefile
+targets specified to the variable NDK_BUILD_MODULES.
+
+In some cases, an ``Android.mk'' file may chose to import a module
+defined in ``--with-ndk-path'', but not defined inside its own
+``Android.mk'' file. build-aux/ndk-build-helper.mk defines the
+`import-module' function to add the modules being imported to a
+variable, which is then printed out after ``ndk-build-helper.mk''
+completes. For example, libxml2 imports the ``libicucc'' module,
+which results in the following text being printed:
+
+Building shared
+libxml2
+/home/oldosfan/libxml2/SAX.c /home/oldosfan/libxml2/entities.c /home/oldosfan/libxml2/encoding.c /home/oldosfan/libxml2/error.c /home/oldosfan/libxml2/parserInternals.c /home/oldosfan/libxml2/parser.c /home/oldosfan/libxml2/tree.c /home/oldosfan/libxml2/hash.c /home/oldosfan/libxml2/list.c /home/oldosfan/libxml2/xmlIO.c /home/oldosfan/libxml2/xmlmemory.c /home/oldosfan/libxml2/uri.c /home/oldosfan/libxml2/valid.c /home/oldosfan/libxml2/xlink.c /home/oldosfan/libxml2/debugXML.c /home/oldosfan/libxml2/xpath.c /home/oldosfan/libxml2/xpointer.c /home/oldosfan/libxml2/xinclude.c /home/oldosfan/libxml2/DOCBparser.c /home/oldosfan/libxml2/catalog.c /home/oldosfan/libxml2/globals.c /home/oldosfan/libxml2/threads.c /home/oldosfan/libxml2/c14n.c /home/oldosfan/libxml2/xmlstring.c /home/oldosfan/libxml2/buf.c /home/oldosfan/libxml2/xmlregexp.c /home/oldosfan/libxml2/xmlschemas.c /home/oldosfan/libxml2/xmlschemastypes.c /home/oldosfan/libxml2/xmlunicode.c /home/oldosfan/libxml2/xmlreader.c /home/oldosfan/libxml2/relaxng.c /home/oldosfan/libxml2/dict.c /home/oldosfan/libxml2/SAX2.c /home/oldosfan/libxml2/xmlwriter.c /home/oldosfan/libxml2/legacy.c /home/oldosfan/libxml2/chvalid.c /home/oldosfan/libxml2/pattern.c /home/oldosfan/libxml2/xmlsave.c /home/oldosfan/libxml2/xmlmodule.c /home/oldosfan/libxml2/schematron.c /home/oldosfan/libxml2/SAX.c /home/oldosfan/libxml2/entities.c /home/oldosfan/libxml2/encoding.c /home/oldosfan/libxml2/error.c /home/oldosfan/libxml2/parserInternals.c /home/oldosfan/libxml2/parser.c /home/oldosfan/libxml2/tree.c /home/oldosfan/libxml2/hash.c /home/oldosfan/libxml2/list.c /home/oldosfan/libxml2/xmlIO.c /home/oldosfan/libxml2/xmlmemory.c /home/oldosfan/libxml2/uri.c /home/oldosfan/libxml2/valid.c /home/oldosfan/libxml2/xlink.c /home/oldosfan/libxml2/debugXML.c /home/oldosfan/libxml2/xpath.c /home/oldosfan/libxml2/xpointer.c /home/oldosfan/libxml2/xinclude.c /home/oldosfan/libxml2/DOCBparser.c /home/oldosfan/libxml2/catalog.c /home/oldosfan/libxml2/globals.c /home/oldosfan/libxml2/threads.c /home/oldosfan/libxml2/c14n.c /home/oldosfan/libxml2/xmlstring.c /home/oldosfan/libxml2/buf.c /home/oldosfan/libxml2/xmlregexp.c /home/oldosfan/libxml2/xmlschemas.c /home/oldosfan/libxml2/xmlschemastypes.c /home/oldosfan/libxml2/xmlunicode.c /home/oldosfan/libxml2/xmlreader.c /home/oldosfan/libxml2/relaxng.c /home/oldosfan/libxml2/dict.c /home/oldosfan/libxml2/SAX2.c /home/oldosfan/libxml2/xmlwriter.c /home/oldosfan/libxml2/legacy.c /home/oldosfan/libxml2/chvalid.c /home/oldosfan/libxml2/pattern.c /home/oldosfan/libxml2/xmlsave.c /home/oldosfan/libxml2/xmlmodule.c /home/oldosfan/libxml2/schematron.c
+
+
+ -L/home/oldosfan/emacs-dev/emacs-android/cross/ndk-build -l:libxml2_emacs.so -l:libicuuc_emacs.so
+libxml2_emacs.so libicuuc_emacs.so
+End
+Start Imports
+libicuuc
+End Imports
+
+Upon encountering the ``Start Imports'' section,
+build-aux/ndk-module-extract.awk collects all imports until it
+encounters the line ``End Imports'', at which point it prints:
+
+module_imports="libicuuc"
+
+Then, if the list of imports is not empty, ndk_CHECK_MODULES
+additionally calls itself for each import before appending the
+module's own ``Android.mk'', ensuring that the module's imported
+dependencies are included by $ndk_DIR/Makefile before itself.
+
+Finally, immediately before generating src/Makefile.android, configure
+expands:
+
+ ndk_CONFIG_FILES
+
+to generate $ndk_DIR/Makefile and $ndk_DIR/ndk-build.mk.
+
+Now, the $ndk_DIR directory is set up to build all modules upon which
+depends, and $ndk_DIR/ndk-build.mk includes a list of files required
+to link Emacs, along with the rules to chdir into $ndk_DIR in order to
+build them.
+
+$ndk_DIR/ndk-build.mk is included by cross/src/Makefile
+(Makefile.android) and java/Makefile. It defines three different
+variables:
+
+ NDK_BUILD_MODULES the file names of all modules to be built.
+ NDK_BUILD_STATIC absolute names of all library archives
+ to be built.
+ NDK_BUILD_SHARED absolute names of all shared libraries to
+ be built.
+
+and then proceeds to define rules to build each of the modules in
+$(NDK_BUILD_MODULES).
+
+cross/src/Makefile arranges to have all dependencies of Emacs not
+already built built before linking ``libemacs.so'' with them.
+
+java/Makefile additionally arranges to have all shared object
+dependencies built before the application package is built, which is
+normally redundant because they should have already been built before
+linking ``libemacs.so''.
+
+Building the modules is performed through $ndk_DIR/Makefile, which
+contains the actual implementation of the ``ndk-build'' build system.
+First, it defines certain variables constant within the ``ndk-build''
+build system, such as the files included by ``Android.mk'' to build
+shared or static libraries, and CLEAR_VARS. The most important of
+these are:
+
+ CLEAR_VARS cross/ndk-build/ndk-clear-vars.mk
+ BUILD_EXECUTABLE cross/ndk-build/ndk-build-executable.mk
+ BUILD_SHARED_LIBRARY cross/ndk-build/ndk-build-shared-library.mk
+ BUILD_STATIC_LIBRARY cross/ndk-build/ndk-build-static-library.mk
+ PREBUILT_SHARED_LIBRARY cross/ndk-build/ndk-prebuilt-shared-library.mk
+ PREBUILT_STATIC_LIBRARY cross/ndk-build/ndk-prebuilt-static-library.mk
+
+Then, it loads each Emacs dependency's ``Android.mk'' file. For each
+module defined there, ``Android.mk'' includes $(CLEAR_VARS) to unset
+all variables specific to each module, and then includes
+$(BUILD_SHARED_LIBRARY) or $(BUILD_STATIC_LIBRARY) for each shared or
+static library module.
+
+This results in cross/ndk-build/ndk-build-shared-library.mk or
+cross/ndk-build/ndk-build-static-library being included, just like the
+Makefiles in build-aux were inside the configure script.
+
+Each one of those two scripts then defines rules to build all of the
+object files associated with the module, and then link or archive
+them. The name under which the module is linked is the same as the
+Make target found on the sixth line of output from
+build-aux/ndk-build-helper.mk.
+
+In doing so, they both include the file ndk-resolve.mk.
+ndk-resolve.mk is expected to recursively add all of the exported
+CFLAGS and includes of any dependencies to the compiler and linker
+command lines for the module being built.
+
+When building a shared library module, ndk-resolve.mk is also expected
+to define the variables NDK_LOCAL_A_NAMES_$(LOCAL_MODULE) and
+NDK_WHOLE_A_NAMES_$(LOCAL_MODULE), containing all static library
+dependencies' archive files. They are to be linked in to the
+resulting shared object file.
+
+This is done by including cross/ndk-build/ndk-resolve.mk each time a
+shared or static library module is going to be built. How is this
+done?
+
+First, ndk-resolve.mk saves the LOCAL_PATH, LOCAL_STATIC_LIBRARIES,
+LOCAL_SHARED_LIBRARIES, LOCAL_EXPORT_CFLAGS and
+LOCAL_EXPORT_C_INCLUDES from the module.
+
+Next, ndk-resolve loops through the dependencies the module has
+specified, appending its CFLAGS and includes to the command line for
+the current module.
+
+Then, that process is repeated for each such dependency which has not
+already been resolved, until all dependencies have been resolved.
+
+libpng is a very simple module, providing only a single shared object
+module. This module is named libpng_emacs.so and is eventually built
+and packaged into the library directory of the Emacs application
+package. Now, let us look at a more complex module, libwebp:
+
+
+
+When built with libwebp, Emacs depends on a single library,
+libwebpdemux. This library is named ``libwebpdemux'' on Unix systems,
+and that is the name by which it is found with pkg-config.
+
+However, the library's module is only named ``webpdemux'' on Android.
+When ndk_CHECK_MODULES begins to look for a module, it first tries to
+see if its name is found in the variable `ndk_package_map', which was
+set inside ndk_INIT. In this case, it finds the following word:
+
+ libwebpdemux:webpdemux
+
+and immediately replaces ``libwebpdemux'' with ``webpdemux''.
+
+Then, it locates the ``Android.mk'' file containing a static library
+module named webpdemux and gives the output from
+build-aux/ndk-build-helper.mk to the awk script, resulting in:
+
+module_name=webpdemux
+module_kind=static
+module_src="/opt/android/webp/src/demux/anim_decode.c /opt/android/webp/src/demux/demux.c"
+module_includes="-I/opt/android/webp/src"
+module_cflags=""
+module_ldflags=" cross/ndk-build/libwebpdemux.a cross/ndk-build/libwebp.a cross/ndk-build/libwebpdecoder_static.a "
+module_target="libwebpdemux.a libwebp.a libwebpdecoder_static.a"
+
+The attentive reader will notice that in addition to the
+``libwebpdemux.a'' archive associated with the ``webpdemux'' library,
+Emacs has been made to link with two additional libraries. This is
+because the ``webpdemux'' module specifies a dependency on the
+``webp'' module (defined in the same Android.mk).
+build-aux/ndk-build-helper.mk resolved that dependency, noticing that
+it in turn specified another dependency on ``webpdecoder_static'',
+which in turn was added to the linker command line and list of targets
+to build.
+
+As a result, all three dependencies will be built and linked to Emacs,
+instead of just the single ``webpdemux'' dependency that was
+specified.
+
+
+
+This file is part of GNU Emacs.
+
+GNU Emacs is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+GNU Emacs is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Emacs. If not, see <https://www.gnu.org/licenses/>.