Is it necessary to use AHCI_BASE address to rebase a AHCI PORT?

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
User avatar
gamingjam60
Member
Member
Posts: 70
Joined: Sat Aug 24, 2024 10:06 pm
Libera.chat IRC: gamingjam60
Location: India
GitHub: https://github.com/baponkar
Contact:

Is it necessary to use AHCI_BASE address to rebase a AHCI PORT?

Post by gamingjam60 »

The following url is showing to use AHCI_BASE to rebase a valid disk port. But in below I am using a dynamic free address(by using malloc and converting into corresponding physical address) to set port->clb and port->clbu (which I have found from ChatGPT) but fortunately it is working i.e. reading and writing LBA.My questions are is this correct way to implement AHCI SATA Disk read/write? If it is not correct then why it is working? What is the correct way to implement AHCI SATA DMA read/write?

Addition: Here port found from bar5 address which is use only to start and stop command engine not for rebasing memory registers.
Here my rebase function:

Code: Select all

void portRebase(HBA_PORT_T *port)
{
    stopCMD(port);

    // Allocate a physically contiguous region for this port:
    // Make it large enough for CLB (1K), FB (1K), CTBA area (8K), plus margin.
    const size_t ALLOC_SIZE = 64 * 1024; // 64 KiB to be safe
    void *base_virt = (void *) malloc(ALLOC_SIZE);
    if (!base_virt) {
        printf("[AHCI] portRebase: malloc failed\n");
        return;
    }

    // Convert to physical base (what HBA will use)
    uintptr_t base_phys = vir_to_phys((uintptr_t)base_virt);
    if (base_phys == 0) {
        printf("[AHCI] portRebase: vir_to_phys returned 0\n");
        return;
    }

    // Layout within the allocated block (choose simple contiguous layout)
    // CLB: offset 0
    uintptr_t clb_phys = base_phys + 0x0;
    void *clb_virt = (void *)((uintptr_t)base_virt + 0x0); // virtual pointer for CPU
    memset(clb_virt, 0, 0x400); // 1 KiB

    // FB: offset 4K (use 4 KiB aligned area)
    uintptr_t fb_phys = base_phys + 0x1000;
    void *fb_virt = (void *)((uintptr_t)base_virt + 0x1000);
    memset(fb_virt, 0, 0x100); // 256 bytes (FIS receive area), zeroed

    // Command tables area: offset 8K (we'll allocate 8 KiB per port for command tables)
    uintptr_t ctba_base_phys = base_phys + 0x2000;
    void *ctba_base_virt = (void *)((uintptr_t)base_virt + 0x2000);
    // Zero the whole CTBA area (32 * 256 = 8192)
    memset(ctba_base_virt, 0, 0x2000);

    // Program registers (hardware uses physical addresses)
    port->clb  = (uint32_t)(clb_phys & 0xFFFFFFFF);
    port->clbu = (uint32_t)(clb_phys >> 32);

    port->fb   = (uint32_t)(fb_phys & 0xFFFFFFFF);
    port->fbu  = (uint32_t)(fb_phys >> 32);

    // Now initialize each command header to point into the CTBA area
    HBA_CMD_HEADER_T* cmd_header = (HBA_CMD_HEADER_T*) clb_virt; // CPU-side pointer into CLB area
    for (int i = 0; i < 32; ++i) {
        // Each command table sized 256 bytes (0x100) at sequential offsets
        uintptr_t phys_ctba = ctba_base_phys + (i * 0x100);
        cmd_header[i].ctba  = (uint32_t)(phys_ctba & 0xFFFFFFFF);
        cmd_header[i].ctbau = (uint32_t)(phys_ctba >> 32);
        cmd_header[i].prdtl = 8; // example default
        // Clear command table memory (use virtual)
        void* virt_ctba = (void*)((uintptr_t)ctba_base_virt + (i * 0x100));
        memset(virt_ctba, 0, 0x100);
    }

    // Start command engine after setting CLB/FB/CTBA
    startCMD(port);

    // printf("[AHCI] portRebase: done for port %d (phys base %x)\n", port_no, (unsigned long)base_phys);
}
Octocontrabass
Member
Member
Posts: 6247
Joined: Mon Mar 25, 2013 7:01 pm

Re: Is it necessary to use AHCI_BASE address to rebase a AHCI PORT?

Post by Octocontrabass »

gamingjam60 wrote: Wed Oct 08, 2025 1:58 pmThe following url is showing to use AHCI_BASE to rebase a valid disk port.
The code on the wiki is only an example. What does the AHCI specification say about rebasing ports? (Hint: section 10.1.2 is a good place to start.)
gamingjam60 wrote: Wed Oct 08, 2025 1:58 pm(which I have found from ChatGPT)
If you can't tell whether ChatGPT is giving you the correct answer, why are you wasting your time asking it in the first place?
Post Reply