Subject: Re: Re ELF

From: [email-masked]
Date: Thu, 3 Jul 1997 19:59:24 +0100 (BST)

Charles Esson writes:
> Would this only occure if the same physical address was mapped into
> different virtual addresses with write enabled. 	 I see it as a
> reasonable restiction that virtual be mapped to the real on a one to one
> basis when write is enabled.

But the cache works on VIRTUAL ADDRESSES NOT PHYSICAL!  If the processor
finds a cache entry for the virtual (program) address, then it *will*
use it!  It doesn't care about the mapping.  The reason for this is that
the processor/cache/mmu work as follows:

	Processor wants to read a word.
	 - cache gets searched (always, whether caching is enabled or not).
		if entry is found, use it.
	 - if no entry is found, use the mmu to obtain data.  If caching
		is enabled, insert this data into the cache.

The data sections have to use different physical pages for data for
different tasks.  Let's say that two task fopen's a file.  FILE * is
returned from an array of FILE *filp[].  filp would be located in the
shared library.

> To use fixed address libaries code one could you put aside the fixed
> addresses required for these libaries. The MMU would then map the
> virtual into real as the libs are used. Problems would arise if the libs
> have data sections that have to be mapped to different physical
> addresses for different tasks. I have always assumed the libs use stack
> and heap space from the calling task but perhaps this is a bad
> assumption. 

On fopen'ing, both tasks believe that the third entry is free.  You
use that entry.  One task writes address 0x9a40 into it, the other
writes 0x9a20.  Immediately, one task has the wrong data available to
it.

Malloc() does extend the BSS segment on the binary, extending it towards
the shared library.

> You would have to allocate the virtual address space out of a system
> pool on task loading, but you could still map to one physical page as
> long as it was write protected.

I will quote from the StrongARM data sheet:

 The Dcache operates with virtual addresses, so care must be taken to
 ensure that its contents remain consistent with the virtual to physical
 mappings performed by the memory management unit.  If the memory mappings
 are changed, the Dcache validity must be ensured.

On a task switch, the virtual to physical address mappings are changed
to map in the new tasks text segment into 0x8000, so whatever you do with
libraries or anything (unless you're only running multiple copies of the
same program) you HAVE to flush the cache.  You can't get away from it!
No way out!

> I see code being sharable, data non sharable, and stacks a bit of a
> problem as you can't allocate them in the middle of nowhere, you have to
> get some virtual space from the operating system when the task is
> created, and the operating system has to be given some hint about the
> stack size required. To make this work ELF would have to tell me what is
> read only and what is read/write. Further linux would have to keep this
> info for the fork, but I think this is the case.
> 
> I have assumed that ZERO_PAGE is write and read protected so you can
> allocate real memory if you actually access it. If this is the case
> would PAGE_ZERO ever get read or written to be cached. Does ZERO_PAGE
> really have to be mapped to real memory.

Are you really sure that you want to use Linux for this?  It sounds like
you're basically going to have to re-write the whole of the memory
management system (and therefore the mmap()ing of the filesystems)!
   _____
  |_____| ------------------------------------------------- ---+---+-
  |   |       Russell King      [email-masked]         --- ---
  | | | | http://whirligig.ecs.soton.ac.uk/~rmk92/home.html  /  /  |
  | +-+-+                                                     --- -+-
  /   |               THE developer of ARM Linux              |+| /|\
 /  | | |      *  who wishes that he was in Hong Kong  *      ---  |
    +-+-+ -------------------------------------------------  /\\\  |

---

From: Charles Esson <[email-masked]>
Date: Fri, 04 Jul 1997 19:05:27 +1000

>                 is enabled, insert this data into the cache.

Yes there is a problem. When you switch task there is no rule which says
that you have to use a different virtual address space if you live with
this restriction then I can't see why the cache will not always reflect
reality. But you do need to alter the read write status of different
areas. It would seem a flush of the tags invalides the data in the cache
so one has to write back the data in the cache before doing such an
operation. To quote the manual:
" a flush whole must be preceeded by a sequence of loads to cause the
cache to write back dirty entries".

If this is the case, I consider all is lost. Up to now I have lived with
a operating system that works with no MMU. I don't see memory
fragmentaiton as a problem, being able to allocate required memory out
of a virtual memory space instead of a real space would be a dream. But
I want to have tasks restricted to there own space, finding bugs that
write into someone elses space can be a problem.

I don't care what anyone says, 16k flush is not the go for real time
work. Look at the code suggested, it's a load, a test, and a branch, I'm
no expert on the timing but my quess is 5 cycles for the memory read (
you have to move from CCLK to MCLK ), 1 for the test and two for the
branch thats 112000 cycles we have 200,000,000 of them a second. Thats
0.5 msec. Even under linux task switches are common events, in a real
time system they are a dime a dozen. 

I am depressed.

And