Norimasa Okamoto
/
pymite
python-on-a-chip online compiler
Embed:
(wiki syntax)
Show/hide line numbers
pmstdlib_nat.cpp
Go to the documentation of this file.
00001 #undef __FILE_ID__ 00002 #define __FILE_ID__ 0x0A 00003 /** 00004 * PyMite std native function file 00005 * 00006 * automatically created by pmImgCreator.py 00007 * on Sat Mar 02 20:27:03 2013 00008 * 00009 * DO NOT EDIT THIS FILE. 00010 * ANY CHANGES WILL BE LOST. 00011 * 00012 * @file pmstdlib_nat.cpp 00013 */ 00014 00015 #define __IN_LIBNATIVE_C__ 00016 #include "pm.h" 00017 00018 /* From: ../../lib/string.py */ 00019 #include <stdlib.h> 00020 #include <string.h> 00021 00022 PmReturn_t 00023 nat_00___bi_chr(pPmFrame_t *ppframe) 00024 { 00025 00026 pPmObj_t ps; 00027 pPmObj_t pn; 00028 int32_t n; 00029 PmReturn_t retval; 00030 00031 /* If wrong number of args, raise TypeError */ 00032 if (NATIVE_GET_NUM_ARGS() != 1) 00033 { 00034 PM_RAISE(retval, PM_RET_EX_TYPE); 00035 return retval; 00036 } 00037 00038 /* Raise TypeError if arg is not an int */ 00039 pn = NATIVE_GET_LOCAL(0); 00040 if (OBJ_GET_TYPE(pn) != OBJ_TYPE_INT) 00041 { 00042 PM_RAISE(retval, PM_RET_EX_TYPE); 00043 return retval; 00044 } 00045 00046 /* Raise ValueError if arg is not int within range(256) */ 00047 n = ((pPmInt_t)pn)->val; 00048 if ((n < 0) || (n > 255)) 00049 { 00050 PM_RAISE(retval, PM_RET_EX_VAL); 00051 return retval; 00052 } 00053 00054 /* Create char string from integer value */ 00055 retval = string_newFromChar((uint8_t)n, &ps); 00056 NATIVE_SET_TOS(ps); 00057 return retval; 00058 00059 } 00060 00061 PmReturn_t 00062 nat_01___bi_dir(pPmFrame_t *ppframe) 00063 { 00064 00065 PmReturn_t retval = PM_RET_OK; 00066 pPmObj_t po; 00067 pPmObj_t pk; 00068 pPmObj_t pl; 00069 pSeglist_t psl; 00070 int16_t i; 00071 uint8_t objid; 00072 00073 /* Use globals if no arg given */ 00074 if (NATIVE_GET_NUM_ARGS() == 0) 00075 { 00076 /* Get the globals dict */ 00077 po = (pPmObj_t)NATIVE_GET_PFRAME()->fo_globals; 00078 } 00079 00080 /* Otherwise use the given arg */ 00081 else if (NATIVE_GET_NUM_ARGS() == 1) 00082 { 00083 po = NATIVE_GET_LOCAL(0); 00084 00085 /* If object is a function or module, use its attrs dict */ 00086 if ((OBJ_GET_TYPE(po) == OBJ_TYPE_FXN) 00087 || (OBJ_GET_TYPE(po) == OBJ_TYPE_MOD)) 00088 { 00089 po = (pPmObj_t)((pPmFunc_t)po)->f_attrs; 00090 } 00091 00092 #ifdef HAVE_CLASSES 00093 else if (OBJ_GET_TYPE(po) == OBJ_TYPE_CLO) 00094 { 00095 po = (pPmObj_t)((pPmClass_t)po)->cl_attrs; 00096 } 00097 else if (OBJ_GET_TYPE(po) == OBJ_TYPE_CLI) 00098 { 00099 po = (pPmObj_t)((pPmInstance_t)po)->cli_attrs; 00100 } 00101 else if (OBJ_GET_TYPE(po) == OBJ_TYPE_MTH) 00102 { 00103 po = (pPmObj_t)((pPmMethod_t)po)->m_attrs; 00104 } 00105 #endif /* HAVE_CLASSES */ 00106 00107 else 00108 { 00109 po = C_NULL; 00110 } 00111 } 00112 00113 /* Raise TypeError if wrong number of args */ 00114 else 00115 { 00116 PM_RAISE(retval, PM_RET_EX_TYPE); 00117 return retval; 00118 } 00119 00120 if (po == C_NULL) 00121 { 00122 pl = PM_NONE; 00123 } 00124 else 00125 { 00126 /* Create new list */ 00127 retval = list_new(&pl); 00128 PM_RETURN_IF_ERROR(retval); 00129 00130 /* Copy dict's keys to the list */ 00131 psl = ((pPmDict_t)po)->d_keys; 00132 for (i = 0; i < ((pPmDict_t)po)->length; i++) 00133 { 00134 retval = seglist_getItem(psl, i, &pk); 00135 PM_RETURN_IF_ERROR(retval); 00136 heap_gcPushTempRoot(pl, &objid); 00137 retval = list_append(pl, pk); 00138 heap_gcPopTempRoot(objid); 00139 PM_RETURN_IF_ERROR(retval); 00140 } 00141 } 00142 00143 NATIVE_SET_TOS(pl); 00144 return retval; 00145 00146 } 00147 00148 PmReturn_t 00149 nat_02___bi_eval(pPmFrame_t *ppframe) 00150 { 00151 00152 PmReturn_t retval; 00153 pPmObj_t pco; 00154 pPmObj_t pfunc; 00155 pPmObj_t pnewframe; 00156 pPmObj_t pg = C_NULL; 00157 pPmObj_t pl = C_NULL; 00158 uint8_t objid; 00159 00160 /* If wrong number of args, raise TypeError */ 00161 if ((NATIVE_GET_NUM_ARGS() == 0) || (NATIVE_GET_NUM_ARGS() > 3)) 00162 { 00163 PM_RAISE(retval, PM_RET_EX_TYPE); 00164 return retval; 00165 } 00166 00167 /* Raise ValueError if first arg is not a Code Object */ 00168 pco = NATIVE_GET_LOCAL(0); 00169 if (OBJ_GET_TYPE(pco) != OBJ_TYPE_COB) 00170 { 00171 PM_RAISE(retval, PM_RET_EX_VAL); 00172 return retval; 00173 } 00174 00175 /* If 2nd arg exists, raise ValueError if it is not a Dict */ 00176 if (NATIVE_GET_NUM_ARGS() >= 2) 00177 { 00178 pg = NATIVE_GET_LOCAL(1); 00179 if (OBJ_GET_TYPE(pg) != OBJ_TYPE_DIC) 00180 { 00181 PM_RAISE(retval, PM_RET_EX_VAL); 00182 return retval; 00183 } 00184 } 00185 00186 /* If no args are given, use the caller's globals for the function's */ 00187 else 00188 { 00189 pg = (pPmObj_t)NATIVE_GET_PFRAME()->fo_globals; 00190 } 00191 00192 /* If 3rd arg exists, raise ValueError if it is not a Dict */ 00193 if (NATIVE_GET_NUM_ARGS() >= 3) 00194 { 00195 pl = NATIVE_GET_LOCAL(2); 00196 if (OBJ_GET_TYPE(pl) != OBJ_TYPE_DIC) 00197 { 00198 PM_RAISE(retval, PM_RET_EX_VAL); 00199 return retval; 00200 } 00201 } 00202 00203 /* Create func from code object */ 00204 retval = func_new(pco, pg, &pfunc); 00205 PM_RETURN_IF_ERROR(retval); 00206 00207 /* Create frame from module object; globals is set to null */ 00208 heap_gcPushTempRoot(pfunc, &objid); 00209 retval = frame_new(pfunc, &pnewframe); 00210 heap_gcPopTempRoot(objid); 00211 PM_RETURN_IF_ERROR(retval); 00212 00213 /* TODO: Reclaim pnewframe's attrs dict created in frame_new */ 00214 /* 00215 * By default use calling frame's attrs as local namespace. 00216 * This works for ipm because the interactive mode 00217 * needs a locals namespace that persists across calls to eval() 00218 */ 00219 ((pPmFrame_t)pnewframe)->fo_attrs = NATIVE_GET_PFRAME()->fo_attrs; 00220 00221 /* If 2nd arg exists, use it as the global namespace for the new func */ 00222 if (NATIVE_GET_NUM_ARGS() >= 2) 00223 { 00224 ((pPmFrame_t)pnewframe)->fo_globals = (pPmDict_t)pg; 00225 00226 /* If only globals is given, locals defaults to it */ 00227 ((pPmFrame_t)pnewframe)->fo_attrs = (pPmDict_t)pg; 00228 } 00229 00230 /* If 3rd arg exists, use it as the local namespace for the new func */ 00231 if (NATIVE_GET_NUM_ARGS() >= 3) 00232 { 00233 ((pPmFrame_t)pnewframe)->fo_attrs = (pPmDict_t)pl; 00234 } 00235 00236 /* 00237 * Set the fo_back frame so flow returns to eval()'s caller when completed. 00238 * Set the frame pointer so the new frame is interpreted immediately 00239 * after this function returns. 00240 */ 00241 ((pPmFrame_t)pnewframe)->fo_back = NATIVE_GET_PFRAME(); 00242 NATIVE_GET_PFRAME() = (pPmFrame_t)pnewframe; 00243 retval = PM_RET_FRAME_SWITCH; 00244 00245 return retval; 00246 00247 } 00248 00249 PmReturn_t 00250 nat_03___bi_globals(pPmFrame_t *ppframe) 00251 { 00252 00253 pPmObj_t pr = C_NULL; 00254 PmReturn_t retval; 00255 00256 /* If wrong number of args, raise TypeError */ 00257 if (NATIVE_GET_NUM_ARGS() != 0) 00258 { 00259 PM_RAISE(retval, PM_RET_EX_TYPE); 00260 return retval; 00261 } 00262 00263 /* Return calling frame's globals dict on stack*/ 00264 pr = (pPmObj_t)NATIVE_GET_PFRAME()->fo_globals; 00265 NATIVE_SET_TOS(pr); 00266 00267 return PM_RET_OK; 00268 00269 } 00270 00271 PmReturn_t 00272 nat_04___bi_id(pPmFrame_t *ppframe) 00273 { 00274 00275 PmReturn_t retval; 00276 pPmObj_t pr = C_NULL; 00277 00278 /* If wrong number of args, raise TypeError */ 00279 if (NATIVE_GET_NUM_ARGS() != 1) 00280 { 00281 PM_RAISE(retval, PM_RET_EX_TYPE); 00282 return retval; 00283 } 00284 00285 /* Return object's address as an int on the stack */ 00286 retval = int_new((intptr_t)NATIVE_GET_LOCAL(0), &pr); 00287 NATIVE_SET_TOS(pr); 00288 00289 return retval; 00290 00291 } 00292 00293 PmReturn_t 00294 nat_05___bi_len(pPmFrame_t *ppframe) 00295 { 00296 00297 PmReturn_t retval; 00298 pPmObj_t ps = C_NULL; 00299 pPmObj_t pr = C_NULL; 00300 00301 /* If wrong number of args, raise TypeError */ 00302 if (NATIVE_GET_NUM_ARGS() != 1) 00303 { 00304 PM_RAISE(retval, PM_RET_EX_TYPE); 00305 return retval; 00306 } 00307 00308 /* Get first arg */ 00309 ps = NATIVE_GET_LOCAL(0); 00310 00311 #ifdef HAVE_BYTEARRAY 00312 /* If object is an instance, get the thing it contains */ 00313 if (OBJ_GET_TYPE(ps) == OBJ_TYPE_CLI) 00314 { 00315 retval = dict_getItem((pPmObj_t)((pPmInstance_t)ps)->cli_attrs, 00316 PM_NONE, 00317 &pr); 00318 00319 /* If None wasn't in attributes, obj is wrong type for len() */ 00320 if (retval == PM_RET_EX_KEY) retval = PM_RET_EX_TYPE; 00321 PM_RETURN_IF_ERROR(retval); 00322 ps = pr; 00323 } 00324 #endif /* HAVE_BYTEARRAY */ 00325 00326 /* Get the length of the arg based on its type */ 00327 switch (OBJ_GET_TYPE(ps)) 00328 { 00329 case OBJ_TYPE_STR: 00330 retval = int_new(((pPmString_t)ps)->length, &pr); 00331 break; 00332 00333 case OBJ_TYPE_TUP: 00334 retval = int_new(((pPmTuple_t)ps)->length, &pr); 00335 break; 00336 00337 case OBJ_TYPE_LST: 00338 retval = int_new(((pPmList_t)ps)->length, &pr); 00339 break; 00340 00341 case OBJ_TYPE_DIC: 00342 retval = int_new(((pPmDict_t)ps)->length, &pr); 00343 break; 00344 00345 #ifdef HAVE_BYTEARRAY 00346 case OBJ_TYPE_BYA: 00347 retval = int_new(((pPmBytearray_t)ps)->length, &pr); 00348 break; 00349 #endif /* HAVE_BYTEARRAY */ 00350 00351 default: 00352 /* If not a string or sequence type, raise TypeError */ 00353 PM_RAISE(retval, PM_RET_EX_TYPE); 00354 } 00355 00356 NATIVE_SET_TOS(pr); 00357 return retval; 00358 00359 } 00360 00361 PmReturn_t 00362 nat_06___bi_locals(pPmFrame_t *ppframe) 00363 { 00364 00365 pPmObj_t pr = C_NULL; 00366 PmReturn_t retval; 00367 00368 /* If wrong number of args, raise TypeError */ 00369 if (NATIVE_GET_NUM_ARGS() != 0) 00370 { 00371 PM_RAISE(retval, PM_RET_EX_TYPE); 00372 return retval; 00373 } 00374 00375 /* Return calling frame's local attrs dict on the stack */ 00376 pr = (pPmObj_t)NATIVE_GET_PFRAME()->fo_attrs; 00377 NATIVE_SET_TOS(pr); 00378 00379 return PM_RET_OK; 00380 00381 } 00382 00383 PmReturn_t 00384 nat_07___bi_ord(pPmFrame_t *ppframe) 00385 { 00386 00387 pPmObj_t ps; 00388 pPmObj_t pn; 00389 int32_t n; 00390 PmReturn_t retval; 00391 00392 /* If wrong number of args, raise TypeError */ 00393 if (NATIVE_GET_NUM_ARGS() != 1) 00394 { 00395 PM_RAISE(retval, PM_RET_EX_TYPE); 00396 return retval; 00397 } 00398 00399 ps = NATIVE_GET_LOCAL(0); 00400 00401 /* Raise TypeError if arg is not string of length 1 */ 00402 if ((OBJ_GET_TYPE(ps) != OBJ_TYPE_STR) 00403 || (((pPmString_t)ps)->length != 1)) 00404 00405 { 00406 PM_RAISE(retval, PM_RET_EX_TYPE); 00407 return retval; 00408 } 00409 00410 /* Get integer value of character */ 00411 n = ((pPmString_t)ps)->val[0]; 00412 retval = int_new(n, &pn); 00413 NATIVE_SET_TOS(pn); 00414 return retval; 00415 00416 } 00417 00418 PmReturn_t 00419 nat_08___bi_range(pPmFrame_t *ppframe) 00420 { 00421 00422 PmReturn_t retval; 00423 pPmObj_t pa = C_NULL; 00424 pPmObj_t pb = C_NULL; 00425 pPmObj_t pc = C_NULL; 00426 pPmObj_t pi = C_NULL; 00427 pPmObj_t pr = C_NULL; 00428 int16_t i = 0; 00429 uint8_t objid1, objid2; 00430 00431 switch (NATIVE_GET_NUM_ARGS()) 00432 { 00433 case 1: 00434 pa = PM_ZERO; 00435 pb = NATIVE_GET_LOCAL(0); 00436 pc = PM_ONE; 00437 break; 00438 00439 case 2: 00440 pa = NATIVE_GET_LOCAL(0); 00441 pb = NATIVE_GET_LOCAL(1); 00442 pc = PM_ONE; 00443 break; 00444 00445 case 3: 00446 pa = NATIVE_GET_LOCAL(0); 00447 pb = NATIVE_GET_LOCAL(1); 00448 pc = NATIVE_GET_LOCAL(2); 00449 00450 /* If 3rd arg is 0, ValueError */ 00451 if (((pPmInt_t)pc)->val == 0) 00452 { 00453 PM_RAISE(retval, PM_RET_EX_VAL); 00454 return retval; 00455 } 00456 break; 00457 00458 default: 00459 /* If wrong number of args, raise TypeError */ 00460 PM_RAISE(retval, PM_RET_EX_TYPE); 00461 return retval; 00462 } 00463 00464 /* Allocate list */ 00465 retval = list_new(&pr); 00466 PM_RETURN_IF_ERROR(retval); 00467 00468 /* Iterate depending on counting direction */ 00469 if (((pPmInt_t)pc)->val > 0) 00470 { 00471 for (i = ((pPmInt_t)pa)->val; 00472 i < ((pPmInt_t)pb)->val; 00473 i += ((pPmInt_t)pc)->val) 00474 { 00475 heap_gcPushTempRoot(pr, &objid1); 00476 retval = int_new(i, &pi); 00477 if (retval != PM_RET_OK) 00478 { 00479 heap_gcPopTempRoot(objid1); 00480 return retval; 00481 } 00482 00483 heap_gcPushTempRoot(pi, &objid2); 00484 retval = list_append(pr, pi); 00485 heap_gcPopTempRoot(objid1); 00486 PM_RETURN_IF_ERROR(retval); 00487 } 00488 } 00489 else 00490 { 00491 for (i = ((pPmInt_t)pa)->val; 00492 i > ((pPmInt_t)pb)->val; 00493 i += ((pPmInt_t)pc)->val) 00494 { 00495 heap_gcPushTempRoot(pr, &objid1); 00496 retval = int_new(i, &pi); 00497 if (retval != PM_RET_OK) 00498 { 00499 heap_gcPopTempRoot(objid1); 00500 return retval; 00501 } 00502 00503 heap_gcPushTempRoot(pi, &objid2); 00504 retval = list_append(pr, pi); 00505 heap_gcPopTempRoot(objid1); 00506 PM_RETURN_IF_ERROR(retval); 00507 } 00508 } 00509 00510 /* Return list */ 00511 NATIVE_SET_TOS(pr); 00512 return retval; 00513 00514 } 00515 00516 PmReturn_t 00517 nat_09___bi_sum(pPmFrame_t *ppframe) 00518 { 00519 00520 pPmObj_t ps; 00521 pPmObj_t pn; 00522 pPmObj_t po; 00523 int32_t n; 00524 uint16_t len; 00525 uint16_t i; 00526 PmReturn_t retval; 00527 #ifdef HAVE_FLOAT 00528 float f; 00529 uint8_t usefloat = C_FALSE; 00530 #endif /* HAVE_FLOAT */ 00531 00532 /* If wrong number of args, raise TypeError */ 00533 if (NATIVE_GET_NUM_ARGS() != 1) 00534 { 00535 PM_RAISE(retval, PM_RET_EX_TYPE); 00536 return retval; 00537 } 00538 00539 ps = NATIVE_GET_LOCAL(0); 00540 00541 #ifdef HAVE_BYTEARRAY 00542 /* Bytearray is a special case to save RAM converting each byte to an Int */ 00543 if (OBJ_GET_TYPE(ps) == OBJ_TYPE_BYA) 00544 { 00545 n = 0; 00546 len = ((pPmBytearray_t)ps)->length; 00547 po = (pPmObj_t)((pPmBytearray_t)ps)->val; 00548 for (i = 0; i < len; i++) 00549 { 00550 n += (uint8_t)((pPmBytes_t)po)->val[i]; 00551 } 00552 retval = int_new(n, &pn); 00553 NATIVE_SET_TOS(pn); 00554 return retval; 00555 } 00556 #endif /* HAVE_BYTEARRAY */ 00557 00558 /* Raise TypeError if arg is not a sequence */ 00559 if ((OBJ_GET_TYPE(ps) != OBJ_TYPE_TUP) 00560 && (OBJ_GET_TYPE(ps) != OBJ_TYPE_LST) 00561 && (OBJ_GET_TYPE(ps) != OBJ_TYPE_DIC)) 00562 { 00563 PM_RAISE(retval, PM_RET_EX_TYPE); 00564 return retval; 00565 } 00566 00567 /* Get the length of the sequence */ 00568 retval = seq_getLength(ps, &len); 00569 PM_RETURN_IF_ERROR(retval); 00570 00571 /* Calculate the sum of the sequence */ 00572 n = 0; 00573 #ifdef HAVE_FLOAT 00574 f = 0.0; 00575 #endif 00576 for (i = 0; i < len; i++) 00577 { 00578 retval = seq_getSubscript(ps, i, &po); 00579 00580 if (OBJ_GET_TYPE(po) == OBJ_TYPE_INT) 00581 { 00582 /* Add value to sum */ 00583 n += ((pPmInt_t)po)->val; 00584 #ifdef HAVE_FLOAT 00585 f += (float)((pPmInt_t)po)->val; 00586 #endif /* HAVE_FLOAT */ 00587 } 00588 00589 #ifdef HAVE_FLOAT 00590 else if (OBJ_GET_TYPE(po) == OBJ_TYPE_FLT) 00591 { 00592 /* Add value to sum */ 00593 f += ((pPmFloat_t)po)->val; 00594 usefloat = C_TRUE; 00595 } 00596 #endif /* HAVE_FLOAT */ 00597 00598 /* Raise TypeError if item is not an integer */ 00599 else 00600 { 00601 PM_RAISE(retval, PM_RET_EX_TYPE); 00602 return retval; 00603 } 00604 } 00605 00606 #ifdef HAVE_FLOAT 00607 if (usefloat) 00608 { 00609 retval = float_new(f, &pn); 00610 } 00611 else 00612 #endif /* HAVE_FLOAT */ 00613 { 00614 retval = int_new(n, &pn); 00615 } 00616 NATIVE_SET_TOS(pn); 00617 return retval; 00618 00619 } 00620 00621 PmReturn_t 00622 nat_10___bi_type(pPmFrame_t *ppframe) 00623 { 00624 00625 PmReturn_t retval; 00626 pPmObj_t po = C_NULL; 00627 pPmObj_t pr = C_NULL; 00628 00629 /* If wrong number of args, raise TypeError */ 00630 if (NATIVE_GET_NUM_ARGS() != 1) 00631 { 00632 PM_RAISE(retval, PM_RET_EX_TYPE); 00633 return retval; 00634 } 00635 00636 /* Get arg */ 00637 po = NATIVE_GET_LOCAL(0); 00638 00639 /* Create int from type enum */ 00640 retval = int_new(OBJ_GET_TYPE(po), &pr); 00641 NATIVE_SET_TOS(pr); 00642 return retval; 00643 00644 } 00645 00646 PmReturn_t 00647 nat_11___bi_Co(pPmFrame_t *ppframe) 00648 { 00649 00650 PmReturn_t retval; 00651 pPmObj_t pimg; 00652 pPmObj_t pco; 00653 00654 /* If wrong number of args, raise TypeError */ 00655 if (NATIVE_GET_NUM_ARGS() != 1) 00656 { 00657 PM_RAISE(retval, PM_RET_EX_TYPE); 00658 return retval; 00659 } 00660 00661 /* Raise ValueError if arg is not an Image Obj */ 00662 pimg = NATIVE_GET_LOCAL(0); 00663 if (OBJ_GET_TYPE(pimg) != OBJ_TYPE_CIO) 00664 { 00665 PM_RAISE(retval, PM_RET_EX_VAL); 00666 return retval; 00667 } 00668 00669 /* Create a code object from the image */ 00670 retval = obj_loadFromImgObj(pimg, &pco); 00671 PM_RETURN_IF_ERROR(retval); 00672 00673 /* Return the code object */ 00674 NATIVE_SET_TOS(pco); 00675 return retval; 00676 00677 } 00678 00679 PmReturn_t 00680 nat_12___bi___init__(pPmFrame_t *ppframe) 00681 { 00682 00683 PmReturn_t retval; 00684 pPmObj_t pself; 00685 pPmObj_t pfa; 00686 pPmObj_t pfunc; 00687 pPmObj_t pframe; 00688 uint8_t i; 00689 uint8_t objid; 00690 00691 /* Raise TypeError if wrong number of args */ 00692 if (NATIVE_GET_NUM_ARGS() != 2) 00693 { 00694 PM_RAISE(retval, PM_RET_EX_TYPE); 00695 return retval; 00696 } 00697 00698 /* Raise ValueError if first args are not: instance, tuple */ 00699 pself = NATIVE_GET_LOCAL(0); 00700 pfa = NATIVE_GET_LOCAL(1); 00701 if (OBJ_GET_TYPE(pself) != OBJ_TYPE_CLI) 00702 { 00703 PM_RAISE(retval, PM_RET_EX_VAL); 00704 return retval; 00705 } 00706 if (OBJ_GET_TYPE(pfa) != OBJ_TYPE_TUP) 00707 { 00708 PM_RAISE(retval, PM_RET_EX_VAL); 00709 return retval; 00710 } 00711 00712 /* Create a new frame for the function */ 00713 pfunc = ((pPmTuple_t)pfa)->val[0]; 00714 retval = frame_new(pfunc, &pframe); 00715 PM_RETURN_IF_ERROR(retval); 00716 00717 /* Copy args into frame's locals */ 00718 for (i = 0; i < ((pPmTuple_t)pfa)->length - 1; i++) 00719 { 00720 /* The pfa tuple is (func, [arg0, ... argN]) */ 00721 ((pPmFrame_t)pframe)->fo_locals[i] = ((pPmTuple_t)pfa)->val[i + 1]; 00722 } 00723 00724 /* Store frame in None attr of instance */ 00725 heap_gcPushTempRoot(pframe, &objid); 00726 retval = dict_setItem((pPmObj_t)((pPmInstance_t)pself)->cli_attrs, 00727 PM_NONE, pframe); 00728 heap_gcPopTempRoot(objid); 00729 00730 NATIVE_SET_TOS(PM_NONE); 00731 return retval; 00732 00733 } 00734 00735 PmReturn_t 00736 nat_13___bi_send(pPmFrame_t *ppframe) 00737 { 00738 00739 PmReturn_t retval; 00740 pPmObj_t pself; 00741 pPmObj_t parg; 00742 pPmObj_t pgenframe; 00743 00744 /* Raise TypeError if wrong number of args */ 00745 if (NATIVE_GET_NUM_ARGS() != 2) 00746 { 00747 PM_RAISE(retval, PM_RET_EX_TYPE); 00748 return retval; 00749 } 00750 00751 /* Raise ValueError if first arg is not an instance */ 00752 pself = NATIVE_GET_LOCAL(0); 00753 parg = NATIVE_GET_LOCAL(1); 00754 if (OBJ_GET_TYPE(pself) != OBJ_TYPE_CLI) 00755 { 00756 PM_RAISE(retval, PM_RET_EX_VAL); 00757 return retval; 00758 } 00759 00760 /* Get the generator's frame */ 00761 retval = dict_getItem((pPmObj_t)((pPmInstance_t)pself)->cli_attrs, 00762 PM_NONE, &pgenframe); 00763 PM_RETURN_IF_ERROR(retval); 00764 00765 /* Push argument onto generator's frame's stack */ 00766 *(((pPmFrame_t)pgenframe)->fo_sp) = parg; 00767 ((pPmFrame_t)pgenframe)->fo_sp++; 00768 00769 /* Set generator's frame's fo_back so yielded value goes to caller */ 00770 ((pPmFrame_t)pgenframe)->fo_back = NATIVE_GET_PFRAME(); 00771 00772 /* Set active frame to run generator */ 00773 NATIVE_GET_PFRAME() = (pPmFrame_t)pgenframe; 00774 00775 return PM_RET_FRAME_SWITCH; 00776 00777 } 00778 00779 PmReturn_t 00780 nat_14___bi_ismain(pPmFrame_t *ppframe) 00781 { 00782 00783 00784 NATIVE_SET_TOS((NATIVE_GET_PFRAME()->fo_isImport) ? PM_FALSE : PM_TRUE); 00785 00786 return PM_RET_OK; 00787 00788 } 00789 00790 PmReturn_t 00791 nat_15_dict_clear(pPmFrame_t *ppframe) 00792 { 00793 00794 pPmObj_t pd; 00795 PmReturn_t retval = PM_RET_OK; 00796 00797 /* Raise TypeError if it's not a dict or wrong number of args, */ 00798 pd = NATIVE_GET_LOCAL(0); 00799 if ((OBJ_GET_TYPE(pd) != OBJ_TYPE_DIC) || (NATIVE_GET_NUM_ARGS() != 1)) 00800 { 00801 PM_RAISE(retval, PM_RET_EX_TYPE); 00802 return retval; 00803 } 00804 00805 /* Clear the contents of the dict */ 00806 retval = dict_clear(pd); 00807 PM_RETURN_IF_ERROR(retval); 00808 00809 NATIVE_SET_TOS(PM_NONE); 00810 00811 return retval; 00812 00813 } 00814 00815 PmReturn_t 00816 nat_16_dict_keys(pPmFrame_t *ppframe) 00817 { 00818 00819 pPmObj_t pd; 00820 pPmObj_t pl; 00821 pPmObj_t pk; 00822 pSeglist_t psl; 00823 uint16_t i; 00824 PmReturn_t retval = PM_RET_OK; 00825 uint8_t objid; 00826 00827 /* Raise TypeError if it's not a dict or wrong number of args, */ 00828 pd = NATIVE_GET_LOCAL(0); 00829 if ((OBJ_GET_TYPE(pd) != OBJ_TYPE_DIC) || (NATIVE_GET_NUM_ARGS() != 1)) 00830 { 00831 PM_RAISE(retval, PM_RET_EX_TYPE); 00832 return retval; 00833 } 00834 00835 /* Create empty list */ 00836 retval = list_new(&pl); 00837 PM_RETURN_IF_ERROR(retval); 00838 00839 /* Iterate through the keys seglist */ 00840 psl = ((pPmDict_t)pd)->d_keys; 00841 for (i = 0; i < ((pPmDict_t)pd)->length; i++) 00842 { 00843 /* Get the key and append it to the list */ 00844 retval = seglist_getItem(psl, i, &pk); 00845 PM_RETURN_IF_ERROR(retval); 00846 heap_gcPushTempRoot(pl, &objid); 00847 retval = list_append(pl, pk); 00848 heap_gcPopTempRoot(objid); 00849 PM_RETURN_IF_ERROR(retval); 00850 } 00851 00852 /* Return the list of keys to the caller */ 00853 NATIVE_SET_TOS(pl); 00854 00855 return retval; 00856 00857 } 00858 00859 PmReturn_t 00860 nat_17_dict_values(pPmFrame_t *ppframe) 00861 { 00862 00863 pPmObj_t pd; 00864 pPmObj_t pl; 00865 pPmObj_t pv; 00866 pSeglist_t psl; 00867 uint16_t i; 00868 PmReturn_t retval = PM_RET_OK; 00869 uint8_t objid; 00870 00871 /* Raise TypeError if it's not a dict or wrong number of args, */ 00872 pd = NATIVE_GET_LOCAL(0); 00873 if ((OBJ_GET_TYPE(pd) != OBJ_TYPE_DIC) || (NATIVE_GET_NUM_ARGS() != 1)) 00874 { 00875 PM_RAISE(retval, PM_RET_EX_TYPE); 00876 return retval; 00877 } 00878 00879 /* Create empty list */ 00880 retval = list_new(&pl); 00881 PM_RETURN_IF_ERROR(retval); 00882 00883 /* Iterate through the values seglist */ 00884 psl = ((pPmDict_t)pd)->d_vals; 00885 for (i = 0; i < ((pPmDict_t)pd)->length; i++) 00886 { 00887 /* Get the value and append it to the list */ 00888 retval = seglist_getItem(psl, i, &pv); 00889 PM_RETURN_IF_ERROR(retval); 00890 heap_gcPushTempRoot(pl, &objid); 00891 retval = list_append(pl, pv); 00892 heap_gcPopTempRoot(objid); 00893 PM_RETURN_IF_ERROR(retval); 00894 } 00895 00896 /* Return the list of values to the caller */ 00897 NATIVE_SET_TOS(pl); 00898 00899 return retval; 00900 00901 } 00902 00903 PmReturn_t 00904 nat_18_dict_update(pPmFrame_t *ppframe) 00905 { 00906 00907 pPmObj_t pd1; 00908 pPmObj_t pd2; 00909 PmReturn_t retval; 00910 00911 /* Raise TypeError if wrong number of args, */ 00912 if (NATIVE_GET_NUM_ARGS() != 2) 00913 { 00914 PM_RAISE(retval, PM_RET_EX_TYPE); 00915 return retval; 00916 } 00917 00918 pd1 = NATIVE_GET_LOCAL(0); 00919 pd2 = NATIVE_GET_LOCAL(1); 00920 retval = dict_update(pd1, pd2, C_FALSE); 00921 00922 NATIVE_SET_TOS(PM_NONE); 00923 return retval; 00924 00925 } 00926 00927 PmReturn_t 00928 nat_19_list_append(pPmFrame_t *ppframe) 00929 { 00930 00931 pPmObj_t pl; 00932 PmReturn_t retval = PM_RET_OK; 00933 00934 /* Raise TypeError if it's not a list or wrong number of args, */ 00935 pl = NATIVE_GET_LOCAL(0); 00936 if ((OBJ_GET_TYPE(pl) != OBJ_TYPE_LST) || (NATIVE_GET_NUM_ARGS() != 2)) 00937 { 00938 PM_RAISE(retval, PM_RET_EX_TYPE); 00939 return retval; 00940 } 00941 00942 /* Append the object to the list */ 00943 retval = list_append(pl, NATIVE_GET_LOCAL(1)); 00944 00945 NATIVE_SET_TOS(PM_NONE); 00946 00947 return retval; 00948 00949 } 00950 00951 PmReturn_t 00952 nat_20_list_index(pPmFrame_t *ppframe) 00953 { 00954 00955 pPmObj_t pl; 00956 pPmObj_t po; 00957 pPmObj_t pi; 00958 PmReturn_t retval = PM_RET_OK; 00959 uint16_t i; 00960 00961 /* Raise TypeError if it's not a list or wrong number of args, */ 00962 pl = NATIVE_GET_LOCAL(0); 00963 if ((OBJ_GET_TYPE(pl) != OBJ_TYPE_LST) || (NATIVE_GET_NUM_ARGS() != 2)) 00964 { 00965 PM_RAISE(retval, PM_RET_EX_TYPE); 00966 return retval; 00967 } 00968 00969 /* Get the index of the object in the list */ 00970 po = NATIVE_GET_LOCAL(1); 00971 retval = list_index(pl, po, &i); 00972 00973 if (retval == PM_RET_EX_VAL) 00974 { 00975 PM_RAISE(retval, PM_RET_EX_VAL); 00976 return retval; 00977 } 00978 00979 int_new((int32_t)i, &pi); 00980 NATIVE_SET_TOS(pi); 00981 00982 return retval; 00983 00984 } 00985 00986 PmReturn_t 00987 nat_21_list_insert(pPmFrame_t *ppframe) 00988 { 00989 00990 pPmObj_t pl; 00991 pPmObj_t pi; 00992 pPmObj_t po; 00993 PmReturn_t retval = PM_RET_OK; 00994 uint16_t i; 00995 00996 /* 00997 * Raise TypeError if wrong number of args, first arg is not a list, or 00998 * second arg is not an int 00999 */ 01000 pl = NATIVE_GET_LOCAL(0); 01001 pi = NATIVE_GET_LOCAL(1); 01002 po = NATIVE_GET_LOCAL(2); 01003 if ((NATIVE_GET_NUM_ARGS() != 3) 01004 || (OBJ_GET_TYPE(pl) != OBJ_TYPE_LST) 01005 || (OBJ_GET_TYPE(pi) != OBJ_TYPE_INT) ) 01006 { 01007 PM_RAISE(retval, PM_RET_EX_TYPE); 01008 return retval; 01009 } 01010 01011 /* Insert the object before the given index */ 01012 i = (uint16_t)((pPmInt_t)pi)->val; 01013 retval = list_insert(pl, i, po); 01014 01015 if (retval != PM_RET_OK) 01016 { 01017 PM_RAISE(retval, PM_RET_EX_SYS); 01018 } 01019 01020 NATIVE_SET_TOS(PM_NONE); 01021 01022 return retval; 01023 01024 } 01025 01026 PmReturn_t 01027 nat_22_list_pop(pPmFrame_t *ppframe) 01028 { 01029 01030 pPmObj_t pl; 01031 pPmObj_t pi; 01032 pPmObj_t po; 01033 PmReturn_t retval = PM_RET_OK; 01034 int16_t i; 01035 01036 /* 01037 * Raise TypeError if first arg is not a list o second arg is not an int 01038 * or there are the wrong number of arguments 01039 */ 01040 pl = NATIVE_GET_LOCAL(0); 01041 if (OBJ_GET_TYPE(pl) != OBJ_TYPE_LST) 01042 { 01043 PM_RAISE(retval, PM_RET_EX_TYPE); 01044 return retval; 01045 } 01046 01047 pi = NATIVE_GET_LOCAL(1); 01048 if (NATIVE_GET_NUM_ARGS() == 2) 01049 { 01050 if (OBJ_GET_TYPE(pi) != OBJ_TYPE_INT) 01051 { 01052 PM_RAISE(retval, PM_RET_EX_TYPE); 01053 return retval; 01054 } 01055 i = (uint16_t)((pPmInt_t)pi)->val; 01056 } 01057 else 01058 { 01059 i = -1; 01060 } 01061 if ((NATIVE_GET_NUM_ARGS() < 1) || (NATIVE_GET_NUM_ARGS() > 2)) 01062 { 01063 PM_RAISE(retval, PM_RET_EX_TYPE); 01064 return retval; 01065 } 01066 01067 /* Get the object at the given index */ 01068 retval = list_getItem(pl, i, &po); 01069 PM_RETURN_IF_ERROR(retval); 01070 01071 /* Return the object to the caller */ 01072 NATIVE_SET_TOS(po); 01073 01074 /* Remove the object from the given index */ 01075 retval = list_delItem(pl, i); 01076 PM_RETURN_IF_ERROR(retval); 01077 01078 return retval; 01079 01080 } 01081 01082 PmReturn_t 01083 nat_23_list_remove(pPmFrame_t *ppframe) 01084 { 01085 01086 pPmObj_t pl; 01087 pPmObj_t pv; 01088 PmReturn_t retval = PM_RET_OK; 01089 01090 /* Raise TypeError if it's not a list or wrong number of args, */ 01091 pl = NATIVE_GET_LOCAL(0); 01092 if ((OBJ_GET_TYPE(pl) != OBJ_TYPE_LST) || (NATIVE_GET_NUM_ARGS() != 2)) 01093 { 01094 PM_RAISE(retval, PM_RET_EX_TYPE); 01095 return retval; 01096 } 01097 01098 /* Remove the value from the list */ 01099 pv = NATIVE_GET_LOCAL(1); 01100 retval = list_remove(pl, pv); 01101 if (retval != PM_RET_OK) 01102 { 01103 PM_RAISE(retval, retval); 01104 } 01105 01106 NATIVE_SET_TOS(PM_NONE); 01107 01108 return retval; 01109 01110 } 01111 01112 PmReturn_t 01113 nat_24_string_atoi(pPmFrame_t *ppframe) 01114 { 01115 01116 pPmObj_t pa; 01117 pPmObj_t pb; 01118 char const *pc; 01119 char *pend; 01120 long i; 01121 int8_t base; 01122 pPmObj_t pi; 01123 PmReturn_t retval = PM_RET_OK; 01124 01125 /* Raise TypeError if it's not a string or wrong number of args, */ 01126 pa = NATIVE_GET_LOCAL(0); 01127 if ((OBJ_GET_TYPE(pa) != OBJ_TYPE_STR) || (NATIVE_GET_NUM_ARGS() < 1) 01128 || (NATIVE_GET_NUM_ARGS() > 2)) 01129 { 01130 PM_RAISE(retval, PM_RET_EX_TYPE); 01131 return retval; 01132 } 01133 01134 /* Get the base, if it exists; otherwise assume 10 */ 01135 base = 10; 01136 if (NATIVE_GET_NUM_ARGS() == 2) 01137 { 01138 pb = NATIVE_GET_LOCAL(1); 01139 01140 /* Raise a TypeError if 2nd arg is not an int */ 01141 if (OBJ_GET_TYPE(pb) != OBJ_TYPE_INT) 01142 { 01143 PM_RAISE(retval, PM_RET_EX_TYPE); 01144 return retval; 01145 } 01146 01147 base = ((pPmInt_t)pb)->val; 01148 01149 /* Raise ValueError if base is out of range */ 01150 if ((base < 0) || (base == 1) || (base > 36)) 01151 { 01152 PM_RAISE(retval, PM_RET_EX_VAL); 01153 return retval; 01154 } 01155 } 01156 01157 /* Perform conversion */ 01158 pend = C_NULL; 01159 pc = (char const *)&(((pPmString_t)pa)->val); 01160 i = strtol(pc, &pend, base); 01161 01162 /* Raise ValueError if there was a conversion error */ 01163 if (*pend != C_NULL) 01164 { 01165 PM_RAISE(retval, PM_RET_EX_VAL); 01166 return retval; 01167 } 01168 01169 /* Create an int object to hold the result of the conversion */ 01170 retval = int_new(i, &pi); 01171 01172 NATIVE_SET_TOS(pi); 01173 01174 return retval; 01175 01176 } 01177 01178 PmReturn_t 01179 nat_25_string_count(pPmFrame_t *ppframe) 01180 { 01181 01182 pPmObj_t ps1; 01183 pPmObj_t ps2; 01184 uint8_t *pc1; 01185 uint8_t *pc2; 01186 uint8_t *pscan; 01187 uint8_t *pmatch; 01188 uint8_t pc2c0; 01189 uint16_t pc1len; 01190 uint16_t pc2len; 01191 uint16_t n; 01192 uint16_t remaining; 01193 uint16_t cmp; 01194 pPmObj_t pn; 01195 PmReturn_t retval = PM_RET_OK; 01196 01197 /* Raise TypeError if it's not a string or wrong number of args, */ 01198 ps1 = NATIVE_GET_LOCAL(0); 01199 ps2 = NATIVE_GET_LOCAL(1); 01200 if ((OBJ_GET_TYPE(ps1) != OBJ_TYPE_STR) || (NATIVE_GET_NUM_ARGS() != 2) 01201 || (OBJ_GET_TYPE(ps2) != OBJ_TYPE_STR)) 01202 { 01203 PM_RAISE(retval, PM_RET_EX_TYPE); 01204 return retval; 01205 } 01206 01207 pc1 = ((pPmString_t)ps1)->val; 01208 pc2 = ((pPmString_t)ps2)->val; 01209 pc1len = ((pPmString_t)ps1)->length; 01210 pc2len = ((pPmString_t)ps2)->length; 01211 n = 0; 01212 01213 /* Handle some quick special cases (order of if-clauses is important) */ 01214 if (pc2len == 0) 01215 { 01216 n = pc1len + 1; 01217 } 01218 else if (pc1len == 0) 01219 { 01220 n = 0; 01221 } 01222 01223 /* Count the number of matches */ 01224 else 01225 { 01226 n = 0; 01227 remaining = pc1len; 01228 pscan = pc1; 01229 pc2c0 = pc2[0]; 01230 while (pscan <= (pc1 + (pc1len - pc2len))) 01231 { 01232 /* Find the next possible start */ 01233 pmatch = (uint8_t *)memchr(pscan, pc2c0, remaining); 01234 if (pmatch == C_NULL) break; 01235 remaining -= (pmatch - pscan); 01236 pscan = pmatch; 01237 01238 /* If it matches, increase the count, else try the next char */ 01239 cmp = memcmp(pscan, pc2, pc2len); 01240 if (cmp == 0) 01241 { 01242 n++; 01243 pscan += pc2len; 01244 remaining -= pc2len; 01245 } 01246 else 01247 { 01248 pscan++; 01249 remaining--; 01250 } 01251 } 01252 } 01253 01254 retval = int_new(n, &pn); 01255 01256 NATIVE_SET_TOS(pn); 01257 01258 return retval; 01259 01260 } 01261 01262 PmReturn_t 01263 nat_26_string_find(pPmFrame_t *ppframe) 01264 { 01265 01266 pPmObj_t ps1; 01267 pPmObj_t ps2; 01268 uint8_t *pc1; 01269 uint8_t *pc2; 01270 uint8_t *pmatch; 01271 uint16_t pc1len; 01272 uint16_t pc2len; 01273 int32_t n; 01274 pPmObj_t pn; 01275 PmReturn_t retval = PM_RET_OK; 01276 01277 /* Raise TypeError if it's not a string or wrong number of args, */ 01278 ps1 = NATIVE_GET_LOCAL(0); 01279 ps2 = NATIVE_GET_LOCAL(1); 01280 if ((OBJ_GET_TYPE(ps1) != OBJ_TYPE_STR) || (NATIVE_GET_NUM_ARGS() != 2) 01281 || (OBJ_GET_TYPE(ps2) != OBJ_TYPE_STR)) 01282 { 01283 PM_RAISE(retval, PM_RET_EX_TYPE); 01284 return retval; 01285 } 01286 01287 pc1 = ((pPmString_t)ps1)->val; 01288 pc2 = ((pPmString_t)ps2)->val; 01289 pc1len = ((pPmString_t)ps1)->length; 01290 pc2len = ((pPmString_t)ps2)->length; 01291 n = -1; 01292 01293 /* Handle a quick special case */ 01294 if (pc2len == 0) 01295 { 01296 n = 0; 01297 } 01298 01299 /* Try to find the index of the substring */ 01300 else 01301 { 01302 /* Find the next possible start */ 01303 pmatch = (uint8_t *)memchr(pc1, pc2[0], pc1len); 01304 if (pmatch != C_NULL) 01305 { 01306 /* If it matches, calculate the index */ 01307 if (memcmp(pmatch, pc2, pc2len) == 0) 01308 { 01309 n = pmatch - pc1; 01310 } 01311 } 01312 } 01313 01314 retval = int_new(n, &pn); 01315 01316 NATIVE_SET_TOS(pn); 01317 01318 return retval; 01319 01320 } 01321 01322 PmReturn_t 01323 nat_27_sys_exit(pPmFrame_t *ppframe) 01324 { 01325 01326 pPmObj_t pval = C_NULL; 01327 PmReturn_t retval; 01328 01329 /* If no arg given, assume return 0 */ 01330 if (NATIVE_GET_NUM_ARGS() == 0) 01331 { 01332 NATIVE_SET_TOS(PM_ZERO); 01333 } 01334 01335 /* If 1 arg given, put it on stack */ 01336 else if (NATIVE_GET_NUM_ARGS() == 1) 01337 { 01338 pval = NATIVE_GET_LOCAL(0); 01339 NATIVE_SET_TOS(pval); 01340 } 01341 01342 /* If wrong number of args, raise TypeError */ 01343 else 01344 { 01345 PM_RAISE(retval, PM_RET_EX_TYPE); 01346 return retval; 01347 } 01348 01349 /* Raise the SystemExit exception */ 01350 PM_RAISE(retval, PM_RET_EX_EXIT); 01351 return retval; 01352 01353 } 01354 01355 PmReturn_t 01356 nat_28_sys_gc(pPmFrame_t *ppframe) 01357 { 01358 01359 PmReturn_t retval = PM_RET_OK; 01360 #ifdef HAVE_GC 01361 /* If wrong number of args, raise TypeError */ 01362 if (NATIVE_GET_NUM_ARGS() != 0) 01363 { 01364 PM_RAISE(retval, PM_RET_EX_TYPE); 01365 return retval; 01366 } 01367 01368 retval = heap_gcRun(); 01369 #endif 01370 NATIVE_SET_TOS(PM_NONE); 01371 01372 return retval; 01373 01374 } 01375 01376 PmReturn_t 01377 nat_29_sys_getb(pPmFrame_t *ppframe) 01378 { 01379 01380 uint8_t b; 01381 pPmObj_t pb; 01382 PmReturn_t retval; 01383 01384 /* If wrong number of args, raise TypeError */ 01385 if (NATIVE_GET_NUM_ARGS() != 0) 01386 { 01387 PM_RAISE(retval, PM_RET_EX_TYPE); 01388 return retval; 01389 } 01390 01391 retval = plat_getByte(&b); 01392 PM_RETURN_IF_ERROR(retval); 01393 01394 retval = int_new((int32_t)b, &pb); 01395 NATIVE_SET_TOS(pb); 01396 return retval; 01397 01398 } 01399 01400 PmReturn_t 01401 nat_30_sys_heap(pPmFrame_t *ppframe) 01402 { 01403 01404 PmReturn_t retval; 01405 pPmObj_t pavail; 01406 pPmObj_t psize; 01407 pPmObj_t ptup; 01408 uint8_t objid; 01409 01410 /* If wrong number of args, raise TypeError */ 01411 if (NATIVE_GET_NUM_ARGS() != 0) 01412 { 01413 PM_RAISE(retval, PM_RET_EX_TYPE); 01414 return retval; 01415 } 01416 01417 /* Allocate a tuple to store the return values */ 01418 retval = tuple_new(2, &ptup); 01419 PM_RETURN_IF_ERROR(retval); 01420 01421 /* Get the maximum heap size */ 01422 heap_gcPushTempRoot(ptup, &objid); 01423 retval = int_new(heap_getSize (), &psize); 01424 if (retval != PM_RET_OK) 01425 { 01426 heap_gcPopTempRoot(objid); 01427 return retval; 01428 } 01429 01430 /* Allocate an int to hold the amount of heap available */ 01431 retval = int_new(heap_getAvail () - sizeof(PmInt_t), &pavail); 01432 heap_gcPopTempRoot(objid); 01433 PM_RETURN_IF_ERROR(retval); 01434 01435 /* Put the two heap values in the tuple */ 01436 ((pPmTuple_t)ptup)->val[0] = pavail; 01437 ((pPmTuple_t)ptup)->val[1] = psize; 01438 01439 /* Return the tuple on the stack */ 01440 NATIVE_SET_TOS(ptup); 01441 01442 return retval; 01443 01444 } 01445 01446 PmReturn_t 01447 nat_31_sys_putb(pPmFrame_t *ppframe) 01448 { 01449 01450 uint8_t b; 01451 pPmObj_t pb; 01452 PmReturn_t retval; 01453 01454 pb = NATIVE_GET_LOCAL(0); 01455 01456 /* If wrong number of args, raise TypeError */ 01457 if (NATIVE_GET_NUM_ARGS() != 1) 01458 { 01459 PM_RAISE(retval, PM_RET_EX_TYPE); 01460 return retval; 01461 } 01462 01463 /* If arg is not an int, raise TypeError */ 01464 if (OBJ_GET_TYPE(pb) != OBJ_TYPE_INT) 01465 { 01466 PM_RAISE(retval, PM_RET_EX_TYPE); 01467 return retval; 01468 } 01469 01470 b = ((pPmInt_t)pb)->val & 0xFF; 01471 retval = plat_putByte(b); 01472 NATIVE_SET_TOS(PM_NONE); 01473 return retval; 01474 01475 } 01476 01477 PmReturn_t 01478 nat_32_sys_runInThread(pPmFrame_t *ppframe) 01479 { 01480 01481 PmReturn_t retval; 01482 pPmObj_t pf; 01483 01484 /* If wrong number of args, raise TypeError */ 01485 if (NATIVE_GET_NUM_ARGS() != 1) 01486 { 01487 PM_RAISE(retval, PM_RET_EX_TYPE); 01488 return retval; 01489 } 01490 01491 /* If arg is not a function, raise TypeError */ 01492 pf = NATIVE_GET_LOCAL(0); 01493 if (OBJ_GET_TYPE(pf) != OBJ_TYPE_FXN) 01494 { 01495 PM_RAISE(retval, PM_RET_EX_TYPE); 01496 return retval; 01497 } 01498 01499 retval = interp_addThread((pPmFunc_t)pf); 01500 NATIVE_SET_TOS(PM_NONE); 01501 return retval; 01502 01503 } 01504 01505 PmReturn_t 01506 nat_33_sys_time(pPmFrame_t *ppframe) 01507 { 01508 01509 uint32_t t; 01510 pPmObj_t pt; 01511 PmReturn_t retval; 01512 01513 /* If wrong number of args, raise TypeError */ 01514 if (NATIVE_GET_NUM_ARGS() != 0) 01515 { 01516 PM_RAISE(retval, PM_RET_EX_TYPE); 01517 return retval; 01518 } 01519 01520 /* Get the system time (milliseconds since init) */ 01521 retval = plat_getMsTicks(&t); 01522 PM_RETURN_IF_ERROR(retval); 01523 01524 /* 01525 * Raise ValueError if there is an overflow 01526 * (plat_getMsTicks is unsigned; int is signed) 01527 */ 01528 if ((int32_t)t < 0) 01529 { 01530 PM_RAISE(retval, PM_RET_EX_VAL); 01531 return retval; 01532 } 01533 01534 /* Return an int object with the time value */ 01535 retval = int_new((int32_t)t, &pt); 01536 NATIVE_SET_TOS(pt); 01537 return retval; 01538 01539 } 01540 01541 PmReturn_t 01542 nat_34_ipm__getImg(pPmFrame_t *ppframe) 01543 { 01544 01545 PmReturn_t retval; 01546 uint8_t imgType; 01547 uint16_t imgSize; 01548 uint8_t *pchunk; 01549 pPmCodeImgObj_t pimg; 01550 uint16_t i; 01551 uint8_t b; 01552 01553 /* Get the image type */ 01554 retval = plat_getByte(&imgType); 01555 PM_RETURN_IF_ERROR(retval); 01556 01557 /* Quit if a code image type was not received */ 01558 if (imgType != OBJ_TYPE_CIM) 01559 { 01560 PM_RAISE(retval, PM_RET_EX_STOP); 01561 return retval; 01562 } 01563 01564 /* Get the image size (little endien) */ 01565 retval = plat_getByte(&b); 01566 PM_RETURN_IF_ERROR(retval); 01567 imgSize = b; 01568 retval = plat_getByte(&b); 01569 PM_RETURN_IF_ERROR(retval); 01570 imgSize |= (b << 8); 01571 01572 /* Get space for CodeImgObj */ 01573 retval = heap_getChunk(sizeof(PmCodeImgObj_t) + imgSize, &pchunk); 01574 PM_RETURN_IF_ERROR(retval); 01575 pimg = (pPmCodeImgObj_t)pchunk; 01576 OBJ_SET_TYPE(pimg, OBJ_TYPE_CIO); 01577 01578 /* Start the image with the bytes that have already been received */ 01579 i = 0; 01580 pimg->val[i++] = imgType; 01581 pimg->val[i++] = imgSize & 0xFF; 01582 pimg->val[i++] = (imgSize >> 8) & 0xFF; 01583 01584 /* Get the remaining bytes in the image */ 01585 for(; i < imgSize; i++) 01586 { 01587 retval = plat_getByte(&b); 01588 PM_RETURN_IF_ERROR(retval); 01589 01590 pimg->val[i] = b; 01591 } 01592 01593 /* Return the image as a code image object on the stack */ 01594 NATIVE_SET_TOS((pPmObj_t)pimg); 01595 return retval; 01596 01597 } 01598 01599 PmReturn_t 01600 nat_35_ipm_x04(pPmFrame_t *ppframe) 01601 { 01602 01603 NATIVE_SET_TOS(PM_NONE); 01604 return plat_putByte(0x04); 01605 01606 } 01607 01608 /* Native function lookup table */ 01609 pPmNativeFxn_t const std_nat_fxn_table[] = 01610 { 01611 nat_00___bi_chr, 01612 nat_01___bi_dir, 01613 nat_02___bi_eval, 01614 nat_03___bi_globals, 01615 nat_04___bi_id, 01616 nat_05___bi_len, 01617 nat_06___bi_locals, 01618 nat_07___bi_ord, 01619 nat_08___bi_range, 01620 nat_09___bi_sum, 01621 nat_10___bi_type, 01622 nat_11___bi_Co, 01623 nat_12___bi___init__, 01624 nat_13___bi_send, 01625 nat_14___bi_ismain, 01626 nat_15_dict_clear, 01627 nat_16_dict_keys, 01628 nat_17_dict_values, 01629 nat_18_dict_update, 01630 nat_19_list_append, 01631 nat_20_list_index, 01632 nat_21_list_insert, 01633 nat_22_list_pop, 01634 nat_23_list_remove, 01635 nat_24_string_atoi, 01636 nat_25_string_count, 01637 nat_26_string_find, 01638 nat_27_sys_exit, 01639 nat_28_sys_gc, 01640 nat_29_sys_getb, 01641 nat_30_sys_heap, 01642 nat_31_sys_putb, 01643 nat_32_sys_runInThread, 01644 nat_33_sys_time, 01645 nat_34_ipm__getImg, 01646 nat_35_ipm_x04, 01647 };
Generated on Tue Jul 12 2022 23:13:47 by 1.7.2