Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

plugin: cyclic dependencies are allowed #41672

Open
FloThinksPi opened this issue Sep 28, 2020 · 4 comments
Open

plugin: cyclic dependencies are allowed #41672

FloThinksPi opened this issue Sep 28, 2020 · 4 comments

Comments

@FloThinksPi
Copy link

@FloThinksPi FloThinksPi commented Sep 28, 2020

What version of Go are you using (go version)?

$ go version
1.15.2 linux/amd64

Does this issue reproduce with the latest release?

yes

What operating system and processor architecture are you using (go env)?

go env Output
$ go env
GO111MODULE=""
GOARCH="amd64"
GOBIN=""
GOCACHE="/home/REDACTED/.cache/go-build"
GOENV="/home/REDACTED/.config/go/env"
GOEXE=""
GOFLAGS=""
GOHOSTARCH="amd64"
GOHOSTOS="linux"
GOINSECURE=""
GONOPROXY=""
GONOSUMDB=""
GOOS="linux"
GOPATH="/home/REDACTED/go"
GOPRIVATE=""
GOPROXY="direct"
GOROOT="/usr/lib/golang"
GOSUMDB="off"
GOTMPDIR=""
GOTOOLDIR="/usr/lib/golang/pkg/tool/linux_amd64"
GCCGO="gccgo"
AR="ar"
CC="gcc"
CXX="g++"
CGO_ENABLED="1"
GOMOD=""
CGO_CFLAGS="-g -O2"
CGO_CPPFLAGS=""
CGO_CXXFLAGS="-g -O2"
CGO_FFLAGS="-g -O2"
CGO_LDFLAGS="-g -O2"
PKG_CONFIG="pkg-config"
GOGCCFLAGS="-fPIC -m64 -pthread -fmessage-length=0 -fdebug-prefix-map=/tmp/go-build171908665=/tmp/go-build -gno-record-gcc-switches"

What did you do?

Normally golang prohibits cyclic imports on compile time.

                project/first
                 ^           \    
                /             \
               /               \ 
              /                \/
     project/third <--- project/second

However if one uses plugins(each package in an own plugin) and load all thre plugins dynamically in a program, it is allowed (plugin load does not fail). However the result (in the case of my implementation mistake where i noticed it) is an infinite loop as all involved functions call themselfs in a cycle.

What did you expect to see?

Out of uniformity i expected that cyclic imports are also not possible in plugins.
I expected the plugin load to fail on the last of the 3 plugins when the cycle "closes"

What did you see instead?

Cyclic imports are possible and result in e.g. infinite loops.

Is this a conscious design choice ? I did not find any documentation for this behaviour.
If necessary to understand it i could make a minimal code example.

@andybons andybons changed the title cyclic dependencies in plugins are allowed plugin: cyclic dependencies are allowed Sep 29, 2020
@andybons andybons added this to the Unplanned milestone Sep 29, 2020
@andybons
Copy link
Member

@andybons andybons commented Sep 29, 2020

@FloThinksPi
Copy link
Author

@FloThinksPi FloThinksPi commented Sep 29, 2020

Hm one may need to add here that i pass the function from plugin 1 via empty interfaces trough the main programm to plugin 2 which casts it to a struct specified in plugin 1 and vice versa. I think this is why cyclic imports happened and the compiler could not know since it only sees empty interfaces being passed around, although plugin 1 imports the struct of plugin 2 and vice versa.

@cherrymui
Copy link
Contributor

@cherrymui cherrymui commented Sep 29, 2020

Could you share a code example? I'm not sure how you can build something with import cycles into plugins.

@FloThinksPi
Copy link
Author

@FloThinksPi FloThinksPi commented Sep 30, 2020

@cherrymui i build this: https://github.com/FloThinksPi/go-plugin-cyclic-dependencie-test
While doing it i noticed the plugins three and four are not cyclic imports, they are more like this:

                plugin_example/main
                 ^           ^    
                /             \
               /               \ 
              \/               \/
     plugins/three      plugins/four
                  \       / 
                   \     /  
                    \   /   
                     \ /     
                      |      
                     / \     
                    /   \   
                   /     \  
                  \/     \/
plugins/threeInterface  plugins/fourInterface

Also i think as this is evaluated at runtime there is no option for the compiler or pluginloader to know it ?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked pull requests

Successfully merging a pull request may close this issue.

None yet
3 participants
You can’t perform that action at this time.