cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 
fpgae
Observer
Observer
4,436 Views
Registered: ‎05-29-2018

Problem with AXI Interrupt Controller: XIntc_Start

Jump to solution

Hello, I have ported a design from Vivado 2015.4. to 2018.1. This design contains a timer which provides a 1ms signal through an AXI interrupt controller to the Microblaze. Now, I have the problem that the interrupt never occurred. I traced back the error using ILA. I see the interrupt signal (1ms timer interrupt) until the AXI interrupt controller. So I suspect that the AXI interrupt controller output is deactivated.

As far as I tracked the problem, XIntc_Start does not return successful.

Therefore I would like to ask if the sequence is correct and why could XIntc_Start fail?

My code for initialization is the following (here the device id is set fixed):

	XIntc intc;
	status = XIntc_Initialize(&intc, 0); //0=device ID for AXI INTC
	if (status == XST_SUCCESS) {
		gpiostatEnable(STAT_LED1);
	}
	status = XIntc_Connect(&intc, 0, (XInterruptHandler)systemISR2, (void *)0);
	if (status == XST_SUCCESS) {
		gpiostatEnable(STAT_LED2);
	}
	status = XIntc_Start(&intc, XIN_REAL_MODE);
	if (status == XST_SUCCESS) {
		gpiostatEnable(STAT_LED3);
	}
	XIntc_Enable(&intc, 0);

 

0 Kudos
1 Solution

Accepted Solutions
fpgae
Observer
Observer
4,638 Views
Registered: ‎05-29-2018

Ok, I found the problem. The IRQs were not acknowledged from the MB. Again, I had to update to XIntc_Acknowledge instead of XIntc_AckIntr. After that, the interrupt handling worked fine.

View solution in original post

0 Kudos
6 Replies
josephsamson
Voyager
Voyager
4,404 Views
Registered: ‎10-05-2010

I cannot claim any special knowledge, but this is the sequence that works for me in Vivado 2018.1. I got it from looking at the programming examples.

 

Status = XIntc_Initialize(&InterruptController, INTC_DEVICE_ID);
if (Status != XST_SUCCESS) {xil_printf("\r\nInterrupt Initialization Failed");}

// Connect the sensor 0 write VDMA interrupt handler
Status = XIntc_Connect(&InterruptController, S0_OKTOREPROGRAM_VECT,
	   (XInterruptHandler)s0_writeVDMAHandler, (void *)&InterruptController);
if (Status != XST_SUCCESS) {xil_printf("\r\ns0 VDMA Handler Connect Failed");}

// Connect the image readback VDMA interrupt handler
 Status = XIntc_Connect(&InterruptController, RD_REPROGRAM_VECT,
           (XInterruptHandler)readVDMAHandler, (void *)&InterruptController);
if (Status != XST_SUCCESS) {xil_printf("\r\nread VDMA Handler Connect Failed");}

// Connect the I2C interrupt handler
Status = XIntc_Connect(&InterruptController, I2C_INTERRUPT_VECT,
	   (XInterruptHandler) XIic_InterruptHandler, &IicInstance);
if (Status != XST_SUCCESS) {xil_printf("\r\nI2C Interrupt Handler Connect Failed");}

// Connect the UART Lite interrupt handler  
Status = XIntc_Connect(&InterruptController, UARTLITE_VECT,
          (XInterruptHandler)XUartLite_InterruptHandler, (void *)&UartLite);
if (Status != XST_SUCCESS){xil_printf("\r\nUART Lite Interrupt Handler Connect Failed");}
  
// Start the interrupt controller such that interrupts are enabled for
// all devices that cause interrupts, XIN_SIMULATION_MODE or XIN_REAL_MODE
Status = XIntc_Start(&InterruptController, XIN_REAL_MODE);
if (Status != XST_SUCCESS) {xil_printf("\r\nXIntc_Start Failed");}

// Initialize the exception table.
Xil_ExceptionInit();

// Register the interrupt controller handler with the exception table.
Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_INT,
	(Xil_ExceptionHandler)XIntc_InterruptHandler,	&InterruptController);

// Enable exceptions.
Xil_ExceptionEnable();
  
//Status = XIntc_SelfTest(&InterruptController);
//if (Status != XST_SUCCESS) {
// xil_printf("\r\nInterrupt Self Test Failed - XIN_REAL_MODE?\r\n");
//} // The self test only works if the controller is in XIN_SIMULATION_MODE and has // NEVER been in real mode. // Enable the interrupts XIntc_Disable(&InterruptController, S0_OKTOREPROGRAM_VECT); XIntc_Disable(&InterruptController, RD_REPROGRAM_VECT); XIntc_Enable (&InterruptController, UARTLITE_VECT); XIntc_Enable (&InterruptController, I2C_INTERRUPT_VECT);

My design has 4 interrupts: two that I generate in the fabric, plus the UARTLite and AXI_IIC.

 

Maybe your XIntc_Enable is wrong? Should be: XIntc_Enable(&intc, systemISR2);

 

 

---

Joe Samson

fpgae
Observer
Observer
4,390 Views
Registered: ‎05-29-2018

Thank you for sharing the code. My problem is not (at the moment) XIntc_Enable, it is XIntc_Start which returns an error. I have only one interrrupt connected to my AXI INTC. Actually, this u8 Id Parameter should be 0 according to my xparameters.h i think.

My 1ms timer is listed as following:

#define XPAR_CTRL_FIT_TIMER_1MS_INTERRUPT_MASK 0X000001U
#define XPAR_CTRL_MB_AXI_INTC_CTRL_FIT_TIMER_1MS_INTERRUPT_INTR 0U

So Id should be 0.

 

@josephsamson: systemISR2 is the name of my ISR. Where have you looked up your "I2C_INTERRUPT_VECT" (for example), are these entries of xparameters.h (this is were I searched)? 

0 Kudos
fpgae
Observer
Observer
4,381 Views
Registered: ‎05-29-2018

Hi, today I continued my testing. Now XIntc_Start no longer reports any errors, but still no interrupts incoming into the AXI INTC are send to the Microblaze. Debugging with ILA shows now that the output of the AXI INTC is always high while previously being always low. AXI INTC is configured for level detection active high.

0 Kudos
fpgae
Observer
Observer
4,367 Views
Registered: ‎05-29-2018

@josephsamson: I renamed the interrupt source id and added the exceptions handler to see if they are linked to my problem (I saw them also in another example, so I just added them now). But the interrupts are still now reaching the MB. The disassembly shows the ISR is included. So the issues is still the same.

	int status = 0;
	XIntc intc;
	status += XIntc_Initialize(&intc, AXI_INTC_DEVICE_ID); //0=device ID for AXI INTC
	if (status != XST_SUCCESS) {
		CDCprintf("Failed to initialize AXI INTC");
	}
	status += XIntc_Connect(&intc, FIX_TIMER_1MS_INTR, (XInterruptHandler)systemISR2, (void *)0);
	if (status != XST_SUCCESS) {
		CDCprintf("Failed to connect interrupt handler for 1ms timer in AXI INTC");
	}
	status += XIntc_Start(&intc, XIN_REAL_MODE);
	if (status != XST_SUCCESS) {
		CDCprintf("Failed to start AXI INTC");
	}

	// Exceptions
	Xil_ExceptionInit();
	Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_INT, (Xil_ExceptionHandler)XIntc_InterruptHandler, &intc);
	Xil_ExceptionEnable();

	XIntc_Enable(&intc, FIX_TIMER_1MS_INTR);
0 Kudos
josephsamson
Voyager
Voyager
4,352 Views
Registered: ‎10-05-2010

A few more things to try:

1. It is possible to generate interrupts through software by writing the interrupt controller's Interrupt Status register. See AXI INTC v4.1 Product Guide PG099, page 15.

2. What value is in the Master Enable Register? It should be 3. - Master IRQ Enable and Hardware Interrupt Enable

3. Are the appropriate bits set in the Interrupt Enable Register?

4. If you change the Intc_Start to start in XIN_SIMULATION_MODE, you can run the self test. Note that once you start in XIN_REAL_MODE, you can't switch to XIN_SIMULATION_MODE (according to xintc.c), so modify the code, then reload the bitstream.

 

---

Joe

0 Kudos
fpgae
Observer
Observer
4,639 Views
Registered: ‎05-29-2018

Ok, I found the problem. The IRQs were not acknowledged from the MB. Again, I had to update to XIntc_Acknowledge instead of XIntc_AckIntr. After that, the interrupt handling worked fine.

View solution in original post

0 Kudos