]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/cgo: update documentation on implementation details
authorHiroshi Ioka <hirochachacha@gmail.com>
Tue, 29 Aug 2017 08:28:15 +0000 (17:28 +0900)
committerIan Lance Taylor <iant@golang.org>
Tue, 29 Aug 2017 17:25:23 +0000 (17:25 +0000)
Change-Id: Iec771d5bbdf510b6c5ec17a614da90e7974a6348
Reviewed-on: https://go-review.googlesource.com/59870
Reviewed-by: Ian Lance Taylor <iant@golang.org>
src/cmd/cgo/doc.go

index bed2ab44c7f4bee26045297356536e07b6c2d31d..cfd09246af0e674c47135016d9b1894a27205a61 100644 (file)
@@ -406,21 +406,24 @@ about simple #defines for constants and the like. These are recorded
 for later use.
 
 Next, cgo needs to identify the kinds for each identifier. For the
-identifiers C.foo and C.bar, cgo generates this C program:
+identifiers C.foo, cgo generates this C program:
 
        <preamble>
        #line 1 "not-declared"
-       void __cgo_f_xxx_1(void) { __typeof__(foo) *__cgo_undefined__; }
+       void __cgo_f_1_1(void) { __typeof__(foo) *__cgo_undefined__1; }
        #line 1 "not-type"
-       void __cgo_f_xxx_2(void) { foo *__cgo_undefined__; }
-       #line 1 "not-const"
-       void __cgo_f_xxx_3(void) { enum { __cgo_undefined__ = (foo)*1 }; }
-       #line 2 "not-declared"
-       void __cgo_f_xxx_1(void) { __typeof__(bar) *__cgo_undefined__; }
-       #line 2 "not-type"
-       void __cgo_f_xxx_2(void) { bar *__cgo_undefined__; }
-       #line 2 "not-const"
-       void __cgo_f_xxx_3(void) { enum { __cgo_undefined__ = (bar)*1 }; }
+       void __cgo_f_1_2(void) { foo *__cgo_undefined__2; }
+       #line 1 "not-int-const"
+       void __cgo_f_1_3(void) { enum { __cgo_undefined__3 = (foo)*1 }; }
+       #line 1 "not-num-const"
+       void __cgo_f_1_4(void) { static const double __cgo_undefined__4 = (foo); }
+       #line 1 "not-str-lit"
+       void __cgo_f_1_5(void) { static const char __cgo_undefined__5[] = (foo); }
+       #line 1 "not-signed-int-const"
+       #if 0 < -(foo)
+       #line 1 "not-signed-int-const"
+       #error found unsigned int
+       #endif
 
 This program will not compile, but cgo can use the presence or absence
 of an error message on a given line to deduce the information it
@@ -430,45 +433,72 @@ errors that might stop parsing early.
 
 An error on not-declared:1 indicates that foo is undeclared.
 An error on not-type:1 indicates that foo is not a type (if declared at all, it is an identifier).
-An error on not-const:1 indicates that foo is not an integer constant.
+An error on not-int-const:1 indicates that foo is not an integer constant.
+An error on not-num-const:1 indicates that foo is not a number constant.
+An error on not-str-lit:1 indicates that foo is not a string literal.
+An error on not-signed-int-const:1 indicates that foo is not a signed integer constant.
 
-The line number specifies the name involved. In the example, 1 is foo and 2 is bar.
+The line number specifies the name involved. In the example, 1 is foo.
 
 Next, cgo must learn the details of each type, variable, function, or
 constant. It can do this by reading object files. If cgo has decided
-that t1 is a type, v2 and v3 are variables or functions, and c4, c5,
-and c6 are constants, it generates:
+that t1 is a type, v2 and v3 are variables or functions, and i4, i5
+are integer constants, u6 is an unsigned integer constant, and f7 and f8
+are float constants, and s9 and s10 are string constants, it generates:
 
        <preamble>
        __typeof__(t1) *__cgo__1;
        __typeof__(v2) *__cgo__2;
        __typeof__(v3) *__cgo__3;
-       __typeof__(c4) *__cgo__4;
-       enum { __cgo_enum__4 = c4 };
-       __typeof__(c5) *__cgo__5;
-       enum { __cgo_enum__5 = c5 };
-       __typeof__(c6) *__cgo__6;
-       enum { __cgo_enum__6 = c6 };
-
-       long long __cgo_debug_data[] = {
+       __typeof__(i4) *__cgo__4;
+       enum { __cgo_enum__4 = i4 };
+       __typeof__(i5) *__cgo__5;
+       enum { __cgo_enum__5 = i5 };
+       __typeof__(u6) *__cgo__6;
+       enum { __cgo_enum__6 = u6 };
+       __typeof__(f7) *__cgo__7;
+       __typeof__(f8) *__cgo__8;
+       __typeof__(s9) *__cgo__9;
+       __typeof__(s10) *__cgo__10;
+
+       long long __cgodebug_ints[] = {
                0, // t1
                0, // v2
                0, // v3
-               c4,
-               c5,
-               c6,
+               i4,
+               i5,
+               u6,
+               0, // f7
+               0, // f8
+               0, // s9
+               0, // s10
                1
        };
 
+       double __cgodebug_floats[] = {
+               0, // t1
+               0, // v2
+               0, // v3
+               0, // i4
+               0, // i5
+               0, // u6
+               f7,
+               f8,
+               0, // s9
+               0, // s10
+               1
+       };
+
+       const char __cgodebug_str__9[] = s9;
+       const unsigned long long __cgodebug_strlen__9 = sizeof(s9)-1;
+       const char __cgodebug_str__10[] = s10;
+       const unsigned long long __cgodebug_strlen__10 = sizeof(s10)-1;
+
 and again invokes the system C compiler, to produce an object file
 containing debug information. Cgo parses the DWARF debug information
 for __cgo__N to learn the type of each identifier. (The types also
-distinguish functions from global variables.) If using a standard gcc,
-cgo can parse the DWARF debug information for the __cgo_enum__N to
-learn the identifier's value. The LLVM-based gcc on OS X emits
-incomplete DWARF information for enums; in that case cgo reads the
-constant values from the __cgo_debug_data from the object file's data
-segment.
+distinguish functions from global variables.) Cgo reads the constant
+values from the __cgodebug_* from the object file's data segment.
 
 At this point cgo knows the meaning of each C.xxx well enough to start
 the translation process.
@@ -553,9 +583,12 @@ _cgo_main.c:
 
        int main() { return 0; }
        void crosscall2(void(*fn)(void*, int, uintptr_t), void *a, int c, uintptr_t ctxt) { }
-       uintptr_t _cgo_wait_runtime_init_done() { }
+       uintptr_t _cgo_wait_runtime_init_done() { return 0; }
+       void _cgo_release_context(uintptr_t ctxt) { }
+       char* _cgo_topofstack(void) { return (char*)0; }
        void _cgo_allocate(void *a, int c) { }
        void _cgo_panic(void *a, int c) { }
+       void _cgo_reginit(void) { }
 
 The extra functions here are stubs to satisfy the references in the C
 code generated for gcc. The build process links this stub, along with