diff --git a/serial_darwin.go b/serial_darwin.go index e30c1a4..393236d 100644 --- a/serial_darwin.go +++ b/serial_darwin.go @@ -11,48 +11,6 @@ import "syscall" const devFolder = "/dev" const regexFilter = "^(cu|tty)\\..*" -// termios manipulation functions - -var baudrateMap = map[int]uint{ - 0: syscall.B9600, // Default to 9600 - 50: syscall.B50, - 75: syscall.B75, - 110: syscall.B110, - 134: syscall.B134, - 150: syscall.B150, - 200: syscall.B200, - 300: syscall.B300, - 600: syscall.B600, - 1200: syscall.B1200, - 1800: syscall.B1800, - 2400: syscall.B2400, - 4800: syscall.B4800, - 9600: syscall.B9600, - 19200: syscall.B19200, - 38400: syscall.B38400, - 57600: syscall.B57600, - 115200: syscall.B115200, - 230400: syscall.B230400, -} - -var databitsMap = map[int]uint{ - 0: syscall.CS8, // Default to 8 bits - 5: syscall.CS5, - 6: syscall.CS6, - 7: syscall.CS7, - 8: syscall.CS8, -} - -const tcCMSPAR uint = 0 // may be CMSPAR or PAREXT -const tcIUCLC uint = 0 - -const tcCCTS_OFLOW uint = 0x00010000 -const tcCRTS_IFLOW uint = 0x00020000 - -const tcCRTSCTS uint = (tcCCTS_OFLOW | tcCRTS_IFLOW) - -// syscall wrappers - //sys ioctl(fd int, req uint64, data uintptr) (err error) const ioctlTcgetattr = syscall.TIOCGETA diff --git a/serial_darwin_386.go b/serial_darwin_386.go index 43f0375..a1a6771 100644 --- a/serial_darwin_386.go +++ b/serial_darwin_386.go @@ -6,6 +6,44 @@ package serial // import "go.bug.st/serial.v1" -func termiosMask(data uint) uint32 { - return uint32(data) +import "syscall" + +// termios manipulation functions + +var baudrateMap = map[int]uint32{ + 0: syscall.B9600, // Default to 9600 + 50: syscall.B50, + 75: syscall.B75, + 110: syscall.B110, + 134: syscall.B134, + 150: syscall.B150, + 200: syscall.B200, + 300: syscall.B300, + 600: syscall.B600, + 1200: syscall.B1200, + 1800: syscall.B1800, + 2400: syscall.B2400, + 4800: syscall.B4800, + 9600: syscall.B9600, + 19200: syscall.B19200, + 38400: syscall.B38400, + 57600: syscall.B57600, + 115200: syscall.B115200, + 230400: syscall.B230400, } + +var databitsMap = map[int]uint32{ + 0: syscall.CS8, // Default to 8 bits + 5: syscall.CS5, + 6: syscall.CS6, + 7: syscall.CS7, + 8: syscall.CS8, +} + +const tcCMSPAR uint32 = 0 // may be CMSPAR or PAREXT +const tcIUCLC uint32 = 0 + +const tcCCTS_OFLOW uint32 = 0x00010000 +const tcCRTS_IFLOW uint32 = 0x00020000 + +const tcCRTSCTS uint32 = (tcCCTS_OFLOW | tcCRTS_IFLOW) diff --git a/serial_darwin_amd64.go b/serial_darwin_amd64.go index 0e70ce5..b721d78 100644 --- a/serial_darwin_amd64.go +++ b/serial_darwin_amd64.go @@ -6,8 +6,44 @@ package serial // import "go.bug.st/serial.v1" +import "syscall" + // termios manipulation functions -func termiosMask(data uint) uint64 { - return uint64(data) +var baudrateMap = map[int]uint64{ + 0: syscall.B9600, // Default to 9600 + 50: syscall.B50, + 75: syscall.B75, + 110: syscall.B110, + 134: syscall.B134, + 150: syscall.B150, + 200: syscall.B200, + 300: syscall.B300, + 600: syscall.B600, + 1200: syscall.B1200, + 1800: syscall.B1800, + 2400: syscall.B2400, + 4800: syscall.B4800, + 9600: syscall.B9600, + 19200: syscall.B19200, + 38400: syscall.B38400, + 57600: syscall.B57600, + 115200: syscall.B115200, + 230400: syscall.B230400, } + +var databitsMap = map[int]uint64{ + 0: syscall.CS8, // Default to 8 bits + 5: syscall.CS5, + 6: syscall.CS6, + 7: syscall.CS7, + 8: syscall.CS8, +} + +const tcCMSPAR uint64 = 0 // may be CMSPAR or PAREXT +const tcIUCLC uint64 = 0 + +const tcCCTS_OFLOW uint64 = 0x00010000 +const tcCRTS_IFLOW uint64 = 0x00020000 + +const tcCRTSCTS uint64 = (tcCCTS_OFLOW | tcCRTS_IFLOW) diff --git a/serial_freebsd.go b/serial_freebsd.go index 046c489..1e09349 100644 --- a/serial_freebsd.go +++ b/serial_freebsd.go @@ -13,7 +13,7 @@ const regexFilter = "^(cu|tty)\\..*" // termios manipulation functions -var baudrateMap = map[int]uint{ +var baudrateMap = map[int]uint32{ 0: syscall.B9600, // Default to 9600 50: syscall.B50, 75: syscall.B75, @@ -37,7 +37,7 @@ var baudrateMap = map[int]uint{ 921600: syscall.B921600, } -var databitsMap = map[int]uint{ +var databitsMap = map[int]uint32{ 0: syscall.CS8, // Default to 8 bits 5: syscall.CS5, 6: syscall.CS6, @@ -45,19 +45,13 @@ var databitsMap = map[int]uint{ 8: syscall.CS8, } -const tcCMSPAR uint = 0 // may be CMSPAR or PAREXT -const tcIUCLC uint = 0 +const tcCMSPAR uint32 = 0 // may be CMSPAR or PAREXT +const tcIUCLC uint32 = 0 -const tcCCTS_OFLOW uint = 0x00010000 -const tcCRTS_IFLOW uint = 0x00020000 +const tcCCTS_OFLOW uint32 = 0x00010000 +const tcCRTS_IFLOW uint32 = 0x00020000 -const tcCRTSCTS uint = tcCCTS_OFLOW - -func termiosMask(data uint) uint32 { - return uint32(data) -} - -// syscall wrappers +const tcCRTSCTS uint32 = tcCCTS_OFLOW //sys ioctl(fd int, req uint64, data uintptr) (err error) diff --git a/serial_linux.go b/serial_linux.go index 1490a5e..89f3aed 100644 --- a/serial_linux.go +++ b/serial_linux.go @@ -13,7 +13,7 @@ const regexFilter = "(ttyS|ttyUSB|ttyACM|ttyAMA|rfcomm|ttyO)[0-9]{1,3}" // termios manipulation functions -var baudrateMap = map[int]uint{ +var baudrateMap = map[int]uint32{ 0: syscall.B9600, // Default to 9600 50: syscall.B50, 75: syscall.B75, @@ -47,7 +47,7 @@ var baudrateMap = map[int]uint{ 4000000: syscall.B4000000, } -var databitsMap = map[int]uint{ +var databitsMap = map[int]uint32{ 0: syscall.CS8, // Default to 8 bits 5: syscall.CS5, 6: syscall.CS6, @@ -55,16 +55,10 @@ var databitsMap = map[int]uint{ 8: syscall.CS8, } -const tcCMSPAR uint = 0 // may be CMSPAR or PAREXT +const tcCMSPAR uint32 = 0 // may be CMSPAR or PAREXT const tcIUCLC = syscall.IUCLC -const tcCRTSCTS uint = 0x80000000 - -func termiosMask(data uint) uint32 { - return uint32(data) -} - -// syscall wrappers +const tcCRTSCTS uint32 = 0x80000000 //sys ioctl(fd int, req uint64, data uintptr) (err error) diff --git a/serial_unix.go b/serial_unix.go index c481ffb..b5cf703 100644 --- a/serial_unix.go +++ b/serial_unix.go @@ -148,38 +148,43 @@ func setTermSettingsBaudrate(speed int, settings *syscall.Termios) error { return &PortError{code: InvalidSpeed} } // revert old baudrate - var BAUDMASK uint for _, rate := range baudrateMap { - BAUDMASK |= rate + settings.Cflag &^= rate } - settings.Cflag &= ^termiosMask(BAUDMASK) // set new baudrate - settings.Cflag |= termiosMask(baudrate) - settings.Ispeed = termiosMask(baudrate) - settings.Ospeed = termiosMask(baudrate) + settings.Cflag |= baudrate + settings.Ispeed = baudrate + settings.Ospeed = baudrate return nil } func setTermSettingsParity(parity Parity, settings *syscall.Termios) error { switch parity { case NoParity: - settings.Cflag &= ^termiosMask(syscall.PARENB | syscall.PARODD | tcCMSPAR) - settings.Iflag &= ^termiosMask(syscall.INPCK) + settings.Cflag &^= syscall.PARENB + settings.Cflag &^= syscall.PARODD + settings.Cflag &^= tcCMSPAR + settings.Iflag &^= syscall.INPCK case OddParity: - settings.Cflag |= termiosMask(syscall.PARENB | syscall.PARODD) - settings.Cflag &= ^termiosMask(tcCMSPAR) - settings.Iflag |= termiosMask(syscall.INPCK) + settings.Cflag |= syscall.PARENB + settings.Cflag |= syscall.PARODD + settings.Cflag &^= tcCMSPAR + settings.Iflag |= syscall.INPCK case EvenParity: - settings.Cflag &= ^termiosMask(syscall.PARODD | tcCMSPAR) - settings.Cflag |= termiosMask(syscall.PARENB) - settings.Iflag |= termiosMask(syscall.INPCK) + settings.Cflag |= syscall.PARENB + settings.Cflag &^= syscall.PARODD + settings.Cflag &^= tcCMSPAR + settings.Iflag |= syscall.INPCK case MarkParity: - settings.Cflag |= termiosMask(syscall.PARENB | syscall.PARODD | tcCMSPAR) - settings.Iflag |= termiosMask(syscall.INPCK) + settings.Cflag |= syscall.PARENB + settings.Cflag |= syscall.PARODD + settings.Cflag |= tcCMSPAR + settings.Iflag |= syscall.INPCK case SpaceParity: - settings.Cflag &= ^termiosMask(syscall.PARODD) - settings.Cflag |= termiosMask(syscall.PARENB | tcCMSPAR) - settings.Iflag |= termiosMask(syscall.INPCK) + settings.Cflag |= syscall.PARENB + settings.Cflag &^= syscall.PARODD + settings.Cflag |= tcCMSPAR + settings.Iflag |= syscall.INPCK } return nil } @@ -189,40 +194,63 @@ func setTermSettingsDataBits(bits int, settings *syscall.Termios) error { if !ok { return &PortError{code: InvalidDataBits} } - settings.Cflag &= ^termiosMask(syscall.CSIZE) - settings.Cflag |= termiosMask(databits) + // Remove previous databits setting + settings.Cflag &^= syscall.CSIZE + // Set requested databits + settings.Cflag |= databits return nil } func setTermSettingsStopBits(bits StopBits, settings *syscall.Termios) error { switch bits { case OneStopBit: - settings.Cflag &= ^termiosMask(syscall.CSTOPB) + settings.Cflag &^= syscall.CSTOPB case OnePointFiveStopBits, TwoStopBits: - settings.Cflag |= termiosMask(syscall.CSTOPB) + settings.Cflag |= syscall.CSTOPB } return nil } func setTermSettingsCtsRts(enable bool, settings *syscall.Termios) { if enable { - settings.Cflag |= termiosMask(tcCRTSCTS) + settings.Cflag |= tcCRTSCTS } else { - settings.Cflag &= ^termiosMask(tcCRTSCTS) + settings.Cflag &^= tcCRTSCTS } } func setRawMode(settings *syscall.Termios) { // Set local mode - settings.Cflag |= termiosMask(syscall.CREAD | syscall.CLOCAL) + settings.Cflag |= syscall.CREAD + settings.Cflag |= syscall.CLOCAL // Set raw mode - settings.Lflag &= ^termiosMask(syscall.ICANON | syscall.ECHO | syscall.ECHOE | syscall.ECHOK | - syscall.ECHONL | syscall.ECHOCTL | syscall.ECHOPRT | syscall.ECHOKE | syscall.ISIG | syscall.IEXTEN) - settings.Iflag &= ^termiosMask(syscall.IXON | syscall.IXOFF | syscall.IXANY | syscall.INPCK | - syscall.IGNPAR | syscall.PARMRK | syscall.ISTRIP | syscall.IGNBRK | syscall.BRKINT | syscall.INLCR | - syscall.IGNCR | syscall.ICRNL | tcIUCLC) - settings.Oflag &= ^termiosMask(syscall.OPOST) + settings.Lflag &^= syscall.ICANON + settings.Lflag &^= syscall.ECHO + settings.Lflag &^= syscall.ECHOE + settings.Lflag &^= syscall.ECHOK + settings.Lflag &^= syscall.ECHONL + settings.Lflag &^= syscall.ECHOCTL + settings.Lflag &^= syscall.ECHOPRT + settings.Lflag &^= syscall.ECHOKE + settings.Lflag &^= syscall.ISIG + settings.Lflag &^= syscall.IEXTEN + + settings.Iflag &^= syscall.IXON + settings.Iflag &^= syscall.IXOFF + settings.Iflag &^= syscall.IXANY + settings.Iflag &^= syscall.INPCK + settings.Iflag &^= syscall.IGNPAR + settings.Iflag &^= syscall.PARMRK + settings.Iflag &^= syscall.ISTRIP + settings.Iflag &^= syscall.IGNBRK + settings.Iflag &^= syscall.BRKINT + settings.Iflag &^= syscall.INLCR + settings.Iflag &^= syscall.IGNCR + settings.Iflag &^= syscall.ICRNL + settings.Iflag &^= tcIUCLC + + settings.Oflag &^= syscall.OPOST // Block reads until at least one char is available (no timeout) settings.Cc[syscall.VMIN] = 1