In the last instalment we cycled through a number of work groups each containing two cores, within the work group these cores ran slightly different applications to demonstrate parallel operation. The output of these applications consisted of the coreid and a simple identifier as to which core in the work group had generated it.
Rather helpfully this application provides a platform to build a demonstration of how we can communicate between cores in the simplest form. The previous example stored the information intended for communication with the host processor within local memory, these were then accessed by the host using the Hardware Abstraction Library e_read() function to extract the stored data from the local memories and display it. However by understanding the architecture of the Epiphany memory we will gain a understanding of how we can use this for inter core communication.
Each of the 16 cores within a epiphany chip has 32 KB of local memory which is used for both program and data storage. This 32KB is sub divided into four 8 KB banks, it is good practice to store data and code in separate memory banks, this gives a local memory address between 0x0000 and 0x7FFFF for each core.
The Epiphany however, has a flat memory space globally, this enables any core to access another cores local memory to do this we must extend the address from five bytes to eight which allows for the addressing of the each cores local memory. To ease addressing the three remaining bytes are split into two 6 bit fields which identify the RowID and ColumnID of the addressed core the combined 8 Byte address is known as the global address.
This provides the ability to communicate simply between cores, small quantities of information while if a higher data rate is needed we can use the Network on Chip (NOC) which will be addressed in future blogs.
A very simple example of this can be the swapping of information from the example we used in the last blog that is each core will store its coreid and message in the others local memory. When the host reads them out this make them appear swapped in terms of what we saw in the last blog.
In the simplest case we can achieve this by looking up the global address we require for the core concerned and modifying the pointer addresses in the epiphany applications to the opposite cores location we can use the table below to help us.
For instance the first application hello_world.c stores its information at address 0x80903000 i.e. that of the second core, while the second application (hello_world2.c) stores its information at address 0x80803000 the address of the first. Note the only bytes which change are the upper three which define column and row information
As demonstrated below the original from issue 4
While the flipped core and message ID’s resulting from the updated code is below
In the next blog we will look further in detail at how we can use the flat memory space to transfer more than a few bytes about and look at the shared memory with the Host as that is obviously an interesting method of sharing data between host and epiphany cores.
You can find the code for this example here as always
Links to previous instalments of this series
Part 4 Work Groups
Part 3 Hello World
Part 2 The SDK
Part 1 Introduction