mirror of
https://github.com/peterdell/wudsn-ide.git
synced 2024-06-03 06:29:35 +00:00
256 lines
9.3 KiB
Java
256 lines
9.3 KiB
Java
/**
|
|
* Copyright (C) 2009 - 2019 <a href="https://www.wudsn.com" target="_top">Peter Dell</a>
|
|
*
|
|
* This file is part of WUDSN IDE.
|
|
*
|
|
* WUDSN IDE is free software: you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation, either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* WUDSN IDE is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with WUDSN IDE. If not, see <http://www.gnu.org/licenses/>.
|
|
*/
|
|
|
|
package com.wudsn.ide.asm.compiler;
|
|
|
|
import java.io.File;
|
|
|
|
import org.eclipse.core.resources.IFile;
|
|
|
|
import com.wudsn.ide.asm.AssemblerProperties;
|
|
import com.wudsn.ide.asm.AssemblerProperties.AssemblerProperty;
|
|
import com.wudsn.ide.asm.preferences.CompilerPreferences;
|
|
import com.wudsn.ide.base.common.FileUtility;
|
|
import com.wudsn.ide.base.common.StringUtility;
|
|
|
|
/**
|
|
* Container class for the folder, file names and paths of the source file, the
|
|
* output file and the symbols file.
|
|
*
|
|
* @author Peter Dell
|
|
*
|
|
*/
|
|
public final class CompilerFiles {
|
|
|
|
public final class SourceFile {
|
|
|
|
public final IFile iFile;
|
|
|
|
public final File folder;
|
|
public final String folderPath;
|
|
|
|
public final File file;
|
|
public final String filePath;
|
|
public final String fileName;
|
|
public final String fileNameWithoutExtension;
|
|
|
|
public final AssemblerProperties assemblerProperties;
|
|
|
|
SourceFile(IFile iFile, AssemblerProperties assemblerProperties) {
|
|
|
|
if (iFile == null) {
|
|
throw new IllegalArgumentException("Parameter 'iFile' must not be null.");
|
|
}
|
|
if (assemblerProperties == null) {
|
|
throw new IllegalArgumentException("Parameter 'assemblerProperties' must not be null.");
|
|
}
|
|
|
|
this.iFile = iFile;
|
|
this.assemblerProperties = assemblerProperties;
|
|
|
|
// Source file.
|
|
filePath = iFile.getLocation().toOSString();
|
|
file = FileUtility.getCanonicalFile(new File(filePath));
|
|
fileName = file.getName();
|
|
|
|
String extension = iFile.getFileExtension();
|
|
if (extension == null) {
|
|
extension = "";
|
|
}
|
|
fileNameWithoutExtension = fileName.substring(0, fileName.length() - extension.length() - 1);
|
|
|
|
// Source folder.
|
|
folder = file.getParentFile();
|
|
folderPath = folder.getPath();
|
|
}
|
|
}
|
|
|
|
/**
|
|
* The actual source file which is currently open.
|
|
*/
|
|
public final SourceFile sourceFile;
|
|
|
|
/**
|
|
* The main source file which is either the current file or the file
|
|
* indicated by the property "@com.wudsn.ide.asm.editor.MainSourceFile".
|
|
*/
|
|
public final SourceFile mainSourceFile;
|
|
|
|
public final AssemblerProperty outputFolderModeProperty;
|
|
public final String outputFolderMode;
|
|
|
|
public final AssemblerProperty outputFolderProperty;
|
|
public final File outputFolder;
|
|
public final String outputFolderPath;
|
|
|
|
public final File outputFile;
|
|
public final String outputFilePath;
|
|
public final String outputFilePathWithoutExtension;
|
|
|
|
public final AssemblerProperty outputFileProperty;
|
|
public final String outputFileName;
|
|
public final String outputFileNameWithoutExtension;
|
|
public final AssemblerProperty outputFileExtensionProperty;
|
|
public final String outputFileExtension;
|
|
public final String outputFileNameShortWithoutExtension;
|
|
|
|
public final File symbolsFile;
|
|
public final String symbolsFilePath;
|
|
public final String symbolsFileName;
|
|
|
|
public CompilerFiles(IFile mainSourceIFile, AssemblerProperties mainSourceFileAssemblerProperties,
|
|
IFile sourceIFile, AssemblerProperties sourceFileAssemblerProperties,
|
|
CompilerPreferences compilerPreferences) {
|
|
|
|
if (mainSourceIFile == null) {
|
|
throw new IllegalArgumentException("Parameter 'mainSourceIFile' must not be null.");
|
|
}
|
|
if (sourceIFile == null) {
|
|
throw new IllegalArgumentException("Parameter 'sourceIFile' must not be null.");
|
|
}
|
|
if (compilerPreferences == null) {
|
|
throw new IllegalArgumentException("Parameter 'compilerPreferences' must not be null.");
|
|
}
|
|
this.mainSourceFile = new SourceFile(mainSourceIFile, mainSourceFileAssemblerProperties);
|
|
this.sourceFile = new SourceFile(sourceIFile, sourceFileAssemblerProperties);
|
|
|
|
// Output folder mode
|
|
// Can be overridden via annotation property in main source file
|
|
String localOutputFolderPath = compilerPreferences.getOutputFolderPath();
|
|
String localOutputFolderMode = compilerPreferences.getOutputFolderMode();
|
|
String localOutputFileExtension = compilerPreferences.getOutputFileExtension();
|
|
|
|
// Properties which override the preferences
|
|
outputFolderModeProperty = mainSourceFileAssemblerProperties.get(AssemblerProperties.OUTPUT_FOLDER_MODE);
|
|
outputFolderProperty = mainSourceFileAssemblerProperties.get(AssemblerProperties.OUTPUT_FOLDER);
|
|
outputFileExtensionProperty = mainSourceFileAssemblerProperties.get(AssemblerProperties.OUTPUT_FILE_EXTENSION);
|
|
outputFileProperty = mainSourceFileAssemblerProperties.get(AssemblerProperties.OUTPUT_FILE);
|
|
|
|
// The following sequence sets the instance fields "outputFolder" and
|
|
// "outputFileNameWithoutExtension" as well as the
|
|
// "outputFileNameWithoutExtension".
|
|
// If the output file is specified explicitly, it overrides all output
|
|
// properties.
|
|
if (outputFileProperty != null) {
|
|
|
|
// Make the file an absolute file.
|
|
File file = new File(outputFileProperty.value);
|
|
if (!file.isAbsolute()) {
|
|
file = new File(mainSourceFile.file.getParentFile(), file.getPath());
|
|
}
|
|
file = FileUtility.getCanonicalFile(file);
|
|
|
|
outputFolderMode = CompilerOutputFolderMode.FIXED_FOLDER;
|
|
outputFolder = file.getParentFile();
|
|
|
|
// Split the file name and file extension.
|
|
String fileName = file.getName();
|
|
int index = fileName.lastIndexOf('.');
|
|
if (index > 0) {
|
|
outputFileNameWithoutExtension = fileName.substring(0, index);
|
|
localOutputFileExtension = fileName.substring(index);
|
|
} else {
|
|
outputFileNameWithoutExtension = fileName;
|
|
localOutputFileExtension = "";
|
|
}
|
|
} else {
|
|
// The output file extension is independent of the rest.
|
|
if (outputFileExtensionProperty != null) {
|
|
localOutputFileExtension = outputFileExtensionProperty.value;
|
|
}
|
|
// If the output folder mode is specified explicitly, it overrides
|
|
// the output
|
|
// folder mode preferences.
|
|
if (outputFolderModeProperty != null) {
|
|
localOutputFolderMode = outputFolderModeProperty.value;
|
|
}
|
|
|
|
// If the output folder is specified explicitly, it overrides the
|
|
// output folder mode and folder preferences.
|
|
if (outputFolderProperty != null) {
|
|
localOutputFolderMode = CompilerOutputFolderMode.FIXED_FOLDER;
|
|
localOutputFolderPath = outputFolderProperty.value;
|
|
}
|
|
|
|
if (localOutputFolderMode.equals(CompilerOutputFolderMode.SOURCE_FOLDER)) {
|
|
localOutputFolderPath = mainSourceFile.folderPath;
|
|
} else if (localOutputFolderMode.equals(CompilerOutputFolderMode.FIXED_FOLDER)) {
|
|
// Fallback
|
|
if (StringUtility.isEmpty(localOutputFolderPath)) {
|
|
localOutputFolderPath = System.getProperty("java.io.tmpdir");
|
|
}
|
|
} else {
|
|
localOutputFolderPath = System.getProperty("java.io.tmpdir");
|
|
}
|
|
|
|
File file = new File(localOutputFolderPath);
|
|
if (!file.isAbsolute()) {
|
|
file = new File(sourceFile.file, file.getPath());
|
|
}
|
|
file = FileUtility.getCanonicalFile(file);
|
|
|
|
outputFolderMode = localOutputFolderMode;
|
|
outputFolder = file;
|
|
|
|
// Output file.
|
|
outputFileNameWithoutExtension = mainSourceFile.fileNameWithoutExtension;
|
|
}
|
|
|
|
// Common output parts.
|
|
outputFolderPath = outputFolder.getPath();
|
|
outputFileNameShortWithoutExtension = getFileNameShort(outputFileNameWithoutExtension);
|
|
outputFileName = outputFileNameWithoutExtension + localOutputFileExtension;
|
|
outputFileExtension = localOutputFileExtension;
|
|
outputFile = new File(outputFolder, outputFileName);
|
|
outputFilePath = outputFile.getPath();
|
|
outputFilePathWithoutExtension = new File(outputFolder, outputFileNameWithoutExtension).getPath();
|
|
|
|
// Symbols file.
|
|
symbolsFileName = mainSourceFile.fileNameWithoutExtension + ".lbl";
|
|
symbolsFile = new File(outputFolder, symbolsFileName);
|
|
symbolsFilePath = symbolsFile.getPath();
|
|
|
|
}
|
|
|
|
/**
|
|
* Computes a short file consisting of at most 8 ASCII letters and digits
|
|
* which starts with a letter.
|
|
*
|
|
* @param fileName
|
|
* The file name, may be empty, not <code>null</code>.
|
|
* @return The short file, name, not empty and not <code>null</code>.
|
|
*/
|
|
private String getFileNameShort(String fileName) {
|
|
if (fileName == null) {
|
|
throw new IllegalArgumentException("Parameter 'fileName' must not be null.");
|
|
}
|
|
StringBuilder builder = new StringBuilder(fileName);
|
|
for (int i = 0; i < fileName.length() && builder.length() < 8; i++) {
|
|
char c = fileName.charAt(i);
|
|
c = Character.toUpperCase(c);
|
|
if (c >= 'A' && c <= 'Z' && (builder.length() > 0) || c >= '0' && c <= '9') {
|
|
builder.append(c);
|
|
}
|
|
}
|
|
if (builder.length() == 0) {
|
|
return "UNKNOWN";
|
|
}
|
|
return builder.toString();
|
|
}
|
|
} |