Вот два возможных решения.
Вы можете изолировать ВСЕ доступ к сокету в потоке сокета (неосновном), и вместо того, чтобы отсоединить сокет от первичного потока, пусть этот поток сигнализирует неосновныйПоток, который отключается (или какое-то другое действие), необходим.Это потребует от вашего вторичного потока ожидания двух объектов - сокета и сигнализатора (скажем, Win32 Event ), который указывает на необходимость отключения.
Если, с другой стороны, вы хотитечтобы позволить первичному потоку отключиться (как вы это делаете сейчас), вам необходимо проверить весь ваш код, использующий сокет, и сделать его поточно-ориентированным, используя средства защиты от блокировки, чтобы предотвратить одновременный доступ к сокету и связанным данным состояния. Boost.Thread имеет подходящие блокировки, которые вы можете использовать здесь, в противном случае вы можете реализовать свою собственную как оболочку для чего-то вроде Win32 CriticalSection .
Вторым будет мое предпочтительное решение - тот факт, что вы задаете этот вопрос, означает, что вам все равно нужно вернуться и подумать о безопасности потоков в своем проекте.Даже если вы придерживаетесь первой идеи, изложенной выше, вам все равно, вероятно, потребуется поддерживать состояние, чтобы избежать нескольких сигналов разъединения, отправляемых из основного потока, и это должно быть защищено блокировкой.Также, если вы хотите, чтобы неосновной поток обрабатывал входящие события, отличные от «разъединения», между потоками должно было бы быть связано состояние, которым нужно будет управлять.
Я думаю, что путь наименьшего сопротивления с того места, где вы сейчас находитесь, - это добавить блокировку к существующему коду.Удостоверьтесь, что вы ограничиваете свои блокировки настолько узко, насколько это возможно - не устанавливайте блокировку, которую вы удерживаете для любого вызова сокета, который может блокировать или занимать, например, длительное время.