Hi Alain, Thanks for sharing your patch. Others have encountered similar issues. This is the case when the calibration coefficients are incorrect. These are hard programmed into devices from the factory. It are typically clone devices, which don't implement all DS4 functionality properly. Can you try printing all the variables (gyro_speed_plus,.. acc_z_minus) for your device as decimal numbers from the get_calibration_data function? I have been considering to add a little bit of clone support code if possible to the new hid-playstation as long as it doesn't pollute the code too much or causes issues. Thanks, Roderick On Sun, Dec 25, 2022 at 4:08 PM Alain Carlucci <alain.carlucci@xxxxxxxxx> wrote: > > Hello, > > Today I connected a partially broken DS4 via USB and got a kernel > panic with a division by zero in the hid-sony driver. > > The issue is caused by sens_denom=0 in the sensor calibration data, > which triggers a division by zero when dualshock4_parse_report() is > invoked, the division happens in the mult_frac() macro. > > This patch applies a workaround that allows the DS4 to be used even > with a broken sensor: if the denominator sent by the device is zero, > it is replaced with 1 and a warning is emitted. > > Signed-off-by: Alain Carlucci <alain.carlucci@xxxxxxxxx> > --- > drivers/hid/hid-sony.c | 18 ++++++++++++++++++ > 1 file changed, 18 insertions(+) > > diff --git a/drivers/hid/hid-sony.c b/drivers/hid/hid-sony.c > index 13125997a..f8b05cb29 100644 > --- a/drivers/hid/hid-sony.c > +++ b/drivers/hid/hid-sony.c > @@ -1714,6 +1714,7 @@ static int dualshock4_get_calibration_data(struct sony_sc *sc) > short acc_z_plus, acc_z_minus; > int speed_2x; > int range_2g; > + int calib_id; > > /* For Bluetooth we use a different request, which supports CRC. > * Note: in Bluetooth mode feature report 0x02 also changes the state > @@ -1858,6 +1859,23 @@ static int dualshock4_get_calibration_data(struct sony_sc *sc) > sc->ds4_calib_data[5].sens_numer = 2*DS4_ACC_RES_PER_G; > sc->ds4_calib_data[5].sens_denom = range_2g; > > + for (calib_id = 0; calib_id < 6; calib_id++) { > + /* Ensure there are no denominators equal to zero to prevent > + * crashes while dividing by that number. > + */ > + > + if (sc->ds4_calib_data[calib_id].sens_denom != 0) { > + /* Denominator OK, skip this */ > + continue; > + } > + > + sc->ds4_calib_data[calib_id].sens_denom = 1; > + > + hid_warn(sc->hdev, > + "DualShock 4 USB dongle: invalid calibration for sensor %d\n", > + calib_id); > + } > + > err_stop: > kfree(buf); > return ret; > -- > 2.39.0