Segurança na fronteira
As cinco formas de corromper memória chamando C, e a conferência que cada uma pede.
Do lado do DataForge, todo índice é conferido e nenhum ponteiro solto existe. Do lado do C, nada disso vale. Os defeitos abaixo não dão erro na linha que os causa: aparecem depois, em outro lugar, ou derrubam o processo sem mensagem.
| Defeito | Como acontece | A conferência |
|---|---|---|
| assinatura errada | i32 onde o C quer i64, f32 onde quer double | copie do .h, nunca de memória |
| buffer pequeno | passar 16 bytes para uma função que escreve 64 | alocar o que a documentação pede, com folga |
| uso depois de liberar | guardar um ponteiro de um bloco já liberado | C.liberar num lugar só, e nada guarda o ponteiro depois |
| callback coletado | o C guarda a função e chama depois que o lado de cá a soltou | manter a referência viva enquanto o C puder chamar |
| thread errada | biblioteca que não é thread-safe chamada de duas threads | um mutex em volta de toda chamada a ela |
dataforge
adopt Arcane.C as C
bloco := C.alocar(4 * C.tamanho_de("i32"))
p := C.ponteiro(bloco, "i32")
p.escrever(7)
assert p.ler() is 7
C.liberar(bloco)
recusado := no
monitor:
C.ponteiro(C.nulo(), "i32").ler() // o nulo é recusado, e não lido
handle Error:
recusado := yes
assert recusado