If you have a IBM IDE hard disk on Solaris x86 and did enable DMA for ata,
then your system may hang after a reboot due to a firmware bug in the IBM
drive. On Solaris 9 you may edit the config file /platform/i86pc/kernel/drv/ata.conf
see also man ata.

On earlier versions, you need to patch the ata driver (see below):

Juergen Keil <jk@tools.de>

Bruce posted a patch for this problem some time ago: 
 
http://groups.google.com/groups?q=solaris+DMA+IBM+timeout&hl=en&lr=&safe=off&site=groups 
 
http://groups.google.com/groups?hl=en&safe=off&th=28213cb0f9e4067b,8&seekm=wywvaq7dvy.fsf%40tools.de#p 

/*--------------------------------------------------------------------------*/

> >> "Bruce Adler" <bruce.NxOxSxPxAxMx.adler@acm.org> writes:
> >> ...
> >> > Here's a patch that will change the Solaris 8 FCS ata driver's 0xCC
> >> > command into a 0x66:
> >> > 
> >> > cd /platform/i86pc/kernel/drv
> >> > cp ata ata.SAVE
> >> > adb -w ata<<EOF
> >> >     ata_devo_reset+0x54?w 0xaa68  ;; was 0xcc68
> >> > EOF
> >> 
> >> Small typo, that should be 
> >> 
> >>   ata_devo_reset+0x54?w 0x6668
> >> 
> >> > This should change the "pushl 0xcc" into a "pushl 0xaa" just before
> >> > the call to ata_set_feature().
> >> 
> >> Indeed, changing the "pushl 0xcc" into a "pushl 0x66" fixes the reboot
> >> problem!
/*--------------------------------------------------------------------------*/
ata_devo_reset,50?ai
ata_devo_reset: 
ata_devo_reset: pushl   %ebp
ata_devo_reset+1:               movl    %esp,%ebp
ata_devo_reset+3:               subl    $4,%esp
ata_devo_reset+6:               pushl   %ebx
ata_devo_reset+7:               pushl   %esi
ata_devo_reset+8:               pushl   %edi
ata_devo_reset+9:               cmpl    $0,+0xc(%ebp)
ata_devo_reset+0xd:             je      +0xb            <ata_devo_reset+0x18>
ata_devo_reset+0xf:             xorl    %eax,%eax
ata_devo_reset+0x11:            popl    %edi
ata_devo_reset+0x12:            popl    %esi
ata_devo_reset+0x13:            popl    %ebx
ata_devo_reset+0x14:            movl    %ebp,%esp
ata_devo_reset+0x16:            popl    %ebp
ata_devo_reset+0x17:            ret
ata_devo_reset+0x18:            pushl   +8(%ebp)
ata_devo_reset+0x1b:            call    +1              <ata_devo_reset+0x1c>
ata_devo_reset+0x20:            addl    $4,%esp
ata_devo_reset+0x23:            pushl   %eax
ata_devo_reset+0x24:            pushl   0
ata_devo_reset+0x2a:            call    +1              <ata_devo_reset+0x2b>
ata_devo_reset+0x2f:            addl    $8,%esp
ata_devo_reset+0x32:            movl    %eax,%edi
ata_devo_reset+0x34:            testl   %edi,%edi
ata_devo_reset+0x36:            je      +0x8d           <ata_devo_reset+0xc3>
ata_devo_reset+0x3c:            movl    $1,-4(%ebp)
ata_devo_reset+0x43:            xorl    %esi,%esi
ata_devo_reset+0x45:            nop
ata_devo_reset+0x46:            nop
ata_devo_reset+0x47:            nop
ata_devo_reset+0x48:            movl    %esi,%eax
ata_devo_reset+0x4a:            shll    $6,%eax
ata_devo_reset+0x4d:            movl    +0xc(%edi,%eax),%ebx
ata_devo_reset+0x51:            testl   %ebx,%ebx
ata_devo_reset+0x53:            je      +0x4d           <ata_devo_reset+0xa0>
ata_devo_reset+0x55:            movl    +0x204(%ebx),%eax
ata_devo_reset+0x5b:            andl    $2,%eax
ata_devo_reset+0x5e:            je      +0x13           <ata_devo_reset+0x71>
ata_devo_reset+0x60:            pushl   $0
ata_devo_reset+0x62:            pushl   $0x66		<<<======== War vorher pushl $0xcc
ata_devo_reset+0x67:            pushl   %ebx
ata_devo_reset+0x68:            pushl   %edi
ata_devo_reset+0x69:            call    +0x1846         <ata_set_feature>
ata_devo_reset+0x6e:            addl    $0x10,%esp
ata_devo_reset+0x71:            movl    +0x204(%ebx),%eax
ata_devo_reset+0x77:            andl    $1,%eax
ata_devo_reset+0x7a:            je      +0x11           <ata_devo_reset+0x8b>


Note that the exact position of the instruction that needs to be patched
may vary depending on the version of Solaris you use. Be extremely careful
when applying the patch.
