adding the embedded Python init/terminate code
This commit is contained in:
		
							parent
							
								
									aad0c5ed98
								
							
						
					
					
						commit
						79bb9552da
					
				
							
								
								
									
										14
									
								
								src/Makefile
									
									
									
									
									
								
							
							
						
						
									
										14
									
								
								src/Makefile
									
									
									
									
									
								
							@ -1,17 +1,21 @@
 | 
				
			|||||||
OBJS=main.o sysinput.o fbinit.o fbprimitive.o log.o gpio.o msg_queue.o time_func.o config.o splash.o
 | 
					OBJS=main.o sysinput.o ep_init.o ep_util.o fbinit.o fbprimitive.o log.o gpio.o msg_queue.o \
 | 
				
			||||||
LIBS=-lbcm2835 -lpthread
 | 
					     time_func.o config.o splash.o
 | 
				
			||||||
CFLAGS=-g -O -DDEBUG_ASSERT
 | 
					LIBS=-lpython3.7m -lcrypt -lbcm2835 -lpthread -ldl -lutil -lm
 | 
				
			||||||
 | 
					CFLAGS=-I/usr/include/python3.7m -Wall -fstack-protector -fwrapv -fno-PIE -g -O3 -DDEBUG_ASSERT
 | 
				
			||||||
 | 
					LDFLAGS=-L/usr/lib/python3.7/config-3.7m-arm-linux-gnueabihf -Xlinker -export-dynamic -Wl,-O1 \
 | 
				
			||||||
 | 
					        -Wl,-Bsymbolic-functions
 | 
				
			||||||
 | 
					
 | 
				
			||||||
all: upiwin
 | 
					all: upiwin
 | 
				
			||||||
 | 
					
 | 
				
			||||||
upiwin: $(OBJS)
 | 
					upiwin: $(OBJS)
 | 
				
			||||||
	gcc -o upiwin $(OBJS) $(LIBS)
 | 
						gcc -o upiwin $(LDFLAGS) $(OBJS) $(LIBS)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
.c.o:
 | 
					.c.o:
 | 
				
			||||||
	gcc -c $(CFLAGS) $<
 | 
						gcc -c $(CFLAGS) $<
 | 
				
			||||||
 | 
					
 | 
				
			||||||
splash.o: splash.bin
 | 
					splash.o: splash.bin
 | 
				
			||||||
	objcopy -I binary -O elf32-littlearm -B arm --rename-section .data=.rodata,alloc,load,readonly,data,contents splash.bin splash.o
 | 
						objcopy -I binary -O elf32-littlearm -B arm --rename-section \
 | 
				
			||||||
 | 
							.data=.rodata,alloc,load,readonly,data,contents splash.bin splash.o
 | 
				
			||||||
 | 
					
 | 
				
			||||||
splash.bin: splash.png ../buildutils/mksplash
 | 
					splash.bin: splash.png ../buildutils/mksplash
 | 
				
			||||||
	../buildutils/mksplash splash.png splash.bin
 | 
						../buildutils/mksplash splash.png splash.bin
 | 
				
			||||||
 | 
				
			|||||||
@ -66,6 +66,7 @@ static void init_defaults(void)
 | 
				
			|||||||
  memset(&Gconfig, 0, sizeof(GLOBAL_CONFIG));
 | 
					  memset(&Gconfig, 0, sizeof(GLOBAL_CONFIG));
 | 
				
			||||||
  Gconfig.framebuffer_device = "/dev/fb1";
 | 
					  Gconfig.framebuffer_device = "/dev/fb1";
 | 
				
			||||||
  Gconfig.touchscreen_device = "/dev/input/touchscreen";
 | 
					  Gconfig.touchscreen_device = "/dev/input/touchscreen";
 | 
				
			||||||
 | 
					  Gconfig.python_loc = "/usr/bin/python3";
 | 
				
			||||||
  Gconfig.button_debounce = 100;
 | 
					  Gconfig.button_debounce = 100;
 | 
				
			||||||
  Gconfig.sys_mq_length = 64;
 | 
					  Gconfig.sys_mq_length = 64;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -9,6 +9,7 @@ typedef void (*PEXITFUNC)(void);
 | 
				
			|||||||
typedef struct tagGLOBAL_CONFIG {
 | 
					typedef struct tagGLOBAL_CONFIG {
 | 
				
			||||||
  PCSTR framebuffer_device;    /* name of frame buffer device */
 | 
					  PCSTR framebuffer_device;    /* name of frame buffer device */
 | 
				
			||||||
  PCSTR touchscreen_device;    /* name of touchscreen device */
 | 
					  PCSTR touchscreen_device;    /* name of touchscreen device */
 | 
				
			||||||
 | 
					  PCSTR python_loc;            /* location of the Python3 executable */
 | 
				
			||||||
  UINT32 button_debounce;      /* minimum time between button up and next button down (ms) */
 | 
					  UINT32 button_debounce;      /* minimum time between button up and next button down (ms) */
 | 
				
			||||||
  UINT32 sys_mq_length;        /* length of system message queue */
 | 
					  UINT32 sys_mq_length;        /* length of system message queue */
 | 
				
			||||||
} GLOBAL_CONFIG;
 | 
					} GLOBAL_CONFIG;
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										104
									
								
								src/ep_init.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										104
									
								
								src/ep_init.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,104 @@
 | 
				
			|||||||
 | 
					#define PY_SSIZE_T_CLEAN
 | 
				
			||||||
 | 
					#include <Python.h>
 | 
				
			||||||
 | 
					#include "scode.h"
 | 
				
			||||||
 | 
					#include "config.h"
 | 
				
			||||||
 | 
					#include "log.h"
 | 
				
			||||||
 | 
					#include "ep_init.h"
 | 
				
			||||||
 | 
					#include "ep_util.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					PCSTR Mod_UPIWIN = "upiwin";              /* name of the primary UPIWIN module */
 | 
				
			||||||
 | 
					PCSTR Mod_UPIWIN_tmp = "upiwin_tmp";      /* name of the temporary UPIWIN module */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static wchar_t *python_name = NULL;       /* location of the Python executable */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static PyObject *upiwin_module = NULL;
 | 
				
			||||||
 | 
					static PyObject *upiwin_tmp_module = NULL;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static PyObject *init_upiwin_module(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static PyObject *init_upiwin_tmp_module(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* used to link the two modules into Python's init table */
 | 
				
			||||||
 | 
					static struct _inittab upiwin_inittab[] = {
 | 
				
			||||||
 | 
					  { Mod_UPIWIN,     init_upiwin_module     },
 | 
				
			||||||
 | 
					  { Mod_UPIWIN_tmp, init_upiwin_tmp_module },
 | 
				
			||||||
 | 
					  { NULL,           NULL                   }
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void epython_cleanup(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					  Py_DECREF(upiwin_tmp_module);
 | 
				
			||||||
 | 
					  upiwin_tmp_module = NULL;
 | 
				
			||||||
 | 
					  Py_DECREF(upiwin_module);
 | 
				
			||||||
 | 
					  upiwin_module = NULL;
 | 
				
			||||||
 | 
					  if (!Py_FinalizeEx())
 | 
				
			||||||
 | 
					    Log(LWARN, "errors encountered when Python uninitialized itself");
 | 
				
			||||||
 | 
					  PyMem_RawFree(python_name);
 | 
				
			||||||
 | 
					  python_name = NULL;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					HRESULT Epython_setup(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					  HRESULT hr;
 | 
				
			||||||
 | 
					  size_t size;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  python_name = Py_DecodeLocale(Gconfig.python_loc, &size);
 | 
				
			||||||
 | 
					  if (!python_name)
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    if (size==(size_t)(-1))
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      Log(LFATAL, "error allocating Python program location");
 | 
				
			||||||
 | 
					      return E_OUTOFMEMORY;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    else
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      Log(LFATAL, "internal error in Py_DecodeLocale");
 | 
				
			||||||
 | 
					      return E_UNEXPECTED;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  Py_SetProgramName(python_name);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if (PyImport_ExtendInittab(upiwin_inittab))
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    Log(LFATAL, "error allocating extended init table");
 | 
				
			||||||
 | 
					    hr = E_OUTOFMEMORY;
 | 
				
			||||||
 | 
					    goto error_0;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  Py_Initialize();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  /* Import the modules */
 | 
				
			||||||
 | 
					  upiwin_module = PyImport_ImportModule(Mod_UPIWIN);
 | 
				
			||||||
 | 
					  if (!upiwin_module)
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    Log(LFATAL, "error importing the upiwin module");
 | 
				
			||||||
 | 
					    hr = Epython_trace_exception();
 | 
				
			||||||
 | 
					    goto error_1;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  upiwin_tmp_module = PyImport_ImportModule(Mod_UPIWIN_tmp);
 | 
				
			||||||
 | 
					  if (!upiwin_tmp_module)
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    Log(LFATAL, "error importing the upiwin_tmp module");
 | 
				
			||||||
 | 
					    hr = Epython_trace_exception();
 | 
				
			||||||
 | 
					    goto error_2;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  hr = Config_exitfunc(epython_cleanup);
 | 
				
			||||||
 | 
					  if (FAILED(hr))
 | 
				
			||||||
 | 
					    epython_cleanup();
 | 
				
			||||||
 | 
					  return hr;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					error_2:
 | 
				
			||||||
 | 
					  Py_DECREF(upiwin_module);
 | 
				
			||||||
 | 
					  upiwin_module = NULL;
 | 
				
			||||||
 | 
					error_1:
 | 
				
			||||||
 | 
					  Py_FinalizeEx();
 | 
				
			||||||
 | 
					error_0:
 | 
				
			||||||
 | 
					  PyMem_RawFree(python_name);
 | 
				
			||||||
 | 
					  python_name = NULL;
 | 
				
			||||||
 | 
					  return hr;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										11
									
								
								src/ep_init.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								src/ep_init.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,11 @@
 | 
				
			|||||||
 | 
					#ifndef __EP_INIT_H_INCLUDED
 | 
				
			||||||
 | 
					#define __EP_INIT_H_INCLUDED
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "wintype.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern PCSTR Mod_UPIWIN;
 | 
				
			||||||
 | 
					extern PCSTR Mod_UPIWIN_tmp;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern HRESULT Epython_setup(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif /* __EP_INIT_H_INCLUDED */
 | 
				
			||||||
							
								
								
									
										44
									
								
								src/ep_util.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										44
									
								
								src/ep_util.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,44 @@
 | 
				
			|||||||
 | 
					#define PY_SSIZE_T_CLEAN
 | 
				
			||||||
 | 
					#include <Python.h>
 | 
				
			||||||
 | 
					#include "scode.h"
 | 
				
			||||||
 | 
					#include "ep_util.h"
 | 
				
			||||||
 | 
					#include "log.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void Epython_log_object(int level, const char *label, PyObject *object)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					  BOOL traced = FALSE;
 | 
				
			||||||
 | 
					  PyObject *repr;
 | 
				
			||||||
 | 
					  PCSTR pstr;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  repr = PyObject_Repr(object);
 | 
				
			||||||
 | 
					  if (repr)
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    ASSERT(PyUnicode_Check(repr));
 | 
				
			||||||
 | 
					    pstr = PyUnicode_AsUTF8(repr);
 | 
				
			||||||
 | 
					    Log(level, "object %s: %s", label, pstr);
 | 
				
			||||||
 | 
					    traced = TRUE;
 | 
				
			||||||
 | 
					    Py_DECREF(repr);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if (!traced)
 | 
				
			||||||
 | 
					    Log(level, "object %s: could not be logged (memory error)", label);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					HRESULT Epython_trace_exception(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					  HRESULT hr = E_FAIL;
 | 
				
			||||||
 | 
					  
 | 
				
			||||||
 | 
					  PyObject *type, *value, *traceback;
 | 
				
			||||||
 | 
					  PyErr_Fetch(&type, &value, &traceback);
 | 
				
			||||||
 | 
					  if (!type)
 | 
				
			||||||
 | 
					    return S_OK;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  Epython_log_object(LERROR, "exception type", type);
 | 
				
			||||||
 | 
					  Epython_log_object(LERROR, "exception value", value);
 | 
				
			||||||
 | 
					  Epython_log_object(LERROR, "exception traceback", value);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  Py_DECREF(type);
 | 
				
			||||||
 | 
					  Py_DECREF(value);
 | 
				
			||||||
 | 
					  Py_DECREF(traceback);
 | 
				
			||||||
 | 
					  return hr;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										11
									
								
								src/ep_util.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								src/ep_util.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,11 @@
 | 
				
			|||||||
 | 
					#ifndef __EP_UTIL_H_INCLUDED
 | 
				
			||||||
 | 
					#define __EP_UTIL_H_INCLUDED
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define PY_SSIZE_T_CLEAN
 | 
				
			||||||
 | 
					#include <Python.h>
 | 
				
			||||||
 | 
					#include "wintype.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern void Epython_log_object(int level, const char *label, PyObject *object);
 | 
				
			||||||
 | 
					extern HRESULT Epython_trace_exception(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif /* __EP_UTIL_H_INCLUDED */
 | 
				
			||||||
@ -8,6 +8,7 @@
 | 
				
			|||||||
#include "fbinit.h"
 | 
					#include "fbinit.h"
 | 
				
			||||||
#include "fbprimitive.h"
 | 
					#include "fbprimitive.h"
 | 
				
			||||||
#include "time_func.h"
 | 
					#include "time_func.h"
 | 
				
			||||||
 | 
					#include "ep_init.h"
 | 
				
			||||||
#include "sysinput.h"
 | 
					#include "sysinput.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void do_draw(void)
 | 
					static void do_draw(void)
 | 
				
			||||||
@ -46,10 +47,12 @@ int main(int argc, char *argv[])
 | 
				
			|||||||
    return EXIT_FAILURE;
 | 
					    return EXIT_FAILURE;
 | 
				
			||||||
  if (FAILED(Gpio_setup()))
 | 
					  if (FAILED(Gpio_setup()))
 | 
				
			||||||
    return EXIT_FAILURE;
 | 
					    return EXIT_FAILURE;
 | 
				
			||||||
 | 
					  if (FAILED(Epython_setup()))
 | 
				
			||||||
 | 
					    return EXIT_FAILURE;
 | 
				
			||||||
  if (FAILED(Sys_enable_input()))
 | 
					  if (FAILED(Sys_enable_input()))
 | 
				
			||||||
    return EXIT_FAILURE;
 | 
					    return EXIT_FAILURE;
 | 
				
			||||||
  Log(LINFO, "Pausing at startup.");
 | 
					  Log(LINFO, "Pausing at startup.");
 | 
				
			||||||
  sleep(3); /* wait to show off splash screen */
 | 
					  sleep(2); /* wait to show off splash screen */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  Fb_clear();
 | 
					  Fb_clear();
 | 
				
			||||||
  /* temporary drawing here */
 | 
					  /* temporary drawing here */
 | 
				
			||||||
 | 
				
			|||||||
@ -64,6 +64,6 @@
 | 
				
			|||||||
#define E_UNEXPECTED                 SCODE_CAST(0x8000FFFF)    /* unexpected error */
 | 
					#define E_UNEXPECTED                 SCODE_CAST(0x8000FFFF)    /* unexpected error */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* UPIWIN-specific errorcodes */
 | 
					/* UPIWIN-specific errorcodes */
 | 
				
			||||||
#define UPIWIN_E_OUTOFRANGE          SCODE_CAST(0x80060000)    /* value out of range */
 | 
					#define UPIWIN_E_INVALIDSTRING       SCODE_CAST(0x80060000)    /* invalid string (decode error) */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#endif /* __SCODE_H_INCLUDED */
 | 
					#endif /* __SCODE_H_INCLUDED */
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user