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.
Fork of pymite by
bytearray.c
00001 /* 00002 # This file is Copyright 2010 Dean Hall. 00003 # This file is part of the PyMite VM. 00004 # This file is licensed under the MIT License. 00005 # See the LICENSE file for details. 00006 */ 00007 00008 00009 #undef __FILE_ID__ 00010 #define __FILE_ID__ 0x19 00011 00012 00013 /** 00014 * \file 00015 * \brief VM Bytearray Type 00016 * 00017 * VM Bytearray object type operations. 00018 */ 00019 00020 #include "pm.h" 00021 #ifdef HAVE_BYTEARRAY 00022 00023 00024 #define ROUND_UP_TO_MUL_OF_FOUR(n) n = (((n) + 3) & ~3) 00025 00026 00027 /* Returns a container that can hold at least n bytes */ 00028 static 00029 PmReturn_t 00030 bytes_new(int16_t n, pPmObj_t *r_pobj) 00031 { 00032 PmReturn_t retval = PM_RET_OK; 00033 pPmBytes_t pb = C_NULL; 00034 00035 ROUND_UP_TO_MUL_OF_FOUR(n); 00036 00037 /* Allocate a container */ 00038 retval = heap_getChunk(sizeof(PmBytes_t) + n, (uint8_t **)&pb); 00039 PM_RETURN_IF_ERROR(retval); 00040 OBJ_SET_TYPE(pb, OBJ_TYPE_BYS); 00041 pb->length = n; 00042 00043 *r_pobj = (pPmObj_t)pb; 00044 return retval; 00045 } 00046 00047 00048 /* Returns the int or one-char string as a byte */ 00049 static 00050 PmReturn_t 00051 bytes_getByteFromObj(pPmObj_t pobj, uint8_t *b) 00052 { 00053 PmReturn_t retval = PM_RET_OK; 00054 00055 if (OBJ_GET_TYPE(pobj) == OBJ_TYPE_INT) { 00056 if ((((pPmInt_t)pobj)->val > 255) || (((pPmInt_t)pobj)->val < 0)) { 00057 PM_RAISE(retval, PM_RET_EX_VAL); 00058 return retval; 00059 } 00060 00061 *b = (uint8_t)((pPmInt_t)pobj)->val; 00062 } 00063 00064 else if (OBJ_GET_TYPE(pobj) == OBJ_TYPE_STR) { 00065 if (((pPmString_t)pobj)->length != 1) { 00066 PM_RAISE(retval, PM_RET_EX_VAL); 00067 return retval; 00068 } 00069 *b = ((pPmString_t)pobj)->val[0]; 00070 } 00071 00072 else { 00073 PM_RAISE(retval, PM_RET_EX_TYPE); 00074 } 00075 return retval; 00076 } 00077 00078 00079 PmReturn_t 00080 bytearray_new(pPmObj_t pobj, pPmObj_t *r_pobj) 00081 { 00082 PmReturn_t retval = PM_RET_OK; 00083 pPmBytearray_t pba = C_NULL; 00084 pPmBytes_t pb = C_NULL; 00085 pPmObj_t pitem; 00086 int32_t i; 00087 int16_t n; 00088 uint8_t b; 00089 uint8_t objid; 00090 00091 /* If object is an instance, get the thing it is containing */ 00092 if (OBJ_GET_TYPE(pobj) == OBJ_TYPE_CLI) { 00093 retval = dict_getItem((pPmObj_t)((pPmInstance_t)pobj)->cli_attrs, 00094 PM_NONE, 00095 (pPmObj_t *)&pba); 00096 PM_RETURN_IF_ERROR(retval); 00097 pobj = (pPmObj_t)pba; 00098 } 00099 00100 /* Get the requested length of the new bytearray */ 00101 switch (OBJ_GET_TYPE(pobj)) { 00102 case OBJ_TYPE_INT: 00103 i = ((pPmInt_t)pobj)->val; 00104 if ((i < 0) || (i > 65535)) { 00105 PM_RAISE(retval, PM_RET_EX_VAL); 00106 return retval; 00107 } 00108 n = i; 00109 break; 00110 00111 case OBJ_TYPE_STR: 00112 n = ((pPmString_t)pobj)->length; 00113 break; 00114 00115 case OBJ_TYPE_LST: 00116 n = ((pPmList_t)pobj)->length; 00117 break; 00118 00119 case OBJ_TYPE_TUP: 00120 n = ((pPmTuple_t)pobj)->length; 00121 break; 00122 00123 case OBJ_TYPE_BYA: 00124 n = ((pPmBytearray_t)pobj)->length; 00125 break; 00126 00127 default: 00128 PM_RAISE(retval, PM_RET_EX_TYPE); 00129 return retval; 00130 } 00131 00132 /* Allocate a bytearray */ 00133 retval = heap_getChunk(sizeof(PmBytearray_t), (uint8_t **)&pba); 00134 PM_RETURN_IF_ERROR(retval); 00135 OBJ_SET_TYPE(pba, OBJ_TYPE_BYA); 00136 pba->length = n; 00137 pba->val = C_NULL; 00138 00139 /* Allocate the bytes container */ 00140 heap_gcPushTempRoot((pPmObj_t)pba, &objid); 00141 retval = bytes_new(n, (pPmObj_t *)&pb); 00142 heap_gcPopTempRoot(objid); 00143 PM_RETURN_IF_ERROR(retval); 00144 pba->val = pb; 00145 00146 /* Fill the bytes */ 00147 switch (OBJ_GET_TYPE(pobj)) { 00148 case OBJ_TYPE_INT: 00149 sli_memset((unsigned char *)&(pb->val), '\0', n); 00150 break; 00151 00152 case OBJ_TYPE_BYA: 00153 pitem = (pPmObj_t)((pPmBytearray_t)pobj)->val; 00154 sli_memcpy(&(pb->val[0]), &(((pPmBytes_t)pitem)->val[0]), n); 00155 break; 00156 00157 case OBJ_TYPE_STR: 00158 sli_memcpy(&(pb->val[0]), &(((pPmString_t)pobj)->val[0]), n); 00159 break; 00160 00161 case OBJ_TYPE_LST: 00162 case OBJ_TYPE_TUP: 00163 for (i = 0; i < n; i++) { 00164 retval = seq_getSubscript(pobj, i, &pitem); 00165 PM_RETURN_IF_ERROR(retval); 00166 retval = bytes_getByteFromObj(pitem, &b); 00167 PM_RETURN_IF_ERROR(retval); 00168 pb->val[i] = b; 00169 } 00170 break; 00171 } 00172 00173 *r_pobj = (pPmObj_t)pba; 00174 return retval; 00175 } 00176 00177 00178 PmReturn_t 00179 bytearray_getItem(pPmObj_t pobj, int16_t index, pPmObj_t *r_pobj) 00180 { 00181 PmReturn_t retval = PM_RET_OK; 00182 pPmBytearray_t pba; 00183 pPmBytes_t pb; 00184 int32_t n; 00185 00186 pba = (pPmBytearray_t)pobj; 00187 00188 /* Adjust a negative index */ 00189 if (index < 0) { 00190 index += pba->length; 00191 } 00192 00193 /* Check the bounds of the index */ 00194 if ((index < 0) || (index >= pba->length)) { 00195 PM_RAISE(retval, PM_RET_EX_INDX); 00196 return retval; 00197 } 00198 00199 /* Create int from byte at index */ 00200 pb = pba->val; 00201 n = (int32_t)pb->val[index]; 00202 retval = int_new(n, r_pobj); 00203 00204 return retval; 00205 } 00206 00207 00208 PmReturn_t 00209 bytearray_setItem(pPmObj_t pba, int16_t index, pPmObj_t pobj) 00210 { 00211 PmReturn_t retval; 00212 pPmBytes_t pb; 00213 uint8_t b = 0; 00214 00215 /* Adjust a negative index */ 00216 if (index < 0) { 00217 index += ((pPmBytearray_t)pba)->length; 00218 } 00219 00220 /* Check the bounds of the index */ 00221 if ((index < 0) || (index >= ((pPmBytearray_t)pba)->length)) { 00222 PM_RAISE(retval, PM_RET_EX_INDX); 00223 return retval; 00224 } 00225 00226 /* Set the item */ 00227 retval = bytes_getByteFromObj(pobj, &b); 00228 pb = ((pPmBytearray_t)pba)->val; 00229 pb->val[index] = b; 00230 00231 return retval; 00232 } 00233 00234 00235 #ifdef HAVE_PRINT 00236 PmReturn_t 00237 bytearray_print(pPmObj_t pobj) 00238 { 00239 PmReturn_t retval; 00240 pPmBytes_t pb; 00241 00242 obj_print(PM_BYTEARRAY_STR, C_FALSE, C_FALSE); 00243 plat_putByte('('); 00244 plat_putByte('b'); 00245 pb = ((pPmBytearray_t)pobj)->val; 00246 retval = string_printFormattedBytes(&(pb->val[0]), 00247 C_TRUE, 00248 ((pPmBytearray_t)pobj)->length); 00249 plat_putByte(')'); 00250 return retval; 00251 } 00252 #endif /* HAVE_PRINT */ 00253 #endif /* HAVE_BYTEARRAY */
Generated on Tue Jul 12 2022 21:25:46 by
1.7.2
