THRIFT-5384 Improved error message for HTTP transports
Client: Delphi
Patch: Jens Geyer
diff --git a/lib/delphi/src/Thrift.Protocol.pas b/lib/delphi/src/Thrift.Protocol.pas
index d5a7587..aa12ad3 100644
--- a/lib/delphi/src/Thrift.Protocol.pas
+++ b/lib/delphi/src/Thrift.Protocol.pas
@@ -833,6 +833,7 @@
begin
Reset;
Init( result);
+
size := ReadI32;
if (size < 0) then begin
version := size and Integer( VERSION_MASK);
@@ -842,14 +843,20 @@
result.Type_ := TMessageType( size and $000000ff);
result.Name := ReadString;
result.SeqID := ReadI32;
- end
- else begin
- if FStrictRead then begin
- raise TProtocolExceptionBadVersion.Create('Missing version in readMessageBegin, old client?' );
- end;
+ Exit;
+ end;
+
+ try
+ if FStrictRead
+ then raise TProtocolExceptionBadVersion.Create('Missing version in readMessageBegin, old client?' );
+
result.Name := ReadStringBody( size );
result.Type_ := TMessageType( ReadByte );
result.SeqID := ReadI32;
+ except
+ if CharUtils.IsHtmlDoctype(size)
+ then raise TProtocolExceptionInvalidData.Create('Remote end sends HTML instead of data')
+ else raise; // something else
end;
end;
diff --git a/lib/delphi/src/Thrift.Transport.pas b/lib/delphi/src/Thrift.Transport.pas
index 6a69d93..79fc977 100644
--- a/lib/delphi/src/Thrift.Transport.pas
+++ b/lib/delphi/src/Thrift.Transport.pas
@@ -1437,7 +1437,9 @@
if Int64(size) > Int64(Configuration.MaxFrameSize) then begin
Close();
- raise TTransportExceptionCorruptedData.Create('Frame size ('+IntToStr(size)+') larger than allowed maximum ('+IntToStr(Configuration.MaxFrameSize)+')');
+ if CharUtils.IsHtmlDoctype(size)
+ then raise TTransportExceptionCorruptedData.Create('Remote end sends HTML instead of data')
+ else raise TTransportExceptionCorruptedData.Create('Frame size ('+IntToStr(size)+') larger than allowed maximum ('+IntToStr(Configuration.MaxFrameSize)+')');
end;
UpdateKnownMessageSize(size + SizeOf(size));
diff --git a/lib/delphi/src/Thrift.Utils.pas b/lib/delphi/src/Thrift.Utils.pas
index bfd020e..4a75af8 100644
--- a/lib/delphi/src/Thrift.Utils.pas
+++ b/lib/delphi/src/Thrift.Utils.pas
@@ -80,6 +80,8 @@
public
class function IsHighSurrogate( const c : Char) : Boolean; static; inline;
class function IsLowSurrogate( const c : Char) : Boolean; static; inline;
+
+ class function IsHtmlDoctype( const fourBytes : Integer) : Boolean; static;
end;
EnumUtils<T> = class sealed
@@ -259,6 +261,30 @@
end;
+class function CharUtils.IsHtmlDoctype( const fourBytes : Integer) : Boolean;
+var pc : PAnsiChar;
+const HTML_BEGIN : PAnsiChar = 'OD!<'; // first 4 bytes of '<!DOCTYPE ' in LE byte order
+begin
+ pc := @fourBytes;
+
+ if UpCase(pc^) <> HTML_BEGIN[0]
+ then Exit(FALSE);
+
+ Inc( pc);
+ if UpCase(pc^) <> HTML_BEGIN[1]
+ then Exit(FALSE);
+
+
+ Inc( pc);
+ if UpCase(pc^) <> HTML_BEGIN[2]
+ then Exit(FALSE);
+
+ Inc( pc);
+ result := (UpCase(pc^) = HTML_BEGIN[3]);
+end;
+
+
+
{$IFDEF Win64}
function InterlockedCompareExchange64( var Target : Int64; Exchange, Comparand : Int64) : Int64; inline;