/* * Copyright 2000-2012 JetBrains s.r.o. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.jetbrains.jps.incremental.storage; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.util.io.FileUtil; import com.intellij.util.io.IOUtil; import org.jetbrains.jps.builders.BuildTarget; import org.jetbrains.jps.builders.BuildTargetLoader; import org.jetbrains.jps.builders.BuildTargetType; import java.io.*; import java.util.HashMap; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentMap; /** * @author nik */ public class BuildTargetTypeState { private static final Logger LOG = Logger.getInstance("#org.jetbrains.jps.incremental.storage.BuildTargetTypeState"); private final Map<BuildTarget<?>, Integer> myTargetIds; private final ConcurrentMap<BuildTarget<?>, BuildTargetConfiguration> myConfigurations; private final BuildTargetType<?> myTargetType; private final BuildTargetsState myTargetsState; private final File myTargetsFile; public BuildTargetTypeState(BuildTargetType<?> targetType, BuildTargetsState state) { myTargetType = targetType; myTargetsState = state; myTargetsFile = new File(state.getDataPaths().getTargetTypeDataRoot(targetType), "targets.dat"); myConfigurations = new ConcurrentHashMap<>(16, 0.75f, 1); myTargetIds = new HashMap<>(); load(); } private boolean load() { if (!myTargetsFile.exists()) { return false; } try { DataInputStream input = new DataInputStream(new BufferedInputStream(new FileInputStream(myTargetsFile))); try { input.readInt();//reserved for version int size = input.readInt(); BuildTargetLoader<?> loader = myTargetType.createLoader(myTargetsState.getModel()); while (size-- > 0) { String stringId = IOUtil.readString(input); int intId = input.readInt(); myTargetsState.markUsedId(intId); BuildTarget<?> target = loader.createTarget(stringId); if (target != null) { myTargetIds.put(target, intId); } else { LOG.info("Unknown " + myTargetType.getTypeId() + " target: " + stringId); } } return true; } finally { input.close(); } } catch (IOException e) { LOG.info("Cannot load " + myTargetType.getTypeId() + " targets data: " + e.getMessage(), e); return false; } } public synchronized void save() { try { FileUtil.createParentDirs(myTargetsFile); DataOutputStream output = new DataOutputStream(new BufferedOutputStream(new FileOutputStream(myTargetsFile))); try { output.writeInt(0); output.writeInt(myTargetIds.size()); for (Map.Entry<BuildTarget<?>, Integer> entry : myTargetIds.entrySet()) { IOUtil.writeString(entry.getKey().getId(), output); output.writeInt(entry.getValue()); } } finally { output.close(); } } catch (IOException e) { LOG.info("Cannot save " + myTargetType.getTypeId() + " targets data: " + e.getMessage(), e); } } public synchronized int getTargetId(BuildTarget<?> target) { if (!myTargetIds.containsKey(target)) { myTargetIds.put(target, myTargetsState.getFreeId()); } return myTargetIds.get(target); } public BuildTargetConfiguration getConfiguration(BuildTarget<?> target) { BuildTargetConfiguration configuration = myConfigurations.get(target); if (configuration == null) { configuration = new BuildTargetConfiguration(target, myTargetsState); myConfigurations.putIfAbsent(target, configuration); configuration = myConfigurations.get(target); } return configuration; } }