This is a micro controller, so single thread. As I said the problem is that I need the compiler to not assume variables have not changed, basically to not try to optimize that, to do that I have to rewrite everything from what you say. Sorry, but the compiler has caused the compilers own problem because even with no optimization turned on it will cause an issue. Now it is easy to simply disable the interrupt during the memcpy access but the compiler will not understand this either will it? I have no way of helping the compiler.
Microcontrollers can be just as multithreaded.
You can run a RTOS on a MCU and have many threads. Even without a RTOS you still have the equivalent of threads when interrupt service routines get called. The ISR could happen at any point in your main thread code, so things could change in between any two instructions. Heck these days MCUs even have CPU cache, so you can even run into cache coherency issues like you can in multicore CPUs (Except here it tends to happen between the CPU and DMA controller). All of this is just part of programing modern computers.
You can always just globally disable all optimizations, but this has a significant speed impact so you likely won't want to do that. So you have to explain to the C compiler what it can and can't assume.
The volatile keyword only sticks to the variable type, not the contents, hence why C will warn you when casting volatiles into other normal types, so after the cast the compiler can't know it is volatile. If you have issues with memcpy, you can always write your own mem copy function that takes volatile as parameters. Inside your custom mem copy you can optimize it as much as you like for what your application can handle, it can be a simple byte by byte FOR loop, or up to a fancy super fast assembler hand optimized function with SIMD instructions.
Just make sure you understand where the problem you are having is coming from. Reading weird values from RAM can be caused by compiler attempting to optimize multitreaded code, however it can also be caused by a buffer overrun somewhere tramping over your memory or a cache coherence issue holding onto old data.