aboutsummaryrefslogtreecommitdiffstats
path: root/arch/score
diff options
context:
space:
mode:
Diffstat (limited to 'arch/score')
-rw-r--r--arch/score/include/asm/irq.h2
-rw-r--r--arch/score/include/asm/irq_regs.h7
-rw-r--r--arch/score/include/asm/linkage.h3
-rw-r--r--arch/score/include/asm/page.h4
-rw-r--r--arch/score/include/asm/pgalloc.h2
-rw-r--r--arch/score/include/asm/pgtable.h31
-rw-r--r--arch/score/include/asm/ptrace.h8
-rw-r--r--arch/score/include/asm/uaccess.h433
-rw-r--r--arch/score/include/asm/user.h17
9 files changed, 472 insertions, 35 deletions
diff --git a/arch/score/include/asm/irq.h b/arch/score/include/asm/irq.h
index 6edd2a2adef7..c883f3df33fa 100644
--- a/arch/score/include/asm/irq.h
+++ b/arch/score/include/asm/irq.h
@@ -20,4 +20,6 @@
20 20
21#define IRQ_TIMER (7) /* Timer IRQ number of SPCT6600 */ 21#define IRQ_TIMER (7) /* Timer IRQ number of SPCT6600 */
22 22
23extern void interrupt_exception_vector(void);
24
23#endif /* _ASM_SCORE_IRQ_H */ 25#endif /* _ASM_SCORE_IRQ_H */
diff --git a/arch/score/include/asm/irq_regs.h b/arch/score/include/asm/irq_regs.h
index 905b7b078bae..b8e881c9a69f 100644
--- a/arch/score/include/asm/irq_regs.h
+++ b/arch/score/include/asm/irq_regs.h
@@ -1,6 +1,11 @@
1#ifndef _ASM_SCORE_IRQ_REGS_H 1#ifndef _ASM_SCORE_IRQ_REGS_H
2#define _ASM_SCORE_IRQ_REGS_H 2#define _ASM_SCORE_IRQ_REGS_H
3 3
4#include <asm-generic/irq_regs.h> 4#include <linux/thread_info.h>
5
6static inline struct pt_regs *get_irq_regs(void)
7{
8 return current_thread_info()->regs;
9}
5 10
6#endif /* _ASM_SCORE_IRQ_REGS_H */ 11#endif /* _ASM_SCORE_IRQ_REGS_H */
diff --git a/arch/score/include/asm/linkage.h b/arch/score/include/asm/linkage.h
index 2580fbbfe946..2323a8ecf445 100644
--- a/arch/score/include/asm/linkage.h
+++ b/arch/score/include/asm/linkage.h
@@ -1,4 +1,7 @@
1#ifndef _ASM_SCORE_LINKAGE_H 1#ifndef _ASM_SCORE_LINKAGE_H
2#define _ASM_SCORE_LINKAGE_H 2#define _ASM_SCORE_LINKAGE_H
3 3
4#define __ALIGN .align 2
5#define __ALIGN_STR ".align 2"
6
4#endif /* _ASM_SCORE_LINKAGE_H */ 7#endif /* _ASM_SCORE_LINKAGE_H */
diff --git a/arch/score/include/asm/page.h b/arch/score/include/asm/page.h
index 67e98206be6a..ee5821042fcc 100644
--- a/arch/score/include/asm/page.h
+++ b/arch/score/include/asm/page.h
@@ -57,8 +57,8 @@ extern unsigned long max_low_pfn;
57extern unsigned long min_low_pfn; 57extern unsigned long min_low_pfn;
58extern unsigned long max_pfn; 58extern unsigned long max_pfn;
59 59
60#define __pa(vaddr) ((unsigned long) (vaddr)) 60#define __pa(x) ((unsigned long)(x) - PAGE_OFFSET)
61#define __va(paddr) ((void *) (paddr)) 61#define __va(x) ((void *)((unsigned long) (x) + PAGE_OFFSET))
62 62
63#define phys_to_pfn(phys) (PFN_DOWN(phys)) 63#define phys_to_pfn(phys) (PFN_DOWN(phys))
64#define pfn_to_phys(pfn) (PFN_PHYS(pfn)) 64#define pfn_to_phys(pfn) (PFN_PHYS(pfn))
diff --git a/arch/score/include/asm/pgalloc.h b/arch/score/include/asm/pgalloc.h
index 28dacc1cbbab..059a61b7071b 100644
--- a/arch/score/include/asm/pgalloc.h
+++ b/arch/score/include/asm/pgalloc.h
@@ -72,7 +72,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte)
72 __free_pages(pte, PTE_ORDER); 72 __free_pages(pte, PTE_ORDER);
73} 73}
74 74
75#define __pte_free_tlb(tlb, pte) \ 75#define __pte_free_tlb(tlb, pte, buf) \
76do { \ 76do { \
77 pgtable_page_dtor(pte); \ 77 pgtable_page_dtor(pte); \
78 tlb_remove_page((tlb), pte); \ 78 tlb_remove_page((tlb), pte); \
diff --git a/arch/score/include/asm/pgtable.h b/arch/score/include/asm/pgtable.h
index 5e913e57c671..674934b40170 100644
--- a/arch/score/include/asm/pgtable.h
+++ b/arch/score/include/asm/pgtable.h
@@ -106,7 +106,8 @@ static inline void pmd_clear(pmd_t *pmdp)
106 ((swp_entry_t) { pte_val(pte)}) 106 ((swp_entry_t) { pte_val(pte)})
107#define __swp_entry_to_pte(x) ((pte_t) {(x).val}) 107#define __swp_entry_to_pte(x) ((pte_t) {(x).val})
108 108
109#define pmd_page(pmd) virt_to_page(__va(pmd_val(pmd))) 109#define pmd_phys(pmd) __pa((void *)pmd_val(pmd))
110#define pmd_page(pmd) (pfn_to_page(pmd_phys(pmd) >> PAGE_SHIFT))
110#define mk_pte(page, prot) pfn_pte(page_to_pfn(page), prot) 111#define mk_pte(page, prot) pfn_pte(page_to_pfn(page), prot)
111static inline pte_t pte_mkspecial(pte_t pte) { return pte; } 112static inline pte_t pte_mkspecial(pte_t pte) { return pte; }
112 113
@@ -129,14 +130,11 @@ static inline pte_t pte_mkspecial(pte_t pte) { return pte; }
129#define pgd_clear(pgdp) do { } while (0) 130#define pgd_clear(pgdp) do { } while (0)
130 131
131#define kern_addr_valid(addr) (1) 132#define kern_addr_valid(addr) (1)
132#define pmd_offset(a, b) ((void *) 0)
133#define pmd_page_vaddr(pmd) pmd_val(pmd) 133#define pmd_page_vaddr(pmd) pmd_val(pmd)
134 134
135#define pte_none(pte) (!(pte_val(pte) & ~_PAGE_GLOBAL)) 135#define pte_none(pte) (!(pte_val(pte) & ~_PAGE_GLOBAL))
136#define pte_present(pte) (pte_val(pte) & _PAGE_PRESENT) 136#define pte_present(pte) (pte_val(pte) & _PAGE_PRESENT)
137 137
138#define pud_offset(pgd, address) ((pud_t *) pgd)
139
140#define PAGE_NONE __pgprot(_PAGE_PRESENT | _PAGE_CACHE) 138#define PAGE_NONE __pgprot(_PAGE_PRESENT | _PAGE_CACHE)
141#define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_READ | _PAGE_WRITE | \ 139#define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_READ | _PAGE_WRITE | \
142 _PAGE_CACHE) 140 _PAGE_CACHE)
@@ -165,15 +163,27 @@ static inline pte_t pte_mkspecial(pte_t pte) { return pte; }
165#define __S110 PAGE_SHARED 163#define __S110 PAGE_SHARED
166#define __S111 PAGE_SHARED 164#define __S111 PAGE_SHARED
167 165
168#define pgprot_noncached(x) (x) 166#define pgprot_noncached pgprot_noncached
167
168static inline pgprot_t pgprot_noncached(pgprot_t _prot)
169{
170 unsigned long prot = pgprot_val(_prot);
171
172 prot = (prot & ~_CACHE_MASK);
173
174 return __pgprot(prot);
175}
169 176
170#define __swp_type(x) (0) 177#define __swp_type(x) ((x).val & 0x1f)
171#define __swp_offset(x) (0) 178#define __swp_offset(x) ((x).val >> 11)
172#define __swp_entry(typ, off) ((swp_entry_t) { ((typ) | ((off) << 7)) }) 179#define __swp_entry(type, offset) ((swp_entry_t){(type) | ((offset) << 11)})
173 180
174#define ZERO_PAGE(vaddr) ({ BUG(); NULL; }) 181extern unsigned long empty_zero_page;
182extern unsigned long zero_page_mask;
175 183
176#define swapper_pg_dir ((pgd_t *) NULL) 184#define ZERO_PAGE(vaddr) \
185 (virt_to_page((void *)(empty_zero_page + \
186 (((unsigned long)(vaddr)) & zero_page_mask))))
177 187
178#define pgtable_cache_init() do {} while (0) 188#define pgtable_cache_init() do {} while (0)
179 189
@@ -248,6 +258,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
248#define pte_present(pte) (pte_val(pte) & _PAGE_PRESENT) 258#define pte_present(pte) (pte_val(pte) & _PAGE_PRESENT)
249 259
250extern unsigned long pgd_current; 260extern unsigned long pgd_current;
261extern pgd_t swapper_pg_dir[PTRS_PER_PGD];
251extern void paging_init(void); 262extern void paging_init(void);
252 263
253static inline pte_t pte_modify(pte_t pte, pgprot_t newprot) 264static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
diff --git a/arch/score/include/asm/ptrace.h b/arch/score/include/asm/ptrace.h
index 66b14c8891cf..d40e691f23e2 100644
--- a/arch/score/include/asm/ptrace.h
+++ b/arch/score/include/asm/ptrace.h
@@ -51,9 +51,11 @@
51 * system call/exception. As usual the registers k0/k1 aren't being saved. 51 * system call/exception. As usual the registers k0/k1 aren't being saved.
52 */ 52 */
53struct pt_regs { 53struct pt_regs {
54 unsigned long pad0[6]; 54 unsigned long pad0[6]; /* stack arguments */
55 unsigned long orig_r4; 55 unsigned long orig_r4;
56 unsigned long orig_r7; 56 unsigned long orig_r7;
57 long is_syscall;
58
57 unsigned long regs[32]; 59 unsigned long regs[32];
58 60
59 unsigned long cel; 61 unsigned long cel;
@@ -68,12 +70,12 @@ struct pt_regs {
68 unsigned long cp0_psr; 70 unsigned long cp0_psr;
69 unsigned long cp0_ecr; 71 unsigned long cp0_ecr;
70 unsigned long cp0_condition; 72 unsigned long cp0_condition;
71
72 long is_syscall;
73}; 73};
74 74
75#ifdef __KERNEL__ 75#ifdef __KERNEL__
76 76
77struct task_struct;
78
77/* 79/*
78 * Does the process account for user or for system time? 80 * Does the process account for user or for system time?
79 */ 81 */
diff --git a/arch/score/include/asm/uaccess.h b/arch/score/include/asm/uaccess.h
index 6f09e2b7ddb9..ab66ddde777b 100644
--- a/arch/score/include/asm/uaccess.h
+++ b/arch/score/include/asm/uaccess.h
@@ -1,27 +1,424 @@
1#ifndef _ASM_SCORE_UACCESS_H 1#ifndef __SCORE_UACCESS_H
2#define _ASM_SCORE_UACCESS_H 2#define __SCORE_UACCESS_H
3
4#include <linux/kernel.h>
5#include <linux/errno.h>
6#include <linux/thread_info.h>
7
8#define VERIFY_READ 0
9#define VERIFY_WRITE 1
10
11#define get_ds() (KERNEL_DS)
12#define get_fs() (current_thread_info()->addr_limit)
13#define segment_eq(a, b) ((a).seg == (b).seg)
14
3/* 15/*
4 * Copyright (C) 2006 Atmark Techno, Inc. 16 * Is a address valid? This does a straighforward calculation rather
17 * than tests.
18 *
19 * Address valid if:
20 * - "addr" doesn't have any high-bits set
21 * - AND "size" doesn't have any high-bits set
22 * - AND "addr+size" doesn't have any high-bits set
23 * - OR we are in kernel mode.
5 * 24 *
6 * This file is subject to the terms and conditions of the GNU General Public 25 * __ua_size() is a trick to avoid runtime checking of positive constant
7 * License. See the file "COPYING" in the main directory of this archive 26 * sizes; for those we already know at compile time that the size is ok.
8 * for more details.
9 */ 27 */
10struct pt_regs; 28#define __ua_size(size) \
11extern int fixup_exception(struct pt_regs *regs); 29 ((__builtin_constant_p(size) && (signed long) (size) > 0) ? 0 : (size))
30
31/*
32 * access_ok: - Checks if a user space pointer is valid
33 * @type: Type of access: %VERIFY_READ or %VERIFY_WRITE. Note that
34 * %VERIFY_WRITE is a superset of %VERIFY_READ - if it is safe
35 * to write to a block, it is always safe to read from it.
36 * @addr: User space pointer to start of block to check
37 * @size: Size of block to check
38 *
39 * Context: User context only. This function may sleep.
40 *
41 * Checks if a pointer to a block of memory in user space is valid.
42 *
43 * Returns true (nonzero) if the memory block may be valid, false (zero)
44 * if it is definitely invalid.
45 *
46 * Note that, depending on architecture, this function probably just
47 * checks that the pointer is in the user space range - after calling
48 * this function, memory access functions may still return -EFAULT.
49 */
50
51#define __access_ok(addr, size) \
52 (((long)((get_fs().seg) & \
53 ((addr) | ((addr) + (size)) | \
54 __ua_size(size)))) == 0)
55
56#define access_ok(type, addr, size) \
57 likely(__access_ok((unsigned long)(addr), (size)))
58
59/*
60 * put_user: - Write a simple value into user space.
61 * @x: Value to copy to user space.
62 * @ptr: Destination address, in user space.
63 *
64 * Context: User context only. This function may sleep.
65 *
66 * This macro copies a single simple value from kernel space to user
67 * space. It supports simple types like char and int, but not larger
68 * data types like structures or arrays.
69 *
70 * @ptr must have pointer-to-simple-variable type, and @x must be assignable
71 * to the result of dereferencing @ptr.
72 *
73 * Returns zero on success, or -EFAULT on error.
74 */
75#define put_user(x, ptr) __put_user_check((x), (ptr), sizeof(*(ptr)))
76
77/*
78 * get_user: - Get a simple variable from user space.
79 * @x: Variable to store result.
80 * @ptr: Source address, in user space.
81 *
82 * Context: User context only. This function may sleep.
83 *
84 * This macro copies a single simple variable from user space to kernel
85 * space. It supports simple types like char and int, but not larger
86 * data types like structures or arrays.
87 *
88 * @ptr must have pointer-to-simple-variable type, and the result of
89 * dereferencing @ptr must be assignable to @x without a cast.
90 *
91 * Returns zero on success, or -EFAULT on error.
92 * On error, the variable @x is set to zero.
93 */
94#define get_user(x, ptr) __get_user_check((x), (ptr), sizeof(*(ptr)))
95
96/*
97 * __put_user: - Write a simple value into user space, with less checking.
98 * @x: Value to copy to user space.
99 * @ptr: Destination address, in user space.
100 *
101 * Context: User context only. This function may sleep.
102 *
103 * This macro copies a single simple value from kernel space to user
104 * space. It supports simple types like char and int, but not larger
105 * data types like structures or arrays.
106 *
107 * @ptr must have pointer-to-simple-variable type, and @x must be assignable
108 * to the result of dereferencing @ptr.
109 *
110 * Caller must check the pointer with access_ok() before calling this
111 * function.
112 *
113 * Returns zero on success, or -EFAULT on error.
114 */
115#define __put_user(x, ptr) __put_user_nocheck((x), (ptr), sizeof(*(ptr)))
116
117/*
118 * __get_user: - Get a simple variable from user space, with less checking.
119 * @x: Variable to store result.
120 * @ptr: Source address, in user space.
121 *
122 * Context: User context only. This function may sleep.
123 *
124 * This macro copies a single simple variable from user space to kernel
125 * space. It supports simple types like char and int, but not larger
126 * data types like structures or arrays.
127 *
128 * @ptr must have pointer-to-simple-variable type, and the result of
129 * dereferencing @ptr must be assignable to @x without a cast.
130 *
131 * Caller must check the pointer with access_ok() before calling this
132 * function.
133 *
134 * Returns zero on success, or -EFAULT on error.
135 * On error, the variable @x is set to zero.
136 */
137#define __get_user(x, ptr) __get_user_nocheck((x), (ptr), sizeof(*(ptr)))
138
139struct __large_struct { unsigned long buf[100]; };
140#define __m(x) (*(struct __large_struct __user *)(x))
141
142/*
143 * Yuck. We need two variants, one for 64bit operation and one
144 * for 32 bit mode and old iron.
145 */
146extern void __get_user_unknown(void);
147
148#define __get_user_common(val, size, ptr) \
149do { \
150 switch (size) { \
151 case 1: \
152 __get_user_asm(val, "lb", ptr); \
153 break; \
154 case 2: \
155 __get_user_asm(val, "lh", ptr); \
156 break; \
157 case 4: \
158 __get_user_asm(val, "lw", ptr); \
159 break; \
160 case 8: \
161 if ((copy_from_user((void *)&val, ptr, 8)) == 0) \
162 __gu_err = 0; \
163 else \
164 __gu_err = -EFAULT; \
165 break; \
166 default: \
167 __get_user_unknown(); \
168 break; \
169 } \
170} while (0)
171
172#define __get_user_nocheck(x, ptr, size) \
173({ \
174 long __gu_err = 0; \
175 __get_user_common((x), size, ptr); \
176 __gu_err; \
177})
178
179#define __get_user_check(x, ptr, size) \
180({ \
181 long __gu_err = -EFAULT; \
182 const __typeof__(*(ptr)) __user *__gu_ptr = (ptr); \
183 \
184 if (likely(access_ok(VERIFY_READ, __gu_ptr, size))) \
185 __get_user_common((x), size, __gu_ptr); \
186 \
187 __gu_err; \
188})
189
190#define __get_user_asm(val, insn, addr) \
191{ \
192 long __gu_tmp; \
193 \
194 __asm__ __volatile__( \
195 "1:" insn " %1, %3\n" \
196 "2:\n" \
197 ".section .fixup,\"ax\"\n" \
198 "3:li %0, %4\n" \
199 "j 2b\n" \
200 ".previous\n" \
201 ".section __ex_table,\"a\"\n" \
202 ".word 1b, 3b\n" \
203 ".previous\n" \
204 : "=r" (__gu_err), "=r" (__gu_tmp) \
205 : "0" (0), "o" (__m(addr)), "i" (-EFAULT)); \
206 \
207 (val) = (__typeof__(*(addr))) __gu_tmp; \
208}
209
210/*
211 * Yuck. We need two variants, one for 64bit operation and one
212 * for 32 bit mode and old iron.
213 */
214#define __put_user_nocheck(val, ptr, size) \
215({ \
216 __typeof__(*(ptr)) __pu_val; \
217 long __pu_err = 0; \
218 \
219 __pu_val = (val); \
220 switch (size) { \
221 case 1: \
222 __put_user_asm("sb", ptr); \
223 break; \
224 case 2: \
225 __put_user_asm("sh", ptr); \
226 break; \
227 case 4: \
228 __put_user_asm("sw", ptr); \
229 break; \
230 case 8: \
231 if ((__copy_to_user((void *)ptr, &__pu_val, 8)) == 0) \
232 __pu_err = 0; \
233 else \
234 __pu_err = -EFAULT; \
235 break; \
236 default: \
237 __put_user_unknown(); \
238 break; \
239 } \
240 __pu_err; \
241})
242
243
244#define __put_user_check(val, ptr, size) \
245({ \
246 __typeof__(*(ptr)) __user *__pu_addr = (ptr); \
247 __typeof__(*(ptr)) __pu_val = (val); \
248 long __pu_err = -EFAULT; \
249 \
250 if (likely(access_ok(VERIFY_WRITE, __pu_addr, size))) { \
251 switch (size) { \
252 case 1: \
253 __put_user_asm("sb", __pu_addr); \
254 break; \
255 case 2: \
256 __put_user_asm("sh", __pu_addr); \
257 break; \
258 case 4: \
259 __put_user_asm("sw", __pu_addr); \
260 break; \
261 case 8: \
262 if ((__copy_to_user((void *)__pu_addr, &__pu_val, 8)) == 0)\
263 __pu_err = 0; \
264 else \
265 __pu_err = -EFAULT; \
266 break; \
267 default: \
268 __put_user_unknown(); \
269 break; \
270 } \
271 } \
272 __pu_err; \
273})
274
275#define __put_user_asm(insn, ptr) \
276 __asm__ __volatile__( \
277 "1:" insn " %2, %3\n" \
278 "2:\n" \
279 ".section .fixup,\"ax\"\n" \
280 "3:li %0, %4\n" \
281 "j 2b\n" \
282 ".previous\n" \
283 ".section __ex_table,\"a\"\n" \
284 ".word 1b, 3b\n" \
285 ".previous\n" \
286 : "=r" (__pu_err) \
287 : "0" (0), "r" (__pu_val), "o" (__m(ptr)), \
288 "i" (-EFAULT));
289
290extern void __put_user_unknown(void);
291extern int __copy_tofrom_user(void *to, const void *from, unsigned long len);
292
293static inline unsigned long
294copy_from_user(void *to, const void *from, unsigned long len)
295{
296 unsigned long over;
297
298 if (access_ok(VERIFY_READ, from, len))
299 return __copy_tofrom_user(to, from, len);
300
301 if ((unsigned long)from < TASK_SIZE) {
302 over = (unsigned long)from + len - TASK_SIZE;
303 return __copy_tofrom_user(to, from, len - over) + over;
304 }
305 return len;
306}
307
308static inline unsigned long
309copy_to_user(void *to, const void *from, unsigned long len)
310{
311 unsigned long over;
312
313 if (access_ok(VERIFY_WRITE, to, len))
314 return __copy_tofrom_user(to, from, len);
315
316 if ((unsigned long)to < TASK_SIZE) {
317 over = (unsigned long)to + len - TASK_SIZE;
318 return __copy_tofrom_user(to, from, len - over) + over;
319 }
320 return len;
321}
12 322
13#ifndef __ASSEMBLY__ 323#define __copy_from_user(to, from, len) \
324 __copy_tofrom_user((to), (from), (len))
14 325
15#define __range_ok(addr, size) \ 326#define __copy_to_user(to, from, len) \
16 ((((unsigned long __force)(addr) >= 0x80000000) \ 327 __copy_tofrom_user((to), (from), (len))
17 || ((unsigned long)(size) > 0x80000000) \
18 || (((unsigned long __force)(addr) + (unsigned long)(size)) > 0x80000000)))
19 328
20#define __access_ok(addr, size) \ 329static inline unsigned long
21 (__range_ok((addr), (size)) == 0) 330__copy_to_user_inatomic(void *to, const void *from, unsigned long len)
331{
332 return __copy_to_user(to, from, len);
333}
22 334
23#include <asm-generic/uaccess.h> 335static inline unsigned long
336__copy_from_user_inatomic(void *to, const void *from, unsigned long len)
337{
338 return __copy_from_user(to, from, len);
339}
340
341#define __copy_in_user(to, from, len) __copy_from_user(to, from, len)
342
343static inline unsigned long
344copy_in_user(void *to, const void *from, unsigned long len)
345{
346 if (access_ok(VERIFY_READ, from, len) &&
347 access_ok(VERFITY_WRITE, to, len))
348 return copy_from_user(to, from, len);
349}
350
351/*
352 * __clear_user: - Zero a block of memory in user space, with less checking.
353 * @to: Destination address, in user space.
354 * @n: Number of bytes to zero.
355 *
356 * Zero a block of memory in user space. Caller must check
357 * the specified block with access_ok() before calling this function.
358 *
359 * Returns number of bytes that could not be cleared.
360 * On success, this will be zero.
361 */
362extern unsigned long __clear_user(void __user *src, unsigned long size);
363
364static inline unsigned long clear_user(char *src, unsigned long size)
365{
366 if (access_ok(VERIFY_WRITE, src, size))
367 return __clear_user(src, size);
368
369 return -EFAULT;
370}
371/*
372 * __strncpy_from_user: - Copy a NUL terminated string from userspace, with less checking.
373 * @dst: Destination address, in kernel space. This buffer must be at
374 * least @count bytes long.
375 * @src: Source address, in user space.
376 * @count: Maximum number of bytes to copy, including the trailing NUL.
377 *
378 * Copies a NUL-terminated string from userspace to kernel space.
379 * Caller must check the specified block with access_ok() before calling
380 * this function.
381 *
382 * On success, returns the length of the string (not including the trailing
383 * NUL).
384 *
385 * If access to userspace fails, returns -EFAULT (some data may have been
386 * copied).
387 *
388 * If @count is smaller than the length of the string, copies @count bytes
389 * and returns @count.
390 */
391extern int __strncpy_from_user(char *dst, const char *src, long len);
392
393static inline int strncpy_from_user(char *dst, const char *src, long len)
394{
395 if (access_ok(VERIFY_READ, src, 1))
396 return __strncpy_from_user(dst, src, len);
397
398 return -EFAULT;
399}
400
401extern int __strlen_user(const char *src);
402static inline long strlen_user(const char __user *src)
403{
404 return __strlen_user(src);
405}
406
407extern int __strnlen_user(const char *str, long len);
408static inline long strnlen_user(const char __user *str, long len)
409{
410 if (!access_ok(VERIFY_READ, str, 0))
411 return 0;
412 else
413 return __strnlen_user(str, len);
414}
415
416struct exception_table_entry {
417 unsigned long insn;
418 unsigned long fixup;
419};
420
421extern int fixup_exception(struct pt_regs *regs);
24 422
25#endif /* __ASSEMBLY__ */ 423#endif /* __SCORE_UACCESS_H */
26 424
27#endif /* _ASM_SCORE_UACCESS_H */
diff --git a/arch/score/include/asm/user.h b/arch/score/include/asm/user.h
index 3cf75720fe08..7bfb8e2c8054 100644
--- a/arch/score/include/asm/user.h
+++ b/arch/score/include/asm/user.h
@@ -1,4 +1,21 @@
1#ifndef _ASM_SCORE_USER_H 1#ifndef _ASM_SCORE_USER_H
2#define _ASM_SCORE_USER_H 2#define _ASM_SCORE_USER_H
3 3
4struct user_regs_struct {
5 unsigned long regs[32];
6
7 unsigned long cel;
8 unsigned long ceh;
9
10 unsigned long sr0; /* cnt */
11 unsigned long sr1; /* lcr */
12 unsigned long sr2; /* scr */
13
14 unsigned long cp0_epc;
15 unsigned long cp0_ema;
16 unsigned long cp0_psr;
17 unsigned long cp0_ecr;
18 unsigned long cp0_condition;
19};
20
4#endif /* _ASM_SCORE_USER_H */ 21#endif /* _ASM_SCORE_USER_H */