smp.h revision 204152
180708Sjake/*- 280708Sjake * Copyright (c) 2001 Jake Burkholder. 380708Sjake * All rights reserved. 480708Sjake * 580708Sjake * Redistribution and use in source and binary forms, with or without 680708Sjake * modification, are permitted provided that the following conditions 780708Sjake * are met: 880708Sjake * 1. Redistributions of source code must retain the above copyright 980708Sjake * notice, this list of conditions and the following disclaimer. 1080708Sjake * 2. Redistributions in binary form must reproduce the above copyright 1180708Sjake * notice, this list of conditions and the following disclaimer in the 1280708Sjake * documentation and/or other materials provided with the distribution. 1380708Sjake * 1481334Sobrien * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 1580708Sjake * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1680708Sjake * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1781334Sobrien * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 1880708Sjake * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 1980708Sjake * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2080708Sjake * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2180708Sjake * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2280708Sjake * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2380708Sjake * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2480708Sjake * SUCH DAMAGE. 2580708Sjake * 2680708Sjake * $FreeBSD: head/sys/sparc64/include/smp.h 204152 2010-02-20 23:24:19Z marius $ 2780708Sjake */ 2880708Sjake 2980708Sjake#ifndef _MACHINE_SMP_H_ 3080708Sjake#define _MACHINE_SMP_H_ 3180708Sjake 32183142Smarius#ifdef SMP 33183142Smarius 34182730Smarius#define CPU_TICKSYNC 1 35182730Smarius#define CPU_STICKSYNC 2 36182730Smarius#define CPU_INIT 3 37182730Smarius#define CPU_BOOTSTRAP 4 3889051Sjake 3989051Sjake#ifndef LOCORE 4089051Sjake 4191157Sjake#include <machine/intr_machdep.h> 42169730Skan#include <machine/pcb.h> 4391617Sjake#include <machine/tte.h> 4491157Sjake 45170846Smarius#define IDR_BUSY 0x0000000000000001ULL 46170846Smarius#define IDR_NACK 0x0000000000000002ULL 47170846Smarius#define IDR_CHEETAH_ALL_BUSY 0x5555555555555555ULL 48170846Smarius#define IDR_CHEETAH_ALL_NACK (~IDR_CHEETAH_ALL_BUSY) 49170846Smarius#define IDR_CHEETAH_MAX_BN_PAIRS 32 50170846Smarius#define IDR_JALAPENO_MAX_BN_PAIRS 4 5189051Sjake 52169796Smarius#define IDC_ITID_SHIFT 14 53170846Smarius#define IDC_BN_SHIFT 24 54169796Smarius 5589051Sjake#define IPI_AST PIL_AST 5689051Sjake#define IPI_RENDEZVOUS PIL_RENDEZVOUS 57178048Smarius#define IPI_PREEMPT PIL_PREEMPT 5889051Sjake#define IPI_STOP PIL_STOP 59196196Sattilio#define IPI_STOP_HARD PIL_STOP 6089051Sjake 61135943Skensmith#define IPI_RETRIES 5000 6289051Sjake 6389051Sjakestruct cpu_start_args { 6491783Sjake u_int csa_count; 6589051Sjake u_int csa_mid; 6689051Sjake u_int csa_state; 6791783Sjake vm_offset_t csa_pcpu; 6891617Sjake u_long csa_tick; 69182730Smarius u_long csa_stick; 7091617Sjake u_long csa_ver; 7191617Sjake struct tte csa_ttes[PCPU_PAGES]; 7289051Sjake}; 7389051Sjake 7497001Sjakestruct ipi_cache_args { 7597001Sjake u_int ica_mask; 76113238Sjake vm_paddr_t ica_pa; 7797001Sjake}; 7897001Sjake 7989051Sjakestruct ipi_tlb_args { 8092199Sjake u_int ita_mask; 8191783Sjake struct pmap *ita_pmap; 8289051Sjake u_long ita_start; 8389051Sjake u_long ita_end; 8489051Sjake}; 8589051Sjake#define ita_va ita_start 8689051Sjake 8789051Sjakestruct pcpu; 8889051Sjake 89152022Sjhbextern struct pcb stoppcbs[]; 90152022Sjhb 9189051Sjakevoid cpu_mp_bootstrap(struct pcpu *pc); 9292199Sjakevoid cpu_mp_shutdown(void); 9389051Sjake 94170846Smariustypedef void cpu_ipi_selected_t(u_int, u_long, u_long, u_long); 95170846Smariusextern cpu_ipi_selected_t *cpu_ipi_selected; 9689051Sjake 97204152Smariusvoid mp_init(u_int cpu_impl); 9891617Sjake 99108187Sjakeextern struct mtx ipi_mtx; 100108187Sjakeextern struct ipi_cache_args ipi_cache_args; 101108187Sjakeextern struct ipi_tlb_args ipi_tlb_args; 10289051Sjake 10391617Sjakeextern char *mp_tramp_code; 10491617Sjakeextern u_long mp_tramp_code_len; 10591617Sjakeextern u_long mp_tramp_tlb_slots; 10691617Sjakeextern u_long mp_tramp_func; 10791617Sjake 10891617Sjakeextern void mp_startup(void); 10991617Sjake 110112399Sjakeextern char tl_ipi_cheetah_dcache_page_inval[]; 111112399Sjakeextern char tl_ipi_spitfire_dcache_page_inval[]; 112112399Sjakeextern char tl_ipi_spitfire_icache_page_inval[]; 113112399Sjake 11489051Sjakeextern char tl_ipi_level[]; 11589051Sjakeextern char tl_ipi_tlb_context_demap[]; 11689051Sjakeextern char tl_ipi_tlb_page_demap[]; 11789051Sjakeextern char tl_ipi_tlb_range_demap[]; 11889051Sjake 119183142Smariusstatic __inline void 120183142Smariusipi_all_but_self(u_int ipi) 121183142Smarius{ 12289051Sjake 123183142Smarius cpu_ipi_selected(PCPU_GET(other_cpus), 0, (u_long)tl_ipi_level, ipi); 124183142Smarius} 125183142Smarius 126183142Smariusstatic __inline void 127183142Smariusipi_selected(u_int cpus, u_int ipi) 128183142Smarius{ 129183142Smarius 130183142Smarius cpu_ipi_selected(cpus, 0, (u_long)tl_ipi_level, ipi); 131183142Smarius} 132183142Smarius 133108187Sjake#if defined(_MACHINE_PMAP_H_) && defined(_SYS_MUTEX_H_) 134108187Sjake 13597001Sjakestatic __inline void * 136113238Sjakeipi_dcache_page_inval(void *func, vm_paddr_t pa) 13797001Sjake{ 13897001Sjake struct ipi_cache_args *ica; 13997001Sjake 14097001Sjake if (smp_cpus == 1) 14197001Sjake return (NULL); 14297001Sjake ica = &ipi_cache_args; 143108187Sjake mtx_lock_spin(&ipi_mtx); 14497001Sjake ica->ica_mask = all_cpus; 14597001Sjake ica->ica_pa = pa; 146112399Sjake cpu_ipi_selected(PCPU_GET(other_cpus), 0, (u_long)func, (u_long)ica); 14797001Sjake return (&ica->ica_mask); 14897001Sjake} 14997001Sjake 15097001Sjakestatic __inline void * 151113238Sjakeipi_icache_page_inval(void *func, vm_paddr_t pa) 15297001Sjake{ 15397001Sjake struct ipi_cache_args *ica; 15497001Sjake 15597001Sjake if (smp_cpus == 1) 15697001Sjake return (NULL); 15797001Sjake ica = &ipi_cache_args; 158108187Sjake mtx_lock_spin(&ipi_mtx); 15997001Sjake ica->ica_mask = all_cpus; 16097001Sjake ica->ica_pa = pa; 161112399Sjake cpu_ipi_selected(PCPU_GET(other_cpus), 0, (u_long)func, (u_long)ica); 16297001Sjake return (&ica->ica_mask); 16397001Sjake} 16497001Sjake 16589051Sjakestatic __inline void * 16691783Sjakeipi_tlb_context_demap(struct pmap *pm) 16789051Sjake{ 16889051Sjake struct ipi_tlb_args *ita; 16991783Sjake u_int cpus; 17089051Sjake 17191783Sjake if (smp_cpus == 1) 17289051Sjake return (NULL); 17391783Sjake if ((cpus = (pm->pm_active & PCPU_GET(other_cpus))) == 0) 17491783Sjake return (NULL); 17589051Sjake ita = &ipi_tlb_args; 176108187Sjake mtx_lock_spin(&ipi_mtx); 17792199Sjake ita->ita_mask = cpus | PCPU_GET(cpumask); 17891783Sjake ita->ita_pmap = pm; 17991783Sjake cpu_ipi_selected(cpus, 0, (u_long)tl_ipi_tlb_context_demap, 18091783Sjake (u_long)ita); 18192199Sjake return (&ita->ita_mask); 18289051Sjake} 18389051Sjake 18489051Sjakestatic __inline void * 185100718Sjakeipi_tlb_page_demap(struct pmap *pm, vm_offset_t va) 18689051Sjake{ 18789051Sjake struct ipi_tlb_args *ita; 18891783Sjake u_int cpus; 18989051Sjake 19091783Sjake if (smp_cpus == 1) 19189051Sjake return (NULL); 19291783Sjake if ((cpus = (pm->pm_active & PCPU_GET(other_cpus))) == 0) 19391783Sjake return (NULL); 19489051Sjake ita = &ipi_tlb_args; 195108187Sjake mtx_lock_spin(&ipi_mtx); 19692199Sjake ita->ita_mask = cpus | PCPU_GET(cpumask); 19791783Sjake ita->ita_pmap = pm; 19889051Sjake ita->ita_va = va; 19991783Sjake cpu_ipi_selected(cpus, 0, (u_long)tl_ipi_tlb_page_demap, (u_long)ita); 20092199Sjake return (&ita->ita_mask); 20189051Sjake} 20289051Sjake 20389051Sjakestatic __inline void * 20491783Sjakeipi_tlb_range_demap(struct pmap *pm, vm_offset_t start, vm_offset_t end) 20589051Sjake{ 20689051Sjake struct ipi_tlb_args *ita; 20791783Sjake u_int cpus; 20889051Sjake 20991783Sjake if (smp_cpus == 1) 21089051Sjake return (NULL); 21191783Sjake if ((cpus = (pm->pm_active & PCPU_GET(other_cpus))) == 0) 21291783Sjake return (NULL); 21389051Sjake ita = &ipi_tlb_args; 214108187Sjake mtx_lock_spin(&ipi_mtx); 21592199Sjake ita->ita_mask = cpus | PCPU_GET(cpumask); 21691783Sjake ita->ita_pmap = pm; 21789051Sjake ita->ita_start = start; 21889051Sjake ita->ita_end = end; 21991783Sjake cpu_ipi_selected(cpus, 0, (u_long)tl_ipi_tlb_range_demap, (u_long)ita); 22092199Sjake return (&ita->ita_mask); 22189051Sjake} 22289051Sjake 22389051Sjakestatic __inline void 22489051Sjakeipi_wait(void *cookie) 22589051Sjake{ 226143190Salc volatile u_int *mask; 22789051Sjake 22892199Sjake if ((mask = cookie) != NULL) { 22992199Sjake atomic_clear_int(mask, PCPU_GET(cpumask)); 23092199Sjake while (*mask != 0) 23191617Sjake ; 232108187Sjake mtx_unlock_spin(&ipi_mtx); 23389051Sjake } 23489051Sjake} 23589051Sjake 236108187Sjake#endif /* _MACHINE_PMAP_H_ && _SYS_MUTEX_H_ */ 23791783Sjake 238183142Smarius#endif /* !LOCORE */ 239183142Smarius 24089051Sjake#else 24189051Sjake 242183142Smarius#ifndef LOCORE 243183142Smarius 24489051Sjakestatic __inline void * 245113238Sjakeipi_dcache_page_inval(void *func, vm_paddr_t pa) 24697001Sjake{ 247169796Smarius 24897001Sjake return (NULL); 24997001Sjake} 25097001Sjake 25197001Sjakestatic __inline void * 252113238Sjakeipi_icache_page_inval(void *func, vm_paddr_t pa) 25397001Sjake{ 254169796Smarius 25597001Sjake return (NULL); 25697001Sjake} 25797001Sjake 25897001Sjakestatic __inline void * 25991783Sjakeipi_tlb_context_demap(struct pmap *pm) 26089051Sjake{ 261169796Smarius 26289051Sjake return (NULL); 26389051Sjake} 26489051Sjake 26589051Sjakestatic __inline void * 266100718Sjakeipi_tlb_page_demap(struct pmap *pm, vm_offset_t va) 26789051Sjake{ 268169796Smarius 26989051Sjake return (NULL); 27089051Sjake} 27189051Sjake 27289051Sjakestatic __inline void * 27391783Sjakeipi_tlb_range_demap(struct pmap *pm, vm_offset_t start, vm_offset_t end) 27489051Sjake{ 275169796Smarius 27689051Sjake return (NULL); 27789051Sjake} 27889051Sjake 27989051Sjakestatic __inline void 28089051Sjakeipi_wait(void *cookie) 28189051Sjake{ 282169796Smarius 28389051Sjake} 28489051Sjake 285183142Smariusstatic __inline void 286183142Smariustl_ipi_cheetah_dcache_page_inval(void) 287183142Smarius{ 28889051Sjake 289183142Smarius} 290183142Smarius 291183142Smariusstatic __inline void 292183142Smariustl_ipi_spitfire_dcache_page_inval(void) 293183142Smarius{ 294183142Smarius 295183142Smarius} 296183142Smarius 297183142Smariusstatic __inline void 298183142Smariustl_ipi_spitfire_icache_page_inval(void) 299183142Smarius{ 300183142Smarius 301183142Smarius} 302183142Smarius 30389051Sjake#endif /* !LOCORE */ 30489051Sjake 305183142Smarius#endif /* SMP */ 306183142Smarius 30780708Sjake#endif /* !_MACHINE_SMP_H_ */ 308