From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1LKYUk-0003jR-TQ for qemu-devel@nongnu.org; Wed, 07 Jan 2009 08:30:51 -0500 Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1LKYUi-0003i6-5V for qemu-devel@nongnu.org; Wed, 07 Jan 2009 08:30:49 -0500 Received: from [199.232.76.173] (port=38995 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1LKYUg-0003hZ-9x for qemu-devel@nongnu.org; Wed, 07 Jan 2009 08:30:46 -0500 Received: from savannah.gnu.org ([199.232.41.3]:40150 helo=sv.gnu.org) by monty-python.gnu.org with esmtps (TLS-1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1LKYUf-0004kr-SA for qemu-devel@nongnu.org; Wed, 07 Jan 2009 08:30:46 -0500 Received: from cvs.savannah.gnu.org ([199.232.41.69]) by sv.gnu.org with esmtp (Exim 4.63) (envelope-from ) id 1LKYUe-0000w8-9c for qemu-devel@nongnu.org; Wed, 07 Jan 2009 13:30:44 +0000 Received: from edgar_igl by cvs.savannah.gnu.org with local (Exim 4.63) (envelope-from ) id 1LKYUd-0000w2-9R for qemu-devel@nongnu.org; Wed, 07 Jan 2009 13:30:43 +0000 MIME-Version: 1.0 Errors-To: edgar_igl Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit From: "Edgar E. Iglesias" Message-Id: Date: Wed, 07 Jan 2009 13:30:43 +0000 Subject: [Qemu-devel] [6207] ETRAX: Correctly update the interrupt vector when interrupts get masked. Reply-To: qemu-devel@nongnu.org List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Revision: 6207 http://svn.sv.gnu.org/viewvc/?view=rev&root=qemu&revision=6207 Author: edgar_igl Date: 2009-01-07 13:30:41 +0000 (Wed, 07 Jan 2009) Log Message: ----------- ETRAX: Correctly update the interrupt vector when interrupts get masked. Cannot believe this bug has been around for so long. Signed-off-by: Edgar E. Iglesias Modified Paths: -------------- trunk/hw/etraxfs_pic.c Modified: trunk/hw/etraxfs_pic.c =================================================================== --- trunk/hw/etraxfs_pic.c 2009-01-07 13:24:40 UTC (rev 6206) +++ trunk/hw/etraxfs_pic.c 2009-01-07 13:30:41 UTC (rev 6207) @@ -41,14 +41,41 @@ uint32_t r_guru; }; -static uint32_t pic_readb (void *opaque, target_phys_addr_t addr) -{ - return 0; +static void pic_update(struct fs_pic_state_t *fs) +{ + CPUState *env = fs->env; + int i; + uint32_t vector = 0; + + fs->r_masked_vect = fs->r_vect & fs->rw_mask; + + /* The ETRAX interrupt controller signals interrupts to teh core + through an interrupt request wire and an irq vector bus. If + multiple interrupts are simultaneously active it chooses vector + 0x30 and lets the sw choose the priorities. */ + if (fs->r_masked_vect) { + uint32_t mv = fs->r_masked_vect; + for (i = 0; i < 31; i++) { + if (mv & 1) { + vector = 0x31 + i; + /* Check for multiple interrupts. */ + if (mv > 1) + vector = 0x30; + break; + } + mv >>= 1; + } + if (vector) { + env->interrupt_vector = vector; + D(printf("%s vector=%x\n", __func__, vector)); + cpu_interrupt(env, CPU_INTERRUPT_HARD); + } + } else { + env->interrupt_vector = 0; + cpu_reset_interrupt(env, CPU_INTERRUPT_HARD); + D(printf("%s reset irqs\n", __func__)); + } } -static uint32_t pic_readw (void *opaque, target_phys_addr_t addr) -{ - return 0; -} static uint32_t pic_readl (void *opaque, target_phys_addr_t addr) { @@ -82,16 +109,6 @@ } static void -pic_writeb (void *opaque, target_phys_addr_t addr, uint32_t value) -{ -} - -static void -pic_writew (void *opaque, target_phys_addr_t addr, uint32_t value) -{ -} - -static void pic_writel (void *opaque, target_phys_addr_t addr, uint32_t value) { struct fs_pic_state_t *fs = opaque; @@ -100,19 +117,8 @@ { case 0x0: fs->rw_mask = value; + pic_update(fs); break; - case 0x4: - fs->r_vect = value; - break; - case 0x8: - fs->r_masked_vect = value; - break; - case 0xc: - fs->r_nmi = value; - break; - case 0x10: - fs->r_guru = value; - break; default: cpu_abort(fs->env, "invalid PIC register.\n"); break; @@ -120,14 +126,12 @@ } static CPUReadMemoryFunc *pic_read[] = { - &pic_readb, - &pic_readw, + NULL, NULL, &pic_readl, }; static CPUWriteMemoryFunc *pic_write[] = { - &pic_writeb, - &pic_writew, + NULL, NULL, &pic_writel, }; @@ -142,9 +146,6 @@ static void irq_handler(void *opaque, int irq, int level) { struct fs_pic_state_t *fs = (void *)opaque; - CPUState *env = fs->env; - int i; - uint32_t vector = 0; D(printf("%s irq=%d level=%d mask=%x v=%x mv=%x\n", __func__, irq, level, @@ -153,34 +154,8 @@ irq -= 1; fs->r_vect &= ~(1 << irq); fs->r_vect |= (!!level << irq); - fs->r_masked_vect = fs->r_vect & fs->rw_mask; - /* The ETRAX interrupt controller signals interrupts to teh core - through an interrupt request wire and an irq vector bus. If - multiple interrupts are simultaneously active it chooses vector - 0x30 and lets the sw choose the priorities. */ - if (fs->r_masked_vect) { - uint32_t mv = fs->r_masked_vect; - for (i = 0; i < 31; i++) { - if (mv & 1) { - vector = 0x31 + i; - /* Check for multiple interrupts. */ - if (mv > 1) - vector = 0x30; - break; - } - mv >>= 1; - } - if (vector) { - env->interrupt_vector = vector; - D(printf("%s vector=%x\n", __func__, vector)); - cpu_interrupt(env, CPU_INTERRUPT_HARD); - } - } else { - env->interrupt_vector = 0; - cpu_reset_interrupt(env, CPU_INTERRUPT_HARD); - D(printf("%s reset irqs\n", __func__)); - } + pic_update(fs); } static void nmi_handler(void *opaque, int irq, int level) @@ -209,7 +184,6 @@ } - struct etraxfs_pic *etraxfs_pic_init(CPUState *env, target_phys_addr_t base) { struct fs_pic_state_t *fs = NULL;