লিনাক্স, উইন্ডোজ দৃষ্টিকোণ থেকে ব্যাখ্যা করুন?
আমি সি # তে প্রোগ্রামিং করছি, এই দুটি পদটি কোনও পার্থক্য আনবে। উদাহরণস্বরূপ এবং এর সাথে আপনি যতটা পারেন পোস্ট করুন ...
ধন্যবাদ
লিনাক্স, উইন্ডোজ দৃষ্টিকোণ থেকে ব্যাখ্যা করুন?
আমি সি # তে প্রোগ্রামিং করছি, এই দুটি পদটি কোনও পার্থক্য আনবে। উদাহরণস্বরূপ এবং এর সাথে আপনি যতটা পারেন পোস্ট করুন ...
ধন্যবাদ
উত্তর:
উইন্ডোজের জন্য, সমালোচনা বিভাগগুলি মুটেক্সেসের চেয়ে হালকা ওজনযুক্ত।
প্রক্রিয়াগুলির মধ্যে মিটেক্সগুলি ভাগ করা যায় তবে সর্বদা কার্নেলের কাছে একটি সিস্টেম কল আসে যার কিছু ওভারহেড থাকে।
সমালোচনামূলক বিভাগগুলি কেবলমাত্র একটি প্রক্রিয়ার মধ্যেই ব্যবহার করা যেতে পারে, তবে সুবিধা রয়েছে যে তারা কেবল বিতর্কের ক্ষেত্রে কার্নেল মোডে স্যুইচ করে - অযৌক্তিক অর্জনগুলি, যা সাধারণ ক্ষেত্রে হওয়া উচিত, এটি অবিশ্বাস্যভাবে দ্রুত fast বিতর্ক ক্ষেত্রে, তারা কিছু সিঙ্ক্রোনাইজেশন আদিম (যেমন কোনও ইভেন্ট বা সেমোফোরের মতো) অপেক্ষা করতে কার্নেলটিতে প্রবেশ করে।
আমি একটি দ্রুত নমুনা অ্যাপ্লিকেশন লিখেছি যা তাদের দুজনের মধ্যে সময়ের তুলনা করে। আমার সিস্টেমে ১,০০,০০০ অপরিবর্তিত অর্জন এবং প্রকাশের জন্য, একটি মিটেক্স এক সেকেন্ডের বেশি সময় নেয়। একটি সমালোচনা বিভাগটি 1,000,000 অর্জনের জন্য ms 50 এমএস নেয়।
এখানে পরীক্ষার কোডটি রয়েছে, আমি এটি চালিয়ে গিয়েছিলাম এবং মিটেক্স প্রথম বা দ্বিতীয় হয় তবে অনুরূপ ফলাফল পেয়েছি, সুতরাং আমরা অন্য কোনও প্রভাব দেখছি না।
HANDLE mutex = CreateMutex(NULL, FALSE, NULL);
CRITICAL_SECTION critSec;
InitializeCriticalSection(&critSec);
LARGE_INTEGER freq;
QueryPerformanceFrequency(&freq);
LARGE_INTEGER start, end;
// Force code into memory, so we don't see any effects of paging.
EnterCriticalSection(&critSec);
LeaveCriticalSection(&critSec);
QueryPerformanceCounter(&start);
for (int i = 0; i < 1000000; i++)
{
EnterCriticalSection(&critSec);
LeaveCriticalSection(&critSec);
}
QueryPerformanceCounter(&end);
int totalTimeCS = (int)((end.QuadPart - start.QuadPart) * 1000 / freq.QuadPart);
// Force code into memory, so we don't see any effects of paging.
WaitForSingleObject(mutex, INFINITE);
ReleaseMutex(mutex);
QueryPerformanceCounter(&start);
for (int i = 0; i < 1000000; i++)
{
WaitForSingleObject(mutex, INFINITE);
ReleaseMutex(mutex);
}
QueryPerformanceCounter(&end);
int totalTime = (int)((end.QuadPart - start.QuadPart) * 1000 / freq.QuadPart);
printf("Mutex: %d CritSec: %d\n", totalTime, totalTimeCS);
একটি তাত্ত্বিক দৃষ্টিকোণ থেকে, একটি সমালোচনা বিভাগ কোডের একটি অংশ যা একসাথে একাধিক থ্রেড দ্বারা চালিত হওয়া উচিত নয় কারণ কোডটি ভাগ করে নেওয়া সংস্থানগুলিকে অ্যাক্সেস করে।
একটি মিউটেক্স একটি অ্যালগরিদম (এবং কখনও কখনও ডেটা স্ট্রাকচারের নাম) যা সমালোচনা বিভাগগুলি রক্ষার জন্য ব্যবহৃত হয়।
Semaphores এবং মনিটর একটি mutex সাধারণ বাস্তবায়নের হয়।
অনুশীলনে উইন্ডোতে অনেকগুলি মুটিেক্স বাস্তবায়নযোগ্য। তারা তাদের লকিং স্তর, তাদের স্কোপস, তাদের ব্যয় এবং বিভিন্ন স্তরের মতবিরোধের অধীনে তাদের কার্যকারিতা দ্বারা প্রয়োগের ফলাফল হিসাবে পৃথক হয়। সিএলআর অভ্যন্তরে দেখুন - বিভিন্ন মুটেক্স বাস্তবায়নের ব্যয়গুলির একটি লেখচিত্রের জন্য স্কেলাবিলিটির জন্য একত্রে ব্যবহার করে rency
উপলভ্য সিঙ্ক্রোনাইজেশন আদিম।
lock(object)
বক্তব্য ব্যবহার বাস্তবায়িত হয় Monitor
- দেখুন দুটিই MSDN রেফারেন্সের জন্য।
গত বছরগুলিতে নন-ব্লকিং সিঙ্ক্রোনাইজেশন নিয়ে অনেক গবেষণা করা হয় । লক্ষ্যটি হ'ল লক-ফ্রি বা অপেক্ষা-মুক্ত উপায়ে অ্যালগরিদমগুলি কার্যকর করা। এই জাতীয় অ্যালগরিদমে একটি প্রক্রিয়া অন্যান্য প্রক্রিয়াগুলি তাদের কাজ শেষ করতে সহায়তা করে যাতে প্রক্রিয়াটি শেষ পর্যন্ত তার কাজ শেষ করতে পারে। ফলস্বরূপ কোনও প্রক্রিয়া তার কাজ শেষ করতে পারে এমনকি যখন অন্যান্য প্রক্রিয়াগুলি কিছু কাজ করার চেষ্টা করেছিল, স্তব্ধ হয়ে যায়। তালিকাগুলি ব্যবহার করার পরে, তারা তাদের লকগুলি প্রকাশ করবে না এবং অন্যান্য প্রক্রিয়াগুলি অব্যাহত রাখতে বাধা দেবে না।
অন্যান্য উত্তরের পাশাপাশি, নিম্নলিখিত বিবরণগুলি উইন্ডোজের সমালোচনামূলক বিভাগগুলির জন্য সুনির্দিষ্ট:
InterlockedCompareExchange
অপারেশনের মতোই সহজলিনাক্সে, আমি মনে করি যে তাদের একটি "স্পিন লক" রয়েছে যা একটি স্পিন গণনা সহ সমালোচনামূলক বিভাগে অনুরূপ উদ্দেশ্যে কাজ করে।
ক্রিটিকাল বিভাগ এবং মুটেক্স অপারেটিং সিস্টেম নির্দিষ্ট নয়, তাদের মাল্টিথ্রেডিং / মাল্টিপ্রসেসিংয়ের ধারণা।
জটিল অংশ কোডের একটি অংশ যা কোনও নির্দিষ্ট সময়ে কেবল এটির দ্বারা চালিত হওয়া আবশ্যক (উদাহরণস্বরূপ, একই সাথে 5 টি থ্রেড চলছে এবং "সমালোচনা_বিজ্ঞান" নামে একটি ফাংশন রয়েছে যা একটি অ্যারে আপডেট করে ... আপনি সমস্ত 5 টি থ্রেড চান না অ্যারে একবারে আপডেট করা হচ্ছে So সুতরাং যখন প্রোগ্রামটি ক্রিয়াকলিট_সেকশন_ফাংশন () চলছে, অন্য থ্রেডগুলির কোনওটিই তাদের সমালোচনামূলক_সংশোধন_ফানশনটি চালাতে হবে না।
মিউটেক্স * মুটেক্স সমালোচনা বিভাগের কোডটি প্রয়োগ করার একটি উপায় (এটি একটি টোকেনের মতো মনে করুন ... সমালোচনা_কেন্দ্র_কোড চালানোর জন্য থ্রেডটির অবশ্যই এটির অধিকার থাকতে হবে)
একটি মিউটেক্স এমন একটি বস্তু যা কোনও থ্রেড অর্জন করতে পারে, এটি অন্য থ্রেডগুলি অর্জন থেকে বাধা দেয়। এটি পরামর্শমূলক, বাধ্যতামূলক নয়; একটি থ্রেড মিটেক্স প্রতিনিধিত্ব করে এমন সংস্থানটি অর্জন না করে ব্যবহার করতে পারে।
একটি সমালোচনা বিভাগটি এমন একটি কোডের দৈর্ঘ্য যা অপারেটিং সিস্টেমের দ্বারা বাধা না দেওয়ার নিশ্চয়তা দেয়। সিউডো-কোডে এটি এমন হবে:
StartCriticalSection();
DoSomethingImportant();
DoSomeOtherImportantThing();
EndCriticalSection();
লিনাক্সের সমালোচনামূলক নির্বাচনের সমান 'দ্রুত' উইন্ডোজ একটি ফিউটেক্স হবে , যা দ্রুত ব্যবহারকারীর স্পেস মিটেক্সের জন্য দাঁড়িয়ে। একটি ফিউটেক্স এবং মিউটেক্সের মধ্যে পার্থক্য হ'ল ফিউটেক্সের সাহায্যে কার্নেল কেবল তখনই যুক্ত হয় যখন সালিশি প্রয়োজন হয়, সুতরাং প্রতিবার পারমাণবিক কাউন্টারটি সংশোধন করার পরে আপনি কার্নেলের সাথে কথা বলার ওভারহেড সংরক্ষণ করুন। যে .. একটি গুরুত্বপূর্ণ সংরক্ষণ করতে পারেন কিছু অ্যাপ্লিকেশনগুলিতে লক আলোচনার পরিমাণ সময় ।
কোনও মিউটেক্স ভাগ করার জন্য আপনি নিযুক্ত করার উপায়গুলি ব্যবহার করে একটি ফুটেক্সও প্রক্রিয়াগুলির মধ্যে ভাগ করা যায়।
দুর্ভাগ্যক্রমে, futexes (পিডিএফ) বাস্তবায়নের জন্য খুব জটিল হতে পারে । (2018 আপডেট, তারা 2009 এর মতো ভয়ঙ্কর নয়))
এর বাইরেও, উভয় প্ল্যাটফর্ম জুড়েই এটি প্রায় একই। আপনি এমনভাবে ভাগ করা কাঠামোর কাছে পারমাণবিক, টোকেন চালিত আপডেটগুলি তৈরি করছেন (আশা করি) অনাহার সৃষ্টি না করে। যা থেকে যায় তা কেবল এটি সম্পাদন করার পদ্ধতি।
কেবল আমার 2 সেন্ট যোগ করার জন্য, সমালোচনামূলক বিভাগগুলি একটি কাঠামো হিসাবে সংজ্ঞায়িত করা হয় এবং সেগুলির উপর ক্রিয়াকলাপগুলি ব্যবহারকারী-মোড প্রসঙ্গে উপস্থাপিত হয়।
ntdll! _RTL_CRITICAL_SECTION + 0x000 ডিবাগইনফো: Ptr32 _RTL_CRITICAL_SECTION_DEBUG + 0x004 লককাউন্ট: Int4B + 0x008 পুনরাবৃত্তি অ্যাকাউন্ট: Int4B + 0x00c মালিকানাধীন: Ptr32 শূন্য + 0x010 লকসেমাপোর: পিটিআর 32 শূন্য + 0x014 স্পিনকাউন্ট: Uint4B
উইন্ডোজ অবজেক্ট ডিরেক্টরিতে মুটেক্স হ'ল কার্নেল অবজেক্টস (এক্সমুটান্টজেক্টটাইপ)। মুটেক্স অপারেশনগুলি বেশিরভাগ কার্নেল-মোডে প্রয়োগ করা হয়। উদাহরণস্বরূপ, একটি মিউেক্স তৈরি করার সময়, আপনি কার্নেলের মধ্যে nt! NtCreateMutant কল করবেন।
মাইকেল এর দুর্দান্ত উত্তর। আমি সি ++ 11-এ প্রবর্তিত মুটেক্স ক্লাসের জন্য একটি তৃতীয় পরীক্ষা যুক্ত করেছি। ফলাফলটি কিছুটা আকর্ষণীয় এবং এখনও একক প্রক্রিয়ার জন্য CRITICAL_SECTION অবজেক্টগুলির তার মূল সমর্থনটি সমর্থন করে।
mutex m;
HANDLE mutex = CreateMutex(NULL, FALSE, NULL);
CRITICAL_SECTION critSec;
InitializeCriticalSection(&critSec);
LARGE_INTEGER freq;
QueryPerformanceFrequency(&freq);
LARGE_INTEGER start, end;
// Force code into memory, so we don't see any effects of paging.
EnterCriticalSection(&critSec);
LeaveCriticalSection(&critSec);
QueryPerformanceCounter(&start);
for (int i = 0; i < 1000000; i++)
{
EnterCriticalSection(&critSec);
LeaveCriticalSection(&critSec);
}
QueryPerformanceCounter(&end);
int totalTimeCS = (int)((end.QuadPart - start.QuadPart) * 1000 / freq.QuadPart);
// Force code into memory, so we don't see any effects of paging.
WaitForSingleObject(mutex, INFINITE);
ReleaseMutex(mutex);
QueryPerformanceCounter(&start);
for (int i = 0; i < 1000000; i++)
{
WaitForSingleObject(mutex, INFINITE);
ReleaseMutex(mutex);
}
QueryPerformanceCounter(&end);
int totalTime = (int)((end.QuadPart - start.QuadPart) * 1000 / freq.QuadPart);
// Force code into memory, so we don't see any effects of paging.
m.lock();
m.unlock();
QueryPerformanceCounter(&start);
for (int i = 0; i < 1000000; i++)
{
m.lock();
m.unlock();
}
QueryPerformanceCounter(&end);
int totalTimeM = (int)((end.QuadPart - start.QuadPart) * 1000 / freq.QuadPart);
printf("C++ Mutex: %d Mutex: %d CritSec: %d\n", totalTimeM, totalTime, totalTimeCS);
আমার ফলাফলগুলি ছিল 217, 473, এবং 19 (নোট করুন যে আমার দু'বারের সময়ের অনুপাতটি মাইকের সাথে প্রায় তুলনামূলক, তবে আমার মেশিন তার চেয়ে কমপক্ষে চার বছর কম বয়সী), সুতরাং আপনি 2009 এবং 2013 এর মধ্যে বর্ধিত গতির প্রমাণ দেখতে পাচ্ছেন , যখন এক্সপিএস-8700 বেরিয়েছে)। নতুন মিউটেক্স ক্লাসটি উইন্ডোজ মিটেক্সের দ্বিগুণ গতিযুক্ত, তবে এখনও উইন্ডোজ ক্রিটিক্যাল_সেকশন বস্তুর গতি দশমের চেয়ে কম। মনে রাখবেন যে আমি কেবল অ-পুনরাবৃত্ত মিটেক্স পরীক্ষা করেছি। CRITICAL_SECTION অবজেক্টগুলি পুনরাবৃত্ত হয় (একটি থ্রেড তাদের বারবার প্রবেশ করতে পারে, তবে এটি একই সংখ্যার বার ছেড়ে যায়)।
এটির প্রকৃত পরামিতিগুলি কেবল যদি ব্যবহার করে তবে এসি ফাংশনগুলিকে রিেন্টেন্ট বলা হয়।
একই সময়ে একাধিক থ্রেড দ্বারা প্রেরণকারী ফাংশনগুলি কল করা যেতে পারে।
প্রেরণকারী কার্যের উদাহরণ:
int reentrant_function (int a, int b)
{
int c;
c = a + b;
return c;
}
অ-প্রেরণকারী ফাংশনের উদাহরণ:
int result;
void non_reentrant_function (int a, int b)
{
int c;
c = a + b;
result = c;
}
সি স্ট্যান্ডার্ড লাইব্রেরি স্ট্রোক () প্রেরণকারী নয় এবং একই সাথে 2 বা ততোধিক থ্রেড ব্যবহার করতে পারে না।
কিছু প্ল্যাটফর্ম এসডিকে'র স্ট্র্টোক () নামক আর্ট্রোক-র () নামক সংস্করণটি আসে;
এনরিকো মিগলিওর