xref: /openbmc/qemu/accel/dummy-cpus.c (revision d16cab541ab9217977e2a39abf3d79f914146741)
19ce84a0dSJason Andryuk /*
29ce84a0dSJason Andryuk  * Dummy cpu thread code
39ce84a0dSJason Andryuk  *
49ce84a0dSJason Andryuk  * Copyright IBM, Corp. 2011
59ce84a0dSJason Andryuk  *
69ce84a0dSJason Andryuk  * Authors:
79ce84a0dSJason Andryuk  *  Anthony Liguori   <aliguori@us.ibm.com>
89ce84a0dSJason Andryuk  *
99ce84a0dSJason Andryuk  * This work is licensed under the terms of the GNU GPL, version 2 or later.
109ce84a0dSJason Andryuk  * See the COPYING file in the top-level directory.
119ce84a0dSJason Andryuk  *
129ce84a0dSJason Andryuk  */
139ce84a0dSJason Andryuk 
149ce84a0dSJason Andryuk #include "qemu/osdep.h"
159ce84a0dSJason Andryuk #include "qemu/rcu.h"
169ce84a0dSJason Andryuk #include "sysemu/cpus.h"
179ce84a0dSJason Andryuk #include "qemu/guest-random.h"
189ce84a0dSJason Andryuk #include "qemu/main-loop.h"
199ce84a0dSJason Andryuk #include "hw/core/cpu.h"
209ce84a0dSJason Andryuk 
dummy_cpu_thread_fn(void * arg)219ce84a0dSJason Andryuk static void *dummy_cpu_thread_fn(void *arg)
229ce84a0dSJason Andryuk {
239ce84a0dSJason Andryuk     CPUState *cpu = arg;
249ce84a0dSJason Andryuk 
259ce84a0dSJason Andryuk     rcu_register_thread();
269ce84a0dSJason Andryuk 
27*195801d7SStefan Hajnoczi     bql_lock();
289ce84a0dSJason Andryuk     qemu_thread_get_self(cpu->thread);
299ce84a0dSJason Andryuk     cpu->thread_id = qemu_get_thread_id();
309ce84a0dSJason Andryuk     current_cpu = cpu;
319ce84a0dSJason Andryuk 
32c9923550SXuzhou Cheng #ifndef _WIN32
33c9923550SXuzhou Cheng     sigset_t waitset;
34c9923550SXuzhou Cheng     int r;
35c9923550SXuzhou Cheng 
369ce84a0dSJason Andryuk     sigemptyset(&waitset);
379ce84a0dSJason Andryuk     sigaddset(&waitset, SIG_IPI);
38c9923550SXuzhou Cheng #endif
399ce84a0dSJason Andryuk 
409ce84a0dSJason Andryuk     /* signal CPU creation */
419ce84a0dSJason Andryuk     cpu_thread_signal_created(cpu);
429ce84a0dSJason Andryuk     qemu_guest_random_seed_thread_part2(cpu->random_seed);
439ce84a0dSJason Andryuk 
449ce84a0dSJason Andryuk     do {
45*195801d7SStefan Hajnoczi         bql_unlock();
46c9923550SXuzhou Cheng #ifndef _WIN32
479ce84a0dSJason Andryuk         do {
489ce84a0dSJason Andryuk             int sig;
499ce84a0dSJason Andryuk             r = sigwait(&waitset, &sig);
509ce84a0dSJason Andryuk         } while (r == -1 && (errno == EAGAIN || errno == EINTR));
519ce84a0dSJason Andryuk         if (r == -1) {
529ce84a0dSJason Andryuk             perror("sigwait");
539ce84a0dSJason Andryuk             exit(1);
549ce84a0dSJason Andryuk         }
55c9923550SXuzhou Cheng #else
56c9923550SXuzhou Cheng         qemu_sem_wait(&cpu->sem);
57c9923550SXuzhou Cheng #endif
58*195801d7SStefan Hajnoczi         bql_lock();
599ce84a0dSJason Andryuk         qemu_wait_io_event(cpu);
609ce84a0dSJason Andryuk     } while (!cpu->unplug);
619ce84a0dSJason Andryuk 
62*195801d7SStefan Hajnoczi     bql_unlock();
639ce84a0dSJason Andryuk     rcu_unregister_thread();
649ce84a0dSJason Andryuk     return NULL;
659ce84a0dSJason Andryuk }
669ce84a0dSJason Andryuk 
dummy_start_vcpu_thread(CPUState * cpu)679ce84a0dSJason Andryuk void dummy_start_vcpu_thread(CPUState *cpu)
689ce84a0dSJason Andryuk {
699ce84a0dSJason Andryuk     char thread_name[VCPU_THREAD_NAME_SIZE];
709ce84a0dSJason Andryuk 
719ce84a0dSJason Andryuk     snprintf(thread_name, VCPU_THREAD_NAME_SIZE, "CPU %d/DUMMY",
729ce84a0dSJason Andryuk              cpu->cpu_index);
739ce84a0dSJason Andryuk     qemu_thread_create(cpu->thread, thread_name, dummy_cpu_thread_fn, cpu,
749ce84a0dSJason Andryuk                        QEMU_THREAD_JOINABLE);
75c9923550SXuzhou Cheng #ifdef _WIN32
76c9923550SXuzhou Cheng     qemu_sem_init(&cpu->sem, 0);
77c9923550SXuzhou Cheng #endif
789ce84a0dSJason Andryuk }
79