summaryrefslogtreecommitdiffhomepage
path: root/pkg
diff options
context:
space:
mode:
Diffstat (limited to 'pkg')
-rw-r--r--pkg/metric/metric.go54
-rw-r--r--pkg/sentry/socket/epsocket/BUILD1
-rw-r--r--pkg/sentry/socket/epsocket/epsocket.go38
3 files changed, 78 insertions, 15 deletions
diff --git a/pkg/metric/metric.go b/pkg/metric/metric.go
index 0743612f0..763cd6bc2 100644
--- a/pkg/metric/metric.go
+++ b/pkg/metric/metric.go
@@ -48,9 +48,6 @@ var (
// TODO: Support metric fields.
//
type Uint64Metric struct {
- // metadata describes the metric. It is immutable.
- metadata *pb.MetricMetadata
-
// value is the actual value of the metric. It must be accessed
// atomically.
value uint64
@@ -101,24 +98,35 @@ func Disable() {
}
}
-// NewUint64Metric creates a new metric with the given name.
+type customUint64Metric struct {
+ // metadata describes the metric. It is immutable.
+ metadata *pb.MetricMetadata
+
+ // value returns the current value of the metric.
+ value func() uint64
+}
+
+// RegisterCustomUint64Metric registers a metric with the given name.
+//
+// Register must only be called at init and will return and error if called
+// after Initialized.
//
-// Metrics must be statically defined (i.e., at startup). NewUint64Metric will
-// return an error if called after Initialized.
+// All metrics must be cumulative, meaning that the return values of value must
+// only increase over time.
//
// Preconditions:
// * name must be globally unique.
// * Initialize/Disable have not been called.
-func NewUint64Metric(name string, sync bool, description string) (*Uint64Metric, error) {
+func RegisterCustomUint64Metric(name string, sync bool, description string, value func() uint64) error {
if initialized {
- return nil, ErrInitializationDone
+ return ErrInitializationDone
}
if _, ok := allMetrics.m[name]; ok {
- return nil, ErrNameInUse
+ return ErrNameInUse
}
- m := &Uint64Metric{
+ allMetrics.m[name] = customUint64Metric{
metadata: &pb.MetricMetadata{
Name: name,
Description: description,
@@ -126,9 +134,25 @@ func NewUint64Metric(name string, sync bool, description string) (*Uint64Metric,
Sync: sync,
Type: pb.MetricMetadata_UINT64,
},
+ value: value,
+ }
+ return nil
+}
+
+// MustRegisterCustomUint64Metric calls RegisterCustomUint64Metric and panics
+// if it returns an error.
+func MustRegisterCustomUint64Metric(name string, sync bool, description string, value func() uint64) {
+ if err := RegisterCustomUint64Metric(name, sync, description, value); err != nil {
+ panic(fmt.Sprintf("Unable to register metric %q: %v", name, err))
}
- allMetrics.m[name] = m
- return m, nil
+}
+
+// NewUint64Metric creates and registers a new metric with the given name.
+//
+// Metrics must be statically defined (i.e., at init).
+func NewUint64Metric(name string, sync bool, description string) (*Uint64Metric, error) {
+ var m Uint64Metric
+ return &m, RegisterCustomUint64Metric(name, sync, description, m.Value)
}
// MustCreateNewUint64Metric calls NewUint64Metric and panics if it returns an
@@ -158,13 +182,13 @@ func (m *Uint64Metric) IncrementBy(v uint64) {
// metricSet holds named metrics.
type metricSet struct {
- m map[string]*Uint64Metric
+ m map[string]customUint64Metric
}
// makeMetricSet returns a new metricSet.
func makeMetricSet() metricSet {
return metricSet{
- m: make(map[string]*Uint64Metric),
+ m: make(map[string]customUint64Metric),
}
}
@@ -172,7 +196,7 @@ func makeMetricSet() metricSet {
func (m *metricSet) Values() metricValues {
vals := make(metricValues)
for k, v := range m.m {
- vals[k] = v.Value()
+ vals[k] = v.value()
}
return vals
}
diff --git a/pkg/sentry/socket/epsocket/BUILD b/pkg/sentry/socket/epsocket/BUILD
index 49af8db85..7f9ea9edc 100644
--- a/pkg/sentry/socket/epsocket/BUILD
+++ b/pkg/sentry/socket/epsocket/BUILD
@@ -19,6 +19,7 @@ go_library(
"//pkg/abi/linux",
"//pkg/binary",
"//pkg/log",
+ "//pkg/metric",
"//pkg/sentry/arch",
"//pkg/sentry/context",
"//pkg/sentry/device",
diff --git a/pkg/sentry/socket/epsocket/epsocket.go b/pkg/sentry/socket/epsocket/epsocket.go
index 550569b4c..c5da18b0e 100644
--- a/pkg/sentry/socket/epsocket/epsocket.go
+++ b/pkg/sentry/socket/epsocket/epsocket.go
@@ -33,6 +33,7 @@ import (
"gvisor.googlesource.com/gvisor/pkg/abi/linux"
"gvisor.googlesource.com/gvisor/pkg/binary"
+ "gvisor.googlesource.com/gvisor/pkg/metric"
"gvisor.googlesource.com/gvisor/pkg/sentry/arch"
"gvisor.googlesource.com/gvisor/pkg/sentry/context"
"gvisor.googlesource.com/gvisor/pkg/sentry/fs"
@@ -53,6 +54,43 @@ import (
"gvisor.googlesource.com/gvisor/pkg/waiter"
)
+func mustCreateMetric(name, description string) *tcpip.StatCounter {
+ var cm tcpip.StatCounter
+ metric.MustRegisterCustomUint64Metric(name, false /* sync */, description, cm.Value)
+ return &cm
+}
+
+// Metrics contains metrics exported by netstack.
+var Metrics = tcpip.Stats{
+ UnknownProtocolRcvdPackets: mustCreateMetric("/netstack/unknown_protocol_received_packets", "Number of packets received by netstack that were for an unknown or unsupported protocol."),
+ MalformedRcvdPackets: mustCreateMetric("/netstack/malformed_received_packets", "Number of packets received by netstack that were deemed malformed."),
+ DroppedPackets: mustCreateMetric("/netstack/dropped_packets", "Number of packets dropped by netstack due to full queues."),
+ IP: tcpip.IPStats{
+ PacketsReceived: mustCreateMetric("/netstack/ip/packets_received", "Total number of IP packets received from the link layer in nic.DeliverNetworkPacket."),
+ InvalidAddressesReceived: mustCreateMetric("/netstack/ip/invalid_addresses_received", "Total number of IP packets received with an unknown or invalid destination address."),
+ PacketsDelivered: mustCreateMetric("/netstack/ip/packets_delivered", "Total number of incoming IP packets that are successfully delivered to the transport layer via HandlePacket."),
+ PacketsSent: mustCreateMetric("/netstack/ip/packets_sent", "Total number of IP packets sent via WritePacket."),
+ OutgoingPacketErrors: mustCreateMetric("/netstack/ip/outgoing_packet_errors", "Total number of IP packets which failed to write to a link-layer endpoint."),
+ },
+ TCP: tcpip.TCPStats{
+ ActiveConnectionOpenings: mustCreateMetric("/netstack/tcp/active_connection_openings", "Number of connections opened successfully via Connect."),
+ PassiveConnectionOpenings: mustCreateMetric("/netstack/tcp/passive_connection_openings", "Number of connections opened successfully via Listen."),
+ FailedConnectionAttempts: mustCreateMetric("/netstack/tcp/failed_connection_attempts", "Number of calls to Connect or Listen (active and passive openings, respectively) that end in an error."),
+ ValidSegmentsReceived: mustCreateMetric("/netstack/tcp/valid_segments_received", "Number of TCP segments received that the transport layer successfully parsed."),
+ InvalidSegmentsReceived: mustCreateMetric("/netstack/tcp/invalid_segments_received", "Number of TCP segments received that the transport layer could not parse."),
+ SegmentsSent: mustCreateMetric("/netstack/tcp/segments_sent", "Number of TCP segments sent."),
+ ResetsSent: mustCreateMetric("/netstack/tcp/resets_sent", "Number of TCP resets sent."),
+ ResetsReceived: mustCreateMetric("/netstack/tcp/resets_received", "Number of TCP resets received."),
+ },
+ UDP: tcpip.UDPStats{
+ PacketsReceived: mustCreateMetric("/netstack/udp/packets_received", "Number of UDP datagrams received via HandlePacket."),
+ UnknownPortErrors: mustCreateMetric("/netstack/udp/unknown_port_errors", "Number of incoming UDP datagrams dropped because they did not have a known destination port."),
+ ReceiveBufferErrors: mustCreateMetric("/netstack/udp/receive_buffer_errors", "Number of incoming UDP datagrams dropped due to the receiving buffer being in an invalid state."),
+ MalformedPacketsReceived: mustCreateMetric("/netstack/udp/malformed_packets_received", "Number of incoming UDP datagrams dropped due to the UDP header being in a malformed state."),
+ PacketsSent: mustCreateMetric("/netstack/udp/packets_sent", "Number of UDP datagrams sent via sendUDP."),
+ },
+}
+
const sizeOfInt32 int = 4
var errStackType = syserr.New("expected but did not receive an epsocket.Stack", linux.EINVAL)