IterateUnreferencedPacks returns the list of unreferenced storage blobs.
(ctx context.Context, blobPrefixes []blob.ID, parallelism int, callback func(blob.Metadata) error)
| 227 | |
| 228 | // IterateUnreferencedPacks returns the list of unreferenced storage blobs. |
| 229 | func (bm *WriteManager) IterateUnreferencedPacks(ctx context.Context, blobPrefixes []blob.ID, parallelism int, callback func(blob.Metadata) error) error { |
| 230 | usedPacks, err := bigmap.NewSet(ctx) |
| 231 | if err != nil { |
| 232 | return errors.Wrap(err, "new set") |
| 233 | } |
| 234 | |
| 235 | defer usedPacks.Close(ctx) |
| 236 | |
| 237 | contentlog.Log(ctx, bm.log, "determining blobs in use") |
| 238 | // find packs in use |
| 239 | if err := bm.IteratePacks( |
| 240 | ctx, |
| 241 | IteratePackOptions{ |
| 242 | Prefixes: blobPrefixes, |
| 243 | IncludePacksWithOnlyDeletedContent: true, |
| 244 | }, |
| 245 | func(pi PackInfo) error { |
| 246 | if pi.ContentCount > 0 { |
| 247 | usedPacks.Put(ctx, []byte(pi.PackID)) |
| 248 | } |
| 249 | return nil |
| 250 | }); err != nil { |
| 251 | return errors.Wrap(err, "error iterating packs") |
| 252 | } |
| 253 | |
| 254 | if len(blobPrefixes) == 0 { |
| 255 | blobPrefixes = PackBlobIDPrefixes |
| 256 | } |
| 257 | |
| 258 | var prefixes []blob.ID |
| 259 | |
| 260 | if parallelism <= len(blobPrefixes) { |
| 261 | prefixes = append(prefixes, blobPrefixes...) |
| 262 | } else { |
| 263 | // iterate {p,q}[0-9,a-f] |
| 264 | for _, prefix := range blobPrefixes { |
| 265 | for hexDigit := range 16 { |
| 266 | prefixes = append(prefixes, blob.ID(fmt.Sprintf("%v%x", prefix, hexDigit))) |
| 267 | } |
| 268 | } |
| 269 | } |
| 270 | |
| 271 | contentlog.Log1(ctx, bm.log, "scanning prefixes", |
| 272 | blobparam.BlobIDList("prefixes", prefixes)) |
| 273 | |
| 274 | var unusedCount atomic.Int32 |
| 275 | |
| 276 | if err := blob.IterateAllPrefixesInParallel(ctx, parallelism, bm.st, prefixes, |
| 277 | func(bm blob.Metadata) error { |
| 278 | if usedPacks.Contains([]byte(bm.BlobID)) { |
| 279 | return nil |
| 280 | } |
| 281 | |
| 282 | unusedCount.Add(1) |
| 283 | |
| 284 | return callback(bm) |
| 285 | }); err != nil { |
| 286 | return errors.Wrap(err, "error iterating blobs") |