1/*-
2 * Copyright (c) 2011 Robert N. M. Watson
3 * All rights reserved.
4 *
5 * This software was developed by SRI International and the University of
6 * Cambridge Computer Laboratory under DARPA/AFRL contract (FA8750-10-C-0237)
7 * ("CTSRD"), as part of the DARPA CRASH research programme.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 *    notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 *    notice, this list of conditions and the following disclaimer in the
16 *    documentation and/or other materials provided with the distribution.
17 *
18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
19 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28 * SUCH DAMAGE.
29 *
30 * $FreeBSD: stable/11/stand/mips/beri/common/mips.h 262197 2014-02-18 23:18:32Z rwatson $
31 */
32
33#ifndef _MIPS_H_
34#define	_MIPS_H_
35
36/*
37 * 64-bit MIPS types.
38 */
39#if 0
40typedef unsigned long	register_t;		/* 64-bit MIPS register */
41#endif
42typedef unsigned long	paddr_t;		/* Physical address */
43typedef unsigned long	vaddr_t;		/* Virtual address */
44
45#if 0
46typedef unsigned char	uint8_t;
47typedef unsigned short	uint16_t;
48typedef unsigned int	uint32_t;
49typedef unsigned long	uint64_t;
50#endif
51
52/*
53 * MIPS address space layout.
54 */
55#define	MIPS_XKPHYS_UNCACHED_BASE	0x9000000000000000
56#define	MIPS_XKPHYS_CACHED_NC_BASE	0x9800000000000000
57
58static inline vaddr_t
59mips_phys_to_cached(paddr_t phys)
60{
61
62	return (phys | MIPS_XKPHYS_CACHED_NC_BASE);
63}
64
65static inline vaddr_t
66mips_phys_to_uncached(paddr_t phys)
67{
68
69	return (phys | MIPS_XKPHYS_UNCACHED_BASE);
70}
71
72/*
73 * Endian conversion routines for use in I/O -- most Altera devices are little
74 * endian, but our processor is big endian.
75 */
76static inline uint16_t
77byteswap16(uint16_t v)
78{
79
80	return ((v & 0xff00) >> 8 | (v & 0xff) << 8);
81}
82
83static inline uint32_t
84byteswap32(uint32_t v)
85{
86
87	return ((v & 0xff000000) >> 24 | (v & 0x00ff0000) >> 8 |
88	    (v & 0x0000ff00) << 8 | (v & 0x000000ff) << 24);
89}
90
91/*
92 * MIPS simple I/O routines -- arguments are virtual addresses so that the
93 * caller can determine required caching properties.
94 */
95static inline uint8_t
96mips_ioread_uint8(vaddr_t vaddr)
97{
98	uint8_t v;
99
100	__asm__ __volatile__ ("lb %0, 0(%1)" : "=r" (v) : "r" (vaddr));
101	return (v);
102}
103
104static inline void
105mips_iowrite_uint8(vaddr_t vaddr, uint8_t v)
106{
107
108	__asm__ __volatile__ ("sb %0, 0(%1)" : : "r" (v), "r" (vaddr));
109}
110
111static inline uint32_t
112mips_ioread_uint32(vaddr_t vaddr)
113{
114	uint32_t v;
115
116	__asm__ __volatile__ ("lw %0, 0(%1)" : "=r" (v) : "r" (vaddr));
117	return (v);
118}
119
120static inline void
121mips_iowrite_uint32(vaddr_t vaddr, uint32_t v)
122{
123
124	__asm__ __volatile__ ("sw %0, 0(%1)" : : "r" (v), "r" (vaddr));
125}
126
127/*
128 * Little-endian versions of 32-bit I/O routines.
129 */
130static inline uint32_t
131mips_ioread_uint32le(vaddr_t vaddr)
132{
133
134	return (byteswap32(mips_ioread_uint32(vaddr)));
135}
136
137static inline void
138mips_iowrite_uint32le(vaddr_t vaddr, uint32_t v)
139{
140
141	mips_iowrite_uint32(vaddr, byteswap32(v));
142}
143
144/*
145 * Coprocessor 0 interfaces.
146 */
147static inline register_t
148cp0_count_get(void)
149{
150        register_t count;
151
152        __asm__ __volatile__ ("dmfc0 %0, $9" : "=r" (count));
153       return (count);
154}
155
156#endif
157