signalwire / freeswitch

FreeSWITCH is a Software Defined Telecom Stack enabling the digital transformation from proprietary telecom switches to a versatile software implementation that runs on any commodity hardware. From a Raspberry PI to a multi-core server, FreeSWITCH can unlock the telecommunications potential of any device.
https://freeswitch.com/#getting-started
Other
3.62k stars 1.43k forks source link

Registrations from "!" #885

Open pikachu937 opened 4 years ago

pikachu937 commented 4 years ago

There is: stock fs (stock config, current profile is selected by default internal) 2 user 1001 and 1002 domain 192.168.0.1 authorization without registration is disabled in the profile (login and pass must be entered, without this there is no way) Actually, he registers from both accounts and calls each other, everything seems to be fine, but there is one BUT! For some reason I do not understand, I can register under the user "!"(Although there is no such thing at all) with the password from the first real user from the list, in this case 1001.

 <!-- <param name = "accept-blind-auth" value = "true" /> -->
 <!-- <param name = "accept-blind-reg" value = "true" /> -->
 <param name = "apply-inbound-acl" value = "domains" />
 <!-- <param name = "apply-register-acl" value = "domains" /> -->
 <param name = "auth-all-packets" value = "false" />
 <param name = "auth-calls" value = "true" />
 <param name="inbound-reg-force-matching-username" value="true"/>

 <list name = "domains" default = "deny">
   <node type = "allow" domain = "$$ {domain}" />
 </list>

 <list name = "lan" default = "allow">
   <node type = "allow" cidr = "192.168.42.42/32" />
 </list>

reg.txt

alexey-khabulyak commented 4 years ago

i think the problem is here https://github.com/signalwire/freeswitch/blob/master/src/switch_xml.c#L444

Freeswitch matches a user with the first node if the user has a leading exclamation mark.

For example: Someone tries to register with username !1000. Freeswitch is trying to look up a user in the directory. It starts to iterate over nodes and leave on the first because of if (*vals[x] == '!'). X = 0

alexey-khabulyak commented 4 years ago

I can't understand the meaning of this check. The only one value with a leading "!" is a pointer. I added some logs and got this:

2020-10-04 23:49:31.330156 [DEBUG] switch_xml.c:424 attrs name:id, value:! 2020-10-04 23:49:31.330156 [DEBUG] switch_xml.c:424 attrs name:number-alias, value:! 2020-10-04 23:49:31.330156 [DEBUG] switch_xml.c:424 attrs name:type, value:!pointer

if vals contains leading "!", we cut it(const char *sval = *vals + 1) In case of "!pointer" we get "pointer". But in case of "!" we get "", or "1000" in case of "!1000". Moreover. why do we use "x" as an index? X increases for every attr. So for attr id x=0, for attr number-alias x=1, for attr type x=2.

then it tries to compare aname(1000 for the first one user) and "!" strcasecmp("1000", "!") returns positive integer and goes to done So we get the first node(user 1000 in this case)

alexey-khabulyak commented 4 years ago

also. 1000 != !1000 because strcasecmp("1000", "1000") returns 0. and it tries the next node(1001). strcasecmp("1000", "1001") returns non zero value(True) and goes to done (returns node 1001)

p.s. sorry for my english.

alexey-khabulyak commented 4 years ago

seems like someone missed an exclamation mark in strcasecmp but I am not sure. with if (!strcasecmp(aname, sval)) it returns Can't find user [!@192.168.122.152] for user "!" and 1000 matches !1000. Maybe It brokes some things.