@@ -345,10 +345,10 @@ public void Dispose()
345345 }
346346
347347 /// <summary>
348- /// Returns the correct colorspace based on the image component count
348+ /// Returns the correct colorspace based on the image component count and the jpeg frame components.
349349 /// </summary>
350350 /// <returns>The <see cref="JpegColorSpace"/></returns>
351- private JpegColorSpace DeduceJpegColorSpace ( byte componentCount )
351+ private JpegColorSpace DeduceJpegColorSpace ( byte componentCount , JpegComponent [ ] components )
352352 {
353353 if ( componentCount == 1 )
354354 {
@@ -362,6 +362,12 @@ private JpegColorSpace DeduceJpegColorSpace(byte componentCount)
362362 return JpegColorSpace . RGB ;
363363 }
364364
365+ // If the component Id's are R, G, B in ASCII the colorspace is RGB and not YCbCr.
366+ if ( components [ 2 ] . Id == 66 && components [ 1 ] . Id == 71 && components [ 0 ] . Id == 82 )
367+ {
368+ return JpegColorSpace . RGB ;
369+ }
370+
365371 // Some images are poorly encoded and contain incorrect colorspace transform metadata.
366372 // We ignore that and always fall back to the default colorspace.
367373 return JpegColorSpace . YCbCr ;
@@ -836,60 +842,60 @@ private void ProcessStartOfFrameMarker(BufferedReadStream stream, int remaining,
836842
837843 // 1 byte: Number of components
838844 byte componentCount = this . temp [ 5 ] ;
839- this . ColorSpace = this . DeduceJpegColorSpace ( componentCount ) ;
840-
841- this . Metadata . GetJpegMetadata ( ) . ColorType = this . ColorSpace == JpegColorSpace . Grayscale ? JpegColorType . Luminance : JpegColorType . YCbCr ;
842845
843846 this . Frame = new JpegFrame ( frameMarker , precision , frameWidth , frameHeight , componentCount ) ;
844847
845- if ( ! metadataOnly )
848+ remaining -= length ;
849+
850+ // Validate: remaining part must be equal to components * 3
851+ const int componentBytes = 3 ;
852+ if ( remaining != componentCount * componentBytes )
846853 {
847- remaining -= length ;
854+ JpegThrowHelper . ThrowBadMarker ( "SOFn" , remaining ) ;
855+ }
848856
849- // Validate: remaining part must be equal to components * 3
850- const int componentBytes = 3 ;
851- if ( remaining != componentCount * componentBytes )
852- {
853- JpegThrowHelper . ThrowBadMarker ( "SOFn" , remaining ) ;
854- }
857+ // components*3 bytes: component data
858+ stream . Read ( this . temp , 0 , remaining ) ;
859+
860+ // No need to pool this. They max out at 4
861+ this . Frame . ComponentIds = new byte [ componentCount ] ;
862+ this . Frame . ComponentOrder = new byte [ componentCount ] ;
863+ this . Frame . Components = new JpegComponent [ componentCount ] ;
855864
856- // components*3 bytes: component data
857- stream . Read ( this . temp , 0 , remaining ) ;
865+ int maxH = 0 ;
866+ int maxV = 0 ;
867+ int index = 0 ;
868+ for ( int i = 0 ; i < componentCount ; i ++ )
869+ {
870+ byte hv = this . temp [ index + 1 ] ;
871+ int h = ( hv >> 4 ) & 15 ;
872+ int v = hv & 15 ;
858873
859- // No need to pool this. They max out at 4
860- this . Frame . ComponentIds = new byte [ componentCount ] ;
861- this . Frame . ComponentOrder = new byte [ componentCount ] ;
862- this . Frame . Components = new JpegComponent [ componentCount ] ;
874+ if ( maxH < h )
875+ {
876+ maxH = h ;
877+ }
863878
864- int maxH = 0 ;
865- int maxV = 0 ;
866- int index = 0 ;
867- for ( int i = 0 ; i < componentCount ; i ++ )
879+ if ( maxV < v )
868880 {
869- byte hv = this . temp [ index + 1 ] ;
870- int h = ( hv >> 4 ) & 15 ;
871- int v = hv & 15 ;
881+ maxV = v ;
882+ }
872883
873- if ( maxH < h )
874- {
875- maxH = h ;
876- }
884+ var component = new JpegComponent ( this . Configuration . MemoryAllocator , this . Frame , this . temp [ index ] , h , v , this . temp [ index + 2 ] , i ) ;
877885
878- if ( maxV < v )
879- {
880- maxV = v ;
881- }
886+ this . Frame . Components [ i ] = component ;
887+ this . Frame . ComponentIds [ i ] = component . Id ;
882888
883- var component = new JpegComponent ( this . Configuration . MemoryAllocator , this . Frame , this . temp [ index ] , h , v , this . temp [ index + 2 ] , i ) ;
889+ index += componentBytes ;
890+ }
884891
885- this . Frame . Components [ i ] = component ;
886- this . Frame . ComponentIds [ i ] = component . Id ;
892+ this . ColorSpace = this . DeduceJpegColorSpace ( componentCount , this . Frame . Components ) ;
887893
888- index += componentBytes ;
889- }
894+ this . Metadata . GetJpegMetadata ( ) . ColorType = this . ColorSpace == JpegColorSpace . Grayscale ? JpegColorType . Luminance : JpegColorType . YCbCr ;
890895
896+ if ( ! metadataOnly )
897+ {
891898 this . Frame . Init ( maxH , maxV ) ;
892-
893899 this . scanDecoder . InjectFrameData ( this . Frame , this ) ;
894900 }
895901 }
0 commit comments