From 0d243683fe97f931253c8db6d570eb5975bb042f Mon Sep 17 00:00:00 2001 From: alexander-the-alright Date: Wed, 6 Jul 2022 23:02:46 -0400 Subject: [PATCH] added muxing for multiple endpoint connections --- src/colonel.go | 8 ++++- src/nodes | 2 ++ src/sentinel.go | 77 +++++++++++++++++++++++++++++++++++++++++-------- 3 files changed, 74 insertions(+), 13 deletions(-) create mode 100644 src/nodes diff --git a/src/colonel.go b/src/colonel.go index 6d1e327..a7a02e5 100644 --- a/src/colonel.go +++ b/src/colonel.go @@ -1,7 +1,7 @@ // ============================================================================= // Auth: Alex Celani // File: colonel.go -// Revn: 06-27-2022 1.2 +// Revn: 07-05-2022 2.0 // Func: Send message to another machine and then receive a single // response. Extremely tight bounds, not robust at all // @@ -13,6 +13,7 @@ //*06-20-2022: changed name to reflect first draft of colonel.go // 06-23-2022: made input an infinite loop // 06-27-2022: added flag package, assumed ip +//*07-05-2022: added support for kill messages // // ============================================================================= @@ -87,6 +88,11 @@ func main() { // convert read bytes into string and print fmt.Println( "<<", string( buf[:n] ) ) + // response is "kill" if user sends a kill message + if string( buf[:n] ) == "kill" { + os.Exit( 1 ) + } + if *verbose { fmt.Println( "\nrtt: ", t.Sub( start ) ) // print time } diff --git a/src/nodes b/src/nodes new file mode 100644 index 0000000..acb5e71 --- /dev/null +++ b/src/nodes @@ -0,0 +1,2 @@ +led|:1212 + led2|:1203 diff --git a/src/sentinel.go b/src/sentinel.go index 35eb424..b1fffa1 100644 --- a/src/sentinel.go +++ b/src/sentinel.go @@ -1,7 +1,7 @@ // ============================================================================= // Auth: Alex Celani // File: sentinel.go -// Revn: 06-27-2022 1.3 +// Revn: 07-06-2022 2.0 // Func: Receive message, determine recipient, forward, get response, // forward back // @@ -19,6 +19,9 @@ // 06-26-2022: refined a new route() function to check for destination // validity // 06-27-2022: added flag package +// 07-05-2022: added support for kill messages +//*07-06-2022: added support for mulitplexing multiple endpoints +// so long as their name and ip is in /nodes/ file // // ============================================================================= @@ -31,6 +34,7 @@ import ( "fmt" // Println, Fprintf "strings" // ToLower, ToUpper "flag" // Parse, String, Bool + "io/ioutil" // ReadFile ) @@ -46,16 +50,20 @@ func check( err error ){ // read the given message and route to the right endpoint -func route( recv []string ) bool { - return recv[1] == "led" // only option right now is led +func route( recv []string ) string { + + ip := nodes[recv[1]] // get correlating ip to given node name + + return ip + } // function to send message to third party and get response -func send( toSend string ) string { +func send( toSend, ip string ) string { // "resolve" ip & host according to TCP rules - tcpAddr, err := net.ResolveTCPAddr( "tcp", *ip ) + tcpAddr, err := net.ResolveTCPAddr( "tcp", ip ) check( err ) // check error // "dial" ( establish connection ) to destination ip & port @@ -103,15 +111,27 @@ func handleClient( conn net.Conn ) { fmt.Println( "recv: ", recv ) } + // split message into separate words keywords := strings.Split( recv, " " ) // parse the input in some way var resp string // declare response variable - if route( keywords ) { // is destination valid? - resp = send( recv ) // send message and get response - // if user wants a list of endpoints - } else if keywords[1] == "list" { - resp = "led" // return list of endpoints + + // if user wants list of endpoints + if keywords[1] == "list" { + // iterate over keys in maps ( endpoint names ) + for key, _ := range nodes { + // collect keys, delimit with newline, in string + resp = resp + key + "\n" + } + // last char is newline, remove that + resp = resp[:len( resp ) - 1] + } else { // user wants to send message + ip := route( keywords ) // find ip of node, if it exists + if ip == "" { // if it doesn't exist + return + } + resp = send( recv, ip ) // send message, get response } if *verbose { @@ -123,25 +143,58 @@ func handleClient( conn net.Conn ) { if err != nil { // erroring on write will simply leave the return // function so it can start again later } + + if resp == "kill" { // if received kill message + os.Exit( 1 ) // kill process + } + } +} + + +// function to read in initialization data for nodes +func initNodes() { + + // open and read config file + file, err := ioutil.ReadFile( "nodes" ) + check( err ) // error checking on read + + // cast file to string, split string over newlines + node := strings.Split( string( file ), "\n" ) + + for i, kvp := range node { // iterate over lines + // XXX for whatever reason, the EOF is seen as a newline? + // so this only works for all but the "last line" + if i != len( node ) - 1 { + // kvp is delimited by a bar, split over bar + // key is the name of the endpoint + // ip is the ip of the same endpoint + nameip := strings.Split( kvp, "|" ) + // insert kvp into map + nodes[nameip[0]] = nameip[1] + } } } var ( // declare global variables for flag - ip *string self *string verbose *bool ) +// declare global variable to contain names and ips of endpoints +var nodes = make( map[string]string ) + func main() { // get flags for verbose, self ip and destination ip verbose = flag.Bool( "v", false, "flag to print extra info" ) - ip = flag.String( "ip", "192.168.1.169:1202", "end node ip and port" ) self = flag.String( "self", ":1201", "port of self" ) flag.Parse() // parse + // read /nodes/ file and populate nodes map + initNodes() + // "resolve" ip & host according to TCP rules tcpAddr, err := net.ResolveTCPAddr( "tcp", *self ) check( err ) // check error