github.com/geniusesgroup/libgo@v0.0.0-20220713101832-828057a9d3d4/ChaparKhane/xp-connections.go (about) 1 /* For license and copyright information please see LEGAL file in repository */ 2 3 package chaparkhane 4 5 import ( 6 "hash/crc32" 7 8 "../chapar" 9 "../crypto" 10 ) 11 12 // xpConnections store pools of connection to retrieve in many ways! 13 type xpConnections struct { 14 old *xpConnections // use just in expanding 15 pathsPool [254][]*routerConnection 16 XPsPoolLen uint32 17 XPsPool []*xpPool 18 } 19 20 type xpPool struct { 21 XPID uint32 22 FreeID uint8 23 RouterID [8]uint32 24 Conn [8]*routerConnection 25 } 26 27 func (xp *xpConnections) init() { 28 // TotalHop = 1 or One hop frame use just in p2p networks and not pass here!! 29 // TotalHop = 2 or Two hop implement by just one Chapar switch device! 30 xp.pathsPool[0] = make([]*routerConnection, 256) 31 // TotalHop > 2 or More than two hop implement by more than one Chapar switch device! 32 var i uint8 33 for i = 1; i < 255; i++ { 34 xp.pathsPool[i] = make([]*routerConnection, 2048) 35 } 36 37 // TODO::: use existing XP number instead of below 1024 number 38 xp.XPsPool = make([]*xpPool, 1024) 39 xp.XPsPoolLen = 1024 40 } 41 42 func (xp *xpConnections) expandPathPool(hopNum uint8) (newPoolLen uint32) { 43 var poolLen uint32 = uint32(len(xp.pathsPool[hopNum])) 44 newPoolLen = poolLen * 2 45 46 var new = make([]*routerConnection, newPoolLen) 47 48 // Copy old paths 49 var existingConn *routerConnection 50 var loc uint32 51 var i uint32 52 for i = 0; i < poolLen; i++ { 53 existingConn = xp.pathsPool[hopNum][i] 54 if existingConn != nil { 55 loc = crc32.ChecksumIEEE(existingConn.Path) % newPoolLen 56 new[loc] = existingConn 57 } 58 } 59 xp.pathsPool[hopNum] = new 60 61 return 62 } 63 64 func (xp *xpConnections) expandXPsPool() { 65 var newPoolLen uint32 = xp.XPsPoolLen * 2 66 var new = make([]*xpPool, newPoolLen) 67 68 // Copy old XPs 69 var eXPPool *xpPool 70 var loc uint32 71 var i uint32 72 for i = 0; i < xp.XPsPoolLen; i++ { 73 eXPPool = xp.XPsPool[i] 74 if eXPPool != nil { 75 loc = eXPPool.XPID % newPoolLen 76 new[loc] = eXPPool 77 } 78 } 79 80 xp.XPsPool = new 81 xp.XPsPoolLen = newPoolLen 82 } 83 84 // registerNewPath use to register or overwrite a path in the related pool! 85 func (xp *xpConnections) registerNewPath(conn *routerConnection, path []byte) { 86 var pathLen uint8 = uint8(len(conn.Path)) 87 var poolLen uint32 = uint32(len(xp.pathsPool[pathLen])) 88 var loc = crc32.ChecksumIEEE(conn.Path) % poolLen 89 90 // Check collision!! 91 var existingConn = xp.pathsPool[pathLen][loc] 92 if existingConn != nil && existingConn.RouterID != conn.RouterID { 93 poolLen = xp.expandPathPool(pathLen) 94 loc = crc32.ChecksumIEEE(conn.Path) % poolLen 95 } 96 97 xp.pathsPool[pathLen][loc] = conn 98 } 99 100 // registerNewRouter use to register or overwrite a router in the related pool! 101 func (xp *xpConnections) registerNewRouter(conn *routerConnection) { 102 var eXPPool = xp.GetXPPool(conn.XPID) 103 if eXPPool != nil { 104 if eXPPool.XPID == conn.XPID { 105 for i := 0; i < 8; i++ { 106 // Check for existing connection 107 if eXPPool.RouterID[i] == conn.RouterID { 108 eXPPool.Conn[i].AlternativePath = append(eXPPool.Conn[i].AlternativePath, conn.Path) 109 xp.registerNewPath(eXPPool.Conn[i], conn.Path) 110 } else if eXPPool.RouterID[i] == 0 { 111 eXPPool.FreeID++ 112 eXPPool.RouterID[i] = conn.RouterID 113 eXPPool.Conn[i] = conn 114 return 115 } 116 } 117 } else { 118 // Collision occurred!! 119 xp.expandXPsPool() 120 xp.registerNewRouter(conn) 121 } 122 } else { 123 eXPPool = &xpPool{ 124 XPID: conn.XPID, 125 FreeID: 1, 126 RouterID: [8]uint32{conn.RouterID, 0, 0, 0, 0, 0, 0, 0}, 127 Conn: [8]*routerConnection{conn, nil, nil, nil, nil, nil, nil, nil}, 128 } 129 var xpLoc = conn.XPID % xp.XPsPoolLen 130 xp.XPsPool[xpLoc] = eXPPool 131 } 132 } 133 134 // MakeNewXPConnectionReq is the request structure of MakeNewXPConnection() 135 type MakeNewXPConnectionReq struct { 136 XPID uint32 137 RouterID uint32 138 Path []byte 139 MaxBandwidth uint64 140 Signature [256]byte 141 } 142 143 // MakeNewXPConnection use to make new connection! 144 func (xp *xpConnections) MakeNewXPConnection(req *MakeNewXPConnectionReq) { 145 // TODO::: Check signature first! 146 147 var conn = routerConnection{ 148 RouterID: req.RouterID, 149 Path: req.Path, 150 ReversePath: chapar.ReversePath(req.Path), 151 Status: routerConnectionStateOpen, 152 MaxBandwidth: req.MaxBandwidth, 153 Cipher: crypto.NewGCM(crypto.NewAES256([32]byte{})), 154 } 155 xp.RegisterConnection(&conn) 156 } 157 158 // RegisterConnection use to register new connection in server xpConnections pool!! 159 func (xp *xpConnections) RegisterConnection(conn *routerConnection) { 160 xp.registerNewPath(conn, conn.Path) 161 xp.registerNewRouter(conn) 162 } 163 164 // GetConnectionByPath use to get a connection by peer GP from xpConnections pool!! 165 func (xp *xpConnections) GetConnectionByPath(path []byte) (conn *routerConnection) { 166 var pathLen = len(path) 167 var poolLen uint32 = uint32(len(xp.pathsPool[pathLen])) 168 var loc = crc32.ChecksumIEEE(path) % poolLen 169 170 conn = xp.pathsPool[pathLen][loc] 171 return 172 } 173 174 // GetConnectionByXPID use to get a connection by given XP ID from xpConnections pool!! 175 func (xp *xpConnections) GetXPPool(xpID uint32) (eXPPool *xpPool) { 176 var xpLoc = xpID % xp.XPsPoolLen 177 eXPPool = xp.XPsPool[xpLoc] 178 return 179 } 180 181 // GetConnectionByXPID use to get a connection by given XP ID from xpConnections pool!! 182 func (xp *xpConnections) GetConnectionByXPID(xpID uint32) (conn *routerConnection) { 183 var xpLoc = xpID % xp.XPsPoolLen 184 conn = xp.XPsPool[xpLoc].Conn[0] 185 186 // check if connection is in not ready status 187 188 return 189 } 190 191 // CloseConnection use to un-register existing connection in xpConnections pool!! 192 func (xp *xpConnections) CloseConnection(conn *routerConnection) { 193 // TODO::: Check GC performance : delete connection vs just reset it and send it to pool of unused connection!! 194 var pathLen = len(conn.Path) 195 var poolLen uint32 = uint32(len(xp.pathsPool[pathLen])) 196 var loc = crc32.ChecksumIEEE(conn.Path) % poolLen 197 var xpLoc = conn.XPID % xp.XPsPoolLen 198 199 xp.pathsPool[pathLen][loc] = nil 200 201 var i uint8 202 var f = xp.XPsPool[xpLoc].FreeID 203 var eXPPool = xp.XPsPool[xpLoc] 204 for ; i < f; i++ { 205 if eXPPool.RouterID[i] == conn.RouterID { 206 eXPPool.RouterID[i] = 0 207 eXPPool.Conn[i] = nil 208 break 209 } 210 } 211 }