[ Pobierz całość w formacie PDF ]
.Pierwsz¹ operacj¹ wykonywan¹ nasekcji krytycznej jest jej zainicjowanie, wykonywane przez nastêpuj¹c¹procedurê API:procedure InitializeCriticalSection(varlpCriticalSection:TRTLCriticalSection);stdcall;Rozpoczêcie wykonywania krytycznego fragmentu kodu musi byæ poprzedzonewej­œciem do sekcji krytycznej (entering critical section).Jest onorealizowane przez procedurê EnterCriticalSection():procedure EnterCriticalSection(varlpCriticalSection:TRTLCriticalSection);stdcall;W danej chwili wewn¹trz okreœlonej sekcji krytycznej mo¿e przebywaæ co najwy¿ejje­den w¹tek — pozosta³e w¹tki zamierzaj¹ce do niej wejœæ (œciœlej — te, którewywo³aj¹ w stosunku do niej procedurê EnterCriticalSection()), zostan¹ przezsystem zawieszone.Po zakoñczeniu wykonywania krytycznego fragmentu kodu w¹tek znajduj¹cy siê wsek­cji krytycznej musi dokonaæ wyjœcia z niej (leaving critical section) przezwywo³anie nastêpuj¹cej procedury:procedure LeaveCriticalSection(var lpCriticalSection:TRTLCriticalSection);stdcall;Umo¿liwi to wejœcie do sekcji krytycznej któremuœ z oczekuj¹cych w¹tków.Ostatni¹ operacj¹ dotycz¹c¹ sekcji krytycznej jest jej zwolnienie, gdy nie jestju¿ d³u¿ej potrzebna; s³u¿y do tego nastêpuj¹ca procedura:procedure DeleteCriticalSection(var lpCriticalSection:TRTLCriticalSection);stdcall;WskazówkaMicrosoft konsekwentnie ukrywa strukturê rekordu TRTLCriticalSection, poniewa¿zmienia siê ona w zale¿noœci od platformy sprzêtowej, a wiêc uzale¿nienieaplikacji od jej konkretnej postaci mog³oby powodowaæ problemy.W systemach„intelowskich” sekcja krytyczna zawiera licznik, pole przechowuj¹ce uchwytprzebywaj¹cego w niej w¹tku i (ewentualnie) wskaŸnik do procedury obs³ugizdarzeñ systemowych.Komputery serii Alpha pos³uguj¹ siê w³asn¹ postaci¹ sekcjikrytycznej o nazwie spinlock, znacznie efektywniejsz¹ od intelowskiej.Wykorzystanie sekcji krytycznej do synchronizacji zape³niania tablicy zpoprzedniego przyk³adu ilustruje projekt CritSec.dpr znajduj¹cy siê naza³¹czonym kr¹¿ku CD-ROM.Jego modu³ g³Ã³wny prezentujemy na wydruku 5.5.Wydruk 5.5.Przyk³ad synchronizacji z wykorzystaniem sekcji krytycznejunit Main;interfaceusesWindows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,StdCtrls;typeTMainForm = class(TForm)Button1: TButton;ListBox1: TListBox;procedure Button1Click(Sender: TObject);privateprocedure ThreadsDone(Sender: TObject);end;TFooThread = class(TThread)protectedprocedure Execute; override;end;varMainForm: TMainForm;implementation{$R *.DFM}constMaxSize = 128;varNextNumber: Integer = 0;DoneFlags: Integer = 0;GlobalArray: array[1.MaxSize] of Integer;CS: TRTLCriticalSection;function GetNextNumber: Integer;beginResult := NextNumber; // zwróæ wartoœæ zmiennej globalnejinc(NextNumber); // zwiêksz zmienn¹ globaln¹end;procedure TFooThread.Execute;vari: Integer;beginOnTerminate := MainForm.ThreadsDone;EnterCriticalSection(CS); // pocz¹tek sekcji krytycznejfor i := 1 to MaxSize dobeginGlobalArray[i] := GetNextNumber; // ustaw element tablicySleep(3+Random(12)); // pozwól dzia³aæ innemu w¹tkowiend;LeaveCriticalSection(CS); // koniec sekcji krytycznejend;procedure TMainForm.ThreadsDone(Sender: TObject);vari: Integer;begininc(DoneFlags);if DoneFlags = 2 thenbegin // upewnij siê, ¿e zwolniono obydwa w¹tkifor i := 1 to MaxSize do{ wype³nij listê zawartoœci¹ tablicy }Listbox1.Items.Add(IntToStr(GlobalArray[i]));DeleteCriticalSection(CS);end;end;procedure TMainForm.Button1Click(Sender: TObject);beginInitializeCriticalSection(CS);// utwórz i uruchom w¹tkiTFooThread [ Pobierz caÅ‚ość w formacie PDF ]

  • zanotowane.pl
  • doc.pisz.pl
  • pdf.pisz.pl
  • listy-do-eda.opx.pl