@@ -1188,16 +1188,8 @@ func ListPools(ctx context.Context, rpcClient UnaryInvoker, req *ListPoolsReq) (
11881188
11891189type rankFreeSpaceMap map [ranklist.Rank ]uint64
11901190
1191- type filterRankFn func (rank ranklist.Rank ) bool
1192-
1193- func newFilterRankFunc (ranks ranklist.RankList ) filterRankFn {
1194- return func (rank ranklist.Rank ) bool {
1195- return len (ranks ) == 0 || rank .InList (ranks )
1196- }
1197- }
1198-
11991191// Add namespace ranks to rankNVMeFreeSpace map and return minimum free available SCM namespace bytes.
1200- func processSCMSpaceStats (log debugLogger , filterRank filterRankFn , scmNamespaces storage.ScmNamespaces , rankNVMeFreeSpace rankFreeSpaceMap ) (uint64 , error ) {
1192+ func processSCMSpaceStats (log debugLogger , ranks ranklist. RankList , scmNamespaces storage.ScmNamespaces , rankNVMeFreeSpace rankFreeSpaceMap ) (uint64 , error ) {
12011193 scmBytes := uint64 (math .MaxUint64 )
12021194
12031195 // Realistically there should only be one-per-rank but handle the case for multiple anyway.
@@ -1207,7 +1199,7 @@ func processSCMSpaceStats(log debugLogger, filterRank filterRankFn, scmNamespace
12071199 scmNamespace .UUID , scmNamespace .BlockDevice , scmNamespace .Name )
12081200 }
12091201
1210- if ! filterRank ( scmNamespace .Mount .Rank ) {
1202+ if ! scmNamespace .Mount .Rank . InList ( ranks ) {
12111203 log .Debugf ("Skipping SCM device %s (bdev %s, name %s, rank %d) not in ranklist" ,
12121204 scmNamespace .UUID , scmNamespace .BlockDevice , scmNamespace .Name ,
12131205 scmNamespace .Mount .Rank )
@@ -1233,7 +1225,7 @@ func processSCMSpaceStats(log debugLogger, filterRank filterRankFn, scmNamespace
12331225}
12341226
12351227// Add NVMe free bytes to rankNVMeFreeSpace map.
1236- func processNVMeSpaceStats (log debugLogger , filterRank filterRankFn , nvmeControllers storage.NvmeControllers , rankNVMeFreeSpace rankFreeSpaceMap ) error {
1228+ func processNVMeSpaceStats (log debugLogger , ranks ranklist. RankList , nvmeControllers storage.NvmeControllers , rankNVMeFreeSpace rankFreeSpaceMap ) error {
12371229 for _ , controller := range nvmeControllers {
12381230 for _ , smdDevice := range controller .SmdDevices {
12391231 msgDev := fmt .Sprintf ("SMD device %s (rank %d, ctrlr %s" , smdDevice .UUID ,
@@ -1258,7 +1250,7 @@ func processNVMeSpaceStats(log debugLogger, filterRank filterRankFn, nvmeControl
12581250 controller .NvmeState .String ())
12591251 }
12601252
1261- if ! filterRank ( smdDevice .Rank ) {
1253+ if ! smdDevice .Rank . InList ( ranks ) {
12621254 log .Debugf ("Skipping %s, not in ranklist" , msgDev )
12631255 continue
12641256 }
@@ -1288,10 +1280,34 @@ func getMaxPoolSize(ctx context.Context, rpcClient UnaryInvoker, createReq *Pool
12881280 return 0 , 0 , errors .New ("invalid mem-ratio, should not be greater than one" )
12891281 }
12901282
1291- // Verify that the DAOS system is ready before attempting to query storage.
1292- if _ , err := SystemQuery (ctx , rpcClient , & SystemQueryReq {}); err != nil {
1293- return 0 , 0 , err
1283+ // Verify that the DAOS system is ready before attempting to query storage and record joined.
1284+ queryResp , err := SystemQuery (ctx , rpcClient , & SystemQueryReq {})
1285+ if err != nil {
1286+ return 0 , 0 , errors .Wrap (err , "getMaxPoolSize: SystemQuery" )
1287+ }
1288+ joinedRanks := ranklist.RankList {}
1289+ for _ , member := range queryResp .Members {
1290+ if member .State == system .MemberStateJoined {
1291+ joinedRanks = append (joinedRanks , member .Rank )
1292+ }
1293+ }
1294+
1295+ // Refuse if any requested ranks are not joined, update ranklist to contain only joined ranks.
1296+ filterRanks := ranklist.RankList {}
1297+ if len (createReq .Ranks ) == 0 {
1298+ filterRanks = joinedRanks
1299+ } else {
1300+ for _ , rank := range createReq .Ranks {
1301+ if ! rank .InList (joinedRanks ) {
1302+ return 0 , 0 , errors .Errorf ("specified rank %d is not joined" , rank )
1303+ }
1304+ filterRanks = append (filterRanks , rank )
1305+ }
12941306 }
1307+ slices .Sort (filterRanks )
1308+ rpcClient .Debugf ("requested/joined/filter ranks: %v/%v/%v" , createReq .Ranks , joinedRanks ,
1309+ filterRanks )
1310+ createReq .Ranks = filterRanks
12951311
12961312 scanReq := & StorageScanReq {
12971313 Usage : true ,
@@ -1307,8 +1323,6 @@ func getMaxPoolSize(ctx context.Context, rpcClient UnaryInvoker, createReq *Pool
13071323 return 0 , 0 , errors .New ("Empty host storage response from StorageScan" )
13081324 }
13091325
1310- // Generate function to verify a rank is in the provided rank slice.
1311- filterRank := newFilterRankFunc (ranklist .RankList (createReq .Ranks ))
13121326 rankNVMeFreeSpace := make (rankFreeSpaceMap )
13131327 scmBytes := uint64 (math .MaxUint64 )
13141328 for _ , key := range scanResp .HostStorage .Keys () {
@@ -1319,7 +1333,7 @@ func getMaxPoolSize(ctx context.Context, rpcClient UnaryInvoker, createReq *Pool
13191333 scanResp .HostStorage [key ].HostSet .String ())
13201334 }
13211335
1322- sb , err := processSCMSpaceStats (rpcClient , filterRank , hostStorage .ScmNamespaces , rankNVMeFreeSpace )
1336+ sb , err := processSCMSpaceStats (rpcClient , filterRanks , hostStorage .ScmNamespaces , rankNVMeFreeSpace )
13231337 if err != nil {
13241338 return 0 , 0 , err
13251339 }
@@ -1328,7 +1342,7 @@ func getMaxPoolSize(ctx context.Context, rpcClient UnaryInvoker, createReq *Pool
13281342 scmBytes = sb
13291343 }
13301344
1331- if err := processNVMeSpaceStats (rpcClient , filterRank , hostStorage .NvmeDevices , rankNVMeFreeSpace ); err != nil {
1345+ if err := processNVMeSpaceStats (rpcClient , filterRanks , hostStorage .NvmeDevices , rankNVMeFreeSpace ); err != nil {
13321346 return 0 , 0 , err
13331347 }
13341348 }
0 commit comments