| <!-- Setting up and using gccgo --> |
| |
| <p> |
| This document explains how to use <code>gccgo</code>, a compiler for |
| the Go language. The <code>gccgo</code> compiler is a new frontend |
| for <code>gcc</code>, the widely used GNU compiler. Although the |
| frontend itself is under a BSD-style license, <code>gccgo</code> is |
| normally used as part of <code>gcc</code> and is then covered by |
| the <a href="http://www.gnu.org/licenses/gpl.html">GNU General Public |
| License</a>. |
| </p> |
| |
| <p> |
| Note that <code>gccgo</code> is not the <code>6g</code> compiler; see |
| the <a href="install.html">Installing Go</a> instructions for that |
| compiler. |
| </p> |
| |
| <h2 id="Source_code">Source code</h2> |
| |
| <p> |
| The <code>gccgo</code> source code is accessible via Subversion. The |
| <code>gcc</code> web site |
| has <a href="http://gcc.gnu.org/svn.html">instructions for getting the |
| <code>gcc</code> source code</a>. The <code>gccgo</code> source code |
| is a branch of the main <code>gcc</code> code |
| repository: <code>svn://gcc.gnu.org/svn/gcc/branches/gccgo</code>. |
| </p> |
| |
| <h2 id="Building">Building</h2> |
| |
| <p> |
| Building <code>gccgo</code> is just like building <code>gcc</code> |
| with one or two additional options. See |
| the <a href="http://gcc.gnu.org/install/">instructions on the gcc web |
| site</a>. When you run <code>configure</code>, add the |
| option <code>--enable-languages=c,c++,go</code> (along with other |
| languages you may want to build). If you are targeting a 32-bit x86, |
| then you will want to build <code>gccgo</code> to default to |
| supporting locked compare and exchange instructions; do this by also |
| using the <code>configure</code> option <code>--with-arch=i586</code> |
| (or a newer architecture, depending on where you need your programs to |
| run). |
| </p> |
| |
| <p> |
| A number of prerequisites are required to build <code>gcc</code>, as |
| described on the <code>gcc</code> web site. If those are all |
| available, then a typical build and install sequence would look like |
| this: |
| |
| <pre> |
| svn checkout svn://gcc.gnu.org/svn/gcc/branches/gccgo gccgo |
| mkdir objdir |
| cd objdir |
| ../gccgo/configure --enable-languages=c,c++,go |
| make |
| make install |
| </pre> |
| </p> |
| |
| <h2 id="Using_gccgo">Using gccgo</h2> |
| |
| <p> |
| The <code>gccgo</code> compiler works like other gcc frontends. |
| |
| <p> |
| To compile a file: |
| |
| <pre> |
| gccgo -c file.go |
| </pre> |
| |
| <p> |
| That produces <code>file.o</code>. To link files together to form an |
| executable: |
| |
| <pre> |
| gccgo -o file file.o |
| </pre> |
| |
| <p> |
| To run the resulting file, you will need to tell the program where to |
| find the Go runtime library. This can be done either by setting |
| <code>LD_LIBRARY_PATH</code> in your environment: |
| |
| <pre> |
| LD_LIBRARY_PATH=/usr/lib/gcc/MACHINE/VERSION |
| </pre> |
| |
| <p> |
| or by passing a <code>-Wl,-R</code> option when you link: |
| |
| <pre> |
| gccgo -o file file.o -Wl,-R,/usr/lib/gcc/MACHINE/VERSION |
| </pre> |
| |
| <p> |
| or you can use the <code>-static-libgo</code> link-time option to link |
| statically against libgo, or you can do a fully static link (static |
| linking is the default for the <code>6l</code> Go linker). On most |
| systems, a static link will look something like: |
| |
| <pre> |
| gccgo -o file file.o -static -L /usr/lib/nptl -lgobegin -lgo -lpthread |
| </pre> |
| |
| <p> |
| You may get a warning about not creating an <code>.eh_frame_hdr</code> |
| section; this has nothing to do with Go, and may be ignored. In the |
| future the requirement of explicitly specifying |
| <code>-L /usr/lib/nptl -lgobegin -lgo -lpthread</code> |
| may be removed. |
| |
| |
| <h2 id="Imports">Imports</h2> |
| |
| <p> |
| When you compile a file which exports something, the export |
| information will be stored directly in the object file. When |
| you import a package, you must tell <code>gccgo</code> how to |
| find the file. |
| |
| <p> |
| When you import the package <var>FILE</var> with <code>gccgo</code>, |
| it will look for the import data in the following files, and use the |
| first one that it finds. |
| |
| <ul> |
| <li><code><var>FILE</var>.gox</code> |
| <li><code><var>FILE</var>.o</code> |
| <li><code>lib<var>FILE</var>.so</code> |
| <li><code>lib<var>FILE</var>.a</code> |
| </ul> |
| |
| <p> |
| <code><var>FILE</var>.gox</code>, when used, will typically contain |
| nothing but export data. This can be generated from |
| <code><var>FILE</var>.o</code> via |
| |
| <pre> |
| objcopy -j .go_export FILE.o FILE.gox |
| </pre> |
| |
| <p> |
| The <code>gccgo</code> compiler will look in the current |
| directory for import files. In more complex scenarios you |
| may pass the <code>-I</code> or <code>-L</code> option to |
| <code>gccgo</code>. Both options take directories to search. The |
| <code>-L</code> option is also passed to the linker. |
| |
| The <code>gccgo</code> compiler does not currently (2009-11-06) record |
| the file name of imported packages in the object file. You must |
| arrange for the imported data to be linked into the program. |
| |
| <pre> |
| gccgo -c mypackage.go # Exports mypackage |
| gccgo -c main.go # Imports mypackage |
| gccgo -o main main.o mypackage.o # Explicitly links with mypackage.o |
| </pre> |
| |
| <h2 id="Unimplemented">Unimplemented</h2> |
| |
| <p> |
| Some Go features are not yet implemented in <code>gccgo</code>. As of |
| 2009-11-06, the following are not implemented: |
| |
| <ul> |
| <li>Garbage collection is not implemented. There is no way to free memory. |
| Thus long running programs are not supported. |
| |
| <li>goroutines are implemented as NPTL threads with a fixed stack size. |
| The number of goroutines that may be created at one time is limited. |
| </ul> |
| |
| <h2 id="Debugging">Debugging</h2> |
| |
| <p> |
| If you use the <code>-g</code> option when you compile, you can run |
| <code>gdb</code> on your executable. The debugger doesn't (yet) |
| know anything about Go. However, you can set breakpoints, single-step, |
| etc. You can print variables, but they will be printed as though they |
| had C/C++ types. For numeric types this doesn't matter. Go strings |
| will show up as pointers to structures; to see the value |
| <code>print *stringvar</code>. In general Go strings, maps, channels |
| and interfaces are always represented as C pointers. |
| |
| <h2 id="C_Interoperability">C Interoperability</h2> |
| |
| <p> |
| When using <code>gccgo</code> there is limited interoperability with C, |
| or with C++ code compiled using <code>extern "C"</code>. |
| |
| <h3 id="Types">Types</h3> |
| |
| <p> |
| Basic types map directly: an <code>int</code> in Go is an <code>int</code> |
| in C, etc. Go <code>byte</code> is equivalent to C <code>unsigned char</code>. |
| Pointers in Go are pointers in C. A Go <code>struct</code> is the same as C |
| <code>struct</code> with the same fields and types. |
| |
| <p> |
| The Go <code>string</code> type is a pointer to a structure. |
| The current definition is |
| (this is <b style="color: red;">expected to change</b>): |
| |
| <pre> |
| struct __go_string { |
| size_t __length; |
| unsigned char __data[]; |
| }; |
| </pre> |
| |
| <p> |
| You can't pass arrays between C and Go. However, a pointer to an |
| array in Go is equivalent to a C pointer to the |
| equivalent of the element type. |
| For example, Go <code>*[10]int</code> is equivalent to C <code>int*</code>, |
| assuming that the C pointer does point to 10 elements. |
| |
| <p> |
| A slice in Go is a structure. The current definition is |
| (this is <b style="color: red;">subject to change</b>): |
| |
| <pre> |
| struct __go_slice { |
| void *__values; |
| int __count; |
| int __capacity; |
| }; |
| </pre> |
| |
| <p> |
| The type of a Go function with no receiver is equivalent to a C function |
| whose parameter types are equivalent. When a Go function returns more |
| than one value, the C function returns a struct. For example, these |
| functions have equivalent types: |
| |
| <pre> |
| func GoFunction(int) (int, float) |
| struct { int i; float f; } CFunction(int) |
| </pre> |
| |
| <p> |
| A pointer to a Go function is equivalent to a pointer to a C function |
| when the functions have equivalent types. |
| |
| <p> |
| Go <code>interface</code>, <code>channel</code>, and <code>map</code> |
| types have no corresponding C type (they roughly correspond to pointers |
| to structs in C, but the structs are deliberately undocumented). C |
| <code>enum</code> types correspond to some Go type, but precisely |
| which one is difficult to predict in general; use a cast. C <code>union</code> |
| types have no corresponding Go type. C <code>struct</code> types containing |
| bitfields have no corresponding Go type. C++ <code>class</code> types have |
| no corresponding Go type. |
| |
| <p> |
| Memory allocation is completely different between C and Go, as Go uses |
| garbage collection. The exact guidelines in this area are undetermined, |
| but it is likely that it will be permitted to pass a pointer to allocated |
| memory from C to Go. The responsibility of eventually freeing the pointer |
| will remain with C side, and of course if the C side frees the pointer |
| while the Go side still has a copy the program will fail. When passing a |
| pointer from Go to C, the Go function must retain a visible copy of it in |
| some Go variable. Otherwise the Go garbage collector may delete the |
| pointer while the C function is still using it. |
| |
| <h3 id="Function_names">Function names</h3> |
| |
| <p> |
| Go code can call C functions directly using a Go extension implemented |
| in <code>gccgo</code>: a function declaration may be followed by |
| <code>__asm__("NAME")</code>. For example, here is how the C function |
| <code>open</code> can be declared in Go: |
| |
| <pre> |
| func c_open(name *byte, mode int, perm int) int __asm__ ("open"); |
| </pre> |
| |
| <p> |
| The C function naturally expects a nul terminated string, which in |
| Go is equivalent to a pointer to an array (not a slice!) of |
| <code>byte</code> with a terminating zero byte. So a sample call |
| from Go would look like (after importing the <code>os</code> package): |
| |
| <pre> |
| var name = [4]byte{'f', 'o', 'o', 0}; |
| i := c_open(&name[0], os.O_RDONLY, 0); |
| </pre> |
| |
| <p> |
| (this serves as an example only, to open a file in Go please use Go's |
| <code>os.Open</code> function instead). |
| |
| <p> |
| The name of Go functions accessed from C is subject to change. At present |
| the name of a Go function that does not have a receiver is |
| <code>package.Functionname</code>. To call it from C you must set the |
| name using a <code>gcc</code> extension similar to the <code>gccgo</code> |
| extension. |
| |
| <pre> |
| extern int go_function(int) __asm__ ("mypackage.Function"); |
| </pre> |
| |
| <h3 id="Automatic_generation_of_Go_declarations_from_C_source_code"> |
| Automatic generation of Go declarations from C source code</h3> |
| |
| <p> |
| The Go version of <code>gcc</code> supports automatically generating |
| Go declarations from C code. The facility is rather awkward at present, |
| and a better mechanism is under development. |
| |
| <p> |
| Compile your C code as usual, but replace <code>-c</code> with |
| <code>-S -ggo</code>. The result will be an assembler file |
| with a <code>.s</code> extension. This assembler file will contain |
| comments beginning with #GO. Those comments are declarations in the Go |
| language for the C types, variables and functions declared in the C code. |
| C types which can not be represented in Go will contain the string INVALID. |
| Unsupported macro definitions will be recorded as <code>unknowndefine</code>, |
| and uses of <code>#undef</code> will be recorded as <code>undef</code>. |
| So it is very approximately possible to get Go code by running |
| |
| <pre> |
| gcc -S -ggo foo.c |
| grep '#GO' foo.s | grep -v INVALID | grep -v unknowndefine | grep -v undef > foo.go |
| </pre> |
| |
| <p> |
| This procedure is full of unstated caveats and restrictions and we make no |
| guarantee that it will not change in the future. It is more useful as a |
| starting point for real Go code than as a regular procedure. |