היום למדתי: הסיפור עם bcrypt ו 72 בתים
לא ברור איך העברתי חיים שלמים בלי לשים לב למגבלה הזאת, אבל עכשיו שגיליתי אותה אני משתף כאן כדי שאתם לא תיפלו באותו בור. לכוכב בסיפור של היום קוראים bcrypt והוא אלגוריתם Password Hashing ישן שעדיין נמצא בשימוש נרחב בהרבה מערכות. בין השאר ספריית Devise שהיא הספריה הפופולרית לניהול משתמשים ב Rails משתמשת בו.
בגדול bcrypt נחשב עדיין מאובטח למרות גילו המבוגר, אבל יש לו מגבלה מתועדת (ומסתבר שמאוד מפורסמת) - הוא לא יודע לערבל סיסמאות ארוכות יותר מ 72 בתים. מה זה אומר? הנה בקוד ריילס:
> u = User.new(name: 'a', email: 'ynon@gmail.com', password: '0' * 80 + '1')
> u.valid_password?('0' * 80 + '2')
=> true
כלומר בדיקת הסיסמאות היא רק על 72 הבתים הראשונים של הסיסמה. כשיש סיסמה ארוכה מ 72 בתים אנחנו מתעלמים מכל מה שבא אחרי.
לקחים? אם אפשר השתמשו ב Aragon2 במקום ב bcrypt, ובכל מקרה כשאתם בוחרים סיסמה לאתר שימו לב לא להתחיל את הסיסמה ב 72 תווים שקל לנחש ורק אז לשים את הסיסמה האמיתית. מי יודע אם הם לא משתמשים בטעות ב bcrypt וחותכים את מה שבא אחרי ה 72.
נ.ב. הפוסט הזה בנושא סופר מעניין וסוקר את המימוש של bcrypt בעוד שפות תכנות בדגש על איזה ספריות יסרבו לעבוד עם קלט שאורכו מעל 72 בתים לעומת איזה ספריות פשוט ימחקו את החלק שאחרי 72 כדי שבכל זאת דברים יעבדו: https://n0rdy.foo/posts/20250121/okta-bcrypt-lessons-for-better-apis/