fixing allocation

This commit is contained in:
Roland Osborne 2023-04-10 15:14:51 -07:00
parent 7299d63711
commit a08a354205
2 changed files with 70 additions and 29 deletions

View File

@ -120,7 +120,6 @@ func (s *Sturn) handleMessage(buf []byte, addr net.Addr) {
} }
func (s *Sturn) handleCreatePermissionRequest(msg *SturnMessage, addr net.Addr) { func (s *Sturn) handleCreatePermissionRequest(msg *SturnMessage, addr net.Addr) {
fmt.Println(addr.String(), msg);
var attributes []SturnAttribute var attributes []SturnAttribute
attributes = append(attributes, SturnAttribute{ attributes = append(attributes, SturnAttribute{
@ -138,13 +137,12 @@ fmt.Println(addr.String(), msg);
fmt.Printf("failed to write stun response"); fmt.Printf("failed to write stun response");
} else { } else {
(*s.conn).WriteTo(s.buf[:n], addr); (*s.conn).WriteTo(s.buf[:n], addr);
fmt.Println("PERM>", s.buf[:n]);
} }
return return
} }
func (s *Sturn) handleSendIndication(msg *SturnMessage, addr net.Addr) { func (s *Sturn) handleSendIndication(msg *SturnMessage, addr net.Addr) {
//fmt.Println(addr.String(), msg); fmt.Println(addr.String(), msg);
} }
func (s *Sturn) handleBindingRequest(msg *SturnMessage, addr net.Addr) { func (s *Sturn) handleBindingRequest(msg *SturnMessage, addr net.Addr) {
@ -195,7 +193,7 @@ func (s *Sturn) sendAllocateError(msg *SturnMessage, addr net.Addr) {
var attributes []SturnAttribute var attributes []SturnAttribute
attributes = append(attributes, SturnAttribute{ attributes = append(attributes, SturnAttribute{
atrType: ATRErrorCode, atrType: ATRErrorCode,
intValue: 400, intValue: 403,
}) })
attributes = append(attributes, SturnAttribute{ attributes = append(attributes, SturnAttribute{
atrType: ATRNonce, atrType: ATRNonce,
@ -219,21 +217,66 @@ func (s *Sturn) sendAllocateError(msg *SturnMessage, addr net.Addr) {
} }
} }
func setAllocation(source string, transaction []byte, response []byte, port int, session *SturnSession) {
allocation := &SturnAllocation{}
allocation.port = port
allocation.source = source
allocation.transaction = make([]byte, len(transaction))
copy(allocation.transaction, transaction)
allocation.response = make([]byte, len(response))
copy(allocation.response, response)
session.allocations = append(session.allocations, allocation)
}
func getAllocation(source string, transaction []byte, session *SturnSession) (*SturnAllocation) {
for _, allocation := range session.allocations {
if allocation.source == source && len(allocation.transaction) == len(transaction) {
match := true
for i := 0; i < len(transaction); i++ {
if transaction[i] != allocation.transaction[i] {
match = false
}
}
if match {
return allocation
}
}
}
return nil
}
func (s *Sturn) handleAllocateRequest(msg *SturnMessage, addr net.Addr) { func (s *Sturn) handleAllocateRequest(msg *SturnMessage, addr net.Addr) {
username := getAttribute(msg, ATRUsername); username := getAttribute(msg, ATRUsername)
if username == nil { if username == nil {
s.sendAllocateError(msg, addr); fmt.Println("no username", addr.String(), msg.transaction);
return; s.sendAllocateError(msg, addr)
return
} }
relayPort, err := s.getRelayPort(); s.sync.Lock();
defer s.sync.Unlock();
session, set := sturn.sessions[username.strValue]
if !set {
fmt.Println("no session", addr.String());
s.sendAllocateError(msg, addr)
return
}
if allocation := getAllocation(addr.String(), msg.transaction, session); allocation != nil {
fmt.Println("dup allocate", addr.String())
(*s.conn).WriteTo(allocation.response, addr)
return
}
relayPort, err := s.getRelayPort()
if err != nil { if err != nil {
fmt.Println(err); fmt.Println(err);
s.sendAllocateError(msg, addr) s.sendAllocateError(msg, addr)
return return
} }
fmt.Println("> ", relayPort, "< ", addr.String(), msg);
address := strings.Split(addr.String(), ":") address := strings.Split(addr.String(), ":")
ip := address[0]; ip := address[0];
port, _ := strconv.Atoi(address[1]); port, _ := strconv.Atoi(address[1]);
@ -242,8 +285,8 @@ func (s *Sturn) handleAllocateRequest(msg *SturnMessage, addr net.Addr) {
atrType: ATRXorRelayedAddress, atrType: ATRXorRelayedAddress,
byteValue: FAMIPv4, byteValue: FAMIPv4,
intValue: int32(relayPort), intValue: int32(relayPort),
strValue: "192.168.13.233", //strValue: "192.168.13.233",
//strValue: "98.234.232.221", strValue: "98.234.232.221",
}); });
attributes = append(attributes, SturnAttribute{ attributes = append(attributes, SturnAttribute{
atrType: ATRLifetime, atrType: ATRLifetime,
@ -265,20 +308,20 @@ func (s *Sturn) handleAllocateRequest(msg *SturnMessage, addr net.Addr) {
attributes: attributes, attributes: attributes,
}; };
err, n := writeMessage(response, s.buf); err, n := writeMessage(response, s.buf)
if err != nil { if err != nil {
fmt.Printf("failed to write stun response"); fmt.Printf("failed to write stun response")
} else { } else {
(*s.conn).WriteTo(s.buf[:n], addr); setAllocation(addr.String(), msg.transaction, s.buf[:n], relayPort, session)
(*s.conn).WriteTo(s.buf[:n], addr)
} }
return return
} }
func getAttribute(msg *SturnMessage, atrType int) (attr *SturnAttribute) { func getAttribute(msg *SturnMessage, atrType int) (attr *SturnAttribute) {
for _, attribute := range msg.attributes { for i, _ := range msg.attributes {
if attribute.atrType == ATRUsername { if msg.attributes[i].atrType == atrType {
attr = &attribute; attr = &msg.attributes[i];
} }
} }
return return

View File

@ -18,10 +18,17 @@ const SturnMaxBindFail = 16
const SturnNonceSize = 8 const SturnNonceSize = 8
const SturnPassSize = 8 const SturnPassSize = 8
type SturnAllocation struct {
source string
transaction []byte
response []byte
port int
}
type SturnSession struct { type SturnSession struct {
user string user string
auth string auth string
nonce string allocations []*SturnAllocation
} }
type Sturn struct { type Sturn struct {
@ -59,7 +66,7 @@ func Listen(port int, relayStart int, relayCount int) (error) {
relayPorts[i] = true relayPorts[i] = true
} }
sturn := &Sturn{ sturn = &Sturn{
sessionId: 0, sessionId: 0,
closing: false, closing: false,
port: port, port: port,
@ -68,6 +75,7 @@ func Listen(port int, relayStart int, relayCount int) (error) {
relayPorts: relayPorts, relayPorts: relayPorts,
conn: &conn, conn: &conn,
buf: make([]byte, SturnMaxSize), buf: make([]byte, SturnMaxSize),
sessions: make(map[string]*SturnSession),
} }
go sturn.serve(conn); go sturn.serve(conn);
@ -114,7 +122,6 @@ func TestSession() {
session := &SturnSession{ session := &SturnSession{
user: "user", user: "user",
auth: "pass", auth: "pass",
nonce: "nonceynoncenonce",
} }
sturn.sessions["user"] = session sturn.sessions["user"] = session
} }
@ -132,22 +139,15 @@ func (s *Sturn) addSession() (*SturnSession, error) {
if authErr != nil { if authErr != nil {
return nil, authErr return nil, authErr
} }
nonceBin, nonceErr := securerandom.Bytes(SturnNonceSize)
if nonceErr != nil {
return nil, nonceErr
}
session := &SturnSession{ session := &SturnSession{
user: user, user: user,
auth: hex.EncodeToString(authBin), auth: hex.EncodeToString(authBin),
nonce: hex.EncodeToString(nonceBin),
} }
s.sessions[user] = session s.sessions[user] = session
return session, nil return session, nil
} }
func (s *Sturn) getRelayPort() (int, error) { func (s *Sturn) getRelayPort() (int, error) {
s.sync.Lock();
defer s.sync.Unlock();
s.relayIndex += 1; s.relayIndex += 1;
for i := 0; i < s.relayCount; i++ { for i := 0; i < s.relayCount; i++ {
key := (i + s.relayIndex) % s.relayCount; key := (i + s.relayIndex) % s.relayCount;
@ -160,8 +160,6 @@ func (s *Sturn) getRelayPort() (int, error) {
} }
func (s *Sturn) setRelayPort(port int) { func (s *Sturn) setRelayPort(port int) {
s.sync.Lock()
defer s.sync.Unlock();
key := port - s.relayStart key := port - s.relayStart
s.relayPorts[key] = true s.relayPorts[key] = true
} }