/******************************************************************************* * Copyright (c) 2016 ARM Ltd. and others * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * ARM Ltd and ARM Germany GmbH - Initial API and implementation *******************************************************************************/ package com.arm.cmsis.pack.installer.jobs; import java.io.File; import java.io.IOException; import java.util.Collection; import java.util.LinkedList; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Path; import org.eclipse.core.runtime.Status; import org.eclipse.core.runtime.SubMonitor; import org.eclipse.jface.dialogs.IDialogConstants; import org.eclipse.jface.dialogs.MessageDialog; import org.eclipse.osgi.util.NLS; import org.eclipse.swt.widgets.Display; import com.arm.cmsis.pack.CpPlugIn; import com.arm.cmsis.pack.ICpPackInstaller; import com.arm.cmsis.pack.common.CmsisConstants; import com.arm.cmsis.pack.data.CpPack; import com.arm.cmsis.pack.data.ICpPack; import com.arm.cmsis.pack.data.ICpPack.PackState; import com.arm.cmsis.pack.events.RteEvent; import com.arm.cmsis.pack.installer.Messages; import com.arm.cmsis.pack.parser.ICpXmlParser; import com.arm.cmsis.pack.utils.Utils; /** * The Pack Unpacking Job. This job unzip the .pack file in the * .Download folder to the corresponding folder. */ public class CpPackUnpackJob extends CpPackJob { /** File path of the .pack file in .Download folder*/ protected IPath fSourceFilePath; /** Destination path of the unpacked file*/ protected IPath fDestPath; protected boolean fInstallRequiredPacks; int returnCode; /** * Constructor for unpacking a .pack or .zip file * @param name the job's name * @param installer the pack installer * @param packId Pack ID * @param sourceFilePath the .pack file's source file path * @param installRequiredPacks Set to true if required packs must also be installed */ public CpPackUnpackJob(String name, ICpPackInstaller installer, String packId, boolean installRequiredPacks) { super(name, installer, packId); fSourceFilePath = createDownloadFolder().append(packId + CmsisConstants.EXT_PACK); String relativeDir = CpPack.getPackRelativeInstallDir(packId); fDestPath = new Path(CpPlugIn.getPackManager().getCmsisPackRootDirectory()).append(relativeDir); this.fInstallRequiredPacks = installRequiredPacks; } @Override public boolean installRequiredPacks() { return fInstallRequiredPacks; } /** * Copy the .pack file to .Download folder * @return true if the operation is successful, otherwise false */ protected boolean copyToDownloadFolder(IProgressMonitor monitor) { return true; } @Override protected IStatus run(IProgressMonitor monitor) { IStatus status = Status.CANCEL_STATUS; SubMonitor progress = SubMonitor.convert(monitor, 100); if (copyToDownloadFolder(progress.newChild(80))) { if (unzip(progress.newChild(20))) { status = Status.OK_STATUS; } } monitor.done(); fPackInstaller.jobFinished(fJobId, RteEvent.PACK_INSTALL_JOB_FINISHED, fResult); return status; } private boolean unzip(IProgressMonitor monitor) { SubMonitor progress = SubMonitor.convert(monitor, 100); File sourceFile = fSourceFilePath.toFile(); monitor.setTaskName(Messages.CpPackUnpackJob_Unpacking + sourceFile.toString()); if (!sourceFile.exists()) { fResult.setErrorString(sourceFile.toString() + Messages.CpPackUnpackJob_SourceFileCannotBeFound); return true; } if (fDestPath.toFile().exists()) { final String messageString = NLS.bind(Messages.CpPackUnpackJob_PathAlreadyExists, fDestPath.toOSString()); Display.getDefault().syncExec(() -> { final MessageDialog dialog = new MessageDialog(Display.getDefault().getActiveShell(), Messages.CpPackUnpackJob_OverwriteQuery, null, messageString, MessageDialog.QUESTION, new String[] { IDialogConstants.YES_LABEL, IDialogConstants.NO_LABEL, IDialogConstants.CANCEL_LABEL }, 0); returnCode = dialog.open(); }); if (returnCode == IDialogConstants.OK_ID) { Utils.deleteFolderRecursive(fDestPath.toFile()); } else { fResult.setErrorString(Messages.CpPackJob_CancelledByUser); return false; } } try { if (!fPackInstaller.unzip(sourceFile, fDestPath, progress.newChild(95))) { fResult.setErrorString(Messages.CpPackJob_CancelledByUser); Utils.deleteFolderRecursive(fDestPath.toFile()); return false; } Collection<String> pdscFiles = new LinkedList<>(); Utils.findPdscFiles(fDestPath.toFile(), pdscFiles, 1); if (pdscFiles.isEmpty()) { Utils.deleteFolderRecursive(fDestPath.toFile()); fResult.setErrorString(Messages.CpPackUnpackJob_PdscFileNotFoundInFolder + fDestPath.toOSString()); return true; } String pdscFile = pdscFiles.iterator().next(); ICpXmlParser parser = CpPlugIn.getPackManager().getParser(); ICpPack pack = (ICpPack) parser.parseFile(pdscFile); if (pack != null) { pack.setPackState(PackState.INSTALLED); fResult.setPack(pack); fResult.setSuccess(true); IPath downloadPath = new Path(CpPlugIn.getPackManager().getCmsisPackDownloadDir()); Utils.copy(new File(pdscFile), downloadPath.append(pack.getId() + CmsisConstants.EXT_PDSC).toFile()); return true; } Utils.deleteFolderRecursive(fDestPath.toFile()); StringBuilder sb = new StringBuilder(Messages.CpPackUnpackJob_FailToParsePdscFile + pdscFile); for (String es : parser.getErrorStrings()) { sb.append(System.lineSeparator()); sb.append(es); } fResult.setErrorString(sb.toString()); return true; } catch (IOException e) { fResult.setErrorString(Messages.CpPackUnpackJob_FailedToUnzipFile + sourceFile.toString()); Utils.deleteFolderRecursive(fDestPath.toFile()); return true; } } protected IPath createDownloadFolder() { IPath downloadDir = new Path(CpPlugIn.getPackManager().getCmsisPackDownloadDir()); if (!downloadDir.toFile().exists()) { downloadDir.toFile().mkdir(); } return downloadDir; } }