summaryrefslogtreecommitdiff
path: root/UGlibThreads.pas
diff options
context:
space:
mode:
authorTomas Bzatek <tbzatek@users.sourceforge.net>2008-06-21 09:41:26 +0200
committerTomas Bzatek <tbzatek@users.sourceforge.net>2008-06-21 09:41:26 +0200
commit4c0435478c2325b107740c812ca54476bebeccee (patch)
tree1b7aae1a78fc0101165ed8d86b81799a62fa540c /UGlibThreads.pas
parenta54366fd435e11ef3d594bcf3419df400725dabe (diff)
downloadtuxcmd-4c0435478c2325b107740c812ca54476bebeccee.tar.xz
Finished glib threads implementation
Diffstat (limited to 'UGlibThreads.pas')
-rw-r--r--UGlibThreads.pas97
1 files changed, 82 insertions, 15 deletions
diff --git a/UGlibThreads.pas b/UGlibThreads.pas
index 3d24afd..9c53691 100644
--- a/UGlibThreads.pas
+++ b/UGlibThreads.pas
@@ -1,6 +1,6 @@
(*
Tux Commander - UGlibThreads - Threading support through the GLIB library
- Copyright (C) 2007 Tomas Bzatek <tbzatek@users.sourceforge.net>
+ Copyright (C) 2007-2008 Tomas Bzatek <tbzatek@users.sourceforge.net>
Check for updates on tuxcmd.sourceforge.net
This program is free software; you can redistribute it and/or modify
@@ -23,10 +23,6 @@ interface
uses glib2;
-// function xg_thread_supported(): gboolean; cdecl; external 'libgthread-2.0.so' name 'g_thread_supported';
-// function xg_thread_create(func: TGThreadFunc; data: gpointer; joinable: gboolean; error: PPGError): PGThread; external 'libgthread-2.0.so' name 'g_thread_create';
-
-
type
TGlibThreadMethod = procedure of object;
@@ -36,7 +32,8 @@ type
FCreateSuspended: Boolean;
FTerminated: Boolean;
FSuspended: Boolean;
-// FFreeOnTerminate: Boolean;
+ FReturnValue: Integer;
+ FFreeOnTerminate: Boolean;
// FFinished: Boolean;
// procedure SetSuspended(Value: Boolean);
protected
@@ -49,38 +46,61 @@ type
// procedure AfterConstruction; override;
procedure Resume;
{ procedure Suspend;
- procedure Terminate;
+ procedure Terminate; }
function WaitFor: LongWord;
property FreeOnTerminate: Boolean read FFreeOnTerminate write FFreeOnTerminate;
- property Suspended: Boolean read FSuspended write SetSuspended; }
+{ property Suspended: Boolean read FSuspended write SetSuspended; }
+ property ReturnValue: Integer read FReturnValue write FReturnValue;
end;
+ TGlibCriticalSection = class
+ private
+ FGMutex: TGStaticMutex;
+ public
+ constructor Create;
+ destructor Destroy;override;
+ procedure Enter;
+ procedure Leave;
+ procedure Acquire;
+ procedure Release;
+ end;
+
+
implementation
uses Classes, SysUtils, UCoreUtils;
function xg_thread_func(data: gpointer): gpointer; cdecl;
+var Thread: TGlibThread;
+ FreeThread: Boolean;
begin
DebugMsg(['(II) TGlibThread.g_thread_func']);
+ Result := nil;
try
-{ if Assigned(data) and (TObject(data) is TGlibThread)
- then TGlibThread(data).Execute
- else DebugMsg(['(EE) TGlibThread.g_thread_func: wrong data argument']); }
+ Thread := TGlibThread(data);
+ if Assigned(Thread) and (Thread is TGlibThread) then begin
+ Thread.Execute;
+ Result := gpointer(Thread.FReturnValue);
+ FreeThread := Thread.FreeOnTerminate;
+ if FreeThread then Thread.Free;
+ end else DebugMsg(['(EE) TGlibThread.g_thread_func: wrong data argument']);
except
on E: Exception do
DebugMsg(['(EE) TGlibThread.g_thread_func: Exception ', E.ClassName, ': ', E.Message]);
end;
- Result := data;
end;
constructor TGlibThread.Create(CreateSuspended: Boolean);
begin
- DebugMsg(['(II) TGlibThread.Create']);
inherited Create;
+ DebugMsg(['(II) TGlibThread.Create']);
FSuspended := CreateSuspended;
FCreateSuspended := CreateSuspended;
FHandle := nil;
+ FReturnValue := 0;
+ FFreeOnTerminate := False;
+ if not CreateSuspended then Resume;
end;
destructor TGlibThread.Destroy;
@@ -101,11 +121,58 @@ var err: PGError;
begin
DebugMsg(['(II) TGlibThread.Resume']);
err := nil;
- FHandle := g_thread_create_full(@xg_thread_func, Self, 0, False, False, G_THREAD_PRIORITY_NORMAL, @err);
- if FHandle = nil then DebugMsg(['(EE) TGlibThread.Resume: Error creating new thread: ', err.message]);
+ FHandle := g_thread_create(@xg_thread_func, Self, True, @err);
+ if FHandle = nil then begin
+ DebugMsg(['(EE) TGlibThread.Resume: Error creating new thread: ', err.message]);
+ g_error_free(err);
+ end;
+end;
+
+function TGlibThread.WaitFor: LongWord;
+begin
+ if FHandle <> nil then g_thread_join(FHandle);
+ Result := FReturnValue;
+end;
+
+
+(**********************************************************************************************************************)
+constructor TGlibCriticalSection.Create;
+begin
+ inherited Create;
+ FGMutex := nG_STATIC_MUTEX_INIT;
+end;
+
+destructor TGlibCriticalSection.Destroy;
+begin
+ inherited Destroy;
+end;
+
+procedure TGlibCriticalSection.Enter;
+begin
+ Acquire;
+end;
+
+procedure TGlibCriticalSection.Leave;
+begin
+ Release;
+end;
+
+procedure TGlibCriticalSection.Acquire;
+begin
+ g_static_mutex_lock(@FGMutex);
end;
+procedure TGlibCriticalSection.Release;
+begin
+ g_static_mutex_unlock(@FGMutex);
+end;
+
+(**********************************************************************************************************************)
+
+initialization
+ if not g_thread_supported then g_thread_init(nil);
+finalization
end.