xref: /f-stack/freebsd/mips/include/cache.h (revision 22ce4aff)
1a9643ea8Slogwang /*	$NetBSD: cache.h,v 1.6 2003/02/17 11:35:01 simonb Exp $	*/
2a9643ea8Slogwang 
3*22ce4affSfengbojiang /*-
4*22ce4affSfengbojiang  * SPDX-License-Identifier: BSD-4-Clause
5*22ce4affSfengbojiang  *
6a9643ea8Slogwang  * Copyright 2001 Wasabi Systems, Inc.
7a9643ea8Slogwang  * All rights reserved.
8a9643ea8Slogwang  *
9a9643ea8Slogwang  * Written by Jason R. Thorpe for Wasabi Systems, Inc.
10a9643ea8Slogwang  *
11a9643ea8Slogwang  * Redistribution and use in source and binary forms, with or without
12a9643ea8Slogwang  * modification, are permitted provided that the following conditions
13a9643ea8Slogwang  * are met:
14a9643ea8Slogwang  * 1. Redistributions of source code must retain the above copyright
15a9643ea8Slogwang  *    notice, this list of conditions and the following disclaimer.
16a9643ea8Slogwang  * 2. Redistributions in binary form must reproduce the above copyright
17a9643ea8Slogwang  *    notice, this list of conditions and the following disclaimer in the
18a9643ea8Slogwang  *    documentation and/or other materials provided with the distribution.
19a9643ea8Slogwang  * 3. All advertising materials mentioning features or use of this software
20a9643ea8Slogwang  *    must display the following acknowledgement:
21a9643ea8Slogwang  *	This product includes software developed for the NetBSD Project by
22a9643ea8Slogwang  *	Wasabi Systems, Inc.
23a9643ea8Slogwang  * 4. The name of Wasabi Systems, Inc. may not be used to endorse
24a9643ea8Slogwang  *    or promote products derived from this software without specific prior
25a9643ea8Slogwang  *    written permission.
26a9643ea8Slogwang  *
27a9643ea8Slogwang  * THIS SOFTWARE IS PROVIDED BY WASABI SYSTEMS, INC. ``AS IS'' AND
28a9643ea8Slogwang  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
29a9643ea8Slogwang  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
30a9643ea8Slogwang  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL WASABI SYSTEMS, INC
31a9643ea8Slogwang  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
32a9643ea8Slogwang  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
33a9643ea8Slogwang  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
34a9643ea8Slogwang  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
35a9643ea8Slogwang  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
36a9643ea8Slogwang  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
37a9643ea8Slogwang  * POSSIBILITY OF SUCH DAMAGE.
38a9643ea8Slogwang  *
39a9643ea8Slogwang  * $FreeBSD$
40a9643ea8Slogwang  */
41a9643ea8Slogwang 
42a9643ea8Slogwang #ifndef	_MACHINE_CACHE_H_
43a9643ea8Slogwang #define	_MACHINE_CACHE_H_
44a9643ea8Slogwang 
45a9643ea8Slogwang /*
46a9643ea8Slogwang  * Cache operations.
47a9643ea8Slogwang  *
48a9643ea8Slogwang  * We define the following primitives:
49a9643ea8Slogwang  *
50a9643ea8Slogwang  * --- Instruction cache synchronization (mandatory):
51a9643ea8Slogwang  *
52a9643ea8Slogwang  *	icache_sync_all		Synchronize I-cache
53a9643ea8Slogwang  *
54a9643ea8Slogwang  *	icache_sync_range	Synchronize I-cache range
55a9643ea8Slogwang  *
56a9643ea8Slogwang  *	icache_sync_range_index	(index ops)
57a9643ea8Slogwang  *
58a9643ea8Slogwang  * --- Primary data cache (mandatory):
59a9643ea8Slogwang  *
60a9643ea8Slogwang  *	pdcache_wbinv_all	Write-back Invalidate primary D-cache
61a9643ea8Slogwang  *
62a9643ea8Slogwang  *	pdcache_wbinv_range	Write-back Invalidate primary D-cache range
63a9643ea8Slogwang  *
64a9643ea8Slogwang  *	pdcache_wbinv_range_index (index ops)
65a9643ea8Slogwang  *
66a9643ea8Slogwang  *	pdcache_inv_range	Invalidate primary D-cache range
67a9643ea8Slogwang  *
68a9643ea8Slogwang  *	pdcache_wb_range	Write-back primary D-cache range
69a9643ea8Slogwang  *
70a9643ea8Slogwang  * --- Secondary data cache (optional):
71a9643ea8Slogwang  *
72a9643ea8Slogwang  *	sdcache_wbinv_all	Write-back Invalidate secondary D-cache
73a9643ea8Slogwang  *
74a9643ea8Slogwang  *	sdcache_wbinv_range	Write-back Invalidate secondary D-cache range
75a9643ea8Slogwang  *
76a9643ea8Slogwang  *	sdcache_wbinv_range_index (index ops)
77a9643ea8Slogwang  *
78a9643ea8Slogwang  *	sdcache_inv_range	Invalidate secondary D-cache range
79a9643ea8Slogwang  *
80a9643ea8Slogwang  *	sdcache_wb_range	Write-back secondary D-cache range
81a9643ea8Slogwang  *
82a9643ea8Slogwang  * There are some rules that must be followed:
83a9643ea8Slogwang  *
84a9643ea8Slogwang  *	I-cache Synch (all or range):
85a9643ea8Slogwang  *		The goal is to synchronize the instruction stream,
86a9643ea8Slogwang  *		so you may need to write-back dirty data cache
87a9643ea8Slogwang  *		blocks first.  If a range is requested, and you
88a9643ea8Slogwang  *		can't synchronize just a range, you have to hit
89a9643ea8Slogwang  *		the whole thing.
90a9643ea8Slogwang  *
91a9643ea8Slogwang  *	D-cache Write-back Invalidate range:
92a9643ea8Slogwang  *		If you can't WB-Inv a range, you must WB-Inv the
93a9643ea8Slogwang  *		entire D-cache.
94a9643ea8Slogwang  *
95a9643ea8Slogwang  *	D-cache Invalidate:
96a9643ea8Slogwang  *		If you can't Inv the D-cache without doing a
97a9643ea8Slogwang  *		Write-back, YOU MUST PANIC.  This is to catch
98a9643ea8Slogwang  *		errors in calling code.  Callers must be aware
99a9643ea8Slogwang  *		of this scenario, and must handle it appropriately
100a9643ea8Slogwang  *		(consider the bus_dma(9) operations).
101a9643ea8Slogwang  *
102a9643ea8Slogwang  *	D-cache Write-back:
103a9643ea8Slogwang  *		If you can't Write-back without doing an invalidate,
104a9643ea8Slogwang  *		that's fine.  Then treat this as a WB-Inv.  Skipping
105a9643ea8Slogwang  *		the invalidate is merely an optimization.
106a9643ea8Slogwang  *
107a9643ea8Slogwang  *	All operations:
108a9643ea8Slogwang  *		Valid virtual addresses must be passed to the
109a9643ea8Slogwang  *		cache operation.
110a9643ea8Slogwang  *
111a9643ea8Slogwang  * Finally, these primitives are grouped together in reasonable
112a9643ea8Slogwang  * ways.  For all operations described here, first the primary
113a9643ea8Slogwang  * cache is frobbed, then the secondary cache frobbed, if the
114a9643ea8Slogwang  * operation for the secondary cache exists.
115a9643ea8Slogwang  *
116a9643ea8Slogwang  *	mips_icache_sync_all	Synchronize I-cache
117a9643ea8Slogwang  *
118a9643ea8Slogwang  *	mips_icache_sync_range	Synchronize I-cache range
119a9643ea8Slogwang  *
120a9643ea8Slogwang  *	mips_icache_sync_range_index (index ops)
121a9643ea8Slogwang  *
122a9643ea8Slogwang  *	mips_dcache_wbinv_all	Write-back Invalidate D-cache
123a9643ea8Slogwang  *
124a9643ea8Slogwang  *	mips_dcache_wbinv_range	Write-back Invalidate D-cache range
125a9643ea8Slogwang  *
126a9643ea8Slogwang  *	mips_dcache_wbinv_range_index (index ops)
127a9643ea8Slogwang  *
128a9643ea8Slogwang  *	mips_dcache_inv_range	Invalidate D-cache range
129a9643ea8Slogwang  *
130a9643ea8Slogwang  *	mips_dcache_wb_range	Write-back D-cache range
131a9643ea8Slogwang  */
132a9643ea8Slogwang 
133a9643ea8Slogwang struct mips_cache_ops {
134a9643ea8Slogwang 	void	(*mco_icache_sync_all)(void);
135a9643ea8Slogwang 	void	(*mco_icache_sync_range)(vm_offset_t, vm_size_t);
136a9643ea8Slogwang 	void	(*mco_icache_sync_range_index)(vm_offset_t, vm_size_t);
137a9643ea8Slogwang 
138a9643ea8Slogwang 	void	(*mco_pdcache_wbinv_all)(void);
139a9643ea8Slogwang 	void	(*mco_pdcache_wbinv_range)(vm_offset_t, vm_size_t);
140a9643ea8Slogwang 	void	(*mco_pdcache_wbinv_range_index)(vm_offset_t, vm_size_t);
141a9643ea8Slogwang 	void	(*mco_pdcache_inv_range)(vm_offset_t, vm_size_t);
142a9643ea8Slogwang 	void	(*mco_pdcache_wb_range)(vm_offset_t, vm_size_t);
143a9643ea8Slogwang 
144a9643ea8Slogwang 	/* These are called only by the (mipsNN) icache functions. */
145a9643ea8Slogwang 	void    (*mco_intern_pdcache_wbinv_all)(void);
146a9643ea8Slogwang 	void    (*mco_intern_pdcache_wbinv_range_index)(vm_offset_t, vm_size_t);
147a9643ea8Slogwang 	void    (*mco_intern_pdcache_wb_range)(vm_offset_t, vm_size_t);
148a9643ea8Slogwang 
149a9643ea8Slogwang 	void	(*mco_sdcache_wbinv_all)(void);
150a9643ea8Slogwang 	void	(*mco_sdcache_wbinv_range)(vm_offset_t, vm_size_t);
151a9643ea8Slogwang 	void	(*mco_sdcache_wbinv_range_index)(vm_offset_t, vm_size_t);
152a9643ea8Slogwang 	void	(*mco_sdcache_inv_range)(vm_offset_t, vm_size_t);
153a9643ea8Slogwang 	void	(*mco_sdcache_wb_range)(vm_offset_t, vm_size_t);
154a9643ea8Slogwang 
155a9643ea8Slogwang 	/* These are called only by the (mipsNN) icache functions. */
156a9643ea8Slogwang 	void    (*mco_intern_sdcache_wbinv_all)(void);
157a9643ea8Slogwang 	void    (*mco_intern_sdcache_wbinv_range_index)(vm_offset_t, vm_size_t);
158a9643ea8Slogwang 	void    (*mco_intern_sdcache_wb_range)(vm_offset_t, vm_size_t);
159a9643ea8Slogwang };
160a9643ea8Slogwang 
161a9643ea8Slogwang extern struct mips_cache_ops mips_cache_ops;
162a9643ea8Slogwang 
163a9643ea8Slogwang /* PRIMARY CACHE VARIABLES */
164a9643ea8Slogwang extern int mips_picache_linesize;
165a9643ea8Slogwang extern int mips_pdcache_linesize;
166*22ce4affSfengbojiang extern int mips_sdcache_linesize;
167*22ce4affSfengbojiang extern int mips_dcache_max_linesize;
168a9643ea8Slogwang 
169a9643ea8Slogwang #define	__mco_noargs(prefix, x)						\
170a9643ea8Slogwang do {									\
171a9643ea8Slogwang 	(*mips_cache_ops.mco_ ## prefix ## p ## x )();			\
172a9643ea8Slogwang 	if (*mips_cache_ops.mco_ ## prefix ## s ## x )			\
173a9643ea8Slogwang 		(*mips_cache_ops.mco_ ## prefix ## s ## x )();		\
174a9643ea8Slogwang } while (/*CONSTCOND*/0)
175a9643ea8Slogwang 
176a9643ea8Slogwang #define	__mco_2args(prefix, x, a, b)					\
177a9643ea8Slogwang do {									\
178a9643ea8Slogwang 	(*mips_cache_ops.mco_ ## prefix ## p ## x )((a), (b));		\
179a9643ea8Slogwang 	if (*mips_cache_ops.mco_ ## prefix ## s ## x )			\
180a9643ea8Slogwang 		(*mips_cache_ops.mco_ ## prefix ## s ## x )((a), (b));	\
181a9643ea8Slogwang } while (/*CONSTCOND*/0)
182a9643ea8Slogwang 
183a9643ea8Slogwang #define	mips_icache_sync_all()						\
184a9643ea8Slogwang 	(*mips_cache_ops.mco_icache_sync_all)()
185a9643ea8Slogwang 
186a9643ea8Slogwang #define	mips_icache_sync_range(v, s)					\
187a9643ea8Slogwang 	(*mips_cache_ops.mco_icache_sync_range)((v), (s))
188a9643ea8Slogwang 
189a9643ea8Slogwang #define	mips_icache_sync_range_index(v, s)				\
190a9643ea8Slogwang 	(*mips_cache_ops.mco_icache_sync_range_index)((v), (s))
191a9643ea8Slogwang 
192a9643ea8Slogwang #define	mips_dcache_wbinv_all()						\
193a9643ea8Slogwang 	__mco_noargs(, dcache_wbinv_all)
194a9643ea8Slogwang 
195a9643ea8Slogwang #define	mips_dcache_wbinv_range(v, s)					\
196a9643ea8Slogwang 	__mco_2args(, dcache_wbinv_range, (v), (s))
197a9643ea8Slogwang 
198a9643ea8Slogwang #define	mips_dcache_wbinv_range_index(v, s)				\
199a9643ea8Slogwang 	__mco_2args(, dcache_wbinv_range_index, (v), (s))
200a9643ea8Slogwang 
201a9643ea8Slogwang #define	mips_dcache_inv_range(v, s)					\
202a9643ea8Slogwang 	__mco_2args(, dcache_inv_range, (v), (s))
203a9643ea8Slogwang 
204a9643ea8Slogwang #define	mips_dcache_wb_range(v, s)					\
205a9643ea8Slogwang 	__mco_2args(, dcache_wb_range, (v), (s))
206a9643ea8Slogwang 
207a9643ea8Slogwang /*
208a9643ea8Slogwang  * Private D-cache functions only called from (currently only the
209a9643ea8Slogwang  * mipsNN) I-cache functions.
210a9643ea8Slogwang  */
211a9643ea8Slogwang #define mips_intern_dcache_wbinv_all()					\
212a9643ea8Slogwang 	__mco_noargs(intern_, dcache_wbinv_all)
213a9643ea8Slogwang 
214a9643ea8Slogwang #define mips_intern_dcache_wbinv_range_index(v, s)			\
215a9643ea8Slogwang 	__mco_2args(intern_, dcache_wbinv_range_index, (v), (s))
216a9643ea8Slogwang 
217a9643ea8Slogwang #define mips_intern_dcache_wb_range(v, s)				\
218a9643ea8Slogwang 	__mco_2args(intern_, dcache_wb_range, (v), (s))
219a9643ea8Slogwang 
220a9643ea8Slogwang /* forward declaration */
221a9643ea8Slogwang struct mips_cpuinfo;
222a9643ea8Slogwang 
223a9643ea8Slogwang void    mips_config_cache(struct mips_cpuinfo *);
224a9643ea8Slogwang 
225a9643ea8Slogwang #include <machine/cache_mipsNN.h>
226a9643ea8Slogwang #endif	/* _MACHINE_CACHE_H_ */
227