• Stars
    star
    134
  • Rank 270,967 (Top 6 %)
  • Language
    OCaml
  • License
    MIT License
  • Created over 2 years ago
  • Updated 3 months ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

A peer-to-peer file-transfer tool in OCaml

BยทoยทB

A peer-to-peer file-transfer in OCaml


Bob is a simple, secure and universal program for transmitting a file or a folder from one person to another. The aim of bob is to offer the possibility to share documents without any constraints:

  • security
  • accesibility: we mainly want to provide one binary which works anywhere
  • usage

The software is available here: bob.com (x86_64). You can use it directly without any installation! You can check how we built bob.com via our website: builds.osau.re

For this purpose, bob uses state-of-the-art security, Cosmopolitan to ensure its accessibility on all systems and a simplicity that only meets the objective of transmitting a document.

A simple example

On Windows,

This is a simple animation of how to use bob.com on Windows:

How to send a file:
send

How to receive a file (with the same password):
receive

On other platforms,

You can compile & install bob with opam:

$ opam pin add -y https://github.com/dinosaure/bob

Bob has 3 sub-programs, the receiver, the sender and the relay. We will concentrate on the first two:

  • bob recv requires a password (decided between you and the sender). Take for example: revolucion-para-siempre. This program has several options like accepting any sender (sharing the same password) automatically or the address of the relay. An example of its use is:
$ bob recv revolucion-para-siempre -r $(dig +short osau.re) -y
>>> Received a file: my_huge_file.txt.
>>> โ ผ   13.5 MiB    2.2 MiB/s
  • bob send requires a document (a file or a folder) and let you to specify few options: compression, password, relay address.
$ bob send --password revolucion-para-siempre -r $(dig +short osau.re) \
    --no-compression my_huge_file.txt
>>> [โ”‚โ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ–ˆโ”‚]   13.5 MiB  / 13.54 MiB

As you can see, some information is displayed and the download can begin. You can let bob decide on the password if you want with regard to the sender:

$ bob send -r $(dig +short osau.re) my_huge_file.txt
Password: wei-widwagamboostu
>>> [โ”‚                            โ”‚]    0.0 B    / 13.54 MiB

And, by default, we always ask for confirmation from the recipients as to what he/she is receiving:

$ bob recv -r $(dig +short osau.re) wei-widwagamboostu
Accept from 213.245.183.59:55291 [Y/n]:

Design, Protocol and Implementation

If you are interested in the implementation of bob, the protocol itself or the design of the program in general, there are some notes on this in the distribution. For future contributions, it is advisable to read these documents.

Avantage of bob

The relay implementation

One of the advantage of bob is the implementation of its relay, which simply transfers information from one peer to another without altering the content. The investigators of the agreement are only the peers and the relay does not intervene in any way in this agreement. The sole role of the relay is to transfer information from one peer to another. When two peers reach an agreement, they notif the relay so that it can allocate a secure channel between the two peers.

The relay is therefore blind to the algorithm used to reach an agreement. This feature ensures that there is no compromise between peers via the relay.

The protocol itself does not allow the relay to obtain enough information to decrypt your communications. Indeed, the initial exchange (the handshake) between the peers is an exchange that could be done without a relay. The purpose of the relay is:

  • to provide a stable connection
  • allow two peers to communicate with each other when they cannot directly (certainly because of a proxy)

The only packet that the relay introspects is that of the receiver's refusal or acceptance in order to allocate a secure communication channel for the two peers.

OCaml & GADTs

The state machine defined to ensure the exchange uses an feature of the OCaml language: GADTs. From this we can encode at type level that a client cannot talk to another client and a server cannot talk to another server. In this way, we can prune problematic cases as errors upstream, outside the implementation of the so-called state machine.

Indeed, the implementation of the state machine utimately focuses only on valid cases - namely, a receiver wanting to communicate with a sender and vice-versa. This property (the duality between receiver and sender) can be encoded with types and GADTs.

type send = | and recv = | and relay = |

type ('a, 'b) peer =
  | Send : (send, recv) peer
  | Recv : (recv, send) peer

type ('from, 'to) src =
  | Relay : (relay, 'to) src
  | Peer  : ('from, 'non_from) peer -> ('from, 'non_from) src

type ('from, 'to) dst =
  | Relay : ('from, relay) dst
  | Peer  : ('to, 'non_to) peer -> ('non_to, 'to) dst

type ('from, 'to) packet =
  | Hello_as_a_client : (recv, relay) packet
  | Hello_as_a_server : (send, relay) packet
  | Client_validator  : (recv,  send) packet
  | Server_validator  : (send,  recv) packet

This does not mean that we cannot receive a packet from a sender to a sender, but we can (and should) elimimate such cases upstream of the state machine. Another property is that we cannot, in OCaml and in this state machine, explicitely send a packet to a sender if we are recognised as a sender.

Unikernels and MirageOS

Bob provides 2 implementations of the relay which are very similar. One is a part of the executable and the user can launch its own relay via bob relay and an other implementation exists as an unikernel (see [mirage/][./mirage]).

The last one lets the user compile a full operating system as a relay and virtualize it with KVM for instance. You must have a machine with KVM. You must install the mirage tool and install bob first. Then, you should be able to craft the operating system with:

$ opam install mirage
$ git clone https://github.com/dinosaure/bob
$ mkdir bob-unikernel
$ cp bob/mirage/* bob-unikernel/
$ cd bob-unikernel/
$ mirage configure -t hvt
$ make depends
$ mirage build
$ ls dist/bob.hvt
dist/bob.hvt

An image bob.hvt is crafted and it can be launched with Solo5 and albatross. Albatross is available via apt if you want:

$ wget -q -O - https://apt.robur.coop/gpg.pub | apt-key add -
$ echo "deb https://apt.robur.coop ubuntu-20.04 main" >> /etc/apt/sources.list
$ sudo apt update
$ sudo apt install solo5 albatross
Networks and unikernels

For OS virtualization, you usually requires a bridge:

$ cat >>/etc/network/interfaces <<EOF

auto service
iface service inet static
  address 10.0.0.1
  netmask 255.255.255.0
  broadcast 10.0.0.255
  bridge_ports none
  bridge_stp off
  bridge_fd 0
  bridge_maxwait 0
EOF
$ systemctl restart networking

Finally, you need to let the unikernel to communicate with Internet and let people to communicate with your unikernel:

$ cat "1" > /proc/sys/net/ipv4/ip_forward
$ iptables -A FORWARD -o service -m conntrack --ctstate RELATED,ESTABLISHED \
    -j ACCEPT
$ iptables -A FORWARD -i service ! -o service -j ACCEPT
$ iptables -A FORWARD -i service -o service -j ACCEPT
$ iptables -t nat -A POSTROUTING -s 10.0.0.0/24 ! -o service \
    -j MASQUERADE
$ iptables -N BOB
$ iptables -A BOB -d 10.0.0.2/32 ! -i service -o service \
    -p tcp -m tcp --dport 9000 -j ACCEPT
$ iptables -A BOB -d 10.0.0.2/32 ! -i service -o service \
    -p tcp -m tcp --dport 9001 -j ACCEPT
$ iptables -A FORWARD -o service -j BOB
$ iptables -t nat -N BOB
$ iptables -t nat -A PREROUTING -m addrtype --dst-type LOCAL -j BOB
$ iptables -t nat -A BOB ! -s 10.0.0.2/32 \
    -p tcp -m tcp --dport 9000 -j DNAT --to-destination 10.0.0.2:9000
$ iptables -t nat -A BOB ! -s 10.0.0.2/32 \
    -p tcp -m tcp --dport 9001 -j DNAT --to-destination 10.0.0.2:9000
Launch the unikernel

You can launch the unikernel with albatross with:

$ albatross-client-local create --net=service \
    --arg="--ipv4=10.0.0.2/24"
    --arg="--ipv4-gateway=10.0.0.1" bob bob.hvt

Locally, you are able to communicate with your relay via the -r option:

$ bob send -r <my-public-ip>:9000
Password: shoacquis-feursonsindlebu

$ bob -r <my-public-ip>:9000 shoacquis-feursonsindlebu
Accept from <server-identity> [Y/n]: Y
Handshake is done with <server-identity>

Reproducible builds

The version you can download of bob.com was produced in such a context that you can reproduce the same binary in the same context. This is called software reproducibility. We provide an infrastructure (developed by robur.coop) builds.osau.re that checks the reproducibility of the software every day.

Esperanto, Cosmopolitan and Windows support

Currently, the bob executable can be compiled with the esperanto toolchain. By this way, we are able to deliver a bob.com which works anywhere. The status of it is experimental. However, few tweak on some libraries (specially mirage-crypto) are needed to be able to compile bob with this toolchain.

The final executable, the bob.com seems to work on PowerShell (Windows) and obviously Linux.

A CI exists which try to compile bob with Esperanto and Cosmopolitan. The builded artifact is available into the GitHub action which built the executable. Any users can download this artifact (see Actions and the last green GitHub Action, you will find a bob.com artifact) and execute it on their computer - there should be no prerequisites.

More Repositories

1

esperanto

build-once run-anywhere OCaml programs
C
134
star
2

pasteur

Paste-eur as unikernel
OCaml
65
star
3

gilbraltar

MirageOS on RPi4
C
58
star
4

art

Adaptive Radix Tree in OCaml
OCaml
48
star
5

paf-le-chien

Port of HTTP/AF & H2 with Mirage and mimic
OCaml
31
star
6

hxd

J'ai plus mal ร  la tรชte maintenant
OCaml
27
star
7

docteur

An opiniated file-system for MirageOS
OCaml
26
star
8

multipart_form

According an other RFC2388...
OCaml
25
star
9

cri

IRC protocol in OCaml
OCaml
25
star
10

carton

Implementation of the PACK file (Git) in OCaml
OCaml
21
star
11

mimic

A dynamic way to instantiate an OCaml flow
OCaml
18
star
12

tuyau

Should be the next conduit ... or not
OCaml
17
star
13

spoke

SPAKE2+EE implementation in OCaml
C
16
star
14

facteur

Send a mail in OCaml
OCaml
15
star
15

blaze

OCaml
15
star
16

dsh

A functionnal programming language
OCaml
15
star
17

contruno

A TLS termination proxy as a MirageOS
OCaml
13
star
18

minifiber

Parallel computation in OCaml - multicore for really poor people
OCaml
12
star
19

dinoscheme

Un langage de programmation inspirรฉ de Scheme et d'OCaml (Compilateur + Machine Virtuelle)
OCaml
11
star
20

sirodepac

Pack file encoder/decoder in OCaml
OCaml
11
star
21

tarides-workshop

C
8
star
22

demilekarantuite

2048 in OCaml
OCaml
8
star
23

z

DON'T USE IT
C
7
star
24

buffet

OCaml
7
star
25

sage

Sage and Agnostic I/O
OCaml
7
star
26

usine

Benchmarking tool for OcsigenServer and other in OCaml
OCaml
6
star
27

radis

ยซ Un รฉnorme radis. ยป
OCaml
6
star
28

ocaml-maildir

OCaml
6
star
29

ocaml-dmarc

OCaml
5
star
30

blogger

OCaml
5
star
31

rainbow

Red-black tree implementation in C with OCaml
OCaml
5
star
32

overlap

Bigarray.overlap as a library
OCaml
5
star
33

prettym

A simple bounded encoder constraints by columns in OCaml
OCaml
5
star
34

unstrctrd

OCaml
4
star
35

deadaf

Shell
4
star
36

caravan

Fixup BSS and inject new section into ELF binary
OCaml
4
star
37

ehouais

EWAH in OCaml (PoC)
HTML
3
star
38

gas-eqaf

Abstract interpretation of GAS assembler for eqaf project
OCaml
3
star
39

rev-list

git rev-list in OCaml
OCaml
3
star
40

mirage-os-shinimy

OCaml
2
star
41

dcpr-inv

Inverted stubs of decompress (OCaml to C)
Makefile
2
star
42

uuuui

Universal Unifier to Unicode Un OCaml (Importation tool)
OCaml
2
star
43

ada-language-19-05-2023

OCaml
2
star
44

not-so-smart

Implementation of the Git protocol
OCaml
2
star
45

conduit-dev

2
star
46

chamonix

Chamo, Chamoni, Chamonix
OCaml
1
star
47

ogaml

Jeu vidรฉo en OCaml et ocamlsdl
OCaml
1
star
48

lavoisier

lol, you should be lost ...
OCaml
1
star
49

mirage-dune

The smallest opam repository to have MirageOS with dune
Shell
1
star
50

short-hash

HTML
1
star
51

mirage.irc.libera.chat

logs on #[email protected]
1
star
52

-

Coq in my dream
Coq
1
star
53

din.osau.re

Site dรฉveloppรฉ avec les technologies Ruby
Ruby
1
star
54

blog.osau.re

Le blog d'un Dinosaure
CSS
1
star
55

tuyau-example

A simple example to download an HTML page and be free to use TLS or not when it's available.
OCaml
1
star
56

mirage-entropy-nocrypto

Functorized entropy engine for ocaml-nocrypto
OCaml
1
star
57

blog.x25519.net

HTML
1
star
58

ULC

Untyped Lambda-Calculus in OCaml
OCaml
1
star
59

mirage-nolink

Which library I need to compile my unikernel? Where is nocrypto's Native module?
OCaml
1
star