func()

in container/raw/watcher.go [117:174]


func (w *rawContainerWatcher) watchDirectory(events chan watcher.ContainerEvent, dir string, containerName string) (bool, error) {
	// Don't watch .mount cgroups because they never have containers as sub-cgroups.  A single container
	// can have many .mount cgroups associated with it which can quickly exhaust the inotify watches on a node.
	if strings.HasSuffix(containerName, ".mount") {
		return false, nil
	}
	alreadyWatching, err := w.watcher.AddWatch(containerName, dir)
	if err != nil {
		return alreadyWatching, err
	}

	// Remove the watch if further operations failed.
	cleanup := true
	defer func() {
		if cleanup {
			_, err := w.watcher.RemoveWatch(containerName, dir)
			if err != nil {
				klog.Warningf("Failed to remove inotify watch for %q: %v", dir, err)
			}
		}
	}()

	// TODO(vmarmol): We should re-do this once we're done to ensure directories were not added in the meantime.
	// Watch subdirectories as well.
	entries, err := os.ReadDir(dir)
	if err != nil {
		return alreadyWatching, err
	}
	for _, entry := range entries {
		if entry.IsDir() {
			entryPath := path.Join(dir, entry.Name())
			subcontainerName := path.Join(containerName, entry.Name())
			alreadyWatchingSubDir, err := w.watchDirectory(events, entryPath, subcontainerName)
			if err != nil {
				klog.Errorf("Failed to watch directory %q: %v", entryPath, err)
				if os.IsNotExist(err) {
					// The directory may have been removed before watching. Try to watch the other
					// subdirectories. (https://github.com/kubernetes/kubernetes/issues/28997)
					continue
				}
				return alreadyWatching, err
			}
			// since we already missed the creation event for this directory, publish an event here.
			if !alreadyWatchingSubDir {
				go func() {
					events <- watcher.ContainerEvent{
						EventType:   watcher.ContainerAdd,
						Name:        subcontainerName,
						WatchSource: watcher.Raw,
					}
				}()
			}
		}
	}

	cleanup = false
	return alreadyWatching, nil
}