Normally, each process has an isolated (ie., private) bit of memory. When data needs to be shared, a block of "shared memory" can be defined. Access to this memory needs to be carefully synchronized using synchronization primitives (e.g., semaphores, critical sections) because you never know if the other process is changing the data while you are reading it. (A common source of bugs)