How do I cross compile a Go project on Linux to generate an executable for running on Windows?
To build from Linux to Windows, you need to set the environment variables GOOS to Windows and GOARCH to amd64.
On Bash or ZSH:
% GOOS=windows GOARCH=amd64 go build
For more details see: https://dave.cheney.net/2015/08/22/cross-compilation-with-go-1-5
A description of possible values for GOOS and GOARCH is available here: https://golang.org/doc/install/source#environment
If your package requires CGO then you need to use the mingw-w64 compiler:
sudo apt-get install gcc-multilib
sudo apt-get install gcc-mingw-w64
GOOS=windows GOARCH=386 \
CGO_ENABLED=1 CXX=i686-w64-mingw32-g++ CC=i686-w64-mingw32-gcc \
go build
Introduction
During your production process you may want to build your go program to support a windows architecture, but this is not always easy but here's a guide to help you building your go program for windows
CGO
Cgo is an element of go that allow Go packages to call C code.
But whether you're using CGO or not is not as easy as "did I called C code?" because while you may not have called C code in you Go program, a package that you're using probably does.
To figure it out the easiest thing is to try without and if it's not working try the second option. (But you can also try this if you want to)
If you don't need CGO
if you don't need CGO, building your go program to another platform is pretty easy as go natively support cross-platform compiling.
all you need to do is this:
x64
#Compile your go program to the windows x64 platform
env GOOS=windows GOARCH=amd64 go build package-import-path
x32
#Compile your go program to the windows x32 platform
env GOOS=windows GOARCH=386 go build package-import-path
Tip: Since go natively support cross compiling, you can easily build your program to other platform as well, further reading here
If you need CGO
if you need CGO, building your program will be a little bit more complicated since C doesn't support native cross-platform compiling..
But don't worry! It is still pretty easy using the MinGW64 project.
Requirements
Since we will be using mingw64 to build our project, we'll need to make sure mingw is installed.
If it's not here's how you can install it:
Ubuntu
On ubuntu simply run:
sudo apt-get install gcc-mingw-w64
Fedora
On fedora simply run:
sudo dnf install mingw64-gcc
Build
Now that we met the requirements, we can now build our project
For windows x64 architecture
To build your program on a windows x64 architecture run:
GOOS=windows GOARCH=amd64 CGO_ENABLED=1 CXX=x86_64-w64-mingw32-g++ CC=x86_64-w64-mingw32-gcc go build package-import-path
For windows x32 architecture
To build your program on a windows x32 architecture run:
GOOS=windows GOARCH=386 CGO_ENABLED=1 CXX=i686-w64-mingw32-g++ CC=i686-w64-mingw32-gcc go build package-import-path
Related
I have GCC v9. But I'm trying to install a GCC 4.8.1 version to test a library compilation on that very old version of GCC.
The version is not available in the official Ubuntu repos,it is deprecated, but I've found it in other mirrors as told by the official GCC website. This one seems like popular one:
https://launchpad.net/~ubuntu-toolchain-r/+archive/ubuntu/test
I have very little knowledge of linux package systems except for the basic. I want to keep both versions. So I should do this:
sudo apt -y install gcc-4.8.1 gcc-9
The reason why I want to use this command and not install it from the file, apart from the difficulty of doing that for me, is that I'm following a guide in order to have several GCCs on my system:
https://www.fosslinux.com/39386/how-to-install-multiple-versions-of-gcc-and-g-on-ubuntu-20-04.htm
When I add the url to the sources.list file seems like it is working.
sudo add-apt-repository ppa:ubuntu-toolchain-r/test
sudo apt update -q
But when I try to call the install with gcc-4.8.1 or gcc-4.8 , or even gcc-4 the package doesn't exist.
Package gcc-4.8 is not available, but is referred to by another
package. This may mean that the package is missing, has been
obsoleted, or is only available from another source E: Package
'gcc-4.8' has no installation candidate
Also, I don't know if websites like these can be added to the repos list in order to find the package using APT:
http://www.netgull.com/gcc/releases/gcc-4.8.1/
[EDIT]
I downloaded the package from the website I linked. I have no idea how to install this by hand. If only I could find a repository that could help me with this... I have no idea how to make APT help me with the installation.
But I'm trying to install a GCC 4.8.1 version to test a library compilation on that very old version of GCC.
Developers have tools up their sleeve so they don't have to install dependencies and bloating their systems for every library (and every configuration of that library!) they want to try out and test.
Use docker. You could write for example a testing script, assuming your project uses make:
# test_my_lib_in_gcc-4.8.sh
#!/bin/sh
docker run -ti --rm -v $PWD:/project -w /project gcc:4.8 -u $UID:$GID sh <<EOF
make && make test
EOF
that will compile and test your application in using 4.8 gcc. Consider how easy it is to change gcc version - just change the number. You could test your library in gcc, in different versions, and using other compilers and on different distributions to make sure it works for others. If you're a developer of the library, write an automatized CI pipeline that would automatically test your application each commit in specific docker environment, using ex. https://docs.gitlab.com/ee/ci/README.html or https://travis-ci.org/ .
I have a project writen with C99. It links to libcurl, generate makefile with cmake. Now, i want to explore the project to window env. I tried cygwin first, everything works except that final user need to install cygwin too.
After some search, mingw64 may archive my goal (build and use directly in window), but i could not find a full use guild for how to build linux project with mingw64 in ubuntu(linux).
Thanks for the help.
After some research, a solutions works:
install window cmake
install mingw-w64
mkdir build && cd build && cmake -G "MinGW Makefiles" ..
mingw32-make
MinGW may not support all API, some compatible job should be done.
I am trying to build some open source library. I need a package management system to easily download the dependencies. At first I am using MinGW and MSYS. But the included packages are limited. Someone told me to use Mingw-w64 and MSYS2.
I downloaded the mingw-w64-install from here. When running, it reports the following error. How can I fix it?
And by the way, from the Mingw-w64 download page, I see a lot of download links. Even Cygwin is listed. How are Cygwin and Mingw-w64 related?
My current understanding is, in the time of MinGW and MSYS, MSYS is just a nice addon to MinGW, while in Mingw-w64 + MSYS2, MSYS2 is stand-alone and Mingw-w64 is just a set of libraries it can work with. Just like Cygwin can download many different packages.
Unfortunately, the MinGW-w64 installer you used sometimes has this issue. I myself am not sure about why this happens (I think it has something to do with Sourceforge URL redirection or whatever that the installer currently can't handle properly enough).
Anyways, if you're already planning on using MSYS2, there's no need for that installer.
Download MSYS2 from this page.
After the install completes, click on the MSYS2 UCRT64 in the Start menu (or C:\msys64\ucrt64.exe).
If done correctly, the terminal prompt will say UCRT64 in magenta letters, not MSYS.
Update MSYS2 using pacman -Syuu. If it closes itself during the update, restart it and repeat the same command to finish the update.
You should routinely update your installation.
Install the toolchain: (i.e. the compiler and some extra tools)
pacman -S mingw-w64-ucrt-x86_64-toolchain
Install any libraries/tools you may need. You can search the repositories by doing
pacman -Ss name_of_something_i_want_to_install
e.g.
pacman -Ss gsl
and install using
pacman -S package_name_of_something_i_want_to_install
e.g.
pacman -S mingw-w64-ucrt-x86_64-gsl
and from then on the GSL library will be automatically found by your compiler!
Make sure any compilers and libraries you install have this package prefix: mingw-w64-ucrt-x86_64-. Only use unprefixed packages for misc command-line utilities (such as grep, sed, make, etc), unless you know what you're doing.
Verify that the compiler is working by doing
gcc --version
If you want to use the toolchains (with installed libraries) outside of the MSYS2 environment, all you need to do is add C:/msys64/ucrt64/bin to your PATH.
MSYS2 provides several compiler flavors, UCRT64 being one of them. It should be a reasonable default.
MSYS has not been updated a long time. MSYS2 is more active, and you can download it from MSYS2. It has both the mingw and cygwin fork package.
To install the MinGW-w64 toolchain (reference):
Open the MSYS2 shell from the start menu
Run pacman -Sy pacman to update the package database
Reopen the shell, and run pacman -Syu to update the package database and core system packages
Reopen the shell, and run pacman -Su to update the rest
Install the compiler:
For a 32-bit target, run pacman -S mingw-w64-i686-toolchain
For a 64-bit target, run pacman -S mingw-w64-x86_64-toolchain
Select which package to install; the default is all
You may also need make. Run pacman -S make
You can now also get the stand-alone personal build of MinGW-w64 from https://winlibs.com/ which doesn't require any installation; just extract and its ready to use. This allow having multiple toolchains on the same system (e.g., one for Windows 32-bit and another for Windows 64-bit).
The most straightforward way, as far as I know, is to use Chocolatey to install MinGW:
choco install mingw
Then check with the command whereis gcc. It is going to be installed in C:\ProgramData\chocolatey\bin.
one more thing, to get make working, just copie (or rename if you wish)
with copy mingw32-make.exe make.exe in C:\ProgramData\chocolatey\bin.
I am trying to install the gnu arm toolchain for ubuntu. I first downloaded the tar from CodeSourcery. However when I go into the bin folder, I cannot run any of the binaries. I have tried with ./ and without and putting it in the PATH and it keeps telling me "Command not Found" yet the file is there in the folder right in front of me. Then I tried sudo apt-get install gcc-arm-linux-gnueabi except after it says it has installed successfully, I cannot find it with whereis gcc-arm-linux-gnueabi. Can anyone help?
fixed, using:
sudo apt-get install gcc-arm*
Are you compiling on a 64-bit OS? Try:
sudo apt-get install ia32-libs
I had the same problem when trying to compile the Raspberry Pi kernel. I was cross-compiling on Ubuntu 12.04 64-bit and the toolchain requires ia32-libs to work on on a 64-bit system.
See http://hertaville.com/2012/09/28/development-environment-raspberry-pi-cross-compiler/
CodeSourcery convention is to use prefix arm-none-linux-gnueabi- for all executables, not gcc-arm-linux-gnueabi that you mention. So, standard name for CodeSourcery gcc would be arm-none-linux-gnueabi-gcc.
After you have installed CodeSourcery G++, you need to add CodeSourcery directory into your PATH.
Typically, I prefer to install CodeSourcery into directory like /opt/arm-2010q1 or something like that. If you don't know where you have installed it, you can find it using locate arm-none-linux-gnueabi-gcc, however you may need to force to update your locate db using sudo updatedb before locate will work properly.
After you have identified where your CodeSourcery is installed, add it your PATH by editing ~/.bashrc like this:
PATH=/opt/arm-2010q1/bin:$PATH
Also, it is customary and very convenient to define
CROSS_COMPILE=arm-none-linux-gnueabi-
in your .bashrc, because with CROSS_COMPILE defined, most tools will automatically use proper compiler for ARM compilation without you doing anything.
if you are on 64 bit os then you need to install this additional libraries.
sudo apt-get install lib32z1 lib32ncurses5 lib32bz2-1.0
got the same error when trying to cross compile the raspberry pi kernel on ubunto 14.04.03 64bit under VM. the solution was found here:
-Install packages used for cross compiling on the Ubuntu box.
sudo apt-get install gcc-arm-linux-gnueabi make git-core ncurses-dev
-Download the toolchain
cd ~
git clone https://github.com/raspberrypi/tools
-Add the toolchain to your path
PATH=$PATH:~/tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian:~/tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin
notice the x64 version in the path command
I was also facing the same issue and resolved it after installing the following dependency:
sudo apt-get install lib32z1-dev
If you are on a 64bit build of ubuntu or debian (see e.g. 'cat /proc/version') you should simply use the 64bit cross compilers, if you cloned
git clone https://github.com/raspberrypi/tools
then the 64bit tools are in
tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64
use that directory for the gcc-toolchain.
A useful tutorial for compiling that I followed is available here Building and compiling Raspberry PI Kernel (use the -x64 path from above as ${CCPREFIX})
You have installed a toolchain which was compiled for i686 on a box which is running an x86_64 userland.
Use an i686 VM.
Its a bit counter-intuitive. The toolchain is called gcc-arm-linux-gnueabi. To invoke the tools execute the following: arm-linux-gnueabi-xxx
where xxx is gcc or ar or ld, etc
try the following command:
which gcc-arm-linux-gnueabi
Its very likely the command is installed in /usr/bin.
I had to cross compile C code in Ubuntu for ARM. This worked for me:
$ sudo apt install gcc-arm-none-eabi
Later, tested it on the qemu emulator
#Install qemu
sudo apt-get install qemu qemu-user-static qemu-system-arm
#Cross compile "helloworld.c"
$ arm-none-eabi-gcc --specs=rdimon.specs -Wl,--start-group -lgcc -lc -lm -lrdimon -Wl,--end-group helloworld.c -o helloworld
#Run
qemu-arm-static helloworld
I'm trying to do this:
Build 32bit on 64 bit Linux using an automake configure script?
Doesn't work for me :(
Compileing wine. I found this in config.log:
configure: failed program was:
| /* confdefs.h */
| #define PACKAGE_NAME "Wine"
| #define PACKAGE_TARNAME "wine"
| #define PACKAGE_VERSION "1.5.19"
| #define PACKAGE_STRING "Wine 1.5.19"
| #define PACKAGE_BUGREPORT "wine-devel#winehq.org"
| #define PACKAGE_URL "http://www.winehq.org"
| /* end confdefs.h. */
|
| int
| main ()
| {
|
| ;
| return 0;
| }
Configuration fails with: Cannot build a 32-bit program, you need to install 32-bit development libraries.
apt-get install gcc-multilib libasound2-dev:i386 libgsm1-dev:i386 libjpeg8-dev:i386 liblcms2-dev:i386 libldap2-dev:i386 libmpg123-dev:i386 libopenal-dev:i386 libv4l-dev:i386 libx11-dev:i386 libxinerama-dev:i386 libxml2-dev:i386 zlib1g-dev:i386
and
apt-get install libcapi20-dev:i386 libcups2:i386 libdbus-1-3:i386 libfontconfig:i386 libfreetype6:i386 libglu1-mesa:i386 libgnutls26:i386 libgphoto2-2:i386 libncurses5:i386 libosmesa6:i386 libsane:i386 libxcomposite1:i386 libxcursor1:i386 libxi6:i386 libxrandr2:i386 libxslt1.1:i386 ocl-icd-libopencl1:i386
got me past X error.
To build 32-bit wine on 64-bit machine, you can use LXC (Linux Containers) which is an operating-system-level virtualization environment for running multiple isolated Linux systems. It's the easiest solution so far, as Linux (such as Ubuntu or Debian) makes building 32-bit wine hard because the 64-bit system doesn't come with a full set of 32-bit development libraries (See: Bug #990982).
So the basic approach to compile both 32-bit and 64-bit wine is:
Build 64-bit wine
Build 32-bit tools in lxc
Build 32-bit wine in lxc, referring to the 64-bit wine and 32-bit tools 1. built in the previous steps
Install 32-bit wine
Install 64-bit wine
On the page Building Biarch (Shared WoW64) Wine On Ubuntu we can read the following instructions:
Install the 64-bit prerequisites:
sudo apt-get update
sudo apt-get build-dep wine
Build 64-bit wine:
mkdir $HOME/wine64
cd $HOME/wine64
../wine-git/configure --enable-win64
make -j4
Install lxc:
sudo apt-get install lxc
Create a 32-bit container named "my32bitbox" using the Ubuntu
template and bind your home directory to the /home directory in the
container:
sudo lxc-create -t ubuntu -n my32bitbox -- --bindhome $LOGNAME -a i386
Copy the apt configuration from the host to the lxc container:
sudo cp -R /etc/apt /var/lib/lxc/my32bitbox/rootfs/etc
Start the container; at the console login prompt it gives you, log
in with your username and password.
sudo lxc-start -n my32bitbox
Now you're inside the container, in your real home directory. If you
are not in the container (you do not have the prompt
username#my32bitbox), then open a new terminal and:
sudo lxc-attach -n my32bitbox
login yourusername+password
Now, you are in the container. Do an out-of-tree build of Wine as
normal, just to get the tools. You'll have to install all the needed
prerequisites first. For instance:
sudo apt-get update
sudo apt-get install python-software-properties git-core
sudo apt-get build-dep wine
mkdir $HOME/wine32-tools
cd $HOME/wine32-tools
~/wine-git/configure
make -j4
Still inside the container, do it again, this time pointing to the
64-bit build for data, and the 32-bit tools build for tools:
mkdir $HOME/wine32
cd $HOME/wine32
~/wine-git/configure --with-wine64=$HOME/wine64 --with-wine-tools=$HOME/wine32-tools
make -j4
Still inside the container, install the 32-bit wine to force the
last little bit of building:
cd $HOME/wine32
sudo make install
While still inside the container, shut it down:
sudo shutdown -h now
This drops you back out into your real machine. Next, you need to
remove all existing Wine packages. You can do this from the command
line but it's probably easier with aptitude or one of the GUI
package management tools. You will need wine-mono, wine-gecko, and
optionally winetricks for your compiled version of wine. However,
these packages may depend on the existing wine installation which
may force you to remove them.
Install the newly built wine into your real machine:
cd $HOME/wine32
sudo make install
cd $HOME/wine64
sudo make install
Warning: When you install a locally built version of Wine, the
package management system will not know it exists since it did not
come from a package. Thus it is possible to later break its
dependencies or install a conflicting version of wine without a
warning from the package management tools. You can prevent this by
creating a package or by blocking conflicting packages with
apt-pinning by setting "Pin-Priority: -1" for the packages.
Next, install Mono, Gecko, and optionally winetricks if you had to
remove their packages because of a dependency on a conflicting wine
package.
Notes:
Many of the above commands require root privileges. Your user account needs to have access to root via sudo or you need to switch to a user account.
It's not necessary to remove your distro version and 'install' your compiled versions (32bit, 64bit) You simply need to invoke your personal version of wine appropriate for the Windows app. For example: ~/wine32/wine32 ~/.wine/path_to_winapp/my_app.
What worked to some extent for me on Debian Wheezy:
dpkg --add-architecture i386
apt-get update
to enable installation from the i386 repos
apt-get install ia32-libs libc6-dev-i386 lib32z1-dev lib32bz2-dev
to install the 32 bit libs. I'm actually still having trouble with X libs:
configure: error: X 32-bit development files not found. Wine will be built
without X support, which probably isn't what you want. You will need
to install 32-bit development packages of Xlib/Xfree86 at the very least.
Use the --without-x option if you really want this.
but it's technically optional.
you may solve the X error:
sudo apt-get install xorg-dev
Don't do that. Wine builds for 32-bit by default even on 64-bit systems (since it has to run 32-bit Windows programs.) It also builds a 64-bit Wine at the same time. If you want to disable that, configure it with:
./configure --disable-win64
I guess you use Ubuntu x64 which now supports multi-architecture. In other words on a 64 bit system you can build only Wine-x64 version. Building 32bit Wine on Ubuntu 12.04 x64 seems to buggy as for now.
So just run:
./configure --enable-win64
The Wine wiki has an easy way to install the needed 32bit development libraries on a 64bit system, using chroot: http://wiki.winehq.org/WineOn64bit