Subversion Repositories Kolibri OS

Rev

Rev 2014 | Rev 3526 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  2. ;;                                                              ;;
  3. ;; Copyright (C) 2010 KolibriOS team.     All rights reserved.  ;;
  4. ;; Distributed under terms of the GNU General Public License    ;;
  5. ;;                                                              ;;
  6. ;;  HT.inc                                                      ;;                                                    ;;
  7. ;;                                                              ;;
  8. ;;  AMD HyperTransport bus control                              ;;
  9. ;;                                                              ;;
  10. ;;                  art_zh  <kolibri@jerdev.co.uk>              ;;
  11. ;;                                                              ;;
  12. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  13.  
  14. $Revision: 1554 $
  15.  
  16. NB_MISC_INDEX   equ     0xF0000060      ; NB Misc indirect access
  17. NB_MISC_DATA    equ     0xF0000064
  18. PCIEIND_INDEX   equ     0xF00000E0      ; PCIe Core indirect config space access
  19. HTIU_NB_INDEX   equ     0xF0000094      ; HyperTransport indirect config space access
  20.  
  21. ;=============================================================================
  22. ;
  23. ; This code is a part of Kolibri-A and will only work with AMD RS760+ chipsets
  24. ;
  25. ;=============================================================================
  26.  
  27. org $-OS_BASE   ; physical addresses needed at initial stage
  28.  
  29. align 4
  30.  
  31. ;------------------------------------------
  32. ;       params:   al = nbconfig register#
  33. ;       returns: eax = register content
  34. ;
  35. rs7xx_nbconfig_read_pci:
  36.         and     eax, 0x0FC               ; leave register# only
  37.         or      eax, 0x80000000          ; bdf = 0:0.0
  38.         mov     dx,  0x0CF8              ; write to index reg
  39.         out     dx, eax
  40.         add     dl, 4
  41.         in      eax, dx
  42.         ret
  43. align 4
  44.  
  45. rs7xx_nbconfig_flush_pci:
  46.         mov     eax, 0x0B0              ; a scratch reg
  47.         mov     dx,  0xCF8
  48.         out     dx,  eax
  49.         ret
  50.  
  51. align 4
  52.  
  53. ;------------------------------------------
  54. ;       params:   al = nbconfig register#
  55. ;                ebx = register content
  56. ;
  57. rs7xx_nbconfig_write_pci:
  58.         and     eax, 0x0FC               ; leave register# only
  59.         or      eax, 0x80000000          ; bdf = 0:0.0
  60.         mov     dx,  0x0CF8              ; write to index reg
  61.         out     dx, eax
  62.         add     dl, 4
  63.         mov     eax, ebx
  64.         out     dx, eax
  65.         ret
  66.  
  67. ;***************************************************************************
  68. ;   Function
  69. ;      rs7xx_unlock_bar3:     unlocks the BAR3 register of nbconfig that
  70. ;                             makes pcie config address space visible
  71. ;   -----------------------
  72. ;   in: nothing      out: nothing      destroys:   eax ebx edx
  73. ;
  74. ;***************************************************************************
  75. align 4
  76. rs7xx_unlock_bar3:
  77.         mov     eax, NB_MISC_INDEX
  78.         mov     ebx, 0x080                      ; NBMISCIND:0x0; write-enable
  79.         call    rs7xx_nbconfig_write_pci        ; set index
  80.         mov     eax, NB_MISC_DATA
  81.         call    rs7xx_nbconfig_read_pci         ; read data
  82.         mov     ebx, eax
  83.         and     ebx, 0xFFFFFFF7                 ; clear bit3
  84.         mov     eax, NB_MISC_DATA
  85.         call    rs7xx_nbconfig_write_pci        ; write it back
  86.         mov     eax, NB_MISC_INDEX
  87.         xor     ebx, ebx                        ; reg#0; write-locked
  88.         call    rs7xx_nbconfig_write_pci        ; set index
  89.         ret
  90.  
  91.  
  92.  
  93. ;***************************************************************************
  94. ;   Function
  95. ;      rs7xx_pcie_init:
  96. ;
  97. ;   Description
  98. ;       PCIe extended (memory-mapped) config space detection
  99. ;
  100. ;***************************************************************************
  101.  
  102. align 4
  103.  
  104. rs7xx_pcie_init:
  105.         call    rs7xx_unlock_bar3
  106.         mov     al, 0x7C                       ; NB_IOC_CFG_CNTL
  107.         call    rs7xx_nbconfig_read_pci
  108.         mov     ebx, eax
  109. ;       call    rs7xx_nbconfig_flush_pci
  110.         test    ebx, 0x20000000                 ; BAR3 locked?
  111.         jz      $
  112.         mov     al, 0x84                        ; NB_PCI_ARB
  113.         call    rs7xx_nbconfig_read_pci
  114.         shr     eax,16
  115.         and     ax, 7                           ; the Bus range lays here:
  116.         jnz     @f
  117.         mov     ax, 8                                   ; 1=2Mb,  2=4MB,  3=8MB,  4=16MB
  118. @@:
  119.         mov     word[PCIe_bus_range-OS_BASE], ax        ; 5=32Mb, 6=64MB, 7=128Mb, 8=256Mb
  120.         mov     cl, al
  121.         call    rs7xx_nbconfig_flush_pci
  122.         dec     cl                              ; <4M ?
  123.         jz      @f
  124.         dec     cl                              ; one PDE needed anyway
  125. @@:
  126.         mov     ebx, 1
  127.         shl     ebx, cl
  128.         mov     word[mmio_pcie_cfg_pdes-OS_BASE], bx    ; 1..64 PDE(s) needed,
  129.         shl     ebx, 22
  130.         mov     dword[mmio_pcie_cfg_lim-OS_BASE], ebx   ; or 4..256Mb space to map
  131.         dec     dword[mmio_pcie_cfg_lim-OS_BASE]
  132.  
  133.         mov     al, 0x1C                        ; NB_BAR3_PCIEXP_MMCFG
  134.         call    rs7xx_nbconfig_read_pci
  135.         mov     ebx, eax
  136.         call    rs7xx_nbconfig_flush_pci
  137.         mov     eax, ebx
  138.         and     eax, 0xFFE00000                 ; valid bits [31..21]
  139.         jz      $                               ; invalid map!
  140. .addr_found:
  141.         mov     dword[mmio_pcie_cfg_addr-OS_BASE], eax  ; physical address (lower 32 bits)
  142.         add     dword[mmio_pcie_cfg_lim-OS_BASE],  eax
  143.  
  144. ; ---- common mapping procedure ----
  145. ; (eax = phys. address of PCIe conf.space)
  146. ;
  147. map_pcie_pages:
  148.         or      eax, (PG_NOCACHE + PG_SHARED + PG_LARGE + PG_UW)  ;  UW is unsafe!
  149.         mov     ecx, PCIe_CONFIG_SPACE                  ; linear address
  150.         mov     ebx, ecx
  151.         shr     ebx, 20
  152.         add     ebx, (sys_pgdir - OS_BASE)              ; PgDir entry @
  153.         mov     dl, byte[mmio_pcie_cfg_pdes-OS_BASE]    ; 1 page = 4M in address space
  154.         cmp     dl, 0x34        ; =(USER_DMA_BUFFER - PCIe_CONFIG_SPACE) / 4M
  155.         jb      @f
  156.         mov     dl, 0x33
  157.         mov     byte[mmio_pcie_cfg_pdes-OS_BASE], dl
  158. @@:
  159.         xor     dx,  dx                         ; PDEs counter
  160. .write_pde:
  161.         mov     dword[ebx], eax                 ; map 4 buses
  162.         add     bx,  4                          ; new PDE
  163.         add     eax, 0x400000                   ; +4M phys.
  164.         add     ecx, 0x400000                   ; +4M lin.
  165.         cmp     dl, byte[mmio_pcie_cfg_pdes-OS_BASE]
  166.         jae     pcie_cfg_mapped
  167.         inc     dl
  168.         jmp     .write_pde
  169.  
  170. ; ---- stepping 10h CPUs and Fusion APUs: the configspace is stored in MSR_C001_0058 ----
  171. align 4
  172. fusion_pcie_init:
  173.         mov     ecx, 0xC0010058
  174.         rdmsr
  175.         or      edx, edx
  176.         jnz     $                               ; PCIe is in the upper memory. Stop.
  177.         xchg    dl, al
  178.         mov     dword[mmio_pcie_cfg_addr-OS_BASE], eax  ; store the physical address
  179.         mov     ecx, edx
  180.         and     dl, 1
  181.         jz      $                               ; bit[0] = 1 means no PCIe mapping allowed. Stop.
  182.         shr     cl, 2                           ; ecx = log2(number of buses)
  183.         mov     word[PCIe_bus_range-OS_BASE], cx
  184.         sub     cl, 2
  185.         jae     @f
  186.         xor     cl, cl
  187. @@:
  188.         shl     edx, cl                         ; edx = number of 4M pages to map
  189.         mov     word[mmio_pcie_cfg_pdes-OS_BASE], dx
  190.         shl     edx, 22
  191.         dec     edx
  192.         add     edx, eax                        ; the upper configspace limit
  193.         mov     dword[mmio_pcie_cfg_lim-OS_BASE], edx
  194.  
  195. pcie_cfg_mapped:
  196.  
  197. create_mmio_pte:
  198.  
  199.         mov     ecx, mmio_pte                           ; physical address
  200.         or      ecx, (PG_NOCACHE + PG_SHARED)  
  201.         mov     ebx, FUSION_MMIO                        ; linear address
  202.         shr     ebx, 20
  203.         add     ebx, (sys_pgdir - OS_BASE)              ; PgDir entry @
  204.         mov     dword[ebx], ecx                         ; Fusion MMIO tables
  205.  
  206. map_apic_mmio:
  207.         mov     ecx, 0x01B      ; APIC BAR
  208.         rdmsr
  209.         and     eax, 0xFFFFF000                         ; physical address
  210.         or      eax, (PG_NOCACHE + PG_SHARED + PG_UW)   ;  UW is unsafe!
  211.         mov     dword[mmio_pte + 0], eax
  212.  
  213.         ret     ; <<< OK >>>
  214.  
  215. ; ================================================================================
  216.  
  217. org OS_BASE+$   ; back to the linear address space
  218.  
  219. ;--------------------------------------------------------------
  220. align 4
  221. rs780_read_misc:
  222. ;  in: eax(al) - reg#           out: eax = NBMISCIND data
  223.         push    edx
  224.         mov     edx, NB_MISC_INDEX
  225.         and     eax, 0x07F
  226.         mov     [edx], eax
  227.         add     dl, 4
  228.         mov     eax, [edx]
  229.         pop     edx
  230.         ret
  231.  
  232. ;-------------------------------------------
  233. align 4
  234. rs780_write_misc:
  235. ;  in: eax(al) - reg#     ebx = NBMISCIND data
  236.         push    edx
  237.         mov     edx, NB_MISC_INDEX
  238.         and     eax, 0x07F
  239.         or      eax, 0x080              ; set WE
  240.         mov     [edx], eax
  241.         add     dl, 4
  242.         mov     [edx], ebx
  243.         sub     dl, 4
  244.         xor     eax,   eax
  245.         mov     [edx], eax              ; safety last
  246.         pop     edx
  247.         ret
  248.  
  249. ;-------------------------------------------------------------
  250. align 4
  251. rs780_read_pcieind:
  252. ;  in: ah = bridge#, al = reg#           out: eax = PCIEIND data
  253.         push    edx
  254.         xor     edx, edx
  255.         mov     ah,  dl                 ; bridge# :     0 = Core+GFX;   0x10 = Core+SB
  256.         and     dl,  15                 ;            0x20 = Core+GPP;  2..12 = a PortBridge
  257.         shl     edx, 15                 ; device#
  258.         add     edx, PCIEIND_INDEX      ; full bdf-address
  259.         and     eax, 0x30FF
  260.         or      al,  al
  261.         jnz     @f
  262.         shl     eax, 4                  ; set bits 17..16 for a Core bridge
  263. @@:
  264.         mov     [edx], eax
  265.         add     dl,  4
  266.         mov     eax, [edx]
  267.         pop     edx
  268.         ret
  269.  
  270. ;-------------------------------------------
  271. align 4
  272. rs780_write_pcieind:
  273. ;  in: ah = bridge#, al = reg#,  ebx = PCIEIND data
  274.         push    edx
  275.         xor     edx, edx
  276.         mov     ah,  dl                 ; bridge# :     0 = Core+GFX;   0x10 = Core+SB
  277.         and     dl,  15                 ;            0x20 = Core+GPP;  2..12 = a PortBridge
  278.         shl     edx, 15                 ; device#
  279.         add     edx, PCIEIND_INDEX      ; full bdf-address
  280.         and     eax, 0x30FF
  281.         or      al,  al
  282.         jnz     @f
  283.         shl     eax, 4                  ; set bits 17..16 for a Core bridge
  284. @@:
  285.         mov     [edx], eax
  286.         add     dl,  4
  287.         mov     [edx], ebx
  288.         sub     dl,  4
  289.         xor     eax,   eax
  290.         mov     [edx], eax              ; safety last
  291.         pop     edx
  292.         ret
  293.  
  294. ;------------------------------------------------
  295. align 4
  296. rs780_read_htiu:
  297. ; in:  al = reg#  |  out: eax = HTIU data
  298. ;------------------------------------------------
  299.         push    edx
  300.         mov     edx,  HTIU_NB_INDEX
  301.         and     eax, 0x07F
  302.         mov     [edx], eax
  303.         add     dl,  4
  304.         mov     eax, [edx]
  305.         pop     edx
  306.         ret
  307. ;------------------------------------------------
  308. align 4
  309. rs780_write_htiu:
  310. ; in:  al = reg#; ebx = data
  311. ;------------------------------------------------
  312.         push    edx
  313.         mov     edx,  HTIU_NB_INDEX
  314.         and     eax, 0x07F
  315.         or      eax, 0x100
  316.         mov     [edx], eax
  317.         add     dl,  4
  318.         mov     [edx], ebx
  319.         sub     dl,  4
  320.         xor     eax,   eax
  321.         mov     [edx], eax
  322.         pop     edx
  323.         ret
  324.  
  325. ;------------------------------------------------
  326. align 4
  327. sys_rdmsr:
  328. ;  in: [esp+8] = MSR#
  329. ; out: [esp+8] = MSR[63:32]
  330. ;        [eax] = MSR[31: 0]
  331. ;------------------------------------------------
  332.         push    ecx edx
  333.         mov     ecx, [esp+16]
  334.         rdmsr
  335.         mov     [esp+16], edx
  336.         pop     edx ecx
  337.         ret
  338.  
  339.  
  340.