501 texcb = KArmV6MemAttNCNC; |
501 texcb = KArmV6MemAttNCNC; |
502 break; |
502 break; |
503 case EMemAttNormalCached: |
503 case EMemAttNormalCached: |
504 texcb = KArmV6MemAttWBWAWBWA; |
504 texcb = KArmV6MemAttWBWAWBWA; |
505 break; |
505 break; |
506 default: |
506 case EMemAttKernelInternal4: |
507 __NK_ASSERT_ALWAYS(0); // undefined memory type |
507 case EMemAttPlatformSpecific5: |
|
508 case EMemAttPlatformSpecific6: |
|
509 case EMemAttPlatformSpecific7: |
|
510 { |
|
511 TUint32 cachingAttr = InternalCache::TypeToCachingAttributes((TMemoryType)(attr&EMemoryAttributeTypeMask)); |
|
512 switch (cachingAttr) |
|
513 { |
|
514 case EMapAttrFullyBlocking: |
|
515 texcb = KArmV6MemAttSO; |
|
516 break; |
|
517 case EMapAttrBufferedNC: |
|
518 texcb = KArmV6MemAttSD; |
|
519 break; |
|
520 default: |
|
521 { |
|
522 //attr describes normal mapping |
|
523 //set texcb to b1BBAA where AA is internal and BB is external caching |
|
524 // TYPE AA/BB |
|
525 // uncached 0 |
|
526 // WBWA 1 |
|
527 // WTRA 2 |
|
528 // WBRA 3 |
|
529 texcb = 0x10; |
|
530 switch (cachingAttr&EMapAttrL1CacheMask) |
|
531 { |
|
532 case EMapAttrL1Uncached: break; |
|
533 #if defined(__CPU_ARM1136_ERRATUM_399234_FIXED) |
|
534 case EMapAttrCachedWTRA: texcb |= 2;break; // It is OK to use WT memory |
|
535 #else |
|
536 case EMapAttrCachedWTRA:;break; // Erratum not fixed. Use uncached memory instead |
|
537 #endif |
|
538 case EMapAttrCachedWBRA: texcb |= 3; break; |
|
539 default: texcb |= 1;//fully cached (WBWA) |
|
540 } |
|
541 switch (cachingAttr&EMapAttrL2CacheMask) |
|
542 { |
|
543 case EMapAttrL2Uncached: break; |
|
544 case EMapAttrL2CachedWTRA: texcb |= 8;break; |
|
545 case EMapAttrL2CachedWBRA: texcb |= 0xc; break; |
|
546 default: texcb |= 4;//fully cached (WBWA) |
|
547 } |
|
548 } |
|
549 } |
|
550 } |
|
551 break; |
|
552 default: |
|
553 __NK_ASSERT_ALWAYS(0); // undefined memory type |
508 texcb = KArmV6MemAttSO; |
554 texcb = KArmV6MemAttSO; |
509 break; |
555 break; |
510 } |
556 } |
511 pte |= ((texcb&0x1c)<<4) | ((texcb&0x03)<<2); |
557 pte |= ((texcb&0x1c)<<4) | ((texcb&0x03)<<2); |
512 |
558 |
880 } |
926 } |
881 |
927 |
882 // Now we have the os asid check access to kernel memory. |
928 // Now we have the os asid check access to kernel memory. |
883 if(aAddr >= KUserMemoryLimit && osAsid != (TUint)KKernelOsAsid) |
929 if(aAddr >= KUserMemoryLimit && osAsid != (TUint)KKernelOsAsid) |
884 { |
930 { |
885 NKern::ThreadEnterCS(); |
|
886 MmuLock::Unlock(); |
|
887 if (!iAliasLinAddr) |
931 if (!iAliasLinAddr) |
888 {// Close the new reference as RemoveAlias won't do as iAliasLinAddr is not set. |
932 {// Close the new reference as RemoveAlias won't do as iAliasLinAddr is not set. |
889 aProcess->AsyncCloseOsAsid(); // Asynchronous close as this method should be quick. |
933 aProcess->AsyncCloseOsAsid(); // Asynchronous close as this method should be quick. |
890 } |
934 } |
891 NKern::ThreadLeaveCS(); |
935 MmuLock::Unlock(); |
892 return KErrBadDescriptor; // prevent access to supervisor only memory |
936 return KErrBadDescriptor; // prevent access to supervisor only memory |
893 } |
937 } |
894 |
938 |
895 // Now we know all accesses to global memory are safe so check if aAddr is global. |
939 // Now we know all accesses to global memory are safe so check if aAddr is global. |
896 if(aAddr >= KGlobalMemoryBase) |
940 if(aAddr >= KGlobalMemoryBase) |
897 { |
941 { |
898 // address is in global section, don't bother aliasing it... |
942 // address is in global section, don't bother aliasing it... |
899 if (!iAliasLinAddr) |
943 if (!iAliasLinAddr) |
900 {// Close the new reference as not required. |
944 {// Close the new reference as not required. |
901 NKern::ThreadEnterCS(); |
945 aProcess->AsyncCloseOsAsid(); // Asynchronous close as this method should be quick. |
902 MmuLock::Unlock(); |
946 MmuLock::Unlock(); |
903 aProcess->AsyncCloseOsAsid(); // Asynchronous close as this method should be quick. |
|
904 NKern::ThreadLeaveCS(); |
|
905 } |
947 } |
906 else |
948 else |
907 {// Remove the existing alias as it is not required. |
949 {// Remove the existing alias as it is not required. |
908 DoRemoveAlias(iAliasLinAddr); // Releases mmulock. |
950 DoRemoveAlias(iAliasLinAddr); // Releases mmulock. |
909 } |
951 } |
1013 __NK_ASSERT_DEBUG(iCpuRestoreCookie>=0); |
1055 __NK_ASSERT_DEBUG(iCpuRestoreCookie>=0); |
1014 NKern::EndFreezeCpu(iCpuRestoreCookie); |
1056 NKern::EndFreezeCpu(iCpuRestoreCookie); |
1015 iCpuRestoreCookie = -1; |
1057 iCpuRestoreCookie = -1; |
1016 #endif |
1058 #endif |
1017 |
1059 |
1018 // Must close the os asid while in critical section to prevent it being |
1060 // Must close the os asid while holding MmuLock so we are in an implicit critical section. |
1019 // leaked. However, we can't hold the mmu lock so we have to enter an |
1061 iAliasProcess->AsyncCloseOsAsid(); // Asynchronous close as this method should be quick. |
1020 // explict crtical section. It is ok to release the mmu lock as the |
|
1021 // iAliasLinAddr and iAliasProcess members are only ever updated by the |
|
1022 // current thread. |
|
1023 NKern::ThreadEnterCS(); |
|
1024 MmuLock::Unlock(); |
1062 MmuLock::Unlock(); |
1025 iAliasProcess->AsyncCloseOsAsid(); // Asynchronous close as this method should be quick. |
|
1026 NKern::ThreadLeaveCS(); |
|
1027 } |
1063 } |
1028 |
1064 |
1029 |
1065 |
1030 TInt M::DemandPagingFault(TAny* aExceptionInfo) |
1066 TInt M::DemandPagingFault(TAny* aExceptionInfo) |
1031 { |
1067 { |