Changeset View
Changeset View
Standalone View
Standalone View
sys/kern/kern_membarrier.c
Show First 20 Lines • Show All 45 Lines • ▼ Show 20 Lines | |||||
#define MEMBARRIER_SUPPORTED_CMDS ( \ | #define MEMBARRIER_SUPPORTED_CMDS ( \ | ||||
MEMBARRIER_CMD_GLOBAL | \ | MEMBARRIER_CMD_GLOBAL | \ | ||||
MEMBARRIER_CMD_GLOBAL_EXPEDITED | \ | MEMBARRIER_CMD_GLOBAL_EXPEDITED | \ | ||||
MEMBARRIER_CMD_REGISTER_GLOBAL_EXPEDITED | \ | MEMBARRIER_CMD_REGISTER_GLOBAL_EXPEDITED | \ | ||||
MEMBARRIER_CMD_PRIVATE_EXPEDITED | \ | MEMBARRIER_CMD_PRIVATE_EXPEDITED | \ | ||||
MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED | \ | MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED | \ | ||||
MEMBARRIER_CMD_PRIVATE_EXPEDITED_SYNC_CORE | \ | MEMBARRIER_CMD_PRIVATE_EXPEDITED_SYNC_CORE | \ | ||||
MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_SYNC_CORE) | MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_SYNC_CORE | \ | ||||
MEMBARRIER_CMD_PRIVATE_EXPEDITED_RSEQ | \ | |||||
MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_RSEQ) | |||||
static void | static void | ||||
membarrier_action_rseq(void *arg __unused) | |||||
{ | |||||
struct thread *td; | |||||
td = curthread; | |||||
thread_lock(td); | |||||
ast_sched_locked(td, TDA_RSEQ); | |||||
td->td_flags |= TDF_RSEQ_MB; | |||||
thread_unlock(td); | |||||
} | |||||
static void | |||||
membarrier_action_seqcst(void *arg __unused) | membarrier_action_seqcst(void *arg __unused) | ||||
{ | { | ||||
atomic_thread_fence_seq_cst(); | atomic_thread_fence_seq_cst(); | ||||
} | } | ||||
static void | static void | ||||
membarrier_action_seqcst_sync_core(void *arg __unused) | membarrier_action_seqcst_sync_core(void *arg __unused) | ||||
{ | { | ||||
▲ Show 20 Lines • Show All 150 Lines • ▼ Show 20 Lines | if ((td->td_proc->p_flag2 & P2_MEMBAR_PRIVE_SYNCORE) == 0) { | ||||
membarrier_action_seqcst_sync_core); | membarrier_action_seqcst_sync_core); | ||||
} | } | ||||
break; | break; | ||||
case MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_SYNC_CORE: | case MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_SYNC_CORE: | ||||
if ((p->p_flag2 & P2_MEMBAR_PRIVE_SYNCORE) == 0) { | if ((p->p_flag2 & P2_MEMBAR_PRIVE_SYNCORE) == 0) { | ||||
PROC_LOCK(p); | PROC_LOCK(p); | ||||
p->p_flag2 |= P2_MEMBAR_PRIVE_SYNCORE; | p->p_flag2 |= P2_MEMBAR_PRIVE_SYNCORE; | ||||
PROC_UNLOCK(p); | |||||
} | |||||
break; | |||||
case MEMBARRIER_CMD_PRIVATE_EXPEDITED_RSEQ: | |||||
if ((td->td_proc->p_flag2 & P2_MEMBAR_PRIVE_RSEQ) == 0) { | |||||
error = EPERM; | |||||
break; | |||||
} | |||||
pmap_active_cpus(vmspace_pmap(p->p_vmspace), &cs); | |||||
if ((flags & MEMBARRIER_CMD_FLAG_CPU) != 0) { | |||||
if (!CPU_ISSET(cpu_id, &cs)) | |||||
break; | |||||
CPU_ZERO(&cs); | |||||
CPU_SET(cpu_id, &cs); | |||||
} | |||||
do_membarrier_ipi(&cs, membarrier_action_rseq); | |||||
break; | |||||
case MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_RSEQ: | |||||
if ((p->p_flag2 & P2_MEMBAR_PRIVE_RSEQ) == 0) { | |||||
PROC_LOCK(p); | |||||
p->p_flag2 |= P2_MEMBAR_PRIVE_RSEQ; | |||||
PROC_UNLOCK(p); | PROC_UNLOCK(p); | ||||
} | } | ||||
break; | break; | ||||
default: | default: | ||||
error = EINVAL; | error = EINVAL; | ||||
break; | break; | ||||
} | } | ||||
Show All 9 Lines |