সি # তে স্ট্যাকের আকার কেন ঠিক 1 এমবি?


103

আজকের পিসিগুলিতে প্রচুর পরিমাণে শারীরিক র‌্যাম রয়েছে তবে তবুও, সি # এর স্ট্যাকের আকার 32-বিট প্রসেসের জন্য 1 এমবি এবং 64-বিট প্রসেসের জন্য 4 এমবি ( সি # তে স্ট্যাক ক্ষমতা ) capacity

সিএলআরতে স্ট্যাকের আকার এখনও এত সীমিত কেন?

এবং কেন এটি হ'ল 1 এমবি (4 এমবি) (এবং 2 এমবি বা 512 কেবি নয়)? কেন এই পরিমাণ ব্যবহার করার সিদ্ধান্ত নেওয়া হয়েছিল?

আমি এই সিদ্ধান্তের পিছনে বিবেচনা এবং কারণগুলিতে আগ্রহী ।


6
Bit৪ বিট প্রসেসের জন্য ডিফল্ট স্ট্যাকের আকার 4MB, এটি 32 বিট প্রসেসের জন্য 1MB। আপনি প্রধান থ্রেড স্ট্যাকের আকারটিকে তার পিই শিরোনামের মান পরিবর্তন করে সংশোধন করতে পারেন । আপনি Threadকনস্ট্রাক্টরের ডান ওভারলোড ব্যবহার করে স্ট্যাকের আকারটিও নির্দিষ্ট করতে পারেন । কিন্তু, এটি প্রশ্ন করে, আপনার আরও বড় স্ট্যাকের প্রয়োজন কেন?
যুবাল Itzchakov

4
ধন্যবাদ, সম্পাদিত। :) প্রশ্নটি কীভাবে বৃহত্তর স্ট্যাক আকার ব্যবহার করবেন তা নয়, তবে কেন স্ট্যাকের আকার 1 এমবি (4 এমবি) হওয়ার সিদ্ধান্ত নেওয়া হয়
নিকোলে কোস্তভ

8
কারণ প্রতিটি থ্রেড ডিফল্টরূপে এই স্ট্যাকের আকার পাবে এবং বেশিরভাগ থ্রেডের তেমন প্রয়োজন হয় না। আমি সবেমাত্র আমার পিসি বুট করেছি এবং সিস্টেম বর্তমানে 1200 থ্রেড চালায়। এখন গণিত করুন;)
লুকাস ট্রাজেনউইস্কি

4
@ লুকাসট্রিজনেউইস্কি কেবল তাই নয়, এটি অবশ্যই স্মৃতিতে সংক্রামক হতে হবে । স্ট্যাকের আকারটি বৃহত্তর নোট করুন, আপনার প্রক্রিয়াটি তার ভার্চুয়াল ঠিকানার জায়গায় কম থ্রেড তৈরি করতে পারে।
যুবাল Itzchakov

"উইন্ডোজ ৮.১" সম্পর্কে ঠিক "এমবি" সম্পর্কে নিশ্চিত নন: আমার উইন্ডোজ ৮.১-তে একটি। নেট কোর ৩.১ কনসোল অ্যাপ্লিকেশনটিতে 1572864বাইটস ডিফল্ট স্ট্যাক আকার রয়েছে (গেটকন্ট্রেন্টথ্রেডস্ট্যাকলিমিট উইন 32 এপি ব্যবহার করে পুনরুদ্ধার করা হয়েছে)। আমি স্ট্যাকওভারফ্লোএক্সপেশন ব্যতীত stackallocআনুমানিক 1500000বাইট করতে সক্ষম ।
জর্জ চাখিদেজে

উত্তর:


212

এখানে চিত্র বর্ণনা লিখুন

আপনি সেই লোকটির দিকে তাকিয়ে আছেন যে এই পছন্দটি করেছে। ডেভিড কাটার এবং তার দলটি একটি মেগাবাইট ডিফল্ট স্ট্যাক আকার হিসাবে বেছে নিয়েছিল। .NET বা C # এর সাথে কিছুই করার নেই, যখন তারা উইন্ডোজ এনটি তৈরি করেছিল তখন এটিকে পেরেক দেওয়া হয়েছিল। একটি প্রোগ্রামের EXE শিরোনাম বা ক্রিয়েটথ্রেড () উইনাপি কলটি স্ট্যাকের আকারটি স্পষ্টভাবে নির্দিষ্ট না করে, তখন একটি মেগাবাইট যা তা গ্রহণ করে। কোনটি সাধারণ উপায়, প্রায় কোনও প্রোগ্রামার আকার বাছাই করতে এটি OS এ ছেড়ে দেয়।

এই পছন্দটি সম্ভবত উইন্ডোজ এনটি ডিজাইনের প্রাক-তারিখগুলি, ইতিহাস এটি সম্পর্কে খুব ন্যূনতম। কাটলার এ সম্পর্কে একটি বই লিখলে ভাল হত, তবে তিনি কখনও লেখক হননি। কম্পিউটারগুলি যেভাবে কাজ করে সে সম্পর্কে তিনি অসাধারণ প্রভাবশালী। তাঁর প্রথম ওএস ডিজাইনটি আরএসএক্স -11 এম, ডিইসি কম্পিউটারের জন্য একটি 16-বিট অপারেটিং সিস্টেম (ডিজিটাল সরঞ্জাম কর্পোরেশন) ছিল। এটি গ্যারি কিল্ডালের সিপি / এমকে ব্যাপকভাবে প্রভাবিত করেছে, 8-বিট মাইক্রোপ্রসেসরের জন্য প্রথম শালীন ওএস। যা এমএস-ডসকে ব্যাপকভাবে প্রভাবিত করে।

তার পরবর্তী নকশাটি ছিল ভিএমএস, ভার্চুয়াল মেমরি সমর্থন সহ 32-বিট প্রসেসরের অপারেটিং সিস্টেম। খুব সফল. তার পরেরটি ডিসি কর্তৃক সস্তার পিসি হার্ডওয়্যারের সাথে প্রতিযোগিতা করতে না পারার সময় ভেঙে ফেলা শুরু করার সময় বাতিল হয়েছিল canceled কিউ মাইক্রোসফ্ট, তারা তাকে একটি প্রস্তাব দিয়েছিল সে অস্বীকার করতে পারে না। তাঁর অনেক সহকর্মীও এতে যোগ দিয়েছিলেন। তারা ভিএমএস ভি 2-তে কাজ করেছে, উইন্ডোজ এনটি হিসাবে বেশি পরিচিত। ডিসি এ নিয়ে বিচলিত হয়েছিলেন, টাকা নিষ্পত্তি করার জন্য হাত বদল করেছেন। ভিএমএস ইতিমধ্যে একটি মেগাবাইট বাছাই করেছে কিনা এমন কিছু যা আমি জানি না, আমি কেবলমাত্র আরএসএক্স -11কে যথেষ্ট ভাল জানি। এটা অসম্ভব।

যথেষ্ট ইতিহাস। একটি মেগাবাইট অনেক , একটি আসল থ্রেড খুব কমই কয়েক মুঠো কিলোবাইটের বেশি খায়। সুতরাং একটি মেগাবাইট আসলে অপ্রয়োজনীয়। এটি আপনার চাহিদা মতো পৃষ্ঠা ভার্চুয়াল মেমরি অপারেটিং সিস্টেমে যে ধরণের অপচয় করতে পারে তা হ'ল মেগাবাইট হ'ল ভার্চুয়াল মেমরি । প্রসেসরের কেবলমাত্র সংখ্যা, প্রতি 4096 বাইটের জন্য একটি করে। আপনি প্রকৃতপক্ষে শারীরিক স্মৃতি, মেশিনের র‌্যাম কখনই ব্যবহার করেন না যতক্ষণ না আপনি প্রকৃতপক্ষে এটিকে সম্বোধন করেন।

নেট নেট প্রোগ্রামে এটি অতিরিক্ত অতিরিক্ত because যা স্ট্যাকের পাশাপাশি স্ট্যাকিং স্ট্রিং এবং বাফার (অ্যারে) বড় স্ট্যাক ফ্রেম তৈরি করে। ম্যালওয়ার আক্রমণ আক্রমণকারী হিসাবে কুখ্যাত, একটি বাফার ওভারফ্লো ডেটা দিয়ে প্রোগ্রামটি ম্যানিপুলেট করতে পারে। উপায় নয়। নেট প্রোগ্রামগুলি কাজ করে, জিসি হিপগুলিতে স্ট্রিং এবং অ্যারে বরাদ্দ করা হয় এবং সূচীকরণ পরীক্ষা করা হয়। সি # দিয়ে স্ট্যাকের জন্য জায়গা বরাদ্দের একমাত্র উপায় হ'ল অনিরাপদ স্ট্যাকলোক কীওয়ার্ড।

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

সর্বশেষে তবে সর্বনিম্ন নয়, একটি। নেট প্রোগ্রাম স্ট্যাকের সাথে বেশ কিছু অনুৎপরমূলক কিছু করে। সিএলআর একটি থ্রেডের স্ট্যাক কমিট করবে । এটি একটি ব্যয়বহুল শব্দ যার অর্থ এটি কেবল স্ট্যাকের আকার সংরক্ষণ করে না, এটিও নিশ্চিত করে যে অপারেটিং সিস্টেমের পেজিং ফাইলে স্থানটি সংরক্ষিত রয়েছে যাতে প্রয়োজনে স্ট্যাকটি সর্বদা সরিয়ে নেওয়া যায়। প্রতিশ্রুতিবদ্ধতা ব্যর্থতা মারাত্মক ত্রুটি এবং একটি প্রোগ্রামকে নিঃশর্তভাবে বন্ধ করে দেয়। এটি কেবলমাত্র খুব অল্প র‌্যামযুক্ত মেশিনে ঘটে যা পুরোপুরি অনেকগুলি প্রক্রিয়া চালায়, প্রোগ্রামগুলি মারা যেতে শুরু করার আগে এই জাতীয় মেশিনটি গুড় হয়ে যাবে। একটি সম্ভাব্য সমস্যা 15+ বছর আগে, আজকের নয়। প্রোগ্রামাররা যারা এফ 1 রেস-কারের মতো কাজ করার জন্য তাদের প্রোগ্রামটি সুর করে <disableCommitThreadStack>তাদের .config ফাইলে উপাদানটি ব্যবহার করে ।

Fww, ক্যাটলার অপারেটিং সিস্টেম ডিজাইন করা বন্ধ করেনি। সেই ছবিটি তিনি আজুরে কাজ করার সময় তৈরি হয়েছিল।


আপডেট করুন, আমি লক্ষ করেছি যে। নেট আর স্ট্যাকটি কমিট করে না। কখন বা কেন এই ঘটনাটি ঘটেছিল ঠিক তা নিশ্চিত নয়, আমি যাচাই করেছিলাম এটি অনেক দীর্ঘ হয়েছে। আমি অনুমান করছি এই নকশার পরিবর্তনটি প্রায় কোথাও কোথাও ঘটেছিল। নেট 4.5। খুব বুদ্ধিমান পরিবর্তন।


4
আপনার মন্তব্যে আর্ট করুন The only way to allocate space on the stack with C# is with the unsafe stackalloc keyword.- স্থানীয় ভেরিয়েবলগুলি যেমন কোনও intপদ্ধতির অভ্যন্তরে কোনও ঘোষিত স্ট্যাকের উপরে সংরক্ষণ করা হয় না? আমি মনে করি তারা।
আরবিটি

4
ঠিক আছে. এখন আমি বুঝতে পেরেছি যে কোনও ফাংশনের স্থানীয় ভেরিয়েবলের জন্য স্ট্যাক-ফ্রেম কেবল স্টোরেজ পছন্দ নয়। এটা তোলে যাবে যদিও হিসাবে আপনার বুলেট পয়েন্ট এক প্রস্তাব একটি স্ট্যাক ফ্রেম উপর সংরক্ষণ করা হয়। খুব জ্ঞানদীপ্ত হ্যানস। এই জাতীয় অন্তর্দৃষ্টিপূর্ণ পোস্ট লেখার জন্য আপনাকে যথেষ্ট ধন্যবাদ জানাতে পারি না। সত্যিই অহেতুক জটিলতা এড়াতে সাধারণভাবে প্রোগ্রামিংয়ের পক্ষে সত্যই স্ট্যাক একটি বড় বিমূর্ততা।
আরবিটি

@ હંস খুব বিস্তারিত বর্ণনা। আমি কেবল ভাবছিলাম যে maxStackSizeকোনও থ্রেডের ন্যূনতম সম্ভাব্য মান কী? আমি এটি [এমএসডিএন] (এমএসডিএন.মাইক্রোসফটকম /en-us/library/5cykbwz4(v=vs.110).aspx ) তে খুঁজে পাইনি । আপনার মন্তব্যের ভিত্তিতে মনে হয় স্ট্যাকের ব্যবহার নিখুঁত ন্যূনতম এবং আমি সর্বাধিক সম্ভাব্য থ্রেডগুলিকে সামঞ্জস্য করতে সবচেয়ে ছোট মানটি ব্যবহার করতে পারি। ধন্যবাদ
এমকেআর

4
@ কেএফএল: আপনি আপনার প্রশ্নের উত্তর চেষ্টা করে খুব সহজেই দিতে পারবেন!
এরিক লিপার্ট

4
যদি ডিফল্ট আচরণটি আর স্ট্যাকের প্রতিশ্রুতি না দেয় তবে এই মার্কডাউন ফাইলটি github.com/dotnet/docs/blob/master/docs/framework/…
জন স্টিভেন

5

ডিফল্ট সংরক্ষিত স্ট্যাকের আকারটি লিঙ্কার দ্বারা নির্দিষ্ট করা হয় এবং এটি লিংক সময়ে পিই মান পরিবর্তন করার মাধ্যমে বা উইনাপিআই ফাংশনের dwStackSizeজন্য প্যারামিটার নির্দিষ্ট করে একটি পৃথক থ্রেডের মাধ্যমে বিকাশকারীদের দ্বারা ওভাররাইড করা যেতে পারে CreateThread

আপনি যদি প্রাথমিক স্ট্যাকের আকারটি ডিফল্ট স্ট্যাকের আকারের চেয়ে বড় বা সমান করে কোনও থ্রেড তৈরি করেন তবে এটি 1 এমবি এর নিকটতম একাধিক পর্যন্ত গোল হয়।

মানটি 32-বিট প্রক্রিয়াগুলির জন্য 1 এমবি এবং 64-বিটের জন্য 4 এমবি সমান কেন? আমি মনে করি আপনার বিকাশকারীদের জিজ্ঞাসা করা উচিত, যারা উইন্ডোজ ডিজাইন করেছিলেন, বা তাদের কেউ আপনার প্রশ্নের উত্তর না দেওয়া পর্যন্ত অপেক্ষা করবেন।

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

তবে এই সময়ে আমি এমএসডিএন, মার্কস এবং রেমন্ডের ব্লগগুলি ব্যবহার করে মাইক্রোসফ্ট কেন এই মানগুলি বেছে নিয়েছে তার কয়েকটি সম্ভাব্য কারণ ব্যাখ্যা করার চেষ্টা করব।

ডিফল্টদের এই মানগুলি সম্ভবত কারণ প্রথমদিকে পিসি ধীর ছিল এবং স্ট্যাকের মেমরি বরাদ্দকরণ হিপগুলিতে মেমরি বরাদ্দকরণের চেয়ে অনেক দ্রুত ছিল। এবং যেহেতু স্ট্যাক বরাদ্দগুলি সেগুলি খুব কম ব্যবহৃত হত, তবে এটির জন্য বৃহত্তর স্ট্যাক আকার প্রয়োজন।

সুতরাং মানটি ছিল বেশিরভাগ অ্যাপ্লিকেশনের জন্য সর্বোত্তম সংরক্ষিত স্ট্যাক আকার। এটি সর্বোত্তম কারণ কারণ কলিং ফাংশনগুলিতে স্ট্রাকচারগুলি পাস করার জন্য প্রচুর নেস্টেড কল করতে এবং স্ট্যাকটিতে মেমরি বরাদ্দ করতে দেয়। একই সাথে এটি প্রচুর থ্রেড তৈরি করতে দেয়।

আজকাল এই মানগুলি বেশিরভাগ পশ্চাদপটে সামঞ্জস্যের জন্য ব্যবহৃত হয়, কারণ উইনএপিআই ফাংশনগুলির পরামিতি হিসাবে পাস করা কাঠামো এখনও স্ট্যাকের জন্য বরাদ্দ করা হয়। তবে আপনি যদি স্ট্যাক বরাদ্দ ব্যবহার না করে থাকেন তবে থ্রেডের স্ট্যাকের ব্যবহারটি ডিফল্ট 1 এমবি থেকে উল্লেখযোগ্যভাবে কম হবে এবং হান্স পাসেন্টের উল্লিখিত হিসাবে এটি অপ্রয়োজনীয়। এবং এটি প্রতিরোধের জন্য ওএস কেবল স্ট্যাকের প্রথম পৃষ্ঠায় প্রতিশ্রুতি দেয় (4 কেবি), যদি অন্যটি অ্যাপ্লিকেশনটির পিই শিরোনামে নির্দিষ্ট না করা থাকে। অন্যান্য পৃষ্ঠাগুলি চাহিদা অনুসারে বরাদ্দ করা হয়।

কিছু অ্যাপ্লিকেশনগুলি সংরক্ষিত ঠিকানার জায়গাকে ওভাররাইড করে এবং মেমরির ব্যবহারটি সর্বোত্তম করে তুলতে প্রতিশ্রুতিবদ্ধ। উদাহরণস্বরূপ, আইআইএস নেটিভ প্রক্রিয়াটির থ্রেডের সর্বাধিক স্ট্যাকের আকার 256 কেবি ( KB932909 )। এবং এই ডিফল্ট মান হ্রাস মাইক্রোসফ্ট দ্বারা প্রস্তাবিত :

থ্রেড বা ফাইবারকে নির্ভরযোগ্যভাবে চালনার জন্য প্রয়োজনীয় স্ট্যাকটি যতটা সম্ভব ছোট ছোট স্ট্যাকের আকারটি বেছে নেওয়া এবং প্রতিশ্রুতি দেওয়া ভাল। স্ট্যাকের জন্য সংরক্ষিত প্রতিটি পৃষ্ঠা অন্য কোনও উদ্দেশ্যে ব্যবহার করা যাবে না।

সূত্র:

  1. থ্রেড স্ট্যাকের আকার (মাইক্রোসফ্ট ডক্স)
  2. উইন্ডোজ সীমাবদ্ধতা পুশিং: প্রক্রিয়া এবং থ্রেডস (মার্ক রাশিনোভিচ)
  3. ডিফল্টরূপে, স্থানীয় আইআইএস প্রসেসে তৈরি হওয়া থ্রেডের সর্বাধিক স্ট্যাক আকার 256 কেবি (KB932909) হয়

যদি আমি বড় স্ট্যাক আকার চাই তবে আমি এটি সেট করতে পারি ( atalasoft.com/cs/blogs/rickm/archive/2008/04/22/… )। আমি এই সিদ্ধান্তের পিছনে বিবেচনা এবং কারণ জানতে চাই।
নিকলে কোস্তভ

4
ঠিক আছে. এখন আমি আপনাকে বুঝতে পেরেছি :) ডিফল্ট স্ট্যাকের আকারটি সর্বোত্তম হওয়া উচিত (@ লুকাশ ট্রাজেনউইস্কি মন্তব্য দেখুন) এবং বরাদ্দ গ্রানুলারিটির নিকটতম একাধিককে গোল করা উচিত। নির্দিষ্ট স্ট্যাকের আকারটি যদি ডিফল্ট স্ট্যাকের আকারের চেয়ে বড় হয় তবে এটি 1MB এর নিকটতম একাধিক পর্যন্ত গোল হয় ed সুতরাং মাইক্রোসফ্ট সমস্ত ব্যবহারকারী মোড অ্যাপ্লিকেশনগুলির জন্য এই আকারগুলি ডিফল্ট স্ট্যাক আকার হিসাবে বেছে নিয়েছে। এবং অন্য কোনও কারণ নেই।
ইয়াহ ডেডফল

কোন সূত্র? কোন ডকুমেন্টেশন? :)
নিকলে কোস্তভ

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