Opened 11 years ago

Closed 8 years ago

## #823 closed defect (fixed)

# arithmetic-shift fails in extreme cases

Reported by: | sjamaan | Owned by: | |
---|---|---|---|

Priority: | minor | Milestone: | 4.10.0 |

Component: | core libraries | Version: | 4.7.x |

Keywords: | edge cases, numbers, shifting, overflow | Cc: | |

Estimated difficulty: |

### Description

I don't know whether it's worth the trouble to fix this, but I'll put it on here so at least it's documented.

`(arithmetic-shift -123 most-negative-fixnum) => -123`

This should be `-1`

. It fails because in chicken.h the `C_i_fixnum_arithmetic_shift`

function calls `C_fixnum_shift_right`

with the negated value of the shift amount. This overflows and wraps around to zero.

Fixing it would be simplest by just inlining the shift and negating _after_ unboxing. This is easy, but there are some other places that call `C_fixnum_shift_right`

in this way.

This code is obviously wrong but I'm not sure it's worth fixing, since it's such an extreme edge case (if you subtract 1 from the shift amount you get an error that the argument is not a fixnum). On the other hand, not fixing it just seems, I dunno... lazy and possibly dangerous. :)

### Change History (3)

### comment:1 Changed 9 years ago by

Summary: | arithmetic-shift fails in exactly one edge case → arithmetic-shift fails in extreme cases |
---|

### comment:2 Changed 9 years ago by

Milestone: | 4.9.0 → 4.10.0 |
---|

Not important enough to delay 4.9.0 any longer

### comment:3 Changed 8 years ago by

Resolution: | → fixed |
---|---|

Status: | new → closed |

This has been fixed by the numbers integration in CHICKEN 5. It's not important enough to fix in CHICKEN 4.

**Note:**See TracTickets for help on using tickets.

Turns out there's also a bug when shifting more than C_WORD_SIZE positions.

According to the C spec, shifting more than the number of bits in the type is undefined (#3 in section 6.5.7, "bitwise shift operators").

Shifting negative values is also pretty ill-defined (#4 and #5, final sentence in both).

C: Don't you just

loveit?