This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

ICH_EISR_EL2 use-cases

Is there any use case where this register (ICH_EISR_EL2) can report more than one outstanding EOI?

I don't really understand why we have 16-bit wide register (one bit per LR) if there is no use-case. I'm sure I'm missing something.


Parents
  • Sharing some experiments: 

    do {
    		u32 irqstat = gic_read_iar();
    		u32 irqnr = gic_iar_irqnr(irqstat);
    		if (irqnr != GICC_INT_SPURIOUS) {
    
    			... delay ...
    			
    			gic_write_eoir(irqstat);
    		} else {
    			break;
    		}
    	
    } while (1);


    - This example running on a vCPU is able to trigger more than one bit on EISR. when delay is small it sets two bits on EISR before generating the maintenance IRQ. Note that EOIR is performing both priority drop and deactivation.

    Delay has to be a small delay. I wonder how many instructions can we execute :)

    do {
    	u32 irqstat = gic_read_iar();
    	u32 irqnr = gic_iar_irqnr(irqstat);
    	if (irqnr != GICC_INT_SPURIOUS) {
    
    		< IRQ Handling >
    
    		gic_write_eoir(irqstat);
    	} else {
    		break;
    	}
    
    } while (1);
    
    MSR(ICC_DIR_EL1, 7);
    MSR(ICC_DIR_EL1, 6);
    MSR(ICC_DIR_EL1, 5);
    MSR(ICC_DIR_EL1, 4);


    - This example uses separation of the priority drop from deactivation, I inject 4 LRs at the same time with EOI bit set to 1 (vIRQ 7, 6, 5, 4). Then I handle all of the vIRQs (in the guest )with IAR (inactive to active) and EOIR (priority drop) in a loop, and after all do 4 sequencial deactivations with ICC_DIR_EL1 (active to inactive) of the handled vIRQs.

    - In this last case, I observe 4 bits of ICH_ EISR_EL2 are set when receiving the maintenance IRQ on the hypervisor.

    These two examples were tested on NVIDIA Jetson Orin that supports 4 LRs.

Reply
  • Sharing some experiments: 

    do {
    		u32 irqstat = gic_read_iar();
    		u32 irqnr = gic_iar_irqnr(irqstat);
    		if (irqnr != GICC_INT_SPURIOUS) {
    
    			... delay ...
    			
    			gic_write_eoir(irqstat);
    		} else {
    			break;
    		}
    	
    } while (1);


    - This example running on a vCPU is able to trigger more than one bit on EISR. when delay is small it sets two bits on EISR before generating the maintenance IRQ. Note that EOIR is performing both priority drop and deactivation.

    Delay has to be a small delay. I wonder how many instructions can we execute :)

    do {
    	u32 irqstat = gic_read_iar();
    	u32 irqnr = gic_iar_irqnr(irqstat);
    	if (irqnr != GICC_INT_SPURIOUS) {
    
    		< IRQ Handling >
    
    		gic_write_eoir(irqstat);
    	} else {
    		break;
    	}
    
    } while (1);
    
    MSR(ICC_DIR_EL1, 7);
    MSR(ICC_DIR_EL1, 6);
    MSR(ICC_DIR_EL1, 5);
    MSR(ICC_DIR_EL1, 4);


    - This example uses separation of the priority drop from deactivation, I inject 4 LRs at the same time with EOI bit set to 1 (vIRQ 7, 6, 5, 4). Then I handle all of the vIRQs (in the guest )with IAR (inactive to active) and EOIR (priority drop) in a loop, and after all do 4 sequencial deactivations with ICC_DIR_EL1 (active to inactive) of the handled vIRQs.

    - In this last case, I observe 4 bits of ICH_ EISR_EL2 are set when receiving the maintenance IRQ on the hypervisor.

    These two examples were tested on NVIDIA Jetson Orin that supports 4 LRs.

Children
No data