Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why this code generate very big executable in go (around 81M)?

Tags:

go

I'm new to golang. I wrote code like this:

package main

import (
    "fmt"
)

const (
    BIG_NUM = 10 * 1000 * 1000
)

type BigData [BIG_NUM]uint64

func (self BigData) String() string {
    return fmt.Sprintf("%d\n", self[0])
}

func (self *BigData) Clear() {
    *self = BigData{}
}

func main() {
    data := new(BigData)
    fmt.Println(data)
}

After compiling, the executable is around 81M:

$ ls -l
-rwxr-xr-x  1 tchen  522017917  81533376 Dec 19 08:44 test
-rw-r--r--  1 tchen  522017917       290 Dec 19 08:44 test.go

When I remove Clear() function, the executable goes to normal size. So why this Clear() function generate so big executable? It should be called at runtime, not compiling time, right?

------------ further investigation -----------

Enlightened by @FUZxxl, I modified the code to use a global variable in Clear(). This time the file size went back to normal. So global variables are putting to .bss section correctly.

package main

import (
    "fmt"
)

const (
    BIG_NUM = 10 * 1000 * 1000
)

type BigData [BIG_NUM]uint64

var (
    bigData = BigData{}
)

func (self BigData) String() string {
    return fmt.Sprintf("%d\n", self[0])
}

func (self *BigData) Clear() {
    *self = bigData
}

func main() {
    data := new(BigData)
    fmt.Println(data)
}

The compiled executable:

$ ls -l
-rwxr-xr-x  1 tchen  522017917  1534384 Dec 19 10:55 test
-rw-r--r--  1 tchen  522017917      318 Dec 19 10:55 test.go

------------ latest update -----------

So far it seems this is a compiler issue. A bug has been submitted: https://code.google.com/p/go/issues/detail?id=6993. You can follow up it if you're interested.

Before there's any solution to it, you should avoid using x := Y{} in your function. A workaround is (thanks to [email protected]):

func (self *BigData) Clear() {
-   *self = BigData{}
+   var zero BigData
+   *self = zero
} 
like image 538
Tyr Avatar asked Dec 19 '13 00:12

Tyr


1 Answers

Looks like BigData{} in the Clear() function is causing an array of 80,000,000 bytes = sizeof uint64 * 10 * 1000 * 1000 to be hardcoded into the binary.

like image 160
Andrey Mishchenko Avatar answered Oct 06 '22 08:10

Andrey Mishchenko