|
3 | 3 | #include <android/log.h>
|
4 | 4 | #include <android_native_app_glue.h>
|
5 | 5 |
|
6 |
| -#define LOGI(...) ((void)__android_log_print(ANDROID_LOG_INFO, "native-activity", __VA_ARGS__)) |
7 |
| -#define LOGW(...) ((void)__android_log_print(ANDROID_LOG_WARN, "native-activity", __VA_ARGS__)) |
| 6 | +#define LOGI(...) ((void)__android_log_print(ANDROID_LOG_INFO, "python", __VA_ARGS__)) |
| 7 | +#define LOGW(...) ((void)__android_log_print(ANDROID_LOG_WARN, "python", __VA_ARGS__)) |
| 8 | + |
| 9 | +#define PY_SSIZE_T_CLEAN |
| 10 | +#include "Python.h" |
| 11 | +#ifndef Py_PYTHON_H |
| 12 | + #error Python headers needed to compile C extensions, please install development version of Python. |
| 13 | +#endif |
| 14 | + |
| 15 | +static PyObject *androidembed_log(PyObject *self, PyObject *args) { |
| 16 | + char *logstr = NULL; |
| 17 | + if (!PyArg_ParseTuple(args, "s", &logstr)) { |
| 18 | + return NULL; |
| 19 | + } |
| 20 | + __android_log_print(ANDROID_LOG_INFO, "python", "%s", logstr); |
| 21 | + Py_RETURN_NONE; |
| 22 | +} |
| 23 | + |
| 24 | +static PyMethodDef AndroidEmbedMethods[] = { |
| 25 | + {"log", androidembed_log, METH_VARARGS, |
| 26 | + "Log on android platform"}, |
| 27 | + {NULL, NULL, 0, NULL} |
| 28 | +}; |
| 29 | + |
| 30 | +PyMODINIT_FUNC initandroidembed(void) { |
| 31 | + (void) Py_InitModule("androidembed", AndroidEmbedMethods); |
| 32 | +} |
| 33 | + |
| 34 | +int file_exists(const char * filename) |
| 35 | +{ |
| 36 | + FILE *file; |
| 37 | + if (file = fopen(filename, "r")) { |
| 38 | + fclose(file); |
| 39 | + return 1; |
| 40 | + } |
| 41 | + return 0; |
| 42 | +} |
8 | 43 |
|
9 | 44 |
|
10 | 45 | void android_main(struct android_app* state) {
|
11 | 46 | app_dummy();
|
12 |
| - LOGI("android_main: starting minimal bootstrap."); |
| 47 | + LOGI("Starting minimal bootstrap."); |
| 48 | + |
| 49 | + char *env_argument = NULL; |
| 50 | + FILE *fd; |
| 51 | + |
| 52 | + LOGI("Initialize Python for Android"); |
| 53 | + //env_argument = getenv("ANDROID_ARGUMENT"); |
| 54 | + //setenv("ANDROID_APP_PATH", env_argument, 1); |
| 55 | + //setenv("PYTHONVERBOSE", "2", 1); |
| 56 | + Py_SetProgramName("python-android"); |
| 57 | + Py_Initialize(); |
| 58 | + //PySys_SetArgv(argc, argv); |
| 59 | + |
| 60 | + /* ensure threads will work. |
| 61 | + */ |
| 62 | + PyEval_InitThreads(); |
| 63 | + |
| 64 | + /* our logging module for android |
| 65 | + */ |
| 66 | + initandroidembed(); |
| 67 | + |
| 68 | + /* inject our bootstrap code to redirect python stdin/stdout |
| 69 | + * replace sys.path with our path |
| 70 | + */ |
| 71 | + #if 0 |
| 72 | + PyRun_SimpleString( |
| 73 | + "import sys, posix\n" \ |
| 74 | + "private = posix.environ['ANDROID_PRIVATE']\n" \ |
| 75 | + "argument = posix.environ['ANDROID_ARGUMENT']\n" \ |
| 76 | + "sys.path[:] = [ \n" \ |
| 77 | + " private + '/lib/python27.zip', \n" \ |
| 78 | + " private + '/lib/python2.7/', \n" \ |
| 79 | + " private + '/lib/python2.7/lib-dynload/', \n" \ |
| 80 | + " private + '/lib/python2.7/site-packages/', \n" \ |
| 81 | + " argument ]\n") |
| 82 | + #endif |
| 83 | + |
| 84 | + PyRun_SimpleString( |
| 85 | + "import sys, androidembed\n" \ |
| 86 | + "class LogFile(object):\n" \ |
| 87 | + " def __init__(self):\n" \ |
| 88 | + " self.buffer = ''\n" \ |
| 89 | + " def write(self, s):\n" \ |
| 90 | + " s = self.buffer + s\n" \ |
| 91 | + " lines = s.split(\"\\n\")\n" \ |
| 92 | + " for l in lines[:-1]:\n" \ |
| 93 | + " androidembed.log(l)\n" \ |
| 94 | + " self.buffer = lines[-1]\n" \ |
| 95 | + " def flush(self):\n" \ |
| 96 | + " return\n" \ |
| 97 | + "sys.stdout = sys.stderr = LogFile()\n" \ |
| 98 | + "import site; print site.getsitepackages()\n"\ |
| 99 | + "print 'Android path', sys.path\n" \ |
| 100 | + "print 'Android kivy bootstrap done. __name__ is', __name__"); |
| 101 | + |
| 102 | + /* run it ! |
| 103 | + */ |
| 104 | + LOGI("Run user program, change dir and execute main.py"); |
| 105 | + //chdir(env_argument); |
| 106 | + |
| 107 | + /* search the initial main.py |
| 108 | + */ |
| 109 | + char *main_py = "main.pyo"; |
| 110 | + if ( file_exists(main_py) == 0 ) { |
| 111 | + if ( file_exists("main.py") ) |
| 112 | + main_py = "main.py"; |
| 113 | + else |
| 114 | + main_py = NULL; |
| 115 | + } |
| 116 | + |
| 117 | + if ( main_py == NULL ) { |
| 118 | + LOGW("No main.pyo / main.py found."); |
| 119 | + return; |
| 120 | + } |
| 121 | + |
| 122 | + fd = fopen(main_py, "r"); |
| 123 | + if ( fd == NULL ) { |
| 124 | + LOGW("Open the main.py(o) failed"); |
| 125 | + return; |
| 126 | + } |
| 127 | + |
| 128 | + /* run python ! |
| 129 | + */ |
| 130 | + PyRun_SimpleFile(fd, main_py); |
| 131 | + |
| 132 | + if (PyErr_Occurred() != NULL) { |
| 133 | + PyErr_Print(); /* This exits with the right code if SystemExit. */ |
| 134 | + if (Py_FlushLine()) |
| 135 | + PyErr_Clear(); |
| 136 | + } |
| 137 | + |
| 138 | + /* close everything |
| 139 | + */ |
| 140 | + Py_Finalize(); |
| 141 | + fclose(fd); |
| 142 | + |
| 143 | + LOGW("Python for android ended."); |
13 | 144 | }
|
0 commit comments