Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4b382318 authored by Guennadi Liakhovetski's avatar Guennadi Liakhovetski Committed by Wolfram Sang
Browse files

i2c: sh_mobile: eliminate an open-coded "goto" loop



Eliminate an open-coded "goto" loop by introducing a function.

Signed-off-by: default avatarGuennadi Liakhovetski <g.liakhovetski@gmx.de>
Signed-off-by: default avatarWolfram Sang <wolfram@the-dreams.de>
parent 5687265b
Loading
Loading
Loading
Loading
+34 −26
Original line number Diff line number Diff line
@@ -495,6 +495,37 @@ static int start_ch(struct sh_mobile_i2c_data *pd, struct i2c_msg *usr_msg)
	return 0;
}

static int poll_busy(struct sh_mobile_i2c_data *pd)
{
	int i;

	for (i = 1000; i; i--) {
		u_int8_t val = iic_rd(pd, ICSR);

		dev_dbg(pd->dev, "val 0x%02x pd->sr 0x%02x\n", val, pd->sr);

		/* the interrupt handler may wake us up before the
		 * transfer is finished, so poll the hardware
		 * until we're done.
		 */
		if (!(val & ICSR_BUSY)) {
			/* handle missing acknowledge and arbitration lost */
			if ((val | pd->sr) & (ICSR_TACK | ICSR_AL))
				return -EIO;
			break;
		}

		udelay(10);
	}

	if (!i) {
		dev_err(pd->dev, "Polling timed out\n");
		return -ETIMEDOUT;
	}

	return 0;
}

static int sh_mobile_i2c_xfer(struct i2c_adapter *adapter,
			      struct i2c_msg *msgs,
			      int num)
@@ -502,8 +533,7 @@ static int sh_mobile_i2c_xfer(struct i2c_adapter *adapter,
	struct sh_mobile_i2c_data *pd = i2c_get_adapdata(adapter);
	struct i2c_msg	*msg;
	int err = 0;
	u_int8_t val;
	int i, k, retry_count;
	int i, k;

	activate_ch(pd);

@@ -527,33 +557,11 @@ static int sh_mobile_i2c_xfer(struct i2c_adapter *adapter,
			break;
		}

		retry_count = 1000;
again:
		val = iic_rd(pd, ICSR);

		dev_dbg(pd->dev, "val 0x%02x pd->sr 0x%02x\n", val, pd->sr);

		/* the interrupt handler may wake us up before the
		 * transfer is finished, so poll the hardware
		 * until we're done.
		 */
		if (val & ICSR_BUSY) {
			udelay(10);
			if (retry_count--)
				goto again;

			err = -EIO;
			dev_err(pd->dev, "Polling timed out\n");
		err = poll_busy(pd);
		if (err < 0)
			break;
	}

		/* handle missing acknowledge and arbitration lost */
		if ((val | pd->sr) & (ICSR_TACK | ICSR_AL)) {
			err = -EIO;
			break;
		}
	}

	deactivate_ch(pd);

	if (!err)