33// you may not use this file except in compliance with the License.
44// You may obtain a copy of the License at
55//
6- // http://www.apache.org/licenses/LICENSE-2.0
6+ // http://www.apache.org/licenses/LICENSE-2.0
77//
88// Unless required by applicable law or agreed to in writing, software
99// distributed under the License is distributed on an "AS IS" BASIS,
1717package collector
1818
1919import (
20- "errors"
21- "fmt"
22- "log/slog"
23- "unsafe"
20+ "fmt"
21+ "log/slog"
22+ "unsafe"
2423
25- "github.com/prometheus/client_golang/prometheus"
26- "golang.org/x/sys/unix"
24+ "github.com/prometheus/client_golang/prometheus"
25+ "golang.org/x/sys/unix"
2726)
2827
2928/*
@@ -33,76 +32,166 @@ import (
3332#include <netinet/tcp.h>
3433#include <netinet/tcp_var.h>
3534#include <netinet/udp.h>
35+ #include <netinet/udp_var.h>
3636*/
3737import "C"
3838
3939var (
40- bsdNetstatTcpSendPacketsTotal = prometheus .NewDesc (
41- prometheus .BuildFQName (namespace , "netstat" , "tcp_transmit_packets_total" ),
42- "TCP packets sent" ,
43- nil , nil ,
44- )
45-
46- bsdNetstatTcpRecvPacketsTotal = prometheus .NewDesc (
47- prometheus .BuildFQName (namespace , "netstat" , "tcp_receive_packets_total" ),
48- "TCP packets received" ,
49- nil , nil ,
50- )
40+ // TCP metrics
41+ bsdNetstatTcpSendPacketsTotal = prometheus .NewDesc (
42+ prometheus .BuildFQName (namespace , "netstat" , "tcp_transmit_packets_total" ),
43+ "TCP packets sent" ,
44+ nil , nil ,
45+ )
46+ bsdNetstatTcpRecvPacketsTotal = prometheus .NewDesc (
47+ prometheus .BuildFQName (namespace , "netstat" , "tcp_receive_packets_total" ),
48+ "TCP packets received" ,
49+ nil , nil ,
50+ )
51+ bsdNetstatTcpConnectionAttempts = prometheus .NewDesc (
52+ prometheus .BuildFQName (namespace , "netstat" , "tcp_connection_attempts_total" ),
53+ "Number of times TCP connections have been initiated" ,
54+ nil , nil ,
55+ )
56+ bsdNetstatTcpConnectionAccepts = prometheus .NewDesc (
57+ prometheus .BuildFQName (namespace , "netstat" , "tcp_connection_accepts_total" ),
58+ "Number of times TCP connections have made it to established state" ,
59+ nil , nil ,
60+ )
61+ bsdNetstatTcpConnectionDrops = prometheus .NewDesc (
62+ prometheus .BuildFQName (namespace , "netstat" , "tcp_connection_drops_total" ),
63+ "Number of dropped TCP connections" ,
64+ nil , nil ,
65+ )
66+ bsdNetstatTcpRetransmitPackets = prometheus .NewDesc (
67+ prometheus .BuildFQName (namespace , "netstat" , "tcp_retransmit_packets_total" ),
68+ "Number of TCP data packets retransmitted" ,
69+ nil , nil ,
70+ )
71+ // UDP metrics
72+ bsdNetstatUdpSendPacketsTotal = prometheus .NewDesc (
73+ prometheus .BuildFQName (namespace , "netstat" , "udp_transmit_packets_total" ),
74+ "UDP packets sent" ,
75+ nil , nil ,
76+ )
77+ bsdNetstatUdpRecvPacketsTotal = prometheus .NewDesc (
78+ prometheus .BuildFQName (namespace , "netstat" , "udp_receive_packets_total" ),
79+ "UDP packets received" ,
80+ nil , nil ,
81+ )
82+ bsdNetstatUdpHeaderDrops = prometheus .NewDesc (
83+ prometheus .BuildFQName (namespace , "netstat" , "udp_header_drops_total" ),
84+ "Number of UDP packets dropped due to invalid header" ,
85+ nil , nil ,
86+ )
87+ bsdNetstatUdpBadChecksum = prometheus .NewDesc (
88+ prometheus .BuildFQName (namespace , "netstat" , "udp_bad_checksum_total" ),
89+ "Number of UDP packets dropped due to bad checksum" ,
90+ nil , nil ,
91+ )
92+ bsdNetstatUdpNoPort = prometheus .NewDesc (
93+ prometheus .BuildFQName (namespace , "netstat" , "udp_no_port_total" ),
94+ "Number of UDP packets to port with no listener" ,
95+ nil , nil ,
96+ )
5197)
5298
5399type netStatCollector struct {
54- netStatMetric * prometheus.Desc
100+ netStatMetric * prometheus.Desc
55101}
56102
57103func init () {
58- registerCollector ("netstat" , defaultEnabled , NewNetStatCollector )
104+ registerCollector ("netstat" , defaultEnabled , NewNetStatCollector )
59105}
60106
61107func NewNetStatCollector (logger * slog.Logger ) (Collector , error ) {
62- return & netStatCollector {}, nil
108+ return & netStatCollector {}, nil
63109}
64110
65111func (c * netStatCollector ) Describe (ch chan <- * prometheus.Desc ) {
66- ch <- c .netStatMetric
112+ ch <- c .netStatMetric
67113}
68114
69115func (c * netStatCollector ) Collect (ch chan <- prometheus.Metric ) {
70- _ = c .Update (ch )
116+ _ = c .Update (ch )
71117}
72118
73119func getData (queryString string ) ([]byte , error ) {
74- data , err := unix .SysctlRaw (queryString )
75- if err != nil {
76- fmt .Println ("Error:" , err )
77- return nil , err
78- }
79-
80- if len (data ) < int (unsafe .Sizeof (C.struct_tcpstat {})) {
81- return nil , errors .New ("Data Size mismatch" )
82- }
83- return data , nil
120+ data , err := unix .SysctlRaw (queryString )
121+ if err != nil {
122+ fmt .Println ("Error:" , err )
123+ return nil , err
124+ }
125+ return data , nil
84126}
85127
86128func (c * netStatCollector ) Update (ch chan <- prometheus.Metric ) error {
87-
88- tcpData , err := getData ("net.inet.tcp.stats" )
89- if err != nil {
90- return err
91- }
92-
93- tcpStats := * (* C .struct_tcpstat )(unsafe .Pointer (& tcpData [0 ]))
94-
95- ch <- prometheus .MustNewConstMetric (
96- bsdNetstatTcpSendPacketsTotal ,
97- prometheus .CounterValue ,
98- float64 (tcpStats .tcps_sndtotal ),
99- )
100-
101- ch <- prometheus .MustNewConstMetric (
102- bsdNetstatTcpRecvPacketsTotal ,
103- prometheus .CounterValue ,
104- float64 (tcpStats .tcps_rcvtotal ),
105- )
106-
107- return nil
129+ tcpData , err := getData ("net.inet.tcp.stats" )
130+ if err == nil && len (tcpData ) >= int (unsafe .Sizeof (C.struct_tcpstat {})) {
131+ tcpStats := * (* C .struct_tcpstat )(unsafe .Pointer (& tcpData [0 ]))
132+
133+ ch <- prometheus .MustNewConstMetric (
134+ bsdNetstatTcpSendPacketsTotal ,
135+ prometheus .CounterValue ,
136+ float64 (tcpStats .tcps_sndtotal ),
137+ )
138+ ch <- prometheus .MustNewConstMetric (
139+ bsdNetstatTcpRecvPacketsTotal ,
140+ prometheus .CounterValue ,
141+ float64 (tcpStats .tcps_rcvtotal ),
142+ )
143+ ch <- prometheus .MustNewConstMetric (
144+ bsdNetstatTcpConnectionAttempts ,
145+ prometheus .CounterValue ,
146+ float64 (tcpStats .tcps_connattempt ),
147+ )
148+ ch <- prometheus .MustNewConstMetric (
149+ bsdNetstatTcpConnectionAccepts ,
150+ prometheus .CounterValue ,
151+ float64 (tcpStats .tcps_accepts ),
152+ )
153+ ch <- prometheus .MustNewConstMetric (
154+ bsdNetstatTcpConnectionDrops ,
155+ prometheus .CounterValue ,
156+ float64 (tcpStats .tcps_drops ),
157+ )
158+ ch <- prometheus .MustNewConstMetric (
159+ bsdNetstatTcpRetransmitPackets ,
160+ prometheus .CounterValue ,
161+ float64 (tcpStats .tcps_sndrexmitpack ),
162+ )
163+ }
164+
165+ udpData , err := getData ("net.inet.udp.stats" )
166+ if err == nil && len (udpData ) >= int (unsafe .Sizeof (C.struct_udpstat {})) {
167+ udpStats := * (* C .struct_udpstat )(unsafe .Pointer (& udpData [0 ]))
168+
169+ ch <- prometheus .MustNewConstMetric (
170+ bsdNetstatUdpSendPacketsTotal ,
171+ prometheus .CounterValue ,
172+ float64 (udpStats .udps_opackets ),
173+ )
174+ ch <- prometheus .MustNewConstMetric (
175+ bsdNetstatUdpRecvPacketsTotal ,
176+ prometheus .CounterValue ,
177+ float64 (udpStats .udps_ipackets ),
178+ )
179+ ch <- prometheus .MustNewConstMetric (
180+ bsdNetstatUdpHeaderDrops ,
181+ prometheus .CounterValue ,
182+ float64 (udpStats .udps_hdrops ),
183+ )
184+ ch <- prometheus .MustNewConstMetric (
185+ bsdNetstatUdpBadChecksum ,
186+ prometheus .CounterValue ,
187+ float64 (udpStats .udps_badsum ),
188+ )
189+ ch <- prometheus .MustNewConstMetric (
190+ bsdNetstatUdpNoPort ,
191+ prometheus .CounterValue ,
192+ float64 (udpStats .udps_noport ),
193+ )
194+ }
195+
196+ return nil
108197}
0 commit comments