On Fri, 5 Dec 2025 at 14:27, Shusaku KURAMITSU
<[email protected]> wrote:
> I've noticed a possible discrepancy between the comment and the behavior
>
> of i386's prepare_host_addr (located at tcg/i386/tcg-target.c.inc, line
> 2157-2260):
>
>
> ```
>
> /*
>   * For softmmu, perform the TLB load and compare.
>   * For useronly, perform any required alignment tests.
>   * In both cases, return a TCGLabelQemuLdst structure if the slow path
>   * is required and fill in @h with the host address for the fast path.
>   */
> static TCGLabelQemuLdst *prepare_host_addr(TCGContext *s, HostAddress *h,
>                                             TCGReg addr, MemOpIdx oi,
> bool is_ld)
> {
>      TCGLabelQemuLdst *ldst = NULL;
>
> ...
>      if (tcg_use_softmmu) {
>
> ...
>
>          ldst = new_ldst_label(s);
>          ldst->is_ld = is_ld;
>          ldst->oi = oi;
>          ldst->addr_reg = addr;
>
> ...
>
>      } else if (a_mask) {
> ...
>      }
>
>      return ldst;
> }
>
> ```
>
>
> The code appears to always assign (in case of softmmu) a label to `ldst`
> and return it,

No; if tcg_use_softmmu is false and a_mask is zero then
we will not take either the if() or the else if() block,
and ldst will still be NULL when we return it.

This is because:
 * softmmu always requires a slowpath (because we might
   look the guest address up in the TLB but not find it)
 * linux-user mode needs a slowpath only if we need to
   enforce alignment and atomicity checks for this
   memory access (because linux-user always has "guest
   address == host address + some constant", so most
   simple loads and stores cannot fail or be complicated)

If we don't have to do either, then we don't need the slowpath.

> As I understand it, there is no way to determine, at this point, which
> of the two paths to use;
>
> the generated machine code (see L2233-2237), not the C code here,
> performs the TLB comparison.

That's right. We are generating the code in this function
to do everything except the final "load/store from the host
address" part. If we're using softmmu that includes all the
code to look the guest address up in the TLB.

I think the way to understand this function is to look at
the functions that call it, like tgen_qemu_ld(). They do:

 * call prepare_host_addr()
 * call a function to generate a plain host load or store

If the prepare_host_addr() code wants to do an out of
line slow-path, then the code we emit looks like:
  - do stuff to figure out if we can fast path this
  - conditional jump to out-of-line label for slow path
  - fast path handling; at the end of this we have the
    host address for the memory access
  - host load or store generated by tgen_qemu_ld etc
  - and then fall through into code for the next guest insn

At the end of the TB we will arrange to emit the
out-of-line label and the slow path code.

thanks
-- PMM

Reply via email to