On Mon, May 10, 2021 at 5:56 AM 计算鸡 <[email protected]> wrote: > > ```go > package main > > type T struct { > a *int > } > > func test(t *T, b *int) { > t.a = b > } > ``` > compile this code use cmd `go build -gcflags '-l' main.go` > only disable inline stage . > > here is the plan9 assembly of function test > > ```assembly > TEXT main.test(SB) src/write-barrier/main.go > main.go:7 0x45ec60 64488b0c25f8ffffff MOVQ FS:0xfffffff8, CX > main.go:7 0x45ec69 483b6110 CMPQ 0x10(CX), SP > main.go:7 0x45ec6d 7639 JBE 0x45eca8 > main.go:7 0x45ec6f 4883ec08 SUBQ $0x8, SP > main.go:7 0x45ec73 48892c24 MOVQ BP, 0(SP) > main.go:7 0x45ec77 488d2c24 LEAQ 0(SP), BP > main.go:8 0x45ec7b 488b7c2410 MOVQ 0x10(SP), DI > main.go:8 0x45ec80 8407 TESTB AL, 0(DI) > main.go:8 0x45ec82 833d379c090000 CMPL $0x0, > runtime.writeBarrier(SB) > main.go:8 0x45ec89 7511 JNE 0x45ec9c > main.go:8 0x45ec8b 488b442418 MOVQ 0x18(SP), AX > main.go:8 0x45ec90 488907 MOVQ AX, 0(DI) > main.go:9 0x45ec93 488b2c24 MOVQ 0(SP), BP > main.go:9 0x45ec97 4883c408 ADDQ $0x8, SP > main.go:9 0x45ec9b c3 RET > main.go:8 0x45ec9c 488b442418 MOVQ 0x18(SP), AX > main.go:8 0x45eca1 e8facaffff CALL runtime.gcWriteBarrier(SB) > main.go:8 0x45eca6 ebeb JMP 0x45ec93 > main.go:7 0x45eca8 e8b3afffff CALL > runtime.morestack_noctxt(SB) > main.go:7 0x45ecad ebb1 JMP main.test(SB) > ``` > > i was confused with the instruction ` main.go:8 0x45ec80 8407 > TESTB AL, 0(DI)` > i think it must used for checking nil pointer . but both test and cmp will > modify ZF in eflags. ( there is a cmp instruction follow the test ) > > i think it should insert instruction `JE 0x45ec9c ` between test and cml > instruction .
The "TESTB AL, 0(DI)" instruction will force the processor to attempt to retrieve the value at address 0(DI). If DI does not hold a valid address, the processor will fault. The runtime will pick up this fault and turn it into a run-time panic saying "invalid memory address or nil pointer dereference". That is, the instruction is not being executed to set the flags. It is being executed for its effect of testing whether the memory is valid. Ian -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAOyqgcWXDCrMswVfhHSAXUxd8u3ZCO_RrFBNS_Zic%3Da8ABf30g%40mail.gmail.com.
