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

Callbacks for snowflake state #60

Open
cyBerta opened this issue Oct 2, 2024 · 6 comments
Open

Callbacks for snowflake state #60

cyBerta opened this issue Oct 2, 2024 · 6 comments
Assignees

Comments

@cyBerta
Copy link

cyBerta commented Oct 2, 2024

While integrating IPtProxy into onionmasq I was missing a way to receive a callback once snowflake is ready to go.
This would help us to avoid errors when starting onionmasq in the unmanaged PT mode while snowflake is actually not ready yet to be used.
As for RiseupVPN I've used a hacky workaround by parsing the logs written to the logfile while starting snowflake to get informed about state changes, but I would love to avoid to replicate that while integrating IPtProxy into TorVPN.

@n8fr8 mentioned that you already provide a patch for the snowflake proxy mode - and while I've read in another issue that you dislike maintaining patches - I wonder if there are good ways to get state feedback from IptProxy.

@tladesignz
Copy link
Owner

@cohosh, before I start digging into the code without a clue:

  • What's your opinion?
  • Is there already something which would be easy to expose in IPtProxy?
  • If not, would you be willing to provide such a mechanism?

@tladesignz tladesignz self-assigned this Oct 3, 2024
@cohosh
Copy link
Contributor

cohosh commented Oct 3, 2024

My understanding is that ready here means that the Snowflake client has started listening for incoming SOCKS connections on the supplied port.

There are a few options here. It is possible to add a simple callback to the patch. Alternatively, we do have some Snowflake event listeners that can be used for this purpose. Using the events library would require just a slight modification to your Snowflake client patch, and I could provide an example of what that would look like.

However, we're definitely getting to the point now where it would be easier to call the Snowflake client as a library rather than maintaining a patch. If you don't mind waiting a few days, I can give an example of what it would look like to remove the necessity of a patch for Snowflake (and Lyrebird). It would reduce the amount of code and I think it could be really nice to maintain.

@tladesignz
Copy link
Owner

Looking very much forward to the latter!

@n8fr8
Copy link
Contributor

n8fr8 commented Oct 15, 2024

We should make progress on this soon. If @cyBerta just needs a simple status callback, can we provide that?

@cohosh
Copy link
Contributor

cohosh commented Oct 15, 2024

Here is the rewrite I put together quickly last week that cleans up a bunch of the functionality and will make it easier to add a callback: https://github.com/cohosh/IPtProxy/tree/library-refactor
It's close to done, I just need to add back in proxy support and write some documentation. I'll open an MR for this by the end of the week with a full write up and explanation.

If you want a faster solution, you'll need to modify your patch files, because what you need a callback for is determining when you've started listening for incoming SOCKS connections which is already code in the patch. It can be quite simple to do this. This is what I'd recommend:

Add another input for the callback to the Start function:

+func Start(port *int, iceServersCommas, brokerURL, frontDomainsCommas, ampCacheURL, sqsQueueURL, sqsCredsStr, logFilename *string, logToStateDir, keepLocalAddresses, unsafeLogging *bool, max *int, onReady func()) {

And then call that function once you've called pt.ListenSocks:

@@ -270,11 +246,12 @@ func main() {
        switch methodName {
        case "snowflake":
            // TODO: Be able to recover when SOCKS dies.
-           ln, err := pt.ListenSocks("tcp", "127.0.0.1:0")
+           ln, err := pt.ListenSocks("tcp", net.JoinHostPort("127.0.0.1", strconv.Itoa(*port)))
            if err != nil {
                pt.CmethodError(methodName, err.Error())
                break
            }
+           onReady()

@cohosh
Copy link
Contributor

cohosh commented Oct 16, 2024

I just realized that the bindings for gomobile might not support callback functions. In that case, I don't know what the fastest way to support this currently is.

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

No branches or pull requests

4 participants