From ca46040728ccd75ec3be0d8d9b5edccafcf80941 Mon Sep 17 00:00:00 2001 From: nickysn Date: Sun, 18 Dec 2016 00:17:10 +0000 Subject: [PATCH] + added 16-bit versions of the InterLocked* functions for i8086 git-svn-id: trunk@35149 - --- rtl/i8086/i8086.inc | 102 +++++++++++++++++++++++++++++++++++++++++--- rtl/inc/systemh.inc | 14 ++++++ 2 files changed, 111 insertions(+), 5 deletions(-) diff --git a/rtl/i8086/i8086.inc b/rtl/i8086/i8086.inc index 00d8e7e7e8..c43af3038e 100644 --- a/rtl/i8086/i8086.inc +++ b/rtl/i8086/i8086.inc @@ -606,7 +606,25 @@ asm {$endif FPC_X86_DATA_NEAR} end; -{TODO: use smallint?} +function InterLockedDecrement (var Target: smallint) : smallint;nostackframe;assembler; +asm + mov si, sp +{$ifdef FPC_X86_DATA_NEAR} + mov bx, ss:[si + 2 + extra_param_offset] // Target +{$else FPC_X86_DATA_NEAR} + mov cx, ds + lds bx, ss:[si + 2 + extra_param_offset] // Target +{$endif FPC_X86_DATA_NEAR} + pushf + cli + sub word [bx], 1 + mov ax, [bx] + popf +{$if defined(FPC_X86_DATA_FAR) or defined(FPC_X86_DATA_HUGE)} + mov ds, cx +{$endif} +end; + function InterLockedDecrement (var Target: longint) : longint;nostackframe;assembler; asm mov si, sp @@ -628,7 +646,25 @@ asm {$endif} end; -{TODO: use smallint?} +function InterLockedIncrement (var Target: smallint) : smallint;nostackframe;assembler; +asm + mov si, sp +{$ifdef FPC_X86_DATA_NEAR} + mov bx, ss:[si + 2 + extra_param_offset] // Target +{$else FPC_X86_DATA_NEAR} + mov cx, ds + lds bx, ss:[si + 2 + extra_param_offset] // Target +{$endif FPC_X86_DATA_NEAR} + pushf + cli + add word [bx], 1 + mov ax, [bx] + popf +{$if defined(FPC_X86_DATA_FAR) or defined(FPC_X86_DATA_HUGE)} + mov ds, cx +{$endif} +end; + function InterLockedIncrement (var Target: longint) : longint;nostackframe;assembler; asm mov si, sp @@ -650,7 +686,22 @@ asm {$endif} end; -{TODO: use smallint?} +function InterLockedExchange (var Target: smallint;Source : smallint) : smallint;nostackframe;assembler; +asm + mov si, sp +{$ifdef FPC_X86_DATA_NEAR} + mov bx, ss:[si + 4 + extra_param_offset] // Target +{$else FPC_X86_DATA_NEAR} + mov cx, ds + lds bx, ss:[si + 4 + extra_param_offset] // Target +{$endif FPC_X86_DATA_NEAR} + mov ax, ss:[si + 2 + extra_param_offset] // Source + xchg word [bx], ax +{$if defined(FPC_X86_DATA_FAR) or defined(FPC_X86_DATA_HUGE)} + mov ds, cx +{$endif} +end; + function InterLockedExchange (var Target: longint;Source : longint) : longint;nostackframe;assembler; asm mov si, sp @@ -672,7 +723,26 @@ asm {$endif} end; -{TODO: use smallint?} +function InterLockedExchangeAdd (var Target: smallint;Source : smallint) : smallint;nostackframe;assembler; +asm + mov si, sp +{$ifdef FPC_X86_DATA_NEAR} + mov bx, ss:[si + 4 + extra_param_offset] // Target +{$else FPC_X86_DATA_NEAR} + mov cx, ds + lds bx, ss:[si + 4 + extra_param_offset] // Target +{$endif FPC_X86_DATA_NEAR} + mov di, ss:[si + 2 + extra_param_offset] // Source + pushf + cli + mov ax, [bx] + add word [bx], di + popf +{$if defined(FPC_X86_DATA_FAR) or defined(FPC_X86_DATA_HUGE)} + mov ds, cx +{$endif} +end; + function InterLockedExchangeAdd (var Target: longint;Source : longint) : longint;nostackframe;assembler; asm mov si, sp @@ -696,7 +766,29 @@ asm {$endif} end; -{TODO: use smallint?} +function InterlockedCompareExchange(var Target: smallint; NewValue: smallint; Comperand: smallint): smallint;assembler; +asm +{$ifdef FPC_X86_DATA_NEAR} + mov bx, [Target] // Target +{$else FPC_X86_DATA_NEAR} + mov cx, ds + lds bx, [Target] // Target +{$endif FPC_X86_DATA_NEAR} + mov di, [Comperand] + pushf + cli + mov ax, [bx] + cmp ax, di + jne @@not_equal + mov di, [NewValue] + mov [bx], di +@@not_equal: + popf +{$if defined(FPC_X86_DATA_FAR) or defined(FPC_X86_DATA_HUGE)} + mov ds, cx +{$endif} +end; + function InterlockedCompareExchange(var Target: longint; NewValue: longint; Comperand: longint): longint;assembler; asm {$ifdef FPC_X86_DATA_NEAR} diff --git a/rtl/inc/systemh.inc b/rtl/inc/systemh.inc index fb2011fc96..6a2ae18b1b 100644 --- a/rtl/inc/systemh.inc +++ b/rtl/inc/systemh.inc @@ -1377,6 +1377,13 @@ Function GetProcessID:SizeUInt; Function GetThreadID:TThreadID;{$ifdef SYSTEMINLINE}inline;{$endif} {$endif FPC_HAS_FEATURE_PROCESSES} +{$ifdef cpu16} +function InterLockedIncrement (var Target: smallint) : smallint; public name 'FPC_INTERLOCKEDINCREMENT16'; +function InterLockedDecrement (var Target: smallint) : smallint; public name 'FPC_INTERLOCKEDDECREMENT16'; +function InterLockedExchange (var Target: smallint;Source : smallint) : smallint; public name 'FPC_INTERLOCKEDEXCHANGE16'; +function InterLockedExchangeAdd (var Target: smallint;Source : smallint) : smallint; public name 'FPC_INTERLOCKEDEXCHANGEADD16'; +function InterlockedCompareExchange(var Target: smallint; NewValue: smallint; Comperand: smallint): smallint; public name 'FPC_INTERLOCKEDCOMPAREEXCHANGE16'; +{$endif cpu16} function InterLockedIncrement (var Target: longint) : longint; public name 'FPC_INTERLOCKEDINCREMENT'; function InterLockedDecrement (var Target: longint) : longint; public name 'FPC_INTERLOCKEDDECREMENT'; function InterLockedExchange (var Target: longint;Source : longint) : longint; public name 'FPC_INTERLOCKEDEXCHANGE'; @@ -1406,6 +1413,13 @@ function InterlockedCompareExchange(var Target: Pointer; NewValue: Pointer; Comp function InterlockedCompareExchangePointer(var Target: Pointer; NewValue: Pointer; Comperand: Pointer): Pointer; external name 'FPC_INTERLOCKEDCOMPAREEXCHANGE'; {$endif cpu64} { unsigned overloads } +{$ifdef cpu16} +function InterLockedIncrement (var Target: word) : word; external name 'FPC_INTERLOCKEDINCREMENT16'; +function InterLockedDecrement (var Target: word) : word; external name 'FPC_INTERLOCKEDDECREMENT16'; +function InterLockedExchange (var Target: word;Source : word) : word; external name 'FPC_INTERLOCKEDEXCHANGE16'; +function InterLockedExchangeAdd (var Target: word;Source : word) : word; external name 'FPC_INTERLOCKEDEXCHANGEADD16'; +function InterlockedCompareExchange(var Target: word; NewValue: word; Comperand: word): word; external name 'FPC_INTERLOCKEDCOMPAREEXCHANGE16'; +{$endif cpu16} function InterLockedIncrement (var Target: cardinal) : cardinal; external name 'FPC_INTERLOCKEDINCREMENT'; function InterLockedDecrement (var Target: cardinal) : cardinal; external name 'FPC_INTERLOCKEDDECREMENT'; function InterLockedExchange (var Target: cardinal;Source : cardinal) : cardinal; external name 'FPC_INTERLOCKEDEXCHANGE';