char: i.MX: Add support for "TX complete" interrupt
Add support for "TX complete"/TXDC interrupt generate by real HW since it is needed to support guests other than Linux. Based on the patch by Bill Paul as found here: https://bugs.launchpad.net/qemu/+bug/1753314 Cc: qemu-devel@nongnu.org Cc: qemu-arm@nongnu.org Cc: Bill Paul <wpaul@windriver.com> Cc: Peter Maydell <peter.maydell@linaro.org> Signed-off-by: Bill Paul <wpaul@windriver.com> Signed-off-by: Andrey Smirnov <andrew.smirnov@gmail.com> Message-id: 20180315191141.6789-2-andrew.smirnov@gmail.com Reviewed-by: Peter Maydell <peter.maydell@linaro.org> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
parent
824e4a12f3
commit
46d3fb634c
|
@ -37,8 +37,8 @@
|
||||||
|
|
||||||
static const VMStateDescription vmstate_imx_serial = {
|
static const VMStateDescription vmstate_imx_serial = {
|
||||||
.name = TYPE_IMX_SERIAL,
|
.name = TYPE_IMX_SERIAL,
|
||||||
.version_id = 1,
|
.version_id = 2,
|
||||||
.minimum_version_id = 1,
|
.minimum_version_id = 2,
|
||||||
.fields = (VMStateField[]) {
|
.fields = (VMStateField[]) {
|
||||||
VMSTATE_INT32(readbuff, IMXSerialState),
|
VMSTATE_INT32(readbuff, IMXSerialState),
|
||||||
VMSTATE_UINT32(usr1, IMXSerialState),
|
VMSTATE_UINT32(usr1, IMXSerialState),
|
||||||
|
@ -50,6 +50,7 @@ static const VMStateDescription vmstate_imx_serial = {
|
||||||
VMSTATE_UINT32(ubmr, IMXSerialState),
|
VMSTATE_UINT32(ubmr, IMXSerialState),
|
||||||
VMSTATE_UINT32(ubrc, IMXSerialState),
|
VMSTATE_UINT32(ubrc, IMXSerialState),
|
||||||
VMSTATE_UINT32(ucr3, IMXSerialState),
|
VMSTATE_UINT32(ucr3, IMXSerialState),
|
||||||
|
VMSTATE_UINT32(ucr4, IMXSerialState),
|
||||||
VMSTATE_END_OF_LIST()
|
VMSTATE_END_OF_LIST()
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
@ -71,6 +72,11 @@ static void imx_update(IMXSerialState *s)
|
||||||
* unfortunately.
|
* unfortunately.
|
||||||
*/
|
*/
|
||||||
mask = (s->ucr1 & UCR1_TXMPTYEN) ? USR2_TXFE : 0;
|
mask = (s->ucr1 & UCR1_TXMPTYEN) ? USR2_TXFE : 0;
|
||||||
|
/*
|
||||||
|
* TCEN and TXDC are both bit 3
|
||||||
|
*/
|
||||||
|
mask |= s->ucr4 & UCR4_TCEN;
|
||||||
|
|
||||||
usr2 = s->usr2 & mask;
|
usr2 = s->usr2 & mask;
|
||||||
|
|
||||||
qemu_set_irq(s->irq, usr1 || usr2);
|
qemu_set_irq(s->irq, usr1 || usr2);
|
||||||
|
@ -163,6 +169,8 @@ static uint64_t imx_serial_read(void *opaque, hwaddr offset,
|
||||||
return s->ucr3;
|
return s->ucr3;
|
||||||
|
|
||||||
case 0x23: /* UCR4 */
|
case 0x23: /* UCR4 */
|
||||||
|
return s->ucr4;
|
||||||
|
|
||||||
case 0x29: /* BRM Incremental */
|
case 0x29: /* BRM Incremental */
|
||||||
return 0x0; /* TODO */
|
return 0x0; /* TODO */
|
||||||
|
|
||||||
|
@ -191,8 +199,10 @@ static void imx_serial_write(void *opaque, hwaddr offset,
|
||||||
* qemu_chr_fe_write and background I/O callbacks */
|
* qemu_chr_fe_write and background I/O callbacks */
|
||||||
qemu_chr_fe_write_all(&s->chr, &ch, 1);
|
qemu_chr_fe_write_all(&s->chr, &ch, 1);
|
||||||
s->usr1 &= ~USR1_TRDY;
|
s->usr1 &= ~USR1_TRDY;
|
||||||
|
s->usr2 &= ~USR2_TXDC;
|
||||||
imx_update(s);
|
imx_update(s);
|
||||||
s->usr1 |= USR1_TRDY;
|
s->usr1 |= USR1_TRDY;
|
||||||
|
s->usr2 |= USR2_TXDC;
|
||||||
imx_update(s);
|
imx_update(s);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -265,8 +275,12 @@ static void imx_serial_write(void *opaque, hwaddr offset,
|
||||||
s->ucr3 = value & 0xffff;
|
s->ucr3 = value & 0xffff;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x2d: /* UTS1 */
|
|
||||||
case 0x23: /* UCR4 */
|
case 0x23: /* UCR4 */
|
||||||
|
s->ucr4 = value & 0xffff;
|
||||||
|
imx_update(s);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 0x2d: /* UTS1 */
|
||||||
qemu_log_mask(LOG_UNIMP, "[%s]%s: Unimplemented reg 0x%"
|
qemu_log_mask(LOG_UNIMP, "[%s]%s: Unimplemented reg 0x%"
|
||||||
HWADDR_PRIx "\n", TYPE_IMX_SERIAL, __func__, offset);
|
HWADDR_PRIx "\n", TYPE_IMX_SERIAL, __func__, offset);
|
||||||
/* TODO */
|
/* TODO */
|
||||||
|
|
|
@ -67,6 +67,8 @@
|
||||||
#define UCR2_RXEN (1<<1) /* Receiver enable */
|
#define UCR2_RXEN (1<<1) /* Receiver enable */
|
||||||
#define UCR2_SRST (1<<0) /* Reset complete */
|
#define UCR2_SRST (1<<0) /* Reset complete */
|
||||||
|
|
||||||
|
#define UCR4_TCEN BIT(3) /* TX complete interrupt enable */
|
||||||
|
|
||||||
#define UTS1_TXEMPTY (1<<6)
|
#define UTS1_TXEMPTY (1<<6)
|
||||||
#define UTS1_RXEMPTY (1<<5)
|
#define UTS1_RXEMPTY (1<<5)
|
||||||
#define UTS1_TXFULL (1<<4)
|
#define UTS1_TXFULL (1<<4)
|
||||||
|
@ -95,6 +97,7 @@ typedef struct IMXSerialState {
|
||||||
uint32_t ubmr;
|
uint32_t ubmr;
|
||||||
uint32_t ubrc;
|
uint32_t ubrc;
|
||||||
uint32_t ucr3;
|
uint32_t ucr3;
|
||||||
|
uint32_t ucr4;
|
||||||
|
|
||||||
qemu_irq irq;
|
qemu_irq irq;
|
||||||
CharBackend chr;
|
CharBackend chr;
|
||||||
|
|
Loading…
Reference in a new issue