18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-only */ 28c2ecf20Sopenharmony_ci/* 38c2ecf20Sopenharmony_ci * arch/arm/include/asm/domain.h 48c2ecf20Sopenharmony_ci * 58c2ecf20Sopenharmony_ci * Copyright (C) 1999 Russell King. 68c2ecf20Sopenharmony_ci */ 78c2ecf20Sopenharmony_ci#ifndef __ASM_PROC_DOMAIN_H 88c2ecf20Sopenharmony_ci#define __ASM_PROC_DOMAIN_H 98c2ecf20Sopenharmony_ci 108c2ecf20Sopenharmony_ci#ifndef __ASSEMBLY__ 118c2ecf20Sopenharmony_ci#include <asm/barrier.h> 128c2ecf20Sopenharmony_ci#include <asm/thread_info.h> 138c2ecf20Sopenharmony_ci#endif 148c2ecf20Sopenharmony_ci 158c2ecf20Sopenharmony_ci/* 168c2ecf20Sopenharmony_ci * Domain numbers 178c2ecf20Sopenharmony_ci * 188c2ecf20Sopenharmony_ci * DOMAIN_IO - domain 2 includes all IO only 198c2ecf20Sopenharmony_ci * DOMAIN_USER - domain 1 includes all user memory only 208c2ecf20Sopenharmony_ci * DOMAIN_KERNEL - domain 0 includes all kernel memory only 218c2ecf20Sopenharmony_ci * 228c2ecf20Sopenharmony_ci * The domain numbering depends on whether we support 36 physical 238c2ecf20Sopenharmony_ci * address for I/O or not. Addresses above the 32 bit boundary can 248c2ecf20Sopenharmony_ci * only be mapped using supersections and supersections can only 258c2ecf20Sopenharmony_ci * be set for domain 0. We could just default to DOMAIN_IO as zero, 268c2ecf20Sopenharmony_ci * but there may be systems with supersection support and no 36-bit 278c2ecf20Sopenharmony_ci * addressing. In such cases, we want to map system memory with 288c2ecf20Sopenharmony_ci * supersections to reduce TLB misses and footprint. 298c2ecf20Sopenharmony_ci * 308c2ecf20Sopenharmony_ci * 36-bit addressing and supersections are only available on 318c2ecf20Sopenharmony_ci * CPUs based on ARMv6+ or the Intel XSC3 core. 328c2ecf20Sopenharmony_ci */ 338c2ecf20Sopenharmony_ci#ifndef CONFIG_IO_36 348c2ecf20Sopenharmony_ci#define DOMAIN_KERNEL 0 358c2ecf20Sopenharmony_ci#define DOMAIN_USER 1 368c2ecf20Sopenharmony_ci#define DOMAIN_IO 2 378c2ecf20Sopenharmony_ci#else 388c2ecf20Sopenharmony_ci#define DOMAIN_KERNEL 2 398c2ecf20Sopenharmony_ci#define DOMAIN_USER 1 408c2ecf20Sopenharmony_ci#define DOMAIN_IO 0 418c2ecf20Sopenharmony_ci#endif 428c2ecf20Sopenharmony_ci#define DOMAIN_VECTORS 3 438c2ecf20Sopenharmony_ci 448c2ecf20Sopenharmony_ci/* 458c2ecf20Sopenharmony_ci * Domain types 468c2ecf20Sopenharmony_ci */ 478c2ecf20Sopenharmony_ci#define DOMAIN_NOACCESS 0 488c2ecf20Sopenharmony_ci#define DOMAIN_CLIENT 1 498c2ecf20Sopenharmony_ci#ifdef CONFIG_CPU_USE_DOMAINS 508c2ecf20Sopenharmony_ci#define DOMAIN_MANAGER 3 518c2ecf20Sopenharmony_ci#else 528c2ecf20Sopenharmony_ci#define DOMAIN_MANAGER 1 538c2ecf20Sopenharmony_ci#endif 548c2ecf20Sopenharmony_ci 558c2ecf20Sopenharmony_ci#define domain_mask(dom) ((3) << (2 * (dom))) 568c2ecf20Sopenharmony_ci#define domain_val(dom,type) ((type) << (2 * (dom))) 578c2ecf20Sopenharmony_ci 588c2ecf20Sopenharmony_ci#ifdef CONFIG_CPU_SW_DOMAIN_PAN 598c2ecf20Sopenharmony_ci#define DACR_INIT \ 608c2ecf20Sopenharmony_ci (domain_val(DOMAIN_USER, DOMAIN_NOACCESS) | \ 618c2ecf20Sopenharmony_ci domain_val(DOMAIN_KERNEL, DOMAIN_MANAGER) | \ 628c2ecf20Sopenharmony_ci domain_val(DOMAIN_IO, DOMAIN_CLIENT) | \ 638c2ecf20Sopenharmony_ci domain_val(DOMAIN_VECTORS, DOMAIN_CLIENT)) 648c2ecf20Sopenharmony_ci#else 658c2ecf20Sopenharmony_ci#define DACR_INIT \ 668c2ecf20Sopenharmony_ci (domain_val(DOMAIN_USER, DOMAIN_CLIENT) | \ 678c2ecf20Sopenharmony_ci domain_val(DOMAIN_KERNEL, DOMAIN_MANAGER) | \ 688c2ecf20Sopenharmony_ci domain_val(DOMAIN_IO, DOMAIN_CLIENT) | \ 698c2ecf20Sopenharmony_ci domain_val(DOMAIN_VECTORS, DOMAIN_CLIENT)) 708c2ecf20Sopenharmony_ci#endif 718c2ecf20Sopenharmony_ci 728c2ecf20Sopenharmony_ci#define __DACR_DEFAULT \ 738c2ecf20Sopenharmony_ci domain_val(DOMAIN_KERNEL, DOMAIN_CLIENT) | \ 748c2ecf20Sopenharmony_ci domain_val(DOMAIN_IO, DOMAIN_CLIENT) | \ 758c2ecf20Sopenharmony_ci domain_val(DOMAIN_VECTORS, DOMAIN_CLIENT) 768c2ecf20Sopenharmony_ci 778c2ecf20Sopenharmony_ci#define DACR_UACCESS_DISABLE \ 788c2ecf20Sopenharmony_ci (__DACR_DEFAULT | domain_val(DOMAIN_USER, DOMAIN_NOACCESS)) 798c2ecf20Sopenharmony_ci#define DACR_UACCESS_ENABLE \ 808c2ecf20Sopenharmony_ci (__DACR_DEFAULT | domain_val(DOMAIN_USER, DOMAIN_CLIENT)) 818c2ecf20Sopenharmony_ci 828c2ecf20Sopenharmony_ci#ifndef __ASSEMBLY__ 838c2ecf20Sopenharmony_ci 848c2ecf20Sopenharmony_ci#ifdef CONFIG_CPU_CP15_MMU 858c2ecf20Sopenharmony_cistatic __always_inline unsigned int get_domain(void) 868c2ecf20Sopenharmony_ci{ 878c2ecf20Sopenharmony_ci unsigned int domain; 888c2ecf20Sopenharmony_ci 898c2ecf20Sopenharmony_ci asm( 908c2ecf20Sopenharmony_ci "mrc p15, 0, %0, c3, c0 @ get domain" 918c2ecf20Sopenharmony_ci : "=r" (domain) 928c2ecf20Sopenharmony_ci : "m" (current_thread_info()->cpu_domain)); 938c2ecf20Sopenharmony_ci 948c2ecf20Sopenharmony_ci return domain; 958c2ecf20Sopenharmony_ci} 968c2ecf20Sopenharmony_ci 978c2ecf20Sopenharmony_cistatic __always_inline void set_domain(unsigned int val) 988c2ecf20Sopenharmony_ci{ 998c2ecf20Sopenharmony_ci asm volatile( 1008c2ecf20Sopenharmony_ci "mcr p15, 0, %0, c3, c0 @ set domain" 1018c2ecf20Sopenharmony_ci : : "r" (val) : "memory"); 1028c2ecf20Sopenharmony_ci isb(); 1038c2ecf20Sopenharmony_ci} 1048c2ecf20Sopenharmony_ci#else 1058c2ecf20Sopenharmony_cistatic __always_inline unsigned int get_domain(void) 1068c2ecf20Sopenharmony_ci{ 1078c2ecf20Sopenharmony_ci return 0; 1088c2ecf20Sopenharmony_ci} 1098c2ecf20Sopenharmony_ci 1108c2ecf20Sopenharmony_cistatic __always_inline void set_domain(unsigned int val) 1118c2ecf20Sopenharmony_ci{ 1128c2ecf20Sopenharmony_ci} 1138c2ecf20Sopenharmony_ci#endif 1148c2ecf20Sopenharmony_ci 1158c2ecf20Sopenharmony_ci#ifdef CONFIG_CPU_USE_DOMAINS 1168c2ecf20Sopenharmony_ci#define modify_domain(dom,type) \ 1178c2ecf20Sopenharmony_ci do { \ 1188c2ecf20Sopenharmony_ci unsigned int domain = get_domain(); \ 1198c2ecf20Sopenharmony_ci domain &= ~domain_mask(dom); \ 1208c2ecf20Sopenharmony_ci domain = domain | domain_val(dom, type); \ 1218c2ecf20Sopenharmony_ci set_domain(domain); \ 1228c2ecf20Sopenharmony_ci } while (0) 1238c2ecf20Sopenharmony_ci 1248c2ecf20Sopenharmony_ci#else 1258c2ecf20Sopenharmony_cistatic inline void modify_domain(unsigned dom, unsigned type) { } 1268c2ecf20Sopenharmony_ci#endif 1278c2ecf20Sopenharmony_ci 1288c2ecf20Sopenharmony_ci/* 1298c2ecf20Sopenharmony_ci * Generate the T (user) versions of the LDR/STR and related 1308c2ecf20Sopenharmony_ci * instructions (inline assembly) 1318c2ecf20Sopenharmony_ci */ 1328c2ecf20Sopenharmony_ci#ifdef CONFIG_CPU_USE_DOMAINS 1338c2ecf20Sopenharmony_ci#define TUSER(instr) TUSERCOND(instr, ) 1348c2ecf20Sopenharmony_ci#define TUSERCOND(instr, cond) #instr "t" #cond 1358c2ecf20Sopenharmony_ci#else 1368c2ecf20Sopenharmony_ci#define TUSER(instr) TUSERCOND(instr, ) 1378c2ecf20Sopenharmony_ci#define TUSERCOND(instr, cond) #instr #cond 1388c2ecf20Sopenharmony_ci#endif 1398c2ecf20Sopenharmony_ci 1408c2ecf20Sopenharmony_ci#else /* __ASSEMBLY__ */ 1418c2ecf20Sopenharmony_ci 1428c2ecf20Sopenharmony_ci/* 1438c2ecf20Sopenharmony_ci * Generate the T (user) versions of the LDR/STR and related 1448c2ecf20Sopenharmony_ci * instructions 1458c2ecf20Sopenharmony_ci */ 1468c2ecf20Sopenharmony_ci#ifdef CONFIG_CPU_USE_DOMAINS 1478c2ecf20Sopenharmony_ci#define TUSER(instr) instr ## t 1488c2ecf20Sopenharmony_ci#else 1498c2ecf20Sopenharmony_ci#define TUSER(instr) instr 1508c2ecf20Sopenharmony_ci#endif 1518c2ecf20Sopenharmony_ci 1528c2ecf20Sopenharmony_ci#endif /* __ASSEMBLY__ */ 1538c2ecf20Sopenharmony_ci 1548c2ecf20Sopenharmony_ci#endif /* !__ASM_PROC_DOMAIN_H */ 155