الدرس 22: تسابقات الذاكرة العالمية — لماذا نحتاج atomics
حتى الآن، كان كل kernel كتبته تقريبًا يمنح كل thread خانة الإخراج الخاصة به: c[i] = a[i] + b[i]، حيث يكون thread رقم i هو الوحيد الذي يلمس c[i] على الإطلاق. وبما أنه ما من threadين يتشاركان وجهة واحدة، فإن الترتيب الذي يعملان به لا يهم — والنتيجة صحيحة دائمًا. لكن بعض المسائل تُجبر الكثير من الـ thr
تخيّل 30 طفلًا يتشاركون ورقة إحصاء واحدة مكتوب عليها 5. ينظر اثنان إليها معًا، ويرى كلاهما 5، ويكتب كلاهما 6 — واختفى عدّ واحد. العملية الذرية (atomic operation) هي قاعدة تقضي بأن يمسك طفل واحد فقط بالقلم في كل مرة (قراءة، إضافة، كتابة)، فلا يضيع أي عدّ أبدًا.
- حالة التسابق (race condition)
- علة تعتمد فيها النتيجة على التوقيت والترتيب غير المتوقعين اللذين تلمس بهما الـ threads البيانات نفسها — قد تعمل في تشغيلة وتفشل في التالية.
- قراءة-تعديل-كتابة (read-modify-write)
- العملية x++ هي في الحقيقة ثلاث خطوات — قراءة x، وإضافة 1، وكتابة x. ويمكن لـ thread آخر أن يتسلل بين هذه الخطوات.
- التحديث المفقود (lost update)
- يقرأ threadان القيمة القديمة نفسها ويكتب كلاهما مرة أخرى، فتختفي إحدى الزيادتين ببساطة ويخرج العدّ منخفضًا أكثر مما ينبغي.
- العملية الذرية (atomic operation)
- عملية read-modify-write غير قابلة للتجزئة لا يستطيع أي thread آخر مقاطعتها — وهي الحل للتسابق، مثل atomicAdd.