Norimasa Okamoto
/
pymite
python-on-a-chip online compiler
- http://pymbed.appspot.com/
- https://code.google.com/p/python-on-a-chip/
- http://www.youtube.com/watch?v=Oyqc2bFRW9I
- https://bitbucket.org/va009039/pymbed/
more info: python-on-a-chip
Diff: vm/codeobj.c
- Revision:
- 0:65f1469d6bfb
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/vm/codeobj.c Sat Mar 02 11:54:20 2013 +0000 @@ -0,0 +1,176 @@ +/* +# This file is Copyright 2002 Dean Hall. +# This file is part of the PyMite VM. +# This file is licensed under the MIT License. +# See the LICENSE file for details. +*/ + + +#undef __FILE_ID__ +#define __FILE_ID__ 0x01 + + +/** + * \file + * \brief CodeObj Type + * + * CodeObj type operations. + */ + + +#include "pm.h" + + +/* The image format is defined by co_to_str() in src/tools/pmImgCreator.py */ +PmReturn_t +co_loadFromImg(PmMemSpace_t memspace, uint8_t const **paddr, pPmObj_t *r_pco) +{ + PmReturn_t retval = PM_RET_OK; + pPmObj_t pobj; + pPmCo_t pco = C_NULL; + uint8_t *pchunk; + uint8_t objid; +#ifdef HAVE_DEBUG_INFO + uint8_t objtype; + uint16_t len_str; +#endif /* HAVE_DEBUG_INFO */ + + /* Store ptr to top of code img (less type byte) */ + uint8_t const *pci = *paddr - 1; + + /* Get size of code img */ + uint16_t size = mem_getWord(memspace, paddr); + + /* Allocate a code obj */ + retval = heap_getChunk(sizeof(PmCo_t), &pchunk); + PM_RETURN_IF_ERROR(retval); + pco = (pPmCo_t)pchunk; + + /* Fill in the CO struct */ + OBJ_SET_TYPE(pco, OBJ_TYPE_COB); + pco->co_memspace = memspace; + pco->co_argcount = mem_getByte(memspace, paddr); + pco->co_flags = mem_getByte(memspace, paddr); + pco->co_stacksize = mem_getByte(memspace, paddr); + pco->co_nlocals = mem_getByte(memspace, paddr); + + /* Do not set code image address if image is in RAM. + * CIs in RAM have their image address set in obj_loadFromImgObj() */ + pco->co_codeimgaddr = (memspace == MEMSPACE_RAM) ? C_NULL : pci; + + /* Set these to null in case a GC occurs before their objects are alloc'd */ + pco->co_names = C_NULL; + pco->co_consts = C_NULL; + pco->co_codeaddr = C_NULL; + +#ifdef HAVE_CLOSURES + pco->co_nfreevars = mem_getByte(memspace, paddr); + pco->co_cellvars = C_NULL; +#endif /* HAVE_CLOSURES */ + +#ifdef HAVE_DEBUG_INFO + pco->co_firstlineno = mem_getWord(memspace, paddr); + pco->co_lnotab = C_NULL; + pco->co_filename = C_NULL; +#endif /* HAVE_DEBUG_INFO */ + + /* Load names (tuple obj) */ + heap_gcPushTempRoot((pPmObj_t)pco, &objid); + retval = obj_loadFromImg(memspace, paddr, &pobj); + heap_gcPopTempRoot(objid); + PM_RETURN_IF_ERROR(retval); + pco->co_names = (pPmTuple_t)pobj; + +#ifdef HAVE_DEBUG_INFO + /* Get address in memspace of line number table (including length) */ + objtype = mem_getByte(memspace, paddr); + C_ASSERT(objtype == OBJ_TYPE_STR); + pco->co_lnotab = *paddr; + len_str = mem_getWord(memspace, paddr); + *paddr = *paddr + len_str; + + /* Get address in memspace of CO's filename (excluding length) */ + objtype = mem_getByte(memspace, paddr); + C_ASSERT(objtype == OBJ_TYPE_STR); + len_str = mem_getWord(memspace, paddr); + pco->co_filename = *paddr; + *paddr = *paddr + len_str; +#endif /* HAVE_DEBUG_INFO */ + + /* Load consts (tuple obj) assume it follows names */ + heap_gcPushTempRoot((pPmObj_t)pco, &objid); + retval = obj_loadFromImg(memspace, paddr, &pobj); + heap_gcPopTempRoot(objid); + PM_RETURN_IF_ERROR(retval); + pco->co_consts = (pPmTuple_t)pobj; + +#ifdef HAVE_CLOSURES + heap_gcPushTempRoot((pPmObj_t)pco, &objid); + retval = obj_loadFromImg(memspace, paddr, &pobj); + heap_gcPopTempRoot(objid); + PM_RETURN_IF_ERROR(retval); + + /* Save RAM, don't keep empty tuple */ + if (((pPmTuple_t)pobj)->length == 0) + { + heap_freeChunk(pobj); + } + else + { + pco->co_cellvars = (pPmTuple_t)pobj; + } +#endif /* HAVE_CLOSURES */ + + /* Start of bcode always follows consts */ + pco->co_codeaddr = *paddr; + + /* Set addr to point one past end of img */ + *paddr = pci + size; + + *r_pco = (pPmObj_t)pco; + return PM_RET_OK; +} + + +void +co_rSetCodeImgAddr(pPmCo_t pco, uint8_t const *pimg) +{ + uint8_t i; + + pco->co_codeimgaddr = pimg; + + /* Set the image address for any COs in the constant pool */ + for (i = 0; i < pco->co_consts->length; i++) + { + if (OBJ_GET_TYPE(pco->co_consts->val[i]) == OBJ_TYPE_COB) + { + co_rSetCodeImgAddr((pPmCo_t)pco->co_consts->val[i], pimg); + } + } + + return; +} + + +PmReturn_t +no_loadFromImg(PmMemSpace_t memspace, uint8_t const **paddr, pPmObj_t *r_pno) +{ + PmReturn_t retval = PM_RET_OK; + pPmNo_t pno = C_NULL; + uint8_t *pchunk; + + /* Allocate a code obj */ + retval = heap_getChunk(sizeof(PmNo_t), &pchunk); + PM_RETURN_IF_ERROR(retval); + pno = (pPmNo_t)pchunk; + + /* Fill in the NO struct */ + OBJ_SET_TYPE(pno, OBJ_TYPE_NOB); + pno->no_argcount = mem_getByte(memspace, paddr); + + /* Get index into native fxn table */ + pno->no_funcindx = (int16_t)mem_getWord(memspace, paddr); + + *r_pno = (pPmObj_t)pno; + return PM_RET_OK; +}