The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/pc/sd53c8xx.n

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 // NCR 53c8xx driver for Plan 9
    2 // Nigel Roles (nigel@9fs.org)
    3 //
    4 // Microcode
    5 //
    6 // 27/5/02      Fixed problems with transfers >= 256 * 512
    7 //
    8 // 13/3/01      Fixed microcode to support targets > 7
    9 //
   10 
   11 extern  scsi_id_buf
   12 extern  msg_out_buf
   13 extern  cmd_buf
   14 extern  data_buf
   15 extern  status_buf
   16 extern  msgin_buf
   17 extern  dsa_0
   18 extern  dsa_1
   19 extern  dsa_head
   20 extern  ssid_mask
   21 
   22 SIR_MSG_IO_COMPLETE = 0
   23 error_not_cmd_complete = 1
   24 error_disconnected = 2
   25 error_reselected = 3
   26 error_unexpected_phase = 4
   27 error_weird_message = 5
   28 SIR_ERROR_NOT_MSG_IN_AFTER_RESELECT = 6
   29 error_not_identify_after_reselect = 7
   30 error_too_much_data = 8
   31 error_too_little_data = 9
   32 SIR_MSG_REJECT = 10
   33 SIR_MSG_SDTR = 11
   34 SIR_EV_RESPONSE_OK = 12
   35 error_sigp_set = 13
   36 SIR_EV_PHASE_SWITCH_AFTER_ID = 14
   37 SIR_MSG_WDTR = 15
   38 SIR_MSG_IGNORE_WIDE_RESIDUE = 16
   39 SIR_NOTIFY_DISC = 100
   40 SIR_NOTIFY_RESELECT = 101
   41 SIR_NOTIFY_MSG_IN = 102
   42 SIR_NOTIFY_STATUS = 103
   43 SIR_NOTIFY_DUMP = 104
   44 SIR_NOTIFY_DUMP2 = 105
   45 SIR_NOTIFY_SIGP = 106
   46 SIR_NOTIFY_ISSUE = 107
   47 SIR_NOTIFY_WAIT_RESELECT = 108
   48 SIR_NOTIFY_ISSUE_CHECK = 109
   49 SIR_NOTIFY_DUMP_NEXT_CODE = 110
   50 SIR_NOTIFY_COMMAND = 111
   51 SIR_NOTIFY_DATA_IN = 112
   52 SIR_NOTIFY_DATA_OUT = 113
   53 SIR_NOTIFY_BLOCK_DATA_IN = 114
   54 SIR_NOTIFY_WSR = 115
   55 SIR_NOTIFY_LOAD_SYNC = 116
   56 SIR_NOTIFY_RESELECTED_ON_SELECT = 117
   57 SIR_NOTIFY_LOAD_STATE = 118
   58 
   59 STATE_FREE = 0
   60 STATE_ALLOCATED = 1
   61 STATE_ISSUE = 2
   62 STATE_DISCONNECTED = 3
   63 STATE_DONE = 4
   64 STATE_END = 5
   65 
   66 RESULT_OK = 0
   67         
   68 MSG_IDENTIFY = 0x80
   69 MSG_DISCONNECT = 0x04
   70 MSG_SAVE_DATA_POINTER = 0x02
   71 MSG_RESTORE_POINTERS = 0x03
   72 MSG_IGNORE_WIDE_RESIDUE = 0x23
   73 X_MSG = 0x01
   74 X_MSG_SDTR = 0x01
   75 X_MSG_WDTR = 0x03
   76 MSG_REJECT = 0x07
   77 
   78 BSIZE = 512
   79 //BSIZE=4096
   80 
   81  // idle:
   82         jump    wait_for_reselection    
   83 start:
   84         call    load_sync
   85 //      move    13 to ctest0
   86 //      int     SIR_NOTIFY_ISSUE
   87         clear   target
   88         select  atn from scsi_id_buf, reselected_on_select // do I need to clear ATN here?
   89         jump    start1, when msg_in     // why is this here?
   90 start1:
   91 //      move    14 to ctest0
   92         move    from msg_out_buf, when msg_out
   93 id_out_mismatch:
   94         jump    start1, when msg_out            // repeat on parity grounds
   95         jump    to_decisions, when not cmd
   96 cmd_phase:
   97 //      int     SIR_NOTIFY_COMMAND
   98         clear   atn
   99         move    from cmd_buf, when cmd
  100 cmd_out_mismatch:
  101         jump    to_decisions, when not data_in
  102 data_in_phase:
  103         move    memory 4, state, scratcha
  104         move    memory 4, dmaaddr, scratchb
  105 //      int     SIR_NOTIFY_DATA_IN
  106 data_in_block_loop:
  107         move    scratcha2 to sfbr
  108         jump    data_in_normal, if 0
  109 //      int     SIR_NOTIFY_BLOCK_DATA_IN
  110         move    BSIZE, ptr dmaaddr, when data_in                // transfer BSIZE bytes
  111 data_in_block_mismatch:
  112         move    scratchb1 + BSIZE / 256 to scratchb1            // add BSIZE to scratchb
  113         move    scratchb2 + 0 to scratchb2 with carry
  114         move    scratchb3 + 0 to scratchb3 with carry
  115         move    scratcha2 + 255 to scratcha2                    // sub one from block count
  116         move    memory 4, scratchb, dmaaddr                     // save latest dmaddr
  117         jump    data_in_block_loop, when data_in
  118         move    memory 4, scratcha, state                       // save latest state
  119         call    save_state
  120         jump    to_decisions
  121 data_block_mismatch_recover:
  122         move    memory 4, scratchb, dmaaddr                     // save latest dmaddr
  123 data_mismatch_recover:
  124         move    memory 4, scratcha, state                       // save latest state
  125         jump    to_decisions                                    // no need to save
  126                                                                 // as interrupt routine
  127                                                                 // did this
  128 data_in_normal:
  129         move    scratcha3 to sfbr
  130         int     error_too_much_data, if not 0
  131         move    from data_buf, when data_in
  132 data_in_mismatch:
  133         move    2 to scratcha3
  134         move    memory 4, scratcha, state
  135         call    save_state
  136         jump    post_data_to_decisions
  137 data_out_phase:
  138 //      int     SIR_NOTIFY_DATA_OUT
  139         move    memory 4, state, scratcha
  140         move    memory 4, dmaaddr, scratchb
  141 data_out_block_loop:
  142         move    scratcha2 to sfbr
  143         jump    data_out_normal, if 0
  144         move    memory 4, dmaaddr, scratchb
  145         move    BSIZE, ptr dmaaddr, when data_out               // transfer BSIZE bytes
  146 data_out_block_mismatch:
  147         move    scratchb1 + BSIZE / 256 to scratchb1            // add BSIZE to scratchb
  148         move    scratchb2 + 0 to scratchb2 with carry
  149         move    scratchb3 + 0 to scratchb3 with carry
  150         move    scratcha2 + 255 to scratcha2                    // sub one from block count
  151         move    memory 4, scratchb, dmaaddr                     // save latest dmaddr
  152         jump    data_out_block_loop, when data_out
  153         move    memory 4, scratcha, state                       // save latest state
  154         jump    to_decisions
  155 data_out_normal:
  156         move    scratcha3 to sfbr
  157         int     error_too_little_data, if not 0
  158         move    from data_buf, when data_out
  159 data_out_mismatch:
  160         move    2 to scratcha3
  161         move    memory 4, scratcha, state
  162         call    save_state
  163         jump    post_data_to_decisions
  164 status_phase:
  165         move    from status_buf, when status
  166 //      int     SIR_NOTIFY_STATUS
  167         int     error_unexpected_phase, when not msg_in
  168 msg_in_phase:
  169         move    1, scratcha, when msg_in
  170 //      int     SIR_NOTIFY_MSG_IN
  171         jump    rejected, if MSG_REJECT
  172 msg_in_not_reject:
  173         jump    disconnected, if MSG_DISCONNECT
  174         jump    msg_in_skip, if MSG_SAVE_DATA_POINTER
  175         jump    msg_in_skip, if MSG_RESTORE_POINTERS
  176         jump    ignore_wide, if MSG_IGNORE_WIDE_RESIDUE
  177         jump    extended, if X_MSG
  178         int     error_not_cmd_complete, if not 0
  179         move    scntl2&0x7e to scntl2                   // take care not to clear WSR
  180         clear   ack
  181         wait    disconnect
  182         // update state
  183         move    memory 4, state, scratcha
  184         move    STATE_DONE to scratcha0
  185         move    RESULT_OK to scratcha1
  186         move    memory 4, scratcha, state
  187         call    save_state
  188 //      int     SIR_MSG_IO_COMPLETE
  189         intfly  0
  190         jump    issue_check
  191 
  192 rejected:
  193         int     SIR_MSG_REJECT
  194         clear   ack
  195         jump    to_decisions
  196 msg_in_skip:
  197         clear   ack
  198         jump    to_decisions
  199         
  200 extended:
  201         clear   ack
  202         int     error_unexpected_phase, when not msg_in
  203         move    1, scratcha1, when msg_in
  204         jump    ext_3, if 3
  205         jump    ext_2, if 2
  206         int     error_weird_message, if not 1
  207 ext_1:
  208         clear   ack
  209         int     error_unexpected_phase, when not msg_in
  210         move    1, scratcha1, when msg_in
  211         jump    ext_done
  212 
  213 ext_3:  clear   ack
  214         int     error_unexpected_phase, when not msg_in
  215         move    1, scratcha1, when msg_in
  216         clear   ack
  217         int     error_unexpected_phase, when not msg_in
  218         move    1, scratcha2, when msg_in
  219         clear   ack
  220         int     error_unexpected_phase, when not msg_in
  221         move    1, scratcha3, when msg_in
  222         move    scratcha1 to sfbr
  223         jump    ext_done, if not X_MSG_SDTR
  224 
  225 // the target sent SDTR - leave ACK asserted and signal kernel
  226 // kernel will either restart at reject, or continue
  227 sdtr:   int     SIR_MSG_SDTR
  228         clear   ack
  229         jump    to_decisions
  230 
  231 ext_2:  clear   ack
  232         int     error_unexpected_phase, when not msg_in
  233         move    1, scratcha1, when msg_in
  234         clear   ack
  235         int     error_unexpected_phase, when not msg_in
  236         move    1, scratcha2, when msg_in
  237         move    scratcha1 to sfbr
  238         jump    ext_done, if not X_MSG_WDTR
  239 
  240 wdtr:   int     SIR_MSG_WDTR
  241         clear   ack
  242         jump    to_decisions
  243 
  244 ext_done:
  245 //      ought to check message here, but instead reject all
  246 //      NB ATN set
  247 reject:
  248         set     atn                                     // get target's ATN
  249         clear   ack                                     // finish ACK
  250         move    MSG_REJECT to scratcha                  // prepare message
  251         int     error_unexpected_phase, when not msg_out// didn't get ATN
  252         clear   atn                                     // last byte coming
  253         move    1, scratcha, when msg_out               // send byte
  254         clear   ack                                     // finish ACK
  255         jump    reject, when msg_out                    // parity error
  256         jump    to_decisions
  257         
  258 ignore_wide:
  259         clear   ack
  260         int     error_unexpected_phase, when not msg_in
  261         move    1, scratcha1, when msg_in
  262         int     SIR_MSG_IGNORE_WIDE_RESIDUE
  263         clear   ack
  264         jump    to_decisions
  265 
  266 //      sends a response to a message
  267 response:
  268         set     atn
  269         clear   ack
  270         int     error_unexpected_phase, when not msg_out
  271 response_repeat:
  272         move    from msg_out_buf, when msg_out
  273         jump    response_repeat, when msg_out           // repeat on parity grounds
  274 // now look for response
  275 // msg_in could be a REJECT
  276 // anything other message is something else so signal kernel first
  277         jump    response_msg_in, when msg_in
  278         int     SIR_EV_RESPONSE_OK                      // not a MSG_IN so OK
  279         jump    to_decisions
  280 
  281 response_msg_in:
  282         move    1, scratcha, when msg_in
  283         jump    rejected, if MSG_REJECT         // go and generate rej interrupt
  284         int     SIR_EV_RESPONSE_OK              // not a REJECT so OK
  285         jump    msg_in_not_reject               // try others
  286 
  287 disconnected:
  288 //      move    5 to ctest0
  289         move    scntl2&0x7e to scntl2                   // don't clear WSR
  290         clear   ack
  291         wait    disconnect
  292         // UPDATE state to disconnected
  293         move    memory 4, state, scratcha
  294         move    STATE_DISCONNECTED to scratcha0
  295         move    memory 4, scratcha, state
  296         call    save_state
  297 wsr_check:
  298         move    scntl2&0x01 to sfbr
  299         int     SIR_NOTIFY_WSR, if not 0
  300 //      int     SIR_NOTIFY_DISC
  301         jump    issue_check
  302 
  303 reselected_on_select:
  304         int     SIR_NOTIFY_RESELECTED_ON_SELECT
  305         jump    reselected
  306 
  307 wait_for_reselection:
  308 //      move    11 to ctest0
  309 //      int     SIR_NOTIFY_WAIT_RESELECT
  310         wait reselect sigp_set
  311 reselected:
  312 //      move    12 to ctest0
  313         clear   target
  314         int     SIR_ERROR_NOT_MSG_IN_AFTER_RESELECT, when not msg_in
  315         move    1, scratchb, when msg_in
  316         int     error_not_identify_after_reselect, if not MSG_IDENTIFY and mask 0x1f
  317 //      int     SIR_NOTIFY_RESELECT
  318         // now locate the right DSA - note do not clear ACK, so target doesn't start
  319         // synchronous transfer until we are ready
  320 find_dsa:
  321 //      move    6 to ctest0
  322         move    memory 4, dsa_head, dsa
  323 find_dsa_loop:
  324 //      move    7 to ctest0
  325 //      move    8 to ctest0
  326         // load state from DSA into dsa_copy
  327         call    load_state
  328         move    memory 4, state, scratcha               // get dsastate in scratcha
  329         move    scratcha0 to sfbr                       // and state variable in sfbr
  330         jump    find_dsa_next, if not STATE_DISCONNECTED // wrong state
  331         int     error_reselected, if STATE_END
  332         move    ssid & ssid_mask to sfbr                        // get target ID
  333         move    memory 1, targ, find_dsa_smc1           // forge target comparison instruction
  334 find_dsa_smc1:
  335         jump    find_dsa_next, if not 255               // jump if not matched
  336         move    memory 1, lun, find_dsa_smc2            // forge lun comparison instruction
  337         move    scratchb0 to sfbr                       // recover IDENTIFY message
  338 find_dsa_smc2:
  339         jump    reload_sync, if 255 and mask ~7         // off we jolly well go
  340 find_dsa_next:
  341         move    memory 4, next, dsa                     // find next
  342         jump    find_dsa_loop
  343 
  344 // id_out terminated early
  345 // most likely the message wasn't recognised
  346 // clear ATN and accept the message in
  347 // called from sd53c8xx.c directly
  348 id_out_mismatch_recover:
  349         clear   atn
  350         jump    msg_in_phase, when msg_in
  351         int     SIR_MSG_REJECT
  352         jump    to_decisions
  353 
  354 // Reload synchronous registers after a reconnect. If the transfer is a synchronous read, then
  355 // as soon as we clear ACK, the target will switch to data_in and start blasting data into the
  356 // fifo. We need to be executing the 'jump when data_in' instruction before the target stops REQing
  357 // since it is the REQ which latches the 'when'. The target will do 16 REQs before stopping, so
  358 // we have 16 bytes (160uS) plus delays to do this after clearing ACK. Once the jump is executing,
  359 // the target will wait, so as much debugging as you like can happen in data_in_phase, just don't
  360 // stick any delays between 'clear ack' and 'jump data_in_phase, when data_in'.
  361 
  362 reload_sync:
  363         call    load_sync
  364         clear   ack
  365 to_decisions:
  366         jump    data_in_phase, when data_in
  367         jump    cmd_phase, if cmd
  368         jump    data_out_phase, if data_out
  369         jump    status_phase, if status
  370         jump    msg_in_phase, if msg_in
  371         int     error_unexpected_phase
  372 
  373 post_data_to_decisions:
  374         jump    status_phase, when status
  375         jump    msg_in_phase, if msg_in
  376         int     error_unexpected_phase
  377         
  378 //
  379 // MULTI_TARGET
  380 //
  381 // following must mirror top of dsa structure
  382 // the first section is loaded and saved, the
  383 // second section loaded only
  384 dsa_copy:
  385 state:  defw    0                       // a0 is state, a1 result, a2 dma block count
  386 dmaaddr: defw   0                       // dma address for block moves
  387 dsa_save_end:
  388 targ:   defw    0                       // lsb is target
  389 lun:    defw    0                       // lsb is lun
  390 sync:   defw    0                       // lsb is scntl3, sxfer
  391 next:   defw    0
  392 dsa_load_end:
  393 dsa_load_len = dsa_load_end - dsa_copy
  394 dsa_save_len = dsa_save_end - dsa_copy
  395 
  396 load_state:
  397 //      int     SIR_NOTIFY_LOAD_STATE
  398         jump load_state_okay
  399 
  400         move    dsa0 to sfbr
  401         jump load_state_okay, if not 0
  402         move    dsa1 to sfbr
  403         jump load_state_okay, if not 0
  404         move    dsa2 to sfbr
  405         jump load_state_okay, if not 0
  406         move    dsa3 to sfbr
  407         jump load_state_okay, if not 0
  408         // dsa is 0
  409         move    memory 4, dsa, dmaaddr
  410         move    memory 4, dsa, targ
  411         move    memory 4, dsa, lun
  412         move    memory 4, dsa, sync
  413         move    memory 4, dsa, next
  414         move    memory 4, dsa, scratcha
  415         move    STATE_END to sfbr
  416         move    sfbr to scratcha0
  417         move    memory 4, scratcha, state
  418         return
  419 
  420 load_state_okay:
  421         // load state from DSA into dsa_copy
  422 //      move    9 to ctest0
  423         move    memory 4, dsa, load_state_smc0 + 4
  424 load_state_smc0:
  425         move    memory dsa_load_len, 0, dsa_copy
  426 //      move    20 to ctest0
  427         return
  428 save_state:
  429         move    memory 4, dsa, save_state_smc0 + 8
  430 save_state_smc0:
  431         move    memory dsa_save_len, dsa_copy, 0
  432         return
  433 
  434 sigp_set:
  435 //      int     SIR_NOTIFY_SIGP
  436         move    ctest2 to sfbr                          // clear SIGP
  437 issue_check:
  438 //      int     SIR_NOTIFY_ISSUE_CHECK
  439 //      move    1 to ctest0
  440         move    memory 4, dsa_head, dsa
  441 issue_check_loop:
  442         call    load_state
  443         move    memory 4, state, scratcha               // get dsastate in scratcha
  444         move    scratcha0 to sfbr                       // and state variable in sfbr
  445         jump    start, if STATE_ISSUE                   // right state
  446         jump    wait_for_reselection, if STATE_END
  447  //     move    4 to ctest0
  448         move    memory 4, next, dsa                     // find next
  449         jump    issue_check_loop
  450 
  451 
  452 load_sync:
  453         move    memory 4, sync, scratcha                // load the sync stuff
  454         move    scratcha0 to sfbr                       // assuming load_state has been called
  455         move    sfbr to scntl3
  456         move    scratcha1 to sfbr
  457         move    sfbr to sxfer
  458  //     int     SIR_NOTIFY_LOAD_SYNC
  459         return

Cache object: 2d565a3165e540724b47b2e2a122ce6a


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.