>> +/* Convert a priority number to an Interrupt Pending Buffer (IPB) >> + * register, which indicates a pending interrupt at the priority >> + * corresponding to the bit number >> + */ >> +static uint8_t priority_to_ipb(uint8_t priority) >> +{ >> + return priority > XIVE_PRIORITY_MAX ? >> + 0 : 1 << (XIVE_PRIORITY_MAX - priority); > > Does handling out of bounds values here make sense, or should you just > assert() they're not passed in?
The priority can be above in the TM_SPC_SET_OS_PENDING command. >> +} >> + >> +/* Convert an Interrupt Pending Buffer (IPB) register to a Pending >> + * Interrupt Priority Register (PIPR), which contains the priority of >> + * the most favored pending notification. >> + * >> + * TODO: >> + * >> + * PIPR is clamped to CPPR. So the value in the PIPR is: >> + * >> + * v = leftmost_bit_of(ipb) (or 0xff); >> + * pipr = v < cppr ? v : cppr; >> + * >> + * Ben says: "which means it's never actually 0xff ... surprise !". >> + * But, the CPPR can be set to 0xFF ... I am confused ... > > A resolution to this would be nice.. The 'accept' sequence does : - store the PIPR in the CPPR - reset the pending buffer bit in the IPB - recompute the PIPR value from the new IPB - drop the exception bit for OS Typical values are : before IBP=02 PIPR=06 CPPR=ff NSR=80 after IBP=00 PIPR=ff CPPR=06 NSR=00 So today, if the IPB becomes zero, the PIPR is adjusted to 0xFF. But, if the PIPR is clamped to the CPPR (6), there is a disconnect between the IBP and the PIPR values. Is that OK ? Then, the second effect is that as soon as the OS sets back the CPPR to 0xFF, we notify the CPU again and enter a loop. I think this is because a test on the EO bit of the NSR is missing in the routine setting the CPPR. this bit notifies the presence of an exception for the O/S. I will add that. I misunderstood the specs on the topic. C.