void pa_shutdown(){ if(source_names != NULL){ delete source_names; } context_stop(); }
static void run_safe_events(void * arg) { LINK * qp; pid_t mem; if ((uintptr_t)arg != safe_event_generation) return; assert(safe_event_list != NULL); assert(are_channels_suspended(suspend_group)); safe_event_pid_count = 0; mem = safe_event_list->mem; for (qp = context_root.next; qp != &context_root; qp = qp->next) { Context * ctx = ctxl2ctxp(qp); if (ctx->exited || ctx->exiting || ctx->stopped || !context_has_state(ctx)) { ctx->pending_safe_event = 0; continue; } if (mem > 0 && ctx->mem != mem) { ctx->pending_safe_event = 0; continue; } if (!ctx->pending_step || ctx->pending_safe_event >= STOP_ALL_MAX_CNT / 2) { if (context_stop(ctx) < 0) { int error = errno; #ifdef _WRS_KERNEL if (error == S_vxdbgLib_INVALID_CTX) { /* Most often this means that context has exited, * but exit event is not delivered yet. * Not an error. */ error = 0; } #endif if (error) { trace(LOG_ALWAYS, "error: can't temporary stop pid %d; error %d: %s", ctx->pid, error, errno_to_str(error)); } } assert(!ctx->stopped); } if (ctx->pending_safe_event >= STOP_ALL_MAX_CNT) { trace(LOG_ALWAYS, "error: can't temporary stop pid %d; error: timeout", ctx->pid); ctx->exiting = 1; ctx->pending_safe_event = 0; } else { ctx->pending_safe_event++; safe_event_pid_count++; } } while (safe_event_list) { Trap trap; SafeEvent * i = safe_event_list; assert((uintptr_t)arg == safe_event_generation); if (safe_event_pid_count > 0) { post_event_with_delay(run_safe_events, (void *)++safe_event_generation, STOP_ALL_TIMEOUT); return; } if (mem > 0 && i->mem != mem) { post_event(run_safe_events, (void *)++safe_event_generation); return; } assert(is_all_stopped(i->mem)); safe_event_list = i->next; if (set_trap(&trap)) { i->done(i->arg); clear_trap(&trap); } else { trace(LOG_ALWAYS, "Unhandled exception in \"safe\" event dispatch: %d %s", trap.error, errno_to_str(trap.error)); } loc_free(i); if ((uintptr_t)arg != safe_event_generation) return; } channels_resume(suspend_group); cmdline_resume(); /* Lazily continue execution of temporary stopped contexts */ post_event(continue_temporary_stopped, (void *)safe_event_generation); }