Lição 3: Posse, transferência e empréstimo

Agora entramos no modelo de memória: posse linear. Uma requisição HTTP, um buffer ou uma mensagem tem um responsável claro; funções podem transferir essa responsabilidade ou apenas emprestar acesso.

Objetivo

Em uma frase: entender quem é dono de um valor e como passar dados sem copiar.

Código

import io

struct Mensagem {
    texto: str
    prioridade: int
}

func enviar(origem: own Mensagem) {
    io.println(origem.texto)
}

func ler(destino: ref Mensagem) {
    io.println(destino.texto)
}
  • own transfere a posse. Quem recebe passa a ser responsável pelo valor.
  • ref empresta sem transferir posse. A função pode ler o valor, mas não passa a administrá-lo.

Leia a assinatura como uma regra de fluxo: enviar consome a mensagem; depois da chamada, o chamador não pode usar aquela mesma mensagem. ler recebe uma referência temporária; depois da chamada, o dono continua podendo usar o valor. Assim, own controla transferência e ref controla acesso sem cópia.

Experimente

Passe a mesma Mensagem para enviar e depois tente usá-la de novo. O compilador te mostrará que a posse foi movida — e é exatamente isso que impede o use-after-free.

Garantia

É aqui que a Arandu salva de um segfault: você não consegue usar um valor depois de ter cedido a posse. O erro aparece em tempo de compilação, não no servidor em produção.

Por baixo dos panos

Sem lifetimes explícitos no MVP. A regra é simples: ou você é dono (own), ou você empresta (ref). A simplicidade é de propósito — o compilador faz o resto da contabilidade.

Esse é o modelo de transferência de posse linear: o compilador verifica aliasing e uso após movimento sem depender de um coletor de lixo.