This is a creation in Article, where the information may have evolved or changed.
Dave always brings us this kind of plain, interesting and profound article. This is the original: Ice Cream makers and data races.
———— Translation Divider Line ————
Ice cream manufacturers and data races
Dave Cheney
This is an article about the race of data. The relevant code for this article is on Github: Github.com/davecheney/benandjerry.
This example simulates two ice cream makers Ben and Jerry randomly hosting their customers.
Package Mainimport "FMT" type Icecreammaker interface { //to customer say hello hello ()}type Ben struct { name String}fu NC (b *ben) Hello () { fmt. Printf ("Ben says, \" Hello my name is%s\ "\ n", b.name)}type Jerry struct { name String}func (j *jerry) Hello () { FM t.printf ("Jerry says, \" Hello My name is%s\ "\ n", J.name)}func main () { var ben = &ben{"Ben"} var Jerry = & ; jerry{"Jerry"} var maker icecreammaker = Ben var loop0, loop1 func () loop0 = func () { maker = Ben g o Loop1 () } Loop1 = func () { maker = Jerry Go loop0 () } Go Loop0 () for { maker. Hello () }}
It's a data race, fool.
Most programmers should easily see that there is a data race in this program.
The loop function modifies the value of maker without locking, when the loop in the main function calls maker. At the time of Hello (), it is not possible to specify which implementation of Hello will be called.
Some programmers may not care about it, whether Ben or Jerry comes to entertain clients, which is irrelevant.
Let's run this code and see what happens.
% env gomaxprocs=2 Go run main.go ... Ben says, "Hello my name is Ben" Jerry says, "Hello my name was Jerry" Jerry says, "Hello my name is Jerry" Ben says, "Hello M Y name is Jerry ' Ben says, ' Hello my name is Ben ' ...
Wait, what is this! Ben sometimes thinks he's Jerry. How is that possible?
Interface value
The key to understanding this race is to understand the representation of the interface values in memory.
An interface is conceptually a struct with two fields.
If you use Go to describe an interface, it will look like this.
Type interface struct { type uintptr //Pointer to the type that implements the interface data uintptr//holds the recipient's information that implements the interface}
Type points to the struct that implements the type that describes the value of this interface. Data points to the implementation of the value itself. The content of Data is passed through the interface as the recipient of the called method.
By using the statement maker Icecreammaker = Ben, the compiler generates code to do the following things.
The Type field of the interface is set to the definition of the *ben type, and the Data field holds a copy of Ben, a pointer to the value of Ben.
When the statement LOOP1 () executes, maker = Jerry updates the two fields in the interface value.
Type now points to the definition of *jerry, and Data holds a pointer to Jerry.
The Go memory model says that writing to a machine word is atomic, but the interface is two characters in size. When the interface value is modified, another goroutine may read its contents. In this example, there may be
So Jerry's Hello () function calls Ben as the receiver.
Summarize
There is nothing called security data race. Your program either has no data race, or its operations cannot be defined.
In this example, Ben and Jerry's memory layouts match exactly, so in some cases it looks harmless. Imagine what a chaotic world would be like if they had different memory layouts (which was left to the reader as an exercise).
The Go Race detector detects this error and other possibilities by simply adding the-race identity when invoking the go test, build, or install command.
Additional Questions
In the example code, the Hello method is defined as the pointer recipient of Ben or Jerry. If you replace the method defined on the value of Ben or Jerry, can you solve this data race?
Extended Reading
Russ Cox on the Go interface, after you read, you should also understand the next Russ written about the problem of the explanation.
Go Race Detector's blog post (Chinese translation).