.Bss বিভাগ কেন প্রয়োজন?


120

আমি যা জানি তা হল যে গ্লোবাল এবং স্ট্যাটিক ভেরিয়েবলগুলি .dataসেগমেন্টে সঞ্চিত রয়েছে এবং অবিচ্ছিন্ন তথ্য .bssসেগমেন্টে রয়েছে। আমি যা বুঝতে পারি না তা হ'ল আমরা কেন অবিচ্ছিন্ন ভেরিয়েবলগুলির জন্য উত্সর্গীকৃত বিভাগ রাখি? যদি একটি অবিশ্রান্ত ভেরিয়েবলের রান সময় নির্ধারিত একটি মান থাকে, তবে ভেরিয়েবলটি .bssকেবলমাত্র বিভাগে বিদ্যমান ?

নিম্নলিখিত প্রোগ্রামে, aহয় .dataসেগমেন্ট, এবং bহয় .bssসেগমেন্ট; এটা কি ঠিক? আমার বুঝতে ভুল হলে দয়া করে আমাকে সংশোধন করুন।

#include <stdio.h>
#include <stdlib.h>

int a[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9};
int b[20]; /* Uninitialized, so in the .bss and will not occupy space for 20 * sizeof (int) */

int main ()
{
   ;
}  

এছাড়াও, নিম্নলিখিত প্রোগ্রাম বিবেচনা করুন,

#include <stdio.h>
#include <stdlib.h>
int var[10];  /* Uninitialized so in .bss */
int main ()
{
   var[0] = 20  /* **Initialized, where this 'var' will be ?** */
}

3
আপনি ভাল সেভ স্পেস হিসাবে বিএসএস পড়তে পারেন ।
স্মিভিকিপিডিয়া

উত্তর:


89

কারণ হ'ল প্রোগ্রামের আকার হ্রাস করা। কল্পনা করুন যে আপনার সি প্রোগ্রামটি একটি এম্বেড থাকা সিস্টেমে চলে, যেখানে কোড এবং সমস্ত ধ্রুবক সত্য রম (ফ্ল্যাশ মেমরি) এ সংরক্ষণ করা হয়। এই জাতীয় সিস্টেমে, প্রাথমিক () বলা হওয়ার আগে সমস্ত স্থিতিশীল স্টোরেজ সময়কাল অবজেক্ট সেট করতে প্রাথমিক "কপি-ডাউন" চালিত করতে হবে। এটি সাধারণত এই ছদ্ম মত চলে:

for(i=0; i<all_explicitly_initialized_objects; i++)
{
  .data[i] = init_value[i];
}

memset(.bss, 
       0, 
       all_implicitly_initialized_objects);

যেখানে .ডাটা এবং .bss র‌্যামে সংরক্ষিত থাকে তবে init_value রমে সংরক্ষণ করা হয়। যদি এটি একটি বিভাগ ছিল, তবে রমটি প্রচুর পরিমাণে শূন্যে পূরণ করতে হবে, রমের আকার উল্লেখযোগ্যভাবে বাড়িয়েছে।

র‌্যাম-ভিত্তিক এক্সিকিউটেবলগুলি একইভাবে কাজ করে, যদিও তাদের কোনও সত্যিকারের রম নেই।

এছাড়াও, মেমসেট সম্ভবত কিছু খুব দক্ষ ইনলাইন এসেমব্লার, যার অর্থ স্টার্টআপ কপি-ডাউনটি দ্রুত কার্যকর করা যায়।


7
স্পষ্ট করার জন্য: .ডাটা এবং .bss এর মধ্যে একমাত্র পার্থক্য হ'ল প্রারম্ভকালে, "অনুলিপিটি" ক্রমান্বয়ে চালানো যেতে পারে, তাই দ্রুত। যদি এটি দুটি বিভাগে বিভক্ত না হয় তবে আরম্ভের সময়টি অবিচ্ছিন্ন ভেরিয়েবলগুলির র‌্যাম স্পটগুলি এড়িয়ে যেতে হবে, তাই সময় নষ্ট করা।
সিএল 22

80

.bssসেগমেন্ট একটি অপ্টিমাইজেশান হয়। পুরো .bssবিভাগটি একক সংখ্যা দ্বারা সম্ভবত বর্ণনা করা হয়েছে, সম্ভবত 4 বাইট বা 8 বাইট, যা চলমান প্রক্রিয়াতে এর আকার দেয়, যেখানে .dataবিভাগটি প্রাথমিক ভেরিয়েবলগুলির আকারের সমষ্টি হিসাবে বড়। সুতরাং, .bssনির্বাহকগুলি লোড করা আরও দ্রুত এবং দ্রুততর করে তোলে। অন্যথায়, ভেরিয়েবলগুলি .dataসেগমেন্টে শূন্যের স্পষ্ট সূচনা সহ হতে পারে; পার্থক্যটি জানাতে প্রোগ্রামটি চাপ দেওয়া হবে। (বিশদভাবে, অংশে থাকা অবজেক্টের ঠিকানা .bssসম্ভবত ঠিকানা থেকে আলাদা হবে .data))

প্রথম প্রোগ্রাম, aহবে .dataসেগমেন্ট এবং bহবে .bssএক্সিকিউটেবল এর সেগমেন্ট। প্রোগ্রামটি লোড হয়ে গেলে, পার্থক্যটি ইমট্রেটরি হয়ে যায়। রান সময়ে, বাইট bদখল 20 * sizeof(int)

দ্বিতীয় প্রোগ্রামে varস্থান বরাদ্দ করা হয় এবং স্থান নির্ধারণের ক্ষেত্রে অ্যাসাইনমেন্ট main()। এটি ঘটে যায় যে বিভাগটির চেয়ে স্পেসটি সেগমেন্টের পরিবর্তে সেগমেন্টে varবর্ণিত হয়েছিল , তবে প্রোগ্রামটি চলাকালীন যেভাবে আচরণ করে তা প্রভাবিত করে না।.bss.data


16
উদাহরণস্বরূপ, বহু অবিচ্ছিন্ন বাফার দৈর্ঘ্যে 4096 বাইট থাকার কথা বিবেচনা করুন। আপনি কি 4k বাফারগুলির সমস্ত বাইনারি আকারে অবদান রাখতে চান? এটি অনেকটা নষ্ট স্থান হবে।
জেফ মার্কাডো

1
@ জোনাথেন হত্যাকারী: কেন পুরো বিএস বিভাগকে একক সংখ্যা দ্বারা বর্ণিত হয় ??
সুরজ জৈন

@ জোনাথনলফলার মানে সমস্ত জিরো ইনিশিয়ালাইজড স্ট্যাটিক ভেরিয়েবল বিএসএইজে যায়। তাহলে এর মানটি কেবল শূন্য হওয়া উচিত না? এবং এছাড়াও কেন তাদেরকে .ডাটা বিভাগে স্থান দেওয়া হয় না কেন এটি কীভাবে এটি ধীর করতে পারে?
সুরজ জৈন

2
@ সুরজজাইন: সঞ্চিত সংখ্যা হ'ল শূন্যে ভরাট হওয়া বাইটের সংখ্যা। এ জাতীয় কোনও অনিবার্য ভেরিয়েবল না থাকলে, বস বিভাগের দৈর্ঘ্য শূন্য হবে না, যদিও প্রোগ্রামটি লোড হওয়ার পরে আমি বিএস বিভাগের সমস্ত বাইট শূন্য হয়ে যাব।
জোনাথন লেফলার

1
এক্সিকিউটেবলের .bss বিভাগটি কেবল একটি সংখ্যা। ইন-মেমরি প্রক্রিয়া চিত্রের .bss বিভাগটি সাধারণত .Data বিভাগের সাথে সংযুক্ত মেমরি এবং প্রায়শই রানটাইম .ডাটা বিভাগটি .bss এর সাথে মিলিত হয়; রানটাইম মেমোরিতে কোনও পার্থক্য নেই। কখনও কখনও, আপনি কোথায় খুঁজে পেতে পারেন তা খুঁজে পেতে পারেন ( edata)। ব্যবহারিক ভাষায়, প্রক্রিয়া চিত্রটি একবার শেষ হয়ে গেলে .bss মেমরিতে উপস্থিত থাকে না; শূন্য তথ্যটি ডেটা বিভাগের সহজ অংশ simple তবে বিবরণগুলি o / s ইত্যাদির উপর নির্ভর করে পরিবর্তিত হয়
জোনাথন লেফলার

15

অ্যাসেম্বলি ল্যাঙ্গুয়েজ থেকে ধাপে-পদক্ষেপ: জেফ ডন্টেমন দ্বারা লিনাক্স সহ প্রোগ্রামিং , ডাটা বিভাগ সম্পর্কিত:

.Data অধ্যায় সক্রিয়া ডেটা আইটেম এর ডেটা সংজ্ঞা রয়েছে। প্রারম্ভিক ডেটা এমন ডেটা যা প্রোগ্রামটি চলমান শুরু হওয়ার আগেই একটি মান থাকে has এই মানগুলি এক্সিকিউটেবল ফাইলের অংশ। এক্সিকিউটেবল ফাইল কার্যকর করার জন্য মেমরিতে লোড করা হলে এগুলি মেমরিতে লোড হয় into

.ডাটা বিভাগটি সম্পর্কে মনে রাখা গুরুত্বপূর্ণ বিষয়টি হ'ল আপনি যে আরও সূচনাপ্রাপ্ত ডেটা আইটেমগুলি সংজ্ঞায়িত করবেন, এক্সিকিউটেবল ফাইলটি তত বেশি হবে এবং আপনি যখন এটি চালাবেন তখন ডিস্ক থেকে মেমরিতে লোড করতে আরও বেশি সময় লাগবে।

এবং .bss বিভাগ:

প্রোগ্রামটি চলমান শুরু হওয়ার আগে সমস্ত ডেটা আইটেমের মান হওয়া দরকার না। উদাহরণস্বরূপ, আপনি যখন কোনও ডিস্ক ফাইল থেকে ডেটা পড়ছেন, তখন ডিস্ক থেকে আসার পরে ডেটা যাওয়ার জন্য আপনার একটি জায়গা থাকা দরকার। এর মতো ডেটা বাফারগুলি আপনার প্রোগ্রামের .bss বিভাগে সংজ্ঞায়িত করা হয়েছে । আপনি একটি বাফারের জন্য কয়েকটি বাইট রেখেছেন এবং বাফারটিকে একটি নাম দিন, তবে আপনি বাফারে কী মান থাকতে হবে তা বলবেন না।

.ডাটা বিভাগে সংজ্ঞায়িত ডেটা আইটেম এবং .bss বিভাগে সংজ্ঞায়িত ডেটা আইটেমগুলির মধ্যে একটি গুরুত্বপূর্ণ পার্থক্য রয়েছে: .ডাটা বিভাগের ডেটা আইটেমগুলি আপনার এক্সিকিউটেবল ফাইলের আকারকে যুক্ত করে। .Bss বিভাগে ডেটা আইটেমগুলি না। ১,000,০০০ বাইট (বা আরও বেশি কিছু ক্ষেত্রে অনেক বেশি) লাগে এমন একটি বাফারকে .bss এ সংজ্ঞায়িত করা যায় এবং প্রায়োগিক কিছুই (বর্ণনার জন্য প্রায় 50 বাইট) এক্সিকিউটেবল ফাইলের আকারে যুক্ত করা যায় না।


9

ওয়েল, সবার আগে, আপনার উদাহরণে এই পরিবর্তনগুলি একচেটিয়াকরণ নয়; সি নির্দিষ্ট করে যে স্ট্যাটিক ভেরিয়েবলগুলি অন্যথায় শুরু করা হয় না 0 তে আরম্ভ করা হয়।

সুতরাং, বিএসএসের কারণটি হ'ল ছোট এক্সিকিউটেবল, স্থান সাশ্রয় এবং দ্রুত লোডিং প্রোগ্রামের অনুমতি দেওয়া, কারণ লোডার কেবল ডিস্ক থেকে ডেটা অনুলিপি না করে একগুচ্ছ জিরো বরাদ্দ করতে পারে।

প্রোগ্রামটি চলাকালীন, প্রোগ্রাম লোডার .Data এবং .bss মেমরিতে লোড করবে। .ডাটা বা .bss এ থাকা অবজেক্টগুলিতে রচনাগুলি কেবল স্মৃতিতে চলে যায়, এগুলি কোনও বিন্দুতে ডিস্কে বাইনারিগুলিতে ফেলা হয় না।


5

সিস্টেম ভী ABI- র 4.1 (1997) (ওরফে ELF স্পেসিফিকেশন) ও উত্তর রয়েছে:

.bssএই বিভাগটি অবিচ্ছিন্ন ডেটা ধারণ করে যা প্রোগ্রামটির মেমরি ইমেজটিতে অবদান রাখে। সংজ্ঞা অনুসারে, প্রোগ্রামটি যখন চালানো শুরু হয় তখন সিস্টেমটি জিরো দিয়ে ডেটা সূচনা করে। বিভাগটি কোনও ফাইল স্থান দখল করে না, যেমন বিভাগ বিভাগ দ্বারা নির্দেশিত SHT_NOBITS,।

বলে যে বিভাগটির নামটি .bssসংরক্ষিত এবং এর বিশেষ প্রভাব রয়েছে, বিশেষত এটি কোনও ফাইল স্থান দখল করে না , সুতরাং সুবিধাটি ছাড়িয়ে যায় .data

ডাউনসাইড অবশ্যই হ'ল 0যখন ওএস তাদের মেমরির উপরে রাখে তখন সমস্ত বাইট সেট করতে হবে যা আরও সীমাবদ্ধ তবে সাধারণ ব্যবহারের ক্ষেত্রে, এবং অবিচ্ছিন্ন ভেরিয়েবলগুলির জন্য সূক্ষ্মভাবে কাজ করে।

SHT_NOBITSঅধ্যায় টাইপ ডকুমেন্টেশন পুনরাবৃত্তি যে কথন:

sh_sizeএই সদস্যটি বিভাগটির আকার বাইটে দেয়। যদি না অধ্যায় ধরনের SHT_NOBITS, বিভাগ দখল করে sh_size ফাইলের মধ্যে বাইট। প্রকারের একটি অংশের SHT_NOBITSশূন্য-নন আকার থাকতে পারে, তবে এটি ফাইলের কোনও স্থান দখল করে না।

সি মান বিভাগে সম্পর্কে কিছুই বলছেন, কিন্তু যেখানে পরিবর্তনশীল সাথে Linux মধ্যে সংরক্ষিত হয় আমরা সহজেই যাচাই করতে পারেন objdumpএবং readelf, এবং মতামত হলো, uninitialized globals আসলে সংরক্ষিত হয় .bss। উদাহরণস্বরূপ এই উত্তরটি দেখুন: সিটিতে ঘোষিত, অবিচ্ছিন্ন পরিবর্তনশীলটির কী হয়?


3

উইকিপিডিয়া নিবন্ধ .bss একটি দুর্দান্ত ( তিহাসিক ব্যাখ্যা সরবরাহ করে, প্রদত্ত শব্দটি ১৯৫০ এর দশকের মাঝামাঝি থেকে (ইপিপি আমার জন্মদিনে ;-))।

আগের দিন, প্রতিটি বিট মূল্যবান ছিল, তাই সংরক্ষিত ফাঁকা জায়গার সিগন্যাল করার জন্য যে কোনও পদ্ধতি কার্যকর ছিল। এই ( .bss ) এটি আটকে আছে।

.ডাটা বিভাগগুলি ফাঁকা নয় এমন জায়গার জন্য, বরং এতে (আপনার) সংজ্ঞায়িত মান থাকবে।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.