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

Do Not Merge: review and discuss adding tor onion transport #79

Closed
wants to merge 2 commits into from

Conversation

david415
Copy link

The user needs to be able to specify the tor connection information; either an IP addr and TCP port or a UNIX domain socket. Here in this proof of concept I've hardcoded the tor control port addr/port. Terrabad. Let's fix it... I haven't looked at how yet. I just now wrote the onion transport. It has some problems which I hope to discuss in another code review.

@Kubuxu
Copy link
Member

Kubuxu commented Jul 31, 2016

In my opinion we shouldn't add Tor transport without hardening ipfs against leaking information. So even if it will be added to libp2p (which is very useful) it should be disabled by default.

Also added dependencies aren't pinned in gx.

@david415
Copy link
Author

Yes we should modify it's high level design as well as the lower transport layer that I am working on now. I've also been working on the Tor integration for Tahoe-LAFS, a distributed ciphertext file storage system. Our trac ticket for Tor integration has been open for a long while but now finally there's progress and I hope it will be completed soon: https://tahoe-lafs.org/trac/tahoe-lafs/ticket/517

Should we pin the dependencies in gx?

@Kubuxu can you please discuss the high level changes that need to happen for this Tor integration? Can we open a trac ticket for it? Which software components shall I look at next?

@jbenet
Copy link
Contributor

jbenet commented Jul 31, 2016

On specifying the tor conn info--

The user needs to be able to specify the tor connection information; either an IP addr and TCP port or a UNIX domain socket.

Could this be a good job for multiaddr? i know it's not typical to express it so, but it may keep other interfaces more consistent. If it's just this -- a network endpoint -- then i think mutliaddr will be best.

In IPFS: the config could be expanded to support an entry for tor (and other) endpoints.

But it may be ideal to find a way to store, load, and feed this type of configuration info to libp2p transports the same way. (reminds me of XTP, where i plan to use a multiaddr as the internal xtp-ctl endpoint).

This is also similar to how WebRTC introducer addresses may be represented. Basically, we have a situation like:

  • connect to a network endpoint A (using a multiaddr)
  • and get another network endpoint B (multiaddr)
  • send B to others as your own address
  • (in some cases, like tor and i2p, A must be private, internal only. in others, like webrtc, it can be public)

@david415
Copy link
Author

@jbenet yes i agree that the tor control port information should be expressed in the onion multiaddr... and i also think that we need the onion multiaddr to optionally specify a file containing the onion service private key. i've also expressed this in a code comment recently... our current onion multiaddr and the tor onion service api are somewhat mismatched... but we can fix that. i've mentioned it here:

https://github.com/david415/ipfs-onion-transport/blob/master/onion_transport.go#L93-L103

@jbenet
Copy link
Contributor

jbenet commented Jul 31, 2016

On making IPFS not leak information:

I don't think there's a specific github issue (beyond those you've seen already) where all of this is itemized. We wanted to work on this last week but didn't get to it. Maybe we can start a list in a note somewhere...

Off the top of my head, the most important things to do:

  • Transports: Currently, go-ipfs uses the config for listener side of the transports. We must make sure there is an equivalent config for all dialers (i.e. allowed transports list).
    • Ensure having tor as the only transport works - only listener and only dialer.
      • This should make go-ipfs not even use all other network addresses. IPFS should then not know of no other addresses of the local host. this needs to be verified and tested)
  • Peer Discovery: mechanisms must also be configurable
    • mDNS is already configurable. this must always be off in private contexts
    • DHT discovery is fine for privacy. but should also be configurable via config. (hardcoded constants now)

It looks like this is all libp2p related. Likely we can set the example for many other systems built on top of libp2p. So perhaps we can make all this configuration live in its own section in the ipfs config. (some example at the end)

I do not believe ipfs captures host-identifying information itself (beyond what libp2p does), but i could be wrong. this needs to be checked. IPFS specifically, we could roll a new ipfs key per run (ephemeral node) or keep the same. there's uses for both.

I would like the above to translate both into:

  • a config that disables these and puts any go-ipfs daemon into privacy mode (easy, mostly for our own testing)
  • a build that hard-disables (maybe even removes the code?) these (for releases)

example libp2p transport config

this is a super rough idea. could prob compress a lot of this, or use a more meaningful representation.

{ // ipfs config
  "libp2p": { // libp2p config. common standard?
    "swarm": {
      "interfaces": [
        {
          "transport": "tcp", 
          "endpoint": "/ip4/0.0.0.0/tcp/0",
          "options": ["listen", "dial", "reuseport"],
        },
        {
          "transport": "tcp", 
          "endpoint": "/ip6/::/tcp/0",
          "options": ["listen", "dial", "reuseport"],
        },
        {
          "transport": "utp", 
          "endpoint": "/ip4/0.0.0.0/udp/0/utp",
          "options": ["listen", "dial", "reuseport"],
        },
        {
          "transport": "utp", 
          "endpoint": "/ip6/::/udp/0/utp",
          "options": ["listen", "dial", "reuseport"],
        },
        {
          "transport": "tor",
          "endpoint": "/onion/fkbjngvraoici6k7",
          "options": ["listen", "dial", "reuseport"],
          "torctl": "/ip4/127.0.0.1/tcp/1873", // tor conn info endpoint
        },
        {
          "transport": "quic",
          "endpoint": "/ip4/0.0.0.0/udp/0/quic",
          "options": ["listen", "dial", "reuseport", "xtp"],
          "xtpctl": "/unix/var/xtpctl/131/quic", // xtpctl endpoint. unix domain socket
        }
      ]
    }
  }
}

// XXX FIXME: The tor control net and addr should be user specified!
// Note: for sandboxing purposes UNIX domain sockets are preferred instead of TCP.
controlNet := "tcp"
controlAddr := "127.0.0.1:9051"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should this info be embedded into the multiaddr? If its an onion protocol running over tcp i'd expect to see something like /ip4/127.0.0.1/tcp/9051/onion/abcdefsasdasdasd

@david415
Copy link
Author

david415 commented Aug 3, 2016

The Dialer only needs a Tor SOCKS port and the connecting information (onion address + port number). The Listener needs a Tor control port and a 1024 bit RSA key. The Tor SOCKS port can be gathered from the control port. Therefore we could compose onion multiaddrs containing:

  • onion address
  • onion port
  • tor control port
  • onion private key file path

then this onion multiaddr could be used by a client or by a server.

Can we actually encode the onion key file path inside the multiaddr? Paths have slashes... and multiaddr uses slashes as a delimiter.

@whyrusleeping whyrusleeping added the status/deferred Conscious decision to pause or backlog label Sep 14, 2016
@bigs bigs added need/community-input Needs input from the wider community feature labels Sep 18, 2018
@bigs
Copy link
Contributor

bigs commented Sep 18, 2018

i know this is an old issue, but it's something that does keep coming up. imo, this is blocked on a rudimentary audit of the information libp2p hosts expose to one another when connecting/handshaking/opening streams. maybe we could create a specific issue/rfp for that?

@Stebalien Stebalien removed the feature label Mar 27, 2021
@Type-IIx
Copy link

Type-IIx commented Jun 7, 2021

In my opinion we shouldn't add Tor transport without hardening ipfs against leaking information. So even if it will be added to libp2p (which is very useful) it should be disabled by default.

Also added dependencies aren't pinned in gx.

I would suggest someone working on this transport team coordinate with a project like Whonix that is primarily concerned with protecting against the myriad potential leaks to determine scope and scale at the transport level. But please do not lose sight of the importance of location-hidden transport for IPFS (do not let perfect be the enemy of good!). Also, system tor support (vs. embedded instances is important). I saw a relatively old message on the go-onion-transport git from a core IPFS dev frame the argument against Tor as essentially: there are better (theoretical) models (untested in the wild) and we cant guarantee its perfection, so "eh." Don't leave onion transport to something like OpenB-zaar, IPFS has real legitimate use cases for location-hidden users around the world!

@Type-IIx
Copy link

Type-IIx commented Jun 7, 2021

The Dialer only needs a Tor SOCKS port and the connecting information (onion address + port number). The Listener needs a Tor control port and a 1024 bit RSA key. The Tor SOCKS port can be gathered from the control port. Therefore we could compose onion multiaddrs containing:

* onion address

* onion port

* tor control port

* onion private key file path

then this onion multiaddr could be used by a client or by a server.

Can we actually encode the onion key file path inside the multiaddr? Paths have slashes... and multiaddr uses slashes as a delimiter.

Hm, OK, this is very old. Perhaps I am bumping a dead issue entirely. Tor is deprecating v2 and (multiaddr) is now on onion3 along with crypto updates and such.

@Stebalien
Copy link
Member

Yeah. There's little reason to keep this PR open.

@Stebalien Stebalien closed this Jun 28, 2021
marten-seemann pushed a commit that referenced this pull request Jul 1, 2022
expose CanHop as a module function
marten-seemann pushed a commit that referenced this pull request Aug 9, 2022
marten-seemann pushed a commit that referenced this pull request Aug 15, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
need/community-input Needs input from the wider community status/deferred Conscious decision to pause or backlog
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

8 participants