Add support for fwmark on linux
This commit is contained in:
		
							parent
							
								
									c6d03ef17f
								
							
						
					
					
						commit
						4986cfe78b
					
				
					 4 changed files with 44 additions and 12 deletions
				
			
		|  | @ -145,10 +145,10 @@ func ipcSetOperation(device *Device, socket *bufio.ReadWriter) *IPCError { | ||||||
| 					return &IPCError{Code: ipcErrorInvalid} | 					return &IPCError{Code: ipcErrorInvalid} | ||||||
| 				} | 				} | ||||||
| 
 | 
 | ||||||
| 				netc := &device.net | 				device.net.mutex.Lock() | ||||||
| 				netc.mutex.Lock() | 				device.net.addr = addr | ||||||
| 				netc.addr = addr | 				device.net.mutex.Unlock() | ||||||
| 				netc.mutex.Unlock() | 
 | ||||||
| 				err = updateUDPConn(device) | 				err = updateUDPConn(device) | ||||||
| 				if err != nil { | 				if err != nil { | ||||||
| 					logError.Println("Failed to set listen_port:", err) | 					logError.Println("Failed to set listen_port:", err) | ||||||
|  | @ -158,7 +158,24 @@ func ipcSetOperation(device *Device, socket *bufio.ReadWriter) *IPCError { | ||||||
| 				// TODO: Clear source address of all peers
 | 				// TODO: Clear source address of all peers
 | ||||||
| 
 | 
 | ||||||
| 			case "fwmark": | 			case "fwmark": | ||||||
| 				logError.Println("FWMark not handled yet") | 				fwmark, err := strconv.ParseInt(value, 10, 32) | ||||||
|  | 				if err != nil { | ||||||
|  | 					logError.Println("Invalid fwmark", err) | ||||||
|  | 					return &IPCError{Code: ipcErrorInvalid} | ||||||
|  | 				} | ||||||
|  | 
 | ||||||
|  | 				device.net.mutex.Lock() | ||||||
|  | 				device.net.fwmark = int(fwmark) | ||||||
|  | 				err = setMark( | ||||||
|  | 					device.net.conn, | ||||||
|  | 					device.net.fwmark, | ||||||
|  | 				) | ||||||
|  | 				device.net.mutex.Unlock() | ||||||
|  | 				if err != nil { | ||||||
|  | 					logError.Println("Failed to set fwmark:", err) | ||||||
|  | 					return &IPCError{Code: ipcErrorIO} | ||||||
|  | 				} | ||||||
|  | 
 | ||||||
| 				// TODO: Clear source address of all peers
 | 				// TODO: Clear source address of all peers
 | ||||||
| 
 | 
 | ||||||
| 			case "public_key": | 			case "public_key": | ||||||
|  |  | ||||||
							
								
								
									
										16
									
								
								src/conn.go
									
									
									
									
									
								
							
							
						
						
									
										16
									
								
								src/conn.go
									
									
									
									
									
								
							|  | @ -13,6 +13,7 @@ func updateUDPConn(device *Device) error { | ||||||
| 
 | 
 | ||||||
| 	if netc.conn != nil { | 	if netc.conn != nil { | ||||||
| 		netc.conn.Close() | 		netc.conn.Close() | ||||||
|  | 		netc.conn = nil | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
| 	// open new connection
 | 	// open new connection
 | ||||||
|  | @ -26,11 +27,24 @@ func updateUDPConn(device *Device) error { | ||||||
| 			return err | 			return err | ||||||
| 		} | 		} | ||||||
| 
 | 
 | ||||||
|  | 		// set fwmark
 | ||||||
|  | 
 | ||||||
|  | 		err = setMark(netc.conn, netc.fwmark) | ||||||
|  | 		if err != nil { | ||||||
|  | 			return err | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
| 		// retrieve port (may have been chosen by kernel)
 | 		// retrieve port (may have been chosen by kernel)
 | ||||||
| 
 | 
 | ||||||
| 		addr := conn.LocalAddr() | 		addr := conn.LocalAddr() | ||||||
| 		netc.conn = conn | 		netc.conn = conn | ||||||
| 		netc.addr, _ = net.ResolveUDPAddr(addr.Network(), addr.String()) | 		netc.addr, _ = net.ResolveUDPAddr( | ||||||
|  | 			addr.Network(), | ||||||
|  | 			addr.String(), | ||||||
|  | 		) | ||||||
|  | 
 | ||||||
|  | 		// notify goroutines
 | ||||||
|  | 
 | ||||||
| 		signalSend(device.signal.newUDPConn) | 		signalSend(device.signal.newUDPConn) | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -21,9 +21,10 @@ type Device struct { | ||||||
| 		messageBuffers sync.Pool | 		messageBuffers sync.Pool | ||||||
| 	} | 	} | ||||||
| 	net struct { | 	net struct { | ||||||
| 		mutex sync.RWMutex | 		mutex  sync.RWMutex | ||||||
| 		addr  *net.UDPAddr // UDP source address
 | 		addr   *net.UDPAddr // UDP source address
 | ||||||
| 		conn  *net.UDPConn // UDP "connection"
 | 		conn   *net.UDPConn // UDP "connection"
 | ||||||
|  | 		fwmark int | ||||||
| 	} | 	} | ||||||
| 	mutex        sync.RWMutex | 	mutex        sync.RWMutex | ||||||
| 	privateKey   NoisePrivateKey | 	privateKey   NoisePrivateKey | ||||||
|  |  | ||||||
|  | @ -34,28 +34,28 @@ func (device *Device) RoutineTUNEventReader() { | ||||||
| 			if err != nil { | 			if err != nil { | ||||||
| 				logError.Println("Failed to load updated MTU of device:", err) | 				logError.Println("Failed to load updated MTU of device:", err) | ||||||
| 			} else if int(old) != mtu { | 			} else if int(old) != mtu { | ||||||
| 				atomic.StoreInt32(&device.tun.mtu, int32(mtu)) |  | ||||||
| 				if mtu+MessageTransportSize > MaxMessageSize { | 				if mtu+MessageTransportSize > MaxMessageSize { | ||||||
| 					logInfo.Println("MTU updated:", mtu, "(too large)") | 					logInfo.Println("MTU updated:", mtu, "(too large)") | ||||||
| 				} else { | 				} else { | ||||||
| 					logInfo.Println("MTU updated:", mtu) | 					logInfo.Println("MTU updated:", mtu) | ||||||
| 				} | 				} | ||||||
|  | 				atomic.StoreInt32(&device.tun.mtu, int32(mtu)) | ||||||
| 			} | 			} | ||||||
| 		} | 		} | ||||||
| 
 | 
 | ||||||
| 		if event&TUNEventUp != 0 { | 		if event&TUNEventUp != 0 { | ||||||
| 			if !device.tun.isUp.Get() { | 			if !device.tun.isUp.Get() { | ||||||
|  | 				logInfo.Println("Interface set up") | ||||||
| 				device.tun.isUp.Set(true) | 				device.tun.isUp.Set(true) | ||||||
| 				updateUDPConn(device) | 				updateUDPConn(device) | ||||||
| 				logInfo.Println("Interface set up") |  | ||||||
| 			} | 			} | ||||||
| 		} | 		} | ||||||
| 
 | 
 | ||||||
| 		if event&TUNEventDown != 0 { | 		if event&TUNEventDown != 0 { | ||||||
| 			if device.tun.isUp.Get() { | 			if device.tun.isUp.Get() { | ||||||
|  | 				logInfo.Println("Interface set down") | ||||||
| 				device.tun.isUp.Set(false) | 				device.tun.isUp.Set(false) | ||||||
| 				closeUDPConn(device) | 				closeUDPConn(device) | ||||||
| 				logInfo.Println("Interface set down") |  | ||||||
| 			} | 			} | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
		Loading…
	
		Reference in a new issue