View Issue Details

IDProjectCategoryView StatusLast Update
0032025FPCRTLpublic2017-07-10 14:57
ReporterwpAssigned ToMichael Van Canneyt 
PrioritynormalSeverityminorReproducibilityalways
Status closedResolutionfixed 
Product Version3.1.1Product Build 
Target Version3.2.0Fixed in Version3.1.1 
Summary0032025: Issues with the fp-image readers
DescriptionThe package fp-image provides a series of readers for various graphics formats. Calling image.LoadfromStream without a reader triggers automatic format detection which is based on the function InternalCheck. This function is implemented by each reader and must return true if the reader supports this format.

There are several readers which do not implement this function properly and simply return true (fpreadpnm, fpreadpcx, fpreadtga). The pnm format, for example, is checked before the png format. Since the pnm reader always returns true here a png file cannot be autodetected, and therefore not be read correctly unless the reader is explicitely specified in Image.LoadFromStream. (issue 0032005)

In addition, some readers do not correctly check if reading the header goes beyond the stream end. Some simply do not check this at all, others raise an exception which could be avoided if the number of bytes read would be compared with the number of bytes requested. I think unnecessary exceptions should be avoided.

The final problem is that there is an inconsistency in rewinding the stream after checking the file format. Reading occurs in two steps: the method InternalCheck determines the file format after reading the header, and InternalRead reads the data. They always appear together, e.g. in TFPCustomImage.LoadfromStream or TFPCustomImageReader.ImageRead. The stream position must not be changed in between.

png is an example of the case where the stream is not rewinded after checking the header, InternalRead relies on the stream position to be at a valid chunck, not at the file start with the file signature. But exactly here the solution of 0029990 added a change of stream position between these two procedures. As a consequence we have now issue 0032005 reporting the "Incorrect chunk length" error again which 0029990 was supposed to solve.
Steps To ReproduceRun the demo project provided in issue 0032005.
Additional InformationThere are issues in some example programs:
- "textout" and "drawing" do not compile because unit cwstring is not found (it can safely be removed from "uses").
- "interpoldemo" does not run because the sample file "original.png" is missing.

In total, the provided patch fixes several issues:
- Checks the file headers for the format signature in case of pnm, pcx, and tga
- Avoid raising exceptions if reading the header goes beyond the stream size
- Undo the change in 0029990 because it breaks the png reader
- I checked all reader whether the stream position needed by InternalRead is correct. I explicitely rewinded the stream in InternalCheck in the cases where InternalRead expecte the stream to be at the beginning.
- in the xpm reader I found a typo: a constant "whitespace" contains the value 0000008 - this should be 0000009, the tab character.
- Fixes compilation of the demos "textout" and "drawing" where the unit cwstring is not found.

Sorry for stuffing so much into a single patch, but submitting a patch after the previous one has been applied will keep me busy for the next months.

TagsNo tags attached.
Fixed in Revision36708
FPCOldBugId
FPCTarget
Attached Files
  • fp-image-wp.patch (8,135 bytes)
    Index: packages/fcl-image/src/fpimage.inc
    ===================================================================
    --- packages/fcl-image/src/fpimage.inc	(revision 36505)
    +++ packages/fcl-image/src/fpimage.inc	(working copy)
    @@ -124,7 +124,6 @@
                 try
                   if CheckContents (str) then
                     try
    -                  str.Position := startPos;
                       FStream := str;
                       FImage := self;
                       InternalRead (str, self);
    Index: packages/fcl-image/src/fpreadbmp.pp
    ===================================================================
    --- packages/fcl-image/src/fpreadbmp.pp	(revision 36505)
    +++ packages/fcl-image/src/fpreadbmp.pp	(working copy)
    @@ -224,7 +224,7 @@
     end;
     
     procedure TFPReaderBMP.InternalRead(Stream:TStream; Img:TFPCustomImage);
    -
    +// NOTE: Assumes that BMP header already has been read
     Var
       Row, i, pallen : Integer;
       BadCompression : boolean;
    @@ -504,16 +504,21 @@
     end;
     
     function  TFPReaderBMP.InternalCheck (Stream:TStream) : boolean;
    -
    +// NOTE: Does not rewind the stream!
     var
       BFH:TBitMapFileHeader;
    +  n: Int64;
     begin
    -  stream.Read(BFH,SizeOf(BFH));
    -  {$IFDEF ENDIAN_BIG}
    -  SwapBMPFileHeader(BFH);
    -  {$ENDIF}
    -  With BFH do
    -    Result:=(bfType=BMmagic); // Just check magic number
    +  if Stream = nil then
    +    exit(false);
    +  n := SizeOf(BFH);
    +  if Stream.Read(BFH, n) = n then begin
    +   {$IFDEF ENDIAN_BIG}
    +    SwapBMPFileHeader(BFH);
    +   {$ENDIF}
    +    Result := BFH.bfType = BMmagic; // Just check magic number
    +  end else
    +    Result := false;
     end;
     
     initialization
    Index: packages/fcl-image/src/fpreadgif.pas
    ===================================================================
    --- packages/fcl-image/src/fpreadgif.pas	(revision 36505)
    +++ packages/fcl-image/src/fpreadgif.pas	(working copy)
    @@ -475,15 +475,20 @@
     function TFPReaderGif.InternalCheck(Stream: TStream): boolean;
     var
       OldPos: Int64;
    +  n: Int64;
     begin
    +  if Stream = nil then
    +    exit(false);
    +  OldPos:=Stream.Position;
       try
    -    OldPos:=Stream.Position;
    -    Stream.Read(FHeader,SizeOf(FHeader));
    -    Result:=(FHeader.Signature = 'GIF') and
    -            ((FHeader.Version = '87a') or (FHeader.Version = '89a'));
    -    Stream.Position:=OldPos;
    -  except
    -    Result:=False;
    +    n := SizeOf(FHeader);
    +    if Stream.Read(FHeader, n) = n then
    +      Result := (FHeader.Signature = 'GIF') and
    +                ((FHeader.Version = '87a') or (FHeader.Version = '89a'))
    +    else
    +      Result := false;
    +  finally
    +    Stream.Position := OldPos;
       end;
     end;
     
    Index: packages/fcl-image/src/fpreadpcx.pas
    ===================================================================
    --- packages/fcl-image/src/fpreadpcx.pas	(revision 36505)
    +++ packages/fcl-image/src/fpreadpcx.pas	(working copy)
    @@ -301,10 +301,27 @@
     end;
     
     function TFPReaderPCX.InternalCheck(Stream: TStream): boolean;
    +var
    +  hdr: TPcxHeader;
    +  n: Integer;
    +  oldPos: Int64;
     begin
    -  Result := True;
    +  if Stream = nil then
    +    exit(false);
    +  oldPos := Stream.Position;
    +  try
    +    n := SizeOf(hdr);
    +    if Stream.Read(hdr, n) = n then
    +      Result := (hdr.FileID in [$0A, $0C]) and (hdr.ColorPlanes in [1, 3, 4]) and
    +                (hdr.Version in [0, 2, 3, 5]) and (hdr.PaletteType in [1, 2])
    +    else
    +      Result := false;
    +  finally
    +    Stream.Position := oldPos;
    +  end;
     end;
     
    +
     initialization
       ImageHandlers.RegisterImageReader('PCX Format', 'pcx', TFPReaderPCX);
     end.
    Index: packages/fcl-image/src/fpreadpng.pp
    ===================================================================
    --- packages/fcl-image/src/fpreadpng.pp	(revision 36505)
    +++ packages/fcl-image/src/fpreadpng.pp	(working copy)
    @@ -805,6 +805,7 @@
         raise PNGImageException.Create('Critical chunk '+chunk.readtype+' not recognized');
     end;
     
    +// NOTE: It is assumed that signature and IDHDR chunk already have been read.
     procedure TFPReaderPNG.InternalRead (Str:TStream; Img:TFPCustomImage);
     begin
       {$ifdef FPC_Debug_Image}
    @@ -872,13 +873,17 @@
       Result.Y := Height;
     end;
     
    +// NOTE: Stream does not rewind here!
     function  TFPReaderPNG.InternalCheck (Str:TStream) : boolean;
     var SigCheck : array[0..7] of byte;
         r : integer;
    +    oldPos: Int64;
     begin
    +  oldPos := Str.Position;
       try
         // Check Signature
    -    Str.Read(SigCheck, SizeOf(SigCheck));
    +    if Str.Read(SigCheck, SizeOf(SigCheck)) <> SizeOf(SigCheck) then
    +      Exit(false);
         for r := 0 to 7 do
         begin
           If SigCheck[r] <> Signature[r] then
    Index: packages/fcl-image/src/fpreadpnm.pp
    ===================================================================
    --- packages/fcl-image/src/fpreadpnm.pp	(revision 36505)
    +++ packages/fcl-image/src/fpreadpnm.pp	(working copy)
    @@ -48,15 +48,32 @@
     
     implementation
     
    +const
    +  WhiteSpaces=[#9,#10,#13,#32];
    +  {Whitespace (TABs, CRs, LFs, blanks) are separators in the PNM Headers}
    +
    +{ The magic number at the beginning of a pnm file is 'P1', 'P2', ..., 'P7'
    +  followed by a WhiteSpace character }
     function TFPReaderPNM.InternalCheck(Stream:TStream):boolean;
    -
    +var
    +  hdr: array[0..2] of char;
    +  oldPos: Int64;
    +  n: Integer;
     begin
    -  InternalCheck:=True;
    +  if Stream = nil then
    +    exit(false);
    +  oldPos := Stream.Position;
    +  try
    +    n := SizeOf(hdr);
    +    if Stream.Read(hdr[0], n) = n then
    +      Result := (hdr[0] = 'P') and (hdr[1] in ['1'..'7']) and (hdr[2] in WhiteSpaces)
    +    else
    +      Result := false;
    +  finally
    +    Stream.Position := oldPos;
    +  end;
     end;
     
    -const
    -  WhiteSpaces=[#9,#10,#13,#32]; {Whitespace (TABs, CRs, LFs, blanks) are separators in the PNM Headers}
    -
     function DropWhiteSpaces(Stream : TStream) :Char;
     
     begin
    Index: packages/fcl-image/src/fpreadpsd.pas
    ===================================================================
    --- packages/fcl-image/src/fpreadpsd.pas	(revision 36505)
    +++ packages/fcl-image/src/fpreadpsd.pas	(working copy)
    @@ -588,14 +588,17 @@
     function TFPReaderPSD.InternalCheck(Stream: TStream): boolean;
     var
       OldPos: Int64;
    +  n: Integer;
     begin
    +  OldPos := Stream.Position;
       try
    -    OldPos:=Stream.Position;
    -    Stream.Read(FHeader,SizeOf(FHeader));
    -    Result:=(FHeader.Signature = '8BPS');
    -    Stream.Position:=OldPos;
    -  except
    -    Result:=False;
    +    n := SizeOf(FHeader);
    +    if Stream.Read(FHeader, n) = n then
    +      Result := (FHeader.Signature = '8BPS')
    +    else
    +      Result := false;
    +  finally
    +    Stream.Position := OldPos;
       end;
     end;
     
    Index: packages/fcl-image/src/fpreadtga.pp
    ===================================================================
    --- packages/fcl-image/src/fpreadtga.pp	(revision 36505)
    +++ packages/fcl-image/src/fpreadtga.pp	(working copy)
    @@ -335,11 +335,27 @@
     end;
     
     function  TFPReaderTarga.InternalCheck (Stream:TStream) : boolean;
    -
    +var
    +  hdr: TTargaHeader;
    +  oldPos: Int64;
    +  n: Integer;
     begin
    -  Result:=True;
    +  if Stream = nil then
    +    exit(false);
    +  oldPos := Stream.Position;
    +  try
    +    n := SizeOf(hdr);
    +    if Stream.Read(hdr, n) = n then
    +      Result := (hdr.ImgType in [1, 2, 3, 9, 10, 11]) and
    +        (hdr.PixelSize in [8, 16, 24, 32])
    +    else
    +      Result := false;
    +  finally
    +    Stream.Position := oldPos;
    +  end;
     end;
     
    +
     initialization
       ImageHandlers.RegisterImageReader ('TARGA Format', 'tga', TFPReaderTarga);
     end.
    Index: packages/fcl-image/src/fpreadtiff.pas
    ===================================================================
    --- packages/fcl-image/src/fpreadtiff.pas	(revision 36505)
    +++ packages/fcl-image/src/fpreadtiff.pas	(working copy)
    @@ -2013,6 +2013,7 @@
       Progress(psEnding, 100, False, Rect(0,0,0,0), '', aContinue);
     end;
     
    +// To do: Avoid raising an exception by calling ReadTiffHeader
     function TFPReaderTiff.InternalCheck(Str: TStream): boolean;
     var
       IFDStart: DWord;
    Index: packages/fcl-image/src/fpreadxpm.pp
    ===================================================================
    --- packages/fcl-image/src/fpreadxpm.pp	(revision 36505)
    +++ packages/fcl-image/src/fpreadxpm.pp	(working copy)
    @@ -39,7 +39,7 @@
     implementation
     
     const
    -  WhiteSpace = ' '#8#10#13;
    +  WhiteSpace = ' '#9#10#13;
     
     constructor TFPReaderXPM.create;
     begin
    
    fp-image-wp.patch (8,135 bytes)

Relationships

has duplicate 0032013 closedMarco van de Voort FPC "TFPCustomImage.LoadFromStream" throws exception "Invalid chunklength" when compiled with FPC v3.0.2 
related to 0032005 closedwp Lazarus "TLazIntfImage.LoadFromStream" throws "Invalid chunklength" after update to FPC 3.0.2 

Activities

wp

2017-06-15 23:15

reporter  

fp-image-wp.patch (8,135 bytes)
Index: packages/fcl-image/src/fpimage.inc
===================================================================
--- packages/fcl-image/src/fpimage.inc	(revision 36505)
+++ packages/fcl-image/src/fpimage.inc	(working copy)
@@ -124,7 +124,6 @@
             try
               if CheckContents (str) then
                 try
-                  str.Position := startPos;
                   FStream := str;
                   FImage := self;
                   InternalRead (str, self);
Index: packages/fcl-image/src/fpreadbmp.pp
===================================================================
--- packages/fcl-image/src/fpreadbmp.pp	(revision 36505)
+++ packages/fcl-image/src/fpreadbmp.pp	(working copy)
@@ -224,7 +224,7 @@
 end;
 
 procedure TFPReaderBMP.InternalRead(Stream:TStream; Img:TFPCustomImage);
-
+// NOTE: Assumes that BMP header already has been read
 Var
   Row, i, pallen : Integer;
   BadCompression : boolean;
@@ -504,16 +504,21 @@
 end;
 
 function  TFPReaderBMP.InternalCheck (Stream:TStream) : boolean;
-
+// NOTE: Does not rewind the stream!
 var
   BFH:TBitMapFileHeader;
+  n: Int64;
 begin
-  stream.Read(BFH,SizeOf(BFH));
-  {$IFDEF ENDIAN_BIG}
-  SwapBMPFileHeader(BFH);
-  {$ENDIF}
-  With BFH do
-    Result:=(bfType=BMmagic); // Just check magic number
+  if Stream = nil then
+    exit(false);
+  n := SizeOf(BFH);
+  if Stream.Read(BFH, n) = n then begin
+   {$IFDEF ENDIAN_BIG}
+    SwapBMPFileHeader(BFH);
+   {$ENDIF}
+    Result := BFH.bfType = BMmagic; // Just check magic number
+  end else
+    Result := false;
 end;
 
 initialization
Index: packages/fcl-image/src/fpreadgif.pas
===================================================================
--- packages/fcl-image/src/fpreadgif.pas	(revision 36505)
+++ packages/fcl-image/src/fpreadgif.pas	(working copy)
@@ -475,15 +475,20 @@
 function TFPReaderGif.InternalCheck(Stream: TStream): boolean;
 var
   OldPos: Int64;
+  n: Int64;
 begin
+  if Stream = nil then
+    exit(false);
+  OldPos:=Stream.Position;
   try
-    OldPos:=Stream.Position;
-    Stream.Read(FHeader,SizeOf(FHeader));
-    Result:=(FHeader.Signature = 'GIF') and
-            ((FHeader.Version = '87a') or (FHeader.Version = '89a'));
-    Stream.Position:=OldPos;
-  except
-    Result:=False;
+    n := SizeOf(FHeader);
+    if Stream.Read(FHeader, n) = n then
+      Result := (FHeader.Signature = 'GIF') and
+                ((FHeader.Version = '87a') or (FHeader.Version = '89a'))
+    else
+      Result := false;
+  finally
+    Stream.Position := OldPos;
   end;
 end;
 
Index: packages/fcl-image/src/fpreadpcx.pas
===================================================================
--- packages/fcl-image/src/fpreadpcx.pas	(revision 36505)
+++ packages/fcl-image/src/fpreadpcx.pas	(working copy)
@@ -301,10 +301,27 @@
 end;
 
 function TFPReaderPCX.InternalCheck(Stream: TStream): boolean;
+var
+  hdr: TPcxHeader;
+  n: Integer;
+  oldPos: Int64;
 begin
-  Result := True;
+  if Stream = nil then
+    exit(false);
+  oldPos := Stream.Position;
+  try
+    n := SizeOf(hdr);
+    if Stream.Read(hdr, n) = n then
+      Result := (hdr.FileID in [$0A, $0C]) and (hdr.ColorPlanes in [1, 3, 4]) and
+                (hdr.Version in [0, 2, 3, 5]) and (hdr.PaletteType in [1, 2])
+    else
+      Result := false;
+  finally
+    Stream.Position := oldPos;
+  end;
 end;
 
+
 initialization
   ImageHandlers.RegisterImageReader('PCX Format', 'pcx', TFPReaderPCX);
 end.
Index: packages/fcl-image/src/fpreadpng.pp
===================================================================
--- packages/fcl-image/src/fpreadpng.pp	(revision 36505)
+++ packages/fcl-image/src/fpreadpng.pp	(working copy)
@@ -805,6 +805,7 @@
     raise PNGImageException.Create('Critical chunk '+chunk.readtype+' not recognized');
 end;
 
+// NOTE: It is assumed that signature and IDHDR chunk already have been read.
 procedure TFPReaderPNG.InternalRead (Str:TStream; Img:TFPCustomImage);
 begin
   {$ifdef FPC_Debug_Image}
@@ -872,13 +873,17 @@
   Result.Y := Height;
 end;
 
+// NOTE: Stream does not rewind here!
 function  TFPReaderPNG.InternalCheck (Str:TStream) : boolean;
 var SigCheck : array[0..7] of byte;
     r : integer;
+    oldPos: Int64;
 begin
+  oldPos := Str.Position;
   try
     // Check Signature
-    Str.Read(SigCheck, SizeOf(SigCheck));
+    if Str.Read(SigCheck, SizeOf(SigCheck)) <> SizeOf(SigCheck) then
+      Exit(false);
     for r := 0 to 7 do
     begin
       If SigCheck[r] <> Signature[r] then
Index: packages/fcl-image/src/fpreadpnm.pp
===================================================================
--- packages/fcl-image/src/fpreadpnm.pp	(revision 36505)
+++ packages/fcl-image/src/fpreadpnm.pp	(working copy)
@@ -48,15 +48,32 @@
 
 implementation
 
+const
+  WhiteSpaces=[#9,#10,#13,#32];
+  {Whitespace (TABs, CRs, LFs, blanks) are separators in the PNM Headers}
+
+{ The magic number at the beginning of a pnm file is 'P1', 'P2', ..., 'P7'
+  followed by a WhiteSpace character }
 function TFPReaderPNM.InternalCheck(Stream:TStream):boolean;
-
+var
+  hdr: array[0..2] of char;
+  oldPos: Int64;
+  n: Integer;
 begin
-  InternalCheck:=True;
+  if Stream = nil then
+    exit(false);
+  oldPos := Stream.Position;
+  try
+    n := SizeOf(hdr);
+    if Stream.Read(hdr[0], n) = n then
+      Result := (hdr[0] = 'P') and (hdr[1] in ['1'..'7']) and (hdr[2] in WhiteSpaces)
+    else
+      Result := false;
+  finally
+    Stream.Position := oldPos;
+  end;
 end;
 
-const
-  WhiteSpaces=[#9,#10,#13,#32]; {Whitespace (TABs, CRs, LFs, blanks) are separators in the PNM Headers}
-
 function DropWhiteSpaces(Stream : TStream) :Char;
 
 begin
Index: packages/fcl-image/src/fpreadpsd.pas
===================================================================
--- packages/fcl-image/src/fpreadpsd.pas	(revision 36505)
+++ packages/fcl-image/src/fpreadpsd.pas	(working copy)
@@ -588,14 +588,17 @@
 function TFPReaderPSD.InternalCheck(Stream: TStream): boolean;
 var
   OldPos: Int64;
+  n: Integer;
 begin
+  OldPos := Stream.Position;
   try
-    OldPos:=Stream.Position;
-    Stream.Read(FHeader,SizeOf(FHeader));
-    Result:=(FHeader.Signature = '8BPS');
-    Stream.Position:=OldPos;
-  except
-    Result:=False;
+    n := SizeOf(FHeader);
+    if Stream.Read(FHeader, n) = n then
+      Result := (FHeader.Signature = '8BPS')
+    else
+      Result := false;
+  finally
+    Stream.Position := OldPos;
   end;
 end;
 
Index: packages/fcl-image/src/fpreadtga.pp
===================================================================
--- packages/fcl-image/src/fpreadtga.pp	(revision 36505)
+++ packages/fcl-image/src/fpreadtga.pp	(working copy)
@@ -335,11 +335,27 @@
 end;
 
 function  TFPReaderTarga.InternalCheck (Stream:TStream) : boolean;
-
+var
+  hdr: TTargaHeader;
+  oldPos: Int64;
+  n: Integer;
 begin
-  Result:=True;
+  if Stream = nil then
+    exit(false);
+  oldPos := Stream.Position;
+  try
+    n := SizeOf(hdr);
+    if Stream.Read(hdr, n) = n then
+      Result := (hdr.ImgType in [1, 2, 3, 9, 10, 11]) and
+        (hdr.PixelSize in [8, 16, 24, 32])
+    else
+      Result := false;
+  finally
+    Stream.Position := oldPos;
+  end;
 end;
 
+
 initialization
   ImageHandlers.RegisterImageReader ('TARGA Format', 'tga', TFPReaderTarga);
 end.
Index: packages/fcl-image/src/fpreadtiff.pas
===================================================================
--- packages/fcl-image/src/fpreadtiff.pas	(revision 36505)
+++ packages/fcl-image/src/fpreadtiff.pas	(working copy)
@@ -2013,6 +2013,7 @@
   Progress(psEnding, 100, False, Rect(0,0,0,0), '', aContinue);
 end;
 
+// To do: Avoid raising an exception by calling ReadTiffHeader
 function TFPReaderTiff.InternalCheck(Str: TStream): boolean;
 var
   IFDStart: DWord;
Index: packages/fcl-image/src/fpreadxpm.pp
===================================================================
--- packages/fcl-image/src/fpreadxpm.pp	(revision 36505)
+++ packages/fcl-image/src/fpreadxpm.pp	(working copy)
@@ -39,7 +39,7 @@
 implementation
 
 const
-  WhiteSpace = ' '#8#10#13;
+  WhiteSpace = ' '#9#10#13;
 
 constructor TFPReaderXPM.create;
 begin
fp-image-wp.patch (8,135 bytes)

wp

2017-06-15 23:17

reporter   ~0101171

Last edited: 2017-06-20 12:45

View 2 revisions

I cannot add relationships here: These are those already mentioned in the text

0032005: "TLazIntfImage.LoadFromStream" throws "Invalid chunklength" after update to FPC 3.0.2
0029990: Due to changes in FCL, running empty Lazarus GUI application fails with exception "PNGImageException : Invalid chunklength".

Dimitrios Chr. Ioannidis

2017-06-17 08:50

reporter   ~0101199

Last edited: 2017-06-17 08:56

View 3 revisions

"- "textout" and "drawing" do not compile because unit cwstring is not found (it can safely be removed from "uses"). "

No need to remove it, just do {$ifdef unix}cwstring,{$endif}.

It's in the documentation https://www.freepascal.org/docs-html/3.0.0/rtl/cwstring/index.html.

Marco van de Voort

2017-07-01 12:58

manager   ~0101402

(If rewinding after header is a real requirement, maybe the calling code should enforce it instead of adding it to each reader ?)

Michael Van Canneyt

2017-07-09 11:13

administrator   ~0101629

Applied (slightly modified) versions of the patch, thank you very much.

wp

2017-07-09 13:44

reporter   ~0101634

Thanks for applying. You did not apply the patch for fpreadtga - is there something wrong with it?

Michael Van Canneyt

2017-07-09 15:58

administrator   ~0101637

Sorry, I simply forgot to apply that part of the patch
(I split out the original patch per file)

wp

2017-07-10 14:57

reporter   ~0101650

Thank you.

Issue History

Date Modified Username Field Change
2017-06-15 23:13 wp New Issue
2017-06-15 23:15 wp File Added: fp-image-wp.patch
2017-06-15 23:17 wp Note Added: 0101171
2017-06-15 23:20 wp Relationship added related to 0032005
2017-06-17 08:50 Dimitrios Chr. Ioannidis Note Added: 0101199
2017-06-17 08:50 Dimitrios Chr. Ioannidis Note Edited: 0101199 View Revisions
2017-06-17 08:56 Dimitrios Chr. Ioannidis Note Edited: 0101199 View Revisions
2017-06-20 12:45 wp Note Edited: 0101171 View Revisions
2017-07-01 12:58 Marco van de Voort Note Added: 0101402
2017-07-01 13:59 Marco van de Voort Relationship added related to 0032013
2017-07-01 13:59 Marco van de Voort Relationship deleted related to 0032013
2017-07-01 13:59 Marco van de Voort Relationship added has duplicate 0032013
2017-07-09 10:45 Michael Van Canneyt Assigned To => Michael Van Canneyt
2017-07-09 10:45 Michael Van Canneyt Status new => assigned
2017-07-09 11:13 Michael Van Canneyt Fixed in Revision => 36704
2017-07-09 11:13 Michael Van Canneyt Note Added: 0101629
2017-07-09 11:13 Michael Van Canneyt Status assigned => resolved
2017-07-09 11:13 Michael Van Canneyt Fixed in Version => 3.1.1
2017-07-09 11:13 Michael Van Canneyt Resolution open => fixed
2017-07-09 11:13 Michael Van Canneyt Target Version => 3.2.0
2017-07-09 13:44 wp Note Added: 0101634
2017-07-09 13:44 wp Status resolved => feedback
2017-07-09 13:44 wp Resolution fixed => reopened
2017-07-09 15:58 Michael Van Canneyt Fixed in Revision 36704 => 36708
2017-07-09 15:58 Michael Van Canneyt Note Added: 0101637
2017-07-09 15:58 Michael Van Canneyt Status feedback => resolved
2017-07-09 15:58 Michael Van Canneyt Resolution reopened => fixed
2017-07-10 14:57 wp Note Added: 0101650
2017-07-10 14:57 wp Status resolved => closed