/** * Build the {@link HeaderSymlinkTree} rule using the original build params from a target node. In * particular, make sure to drop all dependencies from the original build rule params, as these * are modeled via {@link CxxPreprocessAndCompile}. */ public static HeaderSymlinkTree createHeaderSymlinkTreeBuildRule( SourcePathResolver resolver, BuildTarget target, BuildRuleParams params, Path root, Optional<Path> headerMapPath, ImmutableMap<Path, SourcePath> links) { // Symlink trees never need to depend on anything. BuildRuleParams paramsWithoutDeps = params.copyWithChanges( target, Suppliers.ofInstance(ImmutableSortedSet.<BuildRule>of()), Suppliers.ofInstance(ImmutableSortedSet.<BuildRule>of())); try { if (headerMapPath.isPresent()) { return new HeaderSymlinkTreeWithHeaderMap( paramsWithoutDeps, resolver, root, headerMapPath.get(), links); } else { return new HeaderSymlinkTree(paramsWithoutDeps, resolver, root, links); } } catch (SymlinkTree.InvalidSymlinkTreeException e) { throw e.getHumanReadableExceptionForBuildTarget(target.getUnflavoredBuildTarget()); } }
@Override public T putComputedNodeIfNotPresent(Cell cell, BuildTarget target, T targetNode) throws BuildTargetException { try (AutoCloseableLock writeLock = rawAndComputedNodesLock.writeLock()) { T updatedNode = allComputedNodes.get(target, targetNode); if (updatedNode.equals(targetNode)) { targetsCornucopia.put(target.getUnflavoredBuildTarget(), target); } return updatedNode; } }
@SuppressWarnings({"rawtypes", "unchecked"}) private TargetNode<?> createTargetNode( BuckEventBus eventBus, Cell cell, Path buildFile, BuildTarget target, Map<String, Object> rawNode, TargetNodeListener nodeListener) { BuildRuleType buildRuleType = parseBuildRuleTypeFromRawRule(cell, rawNode); // Because of the way that the parser works, we know this can never return null. Description<?> description = cell.getDescription(buildRuleType); if (target.isFlavored()) { if (description instanceof Flavored) { if (!((Flavored) description).hasFlavors(ImmutableSet.copyOf(target.getFlavors()))) { throw new HumanReadableException( "Unrecognized flavor in target %s while parsing %s%s.", target, UnflavoredBuildTarget.BUILD_TARGET_PREFIX, MorePaths.pathWithUnixSeparators( target.getBasePath().resolve(cell.getBuildFileName()))); } } else { LOG.warn( "Target %s (type %s) must implement the Flavored interface " + "before we can check if it supports flavors: %s", target.getUnflavoredBuildTarget(), buildRuleType, target.getFlavors()); throw new HumanReadableException( "Target %s (type %s) does not currently support flavors (tried %s)", target.getUnflavoredBuildTarget(), buildRuleType, target.getFlavors()); } } Cell targetCell = cell.getCell(target); BuildRuleFactoryParams factoryParams = new BuildRuleFactoryParams( targetCell.getFilesystem(), target.withoutCell(), new FilesystemBackedBuildFileTree(cell.getFilesystem(), cell.getBuildFileName()), targetCell.isEnforcingBuckPackageBoundaries()); Object constructorArg = description.createUnpopulatedConstructorArg(); try { ImmutableSet.Builder<BuildTarget> declaredDeps = ImmutableSet.builder(); ImmutableSet.Builder<BuildTargetPattern> visibilityPatterns = ImmutableSet.builder(); try (SimplePerfEvent.Scope scope = SimplePerfEvent.scope( eventBus, PerfEventId.of("MarshalledConstructorArg"), "target", target)) { marshaller.populate( targetCell.getCellRoots(), targetCell.getFilesystem(), factoryParams, constructorArg, declaredDeps, visibilityPatterns, rawNode); } try (SimplePerfEvent.Scope scope = SimplePerfEvent.scope(eventBus, PerfEventId.of("CreatedTargetNode"), "target", target)) { Hasher hasher = Hashing.sha1().newHasher(); hasher.putString(BuckVersion.getVersion(), UTF_8); JsonObjectHashing.hashJsonObject(hasher, rawNode); synchronized (this) { targetsCornucopia.put(target.getUnflavoredBuildTarget(), target); } TargetNode<?> node = new TargetNode( hasher.hash(), description, constructorArg, typeCoercerFactory, factoryParams, declaredDeps.build(), visibilityPatterns.build(), targetCell.getCellRoots()); nodeListener.onCreate(buildFile, node); return node; } } catch (NoSuchBuildTargetException | TargetNode.InvalidSourcePathInputException e) { throw new HumanReadableException(e); } catch (ConstructorArgMarshalException e) { throw new HumanReadableException("%s: %s", target, e.getMessage()); } catch (IOException e) { throw new HumanReadableException(e.getMessage(), e); } }