static void retro_task_threaded_deinit(void) { slock_lock(running_lock); worker_continue = false; scond_signal(worker_cond); slock_unlock(running_lock); sthread_join(worker_thread); scond_free(worker_cond); slock_free(running_lock); slock_free(finished_lock); worker_thread = NULL; worker_cond = NULL; running_lock = NULL; finished_lock = NULL; }
static void onDestroy(ANativeActivity* activity) { struct android_app *android_app = (struct android_app*)activity->instance; if (!android_app) return; RARCH_LOG("onDestroy: %p\n", activity); sthread_join(android_app->thread); RARCH_LOG("Joined with RetroArch native thread.\n"); close(android_app->msgread); close(android_app->msgwrite); scond_free(android_app->cond); slock_free(android_app->mutex); free(android_app); }
void autosave_free(autosave_t *handle) { if (!handle) return; slock_lock(handle->cond_lock); handle->quit = true; slock_unlock(handle->cond_lock); scond_signal(handle->cond); sthread_join(handle->thread); slock_free(handle->lock); slock_free(handle->cond_lock); scond_free(handle->cond); free(handle->buffer); free(handle); }
int main(int argc, char **argv) { sthread_t thr; void *ret; int i; printf("Testing sthread_join, impl: %s\n", (sthread_get_impl() == STHREAD_PTHREAD_IMPL) ? "pthread" : "user"); sthread_init(); if ((thr = sthread_create(thread_start, (void*)1, 1)) == NULL) { exit(-1); } sthread_join(thr, &ret); printf("back in main\n"); return 0; }
static void deinit_thread(ffemu_t *handle) { if (handle->thread) { slock_lock(handle->cond_lock); handle->alive = false; handle->can_sleep = false; slock_unlock(handle->cond_lock); scond_signal(handle->cond); sthread_join(handle->thread); slock_free(handle->lock); slock_free(handle->cond_lock); scond_free(handle->cond); handle->thread = NULL; } }
static void sunxi_set_texture_enable(void *data, bool state, bool full_screen) { struct sunxi_video *_dispvars = (struct sunxi_video*)data; /* If it wasn't active and starts being active... */ if (!_dispvars->menu_active && state) { /* Stop the vsync thread. */ _dispvars->keep_vsync = false; sthread_join(_dispvars->vsync_thread); } /* If it was active but now it isn't active anymore... */ if (_dispvars->menu_active && !state) { _dispvars->keep_vsync = true; _dispvars->vsync_thread = sthread_create(sunxi_vsync_thread_func, _dispvars); } _dispvars->menu_active = state; }
static void test_smalloc(void) { tag_t t = tag_new(); char *crap; sc_t sc; sthread_t st; crap = smalloc(t, 1024); strcpy(crap, "hi"); sc_init(&sc); sc_mem_add(&sc, t, PROT_READ | PROT_WRITE); if (sthread_create(&st, &sc, smalloc_st, crap)) err(1, "sthread_create()"); if (sthread_join(st, NULL)) err(1, "sthread_join()"); if (strcmp(crap, "bye") != 0) errx(1, "master crap is %s", crap); }
static void libusb_hid_free(void *data) { libusb_hid_t *hid = (libusb_hid_t*)data; while(adapters.next) if (remove_adapter(hid, adapters.next->device) == -1) RARCH_ERR("could not remove device %p\n", adapters.next->device); if (hid->poll_thread) { hid->quit = 1; sthread_join(hid->poll_thread); } pad_connection_destroy(hid->slots); libusb_hotplug_deregister_callback(hid->ctx, hid->hp); libusb_exit(hid->ctx); free(hid); }
int main(int argc, char **argv) { int n; int *arg[MAXTHREADS]; int *retptr; sthread_t child[MAXTHREADS]; printf("Testing sthread_create, impl: %s\n", (sthread_get_impl() == STHREAD_PTHREAD_IMPL) ? "pthread" : "user"); if ( argv[1] ) nThreads = atoi(argv[1]); if ( nThreads > MAXTHREADS ) nThreads = MAXTHREADS; printf("Creating %d threads\n", nThreads); sthread_init(); for (n = 0; n < nThreads; ++n) { arg[n] = malloc(sizeof(arg[n])); if (!arg[n]) { printf("malloc() failed\n"); exit(1); } *(arg[n]) = n; child[n] = sthread_create(thread_start, (void*) arg[n], 1); if (child[n] == NULL) { printf("sthread_create failed\n"); exit(1); } } for (n = nThreads - 1; n >= 0; --n) { retptr = (int *)sthread_join(child[n]); printf("main: joined with %d: %d\n", n, *retptr); free(arg[n]); } return 0; }
static int remove_adapter(void *data, struct libusb_device *dev) { struct libusb_adapter *adapter = (struct libusb_adapter*)&adapters; struct libusb_hid *hid = (struct libusb_hid*)data; while (adapter->next == NULL) return -1; if (adapter->next->device == dev) { struct libusb_adapter *new_next = NULL; const char *name = (const char*)adapter->next->name; input_config_autoconfigure_disconnect(adapter->slot, name); adapter->next->quitting = true; sthread_join(adapter->next->thread); pad_connection_pad_deinit(&hid->slots[adapter->slot], adapter->slot); slock_free(adapter->send_control_lock); fifo_free(adapter->send_control_buffer); libusb_release_interface(adapter->next->handle, adapter->next->interface_number); libusb_close(adapter->next->handle); new_next = adapter->next->next; free(adapter->next); adapter->next = new_next; return 0; } adapter = adapter->next; return -1; }
void rarch_softfilter_free(rarch_softfilter_t *filt) { unsigned i = 0; (void)i; if (!filt) return; free(filt->packets); if (filt->impl && filt->impl_data) filt->impl->destroy(filt->impl_data); #ifdef HAVE_DYLIB for (i = 0; i < filt->num_plugs; i++) { if (filt->plugs[i].lib) dylib_close(filt->plugs[i].lib); } free(filt->plugs); #endif #ifdef HAVE_THREADS for (i = 0; i < filt->threads; i++) { if (!filt->thread_data[i].thread) continue; slock_lock(filt->thread_data[i].lock); filt->thread_data[i].die = true; scond_signal(filt->thread_data[i].cond); slock_unlock(filt->thread_data[i].lock); sthread_join(filt->thread_data[i].thread); slock_free(filt->thread_data[i].lock); scond_free(filt->thread_data[i].cond); } free(filt->thread_data); #endif free(filt); }
void Task::Impl::shutdown() { slock_lock(this->mutex); if (!this->_isThreadRunning) { slock_unlock(this->mutex); return; } this->workFunc = NULL; this->exitThread = true; scond_signal(this->condWork); slock_unlock(this->mutex); sthread_join(this->_thread); slock_lock(this->mutex); this->_isThreadRunning = false; slock_unlock(this->mutex); }
static void sunxi_gfx_free(void *data) { struct sunxi_video *_dispvars = (struct sunxi_video*)data; /* Stop the vsync thread and wait for it to join. */ /* When menu is active, vsync thread has already been stopped. */ if (!_dispvars->menu_active) { _dispvars->keep_vsync = false; sthread_join(_dispvars->vsync_thread); } slock_free(_dispvars->pending_mutex); scond_free(_dispvars->vsync_condition); free(_dispvars->pages); /* Restore text console contents and reactivate cursor blinking. */ sunxi_restore_console(_dispvars); sunxi_disp_close(_dispvars->sunxi_disp); free(_dispvars); }
static void thread_free(void *data) { thread_video_t *thr = (thread_video_t*)data; if (!thr) return; thread_send_cmd(thr, CMD_FREE); thread_wait_reply(thr, CMD_FREE); sthread_join(thr->thread); #if defined(HAVE_MENU) free(thr->texture.frame); #endif free(thr->frame.buffer); slock_free(thr->frame.lock); slock_free(thr->lock); scond_free(thr->cond_cmd); scond_free(thr->cond_thread); RARCH_LOG("Threaded video stats: Frames pushed: %u, Frames dropped: %u.\n", thr->hit_count, thr->miss_count); free(thr); }
static void audio_thread_free(void *data) { audio_thread_t *thr = (audio_thread_t*)data; if (!thr) return; if (thr->thread) { slock_lock(thr->lock); thr->stopped = false; thr->alive = false; scond_signal(thr->cond); slock_unlock(thr->lock); sthread_join(thr->thread); } if (thr->lock) slock_free(thr->lock); if (thr->cond) scond_free(thr->cond); free(thr); }
static int add_adapter(void *data, struct libusb_device *dev) { int rc; struct libusb_device_descriptor desc; const char *device_name = NULL; struct libusb_adapter *old_head = NULL; struct libusb_hid *hid = (struct libusb_hid*)data; struct libusb_adapter *adapter = (struct libusb_adapter*) calloc(1, sizeof(struct libusb_adapter)); if (!adapter) return -1; if (!hid) { free(adapter); RARCH_ERR("Allocation of adapter failed.\n"); return -1; } rc = libusb_get_device_descriptor(dev, &desc); if (rc != LIBUSB_SUCCESS) { RARCH_ERR("Error getting device descriptor.\n"); goto error; } adapter->device = dev; libusb_get_description(adapter->device, adapter); if (adapter->endpoint_in == 0) { RARCH_ERR("Could not find HID config for device.\n"); goto error; } rc = libusb_open (adapter->device, &adapter->handle); if (rc != LIBUSB_SUCCESS) { RARCH_ERR("Error opening device 0x%p (VID/PID: %04x:%04x).\n", (void*)adapter->device, desc.idVendor, desc.idProduct); goto error; } if (desc.iManufacturer) { libusb_get_string_descriptor_ascii(adapter->handle, desc.iManufacturer, adapter->manufacturer_name, sizeof(adapter->manufacturer_name)); #if 0 RARCH_ERR(" Adapter Manufacturer name: %s\n", adapter->manufacturer_name); #endif } if (desc.iProduct) { libusb_get_string_descriptor_ascii(adapter->handle, desc.iProduct, adapter->name, sizeof(adapter->name)); #if 0 RARCH_ERR(" Adapter name: %s\n", adapter->name); #endif } device_name = (const char*)adapter->name; if (string_is_empty((const char*)adapter->name)) goto error; adapter->send_control_lock = slock_new(); adapter->send_control_buffer = fifo_new(4096); if (!adapter->send_control_lock || !adapter->send_control_buffer) { RARCH_ERR("Error creating send control buffer.\n"); goto error; } adapter->slot = pad_connection_pad_init(hid->slots, device_name, desc.idVendor, desc.idProduct, adapter, &libusb_hid_device_send_control); if (adapter->slot == -1) goto error; if (!pad_connection_has_interface(hid->slots, adapter->slot)) { RARCH_ERR(" Interface not found (%s).\n", adapter->name); goto error; } RARCH_LOG("Interface found: [%s].\n", adapter->name); if (libusb_kernel_driver_active(adapter->handle, 0) == 1 && libusb_detach_kernel_driver(adapter->handle, 0)) { RARCH_ERR("Error detaching handle 0x%p from kernel.\n", adapter->handle); goto error; } rc = libusb_claim_interface(adapter->handle, adapter->interface_number); if (rc != LIBUSB_SUCCESS) { RARCH_ERR("Error claiming interface %d .\n", adapter->interface_number); goto error; } RARCH_LOG("Device 0x%p attached (VID/PID: %04x:%04x).\n", adapter->device, desc.idVendor, desc.idProduct); libusb_hid_device_add_autodetect(adapter->slot, device_name, libusb_hid.ident, desc.idVendor, desc.idProduct); adapter->hid = hid; adapter->thread = sthread_create(adapter_thread, adapter); if (!adapter->thread) { RARCH_ERR("Error initializing adapter thread.\n"); goto error; } old_head = adapters.next; adapters.next = adapter; adapter->next = old_head; return 0; error: if (adapter->thread) sthread_join(adapter->thread); if (adapter->send_control_lock) slock_free(adapter->send_control_lock); if (adapter->send_control_buffer) fifo_free(adapter->send_control_buffer); if (adapter) free(adapter); return -1; }
int main(int argc, char **argv) { int sent, checks, i; sthread_t child[MAXTHREADS]; printf("Testing sthread_cond_*, impl: %s\n", (sthread_get_impl() == STHREAD_PTHREAD_IMPL) ? "pthread" : "user"); assert(num_threads <= MAXTHREADS); sthread_init(); mutex = sthread_mutex_init(); avail_cond = sthread_cond_init(); sthread_mutex_lock(mutex); for (i = 0; i < num_threads; i++) { child[i] = sthread_create(thread_start, NULL, 1); if (child[i] == NULL) { printf("sthread_create %d failed\n", i); exit(1); } } assert(transfered == 0); /* This should let the other thread run at some point. */ sthread_mutex_unlock(mutex); /* Send a bunch of things for the other threads to take */ sent = 0; while (sent < max_transfer) { sthread_mutex_lock(mutex); waiting++; sent++; sthread_cond_signal(avail_cond); sthread_mutex_unlock(mutex); sthread_yield(); } printf("Sent %d\n", sent); /* Now give the other threads 100 tries to get * them all across. We assume that's enough * for the sake of not running this test forever. */ checks = 10000; //arbitrary?? while (checks > 0) { sthread_mutex_lock(mutex); if (transfered != max_transfer) checks--; else { /* broadcast to let the consumers know we've * finished, so they can exit * (othrewise, they may still be holding the lock * when we try to free it below) */ sthread_cond_broadcast(avail_cond); checks = -1; } sthread_mutex_unlock(mutex); sthread_yield(); } if (checks == -1) { /* Wait for child threads to finish, otherwise we could try to * free the mutex before they've unlocked it! */ printf("joining on children\n"); for (i = 0; i < num_threads; i++) { sthread_join(child[i]); printf("joined with child %d\n", i); } printf("sthread_cond passed\n"); } else { printf("*** sthread_cond failed\n"); /* If we failed, don't bother joining on threads. */ } sthread_mutex_free(mutex); sthread_cond_free(avail_cond); return 0; }
static int add_adapter(void *data, usb_device_entry *dev) { int rc; usb_devdesc desc; const char *device_name = NULL; struct wiiusb_adapter *old_head = NULL; struct wiiusb_hid *hid = (struct wiiusb_hid*)data; struct wiiusb_adapter *adapter = (struct wiiusb_adapter*) calloc(1, sizeof(struct wiiusb_adapter)); (void)rc; if (!adapter) return -1; if (!hid) { free(adapter); RARCH_ERR("Allocation of adapter failed.\n"); return -1; } if (USB_OpenDevice(dev->device_id, dev->vid, dev->pid, &adapter->handle) < 0) { RARCH_ERR("Error opening device 0x%p (VID/PID: %04x:%04x).\n", (void*)&adapter->device, dev->vid, dev->pid); free(adapter); return -1; } adapter->device = *dev; USB_GetDescriptors(adapter->handle, &desc); wiiusb_get_description(&adapter->device, adapter, &desc); if (adapter->endpoint_in == 0) { RARCH_ERR("Could not find HID config for device.\n"); goto error; } if (desc.iManufacturer) { USB_GetAsciiString(adapter->handle, desc.iManufacturer, 0, sizeof(adapter->manufacturer_name), adapter->manufacturer_name); #if 0 RARCH_ERR(" Adapter Manufacturer name: %s\n", adapter->manufacturer_name); #endif } if (desc.iProduct) { USB_GetAsciiString(adapter->handle, desc.iProduct, 0, sizeof(adapter->name), adapter->name); #if 0 RARCH_ERR(" Adapter name: %s\n", adapter->name); #endif } device_name = (const char *)adapter->name; adapter->send_control_lock = slock_new(); adapter->send_control_buffer = fifo_new(4096); if (!adapter->send_control_lock || !adapter->send_control_buffer) { RARCH_ERR("Error creating send control buffer.\n"); goto error; } adapter->slot = pad_connection_pad_init(hid->slots, device_name, desc.idVendor, desc.idProduct, adapter, &wiiusb_hid_device_send_control); if (adapter->slot == -1) goto error; if (!pad_connection_has_interface(hid->slots, adapter->slot)) { RARCH_ERR(" Interface not found (%s).\n", adapter->name); goto error; } RARCH_LOG("Interface found: [%s].\n", adapter->name); RARCH_LOG("Device 0x%p attached (VID/PID: %04x:%04x).\n", adapter->device, desc.idVendor, desc.idProduct); wiiusb_hid_device_add_autodetect(adapter->slot, device_name, wiiusb_hid.ident, desc.idVendor, desc.idProduct); adapter->hid = hid; adapter->thread = sthread_create(adapter_thread, adapter); if (!adapter->thread) { RARCH_ERR("Error initializing adapter thread.\n"); goto error; } adapter->data = memalign(32, 2048); old_head = adapters.next; adapters.next = adapter; adapter->next = old_head; USB_FreeDescriptors(&desc); USB_DeviceRemovalNotifyAsync(adapter->handle, wiiusb_hid_removalnotify_cb, (void *)hid); return 0; error: if (adapter->thread) sthread_join(adapter->thread); if (adapter->send_control_lock) slock_free(adapter->send_control_lock); if (adapter->send_control_buffer) fifo_free(adapter->send_control_buffer); if (adapter) free(adapter); USB_FreeDescriptors(&desc); USB_CloseDevice(&adapter->handle); return -1; }