On Wed, 28 Feb 2024 at 21:12, Sven Schnelle <sv...@stackframe.org> wrote:
>
> HP-UX 10.20 seems to make the lsi53c895a spinning on a memory location
> under certain circumstances. As the SCSI controller and CPU are not
> running at the same time this loop will never finish. After some
> time, the check loop interrupts with a unexpected device disconnect.
> This works, but is slow because the kernel resets the scsi controller.
> Instead of signaling UDC, add an option 'hpux-spin-workaround' which
> emulates a INTERRUPT 2 script instruction. This instruction tells the
> kernel that the request was fulfilled. With this change, SCSI speeds
> improves significantly.
>
> The option can be enabled by adding
>
> -global lsi53c895a.hpux-spin-workaround=on
>
> to the qemu commandline.
>
> Signed-off-by: Sven Schnelle <sv...@stackframe.org>
> ---
>  hw/scsi/lsi53c895a.c | 20 ++++++++++++++++++--
>  1 file changed, 18 insertions(+), 2 deletions(-)
>
> diff --git a/hw/scsi/lsi53c895a.c b/hw/scsi/lsi53c895a.c
> index d607a5f9fb..20c353f594 100644
> --- a/hw/scsi/lsi53c895a.c
> +++ b/hw/scsi/lsi53c895a.c
> @@ -304,6 +304,7 @@ struct LSIState {
>      uint32_t adder;
>
>      uint8_t script_ram[2048 * sizeof(uint32_t)];
> +    bool hpux_spin_workaround;
>  };
>
>  #define TYPE_LSI53C810  "lsi53c810"
> @@ -1156,8 +1157,17 @@ again:
>              qemu_log_mask(LOG_GUEST_ERROR,
>                            "lsi_scsi: inf. loop with UDC masked");
>          }
> -        lsi_script_scsi_interrupt(s, LSI_SIST0_UDC, 0);
> -        lsi_disconnect(s);
> +        if (s->hpux_spin_workaround) {
> +            /*
> +             * Workaround for HP-UX 10.20: Instead of disconnecting, which
> +             * causes a long delay, emulate a INTERRUPT 2 instruction.
> +             */
> +            s->dsps = 2;
> +            lsi_script_dma_interrupt(s, LSI_DSTAT_SIR);
> +        } else {
> +            lsi_script_scsi_interrupt(s, LSI_SIST0_UDC, 0);
> +            lsi_disconnect(s);
> +        }
>          trace_lsi_execute_script_stop();
>          reentrancy_level--;
>          return;


I see we already have a hacky workaround for other OSes
that do something similar. The ideal fix for both of these
I think would be for lsi_execute_script() to, instead of stopping,
arrange to defer executing more script instructions until
after the guest has had a chance to run a bit more.
I think setting a timer that calls lsi_resume_script() after
a while would have that effect.

-- PMM

Reply via email to