spiritov
(spiritov)
October 8, 2025, 11:19pm
1
when building my program that relies on cgo with go-sqlite3
, i run into this error:
$ go build .
# github.com/mattn/go-sqlite3
cgo: cannot parse gcc output $WORK\b066\\_cgo_.o as ELF, Mach-O, PE, XCOFF object
gcc and my linker are in my path:
$ which gcc
/c/Program Files/w64devkit/bin/gcc
$ gcc --version
gcc.exe (GCC) 15.2.0
Copyright (C) 2025 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
$ ld
C:\Program Files\w64devkit\bin\ld.exe: no input files
and my go env looks like this:
$ go env
set AR=ar
set CC=gcc
set CGO_CFLAGS=-O2 -g
set CGO_CPPFLAGS=
set CGO_CXXFLAGS=-O2 -g
set CGO_ENABLED=1
set CGO_FFLAGS=-O2 -g
set CGO_LDFLAGS=-O2 -g
set CXX=g++
set GCCGO=gccgo
set GO111MODULE=
set GOAMD64=v1
set GOARCH=amd64
set GOAUTH=netrc
set GOBIN=
set GOCACHE=C:\Users\spiritov\AppData\Local\go-build
set GOCACHEPROG=
set GODEBUG=
set GOENV=C:\Users\spiritov\AppData\Roaming\go\env
set GOEXE=.exe
set GOEXPERIMENT=
set GOFIPS140=off
set GOFLAGS=
set GOGCCFLAGS=-m64 -mthreads -Wl,--no-gc-sections -fmessage-length=0 -ffile-prefix-map=C:\Users\spiritov\AppData\Local\Temp\go-build283819157=/tmp/go-build -gno-record-gcc-switches
set GOHOSTARCH=amd64
set GOHOSTOS=windows
set GOINSECURE=
set GOMOD=C:\code\github\spiritov\jump\api\go.mod
set GOMODCACHE=C:\Users\spiritov\go\pkg\mod
set GONOPROXY=
set GONOSUMDB=
set GOOS=windows
set GOPATH=C:\Users\spiritov\go
set GOPRIVATE=
set GOPROXY=https://proxy.golang.org,direct
set GOROOT=C:\Users\spiritov\sdk\go1.24.8
set GOSUMDB=sum.golang.org
set GOTELEMETRY=local
set GOTELEMETRYDIR=C:\Users\spiritov\AppData\Roaming\go\telemetry
set GOTMPDIR=
set GOTOOLCHAIN=auto
set GOTOOLDIR=C:\Users\spiritov\sdk\go1.24.8\pkg\tool\windows_amd64
set GOVCS=
set GOVERSION=go1.24.8
set GOWORK=
set PKG_CONFIG=pkg-config
I don’t use cgo so I’m not familiar with it. But, I did find this issue:
opened 01:21AM - 20 Feb 24 UTC
unverified
### Checklist
- [X] I have searched the [issue tracker](https://github.com/fyne… -io/fyne/issues) for open issues that relate to the same problem, before opening a new one.
- [X] This issue only relates to a single bug. I will open new issues for any other problems.
### Describe the bug
1 computer system is windows10 64bit
2 go version go1.22.0 windows/amd64
3 gcc version 8.1.0 (x86_64-posix-seh-rev0, Built by MinGW-W64 project)
4 fyne Environment Check is pass all
5 run command: go run fyne.io/fyne/v2/cmd/fyne_demo@latest
6 Before today, it was working fine, but after restarting the computer today, it suddenly started throwing an error.
# runtime/cgo
cgo: cannot parse $WORK\b228\_cgo_.o as ELF, Mach-O, PE or XCOFF
### How to reproduce
help help! my english is bad
### Screenshots
help me
### Example code
package main
import (
"fyne.io/fyne/v2/app"
"fyne.io/fyne/v2/widget"
)
func main() {
app := app.New() // 创建应用程序实例
window := app.NewWindow("Hello world") // 创建窗口,标题为"Hello Wolrd"
window.SetContent(widget.NewLabel("Hello world!")) // 往窗口中放入一个内容为"Hello world!"的标签控件
window.ShowAndRun() //展示并运行程序
}
### Fyne version
v2
### Go compiler version
1.22
### Operating system and version
windows10
### Additional Information
Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=D:/develop/software/mingw64/bin/../libexec/gcc/x86_64-w64-mingw32/8.1.0/lto-wrapper.exe
Target: x86_64-w64-mingw32
Configured with: ../../../src/gcc-8.1.0/configure --host=x86_64-w64-mingw32 --build=x86_64-w64-mingw32 --target=x86_64-w64-mingw32 --prefix=/mingw64 --with-sysroot=/c/mingw810/x86_64-810-posix-seh-rt_v6-rev0/mingw64 --enable-shared --enable-static --disable-multilib --enable-languages=c,c++,fortran,lto --enable-libstdcxx-time=yes --enable-threads=posix --enable-libgomp --enable-libatomic --enable-lto --enable-graphite --enable-checking=release --enable-fully-dynamic-string --enable-version-specific-runtime-libs --disable-libstdcxx-pch --disable-libstdcxx-debug --enable-bootstrap --disable-rpath --disable-win32-registry --disable-nls --disable-werror --disable-symvers --with-gnu-as --with-gnu-ld --with-arch=nocona --with-tune=core2 --with-libiconv --with-system-zlib --with-gmp=/c/mingw810/prerequisites/x86_64-w64-mingw32-static --with-mpfr=/c/mingw810/prerequisites/x86_64-w64-mingw32-static --with-mpc=/c/mingw810/prerequisites/x86_64-w64-mingw32-static --with-isl=/c/mingw810/prerequisites/x86_64-w64-mingw32-static --with-pkgversion='x86_64-posix-seh-rev0, Built by MinGW-W64 project' --with-bugurl=https://sourceforge.net/projects/mingw-w64 CFLAGS='-O2 -pipe -fno-ident -I/c/mingw810/x86_64-810-posix-seh-rt_v6-rev0/mingw64/opt/include -I/c/mingw810/prerequisites/x86_64-zlib-static/include -I/c/mingw810/prerequisites/x86_64-w64-mingw32-static/include' CXXFLAGS='-O2 -pipe -fno-ident -I/c/mingw810/x86_64-810-posix-seh-rt_v6-rev0/mingw64/opt/include -I/c/mingw810/prerequisites/x86_64-zlib-static/include -I/c/mingw810/prerequisites/x86_64-w64-mingw32-static/include' CPPFLAGS=' -I/c/mingw810/x86_64-810-posix-seh-rt_v6-rev0/mingw64/opt/include -I/c/mingw810/prerequisites/x86_64-zlib-static/include -I/c/mingw810/prerequisites/x86_64-w64-mingw32-static/include' LDFLAGS='-pipe -fno-ident -L/c/mingw810/x86_64-810-posix-seh-rt_v6-rev0/mingw64/opt/lib -L/c/mingw810/prerequisites/x86_64-zlib-static/lib -L/c/mingw810/prerequisites/x86_64-w64-mingw32-static/lib '
Thread model: posix
gcc version 8.1.0 (x86_64-posix-seh-rev0, Built by MinGW-W64 project)
Did you try cleaning your go cache with go clean -cache
? Your gcc version is very recent, so, wondering if that got updated recently and is causing problems.
spiritov
(spiritov)
October 9, 2025, 7:55pm
3
didn’t find this issue!, but i did go clean -cache
and go clean -modcache
to no avail..
however, i tracked it down to this issue since i was using my GCC version from w64devkit, which includes BigObj even though cgo doesn’t support it:
opened 03:24AM - 24 Sep 25 UTC
golang 1.20.14 + w64devkit-x64-2.4.0
```
$ export GOROOT=D:/develop/golang/go
$… export PATH=D:/develop/mingw64-w64devkit/bin:$GOROOT/bin:$PATH;
$ go build cgo.go
# command-line-arguments
cgo: cannot parse gcc output $WORK\b001\\_cgo_.o as ELF, Mach-O, PE, XCOFF object
```
cgo.go:
```
package main
/*
#include <stdio.h>
void say_hello() {
printf("Hello from C!\n");
}
*/
import "C"
import "fmt"
func main() {
fmt.Println("Going to call C code...")
C.say_hello()
fmt.Println("C code finished.")
}
```
using GCC from mingw-w64 MSYS2 resolved this for me, though there is an open proposal for cgo to support BigObj:
opened 11:40PM - 29 Sep 25 UTC
OS-Windows
Proposal
### Proposal Details
The debug/pe package currently uses this file struct:
```g… o
// A File represents an open PE file.
type File struct {
FileHeader
OptionalHeader any // of type *OptionalHeader32 or *OptionalHeader64
Sections []*Section
Symbols []*Symbol // COFF symbols with auxiliary symbol records removed
COFFSymbols []COFFSymbol // all COFF symbols (including auxiliary symbol records)
StringTable StringTable
closer io.Closer
}
```
Unfortunately, in order to support BigObj COFF, ([golang/go#24341](https://github.com/golang/go/issues/24341)), a few things need to change,.
BigObj files use a different type of header (`ANON_OBJECT_HEADER_BIGOBJ`) with largely the same fields as the FileHeader (`IMAGE_FILE_HEADER`) present already in the File struct.
You can find the C struct declarations in winnt.h.
The most important difference in the header is that `FileHeader.NumberOfSections` is now 32 bits, instead of 16 bits.
Supporting more sections in the file is the entire point of BigObj. I propose to add an extra:
`int32 SectionCount` field in the file struct to deal with this. In the case that the section count is greater than INT16_MAX, `File.FileHeader.NumberOfSections` will be zero. `File.SectionCount` will always contain an accurate number of sections.
`File.FileHeader.NumberOfSections` will be deprecated and new code should not rely on it, and instead refer to `File.SectionCount` to get the true number of sections.
The other fields in the header have 1:1 equivalents in the old FileHeader, so the code can just copy over the values from the BigObj header back to the FileHeader, and they can be accessed from that struct instead.
A similar approach has to be taken for `Symbols` and `COFFSymbols`.
Symbols inside regular COFF files are of the format `IMAGE_SYMBOL` (also present in winnt.h).
BigObj files instead have the format `IMAGE_SYMBOL_EX`. The only difference between them is that the `SectionNumber` field got expanded to 32 bits.
Unfortunately, the current `COFFSymbol` and `Symbol` structs have a 16 bit `SectionNumber`.
I propose adding two new fields:
```
BigObjSymbols []*BigObjSymbol
BigObjCOFFSymbols []BigObjCOFFSymbol
```
The only change in these structs will be a 32 bit SectionNumber.
Similar to the header, the old structs will be deprecated, and both of those arrays will be empty in the case that the section count is greater than INT16_MAX. New code should always prefer to use these fields.
For more details on BigObj, I wrote up a blog post explaining my findings when writing my initial patch:
https://peter0x44.github.io/posts/bigobj_format_explained/
Unfortunately, Microsoft doesn't document the binary format. And it seems no one else did either. So you just have to "Trust Me, Bro".
https://github.com/golang/go/pull/75631
My patch is functional. The issues are that it breaks the go compatibility guarantee.
I am happy to bikeshed over the naming of the structs in this API. I couldn't come up with any I fully liked.
1 Like
mje
(Jeff Emanuel)
October 10, 2025, 4:35pm
4
When I read the original post I was going to suggest this until saw that you already had found it. Years ago when I worked on some projects that needed cgo, I used mingw on windows.
1 Like