Dunk,
Looked at your code again and still don't see anything that stands out as being wrong. You say if you take out Task 2 and 3 it works? So then it's something in Task 2 and 3 that's causing it to fail. To narrow it down, test it with just Task 1 and 2. Next, run just Task 1 and 3. Let me know what happens.
Also in the failing case, you said it doesn't return from SPI_transfer. From your code the first time SPI_transfer is called should be from: MAT_flsh_Test() -> MAT_flsh_Block_Erase() -> MAT_spi_transfer() -> SPI_transfer(). Is this the SPI_transfer that doesn't return or is it in subsequent SPI transfers from MAT_flsh_Page_Program() or MAT_flsh_Page_Read().
Moses