在cgo中使用Windows库

I'm trying to build a Go package which makes use of TagLib, and I'm having a little trouble figuring out exactly how to use the compiled libraries with cgo.

I've compiled TagLib, which has spit out tag.dll, tag.exp, and tag.lib in the taglib dir. There were also the taglib_c.* binaries in the bindings directory, but I'm assuming that I just ignore those.

How do I make use of the compiled libraries for use with Go? I have everything setup in the source from the project on OS X, but what do I need to do to make it compile on Windows? Does the compiled library (dll or static lib?) have to be in the same directory as the source? What about the headers?

Unfortunately I don't have a windows machine available to try this out myself, but theoretically, this should work. The steps I have listed are written with a unix perspective, but it should be directly translatable to Windows unless otherwise noted. For Windows, I like to use GitBash for my terminal as it comes with some useful unix tools.

Anyways, I'm gonna work through the entire process to make sure I'm not making any assumptions. first, we'll start with downloading and installing taglib. Assuming that you've downloading the 1.8 tarball that they have available, then I would install it locally in some folder in my computer:

/home/noj $ mkdir -p clibs/src
/home/noj $ cd clibs/src
/home/noj/clibs/src $ tar -xvf /home/noj/Downloads/
/home/noj/clibs/src $ cd taglib-1.8
/home/noj/clibs/src/taglib-1.8 $ cmake -DCMAKE_INSTALL_PREFIX=/home/noj/clibs -DCMAKE_RELEASE_TYPE=Release .
/home/noj/clibs/src/taglib $ make
/home/noj/clibs/src/taglib $ make install

The above code should install taglib locally for development in the folder /home/noj/clibs. If you take a look at the inside of the folder, you'll find subdirectories for bin, lib, and include.

So here's the funky part. The Windows standard is to dump dynamic lib files (*.dll) into the bin directory. Some open source libraries adhere to this and do that, others still dump the *.dll files in the lib directory since that's where they usually go in Unix systems. You'll want to take a look at the lib directory generated by the installation and copy any *.dll files that are generated over to the bin directory to make sure proper linking takes place without too much hackery.

Now for the go source code! At the top of your source code, you'll want to include the cgo meta comments to tell Go where to search for the libraries you want, as well as their headers (the include directory generated during the installation). Here's some Go source that tries to use the libraries we just built above:

package main

/*
#cgo LDFLAGS: -L/home/noj/clibs/lib -ltag -lstdc++
#cgo CFLAGS: -I/home/noj/clibs/include/taglib

#include <taglib.h>
*/
import "C"

import (
  // normal imports
  // ...
)

func main() {
  // ...
}

Now, Windows, also requires you to add the directory where your *.dll files live to your PATH, so we'll go ahead and do that...

/home/noj $ export PATH=$PATH:/home/noj/clibs/bin

And now we should be ready to compile the code normally using go build within the Go's source directory.

Possible Problems:

So some problems you might run into is finding out that you don't have the necessary libraries to build taglib in Windows, though it sounds like you've already built it, so that should be fine. You'll notice that in the go source I added the LDFLAG for the standard c++ library. This is because taglib uses C++. If this turns out to be a problem, I would create a simple C program alongside your go code that interfaces with the c++ library and creates a C interface for it. From my experience, it's a lot easier to work with a C library and Go than with C++ and Go.