ตรวจสอบปัญหาความปลอดภัยของโค้ดทั่วไป
การทําความเข้าใจช่องโหว่ด้านความปลอดภัยทั่วไปเป็นสิ่งสําคัญในการระบุและแก้ไขปัญหาความปลอดภัยของโค้ดอย่างมีประสิทธิภาพ หน่วยนี้ครอบคลุมปัญหาด้านความปลอดภัยที่แพร่หลายในโค้ดผลกระทบและเหตุใดการแก้ไขทันทีจึงมีความสําคัญต่อความปลอดภัยของแอปพลิเคชัน
เหตุใดจึงต้องให้ความสําคัญกับประเด็นด้านความปลอดภัย
ช่องโหว่ด้านความปลอดภัยแสดงถึงข้อบกพร่องของซอฟต์แวร์ที่สําคัญที่สุดประเภทหนึ่ง ช่องโหว่เดียวอาจส่งผลให้:
- การละเมิดข้อมูล: การเปิดเผยข้อมูลลูกค้าหรือธุรกิจที่ละเอียดอ่อน
- ความสูญเสียทางการเงิน: ต้นทุนโดยตรงจากการละเมิด ค่าปรับตามกฎระเบียบ และค่าใช้จ่ายในการแก้ไข
- ความเสียหายต่อชื่อเสียง: การสูญเสียความไว้วางใจของลูกค้าและความน่าเชื่อถือทางธุรกิจ
- การหยุดชะงักในการดําเนินงาน: การประนีประนอมของระบบอาจทําให้การดําเนินธุรกิจหยุดชะงักได้
ข้อบกพร่องในการทํางานอาจสร้างความอับอายให้กับนักพัฒนา แต่ข้อบกพร่องด้านความปลอดภัยอาจส่งผลร้ายแรงต่อองค์กรและผู้ใช้ นักพัฒนาทุกคนต้องคํานึงถึงความปลอดภัยโดยไม่คํานึงถึงบทบาทหรือความเชี่ยวชาญเฉพาะทาง
เปิดโครงการความปลอดภัยของเว็บแอปพลิเคชัน (OWASP)
โครงการ Open Web Application Security (OWASP) เป็นองค์กรไม่แสวงหาผลกําไรที่มุ่งเน้นการปรับปรุงความปลอดภัยของซอฟต์แวร์ OWASP รักษา "OWASP Top 10" ที่ได้รับการยอมรับอย่างกว้างขวาง ซึ่งเป็นรายการความเสี่ยงด้านความปลอดภัยของเว็บแอปพลิเคชันที่สําคัญที่สุดที่อัปเดตเป็นประจําโดยอิงจากข้อมูลจากองค์กรรักษาความปลอดภัยทั่วโลก
OWASP Top 10 ทําหน้าที่เป็นพื้นฐานด้านความปลอดภัยสําหรับนักพัฒนาและองค์กร ซึ่งช่วยจัดลําดับความสําคัญของช่องโหว่ที่ต้องแก้ไขก่อน การจัดอันดับจะเปลี่ยนไปตามกาลเวลาเมื่อรูปแบบการโจมตีมีวิวัฒนาการ เช่น:
- 2017 OWASP Top 10: ข้อบกพร่องในการฉีดครองตําแหน่ง #1
- 2021 OWASP Top 10: การฉีดย้ายไปที่ #3 เนื่องจากภัยคุกคามใหม่ๆ เช่น การควบคุมการเข้าถึงที่เสียหายเกิดขึ้น
OWASP Top 10 สะท้อนให้เห็นถึงข้อมูลการโจมตีในโลกแห่งความเป็นจริง ไม่ใช่ข้อกังวลทางทฤษฎี ช่องโหว่ของโค้ด เช่น การแทรก SQL และการเข้ารหัสที่อ่อนแออยู่ในอันดับที่กังวลด้านความปลอดภัยที่สําคัญที่สุดของอุตสาหกรรมอย่างต่อเนื่อง
การโจมตีแบบฉีด
การโจมตีแบบแทรกเกิดขึ้นเมื่อข้อมูลที่ไม่น่าเชื่อถือถูกส่งไปยังล่ามโดยเป็นส่วนหนึ่งของคําสั่งหรือแบบสอบถาม ข้อมูลที่เป็นปรปักษ์ของผู้โจมตีหลอกลวงล่ามให้ดําเนินการคําสั่งโดยไม่ได้ตั้งใจหรือเข้าถึงข้อมูลที่ไม่ได้รับอนุญาต
การแทรก SQL
การแทรก SQL เป็นหนึ่งในการโจมตีแบบแทรกที่อันตรายและพบได้บ่อยที่สุด เกิดขึ้นเมื่อแอปพลิเคชันรวมอินพุตที่ไม่น่าเชื่อถือลงในแบบสอบถาม SQL โดยตรงโดยไม่มีการตรวจสอบความถูกต้องหรือการกําหนดพารามิเตอร์ที่เหมาะสม
พิจารณาตัวอย่างโค้ดต่อไปนี้:
// DANGEROUS: Concatenating user input directly into SQL
string query = "SELECT * FROM Users WHERE Username = '" + userInput + "' AND Password = '" + passwordInput + "'";
SqlCommand command = new SqlCommand(query, connection);
SqlDataReader reader = command.ExecuteReader();
ผู้โจมตีสามารถป้อน ' OR '1'='1 เป็นอินพุตชื่อผู้ใช้ โดยแปลงการสืบค้นเป็น:
SELECT * FROM Users WHERE Username = '' OR '1'='1' AND Password = ''
'1'='1'เนื่องจากเป็นจริงเสมอ คิวรีนี้ส่งคืนผู้ใช้ทั้งหมด โดยข้ามการรับรองความถูกต้องทั้งหมด
เอฟเฟกต์ในโลกแห่งความเป็นจริง
การโจมตีแบบแทรก SQL ทําให้เกิดการละเมิดที่มีชื่อเสียงมากมาย ฝ่ายโจมตีสามารถ:
- ข้ามกลไกการรับรองความถูกต้อง
- แยกฐานข้อมูลทั้งหมดที่มีข้อมูลที่ละเอียดอ่อน
- แก้ไขหรือลบข้อมูล
- ดําเนินการดูแลระบบบนฐานข้อมูล
การใช้งานที่ปลอดภัย
วิธีที่ปลอดภัยในการจัดการแบบสอบถาม SQL คือการใช้แบบสอบถามที่มีพารามิเตอร์ (เรียกอีกอย่างว่าคําสั่งที่เตรียมไว้)
เช่น:
// SECURE: Using parameterized queries
string query = "SELECT * FROM Users WHERE Username = @username AND Password = @password";
SqlCommand command = new SqlCommand(query, connection);
command.Parameters.AddWithValue("@username", userInput);
command.Parameters.AddWithValue("@password", passwordInput);
SqlDataReader reader = command.ExecuteReader();
คิวรีที่มีพารามิเตอร์จะแยกโค้ดออกจากข้อมูล ฐานข้อมูลถือว่าค่าพารามิเตอร์เป็นข้อมูลเท่านั้น ไม่ใช่โค้ด SQL ที่ปฏิบัติการได้ เพื่อป้องกันการโจมตีแบบแทรก
ประเภทการฉีดอื่น ๆ
การแทรก SQL เป็นเพียงรูปแบบหนึ่งของการโจมตีแบบแทรก และนักพัฒนาต้องตระหนักถึงช่องโหว่การแทรกอื่นๆ ที่อาจส่งผลต่อความปลอดภัยของแอปพลิเคชัน
แม้ว่าการแทรก SQL จะพบได้บ่อยที่สุด แต่ก็มีช่องโหว่ในการแทรกอื่น ๆ :
- การแทรกคําสั่ง: การแทรกคําสั่งของระบบลงในอินพุตแอปพลิเคชันที่รันคําสั่งเชลล์
- การแทรก Lightweight Directory Access Protocol (LDAP): การจัดการคิวรี LDAP เพื่อเข้าถึงข้อมูลไดเรกทอรีที่ไม่ได้รับอนุญาต
- การแทรก NoSQL: การใช้ประโยชน์จากฐานข้อมูล NoSQL ผ่านการสืบค้นที่เป็นอันตราย
- การแทรก XML: การแทรกเนื้อหา XML ที่เป็นอันตรายเพื่อเข้าถึงหรือแก้ไขข้อมูล
รูปแบบสากล: เมื่อใดก็ตามที่คุณแทรกอินพุตที่ไม่น่าเชื่อถือลงในคําสั่งหรือแบบสอบถามที่ได้รับการตีความ คุณเสี่ยงต่อการแทรก รูปแบบการแก้ปัญหาจะคล้ายกันเสมอ: ฆ่าเชื้อ ตรวจสอบความถูกต้อง หรือกําหนดพารามิเตอร์เพื่อแยกโค้ดออกจากข้อมูล
การเข้ารหัสข้อมูลที่ละเอียดอ่อนที่อ่อนแอ
การจัดเก็บหรือส่งข้อมูลที่ละเอียดอ่อนโดยไม่มีการเข้ารหัสที่เหมาะสมจะทําให้เข้าถึงโดยไม่ได้รับอนุญาต หมวดหมู่นี้มีทั้งวิธีการเข้ารหัสที่ไม่เพียงพอและขาดการเข้ารหัสโดยสิ้นเชิง
การจัดเก็บรหัสผ่านที่ไม่ปลอดภัย
รหัสผ่านต้องการการป้องกันพิเศษเนื่องจากทําหน้าที่เป็นกลไกการรับรองความถูกต้องหลักสําหรับแอปพลิเคชันส่วนใหญ่
การจัดเก็บรหัสผ่านอย่างไม่เหมาะสมเป็นช่องโหว่ที่สําคัญ
การจัดเก็บข้อความธรรมดา (ไม่ยอมรับ)
// DANGEROUS: Storing passwords in plaintext
string password = userInput;
database.SavePassword(username, password);
หากฐานข้อมูลถูกบุกรุก รหัสผ่านของผู้ใช้ทั้งหมดจะถูกเปิดเผยทันที
การแฮชที่อ่อนแอ (ไม่เพียงพอ)
// INSUFFICIENT: Using MD5 or SHA1 without salt
using (MD5 md5 = MD5.Create())
{
byte[] hash = md5.ComputeHash(Encoding.UTF8.GetBytes(password));
string hashedPassword = Convert.ToBase64String(hash);
}
MD5 และ SHA1 เสียการเข้ารหัส GPU สมัยใหม่สามารถทดสอบชุดรหัสผ่านหลายพันล้านชุดต่อวินาทีกับแฮชที่รวดเร็วเหล่านี้ นอกจากนี้ หากไม่มีเกลือ ผู้โจมตีสามารถใช้ตารางสีรุ้งที่คํานวณไว้ล่วงหน้าเพื่อถอดรหัสรหัสผ่านได้ทันที
การแฮชที่ปลอดภัย (แนะนํา)
// SECURE: Using bcrypt with automatic salt generation
string hashedPassword = BCrypt.Net.BCrypt.HashPassword(password);
// Later, for verification:
bool isValid = BCrypt.Net.BCrypt.Verify(userInput, storedHash);
การแฮชรหัสผ่านที่ปลอดภัยต้องการ:
- เกลือ: เพิ่มข้อมูลแบบสุ่มลงในรหัสผ่านก่อนแฮช เพื่อป้องกันการโจมตีตารางสีรุ้ง
- อัลกอริทึมที่ช้า: ฟังก์ชันต่างๆ เช่น bcrypt, scrypt หรือ Argon2 มีราคาแพงในการคํานวณ โดยจํากัดความพยายามของกําลังเดรัจฉานไว้ที่หลายร้อยหรือหลายพันต่อวินาทีแทนที่จะเป็นหลายพันล้าน
การเข้ารหัสข้อมูลที่ไม่ได้ใช้งาน
นอกเหนือจากความปลอดภัยของรหัสผ่านแล้วข้อมูลที่ละเอียดอ่อนใด ๆ ที่จัดเก็บไว้ในดิสก์หรือในฐานข้อมูลจําเป็นต้องได้รับการปกป้องผ่านการเข้ารหัสที่เหมาะสม
ข้อมูลที่ละเอียดอ่อนที่จัดเก็บโดยไม่มีการเข้ารหัสจะมีความเสี่ยงหากสื่อจัดเก็บข้อมูลถูกบุกรุก
สถานการณ์ที่เปราะบาง
// VULNERABLE: Writing sensitive data in plaintext
File.WriteAllText("customer_data.txt", sensitiveInformation);
หากแล็ปท็อปที่มีไฟล์นี้ถูกขโมย หรือหากผู้โจมตีเข้าถึงระบบไฟล์ ข้อมูลจะสามารถอ่านได้ทันที
แนวทางที่ปลอดภัย
// SECURE: Encrypting data before storage
using (Aes aes = Aes.Create())
{
aes.Key = GetEncryptionKey(); // Securely managed key
aes.GenerateIV();
using (FileStream fileStream = new FileStream("customer_data.enc", FileMode.Create))
{
fileStream.Write(aes.IV, 0, aes.IV.Length);
using (CryptoStream cryptoStream = new CryptoStream(fileStream, aes.CreateEncryptor(), CryptoStreamMode.Write))
using (StreamWriter writer = new StreamWriter(cryptoStream))
{
writer.Write(sensitiveInformation);
}
}
}
การเข้ารหัสที่เหมาะสมจะให้ชั้นการป้องกันแม้ว่าพื้นที่จัดเก็บข้อมูลจะถูกบุกรุก โดยสมมติว่าคีย์การเข้ารหัสได้รับการจัดการแยกกันอย่างเหมาะสม
ปัญหาการบันทึกและการจัดการข้อผิดพลาด
การบันทึกและการจัดการข้อผิดพลาดที่ไม่เหมาะสมอาจเปิดเผยข้อมูลที่ละเอียดอ่อนหรือรายละเอียดของระบบที่ช่วยผู้โจมตีโดยไม่ได้ตั้งใจ
การบันทึกข้อมูลที่ละเอียดอ่อน
แม้ว่าการบันทึกจะเป็นสิ่งสําคัญสําหรับการดีบักและการตรวจสอบ แต่ก็อาจกลายเป็นช่องโหว่ด้านความปลอดภัยเมื่อมีการบันทึกข้อมูลที่ละเอียดอ่อน
แอปพลิเคชันต้องไม่บันทึกข้อมูลที่ละเอียดอ่อนในรูปแบบข้อความธรรมดา
แนวทางปฏิบัติในการตัดไม้ที่เป็นอันตราย
// DANGEROUS: Logging sensitive information
logger.LogInformation($"User {username} logged in with password: {password}");
logger.LogInformation($"Credit card processed: {cardNumber}");
logger.LogInformation($"API Key: {apiKey}");
รหัสนี้เปิดเผยข้อมูลที่ละเอียดอ่อนในบันทึก ซึ่งผู้ใช้ที่ไม่ได้รับอนุญาตอาจเข้าถึงได้หรือรั่วไหลผ่านระบบการจัดการบันทึก
แนวทางปฏิบัติในการบันทึกที่ปลอดภัย
// SECURE: Logging without sensitive data
logger.LogInformation($"User {username} logged in successfully");
logger.LogInformation($"Payment processed for order {orderId}");
logger.LogInformation($"API call authenticated successfully");
แนวทางปฏิบัติที่ดีที่สุด
- อย่าบันทึกรหัสผ่าน โทเค็นการรับรองความถูกต้อง หรือคีย์ API
- ปกปิดหรือปกปิดข้อมูลที่ละเอียดอ่อน เช่น หมายเลขบัตรเครดิตหรือหมายเลขประกันสังคม
- บันทึกเหตุการณ์และผลลัพธ์ ไม่ใช่ค่าข้อมูลที่ละเอียดอ่อน
การเปิดเผยข้อมูลข้อผิดพลาดมากเกินไป
ข้อความแสดงข้อผิดพลาดมีจุดประสงค์ในการดีบักที่สําคัญ แต่ต้องสร้างขึ้นอย่างระมัดระวังเพื่อหลีกเลี่ยงการเปิดเผยข้อมูลภายในของระบบต่อผู้โจมตีที่อาจเกิดขึ้น
ข้อความแสดงข้อผิดพลาดโดยละเอียดสามารถเปิดเผยสถาปัตยกรรมระบบ เส้นทางไฟล์ สคีมาฐานข้อมูล และข้อมูลอื่นๆ ที่เป็นประโยชน์ต่อผู้โจมตี
การจัดการข้อผิดพลาดที่มีปัญหา
// PROBLEMATIC: Exposing detailed error information to users
catch (Exception ex)
{
return $"Error: {ex.Message}\nStack Trace: {ex.StackTrace}\nConnection String: {connectionString}";
}
สิ่งนี้เผยให้เห็นรายละเอียดของระบบภายในที่ผู้โจมตีสามารถใช้เพื่อสร้างการโจมตีที่ซับซ้อนยิ่งขึ้น
การจัดการข้อผิดพลาดที่ปลอดภัย
// SECURE: User-friendly messages with detailed internal logging
catch (Exception ex)
{
logger.LogError(ex, "Failed to process user request");
return "An error occurred while processing your request. Please try again or contact support.";
}
ผู้ใช้จะได้รับข้อความแสดงข้อผิดพลาดที่เป็นมิตรและน้อยที่สุดในขณะที่นักพัฒนาจะได้รับข้อมูลข้อผิดพลาดโดยละเอียดผ่านบันทึกที่ปลอดภัย
การโจมตีข้ามเส้นทาง
การข้ามเส้นทาง (เรียกอีกอย่างว่าการสํารวจไดเรกทอรี) เกิดขึ้นเมื่อแอปพลิเคชันใช้อินพุตที่ผู้ใช้ให้มาเพื่อสร้างเส้นทางไฟล์โดยไม่มีการตรวจสอบความถูกต้องที่เหมาะสม ผู้โจมตีสามารถใช้ลําดับอักขระพิเศษเพื่อเข้าถึงไฟล์นอกไดเร็กทอรีที่ต้องการ
พิจารณารหัสที่มีช่องโหว่ต่อไปนี้:
// VULNERABLE: Using user input directly in file paths
string filename = Request.Query["file"];
string filePath = Path.Combine(@"C:\uploads\", filename);
string content = File.ReadAllText(filePath);
ผู้โจมตีสามารถให้ข้อมูล เช่น ../../../Windows/System32/config/SAM การเข้าถึงไฟล์ระบบที่ละเอียดอ่อน หรือ ../../web.config อ่านการกําหนดค่าแอปพลิเคชันที่มีความลับ
โค้ดที่มีช่องโหว่เปิดใช้งานกลไกการโจมตีต่อไปนี้:
-
..ลําดับนําทางขึ้นระดับไดเร็กทอรี - ผู้โจมตีสามารถหลบหนีจากแซนด์บ็อกซ์ไดเรกทอรีที่ตั้งใจไว้ได้
- เข้าถึงไฟล์ที่ละเอียดอ่อน ไฟล์การกําหนดค่า หรือไฟล์ระบบ
- อาจเขียนทับไฟล์แอปพลิเคชันที่สําคัญ
พิจารณาการใช้งานที่ปลอดภัยต่อไปนี้:
// SECURE: Validating and constraining file paths
string filename = Request.Query["file"];
// Remove path traversal sequences
filename = Path.GetFileName(filename);
// Construct full path
string uploadsDirectory = Path.GetFullPath(@"C:\uploads\");
string filePath = Path.GetFullPath(Path.Combine(uploadsDirectory, filename));
// Verify the resulting path is still within the uploads directory
if (!filePath.StartsWith(uploadsDirectory))
{
throw new SecurityException("Invalid file path");
}
string content = File.ReadAllText(filePath);
การใช้งานที่ปลอดภัยแสดงให้เห็นถึงกลยุทธ์การป้องกันต่อไปนี้:
- ใช้เพื่อ
Path.GetFileName()ลบข้อมูลไดเรกทอรี - เพิ่มไฟล์หรือรูปแบบที่อนุญาตในรายการที่อนุญาตแทนการบล็อกอักขระที่เป็นอันตราย
- ตรวจสอบว่าเส้นทางที่แก้ไขแล้วยังคงอยู่ในไดเรกทอรีที่ต้องการ
- ใช้สิทธิ์การเข้าถึงไฟล์ที่เข้มงวดในระดับระบบปฏิบัติการ
ข้อควรพิจารณาด้านความปลอดภัยอื่นๆ
นอกเหนือจากช่องโหว่ที่กล่าวถึงในส่วนก่อนหน้านี้แล้ว ปัญหาด้านความปลอดภัยอื่นๆ อีกหลายประการยังต้องการความตระหนักของนักพัฒนา
การเขียนสคริปต์ข้ามไซต์ (XSS)
การเขียนสคริปต์ข้ามไซต์ช่วยให้ผู้โจมตีสามารถแทรกโค้ดที่เป็นอันตรายลงในเว็บแอปพลิเคชัน ซึ่งอาจส่งผลต่อข้อมูลและเซสชันของผู้ใช้
แม้ว่าจะไม่สามารถใช้ได้กับแอปพลิเคชันคอนโซล แต่นักพัฒนาเว็บต้องตรวจสอบและเข้ารหัสการป้อนข้อมูลของผู้ใช้ทั้งหมดก่อนที่จะแสดงในเบราว์เซอร์
ความลับแบบฮาร์ดโค้ด
ข้อมูลประจําตัวและค่าการกําหนดค่าที่ละเอียดอ่อนที่ฝังอยู่ในซอร์สโค้ดโดยตรงแสดงถึงความเสี่ยงด้านความปลอดภัยที่สําคัญซึ่งอาจเปิดเผยทั้งระบบ
การฝังคีย์ API รหัสผ่าน หรือโทเค็นโดยตรงในซอร์สโค้ดจะทําให้ทุกคนที่มีสิทธิ์เข้าถึงที่เก็บเปิดเผย ความลับควรเป็น:
- จัดเก็บไว้ในระบบการกําหนดค่าหรือห้องนิรภัยที่ปลอดภัย
- ไม่เคยผูกมัดกับการควบคุมเวอร์ชัน
- หมุนอย่างสม่ําเสมอ
- จัดการด้วยการควบคุมการเข้าถึงที่เหมาะสม
ทรัพยากรหมดและการปฏิเสธการให้บริการ
ผู้โจมตีมักใช้ประโยชน์จากแอปพลิเคชันที่จัดการทรัพยากรไม่ถูกต้อง การโจมตีอาจทําให้บริการหยุดชะงักหรือระบบขัดข้อง
การจัดการทรัพยากรที่ไม่ดีอาจทําให้เกิดการโจมตีแบบปฏิเสธการให้บริการ ตัวอย่าง ได้แก่ :
- การอ่านไฟล์ขนาดใหญ่ทั้งหมดลงในหน่วยความจํา (ทําให้เกิดข้อผิดพลาดหน่วยความจําไม่เพียงพอ)
- ไม่จํากัดขนาดหรือความถี่ของคําขอ
- อัลกอริทึมที่ไม่มีประสิทธิภาพซึ่งใช้ CPU มากเกินไป
- ล้มเหลวในการกําจัดทรัพยากรอย่างเหมาะสม
วิธีระบุปัญหาด้านความปลอดภัยในโค้ด
การระบุช่องโหว่ด้านความปลอดภัยในโค้ดต้องใช้วิธีการที่เป็นระบบ
วิเคราะห์การจัดการอินพุตของผู้ใช้
การป้อนข้อมูลของผู้ใช้แสดงถึงเวกเตอร์การโจมตีหลักสําหรับช่องโหว่ด้านความปลอดภัยส่วนใหญ่ ทําให้จําเป็นต้องตรวจสอบว่าโค้ดของคุณประมวลผลข้อมูลภายนอกอย่างไร
ทุกจุดที่โค้ดของคุณยอมรับการป้อนข้อมูลของผู้ใช้เป็นจุดเริ่มต้นที่เป็นไปได้สําหรับการโจมตี:
- ค้นหา: อินพุตที่ใช้ในการสืบค้น SQL, เส้นทางไฟล์, คําสั่งระบบ หรือตรรกะที่สําคัญ
- ถาม: "ฉันเชื่อถือข้อมูลนี้มากเกินไปหรือไม่"
- พิจารณา: ช่องโหว่ในการฉีด การสํารวจเส้นทาง การแทรกคําสั่ง
ตรวจสอบการดําเนินการเข้ารหัส
การใช้งานด้านความปลอดภัยที่เกี่ยวข้องกับการเข้ารหัส การแฮช และการรับรองความถูกต้องจําเป็นต้องมีการตรวจสอบอย่างละเอียดเป็นพิเศษ เนื่องจากการเข้ารหัสที่อ่อนแอสามารถประนีประนอมทั้งระบบได้
รหัสลับต้องมีการตรวจสอบเป็นพิเศษ:
-
มองหา:
MD5.Create(), ,SHA1.Create()ที่เก็บรหัสผ่านข้อความธรรมดา - ถาม: "วิธีการเข้ารหัสนี้ยังถือว่าปลอดภัยหรือไม่"
- พิจารณา: การใช้ bcrypt, scrypt หรือ Argon2 สําหรับรหัสผ่าน SHA-256 หรือดีกว่าสําหรับการตรวจสอบความสมบูรณ์
ตรวจสอบใบแจ้งยอดการบันทึก
บันทึกอาจกลายเป็นช่องโหว่ด้านความปลอดภัยโดยไม่ได้ตั้งใจเมื่อบันทึกข้อมูลที่ละเอียดอ่อนซึ่งควรได้รับการปกป้อง
สแกนโค้ดเบสของคุณเพื่อหาข้อมูลที่ละเอียดอ่อนในบันทึก:
- มองหา: บันทึกคําสั่งที่มีตัวแปรชื่อ password, secret, token, apiKey, cardNumber
- ถาม: "ฉันเปิดเผยข้อมูลอะไรในบันทึก"
- พิจารณา: จะเกิดอะไรขึ้นหากบันทึกเหล่านี้ถูกบุกรุกหรือถูกเปิดเผยโดยไม่ได้ตั้งใจ
ตรวจสอบการทํางานของไฟล์
โค้ดการจัดการไฟล์นําเสนอความท้าทายด้านความปลอดภัยที่ไม่เหมือนใคร เนื่องจากสามารถเปิดเผยทรัพยากรระบบที่อยู่นอกเหนือขอบเขตที่ตั้งใจไว้ของแอปพลิเคชันของคุณ
โค้ดการจัดการไฟล์ต้องการการตรวจสอบอย่างรอบคอบ:
-
มองหา:
Path.Combineด้วยการป้อนข้อมูลของผู้ใช้ การดําเนินการไฟล์ตามเส้นทางที่ผู้ใช้ให้มา - ถาม: "ผู้ใช้สามารถออกจากไดเรกทอรีที่ต้องการได้หรือไม่"
- พิจารณา: การโจมตีการข้ามเส้นทางและเทคนิคการหลบหนีไดเรกทอรี
ใช้เครื่องมืออัตโนมัติ
แม้ว่าการตรวจสอบโค้ดด้วยตนเองจะเป็นสิ่งสําคัญ แต่เครื่องมืออัตโนมัติสามารถสแกนโค้ดเบสขนาดใหญ่ได้อย่างมีประสิทธิภาพ และระบุรูปแบบช่องโหว่ทั่วไปที่อาจพลาดไประหว่างการตรวจสอบด้วยตนเอง
รวมการตรวจสอบโค้ดด้วยตนเองเข้ากับการวิเคราะห์อัตโนมัติ:
- การวิเคราะห์แบบคงที่: เครื่องมือเช่น GitHub CodeQL สแกนโค้ดเพื่อหารูปแบบช่องโหว่ที่รู้จัก
- GitHub Copilot: ใช้โหมดถามเพื่อวิเคราะห์ส่วนของโค้ด: "มีปัญหาด้านความปลอดภัยในโค้ดนี้หรือไม่"
- ตัวระบุความปลอดภัย: เครื่องมือเฉพาะภาษาสามารถตั้งค่าสถานะข้อผิดพลาดด้านความปลอดภัยที่ชัดเจนได้
GitHub Copilot สามารถระบุปัญหาด้านความปลอดภัยทั่วไปได้มากมายเมื่อคุณขอให้วิเคราะห์โค้ด ใช้รูปแบบจากฐานรหัสนับล้านเพื่อจดจําช่องโหว่
แนวทางการรักษาความปลอดภัยแบบเลื่อนซ้าย
หลักการของ "การเลื่อนไปทางซ้าย" หมายถึงการจัดการกับความปลอดภัยก่อนหน้านี้ในวงจรการพัฒนา:
- ขั้นตอนการออกแบบ: พิจารณาผลกระทบด้านความปลอดภัยของการตัดสินใจทางสถาปัตยกรรม
- ขั้นตอนการพัฒนา: เขียนโค้ดที่ปลอดภัยตั้งแต่เริ่มต้น ตรวจจับปัญหาระหว่างการตรวจสอบโค้ด
- ขั้นตอนการทดสอบ: รวมการทดสอบความปลอดภัยควบคู่ไปกับการทดสอบการทํางาน
- ขั้นตอนการปรับใช้: สแกนหาช่องโหว่ก่อนเผยแพร่
การตรวจจับปัญหาด้านความปลอดภัยระหว่างการพัฒนานั้นมีราคาถูกกว่าการค้นพบในการผลิตมาก ค่าใช้จ่ายในการแก้ไขช่องโหว่จะเพิ่มขึ้นอย่างทวีคูณในแต่ละขั้นตอนที่พวกเขาผ่านไป
Summary
ช่องโหว่ด้านความปลอดภัยทั่วไป เช่น การโจมตีแบบแทรก การเข้ารหัสที่อ่อนแอ การบันทึกที่ไม่เหมาะสม และการข้ามเส้นทางแสดงถึงภัยคุกคามร้ายแรงต่อความปลอดภัยของแอปพลิเคชัน การทําความเข้าใจช่องโหว่เหล่านี้จะช่วยให้คุณจดจําช่องโหว่เหล่านี้ในโค้ดและจัดลําดับความสําคัญของการแก้ไข ด้วยการรวมความรู้เกี่ยวกับรูปแบบช่องโหว่ทั่วไปเข้ากับเครื่องมือต่างๆ เช่น GitHub Copilot คุณสามารถระบุและแก้ไขปัญหาด้านความปลอดภัยได้อย่างมีประสิทธิภาพมากขึ้น