[439] | 1 | /////////////////////////////////////////////////////////////////////////////////// |
---|
| 2 | // File : boot_hba_driver.h |
---|
| 3 | // Date : 01/11/2013 |
---|
| 4 | // Authors : Alain Greiner / Vu Son |
---|
| 5 | // Copyright (c) UPMC-LIP6 |
---|
| 6 | /////////////////////////////////////////////////////////////////////////////////// |
---|
| 7 | // This file defines a simplified driver for SocLib vci_multi_ahci, |
---|
| 8 | // a multi-channel, block-oriented, external mass storage peripheral |
---|
| 9 | // respecting the AHCI standard. The driver is used by the ALMOS-MKH |
---|
| 10 | // boot-loader when the USE_IOC_HBA flag is set in the hard_config.h file. |
---|
| 11 | // Each channel can access a different physical disk, modeled by a file |
---|
| 12 | // belonging to the operating system, and containing a complete disk image. |
---|
| 13 | // However, this driver implementation only supports one channel, since the |
---|
| 14 | // ALMOS-MKH boot-loader only uses one physical hard drive. |
---|
| 15 | // The driver uses a software FIFO to register a command defined by a |
---|
| 16 | // Command Descriptor. A 32-entry Command Descriptor array forms the |
---|
| 17 | // Command List. Each Command Descriptor is associated with a Command Table |
---|
| 18 | // describing one given command. |
---|
| 19 | // All accesses to the device registers are performed via 2 low-level |
---|
| 20 | // functions boot_hba_get_register() and boot_hba_set_register(). |
---|
| 21 | // Since the driver is used by the boot-loader, it implements synchronous |
---|
| 22 | // accesses to block device by polling the HBA_PXCI register to detect the |
---|
| 23 | // transfer completion, as interrupts are not activated. |
---|
| 24 | /////////////////////////////////////////////////////////////////////////////////// |
---|
| 25 | |
---|
| 26 | #ifndef BOOT_HBA_DRIVER_H |
---|
| 27 | #define BOOT_HBA_DRIVER_H |
---|
| 28 | |
---|
| 29 | #include <hal_types.h> |
---|
| 30 | |
---|
| 31 | /**************************************************************************** |
---|
| 32 | * Driver register map. * |
---|
| 33 | ****************************************************************************/ |
---|
| 34 | |
---|
| 35 | enum HBA_registers |
---|
| 36 | { |
---|
| 37 | HBA_PXCLB = 0, /* 32 LSB of the Command List address */ |
---|
| 38 | HBA_PXCLBU = 1, /* 32 MSB of the Command List address */ |
---|
| 39 | HBA_PXIS = 2, /* Channel status, for error reporting */ |
---|
| 40 | HBA_PXIE = 3, /* Enabling / disabling the IRQ line */ |
---|
| 41 | HBA_PXCMD = 4, /* Activate Command List polling */ |
---|
| 42 | HBA_PXCI = 5, /* Command status bit-vector. */ |
---|
| 43 | |
---|
| 44 | HBA_SPAN = 0x400, /* HBA channel segment size (32 bits words) */ |
---|
| 45 | }; |
---|
| 46 | |
---|
| 47 | /**************************************************************************** |
---|
| 48 | * This structure defines the Command Descriptor. * |
---|
| 49 | ****************************************************************************/ |
---|
| 50 | |
---|
| 51 | typedef struct hba_cmd_desc_s |
---|
| 52 | { |
---|
| 53 | unsigned char flag[2]; /* WRITE when bit 6 of flag[0] is set. */ |
---|
| 54 | unsigned char prdtl[2]; /* Number of buffers. */ |
---|
| 55 | uint32_t prdbc; /* Number of bytes transfered. */ |
---|
| 56 | uint32_t ctba; /* 32 LSB of Command Table address. */ |
---|
| 57 | uint32_t ctbau; /* 32 MSB of Command Table address. */ |
---|
| 58 | |
---|
| 59 | } |
---|
| 60 | hba_cmd_desc_t; |
---|
| 61 | |
---|
| 62 | /**************************************************************************** |
---|
| 63 | * These structures define the Command Table associated with each Command * |
---|
| 64 | * Descriptor. * |
---|
| 65 | * * |
---|
| 66 | * For a given command, there is only one LBA coded in 48 bits to identify * |
---|
| 67 | * the block(s) on the device to be transfered. Yet the memory buffer can * |
---|
| 68 | * be splitted in a variable number of contiguous buffers. The Command * |
---|
| 69 | * Table thus contains 2 data structures: * |
---|
| 70 | * - 'hba_cmd_header_t' structure: fixed-size header (16 bytes) defining * |
---|
| 71 | * the LBA. * |
---|
| 72 | * - 'hba_cmd_buffer_t' structure: variable-sized array of fixed-size (16 * |
---|
| 73 | * bytes) buffer descriptors. * |
---|
| 74 | ****************************************************************************/ |
---|
| 75 | typedef struct hba_cmd_header_s |
---|
| 76 | { |
---|
| 77 | /* Word 1. */ |
---|
| 78 | uint32_t res0; /* Reserved. */ |
---|
| 79 | |
---|
| 80 | /* Word 2. */ |
---|
| 81 | unsigned char lba0; /* LBA 7:0. */ |
---|
| 82 | unsigned char lba1; /* LBA 15:8. */ |
---|
| 83 | unsigned char lba2; /* LBA 23:16. */ |
---|
| 84 | unsigned char res1; /* Reserved. */ |
---|
| 85 | |
---|
| 86 | /* Word 3. */ |
---|
| 87 | unsigned char lba3; /* LBA 31:24. */ |
---|
| 88 | unsigned char lba4; /* LBA 39:32. */ |
---|
| 89 | unsigned char lba5; /* LBA 47:40. */ |
---|
| 90 | unsigned char res2; /* Reserved. */ |
---|
| 91 | |
---|
| 92 | /* Word 4. */ |
---|
| 93 | uint32_t res3; /* Reserved. */ |
---|
| 94 | } |
---|
| 95 | hba_cmd_header_t; |
---|
| 96 | |
---|
| 97 | typedef struct hba_cmd_buffer_s |
---|
| 98 | { |
---|
| 99 | uint32_t dba; /* 32 LSB buffer base address. */ |
---|
| 100 | uint32_t dbau; /* 32 MSB buffer base address. */ |
---|
| 101 | uint32_t res; /* Reserved. */ |
---|
| 102 | uint32_t dbc; /* Buffer bytes count. */ |
---|
| 103 | } |
---|
| 104 | hba_cmd_buffer_t; |
---|
| 105 | |
---|
| 106 | typedef struct hba_cmd_table_s |
---|
| 107 | { |
---|
| 108 | hba_cmd_header_t header; |
---|
| 109 | hba_cmd_buffer_t buffer; |
---|
| 110 | } |
---|
| 111 | hba_cmd_table_t; |
---|
| 112 | |
---|
| 113 | /**************************************************************************** |
---|
| 114 | * Driver API functions. * |
---|
| 115 | ****************************************************************************/ |
---|
| 116 | |
---|
| 117 | /**************************************************************************** |
---|
| 118 | * This function initializes the HBA hardware registers and Command List. * |
---|
| 119 | * @ returns 0 on success, -1 on error. * |
---|
| 120 | ****************************************************************************/ |
---|
| 121 | int boot_hba_init(); |
---|
| 122 | |
---|
| 123 | /**************************************************************************** |
---|
| 124 | * This function registers a command in the Command List and Command Table. * |
---|
| 125 | * @ lba : LBA of the first block on the block device. * |
---|
| 126 | * @ buff_addr : memory buffer physical address. * |
---|
| 127 | * @ count : number of blocks to be transfered. * |
---|
| 128 | * @ returns 0 on success, -1 on error. * |
---|
| 129 | ****************************************************************************/ |
---|
| 130 | int boot_hba_access( uint32_t lba, |
---|
| 131 | uint64_t buf_paddr, |
---|
| 132 | uint32_t count ); |
---|
| 133 | |
---|
| 134 | #endif // BOOT_HBA_DRIVER_H |
---|