<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: solanav</title>
    <description>The latest articles on DEV Community by solanav (@solanav).</description>
    <link>https://dev.to/solanav</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F118105%2F43b98bcd-d14c-4018-8637-b657c28573df.jpg</url>
      <title>DEV Community: solanav</title>
      <link>https://dev.to/solanav</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/solanav"/>
    <language>en</language>
    <item>
      <title>SECURE COMMS FOR P2P NETWORKS</title>
      <dc:creator>solanav</dc:creator>
      <pubDate>Thu, 25 Jul 2019 10:22:02 +0000</pubDate>
      <link>https://dev.to/solanav/secure-comms-for-p2p-networks-2l33</link>
      <guid>https://dev.to/solanav/secure-comms-for-p2p-networks-2l33</guid>
      <description>&lt;p&gt; Writing software and writing about writing software.&lt;/p&gt;

&lt;p&gt; For the remote administration program I'm working on right now, I have to learn about a lot of things: p2p networks and cryptography for communication, X11 and Wayland for interaction with the remote computer and Linux in general.&lt;/p&gt;

&lt;p&gt; Last post I rambled about my ideas on how to build Liu's p2p network. Now I want to talk a bit about the crypto I'm going to use to avoid being MITMed.&lt;/p&gt;

&lt;p&gt; My first idea was pretty simple. I would create an RSA keypair and keep the private key on the server and hardcode the public one on every client. RSA can only encrypt a bit less than the length of the key, so if my key was 2048 bits I would have a little less than 256 bytes for my packet. I decided that I would better use a 4096 bit key so that I had a bit more space to send data to the server. With the public key the clients have, they could send multiple packets encrypted and only the server would be able to decrypt them with the secret key.&lt;/p&gt;

&lt;p&gt; Even though this is possible and sounded ok for small messages, I decided I would need more space to send logs and other files. After reading more about RSA I also discovered it's a pretty bad idea to use raw RSA for encryption because reasons. So I decided to mix RSA (asymmetric encryption) with AES (symmetric encryption). My idea was to use it the following way:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The client has the public key and the server has the private one.&lt;/li&gt;
&lt;li&gt;The client generates an AES key and ecrypts some data.&lt;/li&gt;
&lt;li&gt;The client encrypts the AES key (192 or 256 bits only) with the public RSA key.&lt;/li&gt;
&lt;li&gt;The client sends the now encrypted AES key to the server.&lt;/li&gt;
&lt;li&gt;The client sends the now encrypted data to the server.&lt;/li&gt;
&lt;li&gt;The server decrypts the AES key with the private RSA key.&lt;/li&gt;
&lt;li&gt;The server now has the AES key, that lets us decrypt the data sent by the user.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt; This is much better than the first option, because we can now encrypt as much data as we want without worrying about splitting the files. We can also encrypt big files much faster because RSA is pretty slow. This technique is also what we use in Liu's encryption plugin to securely encrypt all files in a given computer. The plugin encrypts the files with AES and then sends the AES key encrypted with RSA to the server, removing then the AES from the client's computer. This way we can remotely defend our data in case of an attack.&lt;/p&gt;

&lt;p&gt; Even though the protocol seems good, it still lacks more security. The messages sent from the client to the server are encrypted but the ones the server sends to the client are only signed. When you sign a message, you don't encrypt it. You can verify the message was not tampered with in the middle of your connection but people can read whatever you send to clients. So for the protocol to take care of this I need the client to generate another RSA keypair. This time, the client will keep the private and send the public key to the server. This way, both sides of the connection can encrypt the messages with the other's public key and keep the connection secure.&lt;/p&gt;

&lt;p&gt; So we can now add as step zero, the exchange of keys, where the client sends the key to the server and the server saves it with some other info needed to connect with the client like the IP and the port where the client listens for instructions.&lt;/p&gt;

&lt;p&gt; I want to end the post by saying all this is a very bad idea, you should never roll your own protocol or your own crypto unless you really know what you are doing (and I do not). If you want to use UDP like me and need secure communication you should use DTLS. It's like SSL or TLS but instead of TCP it uses UDP.&lt;/p&gt;

</description>
      <category>malware</category>
      <category>p2p</category>
      <category>c</category>
      <category>cryptography</category>
    </item>
    <item>
      <title>P2P NETWORK SECURITY AND TRUST ISSUES</title>
      <dc:creator>solanav</dc:creator>
      <pubDate>Tue, 23 Jul 2019 09:18:11 +0000</pubDate>
      <link>https://dev.to/solanav/p2p-network-security-and-trust-issues-pkg</link>
      <guid>https://dev.to/solanav/p2p-network-security-and-trust-issues-pkg</guid>
      <description>&lt;p&gt; While writing a p2p communication protocol for my current project, I was faced with the problem of discovery of peers and their authenticity.&lt;/p&gt;

&lt;p&gt; The first security measure is to sign every client or peer that is deployed to the network. The server has a RSA keypair. It uses the private key to sign the IP of the client being installed. The public key of the server is also given to the client for verification of the server instructions.&lt;br&gt;
This seems like a good idea because it prevents a third party to infiltrate the network unless the server infects the attackers computer. We also make sure that the instructions from the server are from the server.&lt;/p&gt;

&lt;p&gt; To allow clients to replicate and install themselves on other computers, we need a way of asking the server for a certificate for a given IP. For this to work, the server has to verify that the client asking for a new certificate is already part of the network. This is problematic because if an attacker gets their computer infected, they now can create as many peers as they want.&lt;/p&gt;

&lt;p&gt; Instead of trying to keep attackers out of the network, I propose the idea of making every peer pay a price for getting into the network. The peers should start with an "untrusted" status and become "trusted" only after they give the server something we want. This could be a certain amount of time mining monero for example.&lt;br&gt;
With this system, the "untrusted" peers cannot get a very limited amount of information from other peers. They are able of relaying instructions to other peers. This way, you allow the attacker to get information only if they help the network function and they potentially make you some money.&lt;/p&gt;

&lt;p&gt; How do we know the state of a peer? This could be fixed in a centralized manner, just by asking the server about the peer. This is good if you want to verify peers by making them mine crypto. Peers could send their proof of work to the server, the server verifies that it is valid and lists the peer as trusted on a database.&lt;br&gt;
The decentralized solution is to let every peer decide if a new peer is or not trusted. This way, peers will only give information to already trusted peers. This would only work if some peers are trusted by default. As a solution to this, the only peers that start as untrusted would be the ones not directly created by the server. So if a peer installs the program on another computer, the new peers is not trusted by anyone. As an example, imagine you are a peer from the network. You have in your known peer list an untrusted one. After this untrusted peer has sent you 10 instructions from the server and you have verified they have not been modified, you can set the status of this peer to trusted.&lt;br&gt;
A hybrid model would first ask the server if the peer is trusted, and update the local database accordingly. When a peer changes the status of another peer to trusted, this would be communicated to the server and when the server receives enough of these, it would update the global status of the peer.&lt;br&gt;
So what is enough peers? We should set a minimum number of peers, but this absolute value is not good. We also need to check the number of peers that do not trust it. So we need to get the list of connected peers. This should be fairly easy using DHT and XOR to calculate the distance to peers. The hash of each peer would be the certificate given by the server. And so you would calculate how many of the neighbors of your peer trust it and judge it that way.&lt;/p&gt;

</description>
      <category>malware</category>
      <category>c</category>
      <category>p2p</category>
    </item>
  </channel>
</rss>
