mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-19 13:59:29 +02:00
* sysutils: changed RunErrorToExcept to use table instead of case statement for OS exceptions. This is to be able to extract exception class alone for the upcoming SEH support.
* Some Delphi-compatible changes: * For floating point underflow condition, raise EUnderflow, not EOverflow. * For unknown codes, raise EInOutError, not Exception. * Added entries for EZeroDivide and EStackOverflow (actually raising EZeroDivide on floating-point division by zero requires further changes to System because currently both integer and float division by zero is mapped to the same code 200). git-svn-id: trunk@19707 -
This commit is contained in:
parent
0d562f04ff
commit
0093517227
@ -87,6 +87,7 @@ resourcestring
|
||||
SOverflow = 'Floating point overflow';
|
||||
SPrivilege = 'Privileged instruction';
|
||||
SRangeError = 'Range check error';
|
||||
SStackOverflow = 'Stack overflow';
|
||||
SSafecallException = 'Exception in safecall method';
|
||||
SiconvError = 'iconv error';
|
||||
|
||||
@ -116,6 +117,7 @@ resourcestring
|
||||
SVarTypeRangeCheck2 = 'Range check error while converting variant of type (%s) into type (%s)';
|
||||
SVarTypeTooManyCustom = 'Too many custom variant types have been registered';
|
||||
SVarUnexpected = 'Unexpected variant error';
|
||||
SZeroDivide = 'Floating point division by zero';
|
||||
|
||||
SFallbackError = 'An error, whose error code is larger than can be returned to the OS, has occured';
|
||||
|
||||
|
@ -294,22 +294,80 @@ begin
|
||||
Writeln(hstdout^,'');
|
||||
end;
|
||||
|
||||
type
|
||||
PExceptMapEntry=^TExceptMapEntry;
|
||||
TExceptMapEntry=record
|
||||
code: byte;
|
||||
cls: ExceptClass;
|
||||
msg: PResStringRec;
|
||||
end;
|
||||
|
||||
const
|
||||
exceptmap: array[0..27] of TExceptMapEntry = (
|
||||
(code: 200; cls: EDivByZero; msg: @SDivByZero),
|
||||
(code: 201; cls: ERangeError; msg: @SRangeError),
|
||||
(code: 202; cls: EStackOverflow; msg: @SStackOverflow),
|
||||
(code: 205; cls: EOverflow; msg: @SOverflow),
|
||||
(code: 206; cls: EUnderflow; msg: @SUnderflow),
|
||||
(code: 207; cls: EInvalidOp; msg: @SInvalidOp),
|
||||
{ Delphi distinguishes reDivByZero from reZeroDivide, but maps both to code 200. }
|
||||
(code: 208; cls: EZeroDivide; msg: @SZeroDivide),
|
||||
(code: 211; cls: EAbstractError; msg: @SAbstractError),
|
||||
(code: 212; cls: EExternalException; msg: @SExternalException),
|
||||
(code: 214; cls: EBusError; msg: @SBusError),
|
||||
(code: 215; cls: EIntOverflow; msg: @SIntOverflow),
|
||||
(code: 216; cls: EAccessViolation; msg: @SAccessViolation),
|
||||
(code: 217; cls: EControlC; msg: @SControlC),
|
||||
(code: 218; cls: EPrivilege; msg: @SPrivilege),
|
||||
(code: 219; cls: EInvalidCast; msg: @SInvalidCast),
|
||||
(code: 220; cls: EVariantError; msg: @SInvalidVarCast),
|
||||
(code: 221; cls: EVariantError; msg: @SInvalidVarOp),
|
||||
(code: 222; cls: EVariantError; msg: @SDispatchError),
|
||||
(code: 223; cls: EVariantError; msg: @SVarArrayCreate),
|
||||
(code: 224; cls: EVariantError; msg: @SVarNotArray),
|
||||
(code: 225; cls: EVariantError; msg: @SVarArrayBounds),
|
||||
(code: 227; cls: EAssertionFailed; msg: @SAssertionFailed),
|
||||
(code: 228; cls: EIntfCastError; msg: @SIntfCastError),
|
||||
(code: 229; cls: ESafecallException; msg: @SSafecallException),
|
||||
(code: 231; cls: EConvertError; msg: @SiconvError),
|
||||
(code: 232; cls: ENoThreadSupport; msg: @SNoThreadSupport),
|
||||
(code: 233; cls: ENoWideStringSupport; msg: @SSigQuit),
|
||||
(code: 234; cls: ENoWideStringSupport; msg: @SMissingWStringManager)
|
||||
);
|
||||
|
||||
function FindExceptMapEntry(err: longint): PExceptMapEntry;
|
||||
var
|
||||
i: longint;
|
||||
begin
|
||||
for i:=low(exceptmap) to high(exceptmap) do
|
||||
if err=exceptmap[i].code then
|
||||
begin
|
||||
result:=@exceptmap[i];
|
||||
exit;
|
||||
end;
|
||||
result:=nil;
|
||||
end;
|
||||
|
||||
Var OutOfMemory : EOutOfMemory;
|
||||
InValidPointer : EInvalidPointer;
|
||||
|
||||
|
||||
Procedure RunErrorToExcept (ErrNo : Longint; Address,Frame : Pointer);
|
||||
|
||||
Var E : Exception;
|
||||
HS : PString;
|
||||
|
||||
var
|
||||
E: Exception;
|
||||
HS: PString;
|
||||
Entry: PExceptMapEntry;
|
||||
begin
|
||||
Case Errno of
|
||||
1,203 : E:=OutOfMemory;
|
||||
204 : E:=InvalidPointer;
|
||||
2,3,4,5,6,100,101,102,103,105,106 : { I/O errors }
|
||||
begin
|
||||
else
|
||||
Entry:=FindExceptMapEntry(ErrNo);
|
||||
if Assigned(Entry) then
|
||||
E:=Entry^.cls.CreateRes(Entry^.msg)
|
||||
else
|
||||
begin
|
||||
HS:=nil;
|
||||
Case Errno of
|
||||
2 : HS:=@SFileNotFound;
|
||||
3 : HS:=@SInvalidFileName;
|
||||
@ -325,7 +383,10 @@ begin
|
||||
105 : HS:=@SFileNotOpenForOutput;
|
||||
106 : HS:=@SInvalidInput;
|
||||
end;
|
||||
E:=EinOutError.Create (HS^);
|
||||
if Assigned(HS) then
|
||||
E:=EInOutError.CreateRes(HS)
|
||||
else
|
||||
E:=EInOutError.CreateResFmt(@SUnknownRunTimeError,[errno]);
|
||||
// this routine can be called from FPC_IOCHECK,
|
||||
// which clears inoutres and then passes its
|
||||
// original value to HandleErrorFrame() (which calls
|
||||
@ -335,36 +396,6 @@ begin
|
||||
EInoutError(E).ErrorCode:=errno;
|
||||
inoutres:=0;
|
||||
end;
|
||||
// We don't set abstracterrorhandler, but we do it here.
|
||||
// Unless the use sets another handler we'll get here anyway...
|
||||
200 : E:=EDivByZero.Create(SDivByZero);
|
||||
201 : E:=ERangeError.Create(SRangeError);
|
||||
205 : E:=EOverflow.Create(SOverflow);
|
||||
206 : E:=EOverflow.Create(SUnderflow);
|
||||
207 : E:=EInvalidOp.Create(SInvalidOp);
|
||||
211 : E:=EAbstractError.Create(SAbstractError);
|
||||
212 : E:=EExternalException.Create(SExternalException);
|
||||
214 : E:=EBusError.Create(SBusError);
|
||||
215 : E:=EIntOverflow.Create(SIntOverflow);
|
||||
216 : E:=EAccessViolation.Create(SAccessViolation);
|
||||
217 : E:=EControlC.Create(SControlC);
|
||||
218 : E:=EPrivilege.Create(SPrivilege);
|
||||
219 : E:=EInvalidCast.Create(SInvalidCast);
|
||||
220 : E:=EVariantError.Create(SInvalidVarCast);
|
||||
221 : E:=EVariantError.Create(SInvalidVarOp);
|
||||
222 : E:=EVariantError.Create(SDispatchError);
|
||||
223 : E:=EVariantError.Create(SVarArrayCreate);
|
||||
224 : E:=EVariantError.Create(SVarNotArray);
|
||||
225 : E:=EVariantError.Create(SVarArrayBounds);
|
||||
227 : E:=EAssertionFailed.Create(SAssertionFailed);
|
||||
228 : E:=EIntfCastError.Create(SIntfCastError);
|
||||
229 : E:=ESafecallException.Create(SSafecallException);
|
||||
231 : E:=EConvertError.Create(SiconvError);
|
||||
232 : E:=ENoThreadSupport.Create(SNoThreadSupport);
|
||||
233 : E:=ENoWideStringSupport.Create(SSigQuit);
|
||||
234 : E:=ENoWideStringSupport.Create(SMissingWStringManager);
|
||||
else
|
||||
E:=Exception.CreateFmt (SUnKnownRunTimeError,[Errno]);
|
||||
end;
|
||||
Raise E at Address,Frame;
|
||||
end;
|
||||
|
Loading…
Reference in New Issue
Block a user