اجعل رورو44 صفحتك الرئيسية | احفظ رورو44 في مفضلتك | ارسل رورو44 إلى صديقك | أعلن على رورو44 | English Interface

 

 

 

شات خدمات مسجات جوال بطاقات رسائل حب دليل مواقع شات خليجي  دردشة منتديات حسناء الفارس عالم الرومانسية

مواقع سعودية | مواقع كويتية | مواقع بحرينية | مواقع قطرية | مواقع عمانية | مواقع يمنية | مواقع عراقية | مواقع اماراتية

 
    دروس في لغات البرمجة  الدلفي - Delphi
 

 

إنجاز وحدة DLL فى لغة دلفي



طريقة إنجاز وحدة DLL   فى لغة الدلفي

 

 مقدمة:

 

وحدة DLL   تختلف عن بقية وحدات دلفى، سنرى فى هذا الدرس أوجه الإختلاف وما هى الأمور التى يجب مراعاتها عند بناء هذه الوحدة، وأنواع الدوال والإجراءات فى DLL   ،إضافة إلى موضوع مهم وهو العلاقة بين DLL   وبعض متغيرات النظام Windows    العامة .

 

 تحليل وحدة DLL    :

 

كأي وحدة من وحدات Pascal   الأخرى فإن DLL Unit   لها شكلها المستقل ، ولدراسة الشكل العام لهذه الوحدة لنستخدم المثال التالي :

 

library TestDLL;
uses
  SysUtils,
  Classes,
  Forms,
  Windows;
procedure SayHello(AForm : TForm);
begin
  MessageBox(AForm.Handle, `Hello From a DLL!',
    `DLL Message Box', MB_OK or MB_ICONEXCLAMATION);
end;
exports
  SayHello;
begin
end.

  1-الكلمة المحجوزة Library   : تستخدم فى بداية الوحدة ، ويليها إسم الوحدة وهو يخضع لاختيارك الشخصي هنا (TestDLL  ) أو أي تسمية أخرى تخضع لشروط التسمية فى Pascal   .

 

2-الكلمة المحجوزة Uses  : تأتي هذه الكلمة متبوعة بأسماء الوحدات المراد تضمينها فى هذه الوحدة.

 

3-الدوال والإجراءات : قائمة بتعريفات الدوال والإجراءات التى تحتويها وحدة DLL   .

 

4-الكلمة المحجوزة Exports  : وتأتي متبوعة بالدوال والإجراءات المصدرة (من بين الدوال والإجراءات التى سبق تعريفها) إلى خارج وحدة DLL   .

 

5-الكلمتان المحجوزتان Begin   و End   : يوضع بينهما كتلة الكود الرئيسي لل DLL   ، حيث تضع هنا أي كود تحتاج لتنفيذه عند لحظة تحميل DLL   ، فى معظم الحالات أنت لا تحتاج لأي كود استهلالي وتكتفي بالدوال والإجراءات وبالتالى تبقى هذه الكتلة فارغة .

 

ملاحظة: أستخدم كلمة تعريف دالة أو إجراء للتعبير عن جسم الدالة أو الإجراء كاملاً ، بينما أستخدم تصريح دالة أو إجراء للتعبير عن ترويستهما فقط ،كما سأستخدم التعبير كتلة الكود الرئيسى للتعبير عن كتلة الكود بين Begin و End   في ال DLL   .

 

 أساسيات كتابة DLL   :

 

إن كتابة DLL   ليست عملية صعبة ويمكن اعتبارها كبرمجة Object Pascal   المعتادة ، لكن هناك عدة أمور هامة يجب عليك إدراكها ،بعدها يمكنك كتابة أول DLL   .

 

 الدوال والإجراءات فى DLL   : تنقسم الدوال (Functions  ) والإجراءات (Procedures  ) فى DLL   إلى قسمين :

 

1-دوال وإجراءات محلية لل DLL   .

 

2-دوال وإجراءات مصدرة إلى خارج ال DLL   .

 

أولاً/ الدوال والإجراءات المحلية:

 

هى الدوال والإجراءات التى سيتم استدعاؤها داخل ال DLL   نفسه . هى لا تتطلب معالجة خاصة عند إنجازها ،كل ماعليك فعله هو تعريف هذه الدوال والإجراءات كأي دالة أو إجراء آخر فى Object Pascal   .

 

ويتم استدعاؤها من قبل دوال وإجراءات أخرى داخل ال DLL   ، لكن لا يمكن استدعاؤها من خارج ال DLL   ، بكلمات أخرى التطبيقات المستدعية لا يمكنها الوصول إلى هذه الدوال والإجراءات وهى تكون Private   لل DLL   .

 

ملاحظة: سيتكرر استخدامي للتعبير التطبيقات المستدعية  (Calling Applications  ) وأقصد به تلك التطبيقات التى تستدعى دالة أو إجراء من دوال وإجراءات ال DLL   .

 

تلميح:إضافة للدوال والإجراءات فإن DLL    يمكن أن يحوى بيانات عامة  Global Data   تستطيع كل الإجراءات والدوال الموجودة فى DLL   الوصول إليها.

 

 فى Windows 16_bit   فإن البيانات العامة فى DLL   مشتركة فيما بين كل مكونات DLL،فإذا قام برنامج ما بتغيير قيمة المتغير العام X   مثلا إلى 100 فإن X   سيمتلك القيمة 100 بالنسبة لكل التطبيقات التى تستخدم هذا ال   DLL  

فى Windows 32_bit   الأمر مختلف حيث أن كل إجراء يصل إلى DLL     يُبنى له نسخة مستقلة من البيانات العامة .

 

 

ثانياً/الدوال والإجراءات المصدَّرة من DLL   :

 

النوع الآخر من الإجراءات والدوال هو النوع الذي يمكن استدعاؤه من خارج DLL   ،وهى تمثل الإجراءات والدوال المبنية Public   بواسطة تصديرها من DLL   حيث يمكن أن تستدعى بواسطة الدوال والإجراءات الموجودة فى DLL   أو بواسطة تطبيقات خارج DLL   أو بواسطة دوال وإجراءات موجودة فى DLLs   الأخرى.

 

ولتصدير الدوال والإجراءات تستخدم الكلمة المحجوزة Exports   وهذا هو الفرق بينها وبين الدوال والإجراءات المحلية لل DLL   .

 

 الكلمة المحجوزة Exports   :

 

كما قلنا سابقا لتصدّر دالة أو إجراء إلى خارج DLL   فإنك تستخدم الكلمة المحجوزة Exports   ، أنظر إلى مثالنا في بداية الدرس ،لاحظ كيف قمنا بتعريف الدالة SayHello    على أنها مصدّرة ،وبالتالى يمكن استدعاؤها من أي تطبيق دلفي آخر .

 

ولتصدير دالة أو إجراء هناك طريقتين :

 

1-التصدير باستخدام الإسم : هى الطريقة الإعتيادية لتصدير الدالة أو الإجراء من DLL   مثلاً :

 

exports
  SayHello,
  DoSomething,
  DoSomethingReallyCool;

  هذه الدوال صدّرت باستخدام إسم التعريف لها وهو الإسم الوارد فى تعريف الدالة السابق ،ونلاحظ أن جزء Exports   له نفس ( Syntax   ) قاعدة القائمة Uses   حيث أنه فصل بين المعرفات باستخدام فاصلة عادية ووضعت فاصلة منقوطة بعد آخر معرّف في القائمة .

 

 2-التصدير باستخدام قيمة الترتيب : يمكن أيضاً تصدير الدوال والإجراءات بواسطة قيمة ترتيبها ،وتستخدم لذلك الكلمة المحجوزة Index   مثال :

 

exports
  SayHello index 1,
  DoSomething index 2,
  DoSomethingReallyCool index 3;
 عندما تقوم باستيراد الدالة فى التطبيق المستدعى عليك تحديد قيمة الترتيب 

عندما تقوم باستيراد الدالة فى التطبيق المستدعى عليك تحديد قيمة الترتيب (Ordinal number)

 فى معظم الحالات يتم استخدام الإسم لتصدير الدالة.

 

 ملاحظة: فى حالة عدم تحديدك لقيمة ترتيب الدوال والإجراءات الموجودة فى جزء Exports   فإن دلفى تقوم أوتوماتيكياً بإسناد قيمة ترتيب لكل إجراء أو دالة فى هذا الجزء ،لكن استخدامك Index   يوفر لك تحكماً فى قيمة Ordinal Number   التى تضعها حسب رغبتك.

 

تصدير الدالة أو الإجراء  هو نصف القصة ،بقي النصف الآخر وهو طريقة استيراد الدالة أو الإجراء من قبل التطبيق المستدعى (سنخوض هذا القسم فى الدرس القادم) وسنعرج هنا على بعض المواضيع التى نحتاج لفهمها قبل دراسة القسم المذكور. 

 العلاقة بين DLLs   ومتغيرات النظام Windows   :

هذا الجانب يعد مهماً  لكنه معقد بعض الشيء ، للنظام Windows   عدد من المتغيرات العامة  المتعلقة بDLL   والتى يمكن رؤيتها من تطبيقك أو من DLL   وهي:

  1-Islibrary  : يحدد هذا المتغير ما إذا كان كودك ينفذ في DLL   أو فى التطبيق ،وقيمته دائماً False   فى التطبيق و True    فى DLL   .

 

 2-HInstance  : يحتوى قيمة (Instance handle  ) ممسك DLL   ،الممسك هو أحد أنواع البيانات المعرفة فى الوحدة Windows   وهى تنفذ كأرقام ،لكنها لا تستعمل كذلك ولكنها إشارة إلى بنية بيانات داخلية للنظام ،مثلاً عندما تتعامل مع نافذة أو نموذج (Form  ) فإن النظام يعطيك ممسك للنافذة ،النظام يخبرك أن النافذة التى تتعامل معها هى نافذة رقم 142 مثلاً ، وبالتالي فالممسك هو توليف داخلي يمكنك استعماله لتشير به إلى عنصر معين يتم مناولته من قبل النظام ،وهذا الأمر ينطبق على DLL   حيث أنه كما قلنا المتغير العام Hinstance   يحتوى ممسك ال DLL   .

 

 3-DLLProc   : (هذا أكثر المتغيرات أهمية)، كما لاحظت عند تحليلنا لوحدة DLL   فإنها لا تحتوي على جزء     initialization    أو جزء finalization    عكس بقية الوحدات الأخرى فى باسكال ،إذاً ماذا يمكنك أن تفعل لتجعل كود معين ينفذ عند لحظة تحميل    DLL   ؟ ،أو عند إلغاء تحميله ؟، أو عند تصدير المعالجات أو استلامها من DLL    محمل فى الذاكرة (هنا حالة استخدام DLL   من قبل عدة تطبيقات فى ذات الوقت ،أو استخدامه من عدة مواضع فى ذات التطبيق) ؟

 

 للقيام بذلك يمكنك حجز ذاكرة فى جزء كتلة الكود الرئيسي لل DLL   وإجراء المعالجة التى ترغب بها ومن ثم تحرير هذه الذاكرة ، للتحكم بكل ذلك توفر لك Windows   المتغير العام DLLProc   .

 

إن DLLProc    هو متغير من نوع إجراء (وبتحديد أكثر مؤشر إلى إجراء).

 

رغم أن شرح نوع إجراء خارج موضوعنا ،لكني سأفترض عدم إحاطتك به ،وبالتالى أنا بحاجة لشرحه لأمكنك من فهم هذا المتغير DLLProc   ،إذا كان النوع إجراء معروفاً بالنسبة لك فبإمكانك تخطى هذه الجزئية.

 

 ماهو المتغير من النوع الإجرائي ؟

 

من الميزات الفريدة فى Object Pascal   هى وجود الأنواع الإجرائية Procedure Types   ،وهو موضوع برمجي متقدم ( يشبه مفهوم مؤشر الوظيفة Function Pointer   فى لغة C   ) .

 

تعريف النوع الإجرائي يشير إلى قائمة من المحددات ونوع المرجوع فى حالة الدوال ،مثلاً يمكنك تعريف نوع إجراء مع محدد برقم صحيح يتم تمريره بالإشارة مثل :

 

Type

 

Intproc = procedure (var num : integer);

 

  -Intproc   :النوع الجديد الذى تقوم بتعريفه تليه علامة المساواة.

 

-الكلمة المحجوزة Procedure    فى حالة الإجراء ،أو الكلمة المحجوزة Function   فى حالة الدالة .

 

-قائمة المحددات وأنواعها ،يمكنك تمرير المحددات بشكل اعتيادى كما فى أى إجراء أو دالة فى باسكال.

 

-فى حالة الدالة عليك ذكر نوع مرجوعها، مثلاً

 

Type

 

sumfunc = function (num1,num2 : integer):integer;

 

   

 

ملاحظة: يمكنك تعريف متغير من نوع إجراء مباشرة فى جزء var    دون الحاجة إلى تعريف نوع عنه مثل:

 

var  

 

 

 

   F:  function (X: Integer): Integer;  

 

بالعودة إلى النوع intproc الذي عرفناه سابقاً نقول أنه متوافق مع أي إجرائية تملك نفس المحددات ،يمكنك تمرير المحددات بشكل اعتيادي كما فى أي إجراء أو دالة فى باسكال ،وهذا مثال لإجرائية متوافقة مع نوع إجراء السابق:

;(Procedure   DoubleTheValue   (var value : integer

Begin

 

   Value:=value*2 ;

 

End ;

 

ويمكنك استخدام نوع إجراء السابق كما يلي :

Var

 

   IP: intproc ;

 

   X : integer ;

 

Begen

 

   IP:= DoubleTheValue ;

 

   X:= 5 ;

 

   IP(X);

لمعرفة المزيد عن النوع الإجرائي بإمكانك مراجعة "   procedural types   " فى مساعدة دلفى.

 

 والآن لنعود إلى موضوعنا وهو DLLProc   ، قلنا أن DLL   يستلم رسائل من النظام Windows   عند لحظة تحميله إلى الذاكرة، وفى لحظة إلغاء تحميله ،أو فى لحظة تصدير المعالجات أو استلامها من DLL   المستخدم من قبل عدة تطبيقات . لالتقاط هذه الرسائل وفحصها ووضع خدمات بناءً عليها فإنك يجب أن تبني إجراء بشكل خاص وتسند عنوان هذا الإجراء إلى المتغير العام DLLProc   ،والشكل النموذجي للإجراء الذي يمكن أن يشير إليه المتغير DLLProc   كالتالي :

 

procedure MyDLLProc(Reason: Integer);
begin
  if Reason = DLL_PROCESS_DETACH then
    { DLL is unloading. Cleanup code here. }
end;

 

   

 

بعد كتابة الإجراء داخل DLL   كأي إجراء آخر عليك أن تسند عنوان الإجراء إلى المتغير العام DLLProc   وذلك فى جزء كتلة الكود الرئيسي لل DLL   ،مثلاً :

 

begin
  DLLProc := @MyDLLProc;
  { More initialization code. }
end.

   هذا الكود سيستدعى أوتوماتيكيا فى الحالات الثلاث التى ذكرتها سابقاً ، الباراميتر Reason   الذي هو المحدد الوحيد للإجراء( المؤشَّر عليه بالمتغير DLLProc    ) قيمة هذا الباراميتر تحدد أي الحالات الثلاث حدثت ،وكما لاحظت فى الشكل النموذجى لإجراء DLLProc   فإنه قد تم فحص الباراميتر Reason   ومقارنته بقيمة معينة ، وإليك الحالات الثلاث لهذا الباراميتر:

 

-DLL_PROCESS_DETACH  : وهى الرسالة التى يمكن أن تُستلم مرة واحدة ضمن حياة DLL   وهى لحظة إلغاء تحميل DLL   من الذاكرة (Unload  )، مثل حالة استدعاء FreeLibrary   (سنراها لاحقاً) .

 

-كلا من DLL_THREAD_ATTACH   و DLL_ THREAD _DETACH  : وهما تستلمان من قبل DLL    عدة مرات خلال حياته (وجوده بالذاكرة) عندما يكون DLLL   مُستخدماً من قبل عدة معالجات سواءً عدة تطبيقات أو تطبيق واحد يملك عدة مسالك لاستخدام DLL   (عدة إجراءات مثلاً)،فالرسالة الأولى تشير إلى أن المعالجة الحالية قد بنت مسلكاً جديداً ،أما الرسالة الثانية فهى على عكسها تشير إلى أن المعالجة الحالية قد أنهت استعمالها لل DLL   .

 

 ملاحظة: طبقاً لما سبق قد تتساءل لماذا لا يتم فحص حالة بدء تحميل DLL   وهى الرسالة DLL_PROCESS_ATTACH    ؟ هذا فى الحقيقة لا يحدث والسبب هو أن Windows   يعرف هذه الرسالة لكن Object Pascal   لا تمررها إلى DLLProc   ، بدلاً عن ذلك فإن Object Pascal   تستدعى جزء الكود الرئيسي الموجود فى DLL   عند لحظة استلامها للرسالة DLL_PROCESS_ATTACH    من النظام Windows   ،وهذا يغني عن تمرير هذه الرسالة إلى DLL   ،حيث يتم وضع أي كود استهلالي فى جزء الكود الرئيسي لل DLL   بين كلمتي Begin    و End   .

 

مثال على استخدام DLLProc   :

 

library TestDLL;
uses
  SysUtils,
  Classes,
  Forms,
  Windows;
var
  SomeBuffer : Pointer;
procedure MyDLLProc(Reason: Integer);
begin
  if Reason = DLL_PROCESS_DETACH then
    { DLL is unloading. Cleanup code here. }
    FreeMem(SomeBuffer);
end;
procedure SayHello(AForm : TForm);
begin
  MessageBox(AForm.Handle, `Hello From a DLL!',
    `DLL Message Box', MB_OK or MB_ICONEXCLAMATION);
end;
{ More DLL code here that uses SomeBuffer. }
exports
  SayHello;
begin
  { Assign our DLLProc to the DLLProc global variable. }
  DLLProc := @MyDLLProc;
  SomeBuffer := AllocMem(1024);

end.      

بإلقاء نظرة عامة على المثال السابق نلاحظ تعريف متغير عام SomeBuffer   من النوع مؤشر واستخدم لحجز ذاكرة فى كتلة الكود الرئيسي (لا تنسى أن كتلة الكود الرئيسي تنفذ فى لحظة تحميل DLL  ) يمكن لل DLL   استخدام هذه الذاكرة لمعالجاته المختلفة ،والنقطة الهامة هى لحظة تحرير هذه الذاكرة كما سبق وعرفنا أن هذه الذاكرة تحرر ضمن الإجراء المؤشر عليه بالمتغير العام DLLProc   فى مثالنا أسم الإجراء  MyDLLProc    الذى يشترط لتحريرها أن يستلم رسالة تفيد بأن ال DLL   هو الآن قيد إلغاء التحميل (Unload  )التى يحددها الباراميتر Reason   عبر القيمة DLL_PROCESS_DETACH   .

 

 الخلاصة:

 

فى هذا الدرس قمنا بتحليل الشكل العام لل DLL   ورأينا الفرق بينه وبين باقى وحدات دلفى ، ثم درسنا ما أعتبره أكثر المواضيع المتعلقة بال DLL   تعقيدا وهو كيفية إدارة العلاقة بين DLL   والتطبيق المستدعى (هنا تطبيق دلفى) وكيف يقوم النظام Windows   بإدارة هذه العلاقة باستخدام متغيراته العامة المختلفة، تلك المتغيرات التى لا نحتاج للإتصال بها فى معظم التطبيقات تعد هامة هنا ،وأهمها المتغير DLLProc   ،والسبب لكل هذا هو أن DLL   ليس تطبيقا مستقلا يُحمّل ويلغى من الذاكرة بذاته ،وإنما يضل مرتبطا بالتطبيقات المستدعية مما اضطرنا لاستخدام متغيرات النظام Windows    لنعرف ما يجرى فى هذه اللحظة وما يجب أن يكون بناء على تصرفات التطبيقات المستدعية المختلفة.

 

 المراجع

 

نفس المراجع المذكورة فى الدرس الأول لل DLL   .

 



المزيد من المواضيع

نافذة الخصائص والأحداث بدلفي
استخدام Forms وResources فى DLLs
تحميل واستدعاء دوال وإجراءات DLL
مقدمة فى برمجة DLL (لغة دلفي)
الدالة Case
حلقات التكرار While - For - Repeat
الكلمة الأساسية IF - THEN
المتغيرات في برنامج الدلفي
الثوابت في برنامج الدلفي

1

 

الاقسام الرئيسية

دروس للمبتدئين

--

دروس في أنظمة التشغيل

--

دروس في الانترنت

--

دروس في لغات البرمجة

--

دروس في برمجة المواقع

--

دروس في الأوفيس

--

دروس في الرسوم و التصميم

--

دروس في قواعد البيانات

--

دروس في الألعاب والبرامج

--

دروس في المكونات الصلبة

--

دروس في الشبكات

--

دروس في أمن المعلومات

--

دروس في الذكاء الاصطناعي

--

القائمة البريدية

  فضائح | ماسنجر | تداول | الحياة الزوجية | عجائب وغرائب| دروس تعليمية | عالم حواء | فضائح الفن | ستار اكاديمي | نكت | برامج | صور | | شات سعودي | شات عربي | ماسينجر | مسجات | دليل مواقع | دليلك | مواقع سعودية | مواقع كويتية | مواقع بحرينية | مواقع قطرية | مواقع عمانية | مواقع يمنية | مواقع عراقية | مواقع اماراتية | دردشة خليجية | دردشة سعودية | دردشة عربية | شات صوتي | دردشة صوتية | دردشة كويتية | دردشة اماراتية | دردشة عمانية | دردشة قطرية | دردشة بحرينية | دردشة عراقية | دردشة يمنية | سكس | طريق الاسلام, انا مسلم , طريق الهدايه , مسلمون , منوعات اسلاميه | اسلاميات , برامج اسلامية , منوعات اسلامية | جنس | الاسرة المسلمة , الاسرة العربية , اسرتي , عائلتي | برامج الاسره , نصائح معلومات , اسرة عربية سعودية خليجية | دروس تعليمية , مكتبة الدروس التعليمية | شروح برامج , شرح برامج , دورات تعليميه | طب وصحه - المركز الطبي | طبيبك على الانترنت , معلومات طبية , معلومات صحيه

Roro44.com xml :                            

شات سعودي | شات عربي | شات خليجي | العاب | دردشات | العاب بنات

 |  اشهر موقعك | احصائيات الموقع | اسعار الاعلانات |  لمراسلة الإدارة  |

:: ©2007-2003 www.roro44.com All rights reserved ::