Wow, that is fast enough that it could be real-time. You said it takes 500 milliseconds, so if you used four threads that would go down to 125 msecs. But the whole things doesn't have to be updated all at once. You could easily cycle through and just do a limited number each frame, and a slow-moving light would look the same. Without threading, at 60 FPS it would take 30 frames to get through the entire job, so the whole thing would update twice each second.
If you use Collider::Pick instead of the world raycast function, that will get rid of a lot of overhead and should be thread-safe.