kernel/eka/include/nkern/nk_cpu.h
changeset 31 56f325a607ea
parent 15 4122176ea935
child 36 538db54a451d
equal deleted inserted replaced
15:4122176ea935 31:56f325a607ea
   777 #define __USER_MEMORY_GUARDS_ENABLED__
   777 #define __USER_MEMORY_GUARDS_ENABLED__
   778 #endif
   778 #endif
   779 #endif
   779 #endif
   780 #endif // end of (_DEBUG) && !(__KERNEL_APIS_DISABLE_USER_MEMORY_GUARDS__)
   780 #endif // end of (_DEBUG) && !(__KERNEL_APIS_DISABLE_USER_MEMORY_GUARDS__)
   781 
   781 
   782 
   782 #ifndef __USER_MEMORY_GUARDS_ENABLED__
   783 #ifdef __USER_MEMORY_GUARDS_ENABLED__
   783 
   784 
   784 #define USER_MEMORY_GUARD_SAVE_WORDS			0
   785 #define USER_MEMORY_GUARD_ON(cc,save,temp)			\
   785 #define USER_MEMORY_DOMAIN						0
   786 	asm("mrc"#cc" p15, 0, "#save", c3, c0, 0 ");	\
   786 
   787 	asm("bic"#cc" "#temp", "#save", #0xc0000000 ");	\
   787 #define USER_MEMORY_GUARD_SAVE(save)
   788 	asm("mcr"#cc" p15, 0, "#temp", c3, c0, 0 ");	\
   788 #define USER_MEMORY_GUARD_RESTORE(save,temp)
   789     __INST_SYNC_BARRIER__(save)                     // Set DACR so no access to domain 15
       
   790 
       
   791 #define USER_MEMORY_GUARD_OFF(cc,save,temp)			\
       
   792 	asm("mrc"#cc" p15, 0, "#save", c3, c0, 0 ");	\
       
   793 	asm("orr"#cc" "#temp", "#save", #0x40000000 ");	\
       
   794 	asm("mcr"#cc" p15, 0, "#temp", c3, c0, 0 ");	\
       
   795     __INST_SYNC_BARRIER__(save)                     // Set DACR so client of domain 15
       
   796 
       
   797 #define USER_MEMORY_GUARD_RESTORE(save,temp)		\
       
   798 	asm("mrc p15, 0, "#temp", c3, c0, 0 ");			\
       
   799 	asm("and "#save", "#save", #0xc0000000 ");		\
       
   800 	asm("bic "#temp", "#temp", #0xc0000000 ");		\
       
   801 	asm("orr "#temp", "#temp", "#save );			\
       
   802 	asm("mcr p15, 0, "#temp", c3, c0, 0 ");    		\
       
   803     __INST_SYNC_BARRIER__(save)                     // Restore domain 15 in DACR from value in 'save'
       
   804 
       
   805 #define USER_MEMORY_GUARD_ON_IF_MODE_USR(rd)		\
       
   806 	asm("mrs "#rd", spsr");							\
       
   807 	asm("tst "#rd", #0x0f ");						\
       
   808 	USER_MEMORY_GUARD_ON(eq,rd,rd)					// If spsr is mode_usr then set DACR so no access to domain 15
       
   809 
       
   810 #define USER_MEMORY_GUARD_OFF_IF_MODE_USR(rd)		\
       
   811 	asm("mrs "#rd", spsr");							\
       
   812 	asm("tst "#rd", #0x0f ");						\
       
   813 	USER_MEMORY_GUARD_OFF(eq,rd,rd)					// If spsr is mode_usr then set DACR so client of domain 15
       
   814 
       
   815 #else // !__USER_MEMORY_GUARDS_ENABLED__
       
   816 
       
   817 #define USER_MEMORY_GUARD_ON(cc,save,temp)
   789 #define USER_MEMORY_GUARD_ON(cc,save,temp)
   818 #define USER_MEMORY_GUARD_OFF(cc,save,temp)
   790 #define USER_MEMORY_GUARD_OFF(cc,save,temp)
   819 #define USER_MEMORY_GUARD_RESTORE(save,temp)
   791 #define USER_MEMORY_GUARD_ON_IF_MODE_USR(temp)
   820 #define USER_MEMORY_GUARD_ON_IF_MODE_USR(rd)
   792 #define USER_MEMORY_GUARD_OFF_IF_MODE_USR(temp)
   821 #define USER_MEMORY_GUARD_OFF_IF_MODE_USR(rd)
   793 #define USER_MEMORY_GUARD_ASSERT_ON(temp)
       
   794 #define USER_MEMORY_GUARD_ASSERT_OFF_IF_MODE_USR(psr)
       
   795 
       
   796 #else // __USER_MEMORY_GUARDS_ENABLED__
       
   797 
       
   798 #define USER_MEMORY_GUARD_SAVE_WORDS			2
       
   799 #define USER_MEMORY_DOMAIN						15
       
   800 #define	USER_MEMORY_DOMAIN_MASK					(3 << (2*USER_MEMORY_DOMAIN))
       
   801 #define	USER_MEMORY_DOMAIN_CLIENT				(1 << (2*USER_MEMORY_DOMAIN))
       
   802 
       
   803 // Save the DACR in the named register
       
   804 #define USER_MEMORY_GUARD_SAVE(save)											\
       
   805 	asm("mrc p15, 0, "#save", c3, c0, 0");			/* save<-DACR */
       
   806 
       
   807 // Restore access to domain 15 (user pages) to the state previously saved
       
   808 // In this case, 'save' may not be the same register as 'temp'
       
   809 #define USER_MEMORY_GUARD_RESTORE(save,temp)									\
       
   810 	asm("mrc p15, 0, "#temp", c3, c0, 0");			/* temp<-DACR */			\
       
   811 	asm("bic "#temp", "#temp", #%a0" : : "i" USER_MEMORY_DOMAIN_MASK);			\
       
   812 	asm("and "#save", "#save", #%a0" : : "i" USER_MEMORY_DOMAIN_MASK);			\
       
   813 	asm("orr "#temp", "#temp", "#save );										\
       
   814 	asm("mcr p15, 0, "#temp", c3, c0, 0");			/* DACR<-temp */			\
       
   815     __INST_SYNC_BARRIER__(temp)
       
   816 
       
   817 // Disable access to domain 15 (user pages)
       
   818 // 'save' may be the same register as 'temp', but in that case the use as
       
   819 // a temporary takes precedence and the value left in 'save' is undefined
       
   820 #define USER_MEMORY_GUARD_ON(cc,save,temp)										\
       
   821 	asm("mrc"#cc" p15, 0, "#save", c3, c0, 0");		/* save<-DACR */			\
       
   822 	asm("bic"#cc" "#temp", "#save", #%a0" : : "i" USER_MEMORY_DOMAIN_MASK);	\
       
   823 	asm("mcr"#cc" p15, 0, "#temp", c3, c0, 0");		/* DACR<-temp */			\
       
   824     __INST_SYNC_BARRIER__(temp)
       
   825 
       
   826 // Enable access to domain 15 (user pages) as a client
       
   827 // 'save' may be the same register as 'temp', but in that case the use as
       
   828 // a temporary takes precedence and the value left in 'save' is undefined
       
   829 #define USER_MEMORY_GUARD_OFF(cc,save,temp)										\
       
   830 	asm("mrc"#cc" p15, 0, "#save", c3, c0, 0");		/* save<-DACR */			\
       
   831 	asm("orr"#cc" "#temp", "#save", #%a0" : : "i" USER_MEMORY_DOMAIN_CLIENT);	\
       
   832 	asm("mcr"#cc" p15, 0, "#temp", c3, c0, 0");		/* DACR<-temp */			\
       
   833     __INST_SYNC_BARRIER__(temp)
       
   834 
       
   835 // Disable access to domain 15 (user pages) if SPSR indicates mode_usr
       
   836 // The specified 'temp' register is left with an undefined value
       
   837 #define USER_MEMORY_GUARD_ON_IF_MODE_USR(temp)									\
       
   838 	asm("mrs "#temp", spsr");													\
       
   839 	asm("tst "#temp", #0x0f");													\
       
   840 	USER_MEMORY_GUARD_ON(eq,temp,temp)
       
   841 
       
   842 // Enable access to domain 15 (user pages) if SPSR indicates mode_usr
       
   843 // The specified 'temp' register is left with an undefined value
       
   844 #define USER_MEMORY_GUARD_OFF_IF_MODE_USR(temp)									\
       
   845 	asm("mrs "#temp", spsr");													\
       
   846 	asm("tst "#temp", #0x0f");													\
       
   847 	USER_MEMORY_GUARD_OFF(eq,temp,temp)
       
   848 
       
   849 // Assert that access to domain 15 (user pages) is disabled
       
   850 #define USER_MEMORY_GUARD_ASSERT_ON(temp)										\
       
   851 	asm("mrc p15, 0, "#temp", c3, c0, 0");		/* temp<-DACR				*/	\
       
   852 	asm("tst "#temp", #%a0" : : "i" USER_MEMORY_DOMAIN_MASK);					\
       
   853 	asm("cdpne p15, 0, c0, c0, c0, 0");			/* fault if nonzero			*/
       
   854 
       
   855 // Assert that access to domain 15 (user pages) is enabled if the value
       
   856 // in 'psr' says we came from/are going back to user mode
       
   857 #define USER_MEMORY_GUARD_ASSERT_OFF_IF_MODE_USR(psr)							\
       
   858 	asm("tst "#psr", #0x0f");					/* check for mode_usr		*/	\
       
   859 	asm("mrceq p15, 0, "#psr", c3, c0, 0");		/* psr<-DACR				*/	\
       
   860 	asm("tsteq "#psr", #%a0" : : "i" USER_MEMORY_DOMAIN_MASK);					\
       
   861 	asm("cdpeq p15, 0, c0, c0, c0, 0");			/* fault if no access		*/
   822 
   862 
   823 #endif // end of else __USER_MEMORY_GUARDS_ENABLED__
   863 #endif // end of else __USER_MEMORY_GUARDS_ENABLED__
   824 
   864 
   825 #endif // End of file
   865 #endif // __NK_CPU_H__