חלקת ליבות איך לנהל נכון את כח העיבוד שלך
חלוקת ליבות - איך לנהל נכון את כוח העיבוד שלך
במבט ראשון, נראה שכל הליבות במעבד זהות, ושהמערכת “כבר יודעת לבד” איך להשתמש בהן. אבל כשמדובר ב-Inference Optimization, ההבדלים הקטנים האלה הם מה שמפריד בין מערכת איטית למערכת יעילה באמת.
מה זה בכלל “חלוקת ליבות”?
כשמודל רץ, הוא לא רץ “באוויר” - הוא רץ על threads (תהליכי משנה). מערכת ההפעלה מחליטה באילו ליבות להריץ כל thread, ולעיתים מעבירה אותם בין ליבות לפי העומס - תהליך שנקרא context switching.
זה נשמע חכם, אבל יש כאן מלכודת: בכל פעם ש-thread “נודד” מליבה אחת לאחרת, הוא מאבד את תוכן ה-cache שהיה שמור בליבה הקודמת.
למה זה קורה?
לכל ליבה יש cache משלה - זיכרון קטן ומהיר שבו נשמרים נתונים ותוצאות ביניים של החישוב האחרון. כל עוד ה-thread רץ על אותה ליבה, הוא נהנה מגישה מהירה לנתונים האלה - בלי לגשת לזיכרון הראשי, שפי כמה יותר איטי.
אבל כשמערכת ההפעלה מעבירה את ה-thread לליבה אחרת:
- אותה ליבה חדשה לא מכירה את הנתונים ששמר קודמתה.
- המעבד נאלץ לטעון מחדש את כל הנתונים מהזיכרון הראשי.
- ה-cache מתאפס, והמערכת “מתחילה מאפס” מבחינת מהירות.
כך נוצר מצב שבו המעבד מבזבז זמן על טעינה מחדש במקום על חישוב אמיתי - וזה מתבטא ישירות ב-latency גבוה יותר וב-throughput נמוך יותר.
איך מנהלים את זה נכון?
במקום לתת למערכת “להחליט לבד”, כדאי לקבוע בעצמנו:
- אילו תהליכים רצים על אילו ליבות.
- אילו threads לא מתחרים זה בזה על אותם משאבים.
זה נקרא Thread Affinity - הצמדת thread לליבה מסוימת. כך כל thread “נשאר בבית”, שומר על ה-cache שלו, והמעבד מנצל את הזמן לחישוב אמיתי ולא להעברות מיותרות.
איך זה משפיע על Inference?
במערכות inference, במיוחד כאלה שמשרתות בקשות רבות במקביל, ניהול נכון של ליבות יכול:
- להפחית latency משמעותית.
- להעלות throughput (כמות תחזיות לשנייה).
- לשמור על יציבות - שכל בקשה תקבל זמן עיבוד עקבי, בלי קפיצות או עיכובים פתאומיים.
בשורה התחתונה
ליבה היא לא רק “עוד כוח חישוב” - היא אזור עבודה עם זיכרון משלה. אם נשמור על רציפות בין thread לליבה שלו, נרוויח מהירות, יעילות ויציבות. ניהול ליבות נכון הוא לא אופטימיזציה שולית - הוא ההבדל בין מערכת שמדשדשת למערכת שמבצעת inference בזמן כמעט אפסי.
📚 פוסטים נוספים בסדרה: אופטימיזציה של חומרת הסקה
- חלק 1 למה בכלל צריך להבין חומרה כשעוסקים באופטימיזציות Inference?
- חלק 2 מה זה NUMA ולמה זה חשוב באופטימיזציות Inference?
- חלק 3 מה זה ליבות (Cores) ו-Threads?
- חלק 4 מה זה Cache ולמה הוא משנה הכל?
- חלק 6 Thread Affinity - How to Bind Cores Smartly
- חלק 7 Divided Resources - איך מחלקים משאבים בין מודלים או תהליכים
- חלק 8 Resource Optimization - איך כל הגורמים משפיעים בפועל על Latency ו-TPS
- חלק 9 סיכום הסדרה: מ-NUMA ועד Throughput - איך אופטימיזציה הופכת חומרה לביצועים