How Computers Execute ProgramsPart 1 of 1
- 01CPU Architecture ও Program Execution: সহজভাবে ব্যাখ্যা
CPU Architecture ও Program Execution: সহজভাবে ব্যাখ্যা
On this page
- শুরুতে CPU নিয়ে দুটো কথা
- CPU এর প্রধান অংশগুলো
- ১. Control Unit (CU)
- ২. Arithmetic Logic Unit (ALU)
- ৩. Registers
- ৪. Cache Memory
- Program Execution Process: Step by Step
- আগে নিজে চালিয়ে দেখুন
- Step 1: Program Loading (Storage থেকে Memory তে)
- Step 2: Fetch Cycle শুরু
- Step 3: Decode Phase
- Step 4: Execute Phase: Line by Line
- Visual Representation
- Step 5: fmt.Printf Function Call
- CPU এর Internal Process
- Cache এর ভূমিকা
- Program Counter এর Journey
- Memory Layout এর চিত্র
- কেন এত Complex Process?
- Performance কোথায় আটকায়
- Practical Tips
- শেষ কথা
- References
সালটা ২০১৭। আমি আমার জীবনের সবচেয়ে বোল্ড সিদ্ধান্তটা নিয়ে ফেললাম: ক্যারিয়ার শিফট করে ঢুকে পড়লাম সফটওয়্যার ইন্ডাস্ট্রিতে।
আমি তখন একজন নন-CSE ব্যাকগ্রাউন্ডের মানুষ। পড়াশোনা করেছি গার্মেন্টস ডিজাইন অ্যান্ড প্যাটার্ন মেকিং ইঞ্জিনিয়ারিং নিয়ে। কোডিং শিখতে শিখতে অনেকটা ভালোবাসাও জন্মে গিয়েছিল, কিন্তু একটা জিনিস আমাকে বারবার ভাবাতো: "আমি কোড তো লিখছি, কিন্তু কম্পিউটার ভিতরে বসে এগুলো আসলে কীভাবে চালায়?"
তখন শুধু code লিখতে পারতাম, কিন্তু আমার লেখা program computer-এর ভিতরে কীভাবে কাজ করে সেটা বুঝতাম না। CPU, memory, OS এই জিনিসগুলো বুঝতে অনেকদিন লেগেছে; ধীরে ধীরে জট খুলতে শুরু করে।
আজকে সেই অভিজ্ঞতা থেকে খুব সহজ করে বোঝানোর চেষ্টা করব CPU-র ভিতরে আসলে কী হয়। বাংলায় সহজ ভাষায় ও গভীরভাবে ব্যাখ্যা করা রিসোর্স খুব কম, তাই এই আর্টিকেলটা লেখা, যাতে আপনার মতো আরেকজন আগ্রহী মানুষ সহজ ভাষায় এই জটিল বিষয়গুলো বুঝতে পারেন।
শুরুতে CPU নিয়ে দুটো কথা
CPU মানে Central Processing Unit। একে computer এর "brain" বলা হয়, কিন্তু আসলে এটা brain এর মতো চিন্তা করে না, বরং খুব দ্রুত গতিতে simple mathematical operations করে। আমরা যে program লিখি, সেটা শেষ পর্যন্ত CPU এর কাছে গিয়ে পৌঁছায় 0 আর 1 হিসেবে, যাকে বলি machine code।
CPU এর প্রধান অংশগুলো
১. Control Unit (CU)
এটা হলো CPU এর "traffic controller"। Program এর instruction গুলো কোন order এ execute হবে, কোন data কোথায় পাঠাতে হবে, এসব control করে CU।
Example: মনে করেন আপনি একটা recipe follow করছেন। CU হলো সেই person যে বলছে "প্রথমে চাল ধুয়ে নাও, তারপর পানি দাও, তারপর চুলায় দাও"।
২. Arithmetic Logic Unit (ALU)
এখানে সব mathematical calculations হয়। Addition, subtraction, multiplication, division এবং logical operations (AND, OR, NOT) সব এখানে হয়।
Example: যদি আপনি লিখেন var result int = 5 + 3{:go} তাহলে এই addition টা ALU তে হবে।
৩. Registers
এগুলো হলো CPU এর সবচেয়ে fast memory। খুব small amount এর data temporarily store করে রাখে। CPU এই মুহূর্তে যে data বা instruction নিয়ে কাজ করছে সেটা register-এ থাকে, তাই ALU কোনো দেরি ছাড়াই data access করতে পারে। যেমন:
- Accumulator: Calculation এর result store করে
- Program Counter (PC): পরবর্তী instruction এর address রাখে
- Instruction Register (IR): Current instruction রাখে
৪. Cache Memory
RAM থেকে data আনতে time লাগে। তাই frequently used data cache এ রাখা হয় যাতে দ্রুত access করা যায়।
- L1 Cache: সবচেয়ে fast, CPU এর সাথে attached
- L2 Cache: একটু slow কিন্তু বড়
- L3 Cache: সবচেয়ে বড়, কিন্তু তিনটার মধ্যে ধীরতম
Program Execution Process: Step by Step
এখন একটা simple calculator program দিয়ে দেখাবো কীভাবে step by step execution হয়:
package main
import "fmt"
func main() {
var a int = 10
var b int = 5
var sum int = a + b
fmt.Printf("Sum: %d\n", sum)
}
আগে নিজে চালিয়ে দেখুন
নিচের visualizer-এ এই program-টাই ধাপে ধাপে execute হয়। Play চাপুন, বাঁয়ে CPU-র register-গুলো আর ডানে memory-র ঘরগুলো কীভাবে বদলায় সেটা লক্ষ্য করুন। যেকোনো memory cell-এ click করলে তার address আর ব্যাখ্যা পাবেন।
সব step পুরোপুরি না বুঝলেও সমস্যা নেই। এবার ধাপে ধাপে দেখি ভেতরে আসলে কী হলো।
Step 1: Program Loading (Storage থেকে Memory তে)
যখন আপনি program run করেন:
- Hard disk/SSD থেকে compiled program (executable file) RAM এ load হয়
- Operating System একটা process create করে
- Program এর instructions এবং data আলাদা আলাদা memory segment এ রাখা হয়
Hard Disk → RAM
[program.exe] → [Code Segment | Data Segment | Stack | Heap]
Step 2: Fetch Cycle শুরু
- Program Counter (PC) এ first instruction এর address থাকে
- CPU সেই address থেকে instruction fetch করে
- Instruction Instruction Register (IR) এ store হয়
PC: 0x1000 → Memory[0x1000] → IR: "var a int = 10"
আসলে IR-এ থাকে machine instruction (binary), source code-এর লাইন নয়। বোঝার সুবিধার জন্য এখানে source line-টাই দেখাচ্ছি।
Step 3: Decode Phase
Control Unit instruction decode করে বুঝে:
- এটা একটা variable declaration
- Value 10 কে register এ store করতে হবে
- Memory তে space allocate করতে হবে
Step 4: Execute Phase: Line by Line
Line 1: var a int = 10{:go}
1. Memory তে 8 bytes space allocate করে → address: 0x2000 (64-bit সিস্টেমে Go-র int হয় 64-bit)
2. Value 10 কে register এ load → R1 = 10
3. R1 এর value memory তে store → Memory[0x2000] = 10
Line 2: var b int = 5{:go}
1. Memory তে আরো 8 bytes space → address: 0x2008
2. Value 5 কে register এ load → R2 = 5
3. Memory তে store → Memory[0x2008] = 5
Line 3: var sum int = a + b{:go}
1. Variable 'a' এর value register এ load → R1 = Memory[0x2000] = 10
2. Variable 'b' এর value register এ load → R2 = Memory[0x2008] = 5
3. ALU তে addition operation → R3 = R1 + R2 = 15
4. Result কে memory তে store → Memory[0x2010] = 15
Visual Representation
প্রতিটা অংশে hover করুন (বা keyboard এ Tab চাপুন): কোন অংশ কী কাজ করে দেখতে পাবেন।
Step 5: fmt.Printf Function Call
fmt.Printf("Sum: %d\n", sum)এটা একটু complex:
- Stack এ sum (function parameters) push হয়
- Function Call হয় → CPU jumps to fmt.Printf
- Output print করে → “Sum: 15”
- Stack clean up হয়
Go 1.17 থেকে argument আসলে আগে register দিয়ে pass হয়; stack-এ push করা দেখাচ্ছি ধারণাটা সহজ রাখতে।
CPU এর Internal Process
1. PUSH sum → Stack: [15]
2. CALL fmt.Printf → PC jumps to fmt.Printf address
3. fmt.Printf executes → Screen output: "Sum: 15"
4. POP stack → Stack: []
5. RETURN → PC returns to main
Cache এর ভূমিকা
আমাদের program execute করার সময়:
- প্রথমে L1 cache check করে data আছে কিনা
- না থাকলে L2, তারপর L3 check করে
- কোথাও না থাকলে RAM থেকে fetch করে
- Frequently used data cache এ রেখে দেয়
CPU Request: "a এর value দাও"
L1 Cache: "নেই"
L2 Cache: "নেই"
RAM: "আছে, 10" → Cache এ copy → CPU কে দেয়
Program Counter এর Journey
Program Counter (PC) continuously track করে কোন instruction execute হবে:
Initial: PC = 0x1000 (var a int = 10)
After: PC = 0x1004 (var b int = 5)
After: PC = 0x1008 (var sum int = a + b)
After: PC = 0x100C (fmt.Printf call)
After: PC = 0x1010 (function end)
Memory Layout এর চিত্র
High Address
Stack
growsLocal variables, function calls
Heap
growsDynamic allocation
Data
Global variables
Code
Program instructions
Low Address
কেন এত Complex Process?
আপনি হয়তো ভাবছেন এত simple একটা program এর জন্য এতো steps কেন? কারণ:
- Security: Memory protection, unauthorized access prevent করা
- Efficiency: Multiple programs same time run করা
- Optimization: Cache ব্যবহার করে speed বাড়ানো
- Error Handling: Program crash হলে পুরো system যাতে crash না হয়
Performance কোথায় আটকায়
CPU এর speed measure করা হয় Clock Speed দিয়ে (GHz এ)। Modern CPU প্রতি second এ billions instructions execute করতে পারে। কিন্তু:
- Memory access: RAM থেকে data আনতে time লাগে
- Cache miss: Data cache এ না থাকলে slow হয়
- Branch prediction: if-else statements এর জন্য CPU guess করে
Practical Tips
Programming করার সময় যেসব বিষয় মাথায় রাখবেন:
- Local variables use করবেন: cache friendly
- Loop optimization করবেন: branch prediction এর জন্য
- Data structures choose করবেন carefully: memory access pattern এর জন্য
শেষ কথা
এই পুরো process টা milliseconds এর fraction এ হয়ে যায়। কিন্তু পর্দার আড়ালে CPU, memory, cache সবার coordination এ আমাদের program run হয়।
যখন এসব জানতাম না, তখন শুধু code লিখতাম। এখন internal process টা জানার পর কোড লেখার সময় ভেতরে কী হচ্ছে সেটা চোখের সামনে দেখতে পাই।
লেখাটা কাজে লাগলে পরিচিত কাউকে পাঠাতে পারেন। আর কোনো ভুল চোখে পড়লে জানাবেন, শুধরে নেব।
References
- David A. Patterson, John L. Hennessy — Computer Organization and Design (Morgan Kaufmann)
- Ulrich Drepper — What Every Programmer Should Know About Memory (Red Hat, 2007)
- Go team — Register-based calling convention (Go 1.17 release notes)