static void semis_dbg(void) { struct debug_xt *debug_xt_item, *debug_xt_up = NULL; /* If current semis is in our debug xt list, disable debug mode */ debug_xt_item = debug_xt_list; while (debug_xt_item->next) { if (debug_xt_item->xt_semis == PC) { if (debug_xt_item->mode != DEBUG_MODE_STEPUP) { /* Handle the normal case */ fstrncpy(xtname, lfa2nfa(debug_xt_item->xt_docol - sizeof(cell)), MAXNFALEN); printf_console("\n[ Finished %s ] ", xtname); /* Reset to step mode in case we were in trace mode */ debug_xt_item->mode = DEBUG_MODE_STEP; } else { /* This word requires execution of the debugger "Up" * semantics. However we can't do this here since we * are iterating through the debug list, and we need * to change it. So we do it afterwards. */ debug_xt_up = debug_xt_item; } } debug_xt_item = debug_xt_item->next; } /* Execute debugger "Up" semantics if required */ if (debug_xt_up) { /* Only add the parent word if it is not within the trampoline */ if (rstack[rstackcnt] != (cell)pointer2cell(&trampoline[1])) { del_debug_xt(debug_xt_up->xt_docol); add_debug_xt(findxtfromcell(rstack[rstackcnt])); fstrncpy(xtname, lfa2nfa(findxtfromcell(rstack[rstackcnt]) - sizeof(cell)), MAXNFALEN); printf_console("\n[ Up to %s ] ", xtname); } else { fstrncpy(xtname, lfa2nfa(findxtfromcell(debug_xt_up->xt_docol) - sizeof(cell)), MAXNFALEN); printf_console("\n[ Finished %s (Unable to go up, hit trampoline) ] ", xtname); del_debug_xt(debug_xt_up->xt_docol); } debug_xt_up = NULL; } PC = POPR(); }
void CreateSurfaceGLES(EAGLSurfaceDesc* surface) { GLuint oldRenderbuffer; GLES_CHK( glGetIntegerv(GL_RENDERBUFFER_BINDING_OES, (GLint *) &oldRenderbuffer) ); DestroySurfaceGLES(surface); InitEAGLLayer(surface->eaglLayer, surface->use32bitColor); GLES_CHK( glGenRenderbuffersOES(1, &surface->renderbuffer) ); GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_OES, surface->renderbuffer) ); if( !AllocateRenderBufferStorageFromEAGLLayer(surface->eaglLayer) ) { GLES_CHK( glDeleteRenderbuffersOES(1, &surface->renderbuffer) ); GLES_CHK( glBindRenderbufferOES(GL_RENDERBUFFER_BINDING_OES, oldRenderbuffer) ); printf_console("FAILED allocating render buffer storage from gles context\n"); return; } GLES_CHK( glGenFramebuffersOES(1, &surface->framebuffer) ); UNITY_DBG_LOG ("glBindFramebufferOES(GL_FRAMEBUFFER_OES, %d) :: AppCtrl\n", surface->framebuffer); GLES_CHK( glBindFramebufferOES(GL_FRAMEBUFFER_OES, surface->framebuffer) ); gDefaultFBO = surface->framebuffer; UNITY_DBG_LOG ("glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, %d) :: AppCtrl\n", surface->renderbuffer); GLES_CHK( glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, surface->renderbuffer) ); CreateSurfaceMultisampleBuffersGLES(surface); }
static int add_debug_xt( ucell xt ) { struct debug_xt *debug_xt_item; /* If the xt CFA isn't DOCOL then issue a warning and do nothing */ if (read_ucell(cell2pointer(xt)) != DOCOL) { printf_console("\nprimitive words cannot be debugged\n"); return 0; } /* If this xt is already in the list, do nothing but indicate success */ for (debug_xt_item = debug_xt_list; debug_xt_item->next != NULL; debug_xt_item = debug_xt_item->next) if (debug_xt_item->xt_docol == xt) return 1; /* We already have the CFA (PC) indicating the starting cell of the word, however we also need the ending cell too (we cannot rely on the rstack as it can be arbitrarily changed by a forth word). Hence the use of findsemis() */ /* Otherwise add to the head of the linked list */ debug_xt_item = malloc(sizeof(struct debug_xt)); debug_xt_item->xt_docol = xt; debug_xt_item->xt_semis = findsemis(xt); debug_xt_item->mode = DEBUG_MODE_NONE; debug_xt_item->next = debug_xt_list; debug_xt_list = debug_xt_item; /* Indicate debug mode change */ interruptforth |= FORTH_INTSTAT_DBG; /* Success */ return 1; }
void CheckGLESError(const char* file, int line) { GLenum e = glGetError(); if( e ) { printf_console ("OpenGLES error 0x%04X in %s:%i\n", e, file, line); } }
bool Application::StartMono() { domain = load_domain(); if (!domain) { printf_console("Error loading domain\n"); return false; } return true; }
static void display_dbg_rstack ( void ) { /* Display rstack contents between parentheses */ int i; if (rstackcnt == 0) { printf_console(" ( Empty ) "); return; } else { printf_console("\nR: ( "); for (i = 1; i <= rstackcnt; i++) { if (i != 1) printf_console(" "); printf_console("%" FMT_CELL_x, rstack[i]); } printf_console(" ) \n"); } }
void unload_domain() { MonoDomain* old_domain = mono_domain_get(); if (old_domain && old_domain != mono_get_root_domain()) { if (!mono_domain_set(mono_get_root_domain(), false)) printf_console("Error setting domain\n"); mono_thread_pop_appdomain_ref(); mono_domain_unload(old_domain); } //unloading a domain is also a nice point in time to have the GC run. mono_gc_collect(mono_gc_max_generation()); }
static void do_debug_xt(void) { ucell xt = POP(); /* Add to the debug list */ if (add_debug_xt(xt)) { /* Display debug banner */ printf_console(DEBUG_BANNER); /* Indicate change to debug mode */ interruptforth |= FORTH_INTSTAT_DBG; } }
MonoDomain* load_domain() { MonoDomain* newDomain = mono_domain_create_appdomain("CCubed Child Domain", NULL); if (!newDomain) { printf("Error creating domain\n"); return nullptr; } mono_thread_push_appdomain_ref(newDomain); if (!mono_domain_set(newDomain, false)) { printf_console("Error setting domain\n"); return nullptr; } return mono_domain_get(); }
static void docol_dbg(void) { /* DOCOL */ struct debug_xt *debug_xt_item; PUSHR(PC); PC = read_ucell(cell2pointer(PC)); /* If current xt is in our debug xt list, display word name */ debug_xt_item = debug_xt_list; while (debug_xt_item->next) { if (debug_xt_item->xt_docol == PC) { fstrncpy(xtname, lfa2nfa(PC - sizeof(cell)), MAXNFALEN); printf_console("\n: %s ", xtname); /* Step mode is the default */ debug_xt_item->mode = DEBUG_MODE_STEP; } debug_xt_item = debug_xt_item->next; } dbg_interp_printk("docol_dbg: %s\n", cell2pointer(lfa2nfa(PC - sizeof(cell)))); }
bool Application::StartMonoAndLoadAssemblies() { // shutdown the child domain StopMono(); // create a new child domain if (!StartMono()) { mono_environment_exitcode_set(-1); return true; } std::string dll = "EmbedThings.dll"; std::string filename = File::BuildRootedPath(assemblyDir, dll); size_t length; // read our entry point assembly char* data = File::Read(filename.c_str(), &length); printf_console("Loading %s into Domain\n", dll.c_str()); MonoImageOpenStatus status; // open the assembly from the data we read, so we never lock files auto image = mono_image_open_from_data_with_name(data, length, true /* copy data */, &status, false /* ref only */, filename.c_str()); if (status != MONO_IMAGE_OK || image == nullptr) { printf_console("Failed loading assembly %s\n", dll); return true; } // load the assembly auto assembly = mono_assembly_load_from_full(image, filename.c_str(), &status, false); if (status != MONO_IMAGE_OK || assembly == nullptr) { mono_image_close(image); printf_console("Failed loading assembly %s\n", dll); return true; } // save the image for lookups later and for cleaning up images.push_back(image); if (!assembly) { printf_console("Couldn't find assembly %s\n", filename.c_str()); return true; } // locate the class we want to load MonoClass* klass = mono_class_from_name(image, "EmbedThings", "EntryPoint"); if (klass == nullptr) { printf_console("Failed loading class %s\n", "EmbedThings.EntryPoint"); return true; } // create the class (doesn't run constructors) MonoObject* obj = mono_object_new(mono_domain_get(), klass); if (obj == nullptr) { printf_console("Failed loading class instance %s\n", "EmbedThings.EntryPoint"); return true; } // initialize the class instance (runs default constructors) mono_runtime_object_init(obj); if (obj == nullptr) { printf_console("Failed initializing class instance %s\n", "EmbedThings.EntryPoint"); return true; } // save the class instance for lookups later instances.push_back(obj); // find the Run() method auto method = find_method(klass, "Run"); MonoObject *result, *exception; // call the Run method. This will block until the managed code decides to exit result = mono_runtime_invoke(method, obj, NULL, NULL); int val = *(int*)mono_object_unbox(result); // if the managed code returns with 0, it wants to exit completely if (val == 0) { return true; } return false; }
static void reload() { printf_console("Reloading\n"); auto app = Manager::GetApplication(); app->FireOnReload(); }
static void do_source_dbg(struct debug_xt *debug_xt_item) { /* Forth source debugger implementation */ char k, done = 0; /* Display current dstack */ display_dbg_dstack(); printf_console("\n"); fstrncpy(xtname, lfa2nfa(read_ucell(cell2pointer(PC)) - sizeof(cell)), MAXNFALEN); printf_console("%p: %s ", cell2pointer(PC), xtname); /* If in trace mode, we just carry on */ if (debug_xt_item->mode == DEBUG_MODE_TRACE) { return; } /* Otherwise in step mode, prompt for a keypress */ k = getchar_console(); /* Only proceed if done is true */ while (!done) { switch (k) { case ' ': case '\n': /* Perform a single step */ done = 1; break; case 'u': case 'U': /* Up - unmark current word for debug, mark its caller for * debugging and finish executing current word */ /* Since this word could alter the rstack during its execution, * we only know the caller when (semis) is called for this xt. * Hence we mark the xt as a special DEBUG_MODE_STEPUP which * means we run as normal, but schedule the xt for deletion * at its corresponding (semis) word when we know the rstack * will be set to its final parent value */ debug_xt_item->mode = DEBUG_MODE_STEPUP; done = 1; break; case 'd': case 'D': /* Down - mark current word for debug and step into it */ done = add_debug_xt(read_ucell(cell2pointer(PC))); if (!done) { k = getchar_console(); } break; case 't': case 'T': /* Trace mode */ debug_xt_item->mode = DEBUG_MODE_TRACE; done = 1; break; case 'r': case 'R': /* Display rstack */ display_dbg_rstack(); done = 0; k = getchar_console(); break; case 'f': case 'F': /* Start subordinate Forth interpreter */ PUSHR(PC - sizeof(cell)); PC = findword("outer-interpreter") + sizeof(ucell); /* Save rstack position for when we return */ dbgrstackcnt = rstackcnt; done = 1; break; default: /* Display debug banner */ printf_console(DEBUG_BANNER); k = getchar_console(); } } }