توقّف اتّصال الكاميرا الصناعيّة بسبب إعادة إرسال TCP: السبب والتضييق
· آخر تحديث: · 小村 豪 · TCP, الشبكات, التحقيق في الأعطال, تطوير Windows, الكاميرا الصناعيّة
سجل التعديلات (3 تحديثات، آخر تحديث 3 Sep، 2026)
سجل بالتغييرات التي أُجريت على هذا المقال. وحيثما حُفظت نسخة سابقة، تبقى متاحة للقراءة عبر رابط دائم يحمل معرّف DOI.
- أُضيفت روابط الاستشارة الموجودة في الأصل الياباني (consultation_services). ولم يتغيّر نصّ المقالة نفسه. قراءة النسخة السابقة لهذا التحديث (DOI: 10.5281/zenodo.22240807)
- أُعيدَت الترجمة العربية كترجمة كاملة عن النص الياباني الأصلي، وأُضيفَت خريطة المعرفة.
- أعيدت الترجمة كترجمة كاملة عن النص الياباني الأصلي. كانت النسخة العربية السابقة مختصراً يسقط أبواباً وجداول ورسوم Mermaid وتعليقات الأشكال وFAQ. أُعيدت هذه العناصر وفق الأصل الياباني، والادّعاءات التقنية مطابقة للنسخة اليابانية.
- النشر الأول
الاستشهاد بهذا المقال(DOI: 10.5281/zenodo.21621327)
هذا المقال محفوظ على Zenodo. يرد أدناه معرّف DOI الذي يشير دائمًا إلى أحدث نسخة، ومعرّف DOI المثبَّت على النسخة التي تقرؤها.
小村 豪 (2026). توقّف اتّصال الكاميرا الصناعيّة بسبب إعادة إرسال TCP: السبب والتضييق. شركة كومورا سوفت ذ.م.م.. https://doi.org/10.5281/zenodo.21621327 https://comcomponent.com/ar/blog/2026/03/11/001-tcp-retransmission-rfc1323-industrial-camera/
- DOI (أحدث نسخة)
- 10.5281/zenodo.21621327
- DOI (هذه النسخة)
- 10.5281/zenodo.22279715
في اتّصالات الكاميرات الصناعيّة والتحكّم بالأجهزة، أشدّ الظواهر إزعاجاً أن يكون المعدّل سريعاً لكن يتوقّف أحياناً لعدّة ثوانٍ. معدّل إعادة الإنتاج منخفض، وفي الأوقات العاديّة لا يحدث شيء، فتبدو الواجهة والخيوط وGC وSDK الكاميرا وNIC والمبدّل كلّها مشبوهة قليلاً.
ما نعالجه هنا ظاهرة توقّف الاتّصال لعدّة ثوانٍ نادرة في TCP بين تطبيق يتحكّم بكاميرا صناعيّة والمضيف. بالتحقيق تبيّن أنّ الهويّة ليست توقّف التطبيق، بل انتظار إعادة إرسال TCP الناشئ عن فقد الحزم. ثمّ بتمكين وظيفة الطوابع الزمنيّة من عائلة RFC1323 (في الترتيب الحاليّ RFC 7323) أمكن في هذا النظام تقريب زمن الانتظار إلى الحدّ الأدنى.
أُعمِّمت أسماء الأجهزة والتكوين والأرقام، لكنّ طريقة التفكير تُستخدَم كما هي في العمل.
المحتويات
- الخلاصة أوّلاً (في جملة)
- كيف بدا العَرَض
- 2.1. التطبيق حيّ، لكنّ الاستجابة وحدها تتوقّف لعدّة ثوانٍ
- 2.2. التردّد منخفض، فالسجلّات وحدها تخفيه
- ما الذي كان يحدث (رسوم)
- 3.1. من فقد الحزم إلى انتظار إعادة الإرسال
- 3.2. توقّف الثواني كان يطابق شكل RTO
- ما نظرنا إليه في التحقيق
- 4.1. أوّلاً استبعاد عوامل التوقّف داخل التطبيق
- 4.2. تأكيد إعادة الإرسال بالتقاط الحزم
- 4.3. النظر إلى خيارات TCP المتفاوض عليها
- لماذا تنفع طوابع RFC1323 الزمنيّة
- 5.1. الطوابع الزمنيّة لأجل RTTM وPAWS
- 5.2. إزالة غموض قياس RTT عند إعادة الإرسال
- 5.3. لماذا أمكن تضييق الانتظار في هذه الحالة
- ما نُفِّذ فعلاً
- 6.1. تفعيل الطوابع الزمنيّة
- 6.2. التحقّق من TSopt في SYN / SYN-ACK
- 6.3. أين ننظر إذا لم ينفع ذلك
- نقاط النظر في Wireshark
- دليل اختيار تقريبيّ
- الخلاصة
- روابط مرجعيّة
في المخطّط، يشير الخطّ المتّصل إلى علاقة قائمة دائماً، ويشير الخطّ المتقطّع إلى علاقة مشروطة (شروط قيامها مذكورة في شرح كلّ علاقة في الصفحة التفصيليّة). القائمة الكاملة للعلاقات (المجموع 19، مع الأدلّة ودرجة اليقين) وتعريفات المفاهيم الرئيسة مجمّعة في صفحة تفاصيل خريطة المعرفة (باليابانية). البيانات: JSON-LD / Turtle
1. الخلاصة أوّلاً (في جملة)
- اتّصال TCP الذي يتوقّف أحياناً لعدّة ثوانٍ قد تكون هويّته انتظار إعادة الإرسال بعد فقد الحزم لا توقّف التطبيق
- إذا ظهر في التقاط الحزم
Retransmissionوفرق زمنيّ كبير، وكان زمن التوقّف يطابق طريقة انتظار RTO، فالشبهة قويّة - TCP timestamps option آليّة لقياس RTT وPAWS، وتزيل أيضاً غموض قياس RTT عند إعادة الإرسال
- في هذه الحالة، بتمكين وظيفة الطوابع الزمنيّة من عائلة RFC1323 قلّ الزمن الذي يبقى فيه تقدير RTO قديماً محافظاً، فقُرِّب التوقّف بالثواني إلى الحدّ الأدنى
- لكنّ هذا ليس سحراً يلغي الفقد نفسه. مراجعة الطبقة الفيزيائيّة وNIC والمبدّل والأجهزة الوسيطة والتعريف وتصميم المخازن تبقى لازمة على حدة
باختصار: إذا كانت هويّة «التوقّف أحياناً لعدّة ثوانٍ» زمناً داخليّاً في TCP، فالاجتهاد في إعادة المحاولة من التطبيق وحده يخطئ اللبّ. النظر أوّلاً إلى السلك وتثبيت هل الانتظار انتظار إعادة إرسال أسرع.
flowchart TB
accTitle: تدفّق خلاصة هذا المقال
accDescr: يبيّن أنّ اتّصال TCP الذي يتوقّف أحياناً لعدّة ثوانٍ يُثبَّت أوّلاً بالنظر إلى السلك هل هو انتظار إعادة إرسال، وأنّ الانتظار قد يُضيَّق بالطوابع الزمنيّة أحياناً، بينما يبقى التحقيق في مصدر الفقد منفصلاً.
sym["اتّصال TCP يتوقّف أحياناً لعدّة ثوانٍ"] --> wire["النظر أوّلاً إلى السلك"]
wire --> conf["تثبيت هل هو انتظار إعادة إرسال"]
conf -.-> ts["قد يُضيَّق الانتظار بالطوابع الزمنيّة"]
conf -.-> loss["التحقيق في مصدر الفقد يبقى منفصلاً"]
الشكل 1: قبل الاجتهاد في إعادة محاولة التطبيق، يُحدَّد من السلك «أين يُنتظَر».
من هنا تظهر اختصارات TCP متتالية. لمطوّري Windows غير المتخصّصين في الشبكات نلخّصها أوّلاً. ضبط هذا الجدول يكفي للمتابعة بلا توقّف.
| المصطلح | الاسم الكامل | المعنى |
|---|---|---|
| ACK | Acknowledgment | تأكيد الاستلام. آليّة تُعلِم الطرف الآخر «استُلم حتّى هنا» |
| RTT | Round-Trip Time | زمن الذهاب والإياب. من الإرسال حتّى عودة ACK |
| RTO | Retransmission Timeout | مؤقّت إعادة الإرسال. إذا لم يعد ACK خلال هذا الزمن يُعاد الإرسال. يُحسَب من تقدير RTT |
| RTTM | Round-Trip Time Measurement | قياس RTT. أحد أغراض وظيفة الطوابع الزمنيّة |
| PAWS | Protect Against Wrapped Sequences | وقاية من حادث دوران رقم التسلسل. الغرض الآخر لوظيفة الطوابع الزمنيّة |
| TSopt | TCP Timestamps Option | خيار يلحق ترويسة TCP. النوع 8 والطول 10 بايت، ويحمل القيمتين التاليتين |
| TSval | Timestamp Value | قيمة ساعة الجانب المرسل التي يضعها هو |
| TSecr | Timestamp Echo Reply | حقل يعيد TSval المستلم كما هو. به يُعرَف «ACK لأيّ إرسال» |
| SACK | Selective Acknowledgment | آليّة يبلّغ بها الجانب المستقبل «أيّ نطاق استُلم» فرداً |
| Dup ACK | Duplicate ACK | عودة ACK يشير إلى رقم التسلسل نفسه مكرّراً. إشارة إلى وجود فجوة في الوسط |
| fast retransmit | — | إعادة إرسال دون انتظار انتهاء RTO إذا تجمّع عدد معيَّن من Dup ACK. افتراض Windows: «عند استلام 3 ACK لنفس رقم التسلسل (الأوّل واثنان مكرّران)» |
| خوارزميّة Karn | — | قاعدة: لا تُؤخَذ عيّنة RTT من مقطع أُعيد إرساله. لأنّه لا يُعرَف لأيّ إرسال يعود ACK |
2. كيف بدا العَرَض
2.1. التطبيق حيّ، لكنّ الاستجابة وحدها تتوقّف لعدّة ثوانٍ
أوّل ما يعقّد الأمر أنّ التطبيق كلّه لا يبدو متجمّداً.
- الواجهة ليست ميّتة تماماً
- العمليّة لم تسقط
- المعالج ليس ملتصقاً
- لكنّ استجابة أوامر التحكّم بالكاميرا أحياناً تسقط لعدّة ثوانٍ
هذا العَرَض يصعب تمييزه عن deadlock داخل التطبيق أو حلقة لا نهائيّة. وفي التحكّم بالأجهزة يصير توقّف ثوانٍ واحدة انطباعاً بتوقّف الخطّ. حتّى لو كان المعدّل نظيفاً، إحساس الموقع سيّئ جدّاً.
2.2. التردّد منخفض، فالسجلّات وحدها تخفيه
ما يزعج في هذا النوع من العطل انخفاض تردّد الحدوث. مرّة في الساعة، مرّة في نصف يوم، فقط عندما تتراكب الشروط.
إذا تُوبع بالسجلّات وحدها يصير الأمر تقريباً هكذا.
- سجلّ التطبيق يتوقّف عند «أُرسل» و«لم يعد شيء»
- سجلّ الجانب المستقبل يبدو «لم يأتِ شيء»
- أحداث أخرى تقع مصادفة في المدّة نفسها فتتشتّت هويّة الجاني
هنا، محاولة استعادة السببيّة من سجلّ التطبيق وحده تغرق بسهولة. النزول درجة إلى طبقة الاتّصال أسرع.
flowchart TB
accTitle: تركيب لا يُحدَّد فيه الجاني من السجلّات وحدها
accDescr: يبيّن أنّ سجلّ التطبيق يتوقّف عند أُرسل ولم يعد، وسجلّ الجانب المستقبل يبدو لم يأتِ شيء، وأحداث أخرى في المدّة نفسها تشتّت الجاني، لذا لا تُستعاد السببيّة من سجلّ التطبيق وحده بل يُنزل إلى طبقة الاتّصال.
l1["سجلّ التطبيق: أُرسل ولم يعد"] --> lost["تشتّت الجاني والغرق"]
l2["سجلّ الجانب المستقبل: لم يأتِ شيء"] --> lost
l3["أحداث أخرى في المدّة نفسها"] -.-> lost
lost --> down["النزول درجة إلى طبقة الاتّصال"]
الشكل 2: التوقّف منخفض التردّد يغرق إذا تُوبع بالسجلّات وحدها. النظر إلى الحزم أسرع.
3. ما الذي كان يحدث (رسوم)
3.1. من فقد الحزم إلى انتظار إعادة الإرسال
مسار هذه الحالة بسيط. سقطت حزمة في مكان ما في الطريق، فانتظر الجانب المرسل ACK، ولم يأتِ فانتظر RTO ثمّ أعاد الإرسال.
sequenceDiagram
participant Host as تطبيق المضيف
participant Net as الشبكة
participant Cam as جانب الكاميرا
Host->>Net: أمر تحكّم (Seq=N)
Note over Net: الفقد هنا
Note over Host: الانتظار لأنّ ACK لم يأتِ
Note over Host: تعافي هذا الطلب يدخل فيه انتظار RTO
Host->>Net: إعادة إرسال أمر التحكّم
Net->>Cam: وصول حزمة إعادة الإرسال
Cam-->>Net: ACK
Net-->>Host: ACK
Note over Host: هنا يُستأنف الاتّصال
الشكل 3: إذا سقطت الحزمة لا يعود ACK، فيُعاد الإرسال بعد انتهاء RTO. التطبيق يرى هذه الفترة «توقّفاً لعدّة ثوانٍ».
من جهة التطبيق يبدو «توقّفاً لعدّة ثوانٍ»، أمّا من جهة TCP فهو فقط «لم يأتِ ACK بعد فانتظرنا انتهاء مؤقّت إعادة الإرسال». شكل التوقّف هذا شائع وإن بدا باهتاً.
اتّصال التحكّم هنا كان كثير request/response الصغير، ولم تُرسَل كمّيّة كبيرة من البيانات غير المؤكَّدة في تبادل واحد. لذلك ظهر انتظار RTO قبل أن تتجمّع duplicate ACK بما يكفي لركوب fast retransmit.
flowchart TB
accTitle: لماذا يظهر انتظار RTO في اتّصال التحكّم
accDescr: يبيّن أنّ اتّصال التحكّم الذي يغلب عليه request/response صغير يقلّ فيه البيانات غير المؤكَّدة فلا تتجمّع Dup ACK بما يكفي، فيصعب ركوب fast retransmit ويظهر انتظار RTO.
small["غلبة request/response الصغير"] --> few["قلّة البيانات غير المؤكَّدة"]
few --> nodup["عدم تجمّع Dup ACK بما يكفي"]
nodup --> nofr["صعوبة ركوب fast retransmit"]
nofr --> rto["ظهور انتظار RTO"]
الشكل 4: بخلاف الاتّصال الذي تجري فيه كمّيّات كبيرة من البيانات، فقد اتّصال التحكّم يميل إلى انتظار انتهاء RTO.
3.2. توقّف الثواني كان يطابق شكل RTO
انتظار إعادة إرسال TCP، مع فروق التنفيذ، ينتظر انتظاراً محافظاً. في RFC 6298 القيمة الابتدائيّة لـ RTO معيارها ثانية واحدة، وإذا كانت نتيجة الحساب أصغر تُرفَع إلى ثانية، وإذا انتهت المهلة تُضاعَف.
flowchart LR
A["فقد الحزم"] --> B["ACK لا يأتي"]
B --> C["انتظار RTO"]
C --> D["إعادة الإرسال"]
D --> E{"هل عاد ACK؟"}
E -- نعم --> F["استئناف الاتّصال"]
E -- لا --> G["مضاعفة RTO"]
G --> C
الشكل 5: RTO يُضاعَف كلّما لم يعد ACK. انتظار ثانية ثمّ ثانيتين ثمّ أربع يأتي من هذا الشكل.
لذلك، حتّى في موضع يُراد إنهاؤه بمئات الميلي ثانية، قد يظهر الانتظار كثانية ثمّ ثانيتين ثمّ أربع إذا ساءت الظروف. «التوقّف أحياناً لعدّة ثوانٍ» في هذه الحالة كان يطابق هذا الشكل بصراحة.
4. ما نظرنا إليه في التحقيق
4.1. أوّلاً استبعاد عوامل التوقّف داخل التطبيق
لم نبتّ في TCP من البداية، بل استبعدنا أوّلاً العوامل النموذجيّة في جانب التطبيق.
| ما تُحقّق منه | سبب النظر | خلاصة هذه الحالة |
|---|---|---|
| خيط الواجهة / خيوط العمّال | التحقّق من التعليق والانتظار المتبادل | لم يكن السبب الرئيسيّ |
| استخدام المعالج | التحقّق من تأخّر المعالجة بسبب الحمل | لم يكن التصاقاً حتّى عند التوقّف |
| GC / ضغط الذاكرة | التحقّق من التوقّف المؤقّت | شكل زمن التوقّف لم يطابق |
| استدعاء SDK الكاميرا | التحقّق من انتظار داخل SDK | لم يطابق التأخّر على السلك |
| التقاط الحزم | تأكيد إعادة الإرسال في طبقة الاتّصال | هنا ظهر مسار السبب |
المهمّ هنا ألا يُحدَّد الجاني من أوقات سجلّ التطبيق وحدها. في تطبيقات التحكّم بالأجهزة قد يكون انتظار الطبقة العليا مجرّد انعكاس لانتظار الطبقة الأدنى.
flowchart TB
accTitle: ترتيب التضييق باستبعاد عوامل التطبيق أوّلاً
accDescr: يبيّن ترتيب التضييق: لا يُبتّ في TCP من البداية، بل تُستبعَد أوّلاً عوامل التوقّف النموذجيّة داخل التطبيق مثل الخيوط والمعالج وGC وSDK الكاميرا، ثم يُؤكَّد إعادة الإرسال في طبقة الاتّصال بالتقاط الحزم.
app["استبعاد الخيوط والمعالج وGC وSDK أوّلاً"] --> cap["النظر إلى طبقة الاتّصال بالتقاط الحزم"]
cap --> found["ظهور مسار إعادة الإرسال"]
app -.-> warn["عدم تحديد الجاني من وقت السجلّ وحده"]
الشكل 6: لا يُبتّ مسبقاً. تُستبعَد العوامل النموذجيّة داخل التطبيق ثم يُنزل إلى السلك.
4.2. تأكيد إعادة الإرسال بالتقاط الحزم
بالتقاط الحزم ظهر TCP Retransmission في فترة التوقّف، وتبيّن فوق ذلك أنّ ACK لم يكن قد عاد قبيل ذلك.
ما يُنظَر إليه تقريباً هذا.
- هل ظهرت إعادة إرسال لنفس
Seq - هل فرق الزمن حتّى إعادة الإرسال يطابق زمن التوقّف
- هل يبدو انتظار انتهاء RTO لا
Dup ACKأوFast Retransmission - هل يظهر الاتّصال المشكل في
tcp.streamنفسه في كلّ مرّة
إذا تطابق هذا، تشتدّ كثافة أنّ الأمر ليس «التطبيق متوقّف» بل «TCP ينتظر إعادة الإرسال».
flowchart TB
accTitle: نقاط التأكيد لانتظار إعادة الإرسال
accDescr: يبيّن أنّ تطابق ثلاث نقاط — ظهور إعادة إرسال لنفس Seq، ومطابقة فرق الزمن لزمن التوقّف، وبدوّه انتظار انتهاء RTO لا fast retransmission — يشتدّ معه أنّ الأمر انتظار إعادة إرسال TCP لا توقّف التطبيق.
c1["هل ظهرت إعادة إرسال لنفس Seq"] --> conc["TCP ينتظر إعادة الإرسال"]
c2["هل فرق الزمن يطابق زمن التوقّف"] --> conc
c3["هل يبدو انتظار انتهاء RTO"] --> conc
conc -.-> not["ليس توقّف التطبيق"]
الشكل 7: إذا تطابقت هذه النقاط الثلاث، تشتدّ كثافة «انتظار إعادة إرسال TCP» لا «توقّف التطبيق».
4.3. النظر إلى خيارات TCP المتفاوض عليها
ما نُظر إليه تالياً هو SYN / SYN-ACK عند بدء الاتّصال. الطوابع الزمنيّة تُفاوض في 3-way handshake لاتّصال TCP، فإذا لم يظهر TSopt هنا لا تُستخدَم في ذلك الاتّصال.
sequenceDiagram
participant Host as المضيف
participant Cam as جانب الكاميرا
Host->>Cam: SYN + TSopt ؟
Cam-->>Host: SYN/ACK + TSopt ؟
Host->>Cam: ACK
Note over Host,Cam: بعد نجاح المفاوضة هنا فقط يُستخدَم TSopt في المقاطع اللاحقة
الشكل 8: الطوابع الزمنيّة تُفاوض في 3-way handshake. إذا غاب TSopt عن SYN / SYN-ACK لا تُستخدَم في ذلك الاتّصال.
لمس إعداد نظام التشغيل دون النظر إلى هذا يولّد حادثاً باهتاً آخر: «فعّلناه لكنّه لا ينفع». واقعة السلك أقوى من قيمة الإعداد.
5. لماذا تنفع طوابع RFC1323 الزمنيّة
في العمل ما زال اسم «طوابع RFC1323 الزمنيّة» شائعاً، لكنّ الترتيب الحاليّ هو RFC 7323. في هذا المقال نكتب RFC1323 وفق العرف، والمقصود TCP timestamps option.
5.1. الطوابع الزمنيّة لأجل RTTM وPAWS
يُستخدَم timestamps option في TCP أساساً لغرضين.
- RTTM (Round-Trip Time Measurement)
- PAWS (Protect Against Wrapped Sequences)
ما نفع في هذه الحالة هو جانب RTTM. بإعادة الجانب الآخر TSval للمقطع المرسل في TSecr الخاصّ بـ ACK، يصير قياس RTT أدقّ وأغزر للجانب المرسل.
flowchart TB
accTitle: غرضا timestamps option
accDescr: يبيّن أنّ timestamps option في TCP يُستخدَم لغرضين: RTTM أي قياس زمن الذهاب والإياب، وPAWS أي وقاية دوران رقم التسلسل، وأنّ ما نفع في هذه الحالة هو جانب RTTM.
tso["timestamps option"] --> rttm["RTTM (قياس زمن الذهاب والإياب)"]
tso --> paws["PAWS (وقاية دوران رقم التسلسل)"]
rttm --> hit["ما نفع هنا هو هذا الجانب"]
rttm -.-> how["القياس بإعادة TSval في TSecr الخاصّ بـ ACK"]
الشكل 9: غرض الطوابع الزمنيّة اثنان: RTTM وPAWS. ما نفع في هذه الحالة هو جانب قياس RTT.
5.2. إزالة غموض قياس RTT عند إعادة الإرسال
إذا دخلت إعادة الإرسال، يصير بلا طوابع زمنيّة غامضاً هل هذا ACK للإرسال الأوّل أم لإعادة الإرسال. هذه النقطة التي تهتمّ بها خوارزميّة Karn.
RFC 6298 يقول إنّه لا يجوز أخذ عيّنة RTT من مقطع أُعيد إرساله. السبب أنّه لا يُعرَف لأيّ إرسال يعود ACK. لكن بوجود timestamps option يُزال هذا الغموض. بالنظر إلى TSecr الداخل في ACK يمكن تمييز أيّ مقطع يحمل أيّ TSval وصل.
sequenceDiagram
participant Host as الجانب المرسل
participant Cam as الجانب المستقبل
Host->>Cam: Seq=N, TSval=1000
Note over Host,Cam: فقد هذا المقطع
Note over Host: الانتظار لأنّ ACK لم يأتِ
Host->>Cam: إعادة إرسال Seq=N, TSval=2000
Cam-->>Host: ACK, TSecr=2000
Note over Host: يمكن تمييز لأيّ إرسال كانت الاستجابة
الشكل 10: بالنظر إلى TSecr يمكن تمييز هل ACK استجابة للإرسال الأوّل أم لإعادة الإرسال.
هذا لبّ التحسين في هذه الحالة.
5.3. لماذا أمكن تضييق الانتظار في هذه الحالة
في هذه الحالة كان فقد الحزم يحدث أحياناً، ومع كلّ مرّة كان تقدير RTT / RTO يميل إلى الجانب المحافظ. بتمكين الطوابع الزمنيّة يسهل تحديث تقدير RTT حتّى في المشاهد التي تشمل إعادة الإرسال، فيُكبح الزمن الذي يبقى فيه تقدير RTO متضخّماً قديماً.
هذا موضع يسهل فيه القفز، لذا نفكّكه بمزيد من الأناة.
أوّلاً، الحدّ الأدنى لـ RTO نفسه لا يتغيّر بوجود الطوابع الزمنيّة أو غيابها. RFC 6298 يقول إنّه إذا كان RTO المحسوب دون ثانية فينبغي رفعه إلى ثانية. وقد يحمل التنفيذ حدّاً أدنى خاصّاً به، وفي Windows يقابله MinRtoMs الظاهر في Get-NetTCPSetting (نطاق 20 إلى 300 ميلي ثانية بخطوات 10 ميلي ثانية). أي أنّ الأمر ليس «انخفض الحدّ الأدنى لأنّنا أدخلنا الطوابع الزمنيّة».
ما ينفع هو ما قبل ذلك. يحدّد RFC 6298 الثلاثة التالية.
- مضاعفة RTO كلّما انتهى مؤقّت إعادة الإرسال (تراجع أسيّ)
- RTO بعد التراجع يعود عندما تُحصَّل قياس RTT جديد
- «قياس RTT الجديد» هذا لا يُحصَّل إلا عندما تُرسَل بيانات لم تُعد إرسالها ويأتي ACK
وفوق ذلك، بخوارزميّة Karn لا يجوز أخذ عيّنة RTT من مقطع أُعيد إرساله. لكنّ هذا القيد يُرفع عند استخدام timestamps option. كما في 5.2، بالنظر إلى TSecr يمكن تمييز لأيّ إرسال يعود ACK.
بترتيب هذا يظهر المسار. في نظام يتواصل فيه الفقد متفرّقاً، بلا طوابع زمنيّة يصعب اجتماع شرطي 2 و3، فيبقى الزمن الذي يعود فيه RTO المضاعَف استناداً إلى قياس فعليّ طويلاً. إذا جاء الفقد التالي في تلك الحالة، يبدأ الانتظار من ثانيتين أو أربع لا من ثانية. بوجود الطوابع الزمنيّة يمكن القياس مجدّداً حتّى في فترة تشمل إعادة الإرسال، فيقصر «زمن العجز عن العودة». هذا المسار الذي نفع هنا.
flowchart TB
accTitle: شروط عودة RTO المضاعَف وأثر الطوابع الزمنيّة
accDescr: يبيّن أنّ RTO يُضاعَف عند كلّ انتهاء مهلة ويعود عند حصوّل قياس RTT جديد، لكنّ ذلك القياس لا يُحصَّل إلا من ACK لبيانات لم تُعد إرسالها، وأنّ رفع هذا القيد بالطوابع الزمنيّة يقصر الزمن الذي يعجز فيه RTO المضاعَف عن العودة.
backoff["مضاعفة RTO عند كلّ انتهاء مهلة"] --> ret["العودة بقياس RTT جديد"]
ret -.-> limit["القياس من ACK لبيانات لم تُعد إرسالها فقط"]
ts2["القياس ممكناً بالطوابع حتّى في فترة إعادة الإرسال"] --> often["زيادة فرص إعادة القياس"]
often --> short["قصر زمن عجز RTO المضاعَف عن العودة"]
الشكل 11: اللبّ ليس انخفاض الحدّ الأدنى، بل عودة RTO المضاعَف أسرع بالقياس الفعليّ.
بصراحة: هذا المقال لم يأخذ قيماً مقاسة لـ RTO بعد التحسين. ما نعرفه أنّ التوقّف بالثواني انخفض إلى درجة لم تعد مشكلة في الموقع. إذا أُريد إظهار الأثر بأرقام، أقصر طريق هو تجميع توزيع فرق الزمن حتّى إعادة الإرسال before / after باستخدام مرشّحات العرض في الفصل 7 وعمود Time delta from previous displayed packet.
بعبارة أخرى، ما فُعل هنا ليس سحراً يسرّع TCP، بل تقليل الزمن الذي يستمرّ فيه TCP في الترقّب أطول ممّا يلزم.
طبعاً، RFC 7323 لا يقول «زيادة عيّنات RTT تحلّ كلّ شيء بنظافة». درجة النفع في تحسين RTO محدودة في جانب. لكنّ إزالة الغموض عند إعادة الإرسال قد تنفع بصراحة في أنظمة كهذه.
هناك أيضاً تنبيهات.
- هذا يعتمد على تنفيذ مكدّس TCP
- الطوابع الزمنيّة وحدها لا تلغي فقد الحزم نفسه
- إذا ساءت الطبقة الفيزيائيّة أو الأجهزة الوسيطة، فالسبب الجذريّ في مكان آخر
- SACK وتعريف NIC وإعدادات offload ومشكلات جانب المبدّل يُفضَّل النظر إليها على حدة
لكن في نظام مثل هذه الحالة — «الفقد ليس صفراً» و«ما يؤلم حقّاً هو انتظار الثواني» — قد ينفع كثيراً.
6. ما نُفِّذ فعلاً
6.1. تفعيل الطوابع الزمنيّة
كإجراء، جُعل الطرفان في حالة يمكن فيها مفاوضة timestamps option. في أنظمة Windows قد تُعامَل كخيارات RFC 1323، وتتأثّر بإعداد نظام التشغيل وإعداد الشبكة.
نكتب الخطوات العمليّة. أوّلاً يُنظَر إلى الحالة الحاليّة.
netsh interface tcp show global
في الخرج بند لطوابع RFC 1323 الزمنيّة، فيُؤكَّد هل هو مفعَّل. للتفعيل، من موجه أوامر بامتيازات مدير هكذا.
netsh interface tcp set global timestamps=enabled
ما يمكن تعيينه لـ timestamps ثلاثة: disabled / enabled / default، وdefault يعيد الافتراضيّ النظاميّ.
للنظر والتعيين من PowerShell هذا.
Get-NetTCPSetting | Select-Object SettingName, Timestamps, MinRtoMs, InitialRtoMs
Set-NetTCPSetting -SettingName InternetCustom -Timestamps Enabled
ما يمكن تعيينه لـ Timestamps هو Enabled / Disabled. SettingName القابل للتغيير يختلف حسب إصدار Windows، لذا لا تُضرَب Set- فوراً، بل يُؤكَّد أوّلاً الاسم الموجود بـ Get-NetTCPSetting. تمرير اسم غير موجود يتوقّف هناك.
في البيئات القديمة، للنظر مباشرة في السجلّ، Tcp1323Opts (REG_DWORD) في المفتاح التالي.
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters
معنى القيمة: 0 يعطّل خيارات RFC 1323، و1 لتحجيم النافذة فقط، و2 للطوابع الزمنيّة فقط، و3 لتفعيل الاثنين. بتذكّر أنّ البت 0 لتحجيم النافذة والبت 1 للطوابع الزمنيّة لا يحدث حيرة.
عند التعيين ثلاثة تنبيهات.
- النفع من الاتّصالات الجديدة فقط. الطوابع الزمنيّة تُفاوض في 3-way handshake، فلا تنفع الاتّصالات القائمة. يلزم إعادة إنشاء اتّصال جانب الجهاز
- لا ينعقد إن لم يدعم الطرفان. تفعيل جانب المضيف وحده لا يكفي إذا لم يُرجع جانب الكاميرا TSopt في SYN/ACK، فلا يُستخدَم في ذلك الاتّصال
- الإعداد يغيّر أيضاً طبيعة الاتّصال. الطوابع الزمنيّة تكبر ترويسة TCP، فتقلّ قليلاً البيانات المحمولة في المقطع الواحد
لكن في العمل، «ركوب TSopt على حزمة SYN / SYN-ACK الفعليّة» أهمّ من «مفعَّل في شاشة الإعداد». هذا صحيح حقّاً.
flowchart TB
accTitle: ثلاثة تنبيهات عند تعيين الطوابع الزمنيّة
accDescr: يبيّن ثلاثة تنبيهات: التعيين لا ينفع إلا من الاتّصالات الجديدة لأنّه يُفاوض في 3-way handshake، ولا ينعقد إن لم يدعم الطرفان، وتكبر الترويسة فتقلّ قليلاً البيانات في المقطع الواحد.
care["ثلاثة تنبيهات عند التعيين"] --> n1["النفع من الاتّصالات الجديدة فقط"]
care --> n2["يلزم دعم الطرفين"]
care --> n3["زيادة الترويسة تقلّل البيانات قليلاً"]
n1 -.-> re["إعادة إنشاء اتّصال جانب الجهاز"]
الشكل 12: التعيين وحده لا يكفي. يلزم إعادة إنشاء الاتّصال والتحقّق من دعم الطرف الآخر.
6.2. التحقّق من TSopt في SYN / SYN-ACK
بعد التفعيل تُحقّق ثلاث نقاط.
- هل يوجد TSopt في SYN للاتّصال المشكل
- هل جانب SYN/ACK أيضاً أعاد TSopt
- هل يستمرّ ركوب TSopt على مقاطع البيانات وACK اللاحقة
بعد تأكيد هذا فقط يمكن القول «الطوابع الزمنيّة تُستخدَم فعلاً في ذلك الاتّصال».
6.3. أين ننظر إذا لم ينفع ذلك
حتّى مع تفعيل الطوابع الزمنيّة قد يضعف التحسين في حالات كهذه.
- معدّل الفقد نفسه مرتفع
- الأجهزة الوسيطة تكسر خيار TCP أو تسقطه أو تحرّفه
- مشكلة أخرى حول NIC / التعريف / offload
- التطبيق يعلّق الكلّ على استدعاء متزامن واحد، فانتظار واحد يبدو توقّفاً كلّيّاً
- السبب الرئيسيّ في الواقع ليس TCP بل توقّف معالجة جانب الكاميرا أو امتلاء طابور داخل الجهاز
لذلك يتّضح التقدّم بهذا الترتيب.
- أوّلاً تأكيد انتظار إعادة الإرسال من السلك
- النظر في وجود مفاوضة TSopt
- تفعيل الطوابع الزمنيّة والنظر في فرق التحسين
- إن بقي شيء، تضييق مصدر الفقد وتصميم التطبيق كلٍّ على حدة
flowchart TB
accTitle: ترتيب تقدّم الإجراءات
accDescr: يبيّن ترتيب الإجراءات: أوّلاً تأكيد انتظار إعادة الإرسال من السلك، ثمّ النظر في وجود مفاوضة TSopt، ثمّ تفعيل الطوابع الزمنيّة والنظر في الفرق، وإن بقي شيء فتضييق مصدر الفقد والتصميم كلٍّ على حدة.
s1["تأكيد انتظار إعادة الإرسال من السلك"] --> s2["النظر في وجود مفاوضة TSopt"]
s2 --> s3["تفعيل الطوابع الزمنيّة والنظر في الفرق"]
s3 --> s4["إن بقي شيء فتضييق مصدر الفقد والتصميم كلٍّ على حدة"]
الشكل 13: التقدّم بترتيب التأكيد ثمّ المفاوضة ثمّ التفعيل ثمّ التحقيق الباقي يسهّل تضييق سبب عدم النفع.
7. نقاط النظر في Wireshark
نذكر مرشّحات عرض سهلة للتضييق.
tcp.stream eq <対象ストリーム>
tcp.analysis.retransmission
tcp.analysis.fast_retransmission
tcp.analysis.lost_segment
tcp.options.timestamp.tsval
tcp.options.timestamp.tsecr
في طريقة النظر بعض الحيل.
- تضييق الاتّصال المستهدف بـ
tcp.stream - إظهار
Time delta from previous displayed packetورؤية ثواني التوقّف كما هي - التحقّق من ظهور
Retransmissionفي لحظة المشكلة - التحقّق من مفاوضة TSopt في SYN / SYN-ACK عند بدء الاتّصال
- النظر هل عاد
TSecrفي ACK
نكتب أيضاً كيف تبدو الشاشة بالنصّ. هذه الحالة تُعرَف من نظرة واحدة بعد الاعتياد.
| موضع النظر | كيف يبدو |
|---|---|
| عمود Info في قائمة الحزم | حزمة إعادة الإرسال تحمل [TCP Retransmission] |
| لون الصفّ | ينطبق عليها قاعدة تلوين Wireshark الافتراضيّة «Bad TCP»، فيصير ذلك الصفّ وحده بخلفية سوداء ونصّ أحمر. يُلتقَط حتّى بالمرور السريع |
| لوحة التفاصيل | باختيار الصفّ وبسط Transmission Control Protocol ثمّ فتح SEQ/ACK analysis داخله يظهر أنّه حُكم عليه بإعادة إرسال |
| فرق الزمن | بإخراج Time delta from previous displayed packet كعمود يُقرأ كم ثانية فصل هذا الصفّ عن الحزمة المعروضة السابقة. هنا تصطفّ ثانية ثمّ ثانيتان |
| Options في SYN | باختيار صفّ SYN وبسط Options يُعرَف وجود TSopt من وجود بند Timestamps |
الترتيب النموذجيّ هكذا. أوّلاً يظهر صفّ لنفس Seq بعد ثانية، ثمّ مرّة أخرى بعد ثانيتين من ذلك، ويعود ACK فور الصفّ الأخير، ومن هناك تُستأنف التبادلات العاديّة. إذا طابقت «الثواني الفارغة» هذه زمن توقّف الاستجابة في سجلّ التطبيق، فالجاني شبه مؤكَّد.
عند مطابقة السجلّ والحزم يلزم الانتباه أيضاً لفرق الأساس بين وقت التطبيق ووقت التقاط الحزم. إذا انزاح هذا يسهل اتّهام أمر آخر.
flowchart TB
accTitle: تدفّق تثبيت الجاني في Wireshark
accDescr: يبيّن التدفّق: تضييق الاتّصال المستهدف بـ tcp.stream، ورؤية ثواني التوقّف مباشرة من عمود فرق الزمن، وإذا طابقت تلك الثواني الفارغة زمن توقّف الاستجابة في سجلّ التطبيق فالجاني شبه مؤكَّد.
filt["تضييق الاتّصال المستهدف بـ tcp.stream"] --> delta["رؤية ثواني الفراغ من عمود فرق الزمن"]
delta --> re["تأكيد اصطفاف إعادة إرسال لنفس Seq"]
re --> match{"هل يطابق زمن توقّف التطبيق؟"}
match -->|"نعم"| fix["الجاني شبه مؤكَّد"]
match -->|"لا"| other["اشتباه فرق أساس الوقت أو عامل آخر"]
الشكل 14: التضييق، ورؤية فرق الزمن، والمطابقة. بهذه الخطوات الثلاث تُثبَّت هويّة «الثواني الفارغة».
8. دليل اختيار تقريبيّ
| العَرَض | ما يُشتبَه به أوّلاً | أوّل ما يُفعَل |
|---|---|---|
| توقّف أحياناً بوحدة الثواني | انتظار RTO في TCP | تأكيد إعادة الإرسال وفرق الزمن من الحزم |
| توقّف في توقيت شبه ثابت كلّ مرّة | انتظار داخل التطبيق، معالجة الجهاز، مهلة ثابتة | النظر إلى الخيوط واستدعاء SDK وسجلّ الجهاز |
| تفاقم عند الحمل العالي فقط | المعالج، GC، امتلاء الطابور | النظر إلى المعالج والمقاطعات والذاكرة وطول الطابور |
| سوء متزامن في اتّصالات واسعة | الطبقة الفيزيائيّة، المبدّل، الأجهزة الوسيطة | النظر إلى NIC والكابل وإحصاءات المنفذ وسجلّ الأجهزة الوسيطة |
| لا تغيّر رغم تغيير الإعداد | خيار TCP لم يُفاوض | إعادة التحقّق من SYN / SYN-ACK |
الصفّ الأخير شائع حقّاً. رضا تعديل الإعداد وواقعة الاستخدام على السلك شيئان مختلفان.
9. الخلاصة
نقاط هذه الحالة:
- «التوقّف أحياناً لعدّة ثوانٍ» قد يكون انتظار إعادة إرسال TCP لا توقّف التطبيق
- إذا طابق زمن التوقّف طريقة انتظار RTO وظهر
Retransmissionفالمسار جيّد جدّاً - TCP timestamps option آليّة لـ RTTM وPAWS، وتزيل غموض قياس RTT عند إعادة الإرسال
- في هذه الحالة، بتمكين طوابع عائلة RFC1323 أمكن كبح الزمن الذي يبقى فيه RTO محافظاً بإفراط
مسار يُراد تجنّبه:
- تحديد جاني توقّف الاتّصال من سجلّ التطبيق وحده
- النظر إلى إعداد نظام التشغيل فقط دون الحزم الفعليّة
- الاعتقاد أنّ تفعيل الطوابع الزمنيّة يلغي أيضاً سبب الفقد
مسار ينفع في العمل:
- النظر أوّلاً إلى السلك
- تأكيد شكل إعادة الإرسال وزمن الانتظار
- تأكيد مفاوضة TSopt
- بعد التحسين أيضاً، تضييق مصدر الفقد وتصميم التطبيق على حدة
أي أنّ هذا النوع من العطل يبدأ بـ «تحديد أين يُنتظَر» قبل «التسريع». عدم إخطاء ذلك وحدَه يقصّر التحقيق كثيراً.
10. روابط مرجعيّة
- RFC 1323 - TCP Extensions for High Performance
- RFC 7323 - TCP Extensions for High Performance
- RFC 5681 - TCP Congestion Control
- RFC 6298 - Computing TCP’s Retransmission Timer
- Description of Windows TCP features - Windows Server, Microsoft Learn
- Netsh commands for Interface Transmission Control Protocol - Microsoft Learn
- Set-NetTCPSetting - Microsoft Learn
- Get-NetTCPSetting - Microsoft Learn
- Wireshark User’s Guide - Time Display Formats And Time References
- Wireshark User’s Guide - Packet Colorization
مقالات ذات صلة
أحدث المقالات التي تشترك في نفس الوسوم. عمّق فهمك بمواضيع مرتبطة.
بنية اختبار مسارات الفشل في Windows بـ Application Verifier
نرتّب ما هو Application Verifier مع بناء بنية اختبار مسارات الفشل في Windows باستخدام Handles وHeaps وLow Resource Simulation و!htrace.
تحقيق تعطّل الكاميرا الصناعيّة بعد تشغيل طويل: فصل handle leak
نرتّب طريقة النظر إلى تعطّل تطبيق Windows فجأة بعد تشغيل طويل، من زوايا إيجاد handle leak وتصميم السجلّات، بحالة تطبيق تحكّم بكاميرا صناع...
Time Travel Debugging ── تسجيل الأخطاء التي لا تتكرّر في التطبيقات طويلة التشغيل وإرجاعها
خطأ يظهر مرّة في الشهر لا يترك في تفريغ الانهيار سوى نتيجته. سجّل التنفيذ وأرجعه بـ WinDbg Time Travel Debugging (TTD): TTD.exe والمخزن ا...
مطبّات محرّك الشبكة ومسار UNC ── التعامل العملي مع خادم الملفّات (المجلّد المشترك) في تطبيقات الأعمال
نرتّب الأعطال الشائعة عند الكتابة إلى مجلّد مشترك أو مراقبته من تطبيق أعمال. نشرح سبب عدم ظهور حرف القرص (Z:) من الخدمة، والصلاحيّات المط...
لا تُحِط HttpClient بـ using ── الممارسة العملية لاتصال HTTP في تطبيقات C# للأعمال (أنماط الإنشاء والمهلة وإعادة المحاولة)
إنشاء HttpClient داخل using في كل مرة يستنزف المقابس، وجعله static يمنعه من متابعة تغيّر DNS. نرتّب نمط الإنشاء الصحيح عبر PooledConnecti...
دراسة حالة ذات صلة
صفحة دراسة حالة توضّح بنية مشابهة للتشخيص أو تحديد الأولويات أو إعادة التصميم.
دراسة حالة: عزل توقّفات تواصل بطول ثوانٍ
دراسة حالة لفصل توقّف تواصل نادر إلى سلوك انتظار إعادة الإرسال وظروف جانب نظام التشغيل.
أين يتصل هذا الموضوع
ترتبط هذه المقالة بشكل طبيعي بصفحات الخدمات التالية.
التحقيق في الأخطاء وتحليل السبب الجذري
الموضوع يدور حول تشخيص توقّف الاتّصال الذي يصعب إعادة إنتاجه اعتماداً على الحزم والأدلّة، لذا فهو يتّصل مباشرةً بالتحقيق في الأعطال وتحليل الأسباب.
تطوير تطبيقات ويندوز
ويمتدّ ذلك إلى استشارة لمراجعة تصميم الاتّصال والمراقبة من جانب التنفيذ، بوصفه تطبيق Windows يتضمّن تكاملاً مع الأجهزة.
الأسئلة الشائعة
أسئلة شائعة حول موضوع هذه المقالة.
- ما هو TCP Retransmission (إعادة إرسال TCP)؟
- آليّة يعيد بها TCP إرسال البيانات نفسها عندما لا يعود ACK (تأكيد الاستلام) للحزمة المرسلة. إذا سقطت الحزمة في مكان ما في الطريق، ينتظر الجانب المرسل ACK، وإن لم يأتِ يعيد الإرسال بعد انتهاء مؤقّت إعادة الإرسال (RTO). من جهة التطبيق يبدو الأمر «توقّفاً لعدّة ثوانٍ»، أمّا من جهة TCP فهو فقط «لم يأتِ ACK بعد فانتظرنا انتهاء مؤقّت إعادة الإرسال». هذا الشكل من التوقّف شائع. في التقاط الحزم يُلاحَظ كـ TCP Retransmission.
- ما أسباب حدوث TCP Retransmission؟
- الزناد المباشر فقد الحزم: لا يعود ACK فيحدث إعادة الإرسال. مصادر الفقد يلزم النظر إليها فرداً: الطبقة الفيزيائيّة (الكابل أو المنفذ)، وNIC وتعريفه وإعدادات offload، ومشكلات المبدّل أو الأجهزة الوسيطة. تفعيل TCP timestamps وما شابه قد يضيّق زمن الانتظار بعد إعادة الإرسال، لكنّه ليس سحراً يلغي الفقد نفسه، لذا يبقى التحقيق في مصدر الفقد منفصلاً. قد تكسر الأجهزة الوسيطة خيارات TCP أو تسقطها، وقد يكون التوقّف الحقيقيّ معالجة الجهاز لا TCP.
- لماذا يتوقّف الاتّصال لعدّة ثوانٍ بسبب إعادة إرسال TCP؟
- لأنّ مؤقّت إعادة الإرسال (RTO) في TCP ينتظر انتظاراً محافظاً. في RFC 6298 القيمة الابتدائيّة لـ RTO معيارها ثانية واحدة، وإذا كانت نتيجة الحساب أصغر تُرفَع إلى ثانية، وتُضاعَف عند كلّ انتهاء مهلة. لذلك في ظروف سيّئة يظهر الانتظار كثانية ثمّ ثانيتين ثمّ أربع. في اتّصال تحكّم يغلب عليه request/response صغير، يظهر انتظار RTO قبل أن تتجمّع duplicate ACK بما يكفي لركوب fast retransmit، فيتبدّى توقّفاً نادراً لعدّة ثوانٍ. تفعيل TCP timestamps option قد يزيل غموض قياس RTT عند إعادة الإرسال فيقلّل الزمن الذي يبقى فيه تقدير RTO محافظاً بإفراط.
- كيف نبحث TCP Retransmission في Wireshark؟
- يمكن استخدام مرشّحات عرض مثل tcp.analysis.retransmission وtcp.analysis.fast_retransmission وtcp.analysis.lost_segment. يُضيَّق الاتّصال المستهدف بـ tcp.stream، ويُعرَض Time delta from previous displayed packet لرؤية الثواني المتوقّفة مباشرة، ويُنظَر هل ظهر Retransmission في لحظة المشكلة، وهل فرق الزمن حتّى إعادة الإرسال يطابق زمن التوقّف. استخدام TCP timestamps يُؤكَّد بمفاوضة TSopt في SYN / SYN-ACK عند بدء الاتّصال. واقعة ركوب TSopt على الحزمة الفعليّة أهمّ من أنّ الإعداد مفعَّل في الشاشة.
الملف الشخصي للمؤلف
صفحة الملف الشخصي لمؤلف المقالة.
غو كومورا
مؤسّس شركة كومورا سوفت ذ.م.م.
يركّز على تطوير برامج ويندوز، والاستشارات التقنية، والتحقيق في الأخطاء، ويتميّز في المشاريع التي تبقى فيها الأصول القديمة ناشطة، وفي تشخيص الأعطال التي يصعب تحديد سببها.