-
Notifications
You must be signed in to change notification settings - Fork 292
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
feat: Add username/password SOCKS5 auth #1683
base: master
Are you sure you want to change the base?
Conversation
|
@nurupo Does this still need testing? I'm willing to test it. |
Yep, so far no one has tested it as far as I'm aware. |
1f15b48
to
b5f2735
Compare
abbf3db
to
bbb3a45
Compare
Fixed a couple of issues I have noticed after reviewing with a fresh set of eyes. |
I managed to verify that SOCKS5 authenticated connections work. Currently I've only tested with |
Update: I managed to verify that SOCKS5 authenticated connections work in qTox too. When using correct credentials, the client connects to a TCP relay and all traffic goes through it. In the case of incorrect credentials or lack of credentials, qTox fails to connect. In all cases, I noticed this in the log: EDIT (comment from IRC): |
Cool, thanks for testing.
This is a qTox-specific thing, it says nothing about toxcore or this PR working or non-working. Would be great if someone else could test this too, I'm not too sure if @cryptogospod tested it correctly. The way it should have been tested, that Since @cryptogospod has asked this on IRC, I want to point it out here too: for this to be merged, there are a few more steps that need to be done:
|
@nurupo I walked through testing with qTox with @cryptogospod at the time, the diff was adding the calls to the new API here: https://github.com/qTox/qTox/blob/da5c165f4116dce736def63b1b917523b848db09/src/core/toxoptions.cpp#L133. The Agreed that the error doesn't say anything about toxcore, but I do think that @cryptogospod's testing showing that toxcore either connects or doesn't connect when using the proxy with the correct or incorrect password shows password support's working. |
Ok, makes sense and also explains why That's a valid way to test it too, so it sounds like it was tested correctly. |
So, as for the state of this PR, per the checklist in #1683 (comment):
|
Also, I'm thinking of replacing the two functions: void tox_options_set_proxy_socks5_username(Tox_Options *options,
const uint8_t username[TOX_MAX_PROXY_SOCKS5_USERNAME_LENGTH], size_t length);
void tox_options_set_proxy_socks5_password(Tox_Options *options,
const uint8_t password[TOX_MAX_PROXY_SOCKS5_PASSWORD_LENGTH], size_t length); with one: void tox_options_set_proxy_socks5_username_password(Tox_Options *options,
const uint8_t username[TOX_MAX_PROXY_SOCKS5_USERNAME_LENGTH], size_t username_length,
const uint8_t password[TOX_MAX_PROXY_SOCKS5_PASSWORD_LENGTH], size_t password_length); Since it doesn't make sense to have one set but not the other. Even the proxy code skips doing username/password authentication if one of the username or the password (or both) is not set. Username and password would still have two separate getter functions though, so it's kind of asymmetric that way -- one setter but two getters. This does make the API clearer, in my opinion, but I wonder if such asymmetry is an issue for @iphydf as far as his binding generating code goes. Opinions? |
Note that SOCKS5 protocol has a lot more authentication methods than just the two of None and Username/Password. So in theory it would make sense to add some sort of Another thing to note is that there is no support for multiple authentication method negotiation. A SOCKS5 client can tell to a SOCKS5 server that it supports multiple authentication methods, e.g. None, Username/Password, etc. and the server then replies with which one it wants the client to use. Currently toxcore says to the proxy that it supports only one authentication method, either None or Username/Password, depending on whether username/password is set by the user or not. It's unusual for the user not to know what authentication method the proxy they are trying to connect to supports, so I figured it doesn't make much sense to support this. |
@nurupo Thanks - I agree the simplest case covers corporate proxies which I feel is the target of this, and perhaps some Tor users. What has to be done to get this merged? 2 failing, and 1 expected checks? |
Does it deserve a couple of lines in docs/TCP_Network.txt ? A cut-n-paste of what you just wrote, plus a little on proxies? This changes Tox_Options so I'll need to change my ctypes wrapper when it lands. It would be nice if it lands in a new release so I can change my wrapper depending on the release version. Is there any kind of "what's new in release" document that gets issued with new releases to note the change in Tox_Options? I don't see a ChangeLog. Should this be tagged with "API Break"? |
e3a1749
to
8db5130
Compare
FWIW there's a partially resurected echobot in Python at https://git.plastiras.org/emdee/toxygen_wrapper/src/branch/main/src/toxygen_wrapper/toxygen_echo.py that is socks aware (partly username/passwd) if it helps you for testing. I don't know Tox AV well enough to fix the AV part of the echobot, but I presume the AV code was working. Alex Baker's echobot is not SOCKSified, nor is it every likely to be alexbakker/EchoBot#9. It's from PyTox https://github.com/aitjcize/PyTox/raw/master/examples/echo.py ported to my toxygen_wrapper bindings. |
tox_options_set_proxy_socks5_username should be tox_options_set_proxy_username i feel but you decide; the proxy user and password should also work for an http proxy, also common in corporate settings. it's seriously unlikely/impossible that you would have http and socks proxies going on at the same time in the same Tox, so you might as well double use the username/password code if you added http passsword proxies later. I've seen corporate settings with both http and socks proxies with the same username/password (NTLM) but very different network behaviours: the http proxy was MITMed. |
* @deprecated The macro will be removed in 0.3.0. Use the function instead. | ||
*/ | ||
#define TOX_MAX_PROXY_SOCKS5_USERNAME_LENGTH 255 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I know these used to be generated, but should we really add new deprecated-at-the-time-of-creation macros?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wonder.
We have also recently changed the API from using *buffer
to buffer[SIZE_CONSTANT]
in #2518, e.g.
bool tox_bootstrap(Tox *tox, const char *host, uint16_t port, const uint8_t public_key[TOX_PUBLIC_KEY_SIZE], Tox_Err_Bootstrap *error);
Why are we making the API functions use deprecated macros?
Are we actually keeping the macros now, not deprecating them?
@iphydf ?
Anyway, I made the API changes such that they would match what the rest of the API does, that is: define constants and use them for array length in function declarations. You can see those used in the function declarations:
void tox_options_set_proxy_socks5_username(Tox_Options *options, const uint8_t username[TOX_MAX_PROXY_SOCKS5_USERNAME_LENGTH], size_t length);
void tox_options_set_proxy_socks5_password(Tox_Options *options, const uint8_t password[TOX_MAX_PROXY_SOCKS5_PASSWORD_LENGTH], size_t length);
I think it makes sense to add the macros, even if they are deprecated at the creation, in order to keep the API coherent. Currently everything has macros. Once we decide to remove the macros, we can remove them all at once and nothing will have macros. That way there is no in-between state where some things have macros but some don't. (Please point out if we are already in the in-between state where some of the added APIs don't define macros, in which case I will remove the macros too. I checked that the ngc defines macros, so figured we are still in the all-macro state, but I might have missed something.)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The arrays are not always of max size, or might not be arrays at all.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Green-Sky I don't understand what you are saying, can you re-phrase that or provide an example of what do you mean?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If I am not mistaken, then the size is supposed to be exact, so you would have to provide a max sized buffer (if your code is also checked by cimple).
so something like
const char* socks_host = "localhost";
would be strongly discoraged.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Green-Sky If you are saying that an API user can pass uint8_t *
for the array and that uint8_t array[SIZE]
doesn't mean that the array the user passes is of exactly SIZE
length (in fact, if you do sizeof(array)
on a function with uint8_t array[SIZE]
argument, you will notice that it's equal to sizeof(uint8_t *)
) -- then yes, that's how it indeed works. The SIZE
in uint8_t array[SIZE]
is merely for the documentation purposes.
Still, I don't understand what you meant by stating the obvious. Is there some issue in here? Do you want something in the PR to be changed? Please be more explicit!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Green-Sky Oh, your 2nd comment didn't show up for me until I refreshed the page just now.
It seems like you are thinking of uint8_t array[static SIZE]
instead of uint8_t array[SIZE]
. It's the static
variant that promises for the array to be at least SIZE
in length. The non-static variant doesn't make any promises, it's equivalent to uint8_t array[]
. Please correct if I'm wrong though, it might be me who is confusing them.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok, I think I understand what you mean. I just checked the API and we have the size specified only for arrays that should always be of that exact size. So it's a cimple thing, not a C standard thing?
Alright, I will be removing those size specifiers then, thanks for letting me know and bearing with my confusion, @Green-Sky.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Green-Sky is this better? You can see the diff as r2 vs r3 in Reviewable (assuming it shows the same revisions to everyone).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@nurupo sorry, this noti got burried in my github inbox.
I just checked the API and we have the size specified only for arrays that should always be of that exact size. So it's a cimple thing, not a C standard thing?
Yea, that is what I meant. We should probably specify when we talk about the toxcore c-dialect cimple. :)
a4262f9
to
4213205
Compare
4213205
to
f6e42c9
Compare
Regarding #1683 (comment), after a discussion with @iphydf on IRC it was decided to keep the username and password setter functions separate, as a single setter function setting both would be bad for binding generation. (An alternative could have been an opaque username-password-socks5-auth struct with a separate constructior/destructor/setter/getter functions, which we would set on Tox_Options, but it seemed a bit excessive). |
Fixes #1682
Not tested. Can someone with a SOCKS5 proxy with username/password test this?
I'm not sure how to prevent APIDSL from generating
tox_options_set_proxy_socks5_username_length()
andtox_options_set_proxy_socks5_password_length()
function declarations. Those seem pointless as the user already sets the length intox_options_set_proxy_socks5_username()
andtox_options_set_proxy_socks5_password()
. Savedata has the same issue with a pointlesstox_options_set_savedata_length()
.This change is