[Vm-dev] Suspect divideByZero protection in JPEGReaderPlugin

David T. Lewis lewis at mail.msen.com
Sun Dec 23 01:19:57 UTC 2012


On Sun, Dec 23, 2012 at 01:12:03AM +0100, Nicolas Cellier wrote:
>  
> There is an incomplete division by zero protection in JPEGReaderPlugin:
> 
> nextSampleY
>         ...snip...
>         (sx = 0 and: [sy = 0]) ifFalse:[
>                 dx := dx // sx.
>                 dy := dy // sy.
>         ].
> 
> It only protect if both sx and sy are 0, but not in case (sx = 0 xor: sy = 0)
> Shouldn't it be:
> 
>         (sx = 0 or: [sy = 0]) ifFalse:[
>                 dx := dx // sx.
>                 dy := dy // sy.
>         ].
> 
> Same in nextSampleCb nextSampleCr...
> 
> Nicolas

Good catch!

Patched for interpreter VM in VMMaker-dtl.261, and change set attached.

I wrote it this way for readability:

	(sx ~= 0 and: [sy ~= 0]) ifTrue: [
		dx := dx // sx.
		dy := dy // sy.
	].

Dave

-------------- next part --------------
'From Squeak3.11alpha of 22 December 2012 [latest update: #12324] on 22 December 2012 at 7:47:43 pm'!

!JPEGReaderPlugin methodsFor: 'decoding' stamp: 'dtl 12/22/2012 19:42'!
nextSampleCb
	| dx dy blockIndex sampleIndex sample curX sx sy |
	<inline: true>
	dx := curX := cbComponent at: CurrentXIndex.
	dy := cbComponent at: CurrentYIndex.
	sx := cbComponent at: HScaleIndex.
	sy := cbComponent at: VScaleIndex.
	(sx ~= 0 and: [sy ~= 0]) ifTrue: [
		dx := dx // sx.
		dy := dy // sy.
	].
	blockIndex := (dy bitShift: -3) * (cbComponent at: BlockWidthIndex) + (dx bitShift: -3).
	sampleIndex := ((dy bitAnd: 7) bitShift: 3) + (dx bitAnd: 7).
	sample := (cbBlocks at: blockIndex) at: sampleIndex.
	curX := curX + 1.
	curX < ((cbComponent at: MCUWidthIndex) * 8) ifTrue:[
		cbComponent at: CurrentXIndex put: curX.
	] ifFalse:[
		cbComponent at: CurrentXIndex put: 0.
		cbComponent at: CurrentYIndex put: (cbComponent at: CurrentYIndex) + 1.
	].
	^ sample! !

!JPEGReaderPlugin methodsFor: 'decoding' stamp: 'dtl 12/22/2012 19:42'!
nextSampleCr
	| dx dy blockIndex sampleIndex sample curX sx sy |
	<inline: true>
	dx := curX := crComponent at: CurrentXIndex.
	dy := crComponent at: CurrentYIndex.
	sx := crComponent at: HScaleIndex.
	sy := crComponent at: VScaleIndex.
	(sx ~= 0 and: [sy ~= 0]) ifTrue: [
		dx := dx // sx.
		dy := dy // sy.
	].
	blockIndex := (dy bitShift: -3) * (crComponent at: BlockWidthIndex) + (dx bitShift: -3).
	sampleIndex := ((dy bitAnd: 7) bitShift: 3) + (dx bitAnd: 7).
	sample := (crBlocks at: blockIndex) at: sampleIndex.
	curX := curX + 1.
	curX < ((crComponent at: MCUWidthIndex) * 8) ifTrue:[
		crComponent at: CurrentXIndex put: curX.
	] ifFalse:[
		crComponent at: CurrentXIndex put: 0.
		crComponent at: CurrentYIndex put: (crComponent at: CurrentYIndex) + 1.
	].
	^ sample! !

!JPEGReaderPlugin methodsFor: 'decoding' stamp: 'dtl 12/22/2012 19:42'!
nextSampleFrom: aComponent blocks: aBlockArray
	| dx dy blockIndex sampleIndex sample curX sx sy |
	<var: #aComponent type: 'int *'>
	<var: #aBlockArray type: 'int **'>
	<inline: true>
	dx := curX := aComponent at: CurrentXIndex.
	dy := aComponent at: CurrentYIndex.
	sx := aComponent at: HScaleIndex.
	sy := aComponent at: VScaleIndex.
	(sx ~= 0 and: [sy ~= 0]) ifTrue: [
		dx := dx // sx.
		dy := dy // sy.
	].
	blockIndex := (dy bitShift: -3) * (aComponent at: BlockWidthIndex) + (dx bitShift: -3).
	sampleIndex := ((dy bitAnd: 7) bitShift: 3) + (dx bitAnd: 7).
	sample := (aBlockArray at: blockIndex) at: sampleIndex.
	curX := curX + 1.
	curX < ((aComponent at: MCUWidthIndex) * 8) ifTrue:[
		aComponent at: CurrentXIndex put: curX.
	] ifFalse:[
		aComponent at: CurrentXIndex put: 0.
		aComponent at: CurrentYIndex put: (aComponent at: CurrentYIndex) + 1.
	].
	^ sample! !

!JPEGReaderPlugin methodsFor: 'decoding' stamp: 'dtl 12/22/2012 19:42'!
nextSampleY
	| dx dy blockIndex sampleIndex sample curX sx sy |
	<inline: true>
	dx := curX := yComponent at: CurrentXIndex.
	dy := yComponent at: CurrentYIndex.
	sx := yComponent at: HScaleIndex.
	sy := yComponent at: VScaleIndex.
	(sx ~= 0 and: [sy ~= 0]) ifTrue: [
		dx := dx // sx.
		dy := dy // sy.
	].
	blockIndex := (dy bitShift: -3) * (yComponent at: BlockWidthIndex) + (dx bitShift: -3).
	sampleIndex := ((dy bitAnd: 7) bitShift: 3) + (dx bitAnd: 7).
	sample := (yBlocks at: blockIndex) at: sampleIndex.
	curX := curX + 1.
	curX < ((yComponent at: MCUWidthIndex) * 8) ifTrue:[
		yComponent at: CurrentXIndex put: curX.
	] ifFalse:[
		yComponent at: CurrentXIndex put: 0.
		yComponent at: CurrentYIndex put: (yComponent at: CurrentYIndex) + 1.
	].
	^ sample! !



More information about the Vm-dev mailing list