Comments (17)
It can be faster. Try a/b testing yourself to see if it does - you can setup a croc relay with one port and then one with more than one port. I did testing back in 2019-2020 and it was faster with four ports for windows/linux machines on networks I needed to use it.
from croc.
Hmm but that makes no sense... it should be the same speed...
Are you sure there is no other reason for the non-multiplex way to be slower?
Using 4 sockets does not mean that you send 4 packets at once... the packets are still sent on a serial manner...
-
Maybe you didn't use async on the single thread version? And then the multithreaded version had more chances of read while on the single thread version some sockets blocked and others didn't?
-
Maybe there is an overhead after each read that causes the reads to be less frequent? And then you need to apply a two threaded program, one that reads packets and one that proves as them?
(I have a feeling that that's what happened)
from croc.
Did you try it?
from croc.
Not yet but when we talk theoretically this should not improve performance... also if it would platforms like Netflix would've done that
(Btw side note just because we are talking, I implemented pake/siec in rust if you want to see)
from croc.
Yeah would love to see a SIEC implementation! Is it public?
The benefits might be OS specific, but they were beneficial with my testing between Windows and Linux. Maybe it's different now, it deserves testing.
from croc.
Hmm but that makes no sense... it should be the same speed... Are you sure there is no other reason for the non-multiplex way to be slower?
Using 4 sockets does not mean that you send 4 packets at once... the packets are still sent on a serial manner...
- Maybe you didn't use async on the single thread version? And then the multithreaded version had more chances of read while on the single thread version some sockets blocked and others didn't?
- Maybe there is an overhead after each read that causes the reads to be less frequent? And then you need to apply a two threaded program, one that reads packets and one that proves as them?
(I have a feeling that that's what happened)
Just dropping into the conversation as I stumbled upon here randomly while scrolling through the issues. Not a contributor of this repo but I just wanted to add my 2 cents on the networking side of things.
Using multiple connections to speed up file transfers is an old trick that has been in use since the time of download managers back in the early 2000s.
It's quite a common misconception to think that using a single socket should provide the same speed as using multiple sockets, however in practice, this is often not the case, and here is why:
-
Parallelism:
- When using multiple sockets, different parts of the file can be sent in parallel over different connections. This parallel transmission can potentially speed up the overall file transfer, especially on networks with high latency or packet loss.
-
Serial vs Parallel Transmission:
- You mentioned that packets are sent in a serial manner, which is true for a single socket. However, when using multiple sockets, each socket can transmit its packets independently and concurrently with the others, essentially moving from a serial to a parallel transmission model.
-
Congestion Control:
- TCP has a "slow start" phase to discover the available bandwidth and to avoid congesting the network. During slow start, the window size starts small and doubles with each successful acknowledgment, until it reaches a threshold or encounters packet loss. By using multiple sockets, each with its own window size, we can essentially bypass the slow start phase for each individual connection, potentially allowing for faster transmission, especially for smaller files, where the slow start phase may be more prevalent.
- Each socket operates its own congestion control mechanism. In networks with good conditions, having multiple congestion windows (one per socket) allows for more data to be in flight simultaneously, which can improve the utilization of the available bandwidth.
-
Error Handling:
- In a scenario where packet loss occurs, a single socket would need to wait for retransmissions, potentially stalling the transfer. With multiple sockets, if one socket encounters an error, the others can continue transmitting data, thus making the process more resilient to network issues.
-
Async and Multithreading:
- While implementing async operations or multithreading can improve the efficiency of a single-socket setup, the potential benefits of having multiple sockets (and thus multiple connections) often surpass those optimizations, especially in challenging network conditions.
-
Overcoming Bandwith Delay Product limitations (e.g. on networks with high latency for instance):
- The Bandwidth Delay Product (BDP) is the product of a network link's capacity and its round-trip time (RTT). A single TCP connection may not fully utilize the available bandwidth, especially in high-latency networks, even if the bandwidth is high (think a satellite link with 100 Mbps second bandwidth but 100s ms latency). Multiple sockets can help overcome this limitation by allowing more data to be in flight at the same time, thus better utilizing the available bandwidth.
from croc.
Yeah would love to see a SIEC implementation! Is it public?
The benefits might be OS specific, but they were beneficial with my testing between Windows and Linux. Maybe it's different now, it deserves testing.
Yes!
https://github.com/AsafFisher/rust-croc
from croc.
Hmm but that makes no sense... it should be the same speed... Are you sure there is no other reason for the non-multiplex way to be slower?
Using 4 sockets does not mean that you send 4 packets at once... the packets are still sent on a serial manner...
- Maybe you didn't use async on the single thread version? And then the multithreaded version had more chances of read while on the single thread version some sockets blocked and others didn't?
- Maybe there is an overhead after each read that causes the reads to be less frequent? And then you need to apply a two threaded program, one that reads packets and one that proves as them?
(I have a feeling that that's what happened)Just dropping into the conversation as I stumbled upon here randomly while scrolling through the issues. Not a contributor of this repo but I just wanted to add my 2 cents on the networking side of things. Using multiple connections to speed up file transfers is an old trick that has been in use since the time of download managers back in the early 2000s. It's quite a common misconception to think that using a single socket should provide the same speed as using multiple sockets, however in practice, this is often not the case, and here is why:
Hmm I didnt read the whole thing because its 2AM, but as for point 1 and 2, its not true.
Even if you have multiple socket transmitting from different threads, you have only a single network device that these packets go through...
Lets assume your network device has multiple cores and can transmit in parallel (which is wierd) you still have a single layer 1 limitation, you cant send multiple packets on a single physical link.... You just cant send serial data with multiple sockets and expect it to be faster. It might be faster because the CPU gives more runtime to your threads but this is due to schedualing not parallelism.
litterally the linux kernel e1000's driver has a single serial rx/tx buffer to send and receive packets
Parallelism:
- When using multiple sockets, different parts of the file can be sent in parallel over different connections. This parallel transmission can potentially speed up the overall file transfer, especially on networks with high latency or packet loss.
Serial vs Parallel Transmission:
- You mentioned that packets are sent in a serial manner, which is true for a single socket. However, when using multiple sockets, each socket can transmit its packets independently and concurrently with the others, essentially moving from a serial to a parallel transmission model.
Also on most OS's you can change the window size using setsockopt
and such... Its not a good reason to use multiple threads to either trick the OS to get bigger windows size nor get more runtime (should use something like nice
instead)
Congestion Control:
- TCP has a "slow start" phase to discover the available bandwidth and to avoid congesting the network. During slow start, the window size starts small and doubles with each successful acknowledgment, until it reaches a threshold or encounters packet loss. By using multiple sockets, each with its own window size, we can essentially bypass the slow start phase for each individual connection, potentially allowing for faster transmission, especially for smaller files, where the slow start phase may be more prevalent.
- Each socket operates its own congestion control mechanism. In networks with good conditions, having multiple congestion windows (one per socket) allows for more data to be in flight simultaneously, which can improve the utilization of the available bandwidth.
is a good point, but I havn't seen a dropped packet since like 5 months ago...
Error Handling:
- In a scenario where packet loss occurs, a single socket would need to wait for retransmissions, potentially stalling the transfer. With multiple sockets, if one socket encounters an error, the others can continue transmitting data, thus making the process more resilient to network issues.
Async and Multithreading:
- While implementing async operations or multithreading can improve the efficiency of a single-socket setup, the potential benefits of having multiple sockets (and thus multiple connections) often surpass those optimizations, especially in challenging network conditions.
I dont use satalite I have fiber optics but I still dont understand why it matters as long as you can really send in parallel on a physical link
Overcoming Bandwith Delay Product limitations (e.g. on networks with high latency for instance):
- The Bandwidth Delay Product (BDP) is the product of a network link's capacity and its round-trip time (RTT). A single TCP connection may not fully utilize the available bandwidth, especially in high-latency networks, even if the bandwidth is high (think a satellite link with 100 Mbps second bandwidth but 100s ms latency). Multiple sockets can help overcome this limitation by allowing more data to be in flight at the same time, thus better utilizing the available bandwidth.
I bet you that I can make a single threaded async
version of it in rust that is faster (am actually working on it).
Also, and I dont like playing this card:
https://stackoverflow.com/questions/29277554/is-transmitting-a-file-over-multiple-sockets-faster-than-just-using-one-socket
from croc.
That’s great, but did you test it? It looks like you can disable the parallel transmission with the option --no-multi.
I used a 670 MB file, macOS on both ends, 100 Mbit/s downstream DSL on the receiving end, multiple runs.
With defaults, multiplexing enabled, it took an average of 78 seconds. Without multiplexing, it took 92 seconds. Seems worthwhile to me.
from croc.
I understand that it's faster rn... My feeling is that it's faster not because the multiplexing but because of the design or some other scheduling reasons (maybe try benchmarking on a single core with nice -20 croc
). I might be wrong but that's my feeling (:
Anyways I'm planning on investing that anyway...
Did you make the time benchmarking start right when the file transmission start?
In general just because something works faster doesn't mean it's the solution to that problem
from croc.
Sure! I did
time croc -yes 1234-xyz
on the receiving end each time, and alternated sending the same file with and without --no-multi. Here are the times in seconds.
no-multi | multi | |
---|---|---|
101 | 82 | |
94 | 75 | |
92 | 82 | |
90 | 73 | |
79 | 76 | |
97 | 78 | |
average | 92 | 78 |
Why not run some tests yourself? And I’m sure if you can build something that’s consistently faster than the current code, people will be interested to see your test results.
from croc.
Sure! I did
time croc -yes 1234-xyz
on the receiving end each time, and alternated sending the same file with and without --no-multi. Here are the times in seconds.
| | no-multi | multi |
| ---: | ---: | ---: |
| | 101 | 82 |
| | 94 | 75 |
| | 92 | 82 |
| | 90 | 73 |
| | 79 | 76 |
| | 97 | 78 |
| average | 92 | 78 |
Why not run some tests yourself? And I’m sure if you can build something that’s consistently faster than the current code, people will be interested to see your test results.
I don't have a lot of time (: + I believe you when you say it's faster... but the math isn't mathing for me 😊
As I said I will take a look for why this happens but yah
from croc.
Hey so I think the decryption part in receiveData is the bottle neck, if you'd send the data received to a different decryption thread and keep reading packets it might be faster in a single threaded environment then on multithreaded one
from croc.
It’s great that you want to speed up croc, but a concrete implementation might be more helpful than unproven hypotheses.
You can disable compression with --no-compress.
I ran another quick test, different file and different endpoint, so not directly comparable to the last.
Compression disabled
default multiplexing: 76 seconds
--no-multi: 111 seconds
from croc.
Thanks so much @ferebee for running some experiments! A 16% improvement seems pretty good.
Also thanks @shidenkai0 for weighing in with a very detailed overview!! That is greatly appreciated.
@AsafFisher I went ahead and tested your hypothesis about decryption with and without multiplexing. I removed encryption and tried sending files. Without ecryption, with multiplexing: 105 seconds. Without encryption, without multiplexing: 115 seconds. Not a 16% improvement like @ferebee, but an improvement nonetheless with multiplexing and without encryption.
@AsafFisher now its your turn! Please try running your own tests, see for yourself.
from croc.
Oh my, there I was looking at compression while @AsafFisher was talking about encryption. Good to see the results hold up anyway.
I’ll mention that in the ’90s we were developing some custom software to send 3D rendering jobs over multiple ISDN lines in parallel. We had several well-reasoned theories about how the Linux TCP/IP stack would behave, and they were all wrong. We ended up multiplexing.
from croc.
Thanks so much @ferebee for running some experiments! A 16% improvement seems pretty good.
Also thanks @shidenkai0 for weighing in with a very detailed overview!! That is greatly appreciated.
@AsafFisher I went ahead and tested your hypothesis about decryption with and without multiplexing. I removed encryption and tried sending files. Without ecryption, with multiplexing: 105 seconds. Without encryption, without multiplexing: 115 seconds. Not a 16% improvement like @ferebee, but an improvement nonetheless with multiplexing and without encryption.
@AsafFisher now its your turn! Please try running your own tests, see for yourself.
I'll do my tests sometime, anyways if it's possible to do a decryption thread and make the file transfer even faster so that's a good outcome (:
from croc.
Related Issues (20)
- Use of Parts of the Shared Secret as Room Name HOT 4
- Unencrypted "ips?" Message Leaks Information from the Sender Side HOT 2
- Shared Secret Passed on Command Line Possibly Leaks to other Local Users HOT 5
- File Chunk Algorithm Causes Files to be Needlessly Read Multiple Times on Sender Side HOT 1
- Explicit Evaluation of Wildcard Characters on the Sender Side CLI HOT 2
- Well known "pingRoom" in Relays HOT 1
- "--yes" does not apply to "Resume?" HOT 1
- Receiving an empty folder throws Exception HOT 3
- Unable to do basic file-transfer HOT 4
- How secure is croc? (resistant to brute force?) HOT 3
- Hide relay if not going to be used HOT 1
- Defining ports is a bit cumbersome HOT 2
- debian12, croc via curl and bash from getcroc schollz, single file transfer completes, but sets no rights at all HOT 2
- --remember doesn't HOT 1
- Send commands
- Pipe (stdout) mode adds newline HOT 4
- Option to skip sender pre-hashing step and receiver verify step to half total transfer time in some cases? HOT 1
- Vulnarbility?
- Incorrect Section field in debian/control files in both 32-bit and 64-bit debian packages
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from croc.