Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Diff: src/vm/img.c
- Revision:
- 0:14e5e829dffe
diff -r 000000000000 -r 14e5e829dffe src/vm/img.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/vm/img.c Wed Jul 21 12:50:41 2010 +0000 @@ -0,0 +1,154 @@ +/* +# This file is Copyright 2003, 2006, 2007, 2009 Dean Hall. +# +# This file is part of the PyMite VM. +# The PyMite VM is free software: you can redistribute it and/or modify +# it under the terms of the GNU GENERAL PUBLIC LICENSE Version 2. +# +# The PyMite VM 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. +# A copy of the GNU GENERAL PUBLIC LICENSE Version 2 +# is seen in the file COPYING in this directory. +*/ + + +#undef __FILE_ID__ +#define __FILE_ID__ 0x07 + + +/** + * \file + * \brief Image routines + * + * Created to eliminate a circular include + * among mem, string and obj. + */ + + +#include "pm.h" + + +/* + * Searches for a module's name in a contiguous array of images + * in the given namespace starting at the given address. + * A module's name is stored in the last index of the names tuple of an image. + */ +static PmReturn_t +img_findInPath(uint8_t *cname, uint8_t cnamelen, PmMemSpace_t memspace, + uint8_t const **paddr) +{ + uint8_t const *imgtop; + PmType_t type; + uint16_t len; + int16_t size = 0; + uint8_t i = 0; + + /* Addr is top of img */ + imgtop = *paddr; + + /* Get img's type byte */ + type = (PmType_t)mem_getByte(memspace, paddr); + + /* Search all sequential images */ + while (type == OBJ_TYPE_CIM) + { + /* Use size field to calc addr of next potential img */ + size = mem_getWord(memspace, paddr); + + /* Point to names tuple */ + *paddr = imgtop + CI_NAMES_FIELD; + + /* Ensure it's a tuple */ + type = (PmType_t)mem_getByte(memspace, paddr); + C_ASSERT(type == OBJ_TYPE_TUP); + + /* Scan to last name in tuple (it's the module's name) */ + i = mem_getByte(memspace, paddr) - (uint8_t)1; + for (; i > 0; i--) + { + /* Ensure obj is a string */ + type = (PmType_t)mem_getByte(memspace, paddr); + C_ASSERT(type == OBJ_TYPE_STR); + + /* Skip the length of the string */ + len = mem_getWord(memspace, paddr); + (*paddr) += len; + } + + /* Ensure it's a string */ + type = (PmType_t)mem_getByte(memspace, paddr); + C_ASSERT(type == OBJ_TYPE_STR); + + /* If strings match, return the address of this image */ + if ((cnamelen == mem_getWord(memspace, paddr)) + && (PM_RET_OK == mem_cmpn(cname, cnamelen, memspace, paddr))) + { + *paddr = imgtop; + return PM_RET_OK; + } + + /* Calc imgtop for next iteration */ + imgtop += size; + + /* Point to next potential img */ + *paddr = imgtop; + + /* Check if another img follows this one */ + type = (PmType_t)mem_getByte(memspace, paddr); + } + return PM_RET_NO; +} + + +PmReturn_t +img_findInPaths(pPmObj_t pname, PmMemSpace_t *r_memspace, + uint8_t const **r_imgaddr) +{ + uint8_t i; + PmReturn_t retval = PM_RET_NO; + + /* Search in each path in the paths */ + for (i = 0; i < gVmGlobal.imgPaths.pathcount; i++) + { + *r_imgaddr = gVmGlobal.imgPaths.pimg[i]; + *r_memspace = gVmGlobal.imgPaths.memspace[i]; + retval = img_findInPath(((pPmString_t)pname)->val, + ((pPmString_t)pname)->length, + *r_memspace, r_imgaddr); + if (retval == PM_RET_NO) + { + continue; + } + else if (retval == PM_RET_OK) + { + break; + } + else + { + return retval; + } + } + + return retval; +} + + +PmReturn_t +img_appendToPath(PmMemSpace_t memspace, uint8_t *paddr) +{ + uint8_t i; + + if (gVmGlobal.imgPaths.pathcount >= PM_NUM_IMG_PATHS) + { + return PM_RET_NO; + } + + i = gVmGlobal.imgPaths.pathcount; + + gVmGlobal.imgPaths.memspace[i] = memspace; + gVmGlobal.imgPaths.pimg[i] = paddr; + gVmGlobal.imgPaths.pathcount++; + + return PM_RET_OK; +}