代码拉取完成,页面将自动刷新
package serialer
import (
"errors"
"io"
"log"
"runtime"
"strings"
"sync"
"time"
"gitee.com/haodreams/golib/logs"
)
// Serial 串口
type Serial struct {
Connect string
conn io.ReadWriteCloser
buf SafeBuffer
err error
lock *sync.RWMutex
HaveRecv bool //是否开启数据接收线程
isRunning bool
eventChan chan byte
}
const (
//ConvertString 默认的转换字符串
ConvertString = "/dev/ttyO"
)
// Closed 串口是否已经关闭
func (s *Serial) Closed() bool {
return !s.isRunning
}
// Setup 设置
func (s *Serial) Setup() (err error) {
s.lock = new(sync.RWMutex)
s.eventChan = make(chan byte, 30)
if len(s.Connect) > 3 {
if runtime.GOOS != "windows" {
ss := strings.ToUpper(s.Connect[:3])
if ss == "COM" {
s.Connect = ConvertString + s.Connect[3:]
}
}
}
_, _, _, _, _, _, err = FormatOption(s.Connect)
s.HaveRecv = true
return
}
func (s *Serial) read() {
buf := make([]byte, 1024)
logs.Info(s.Connect, "Start receive data")
for s.isRunning {
s.lock.RLock()
if s.conn == nil {
s.lock.RUnlock()
break
}
n, err := s.conn.Read(buf)
s.lock.RUnlock()
if err != nil {
if err.Error() != "EOF" {
s.err = err
log.Println(err)
time.Sleep(time.Second)
continue
}
}
if n > 0 {
logs.Debug("R: % 02X", buf[:n])
if s.buf.Len() > 8192 {
//s.buf.Reset()
s.buf.RemoveHead4K()
}
s.buf.Write(buf[:n])
s.eventChan <- 1
}
time.Sleep(time.Millisecond * 10)
}
logs.Info(s.Connect, "Stop receive data.")
}
// Open 打开
func (s *Serial) Open() (err error) {
logs.Info("Open serial:", s.Connect)
s.lock.Lock()
defer s.lock.Unlock()
s.conn, err = Open(s.Connect)
if err != nil {
return
}
if s.conn == nil {
err = errors.New("Open faied")
return
}
s.buf.Reset()
s.err = nil
s.isRunning = true
if s.HaveRecv {
go s.read()
}
return
}
// Close 关闭
func (s *Serial) Close() (err error) {
if s.conn != nil {
logs.Info("Close serial:", s.Connect)
err = s.conn.Close()
s.lock.Lock()
s.conn = nil
s.lock.Unlock()
}
s.isRunning = false
//log.Println("============close")
return
}
// Write 写数据
func (s *Serial) Write(p []byte) (n int, err error) {
if s.conn == nil {
err = errors.New("Not connected")
return
}
n, err = s.conn.Write(p)
if err == nil && n > 0 {
logs.Debug("S: % 02X", p[:n])
}
return
}
// Read 读数据
func (s *Serial) Read(p []byte) (n int, err error) {
//清空事件
numEvent := len(s.eventChan)
for ; numEvent > 0; numEvent-- {
<-s.eventChan
}
if s.conn == nil {
err = errors.New("Not connected")
return
}
if s.err != nil {
return 0, s.err
}
if s.buf.Len() > 0 {
n, err = s.buf.Read(p)
if err != nil {
return
}
if err == nil && n > 0 {
//logs.Info("R: % 02X", p[:n])
}
return
}
select {
case <-time.After(time.Second):
// err = errors.New("timeout")
return
case <-s.eventChan:
n, err = s.buf.Read(p)
if err != nil {
if err.Error() == "EOF" {
err = nil
}
//log.Println(err)
return
}
}
if err == nil && n > 0 {
//logs.Info("R: % 02X", p[:n])
}
return
}
// Len 获取buf 数据的长度
func (s *Serial) Len() int {
return s.buf.Len()
}
// Reset 清空数据
func (s *Serial) Reset() {
//logs.Debug("reset bufer")
s.buf.Reset()
}
此处可能存在不合适展示的内容,页面不予展示。您可通过相关编辑功能自查并修改。
如您确认内容无涉及 不当用语 / 纯广告导流 / 暴力 / 低俗色情 / 侵权 / 盗版 / 虚假 / 无价值内容或违法国家有关法律法规的内容,可点击提交进行申诉,我们将尽快为您处理。