การจัดการหน่วยความจำ

Memory Management

การจัดหน่วยความจำ เป็นงานอย่างหนึ่งของโอเอส ถ้าหน่วยความจำมีปริมาณมาก ขีดความสามารถในการทำงานก็จะเพิ่มขึ้นด้วย โปรแกรมที่มีความสลับซับซ้อนและมีความสามารถมากก็ต้องการหน่วยความจำมาก จึงจำเป็นต้องใช้หน่วยความจำที่มีอยู่ให้เกิดประโยชน์สูงสุด หน้าที่ของโอเอสเช่น ดูว่าโปรแกรมใหม่จะถูกนำไปวางไว้ในหน่วยความจำตรงที่ใด? เมื่อใด? หน่วยความจำไหนควรถูกใช้ก่อนหรือหลัง? โปรแกรมไหนจะได้ใช้หน่วยความจำก่อน?
การจัดหน่วยความจำของโอเอส มีวิธีการจัดอยู่ 3 อย่างคือ
1. วิธีการเฟตช์ (fecth strategy)
2. วิธีการวาง (placement strategy)
3. วิธีการแทนที่ (replacement strategy)

การจัดสรรหน่วยความจำ

ทุกโปรแกรมมีความจำเป็นต้องใช้หน่วยความจำในระบบ จะใช้มากหรือน้อยขึ้นอยู่กับการทำงานและขนาดของโปรแกรม โปรแกรมจะทำงานได้ก็ต่อเมื่อมันได้ถูกนำไปวาง (Load) ไว้ในหน่วยความจำแล้วเท่านั้น การที่โปรแกรมได้เข้าไปใช้หน่วยความจำของระบบเป็นเพราะการจัดสรรหน่วยความจำ(Memory allocation) ของโอเอส
- การจัดสรรหน่วยความจำแบบต่อเนื่อง คอมฯยุคก่อนครอบครองหน่วยความจำให้โปรแกรมต่าง ๆ จะเป็นแบบต่อเนื่องทั้งสิ้น คือ โปรแกรมหนึ่ง ๆ จะถูกโหลดลงหน่วยความจำได้ก็ต่อเมื่อมีหน่วยความจำขนาดใหญ่พอที่วางโค้ดของโปรแกรมนั้นลงไปทั้งโปรแกรม นั่นคือโปรแกรมจะอยู่ติดต่อกันในหน่วยความจำผืนเดียวกัน ถ้าหากไม่มีที่ว่างโปรแกรมก็จะทำงานไม่ได้จนกว่าจะมีพื้นที่เหลือพอ
- การจัดสรรหน่วยความจำแบบไม่ต่อเนื่อง การครอบครองหน่วยความจำแบบนี้ ตัวโปรแกรมจะถูกแบ่งออกเป็นกลุ่มหรือส่วนย่อย ๆ หลายส่วน เมื่อโปรแกรมถูกรัน แต่ละส่วนจะถูกโหลดลงสู่หน่วยความจำตรงไหนก็ได้ที่มีพื้นที่ว่างพอ แต่ละส่วนไม่จำเป็นต้องเรียงเป็นผืนแผ่นเดียว

ระบบโปรแกรมเดี่ยว (Single program)
คอมพิวเตอร์ระบบนี้จะสามารถรันโปรแกรมของผู้ใช้ได้เพียงครั้งละ 1 โปรแกรมเท่านั้น สามารถแบ่งส่วนของหน่วยความจำออกเป็น 2 ส่วนคือ
1. ส่วนของโอเอส คือหน่วยความจำที่ถูกครอบครองโดยโอเอส อย่างที่ทราบกันว่าโอเอสก็เป็นโปรแกรมเช่นกัน โอเอสจะครอบครองหน่วยความจำที่ริมด้านใดด้านหนึ่งหรือทั้ง 2 ด้าน เพื่อให้พื้นที่เหลือยาวต่อเนื่องเป็นผืนใหญ่ผืนเดียว
2. ส่วนของผู้ใช้ (User area) คือส่วนที่สามารถนำโปรแกรมของผู้ใช้ไปวางได้ ดังนั้นในส่วนนี้คือหน่วยความจำที่เหลือจากส่วนของโอเอส

ระบบหลายโปรแกรม

การทำงานของโปรแกรมส่วนมากจะเสียเวลาไปกับการทำงานด้าน Input-Output ซึ่งเป็นงานที่ไม่ต้องใช้Cpu ดังนั้นเวลาที่ใช้ซีพียูจริง ๆ นั้นมีน้อยมากในระบบโปรแกรมเดี่ยว ช่วงเวลาที่รอการทำงานของ routine ทางอินพุต-เอาต์พุต ซีพียูจะอยู่เฉย (idle) ไม่ได้ทำงาน ดังนั้นในช่วงเวลานี้เราอนุญาติให้นำโปรแกรมอื่นเข้ามาใช้ซีพียูได้มันจึงคุ้มค่า แนวคิดนี้จึงสร้างคอมพิวเตอร์ที่สามารถรันได้หลาย ๆ โปรแกรมในเวลาเดียวกัน เรียกระบบนี้ว่าระบบหลายโปรแกรม (Multiprogramming) เมื่อคอมฯสามารถรันได้หลายโปรแกรมพร้อม ๆ กันจึงจำเป็นต้องแบ่ง partition หน่วยความจำออกเป็นส่วน ๆ สำหรับแต่ละโปรแกรมเพื่อไม่ให้ปะปนกัน และเพื่อให้รันโปรแกรมได้หลายโปรแกรม
วิธีที่ทำให้คอมพิวเตอร์สามารถทำงานได้หลายโปรแกรมมีหลายแบบ อาจจัดประเภทได้ดังนี้
1. ระบบหลายโปรแกรมแบบแบ่งหน่วยความจำ (partition multiprogramming) ในหน่วยความจำจะมีโปรแกรมหลาย ๆ โปรแกรมอยู่พร้อมกันโดยแบ่งหน่วยความจำเป็นส่วน ๆ ไป ส่วนหนึ่ง ๆ จะมีโปรแกรมเพียงโปรแกรมเดียว โปรแกรมต่าง ๆ จะครอบครองหน่วยความจำแบบต่อเนื่องในส่วนที่มันครอบครองระบบอาจแบ่งแยกได้อีก 2 ประเภทคือ 1. การแบ่งหน่วยความจำขนาดคงที่ (Fixed partition multiprogramming) และการแบ่งหน่วยความจำขนาดไม่คงที่ (Variable partition multiprogramming)
2. ระบบหลายโปรแกรมแบบสลับหน่วยความจำ (Multiprogramming with storage swaping)

การแบ่งหน่วยความจำขนาดคงที่
วิธีนี้หน่วยความจำถูกแบ่งออกเป็นหลายส่วน แต่ละส่วนมีขนาดคงที่และมีโปรแกรมอยู่โปรแกรมเดียว ดังนั้นจำนวนโปรแกรมที่จะทำงานได้พร้อมกันจะเท่ากับจำนวนของส่วนย่อยของหน่วยความจำ
- การแปลงและโหลดด้วยค่าสัมบูรณ (Absolute translation and loading) งานหรือโปรแกรมของผู้ใช้ถูกแปลเป็นภาษาเครื่องด้วยค่าแอดเดรสสัมบูรณ์ ก็เพื่อให้รันได้ในส่วนที่กำหนดเท่านั้น ค่าแอดเดรสสัมบูรณ์คือค่าแอดเดรสจริง ๆ ในหน่วยความจำ เช่นคำสั่งกระโดดไปที่แอดเดรส 5000 ค่า 5000 นี้จะเป็นแอดเดรส 5000 ในหน่วยความจำจริง ๆ สำหรับการกำหนดว่าโปรแกรมจะไปอยู่ส่วนใดขึ้นอยู่กับขนาดของโปรแกรมและขนาดของส่วนย่อยให้หน่วยความจำด้วย เช่น ส่วนที่1 มีขนาด 5 kb ส่วนที่2 มีขนาด 10 kb ส่วนที่3 มีขนาด 50 kb โปรแกรมที่มีขนาดเล็กกว่า 50 kb แต่ใหญ่กว่า 10 kbจะถูกจัดลงในส่วนที่ 3 โปรแกรมที่มีขนาดเล็กกว่า 10 kb แต่ใหญ่กว่า 5 kb จะถูกจัดลงในส่วนที่ 2 และโปรแกรมที่มีขนาดเล็กกว่า 5 kb จะถูกจัดลงในส่วนที่ 1 ข้อเสียของวิธีนี้คือ ถ้าโปรแกรมที่พร้อมจะรันแล้ว แต่ละส่วนของหน่วยความจำที่มันจะถูกโหลดไปกำลังถูกใช้โดยโปรแกรมอื่น มันต้องรอจนกว่าโปรแกรมนั้นจะเสร็จ ถึงแม้ว่าส่วนอื่นยังว่างอยู่ก็ตาม
- การแปลงและโหลดด้วยค่าสัมพัทธ์ (Relocatable translation and loading) เพื่อแก้ปัญหาที่เกิดขึ้นของการแปลงและโหลดด้วยค่าสัมบูรณ์ โปรแกรมจะถูกแปลงเพื่อให้ได้แอดเดรสที่เป็นค่าสัมพัทธ์กับจุดเริ่มต้นของโปรแกรม จุดเริ่มต้นของโปรแกรมคือแอดเดรส 0 ถ้ามีคำสั่งกระโดดไปที่แอดเดรส 50 ค่า 50 นี้จะหมายถึงแอดเดรสที่ห่างจากจุดเริ่มต้น 50 ไบต์ สมมติว่าโปรแกรมถูกโหลดลงที่แอดเดรสเริ่มต้นที่ 5000 ในหน่วยความจำ กระโดดไปที่แอดเดรส 50 จะหมายถึงการกระโดดไปที่แอดเดรส 5050 ในหน่วยความจำ การแปลงและการโหลดด้วยค่าสัมพัทธ์ทำให้โปรแกรมถูกโหลดลงส่วนใดก็ได้ของหน่วยความจำ(แต่ต้องมีขนาดมากกว่าหรือเท่ากับขนาดของโปรแกรมนั้น)
การจัดแบ่งพื้นที่ในหน่วยความจำไม่ว่าจะใช้วิธีใดก็ตามย่อมต้องเกิดส่วนที่ไม่ถูกใช้งาน เรียกว่าเกิดการแตกกระจาย (Fragmentation) ในการจัดการแบบแบ่งหน่วยความจำขนาดคงที่ การแตกกระจายเกิดขึ้นได้ 2 กรณีคือกรณีส่วนที่ถูกแบ่งของหน่วยความจำไม่ได้ถูกใช้งานเรียกว่าเป็น การแตกกระจายภายนอก(External fragmentation) และกรณีที่โปรแกรมของผู้ใช้ ใช้เนื้อที่ในส่วนย่อยไม่เต็มเรียกว่าเป็นการแตกกระจายภายใน(Internal fragmentation)

การแบ่งหน่วยความจำไม่คงที่

ผู้สร้างโอเอสได้ตระหนักถึงข้อเสียของการแบ่งหน่วยความจำขนาดคงที่ จึงคิดว่าควรปรับปรุงการแบ่งหน่วยความจำให้ดีขึ้น จึงเปลี่ยนวิธีแบ่งหน่วยความจำใหม่คือ โอเอสจะยอมให้โปรแกรมครอบครองหน่วยความจำมากเท่าที่โปรแกรมต้องการ ไม่มีการจำกัดขอบเขตของส่วนย่อย ๆ ที่แน่นอนอีกต่อไป วิธีการนี้จึงเรียกว่าการแบ่งหน่วยความจำขนาดไม่คงที่
ระบบหลายโปรแกรมประเภทแบ่งหน่วยความจำขนาดไม่คงที่ยังคงเป็นการจัดสรรหน่วยความจำแบบต่อเนื่อง เราสามารถรันโปรแกรมขนาดใหญ่เท่าใดก็ได้ ถ้าไม่ใหญ่เกินกว่าขนาดของหน่วยความจำในส่วนของผู้ใช้ ถ้าโปรแกรมต่าง ๆ มีขนาดเล็กคอมพิวเตอร์ก็สามารถรันได้หลายงานมากขึ้นแต่ถ้าโปรแกรมมีขนาดใหญ่คอมพิวเตอร์ก็จะรันโปรแกรมได้จำนวนน้อยลง ถึงแม้ว่าการแบ่งหน่วยความจำชนิดนี้จะวางโปรแกรมให้ติดกันเพื่อไม่ให้เกิดพื้นที่ว่าง การสูญเสียเนื้อที่ในหน่วยความจำเนื่องจากไม่ได้ถูกใช้งานก็ยังเกิดขึ้นได้ กรณีแรกเกิดจากพื้นที่เหลือในส่วนสุดท้ายอาจเหลือเพียงเล็กน้อยไม่เพียงพอสำหรับโปรแกรมใด ๆ อีกกรณีหนึ่งคือ เมื่อโปรแกรมใดเสร็จสิ้น โปรแกรมออกจากระบบต้องคืนพื้นที่หน่วยความจำที่มันครอบครองอยู่ให้กับระบบ ดังนั้นจึงเกิดเป็นเนื้อที่ว่างขึ้น เนื้อที่ว่างเหล่านี้เรียกว่าช่องโหว่หรือโฮล (Hole)


ที่มา : เนื้อหาวิชาระบบปฏิบัติการ อ.ยุพดี อินทสร สถาบันราชภัฏสงขลา

โดย : นาย นักรบ ฆ้องกระโทก, สถาบันราชภัฏสงขลา, วันที่ 1 พฤศจิกายน 2545