Edward Price | 22 Oct 18:51 2014
Picon

Interfaces and Type Assertions

I am trying to wrap my head around the costs of type assertions on interface. I did an anecdotal exploratory benchmark that let me wanting.

https://gist.github.com/pricees/1737068f957137eea354

Can someone provide me with an explanation (response, blog post, video) of what is happening under the hood when a type assertion is made?


Lets say I have a struct Foo
Foo implements 2 methods: hi, bye

I have 2 interfaces:
  ImplementsHi (method set is hi())
  ImplementsHiAndBye (method set is hi(), bye())

My assumptions:
- Asserting type from ImplementsHiAndBye to Foo would be least costly. 
- Asserting type from an empty interface to Foo would be most costly
- Asserting type from ImplementsHi to Foo would be in the middle.

Is this fair to assume?
Is there some reflection magic going on somewhere?


Best,
Ted

ChicaGopher (see what I did there?)

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
Dmitri Shuralyov | 22 Oct 07:51 2014
Picon

[ANN] gostatus - updated CLI in new version

Hi,

I've finally pulled the trigger and merged a PR that changes the command line interface of gostatus, a tool that tells you about any outstanding status of your Go package repos in your GOPATH.

Using it now should be more simple, because it's more like the go tool. Just like you can do `go list some/import/path`, you can now do:

gostatus some/import/path

Or more commonly run it on all of your Go packages:

gostatus all

It will tell you if:

-non-master branch is checked out
-there's a dirty working tree (i.e. git status is not empty)
-there's an updated version available (your revision doesn't match remote revision)
-you have a git stash

It works on git and mercurial repos (for other vcs you'll see "????" status).

If you're building some important package and want to find out the status of its dependencies, you can do:

# Show status of all dependencies (recursive) of package in cur working dir.
go list -f '{{join .Deps "\n"}}' . | gostatus --stdin -v

I modify many packages in place inside my Go workspace (either to add debug printfs, or to fix something and later make a PR, etc.), so I personally find it invaluable to find which packages have uncommitted changes and finalize or revert my changes, etc.

https://github.com/shurcooL/gostatus

If you find it useful, that's great.

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
Yongjian Lian | 22 Oct 05:58 2014
Picon

why sync.pool don't release the item that it holds the only reference unless the first poolCleanup() call

in go1.3.2 sync/pool.go

186 func poolCleanup() {
187     // This function is called with the world stopped, at the beginning of a garbage collection.
188     // It must not allocate and probably should not call any runtime functions.
189     // Defensively zero out everything, 2 reasons:
190     // 1. To prevent false retention of whole Pools.
191     // 2. If GC happens while a goroutine works with l.shared in Put/Get,
192     //    it will retain whole Pool. So next cycle memory consumption would be doubled.
193     for i, p := range allPools {
194         allPools[i] = nil
195         for i := 0; i < int(p.localSize); i++ {
196             l := indexLocal(p.local, i)
197             l.private = nil
198             for j := range l.shared {
199                 l.shared[j] = nil
200             }
201             l.shared = nil
202         }
203     }
204     allPools = []*Pool{}
205 }

here after the first poolCleanup() call, allPools is set to empty,and the pool is no longer put into allPools again?

162 func (p *Pool) pinSlow() *poolLocal {
163     // Retry under the mutex.
164     // Can not lock the mutex while pinned.
165     runtime_procUnpin()
166     allPoolsMu.Lock()
167     defer allPoolsMu.Unlock()
168     pid := runtime_procPin()
169     // poolCleanup won't be called while we are pinned.
170     s := p.localSize
171     l := p.local
172     if uintptr(pid) < s {
173         return indexLocal(l, pid)
174     }
175     if p.local == nil {
176         allPools = append(allPools, p)
177     }   
178     // If GOMAXPROCS changes between GCs, we re-allocate the array and lose the old one.
179     size := runtime.GOMAXPROCS(0)
180     local := make([]poolLocal, size)
181     atomic.StorePointer((*unsafe.Pointer)(&p.local), unsafe.Pointer(&local[0])) // store-release
182     atomic.StoreUintptr(&p.localSize, uintptr(size))                            // store-release
183     return &local[pid]
184 }         

here only p.local is nil will put p into allPools

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
Mateusz Czapliński | 22 Oct 02:31 2014
Picon

trying to use c2go, panic: unexpected C type TypeKind(100017)

I'm trying to use code.google.com/p/rsc/c2go on (preprocessed) Lua 5.1 codebase, and I'm getting a panic like below. Could anyone help to workaround/fix this, or at least debug somewhat more to learn why this happens? The TypeKind 100017 seems to be c2go.String, if I understand correctly. (Files in tmp2go directory are copied from rsc/c2go.)

panic: unexpected C type TypeKind(100017)

goroutine 1 [running]:
runtime.panic(0x57c280, 0xc0840b39c0)
        C:/Users/ADMINI~1/AppData/Local/Temp/2/bindist772277431/go/src/pkg/runtime/panic.c:266 +0xc8
main.toGoType(0x0, 0x0, 0x0, 0xc084169b40, 0xc0840357b0, ...)
        C:/prog/gopath/src/github.com/akavel/goluago/internal/tmp2go/main.go:391 +0x3f0
main.toGoType(0x0, 0x0, 0x0, 0xc0840d2870, 0xc0840357b0, ...)
        C:/prog/gopath/src/github.com/akavel/goluago/internal/tmp2go/main.go:469 +0x878
main.rewriteTypes(0x2652b0, 0xc08400f320)
        C:/prog/gopath/src/github.com/akavel/goluago/internal/tmp2go/main.go:266 +0xd67
main.main()
        C:/prog/gopath/src/github.com/akavel/goluago/internal/tmp2go/main.go:70 +0x6be

goroutine 3 [runnable]:
main.func┬Ě020()
        C:/prog/gopath/src/github.com/akavel/goluago/internal/tmp2go/syntax.go:421 +0x47
created by main.init┬Ě1
        C:/prog/gopath/src/github.com/akavel/goluago/internal/tmp2go/syntax.go:423 +0x24

goroutine 4 [runnable]:
runtime.gosched()
        C:/Users/ADMINI~1/AppData/Local/Temp/2/bindist772277431/go/src/pkg/runtime/proc.c:1370 +0x2a
runtime.gc(0x1)
        C:/Users/ADMINI~1/AppData/Local/Temp/2/bindist772277431/go/src/pkg/runtime/mgc0.c:2044 +0x2a3
runfinq()
        C:/Users/ADMINI~1/AppData/Local/Temp/2/bindist772277431/go/src/pkg/runtime/mgc0.c:2322 +0x1f5
runtime.goexit()
        C:/Users/ADMINI~1/AppData/Local/Temp/2/bindist772277431/go/src/pkg/runtime/proc.c:1396
exit status 2

The c2go code is slightly modified, to disable error on ((void) /*stuff*/) for now, but I think this wouldn't be related to the above?

diff -r c6452e6c462a cc/typecheck.go
--- a/cc/typecheck.go   Tue Jul 29 10:11:03 2014 -0400
+++ b/cc/typecheck.go   Wed Oct 22 02:26:38 2014 +0200
<at> <at> -822,6 +822,8 <at> <at>
                        x.XType = promote2(l, r)
                case l == r:
                        x.XType = l
+               //case l.Is(Func) && r.Is(Func) && isCompat(l, r):
+               //      x.XType = l
                case isCompatPtr(l, r):
                        x.XType = compositePtr(l, r)
                case isPtr(l) && isNull(x.List[1]):
<at> <at> -1082,10 +1084,10 <at> <at>
                if t == nil {
                        break
                }
-               if t.Kind == Void {
-                       lx.Errorf("cannot parenthesize void expression")
-                       break
-               }
+               //if t.Kind == Void {
+               //      lx.Errorf("cannot parenthesize void expression")
+               //      break
+               //}
                x.XType = t

        case PostDec, PostInc, PreDec, PreInc:

I'd be grateful for any help.
/Mateusz.

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
Brian Wolter | 22 Oct 02:24 2014
Picon

FD leak in http.Client

Hey all,

I've been seeing a FD leak issue in http.Client for a while now. I've read a lot of threads on this forum about issues that sound identical, all of which seem to have been resolved for the poster, but I'm still seeing the problem so I'm wondering if anybody else has had a similar problem and what they did about it.

Specifically, I'm running a service that executes a lot of HTTP requests (hundreds of thousands an hour). Slowly, over time, I can see that FDs build up until eventually I run out and have to restart the service. It doesn't seem to happen for every connection, but at the volume of requests I'm making it runs up pretty quickly.

Based on various things I've read, I'm doing the following things to try to guarantee these FDs get released, but to no avail:

- I am always calling rsp.Body.Close(),

- I am always consuming the response body, even if I don't do anything with it via: io.Copy(ioutil.Discard, rsp.Body)

- I have disabled keep-alive connections in http.Client (via the DisableKeepAlives property of Transport)

- I have disabled keep-alive connections in every individual request by setting req.Close = true,

- I am reusing the same http.Client instance for all these requests,

- I have even tried telling the underlying Transport to CloseIdleConnections after each request.

I've also noticed that the goroutines associated with those connections are also constantly increasing, blocked in an I/O wait state.

Is there something obvious I may be missing? I'm seeing this on go1.3.3 linux/amd64.

Thanks for any help,
Brian

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
MarkH | 21 Oct 23:56 2014
Picon

I've been reading about Windows and it's giving me a headache.

The more I read about the making of the many various kinds of "windows" the crazier the whole thing seems. It's like the wild mess Enron made before the whole thing blew up. It seems they started with one clean idea, message passing. But then, for some reason (maybe it didn't work well or maybe they wanted to do more), they added another layer of .dlls and tons of constants and distributed this far and wide with no recognizable scheme for making it all work together. Then, when that seems to have been unsuitable they added in the xml to simplify it. Mind you, this is just how it appears to me on first reading. Maybe it's just like a great murder mystery novel, where nobody knows what's going on and everybody done it.

Now I'm stuck, wondering if I should use windows at all. I'd like a mousey or touchscreen program for ease of use, but it seems ridiculously hard and maybe impossible to prove as correct. This isn't quite what I expected when I started this project.

Yes, I know somebody, maybe several somebodys, will tell me I'm an idiot and I need to read more, but frankly I'd rather not waste my time if I can make a better decision at this point: keep at it, use somebody else's library, write a nasty letter, etc.

Maybe this is why the Googlers aren't so hep on doing Windows stuff.

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
gerald.stanje | 21 Oct 23:17 2014
Picon

compiler in golang

Hello,

Can someone suggest a lexer and parser generator like yacc to write a compiler for a small domain specific language in golang?

Thank,
-Gerald

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
Christian Neumann | 21 Oct 22:27 2014
Picon

Expression evaluation for configuration files

Hi,

I need to evaluate logical expressions in my app's configuration
files. For example, I want to evaluate a filter like "Foo.FieldX < 20".

I could build a parser, but this is much work for this IMHO generic
problem. There exists a solution for the PHP web framework Symfony
called ExpressionLanguage, although I never used it. Is there a similar
project in the golang universe? Or other solutions to this problem?

A hacky workaround could be to exploit text/template for this task. I
thought about wrapping the expression in a template and executing it to
check for the result, e.g. "{{if <EXPRESSION>}}t{{else}}f{{end}}" =>
"t"/"f". But then I would have to use the template syntax, which is
rather awkward for logical expressions.

I also thought about creating a simple "ExpressionLanguage"-like
package using the golang yacc tool. But as I'm not that experience with
building parsers, I'm not sure if this is feasible (maybe yacc/lex are
not the best tools to use for this task?). Any suggestions are welcomed.

Regards,
Christian

--

-- 
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe@...
For more options, visit https://groups.google.com/d/optout.

Gabriel Aszalos | 21 Oct 18:18 2014
Picon

Weird characters when using mail.Address.String()

This happens on my work machine, but at home everything runs fine. Both machines run OS-X. Any ideas?

$ cat t.go
package main

import "fmt"
import "net/mail"

func main() {
ad := mail.Address{"A B", "a <at> b.com"}
fmt.Println(ad.String())
}
$ go run t.go
=?utf-8?q?A_B?= <a <at> b.com>
$

Those "=?utf-8?q" characters are odd. Not sure why they are there. Any help would be appreciated!

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
horrido.hobbies | 21 Oct 16:51 2014
Picon

The Case for Go Web Frameworks

The Case for Go Web Frameworks

It's been posted at Reddit, too.

This is sure to ignite a firestorm of controversy. Will the issue ever be settled??

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.
tiono.tan | 21 Oct 06:52 2014
Picon

How is the correct way to pass app config & db connection to package?

Hello, i am a totally newbie with Golang. I'm trying to design an application that will be seperated to several package. So far this is my test result of the code that run without error.

package main
import (    "database/sql"    "fmt"    _ "github.com/denisenkom/go-mssqldb"    "github.com/gorilla/mux"    "learn/pkg1"    "net/http")
type Context struct {
    Msg string    Db  *sql.DB}
func HomeHandler(w http.ResponseWriter, r *http.Request, ctx *Context) {
    fmt.Println(ctx.Msg)    ctx.Db.Ping()}
func main() {
    db, err := sql.Open("mssql", "server=192.168.4.16;user id=sa;password=dataon;port=1433;database=dbcoffeevalley")    if err != nil {        fmt.Printf("Open connection failed: %v", err)    }
       defer db.Close()
       r := mux.NewRouter()

       appContext := Context{Msg: "Home", Db: db}
    r.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {        HomeHandler(w, r, &appContext)    })
       pkg1Context := pkg1.Context{Msg: "pkg1", Db: db}    r.HandleFunc("/pkg1", func(w http.ResponseWriter, r *http.Request) {        pkg1.Test(w, r, &pkg1Context)    })
    http.Handle("/", r)
       err = http.ListenAndServe(":9090", nil)
    if err != nil {        fmt.Println("ListenAndServe: ", err)    }}

and this is the package pkg1 code

package pkg1
import (
    "database/sql"    "fmt"    "net/http")
type Context struct {
    Msg string    Db  *sql.DB}
func Test(w http.ResponseWriter, r *http.Request, ctx *Context) {
    fmt.Println(ctx.Msg)    ctx.Db.Ping()}

The reason i made the code like above is i'm trying to pass the DB reference to package.

My question is :
Is there a way that I don't need to define Context struct for every single package and declare the package Context in the main func?

Thanks for any help.

--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org.
For more options, visit https://groups.google.com/d/optout.

Gmane