为什么截一张这样的代码图片,是因为程序报错Unix syslog delivery error
起初报这个错误,我也是一脸懵逼,通过Google搜索,找到这段代码
代码意思是:通过网络连接,只要连接成功,就返回
遍历连接方式unixgram
,unix
遍历连接目标 /dev/log
/var/run/syslog
/var/run/log
所有的遍历都尝试后,不成功的,返回错误信息
那么什么是unixgram
unix
, unixpacket
又是什么呢
socket套接字:
基于网络:AF_INET
基于文件: AF_UNIX
Unix套接字,作用于本地进程之间的通信(Unix domain socket) uds 进程之间通信,不需要网络协议栈,
服务端代码例子 s.go
packagemainimport ( "fmt""net""os") funcmain() { os.Remove("/tmp/ee") addr :=&net.UnixAddr{Name: "/tmp/ee", Net: "unix"} unixlisten, err :=net.ListenUnix("unix", addr) iferr!=nil { panic(err) } deferunixlisten.Close() for { unixconn, err :=unixlisten.AcceptUnix() iferr!=nil { continue } gounixWork(unixconn) } } funcunixWork(conn*net.UnixConn) { ipstr :=conn.RemoteAddr() deferconn.Close() fmt.Println(ipstr) varbuf [1024]byten, err :=conn.Read(buf[:]) iferr!=nil { panic(err) } fmt.Printf("%s\n", string(buf[:n])) conn.Write([]byte("hello,world")) }
运行后,会产生一个socket类型文件,客户端进程与服务端进程将通过这个文件进行数据交互
客户端代码 c.go
packagemainimport ( "fmt""net") funcmain() { unixaddr :=&net.UnixAddr{Net: "unix", Name: "/tmp/ee"} conn, err :=net.DialUnix("unix", nil, unixaddr) iferr!=nil { panic(err) } deferconn.Close() conn.Write([]byte("hello,s")) varb [1024]byten, err :=conn.Read(b[:]) iferr!=nil { fmt.Println(err) } fmt.Println(string(b[:n])) }
通过lsof
可以查看到/tmp/ee
被那个进程使用
这下我们大概了解了啥情况,通信使用的,不过没有进入网络层
再来看看三者是啥区别
unix
SOCK_STREAM
tcp
unixgram
SOCK_DGRAM
udp
unixpacket
SOCK_SEQPACKET
这个还没搞清楚
再回到开始的话题,当你看到这个错误syslog delivery error
你可能就秒懂,是因为通过基于文件的套接字连接不上
/dev/log
/var/run/syslog
/var/run/log
这几个文件没有对应的程序去监听它们
我开始也不知道是那些程序会监听这几个文件,不过大概猜测是与日志有关
Linux的日志服务,有syslog,rsyslog,journalctl,索性重启电脑,再通过lsof查看下
如果我把这个服务停止掉,go应用程序某个功能就会出错,报syslog delivery error