A shared_ptr<> is a mechanism to ensure that multiple object owners ensure an object is destructed, not a mechanism to ensure multiple threads can access an object correctly. You still need a separate synchronization mechanism to use it safely in multiple threads (like std::mutex).
Basically, a shared_ptr<> points to a "control block" which is how it keeps track of how many shared_ptr<> objects are actually pointing to the "Real" object.
It is only the control block itself which is thread-safe.