Morphis is a Distributed Hash Table (similar to Bittorrent) over a custom SSH protocol that allows users to upload files to and download files from the network. It is a very fast, encrypted, uncensorable and decentralized datastore that is resistant to Sybil attacks. It uses Kademlia's routing algorithm (the XOR metric etc.) - the specification is much more useful than the previous link - but not it's network algorithm.
Every node on the network generates an RSA-4096 private/public keypair on creation, and the public key is hashed with SHA-512 to give the node's ID. Each node devotes some storage space to the network - 1gb by default, this can be changed by running morphis with
python3 node.py --dssize X, where X is in megabytes.
The URL used to download files/pages is the static or updateable key created when uploading it. So, with http://localhost:4251/sp1nara3xhndtgswh7fznt414we4mi3y, sp1nara.. is the key. A static key is the root hash of the Merkle tree of all the (unencrypted) blocks that make up the file (explained below) - if the file changes, so does the key.
An updateable key is the public half of a private/public key pair generated on the fly for each upload (different from the node's RSA keypair) - the key doesn't depend on the data being uploaded, which means the data can be updated after being uploaded and still be accessed at the same address.
In either case, the whole file is broken into 32 kilobyte blocks if it's bigger than 32k. The hash of the hash of each block is the block ID. The blocks are stored on nodes that have node IDs closest to the block ID. Because any hash is unpredictable, blocks are stored randomly across the network. They are also stored on a minimum of 3 different nodes across the network (the uploading node doesn't count itself as one of the 3).
The encryption key for each block is just the hash of the block. The block is encrypted (again with AES-256), and the key thrown away. It is assumed that anything uploaded is unencrypted, because there is no way to conclusively prove that data has been encrypted. If nodes thought all uploads were already encrypted, unencrypted data could be passed to the network, which would be forced to store it. This unencrypted data could be illegal to possess. The only way to be sure that this can't happen is for storing nodes to assume it's all unecrypted, and encrypt the blocks themselves.
The static/updateable key is hashed, like the individual blocks, to give the file ID. This ID is searched for, the blocks relating to it are found, downloaded and decrypted, and the file is reassembled. Morphis itself actually only handles and stores the 32k blocks, the rest is done by a different file, multipart.py
Morphis has a feature called prefix key search. This means that, unlike the regular internet, you don't need to type a page or file's full address to access it, just a few characters (7 minimum). For the page above, http://localhost:4251/sp1nara is enough to access the page. The network will find the full key just as fast as if you'd typed the full thing in.
A seeding feature will soon be made, where your node will check the availablility of blocks it stores over time and ensure that they remain on the network. This feature will also allow you to essentially 'like' any link, file or webpage and then your node will contribute to storing that file, as well as maintain it's existence on the network.
Morphis not being completely a carbon copy of Kademlia, but only based off of it is important; if you read the specification there (it's not long), you will see this in a note under STORE:
As the transport may be UDP, the message needs to also contain at least the nodeID of the sender, and the reply [needs] the nodeID of the recipient.Obviously, this is a massive anonymity failure, and it's what allows and requires the list of seeders and leechers to be visible for any given Bittorrent file. Morphis does this a bit differently, similar to how Tor works; If you read how Tor works, you'll see the way they route messages from Alice to Bob is by Alice picking the route through the network to Bob, and encrypting the route so that every intermediate node only knows who the next receipient is. Because Morphis is based off Kademlia, where every block is stored relates to the block itself, nodes don't need to route their request through the network; it's done automatically by the intermediate nodes. A route will look like
requester -> node 1 -> node 2 -> storing node.
storing node -> node 2 -> node 1 -> requester- they find this out by comparing the request IDs. In this way, no node needs to know who made the original request. Not even the first node that receives the request can know or figure out that they received it from the requester; it looks identical either way. You could say that it's onion routing without the onions.
Dmail is Morphis' built-in email system, and is inherently spam proof, encrypted (with AES-256 at present) and pseudonymous, with authenticated senders.
Dmail is a bit like Bitcoin in that it also uses proof of work, although a sligtly different kind:
Morphis provides a few different interfaces:
ssh 127.0.0.1 -p 4250.
ssh 127.0.0.1:4250won't work, so don't try it.
Currently you can only do this with updateable keys. To remove a file from the network, just go to the appropriate upload page, don't select a file, path or mime-type, and press "Upload". Your client will then upload the empty byte string to network, and any nodes that store the previous version will overwrite it with the now-empty new version. You might have to do this multiple times, because offline nodes obviously won't see your update.
As of today, the oldest data stored by a node will be deleted once their storage space becomes full. Once this happens, nodes only accept new keys that are closer to itself, and throw out keys that are further away, increasing the accuracy of the network. In the future, once that distance becomes small enough ("enough" is based on the size of the network) they will overwrite data according to when it was last requested, how much it was requested, etc. The above seeding feature will ensure that certain data will never drop off the network even if it is rarely requested, as long as someone is seeding it; only the redundancy would decrease (possibly only the seeding node would store it) until it gets requested/popular again.
Morphis, like Kademlia, lets you control the routing table expansion. The routing table gets bigger with log(base (2^b)), and 3 to 5 are reasonable values for b. This enables O( log(base (2^b)) ) efficiency, so with the lower value of 3 for b, the scaling is log(base 8). That means, with 1000 nodes, the load would be 3.3, but only 10.9 with 7 billion nodes, one for each person.
By the time there are 7 billion nodes, the amount of memory and processing speed will have increased, so b can be raised to 5, giving a load of 6.54 with 7 billion nodes.
Morphis is not yet invulnerable to Sybil attacks, just resistant to them. Node IDs aren't RSA public keys, but the SHA-512 hash of the public key, which makes it much harder to forge a specific node ID. Morphis also tunnels stable connections with tit-for-tat fairness: a node uploads data to a small set of neighbouring peers which are providing it with the best download rates, discouraging freeriding (downloading without uploading) and promoting fairness (the ratio of the amount downloaded by a node to what it uploads).
Nodes, as normal behaviour, relay upload and download requests from other, close, nodes, as well as generating their own requests. The closeness of a node is determined by xor-ing their own node ID with the other node's ID. To prove whether a node is generating a request themself, or just relaying it, a malicious attacker must then create many nodes with IDs that are close to that of the target. This allows them to see if requests from the node were relayed to it, as they would likely be the one who would relay it to them.
As was said above, it is hard to forge specific node IDs - there are 2^512 different IDs. This greatly reduces the chances of nodes being deanonymised, and is why Morphis can be described as pseudonymous. Similar to the regular Internet, anonymity can be built on top of Morphis, like Tor and Freenet provide.
Using the horrific analogy from earlier at the end of the 1st question, one of the only ways you would know if I was the one who asked the original would be to surround me with loads of your friends so you would know if someone else had asked me the question first and I was just relaying it to you. The other way would be to follow the chain of communication and see that it stops with me - i.e. I don't relay the question or the answer to someone else.
You can access Morphis and the files on the network through localhost:port (the default is 4251, and set in maalstroom_server.py). The Maalstroom plugin converts localhost:port into http://localhost:4251/, so download that. It's only for Firefox at the moment though.
If you want to change the port SSH listens on, meanwhile, run morphis with
python3 node.py --bind *:4250, and change the 4250 to any number beside 4251.
# Prevent Internet sites from requesting LAN resources.
Accept from LOCAL
Accept from http://localhost:4251/