کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

سب کو سلام! میرا نام دمتری سامسونوف ہے، میں Odnoklassniki میں ایک سرکردہ سسٹم ایڈمنسٹریٹر کے طور پر کام کرتا ہوں۔ ہمارے پاس 7 ہزار سے زیادہ فزیکل سرورز، ہمارے کلاؤڈ میں 11 ہزار کنٹینرز اور 200 ایپلی کیشنز ہیں، جو مختلف کنفیگریشنز میں 700 مختلف کلسٹرز بناتی ہیں۔ سرورز کی اکثریت CentOS 7 چلاتی ہے۔
14 اگست 2018 کو، FragmentSmack کے خطرے کے بارے میں معلومات شائع کی گئی
(CVE-2018-5391) اور SegmentSmack (CVE-2018-5390)۔ یہ نیٹ ورک اٹیک ویکٹر اور کافی زیادہ اسکور (7.5) کے ساتھ کمزوریاں ہیں، جو وسائل کی تھکن (سی پی یو) کی وجہ سے سروس سے انکار (DoS) کا خطرہ ہے۔ اس وقت FragmentSmack کے لیے کرنل فکس تجویز نہیں کیا گیا تھا؛ مزید یہ کہ یہ خطرے کے بارے میں معلومات کی اشاعت سے بہت بعد میں سامنے آیا۔ SegmentSmack کو ختم کرنے کے لیے، کرنل کو اپ ڈیٹ کرنے کا مشورہ دیا گیا۔ اپ ڈیٹ پیکج خود اسی دن جاری کیا گیا تھا، جو باقی رہ گیا تھا اسے انسٹال کرنا تھا۔
نہیں، ہم دانا کو اپ ڈیٹ کرنے کے بالکل خلاف نہیں ہیں! تاہم، باریکیاں ہیں ...

ہم پیداوار پر دانا کو کیسے اپ ڈیٹ کرتے ہیں۔

عام طور پر، کچھ بھی پیچیدہ نہیں ہے:

  1. پیکجز ڈاؤن لوڈ کریں؛
  2. انہیں متعدد سرورز پر انسٹال کریں (بشمول ہمارے کلاؤڈ کی میزبانی کرنے والے سرورز)؛
  3. یقینی بنائیں کہ کچھ بھی نہیں ٹوٹا ہے۔
  4. اس بات کو یقینی بنائیں کہ تمام معیاری دانا کی ترتیبات غلطیوں کے بغیر لاگو ہوں؛
  5. کچھ دن انتظار کرو؛
  6. سرور کی کارکردگی چیک کریں؛
  7. نئے سرورز کی تعیناتی کو نئے کرنل میں تبدیل کریں۔
  8. ڈیٹا سینٹر کے ذریعے تمام سرورز کو اپ ڈیٹ کریں (ایک وقت میں ایک ڈیٹا سینٹر مسائل کی صورت میں صارفین پر اثر کو کم سے کم کرنے کے لیے)؛
  9. تمام سرورز کو ریبوٹ کریں۔

ہمارے پاس موجود دانا کی تمام شاخوں کے لیے دہرائیں۔ اس وقت یہ ہے:

  • اسٹاک CentOS 7 3.10 - زیادہ تر باقاعدہ سرورز کے لیے؛
  • ونیلا 4.19 - ہمارے لیے ایک بادل بادلکیونکہ ہمیں BFQ، BBR وغیرہ کی ضرورت ہے۔
  • Elrepo kernel-ml 5.2 - کے لیے انتہائی بھری ہوئی تقسیم کار، کیونکہ 4.19 غیر مستحکم برتاؤ کرتا تھا، لیکن اسی خصوصیات کی ضرورت ہے۔

جیسا کہ آپ نے اندازہ لگایا ہوگا، ہزاروں سرورز کو ریبوٹ کرنے میں سب سے زیادہ وقت لگتا ہے۔ چونکہ تمام کمزوریاں تمام سرورز کے لیے اہم نہیں ہیں، اس لیے ہم صرف وہی ریبوٹ کرتے ہیں جو انٹرنیٹ سے براہ راست قابل رسائی ہیں۔ کلاؤڈ میں، لچک کو محدود نہ کرنے کے لیے، ہم بیرونی طور پر قابل رسائی کنٹینرز کو انفرادی سرورز کے ساتھ نئے کرنل کے ساتھ نہیں باندھتے ہیں، لیکن بغیر کسی استثنا کے تمام میزبانوں کو دوبارہ شروع کرتے ہیں۔ خوش قسمتی سے، وہاں کا طریقہ کار باقاعدہ سرورز کے مقابلے میں آسان ہے۔ مثال کے طور پر، ریبوٹ کے دوران سٹیٹ لیس کنٹینرز آسانی سے دوسرے سرور پر جا سکتے ہیں۔

تاہم، ابھی بہت کام باقی ہے، اور اس میں کئی ہفتے لگ سکتے ہیں، اور اگر نئے ورژن میں کوئی مسئلہ ہے تو، کئی مہینوں تک۔ حملہ آور اس بات کو اچھی طرح سمجھتے ہیں، اس لیے انہیں ایک پلان بی کی ضرورت ہے۔

FragmentSmack/SegmentSmack۔ کام کاج

خوش قسمتی سے، کچھ کمزوریوں کے لیے اس طرح کا منصوبہ B موجود ہے، اور اسے Workaround کہا جاتا ہے۔ اکثر، یہ کرنل/ایپلی کیشن سیٹنگز میں تبدیلی ہے جو ممکنہ اثر کو کم کر سکتی ہے یا کمزوریوں کے استحصال کو مکمل طور پر ختم کر سکتی ہے۔

FragmentSmack/SegmentSmack کی صورت میں تجویز کیا گیا تھا یہ حل:

«آپ net.ipv4.ipfrag_high_thresh اور net.ipv3.ipfrag_low_thresh (اور ipv4 net.ipv4.ipfrag_high_thresh اور net.ipv6.ipfrag_low_thresh اور net.ipv6.ipfrag_low_thresh کے لیے ان کے ہم منصب) میں 6MB اور 256MB کی ڈیفالٹ اقدار کو بالترتیب kB192 اور kB262144 میں تبدیل کر سکتے ہیں۔ کم ٹیسٹ ہارڈ ویئر، سیٹنگز اور حالات کے لحاظ سے حملے کے دوران CPU کے استعمال میں معمولی سے نمایاں کمی دکھاتے ہیں۔ تاہم، ipfrag_high_thresh=64 بائٹس کی وجہ سے کارکردگی کا کچھ اثر ہو سکتا ہے، کیونکہ ایک وقت میں صرف دو XNUMXK ٹکڑے ہی دوبارہ جمع ہونے والی قطار میں فٹ ہو سکتے ہیں۔ مثال کے طور پر، یہ خطرہ ہے کہ بڑے UDP پیکٹ کے ساتھ کام کرنے والی ایپلیکیشنز ٹوٹ جائیں گی۔'.

پیرامیٹرز خود کرنل دستاویزات میں مندرجہ ذیل کے طور پر بیان کیا:

ipfrag_high_thresh - LONG INTEGER
    Maximum memory used to reassemble IP fragments.

ipfrag_low_thresh - LONG INTEGER
    Maximum memory used to reassemble IP fragments before the kernel
    begins to remove incomplete fragment queues to free up resources.
    The kernel still accepts new fragments for defragmentation.

ہمارے پاس پروڈکشن سروسز پر بڑے UDPs نہیں ہیں۔ LAN پر کوئی بکھری ٹریفک نہیں ہے؛ WAN پر بکھری ٹریفک ہے، لیکن اہم نہیں ہے۔ کوئی نشانیاں نہیں ہیں - آپ کام کا آغاز کر سکتے ہیں!

FragmentSmack/SegmentSmack۔ پہلا خون

پہلا مسئلہ جس کا ہمیں سامنا کرنا پڑا وہ یہ تھا کہ کلاؤڈ کنٹینرز بعض اوقات نئی ترتیبات کو صرف جزوی طور پر لاگو کرتے ہیں (صرف ipfrag_low_thresh)، اور بعض اوقات انہیں بالکل بھی لاگو نہیں کرتے تھے - وہ شروع میں ہی کریش ہو جاتے ہیں۔ مسئلہ کو مستحکم طور پر دوبارہ پیش کرنا ممکن نہیں تھا (تمام ترتیبات کو بغیر کسی دشواری کے دستی طور پر لاگو کیا گیا تھا)۔ یہ سمجھنا کہ شروع میں کنٹینر کیوں کریش ہوتا ہے اتنا آسان نہیں ہے: کوئی خرابی نہیں ملی۔ ایک چیز یقینی تھی: ترتیبات کو واپس لانے سے کنٹینر کریش ہونے کا مسئلہ حل ہو جاتا ہے۔

میزبان پر Sysctl لاگو کرنا کافی کیوں نہیں ہے؟ کنٹینر اپنے مخصوص نیٹ ورک نیم اسپیس میں رہتا ہے، تو کم از کم نیٹ ورک Sysctl پیرامیٹرز کا حصہ کنٹینر میں میزبان سے مختلف ہو سکتا ہے.

کنٹینر میں Sysctl کی ترتیبات کا اطلاق کیسے ہوتا ہے؟ چونکہ ہمارے کنٹینرز غیر مراعات یافتہ ہیں، اس لیے آپ خود کنٹینر میں جا کر Sysctl کی کوئی ترتیب تبدیل نہیں کر سکیں گے - آپ کے پاس کافی حقوق نہیں ہیں۔ کنٹینرز چلانے کے لیے، اس وقت ہمارے بادل نے Docker (اب پوڈ مین)۔ نئے کنٹینر کے پیرامیٹرز ڈوکر کو API کے ذریعے بھیجے گئے، بشمول ضروری Sysctl ترتیبات۔
ورژن کے ذریعے تلاش کرتے وقت، یہ پتہ چلا کہ Docker API نے تمام غلطیاں واپس نہیں کیں (کم از کم ورژن 1.10 میں)۔ جب ہم نے "ڈوکر رن" کے ذریعے کنٹینر شروع کرنے کی کوشش کی، تو آخر کار ہم نے کم از کم کچھ دیکھا:

write /proc/sys/net/ipv4/ipfrag_high_thresh: invalid argument docker: Error response from daemon: Cannot start container <...>: [9] System error: could not synchronise with container process.

پیرامیٹر کی قدر درست نہیں ہے۔ لیکن کیوں؟ اور یہ صرف بعض اوقات کیوں جائز نہیں ہوتا؟ معلوم ہوا کہ Docker اس ترتیب کی ضمانت نہیں دیتا جس میں Sysctl پیرامیٹرز لاگو ہوتے ہیں (جدید ترین ٹیسٹ شدہ ورژن 1.13.1 ہے)، اس لیے بعض اوقات ipfrag_high_thresh نے 256K پر سیٹ کرنے کی کوشش کی جب ipfrag_low_thresh ابھی بھی 3M تھی، یعنی اوپری حد کم تھی۔ کم حد سے زیادہ، جس کی وجہ سے خرابی ہوئی۔

اس وقت، ہم نے شروع کے بعد کنٹینر کو دوبارہ ترتیب دینے کے لیے پہلے سے ہی اپنا طریقہ کار استعمال کیا تھا (کنٹینر کو منجمد کرنے کے بعد گروپ فریزر اور کنٹینر کے نام کی جگہ کے ذریعے کمانڈز پر عمل درآمد کرنا آئی پی نیٹ)، اور ہم نے اس حصے میں تحریری Sysctl پیرامیٹرز کو بھی شامل کیا۔ مسئلہ حل ہو گیا۔

FragmentSmack/SegmentSmack۔ پہلا خون 2

اس سے پہلے کہ ہمارے پاس کلاؤڈ میں ورک آراؤنڈ کے استعمال کو سمجھنے کا وقت ہوتا، صارفین کی جانب سے پہلی نایاب شکایات آنا شروع ہوگئیں۔ اس وقت، پہلے سرورز پر ورک اراؤنڈ کا استعمال شروع ہوئے کئی ہفتے گزر چکے تھے۔ ابتدائی تحقیقات سے پتہ چلتا ہے کہ انفرادی خدمات کے خلاف شکایات موصول ہوئی تھیں، نہ کہ ان سروسز کے تمام سرورز کے خلاف۔ مسئلہ پھر سے انتہائی غیر یقینی ہو گیا ہے۔

سب سے پہلے، ہم نے، یقیناً، Sysctl کی ترتیبات کو واپس لانے کی کوشش کی، لیکن اس کا کوئی اثر نہیں ہوا۔ سرور اور ایپلیکیشن کی ترتیبات کے ساتھ مختلف ہیرا پھیری سے بھی کوئی فائدہ نہیں ہوا۔ ریبوٹ نے مدد کی۔ لینکس کو ریبوٹ کرنا اتنا ہی غیر فطری ہے جتنا کہ پرانے دنوں میں ونڈوز کے لیے معمول تھا۔ تاہم، اس سے مدد ملی، اور ہم نے Sysctl میں نئی ​​ترتیبات کو لاگو کرتے وقت اسے "کرنل کی خرابی" تک پہنچا دیا۔ کتنا فضول تھا...

تین ہفتے بعد مسئلہ دوبارہ شروع ہوا۔ ان سرورز کی ترتیب کافی آسان تھی: Nginx in proxy/balancer mode. زیادہ ٹریفک نہیں ہے۔ نیا تعارفی نوٹ: کلائنٹس پر 504 غلطیوں کی تعداد ہر روز بڑھ رہی ہے (گیٹ وے ٹائم آؤٹ)۔ گراف اس سروس کے لیے روزانہ 504 غلطیوں کی تعداد دکھاتا ہے:

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

تمام خرابیاں ایک ہی پسدید کے بارے میں ہیں - اس کے بارے میں جو کلاؤڈ میں ہے۔ اس پسدید پر پیکج کے ٹکڑوں کے لیے میموری کی کھپت کا گراف اس طرح نظر آیا:

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

یہ آپریٹنگ سسٹم گرافس میں مسئلہ کی سب سے واضح مظاہر میں سے ایک ہے۔ کلاؤڈ میں، بالکل اسی وقت، QoS (ٹریفک کنٹرول) کی ترتیبات کے ساتھ ایک اور نیٹ ورک کا مسئلہ طے ہو گیا تھا۔ پیکٹ کے ٹکڑوں کے لیے میموری کی کھپت کے گراف پر، یہ بالکل ویسا ہی نظر آتا تھا:

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

مفروضہ سادہ تھا: اگر وہ گراف پر ایک جیسے نظر آتے ہیں، تو ان کی وجہ بھی وہی ہے۔ مزید یہ کہ اس قسم کی میموری کے ساتھ کوئی بھی مسئلہ انتہائی نایاب ہے۔

طے شدہ مسئلہ کا خلاصہ یہ تھا کہ ہم نے QoS میں پہلے سے طے شدہ ترتیبات کے ساتھ fq پیکٹ شیڈیولر استعمال کیا۔ پہلے سے طے شدہ طور پر، ایک کنکشن کے لیے، یہ آپ کو قطار میں 100 پیکٹوں کو شامل کرنے کی اجازت دیتا ہے، اور کچھ کنکشنز، چینل کی کمی کے حالات میں، قطار کو گنجائش تک روکنا شروع کر دیتے ہیں۔ اس صورت میں، پیکٹ گرا دیا جاتا ہے. tc کے اعدادوشمار (tc -s qdisc) میں اسے اس طرح دیکھا جا سکتا ہے:

qdisc fq 2c6c: parent 1:2c6c limit 10000p flow_limit 100p buckets 1024 orphan_mask 1023 quantum 3028 initial_quantum 15140 refill_delay 40.0ms
 Sent 454701676345 bytes 491683359 pkt (dropped 464545, overlimits 0 requeues 0)
 backlog 0b 0p requeues 0
  1024 flows (1021 inactive, 0 throttled)
  0 gc, 0 highprio, 0 throttled, 464545 flows_plimit

"464545 flows_plimit" ایک کنکشن کی قطار کی حد سے تجاوز کرنے کی وجہ سے گرائے گئے پیکٹ ہیں، اور "ڈراپ 464545" اس شیڈیولر کے گرائے گئے تمام پیکٹوں کا مجموعہ ہے۔ قطار کی لمبائی 1 ہزار تک بڑھانے اور کنٹینرز کو دوبارہ شروع کرنے کے بعد مسئلہ آنا بند ہوگیا۔ آپ پیچھے بیٹھ کر اسموتھی پی سکتے ہیں۔

FragmentSmack/SegmentSmack۔ آخری خون

سب سے پہلے، دانا میں کمزوریوں کے اعلان کے کئی مہینوں بعد، آخرکار FragmentSmack کے لیے ایک فکس سامنے آیا (میں آپ کو یاد دلاتا ہوں کہ اگست میں اعلان کے ساتھ، صرف SegmentSmack کے لیے ایک فکس جاری کیا گیا تھا)، جس نے ہمیں ورک آراؤنڈ کو ترک کرنے کا موقع فراہم کیا، جس کی وجہ سے ہمیں کافی پریشانی ہوئی۔ اس وقت کے دوران، ہم پہلے ہی کچھ سرورز کو نئے کرنل میں منتقل کرنے میں کامیاب ہو چکے تھے، اور اب ہمیں شروع سے شروع کرنا تھا۔ ہم نے فریگمنٹ سمیک فکس کا انتظار کیے بغیر دانا کو کیوں اپ ڈیٹ کیا؟ حقیقت یہ ہے کہ ان کمزوریوں سے تحفظ کا عمل خود CentOS کو اپ ڈیٹ کرنے کے عمل کے ساتھ (جس میں صرف دانا کو اپ ڈیٹ کرنے سے بھی زیادہ وقت لگتا ہے) کے ساتھ موافق (اور ضم) ہوا۔ اس کے علاوہ، SegmentSmack ایک زیادہ خطرناک کمزوری ہے، اور اس کا حل فوری طور پر ظاہر ہوا، اس لیے اس کا بہرحال احساس ہوا۔ تاہم، ہم CentOS پر دانا کو آسانی سے اپ ڈیٹ نہیں کر سکے کیونکہ FragmentSmack کمزوری، جو CentOS 7.5 کے دوران نمودار ہوئی تھی، صرف ورژن 7.6 میں طے کی گئی تھی، لہذا ہمیں 7.5 پر اپ ڈیٹ کو روکنا پڑا اور 7.6 پر اپ ڈیٹ کے ساتھ دوبارہ شروع کرنا پڑا۔ اور ایسا بھی ہوتا ہے۔

دوم، مسائل کے بارے میں صارفین کی نایاب شکایات ہمارے پاس واپس آگئی ہیں۔ اب ہم پہلے سے ہی یقینی طور پر جان چکے ہیں کہ ان سب کا تعلق کلائنٹس سے ہمارے کچھ سرورز پر فائلوں کو اپ لوڈ کرنے سے ہے۔ مزید برآں، ان سرورز کے ذریعے کل بڑے پیمانے پر اپ لوڈز کی ایک بہت ہی کم تعداد ہوئی۔

جیسا کہ ہمیں اوپر کی کہانی سے یاد ہے، Sysctl کو رول بیک کرنے سے کوئی فائدہ نہیں ہوا۔ ریبوٹ نے مدد کی، لیکن عارضی طور پر۔
Sysctl کے حوالے سے شکوک و شبہات کو دور نہیں کیا گیا لیکن اس بار زیادہ سے زیادہ معلومات جمع کرنا ضروری تھا۔ کلائنٹ پر اپ لوڈ کے مسئلے کو دوبارہ پیش کرنے کی صلاحیت کا بھی بہت بڑا فقدان تھا تاکہ زیادہ واضح طور پر مطالعہ کیا جا سکے کہ کیا ہو رہا ہے۔

تمام دستیاب اعدادوشمار اور نوشتہ جات کا تجزیہ ہمیں یہ سمجھنے کے قریب نہیں لایا کہ کیا ہو رہا ہے۔ کسی مخصوص تعلق کو "محسوس" کرنے کے لیے مسئلہ کو دوبارہ پیش کرنے کی صلاحیت کی شدید کمی تھی۔ آخر میں، ڈویلپرز، ایپلی کیشن کے ایک خاص ورژن کا استعمال کرتے ہوئے، Wi-Fi کے ذریعے منسلک ہونے پر ٹیسٹ ڈیوائس پر مسائل کی مستحکم تولید کو حاصل کرنے میں کامیاب ہو گئے۔ یہ تفتیش میں ایک پیش رفت تھی۔ Nginx سے منسلک کلائنٹ، جس نے بیک اینڈ پر پراکسی کی، جو ہماری جاوا ایپلی کیشن تھی۔

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

مسائل کے لیے مکالمہ اس طرح تھا (Nginx پراکسی سائیڈ پر طے شدہ):

  1. کلائنٹ: فائل ڈاؤن لوڈ کرنے کے بارے میں معلومات حاصل کرنے کی درخواست۔
  2. جاوا سرور: جواب۔
  3. کلائنٹ: فائل کے ساتھ پوسٹ کریں۔
  4. جاوا سرور: غلطی۔

اسی وقت، جاوا سرور لاگ پر لکھتا ہے کہ کلائنٹ سے 0 بائٹس ڈیٹا موصول ہوا تھا، اور Nginx پراکسی لکھتا ہے کہ درخواست میں 30 سیکنڈ سے زیادہ کا وقت لگا (30 سیکنڈ کلائنٹ کی درخواست کا ٹائم آؤٹ ہے)۔ کیوں ٹائم آؤٹ اور کیوں 0 بائٹس؟ HTTP کے نقطہ نظر سے، سب کچھ کام کرتا ہے جیسا کہ اسے کرنا چاہئے، لیکن فائل کے ساتھ POST نیٹ ورک سے غائب ہوتا ہے. مزید یہ کہ یہ کلائنٹ اور Nginx کے درمیان غائب ہو جاتا ہے۔ یہ Tcpdump کے ساتھ اپنے آپ کو مسلح کرنے کا وقت ہے! لیکن پہلے آپ کو نیٹ ورک کنفیگریشن کو سمجھنے کی ضرورت ہے۔ Nginx پراکسی L3 بیلنس کے پیچھے ہے۔ این ایف ویئر. L3 بیلنسر سے سرور تک پیکٹ پہنچانے کے لیے ٹنلنگ کا استعمال کیا جاتا ہے، جو اس کے ہیڈرز کو پیکٹوں میں شامل کرتا ہے:

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

اس صورت میں، نیٹ ورک اس سرور پر Vlan-tagged ٹریفک کی شکل میں آتا ہے، جو پیکٹوں میں اپنی فیلڈز بھی شامل کرتا ہے:

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

اور اس ٹریفک کو بھی تقسیم کیا جا سکتا ہے (آنے والی بکھری ٹریفک کا وہی چھوٹا فیصد جس کے بارے میں ہم نے ورک آراؤنڈ سے خطرات کا اندازہ لگاتے وقت بات کی تھی)، جو ہیڈرز کے مواد کو بھی تبدیل کر دیتا ہے:

کمزوریوں سے ہوشیار رہیں جو کام کے چکر لاتے ہیں۔ حصہ 1: FragmentSmack/SegmentSmack

ایک بار پھر: پیکٹوں کو ایک Vlan ٹیگ کے ساتھ لپیٹ دیا گیا ہے، ایک سرنگ کے ساتھ لپیٹ کر ٹکڑے ٹکڑے کر دیا گیا ہے۔ یہ کیسے ہوتا ہے اسے بہتر طور پر سمجھنے کے لیے، آئیے کلائنٹ سے Nginx پراکسی تک پیکٹ کے راستے کا پتہ لگائیں۔

  1. پیکٹ L3 بیلنسر تک پہنچتا ہے۔ ڈیٹا سینٹر کے اندر درست روٹنگ کے لیے، پیکٹ کو ایک سرنگ میں بند کر کے نیٹ ورک کارڈ پر بھیجا جاتا ہے۔
  2. چونکہ پیکٹ + ٹنل ہیڈرز MTU میں فٹ نہیں ہوتے ہیں، اس لیے پیکٹ کو ٹکڑوں میں کاٹ کر نیٹ ورک کو بھیج دیا جاتا ہے۔
  3. L3 بیلنسر کے بعد سوئچ، جب ایک پیکٹ وصول کرتا ہے، اس میں Vlan ٹیگ شامل کرتا ہے اور اسے بھیجتا ہے۔
  4. Nginx پراکسی کے سامنے والا سوئچ دیکھتا ہے (پورٹ کی ترتیبات کی بنیاد پر) کہ سرور Vlan-encapsulated پیکٹ کی توقع کر رہا ہے، لہذا یہ Vlan ٹیگ کو ہٹائے بغیر اسے ویسا ہی بھیجتا ہے۔
  5. لینکس انفرادی پیکجوں کے ٹکڑے لیتا ہے اور انہیں ایک بڑے پیکیج میں ضم کرتا ہے۔
  6. اس کے بعد، پیکٹ Vlan انٹرفیس تک پہنچتا ہے، جہاں اس سے پہلی پرت ہٹا دی جاتی ہے - Vlan encapsulation.
  7. لینکس پھر اسے ٹنل انٹرفیس پر بھیجتا ہے، جہاں اس سے ایک اور پرت ہٹا دی جاتی ہے - Tunnel encapsulation.

مشکل یہ ہے کہ اس سب کو پیرامیٹر کے طور پر tcpdump میں منتقل کیا جائے۔
آئیے آخر سے شروع کریں: کیا کلائنٹس کے صاف (غیر ضروری ہیڈر کے بغیر) IP پیکٹ ہیں، جن میں vlan اور tunnel encapsulation کو ہٹا دیا گیا ہے؟

tcpdump host <ip клиента>

نہیں، سرور پر ایسے کوئی پیکیج نہیں تھے۔ اس لیے مسئلہ پہلے سے موجود ہونا چاہیے۔ کیا صرف Vlan encapsulation کے ساتھ کوئی پیکٹ ہٹا دیا گیا ہے؟

tcpdump ip[32:4]=0xx390x2xx

0xx390x2xx ہیکس فارمیٹ میں کلائنٹ کا IP پتہ ہے۔
32:4 — اس فیلڈ کا پتہ اور لمبائی جس میں ٹنل پیکٹ میں SCR IP لکھا گیا ہے۔

فیلڈ ایڈریس کو بروٹ فورس کے ذریعہ منتخب کرنا پڑا، کیونکہ انٹرنیٹ پر وہ 40، 44، 50، 54 کے بارے میں لکھتے ہیں، لیکن وہاں کوئی IP ایڈریس نہیں تھا۔ آپ ہیکس میں سے کسی ایک پیکٹ کو بھی دیکھ سکتے ہیں (tcpdump میں -xx یا -XX پیرامیٹر) اور اس آئی پی ایڈریس کا حساب لگا سکتے ہیں جسے آپ جانتے ہیں۔

کیا Vlan اور Tunnel encapsulation کے بغیر پیکٹ کے ٹکڑے ہٹا دیئے گئے ہیں؟

tcpdump ((ip[6:2] > 0) and (not ip[6] = 64))

یہ جادو ہمیں آخری ایک سمیت تمام ٹکڑے دکھائے گا۔ شاید، ایک ہی چیز کو آئی پی کے ذریعے فلٹر کیا جا سکتا ہے، لیکن میں نے کوشش نہیں کی، کیونکہ ایسے بہت سے پیکٹ نہیں ہیں، اور جن کی مجھے ضرورت تھی وہ عام بہاؤ میں آسانی سے مل گئے تھے۔ وہ یہاں ہیں:

14:02:58.471063 In 00:de:ff:1a:94:11 ethertype IPv4 (0x0800), length 1516: (tos 0x0, ttl 63, id 53652, offset 0, flags [+], proto IPIP (4), length 1500)
    11.11.11.11 > 22.22.22.22: truncated-ip - 20 bytes missing! (tos 0x0, ttl 50, id 57750, offset 0, flags [DF], proto TCP (6), length 1500)
    33.33.33.33.33333 > 44.44.44.44.80: Flags [.], seq 0:1448, ack 1, win 343, options [nop,nop,TS val 11660691 ecr 2998165860], length 1448
        0x0000: 0000 0001 0006 00de fb1a 9441 0000 0800 ...........A....
        0x0010: 4500 05dc d194 2000 3f09 d5fb 0a66 387d E.......?....f8}
        0x0020: 1x67 7899 4500 06xx e198 4000 3206 6xx4 [email protected].
        0x0030: b291 x9xx x345 2541 83b9 0050 9740 0x04 .......A...P.@..
        0x0040: 6444 4939 8010 0257 8c3c 0000 0101 080x dDI9...W.......
        0x0050: 00b1 ed93 b2b4 6964 xxd8 ffe1 006a 4578 ......ad.....jEx
        0x0060: 6966 0000 4x4d 002a 0500 0008 0004 0100 if..MM.*........

14:02:58.471103 In 00:de:ff:1a:94:11 ethertype IPv4 (0x0800), length 62: (tos 0x0, ttl 63, id 53652, offset 1480, flags [none], proto IPIP (4), length 40)
    11.11.11.11 > 22.22.22.22: ip-proto-4
        0x0000: 0000 0001 0006 00de fb1a 9441 0000 0800 ...........A....
        0x0010: 4500 0028 d194 00b9 3f04 faf6 2x76 385x E..(....?....f8}
        0x0020: 1x76 6545 xxxx 1x11 2d2c 0c21 8016 8e43 .faE...D-,.!...C
        0x0030: x978 e91d x9b0 d608 0000 0000 0000 7c31 .x............|Q
        0x0040: 881d c4b6 0000 0000 0000 0000 0000 ..............

یہ تصویر کے ساتھ ایک پیکج (ایک ہی ID 53652) کے دو ٹکڑے ہیں (پہلے پیکج میں لفظ Exif نظر آتا ہے)۔ اس حقیقت کی وجہ سے کہ اس سطح پر پیکیجز موجود ہیں، لیکن ڈمپ میں ضم شدہ شکل میں نہیں، مسئلہ اسمبلی کے ساتھ واضح طور پر ہے۔ آخر کار اس کا دستاویزی ثبوت موجود ہے!

پیکٹ ڈیکوڈر نے ایسی کوئی پریشانی ظاہر نہیں کی جو تعمیر کو روکے۔ اسے یہاں آزمایا: hpd.gasmi.net. سب سے پہلے، جب آپ وہاں کچھ بھرنے کی کوشش کرتے ہیں، تو ڈیکوڈر کو پیکٹ کی شکل پسند نہیں آتی۔ یہ پتہ چلا کہ Srcmac اور Ethertype کے درمیان کچھ اضافی دو آکٹیٹس تھے (ٹکڑے کی معلومات سے متعلق نہیں)۔ ان کو ہٹانے کے بعد ڈیکوڈر نے کام کرنا شروع کر دیا۔ تاہم، اس نے کوئی مسئلہ نہیں دکھایا.
کوئی کچھ بھی کہے، سوائے ان Sysctl کے اور کچھ نہیں ملا۔ بس باقی رہ گیا پیمانہ کو سمجھنے اور مزید کارروائیوں کا فیصلہ کرنے کے لیے مسئلہ سرورز کی شناخت کا راستہ تلاش کرنا تھا۔ مطلوبہ کاؤنٹر کافی تیزی سے مل گیا:

netstat -s | grep "packet reassembles failed”

یہ snmpd میں OID=1.3.6.1.2.1.4.31.1.1.16.1 (ipSystemStatsReasmFails).

"IP دوبارہ اسمبلی الگورتھم کے ذریعہ پتہ چلنے والی ناکامیوں کی تعداد (کسی بھی وجہ سے: ٹائم آؤٹ، غلطیاں، وغیرہ)۔"

سرورز کے جن گروپوں پر اس مسئلے کا مطالعہ کیا گیا تھا، ان میں سے دو پر یہ کاؤنٹر تیزی سے بڑھتا ہے، دو پر آہستہ آہستہ، اور دو اور پر یہ بالکل نہیں بڑھتا تھا۔ اس کاؤنٹر کی حرکیات کا جاوا سرور پر ایچ ٹی ٹی پی کی غلطیوں کی حرکیات کے ساتھ موازنہ کرنے سے ایک ارتباط کا انکشاف ہوا۔ یعنی میٹر کی نگرانی کی جا سکتی تھی۔

مسائل کے قابل اعتماد اشارے کا ہونا بہت ضروری ہے تاکہ آپ درست طریقے سے اس بات کا تعین کر سکیں کہ آیا Sysctl کو واپس لانے سے مدد ملتی ہے، کیونکہ پچھلی کہانی سے ہم جانتے ہیں کہ ایپلیکیشن سے اسے فوری طور پر نہیں سمجھا جا سکتا۔ یہ اشارے ہمیں صارفین کو دریافت کرنے سے پہلے پیداوار میں تمام مسائل کی نشاندہی کرنے کی اجازت دے گا۔
Sysctl کو رول بیک کرنے کے بعد، نگرانی کی غلطیاں رک گئیں، اس طرح مسائل کی وجہ ثابت ہوئی، ساتھ ہی یہ حقیقت بھی کہ رول بیک مدد کرتا ہے۔

ہم نے دوسرے سرورز پر فریگمنٹیشن سیٹنگز کو واپس کر دیا، جہاں نئی ​​نگرانی عمل میں آئی، اور کہیں ہم نے ٹکڑوں کے لیے پہلے سے طے شدہ سے کہیں زیادہ میموری مختص کی (یہ UDP کے اعدادوشمار تھے، جس کا جزوی نقصان عام پس منظر کے خلاف قابل توجہ نہیں تھا) .

اہم ترین سوالات

ہمارے L3 بیلنس پر پیکٹ کیوں بکھرے ہوئے ہیں؟ زیادہ تر پیکٹ جو صارفین سے بیلنسرز تک پہنچتے ہیں وہ SYN اور ACK ہیں۔ ان پیکجوں کے سائز چھوٹے ہیں۔ لیکن چونکہ اس طرح کے پیکٹوں کا حصہ بہت بڑا ہے، اس لیے ان کے پس منظر میں ہم نے بڑے پیکٹوں کی موجودگی کو محسوس نہیں کیا جو بکھرنے لگے۔

وجہ ایک ٹوٹی ہوئی ترتیب اسکرپٹ تھی۔ advmss Vlan انٹرفیس والے سرورز پر (اس وقت پیداوار میں ٹیگ شدہ ٹریفک والے بہت کم سرورز تھے)۔ Advmss ہمیں کلائنٹ کو یہ معلومات پہنچانے کی اجازت دیتا ہے کہ ہماری سمت کے پیکٹ سائز میں چھوٹے ہونے چاہئیں تاکہ ان کے ساتھ سرنگ کے ہیڈر منسلک کرنے کے بعد انہیں ٹکڑے ٹکڑے نہ ہونا پڑے۔

کیوں Sysctl رول بیک نے مدد نہیں کی، لیکن دوبارہ شروع کیا؟ Sysctl کو رول بیک کرنے سے پیکجوں کو ضم کرنے کے لیے دستیاب میموری کی مقدار تبدیل ہو گئی۔ ایک ہی وقت میں، بظاہر ٹکڑوں کے لیے میموری اوور فلو کی حقیقت نے کنکشنز کو سست کردیا، جس کی وجہ سے ٹکڑوں کو قطار میں کافی دیر تک تاخیر ہوئی۔ یعنی یہ عمل چکروں میں چلا گیا۔
ریبوٹ نے میموری کو صاف کردیا اور سب کچھ ترتیب پر واپس آگیا۔

کیا کام کے بغیر کرنا ممکن تھا؟ ہاں، لیکن حملے کی صورت میں صارفین کو سروس کے بغیر چھوڑنے کا خطرہ بہت زیادہ ہے۔ بلاشبہ، ورک آراؤنڈ کے استعمال کے نتیجے میں مختلف مسائل پیدا ہوئے، بشمول صارفین کے لیے ایک سروس کا سست ہونا، لیکن اس کے باوجود ہم سمجھتے ہیں کہ اقدامات جائز تھے۔

آندرے تیموفیف کا بہت شکریہ (atimofeyev) تحقیقات کرنے میں مدد کے ساتھ ساتھ الیکسی کرینیف (ڈیوائس ایکس) - سرورز پر سینٹوس اور کرنل کو اپ ڈیٹ کرنے کے ٹائٹینک کام کے لیے۔ ایک ایسا عمل جو اس معاملے میں شروع سے کئی بار شروع کرنا پڑا، جس کی وجہ سے یہ کئی مہینوں تک گھسیٹتا رہا۔

ماخذ: www.habr.com

نیا تبصرہ شامل کریں