I'm new to C and looking at Go's source tree I found this:
https://code.google.com/p/go/source/browse/src/pkg/runtime/race.c
void runtime∕race·Read(int32 goid, void *addr, void *pc);
void runtime∕race·Write(int32 goid, void *addr, void *pc);
void
runtime·raceinit(void)
{
// ...
}
What do the slashes and dots (·) mean? Is this valid C?
IMPORTANT UPDATE:
The ultimate answer is certainly the one you got from Russ Cox, one of Go authors, on the golang-nuts mailing list. That said, I'm leaving some of my earlier notes below, they might help to understand some things.
Also, from reading this answer linked above, I believe the
∕
"pseudo-slash" may now be translated to regular/
slash too (like the middot is translated to dot) in newer versions of Go C compiler than the one I've tested below - but I don't have time to verify.
The file is compiled by the Go Language Suite's internal C compiler, which originates in the Plan 9 C compiler(1)(2), and has some differences (mostly extensions, AFAIK) to the C standard.
One of the extensions is, that it allows UTF-8 characters in identifiers.
Now, in the Go Language Suite's C compiler, the middot character (·) is treated in a special way, as it is translated to a regular dot (.) in object files, which is interpreted by Go Language Suite's internal linker as namespace separator character.
Example
For the following file
example.c
(note: it must be saved as UTF-8 without BOM):void ·Bar1() {} void foo·bar2() {} void foo∕baz·bar3() {}the internal C compiler produces the following symbols:
$ go tool 8c example.c $ go tool nm example.8 T "".Bar1 T foo.bar2 T foo∕baz.bar3Now, please note I've given the
·Bar1()
a capitalB
. This is because that way, I can make it visible to regular Go code - because it is translated to the exact same symbol as would result from compiling the following Go code:package example func Bar1() {} // nm will show: T "".Bar1
Now, regarding the functions you named in the question, the story goes further down the rabbit hole. I'm a bit less sure if I'm right here, but I'll try to explain based on what I know. Thus, each sentence below this point should be read as if it had "AFAIK" written just at the end.
So, the next missing piece needed to better understand this puzzle, is to know something more about the strange ""
namespace, and how the Go suite's linker handles it. The ""
namespace is what we might want to call an "empty" (because ""
for a programmer means "an empty string") namespace, or maybe better, a "placeholder" namespace. And when the linker sees an import going like this:
import examp "path/to/package/example"
//...
func main() {
examp.Bar1()
}
then it takes the $GOPATH/pkg/.../example.a
library file, and during import phase substitutes on the fly each ""
with path/to/package/example
. So now, in the linked program, we will see a symbol like this:
T path/to/package/example.Bar1