1*3969ec72Srin /* $NetBSD: ipi.c,v 1.16 2020/07/06 11:01:24 rin Exp $ */
2d974db0aSgarbled /*-
3d974db0aSgarbled * Copyright (c) 2007 The NetBSD Foundation, Inc.
4d974db0aSgarbled * All rights reserved.
5d974db0aSgarbled *
6d974db0aSgarbled * This code is derived from software contributed to The NetBSD Foundation
7d974db0aSgarbled * by Tim Rightnour
8d974db0aSgarbled *
9d974db0aSgarbled * Redistribution and use in source and binary forms, with or without
10d974db0aSgarbled * modification, are permitted provided that the following conditions
11d974db0aSgarbled * are met:
12d974db0aSgarbled * 1. Redistributions of source code must retain the above copyright
13d974db0aSgarbled * notice, this list of conditions and the following disclaimer.
14d974db0aSgarbled * 2. Redistributions in binary form must reproduce the above copyright
15d974db0aSgarbled * notice, this list of conditions and the following disclaimer in the
16d974db0aSgarbled * documentation and/or other materials provided with the distribution.
17d974db0aSgarbled *
18d974db0aSgarbled * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
19d974db0aSgarbled * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
20d974db0aSgarbled * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
21d974db0aSgarbled * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
22d974db0aSgarbled * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23d974db0aSgarbled * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24d974db0aSgarbled * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25d974db0aSgarbled * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26d974db0aSgarbled * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27d974db0aSgarbled * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28d974db0aSgarbled * POSSIBILITY OF SUCH DAMAGE.
29d974db0aSgarbled */
30d974db0aSgarbled
31d974db0aSgarbled #include <sys/cdefs.h>
32*3969ec72Srin __KERNEL_RCSID(0, "$NetBSD: ipi.c,v 1.16 2020/07/06 11:01:24 rin Exp $");
33d974db0aSgarbled
3416031f7dSrin #ifdef _KERNEL_OPT
35d974db0aSgarbled #include "opt_multiprocessor.h"
3616031f7dSrin #endif
37d974db0aSgarbled
38d974db0aSgarbled #include <sys/param.h>
39d974db0aSgarbled #include <sys/kernel.h>
40f66e2cf3Srmind #include <sys/xcall.h>
418011b285Srmind #include <sys/ipi.h>
4201fd9255Smatt #include <sys/atomic.h>
4301fd9255Smatt #include <sys/cpu.h>
44d974db0aSgarbled
45bc7ec336Smatt #include <powerpc/psl.h>
46bc7ec336Smatt
47bc7ec336Smatt #include <powerpc/pic/picvar.h>
48bc7ec336Smatt #include <powerpc/pic/ipivar.h>
49d974db0aSgarbled
50d974db0aSgarbled #ifdef MULTIPROCESSOR
51d974db0aSgarbled
52d974db0aSgarbled struct ipi_ops ipiops;
53d974db0aSgarbled
54d974db0aSgarbled /* Process an actual IPI */
55d974db0aSgarbled
56d974db0aSgarbled int
ipi_intr(void * v)5701fd9255Smatt ipi_intr(void *v)
58d974db0aSgarbled {
5901fd9255Smatt struct cpu_info * const ci = curcpu();
6001fd9255Smatt int cpu_id = cpu_index(ci);
61d974db0aSgarbled int msr;
6201fd9255Smatt uint32_t ipi;
63d974db0aSgarbled
6401fd9255Smatt ci->ci_ev_ipi.ev_count++;
6501fd9255Smatt ipi = atomic_swap_32(&ci->ci_pending_ipis, 0);
66d974db0aSgarbled
6701fd9255Smatt if (ipi == IPI_NOMESG)
68d974db0aSgarbled return 1;
69d974db0aSgarbled
7001fd9255Smatt if (ipi & IPI_XCALL)
711840edb9Srmind xc_ipi_handler();
721840edb9Srmind
738011b285Srmind if (ipi & IPI_GENERIC)
748011b285Srmind ipi_cpu_handler();
758011b285Srmind
76ef2e796fSnonaka if (ipi & IPI_SUSPEND)
77ef2e796fSnonaka cpu_pause(NULL);
78ef2e796fSnonaka
79b1bd2e89Sad if (ipi & IPI_AST)
8057eb66c6Sad ci->ci_onproc->l_md.md_astpending = 1;
81b1bd2e89Sad
8201fd9255Smatt if (ipi & IPI_HALT) {
83ef2e796fSnonaka struct cpuset_info * const csi = &cpuset_info;
84d974db0aSgarbled aprint_normal("halting CPU %d\n", cpu_id);
85ef2e796fSnonaka kcpuset_set(csi->cpus_halted, cpu_id);
86d974db0aSgarbled msr = (mfmsr() & ~PSL_EE) | PSL_POW;
87d974db0aSgarbled for (;;) {
88d974db0aSgarbled __asm volatile ("sync; isync");
89d974db0aSgarbled mtmsr(msr);
90d974db0aSgarbled }
91d974db0aSgarbled }
921840edb9Srmind
93d974db0aSgarbled return 1;
94d974db0aSgarbled }
95d974db0aSgarbled #endif /*MULTIPROCESSOR*/
96