func visit()

in Sources/SwiftDriver/ExplicitModuleBuilds/ClangVersionedDependencyResolution.swift [113:171]


    func visit(_ moduleId: ModuleDependencyId,
               pathPCMArtSet: Set<[String]>,
               pcmArgSetMap: inout [ModuleDependencyId : Set<[String]>])
    throws {
      guard let moduleInfo = modules[moduleId] else {
        throw Driver.Error.missingModuleDependency(moduleId.moduleName)
      }
      switch moduleId {
        case .swift:
          if visitedSwiftModules.contains(moduleId) {
            return
          } else {
            visitedSwiftModules.insert(moduleId)
          }
          guard case .swift(let swiftModuleDetails) = moduleInfo.details else {
            throw Driver.Error.malformedModuleDependency(moduleId.moduleName,
                                                         "no Swift `details` object")
          }
          // Add extraPCMArgs of the visited node to the current path set
          // and proceed to visit all direct dependencies
          let modulePCMArgs = swiftModuleDetails.extraPcmArgs
          var newPathPCMArgSet = pathPCMArtSet
          newPathPCMArgSet.insert(modulePCMArgs)
          for dependencyId in moduleInfo.directDependencies! {
            try visit(dependencyId,
                      pathPCMArtSet: newPathPCMArgSet,
                      pcmArgSetMap: &pcmArgSetMap)
          }
        case .clang:
          guard case .clang(let clangModuleDetails) = moduleInfo.details else {
            throw Driver.Error.malformedModuleDependency(moduleId.moduleName,
                                                         "no Clang `details` object")
          }
          // The details of this module contain information on which sets of PCMArgs are already
          // captured in the described dependencies of this module. Only re-scan at PCMArgs not
          // already captured.
          let alreadyCapturedPCMArgs =
            clangModuleDetails.capturedPCMArgs ?? Set<[String]>()
          let newPCMArgSet = pathPCMArtSet.filter { !alreadyCapturedPCMArgs.contains($0) }
          // Add current path's PCMArgs to the SetMap and stop traversal
          if pcmArgSetMap[moduleId] != nil {
            newPCMArgSet.forEach { pcmArgSetMap[moduleId]!.insert($0) }
          } else {
            pcmArgSetMap[moduleId] = newPCMArgSet
          }
          return
        case .swiftPrebuiltExternal:
          // We can rely on the fact that this pre-built module already has its
          // versioned-PCM dependencies satisfied, so we do not need to add additional
          // arguments. Proceed traversal to its dependencies.
          for dependencyId in moduleInfo.directDependencies! {
            try visit(dependencyId,
                      pathPCMArtSet: pathPCMArtSet,
                      pcmArgSetMap: &pcmArgSetMap)
          }
        case .swiftPlaceholder:
          fatalError("Unresolved placeholder dependencies at planning stage: \(moduleId)")
      }
    }