You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

269 lines
5.6 KiB
Go

package icsnet
import (
"net"
"strings"
"time"
"gitlab.com/ics_cinnamon/voicegateway/icserror"
"gitlab.com/ics_cinnamon/voicegateway/icslog"
)
const (
NET_BUFFER_LENGTH = 4096
)
type IcsTCPNet struct {
laddr *IcsNetAddr
raddr *IcsNetAddr
conn *IcsConn
listener *net.TCPListener
}
func NewTCP(laddr, raddr *IcsNetAddr) (tcpnet *IcsTCPNet) {
tcpnet = &IcsTCPNet{
laddr: laddr,
raddr: raddr,
conn: &IcsConn{},
}
return tcpnet
}
func (t *IcsTCPNet) Listen() *icserror.IcsError {
addr, err := t.laddr.ResolveIcsNetAddr("tcp")
if err != nil {
return err
}
var aerr error
switch v := addr.(type) {
case net.TCPAddr:
t.listener, aerr = net.ListenTCP("tcp", &v)
if aerr != nil {
icserror.ICSERRNETListenError.SetError(aerr)
return icserror.ICSERRNETListenError
}
}
return nil
}
func (t *IcsTCPNet) Accept() *icserror.IcsError {
var err error
if t.listener != nil {
t.conn.ICSTCPConn, err = t.listener.AcceptTCP()
if err != nil {
icserror.ICSERRNETAcceptError.SetError(err)
return icserror.ICSERRNETAcceptError
}
} else {
return icserror.ICSERRNETAcceptError
}
return nil
}
func (t *IcsTCPNet) Connect(localAddr, remoteAddr *IcsNetAddr) *icserror.IcsError {
if remoteAddr != nil {
t.raddr = remoteAddr
}
raddr, rerr := t.raddr.ResolveIcsNetAddr("tcp")
if rerr != nil {
return rerr
}
var aerr error
switch v := raddr.(type) {
case net.TCPAddr:
t.conn.ICSTCPConn, aerr = net.DialTCP("tcp", nil, &v)
if aerr != nil {
icserror.ICSERRNETConnectError.SetError(aerr)
return icserror.ICSERRNETConnectError
}
}
return nil
}
func (t *IcsTCPNet) Close() *icserror.IcsError {
if t.conn.ICSTCPConn == nil {
return icserror.ICSERRNETNotConnectError
}
aerr := t.conn.ICSTCPConn.Close()
if aerr != nil {
icserror.ICSERRNETNotConnectError.SetError(aerr)
return icserror.ICSERRNETNotConnectError
}
return nil
}
func (t *IcsTCPNet) Write(b []byte) (int, *icserror.IcsError) {
if t.conn.ICSTCPConn == nil {
return 0, icserror.ICSERRNETNotConnectError
}
wsize, err := t.conn.ICSTCPConn.Write(b)
if err != nil {
icserror.ICSERRNETWriteError.SetError(err)
return -1, icserror.ICSERRNETWriteError
}
return wsize, nil
}
func (u *IcsTCPNet) WriteSIP(b []byte) (int, *icserror.IcsError) {
return 0, nil
}
func (u *IcsTCPNet) WriteSIPTo(b []byte, addr *net.UDPAddr) (int, *icserror.IcsError) {
return 0, nil
}
func (u *IcsTCPNet) WriteRTP(b []byte) (int, *icserror.IcsError) {
return 0, nil
}
func (t *IcsTCPNet) Read(size int) ([]byte, int, *icserror.IcsError) {
var rlen int = 0
buf := make([]byte, size)
for rlen = 0; ; {
len, err := t.conn.ICSTCPConn.Read(buf[rlen:])
//len, err := t.conn.ICSTCPConn.Read(buf)
if err == nil {
rlen += len
if rlen >= size {
return buf, rlen, nil
}
} else {
icserror.ICSERRNETReadError.SetError(err)
return nil, -1, icserror.ICSERRNETReadError
}
}
}
func (t *IcsTCPNet) ReadS(length int, lineEnd string) ([]byte, int, *icserror.IcsError) {
var rlen int = 0
size := NET_BUFFER_LENGTH
if length > 0 {
size = length
}
buf := make([]byte, size)
//fmt.Println("Reads make size:", size, "buf size:", len(buf))
for rlen = 0; ; {
rbuf := make([]byte, size)
len, err := t.conn.ICSTCPConn.Read(rbuf)
if err == nil {
rlen += len
copy(buf[:rlen], rbuf)
if rlen >= size {
return buf, rlen, nil
} else if strings.Contains(string(buf), lineEnd) {
return buf, rlen, nil
}
} else {
icserror.ICSERRNETReadError.SetError(err)
return nil, -1, icserror.ICSERRNETReadError
}
}
}
func (u *IcsTCPNet) ReadSIP() ([]byte, *net.UDPAddr, int, *icserror.IcsError) {
return nil, nil, 0, nil
}
func (u *IcsTCPNet) ReadRTP() ([]byte, *net.UDPAddr, int, *icserror.IcsError) {
return nil, nil, 0, nil
}
func (t *IcsTCPNet) LocalAddr() net.Addr {
return t.conn.ICSTCPConn.LocalAddr()
}
func (t *IcsTCPNet) RemoteAddr() net.Addr {
return t.conn.ICSTCPConn.RemoteAddr()
}
func (t *IcsTCPNet) SetRemoteAddr(raddr *IcsNetAddr) {
t.raddr = raddr
}
func (t *IcsTCPNet) SetLinger(sec int) {
t.conn.ICSTCPConn.SetLinger(sec)
}
func (t *IcsTCPNet) SetDeadline(sec int64) {
t.conn.ICSTCPConn.SetDeadline(time.Now().Add(time.Second * time.Duration(sec)))
}
func (t *IcsTCPNet) SetWriteDeadline(sec int64) {
t.conn.ICSTCPConn.SetWriteDeadline(time.Now().Add(time.Second * time.Duration(sec)))
}
func (t *IcsTCPNet) SetReadDeadline(sec int64) {
t.conn.ICSTCPConn.SetReadDeadline(time.Now().Add(time.Second * time.Duration(sec)))
}
func SendCallSignal(laddr, raddr *IcsNetAddr, buf []byte) (t *IcsTCPNet, sendlen int, err *icserror.IcsError) {
t = NewTCP(laddr, raddr)
//connect to VoiceAgent
err = t.Connect(laddr, raddr)
if err != nil {
return nil, -1, err
}
//defer t.Close()
t.SetLinger(1)
t.SetDeadline(180)
//send call signal
sendlen, err = t.Write(buf)
if err != nil {
return nil, -1, err
}
return t, sendlen, err
}
func ListenAndServeTCP(laddr, raddr *IcsNetAddr, bufend string, f func(*IcsTCPNet, string)) (t *IcsTCPNet, err *icserror.IcsError) {
t = NewTCP(laddr, raddr)
err = t.Listen()
if err != nil {
return nil, err
}
//defer t.listener.Close()
l := icslog.GetIcsLog()
go func() {
//fmt.Printf("Started TCP Listen - %s\n", laddr.String())
l.Printf(icslog.LOG_LEVEL_INFO, -1, "Started TCP Listen - %s", laddr.String())
for {
if accepterr := t.Accept(); accepterr != nil {
continue
}
go f(t, bufend)
}
}()
return
}
func (t *IcsTCPNet) CloseListener() *icserror.IcsError {
if t.listener == nil {
return icserror.ICSERRNETNotConnectError
}
aerr := t.listener.Close()
if aerr != nil {
icserror.ICSERRNETNotConnectError.SetError(aerr)
return icserror.ICSERRNETNotConnectError
}
return nil
}