Convert hcsshim's stats to cgroups' stats
Since hcsshim still uses containerd/cgroups 1.x which uses
gogo/protobuf.
@@ -24,15 +24,16 @@ import (
"text/tabwriter"
wstats "github.com/Microsoft/hcsshim/cmd/containerd-shim-runhcs-v1/stats"
- v1 "github.com/containerd/cgroups/stats/v1"
- v2 "github.com/containerd/cgroups/v2/stats"
+ v1 "github.com/containerd/cgroups/v3/cgroup1/stats"
+ v2 "github.com/containerd/cgroups/v3/cgroup2/stats"
"github.com/containerd/containerd/cmd/ctr/commands"
+ "github.com/containerd/containerd/protobuf/proto"
"github.com/containerd/typeurl"
"github.com/urfave/cli"
)
func init() {
- // metricsCommand is only added on Linux as github.com/containerd/cgroups
+ // metricsCommand is only added on Linux as github.com/containerd/cgroups/v3
// does not compile on darwin or windows
Command.Subcommands = append(Command.Subcommands, metricsCommand)
}
@@ -103,14 +104,9 @@ var metricsCommand = cli.Command{
} else if data2 != nil {
printCgroup2MetricsTable(w, data2)
} else {
- if windowsStats.GetLinux() != nil {
- printCgroupMetricsTable(w, windowsStats.GetLinux())
- } else if windowsStats.GetWindows() != nil {
- printWindowsContainerStatistics(w, windowsStats.GetWindows())
- }
- // Print VM stats if its isolated
- if windowsStats.VM != nil {
- printWindowsVMStatistics(w, windowsStats.VM)
+ err := printWindowsStats(w, windowsStats)
+ if err != nil {
+ return fmt.Errorf("cannot convert metrics data from windows.Statistics: %w", err)
}
}
return w.Flush()
@@ -166,6 +162,34 @@ func printCgroup2MetricsTable(w *tabwriter.Writer, data *v2.Metrics) {
}
}
+func printWindowsStats(w *tabwriter.Writer, windowsStats *wstats.Statistics) error {
+ if windowsStats.GetLinux() != nil {
+ var stats v1.Metrics
+
+ // It cannot be casted to v1.Metrics since windowsStats is still generated by gogo/protobuf.
+ linux := windowsStats.GetLinux()
+
+ // But Marshal/Unmarshal works because the underlying protobuf message is compatible.
+ data, err := linux.Marshal()
+ if err != nil {
+ return err
+ }
+ err = proto.Unmarshal(data, &stats)
+ if err != nil {
+ return err
+ }
+
+ printCgroupMetricsTable(w, &stats)
+ } else if windowsStats.GetWindows() != nil {
+ printWindowsContainerStatistics(w, windowsStats.GetWindows())
+ }
+ // Print VM stats if its isolated
+ if windowsStats.VM != nil {
+ printWindowsVMStatistics(w, windowsStats.VM)
+ }
+ return nil
+}
+
func printWindowsContainerStatistics(w *tabwriter.Writer, stats *wstats.WindowsContainerStatistics) {
fmt.Fprintf(w, "METRIC\tVALUE\t\n")
fmt.Fprintf(w, "timestamp\t%s\t\n", stats.Timestamp)
