@@ -50,11 +50,11 @@ func singleNUMAContainerLevelHandler(lh logr.Logger, pod *v1.Pod, info *filterIn
50
50
clh := lh .WithValues (logging .KeyContainer , initContainer .Name , logging .KeyContainerKind , cntKind )
51
51
clh .V (6 ).Info ("desired resources" , stringify .ResourceListToLoggable (initContainer .Resources .Requests )... )
52
52
53
- _ , match := resourcesAvailableInAnyNUMANodes (clh , info , initContainer .Resources .Requests )
53
+ _ , match , reason := resourcesAvailableInAnyNUMANodes (clh , info , initContainer .Resources .Requests )
54
54
if ! match {
55
55
msg := "cannot align " + cntKind + " container"
56
56
// we can't align init container, so definitely we can't align a pod
57
- clh .V (2 ).Info (msg )
57
+ clh .V (2 ).Info (msg , "reason" , reason )
58
58
return framework .NewStatus (framework .Unschedulable , msg )
59
59
}
60
60
}
@@ -63,10 +63,10 @@ func singleNUMAContainerLevelHandler(lh logr.Logger, pod *v1.Pod, info *filterIn
63
63
clh := lh .WithValues (logging .KeyContainer , container .Name , logging .KeyContainerKind , logging .KindContainerApp )
64
64
clh .V (6 ).Info ("container requests" , stringify .ResourceListToLoggable (container .Resources .Requests )... )
65
65
66
- numaID , match := resourcesAvailableInAnyNUMANodes (clh , info , container .Resources .Requests )
66
+ numaID , match , reason := resourcesAvailableInAnyNUMANodes (clh , info , container .Resources .Requests )
67
67
if ! match {
68
68
// we can't align container, so definitely we can't align a pod
69
- clh .V (2 ).Info ("cannot align container" )
69
+ clh .V (2 ).Info ("cannot align container" , "reason" , reason )
70
70
return framework .NewStatus (framework .Unschedulable , "cannot align container" )
71
71
}
72
72
@@ -84,7 +84,7 @@ func singleNUMAContainerLevelHandler(lh logr.Logger, pod *v1.Pod, info *filterIn
84
84
85
85
// resourcesAvailableInAnyNUMANodes checks for sufficient resource and return the NUMAID that would be selected by Kubelet.
86
86
// this function requires NUMANodeList with properly populated NUMANode, NUMAID should be in range 0-63
87
- func resourcesAvailableInAnyNUMANodes (lh logr.Logger , info * filterInfo , resources v1.ResourceList ) (int , bool ) {
87
+ func resourcesAvailableInAnyNUMANodes (lh logr.Logger , info * filterInfo , resources v1.ResourceList ) (int , bool , string ) {
88
88
numaID := highestNUMAID
89
89
bitmask := bm .NewEmptyBitMask ()
90
90
// set all bits, each bit is a NUMA node, if resources couldn't be aligned
@@ -94,50 +94,54 @@ func resourcesAvailableInAnyNUMANodes(lh logr.Logger, info *filterInfo, resource
94
94
nodeResources := util .ResourceList (info .node .Allocatable )
95
95
96
96
for resource , quantity := range resources {
97
+ clh := lh .WithValues ("resource" , resource )
97
98
if quantity .IsZero () {
98
99
// why bother? everything's fine from the perspective of this resource
99
- lh .V (4 ).Info ("ignoring zero-qty resource request" , "resource" , resource )
100
+ clh .V (4 ).Info ("ignoring zero-qty resource request" )
100
101
continue
101
102
}
102
103
103
104
if _ , ok := nodeResources [resource ]; ! ok {
104
105
// some resources may not expose NUMA affinity (device plugins, extended resources), but all resources
105
106
// must be reported at node level; thus, if they are not present at node level, we can safely assume
106
107
// we don't have the resource at all.
107
- lh .V (2 ).Info ("early verdict: cannot meet request" , "resource" , resource , "suitable" , "false " )
108
- return numaID , false
108
+ clh .V (2 ).Info ("early verdict: cannot meet request" )
109
+ return - 1 , false , string ( resource )
109
110
}
110
111
111
112
// for each requested resource, calculate which NUMA slots are good fits, and then AND with the aggregated bitmask, IOW unset appropriate bit if we can't align resources, or set it
112
113
// obvious, bits which are not in the NUMA id's range would be unset
113
114
hasNUMAAffinity := false
114
115
resourceBitmask := bm .NewEmptyBitMask ()
115
116
for _ , numaNode := range info .numaNodes {
117
+ nlh := clh .WithValues ("numaCell" , numaNode .NUMAID )
116
118
numaQuantity , ok := numaNode .Resources [resource ]
117
119
if ! ok {
120
+ nlh .V (6 ).Info ("missing" )
118
121
continue
119
122
}
120
123
121
124
hasNUMAAffinity = true
122
125
if ! isResourceSetSuitable (info .qos , resource , quantity , numaQuantity ) {
126
+ nlh .V (6 ).Info ("discarded" , "quantity" , quantity .String (), "numaQuantity" , numaQuantity .String ())
123
127
continue
124
128
}
125
129
126
130
resourceBitmask .Add (numaNode .NUMAID )
127
- lh .V (6 ).Info ("feasible" , "numaCell" , numaNode . NUMAID , "resource" , resource )
131
+ nlh .V (6 ).Info ("feasible" )
128
132
}
129
133
130
134
// non-native resources or ephemeral-storage may not expose NUMA affinity,
131
135
// but since they are available at node level, this is fine
132
136
if ! hasNUMAAffinity && isHostLevelResource (resource ) {
133
- lh .V (6 ).Info ("resource available at host level (no NUMA affinity)" , "resource" , resource )
137
+ clh .V (6 ).Info ("resource available at host level (no NUMA affinity)" )
134
138
continue
135
139
}
136
140
137
141
bitmask .And (resourceBitmask )
138
142
if bitmask .IsEmpty () {
139
- lh .V (2 ).Info ("early verdict" , "resource" , resource , "suitable" , "false " )
140
- return numaID , false
143
+ lh .V (2 ).Info ("early verdict: cannot find affinity " )
144
+ return numaID , false , string ( resource )
141
145
}
142
146
}
143
147
// according to TopologyManager, the preferred NUMA affinity, is the narrowest one.
@@ -149,16 +153,16 @@ func resourcesAvailableInAnyNUMANodes(lh logr.Logger, info *filterInfo, resource
149
153
// at least one NUMA node is available
150
154
ret := ! bitmask .IsEmpty ()
151
155
lh .V (2 ).Info ("final verdict" , "suitable" , ret , "numaCell" , numaID )
152
- return numaID , ret
156
+ return numaID , ret , "generic"
153
157
}
154
158
155
159
func singleNUMAPodLevelHandler (lh logr.Logger , pod * v1.Pod , info * filterInfo ) * framework.Status {
156
160
resources := util .GetPodEffectiveRequest (pod )
157
161
lh .V (6 ).Info ("pod desired resources" , stringify .ResourceListToLoggable (resources )... )
158
162
159
- numaID , match := resourcesAvailableInAnyNUMANodes (lh , info , resources )
163
+ numaID , match , reason := resourcesAvailableInAnyNUMANodes (lh , info , resources )
160
164
if ! match {
161
- lh .V (2 ).Info ("cannot align pod" , "name" , pod .Name )
165
+ lh .V (2 ).Info ("cannot align pod" , "name" , pod .Name , "reason" , reason )
162
166
return framework .NewStatus (framework .Unschedulable , "cannot align pod" )
163
167
}
164
168
lh .V (4 ).Info ("all container placed" , "numaCell" , numaID )
0 commit comments