From 1381c87965ab669820a4a7b48c09aca026f5b478 Mon Sep 17 00:00:00 2001 From: Mark Donszelmann Date: Fri, 18 Nov 2005 21:02:34 +0000 Subject: --- .../cpptasks/borland/BorlandCCompiler.java | 134 +++++ .../cpptasks/borland/BorlandCfgParser.java | 70 +++ .../cpptasks/borland/BorlandLibrarian.java | 219 +++++++++ .../antcontrib/cpptasks/borland/BorlandLinker.java | 293 +++++++++++ .../cpptasks/borland/BorlandProcessor.java | 219 +++++++++ .../cpptasks/borland/BorlandResourceCompiler.java | 129 +++++ .../cpptasks/borland/CBuilderXProjectWriter.java | 542 +++++++++++++++++++++ src/net/sf/antcontrib/cpptasks/borland/CVS/Entries | 12 + .../sf/antcontrib/cpptasks/borland/CVS/Repository | 1 + src/net/sf/antcontrib/cpptasks/borland/CVS/Root | 1 + .../cpptasks/borland/CfgFilenameState.java | 46 ++ .../cpptasks/borland/ConsumeToSpaceOrNewLine.java | 30 ++ .../cpptasks/borland/QuoteBranchState.java | 35 ++ .../sf/antcontrib/cpptasks/borland/package.html | 27 + 14 files changed, 1758 insertions(+) create mode 100644 src/net/sf/antcontrib/cpptasks/borland/BorlandCCompiler.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/BorlandCfgParser.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/BorlandLibrarian.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/BorlandLinker.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/BorlandProcessor.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/BorlandResourceCompiler.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/CBuilderXProjectWriter.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/CVS/Entries create mode 100644 src/net/sf/antcontrib/cpptasks/borland/CVS/Repository create mode 100644 src/net/sf/antcontrib/cpptasks/borland/CVS/Root create mode 100644 src/net/sf/antcontrib/cpptasks/borland/CfgFilenameState.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/ConsumeToSpaceOrNewLine.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/QuoteBranchState.java create mode 100644 src/net/sf/antcontrib/cpptasks/borland/package.html (limited to 'src/net/sf/antcontrib/cpptasks/borland') diff --git a/src/net/sf/antcontrib/cpptasks/borland/BorlandCCompiler.java b/src/net/sf/antcontrib/cpptasks/borland/BorlandCCompiler.java new file mode 100644 index 0000000..fd9c657 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/BorlandCCompiler.java @@ -0,0 +1,134 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import java.io.File; +import java.util.Vector; + +import net.sf.antcontrib.cpptasks.compiler.CommandLineCompilerConfiguration; +import net.sf.antcontrib.cpptasks.compiler.CompilerConfiguration; +import net.sf.antcontrib.cpptasks.compiler.LinkType; +import net.sf.antcontrib.cpptasks.compiler.Linker; +import net.sf.antcontrib.cpptasks.compiler.PrecompilingCommandLineCCompiler; +import net.sf.antcontrib.cpptasks.compiler.Processor; +import net.sf.antcontrib.cpptasks.OptimizationEnum; + +import org.apache.tools.ant.types.Environment; +/** + * Adapter for the Borland(r) C/C++ compiler. + * + * @author Curt Arnold + */ +public class BorlandCCompiler extends PrecompilingCommandLineCCompiler { + private static final String[] headerExtensions = new String[]{".h", ".hpp", + ".inl"}; + private static final String[] sourceExtensions = new String[]{".c", ".cc", + ".cpp", ".cxx", ".c++"}; + private static final BorlandCCompiler instance = new BorlandCCompiler( + false, null); + public static BorlandCCompiler getInstance() { + return instance; + } + private BorlandCCompiler(boolean newEnvironment, Environment env) { + super("bcc32", "--version", sourceExtensions, headerExtensions, ".obj", false, + null, newEnvironment, env); + } + protected void addImpliedArgs(final Vector args, + final boolean debug, + final boolean multithreaded, + final boolean exceptions, + final LinkType linkType, + final Boolean rtti, + final OptimizationEnum optimization) { + args.addElement("-c"); + // + // turn off compiler autodependency since + // we do it ourselves + args.addElement("-X"); + if (exceptions) { + args.addElement("-x"); + } else { + args.addElement("-x-"); + } + if (multithreaded) { + args.addElement("-tWM"); + } + if (debug) { + args.addElement("-Od"); + args.addElement("-v"); + } else { + if (optimization != null) { + if (optimization.isSpeed()) { + args.addElement("-O1"); + } else { + if (optimization.isSpeed()) { + args.addElement("-O2"); + } else { + if (optimization.isNoOptimization()) { + args.addElement("-Od"); + } + } + } + } + } + if (rtti != null && !rtti.booleanValue()) { + args.addElement("-RT-"); + } + } + protected void addWarningSwitch(Vector args, int level) { + BorlandProcessor.addWarningSwitch(args, level); + } + public Processor changeEnvironment(boolean newEnvironment, Environment env) { + if (newEnvironment || env != null) { + return new BorlandCCompiler(newEnvironment, env); + } + return this; + } + protected CompilerConfiguration createPrecompileGeneratingConfig( + CommandLineCompilerConfiguration baseConfig, File prototype, + String lastInclude) { + String[] additionalArgs = new String[]{"-H=" + lastInclude, "-Hc"}; + return new CommandLineCompilerConfiguration(baseConfig, additionalArgs, + null, true); + } + protected CompilerConfiguration createPrecompileUsingConfig( + CommandLineCompilerConfiguration baseConfig, File prototype, + String lastInclude, String[] exceptFiles) { + String[] additionalArgs = new String[]{"-Hu"}; + return new CommandLineCompilerConfiguration(baseConfig, additionalArgs, + exceptFiles, false); + } + protected void getDefineSwitch(StringBuffer buffer, String define, + String value) { + BorlandProcessor.getDefineSwitch(buffer, define, value); + } + protected File[] getEnvironmentIncludePath() { + return BorlandProcessor.getEnvironmentPath("bcc32", 'I', + new String[]{"..\\include"}); + } + protected String getIncludeDirSwitch(String includeDir) { + return BorlandProcessor.getIncludeDirSwitch("-I", includeDir); + } + public Linker getLinker(LinkType type) { + return BorlandLinker.getInstance().getLinker(type); + } + public int getMaximumCommandLength() { + return 1024; + } + protected void getUndefineSwitch(StringBuffer buffer, String define) { + BorlandProcessor.getUndefineSwitch(buffer, define); + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/BorlandCfgParser.java b/src/net/sf/antcontrib/cpptasks/borland/BorlandCfgParser.java new file mode 100644 index 0000000..a452b1b --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/BorlandCfgParser.java @@ -0,0 +1,70 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import java.io.IOException; +import java.io.Reader; +import java.util.Vector; + +import net.sf.antcontrib.cpptasks.parser.AbstractParser; +import net.sf.antcontrib.cpptasks.parser.AbstractParserState; +import net.sf.antcontrib.cpptasks.parser.LetterState; +import net.sf.antcontrib.cpptasks.parser.WhitespaceOrLetterState; +/** + * A parser that paths from a borland cfg file + * + * @author Curt Arnold + */ +public final class BorlandCfgParser extends AbstractParser { + private AbstractParserState newLineState; + private final Vector path = new Vector(); + /** + * + * + */ + public BorlandCfgParser(char switchChar) { + // + // a quoted path (-I"some path") + // doesn't end till a close quote and will be abandoned + // if a new line is encountered first + // + AbstractParserState quote = new CfgFilenameState(this, new char[]{'"'}); + // + // an unquoted path (-Ic:\borland\include) + // ends at the first space or new line + AbstractParserState unquote = new CfgFilenameState(this, new char[]{ + ' ', '\n', '\r'}); + AbstractParserState quoteBranch = new QuoteBranchState(this, quote, + unquote); + AbstractParserState toNextSwitch = new ConsumeToSpaceOrNewLine(this); + AbstractParserState switchState = new LetterState(this, switchChar, + quoteBranch, toNextSwitch); + newLineState = new WhitespaceOrLetterState(this, '-', switchState); + } + public void addFilename(String include) { + path.addElement(include); + } + public AbstractParserState getNewLineState() { + return newLineState; + } + public String[] parsePath(Reader reader) throws IOException { + path.setSize(0); + super.parse(reader); + String[] retval = new String[path.size()]; + path.copyInto(retval); + return retval; + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/BorlandLibrarian.java b/src/net/sf/antcontrib/cpptasks/borland/BorlandLibrarian.java new file mode 100644 index 0000000..6693ab9 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/BorlandLibrarian.java @@ -0,0 +1,219 @@ +/* + * + * Copyright 2002-2005 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import java.io.File; +import java.io.IOException; +import java.util.Vector; +import org.apache.tools.ant.BuildException; + +import net.sf.antcontrib.cpptasks.CUtil; +import net.sf.antcontrib.cpptasks.compiler.CommandLineLinker; +import net.sf.antcontrib.cpptasks.compiler.LinkType; +import net.sf.antcontrib.cpptasks.compiler.Linker; +import net.sf.antcontrib.cpptasks.CCTask; +import net.sf.antcontrib.cpptasks.compiler.CommandLineLinkerConfiguration; +import net.sf.antcontrib.cpptasks.types.LibraryTypeEnum; + +/** + * Adapter for the Borland(r) tlib Librarian + * + * @author Curt Arnold + */ +public class BorlandLibrarian extends CommandLineLinker { + private static final BorlandLibrarian instance = new BorlandLibrarian(); + public static BorlandLibrarian getInstance() { + return instance; + } + private BorlandLibrarian() { + super("tlib", "--version", new String[]{".obj"}, new String[0], ".lib", false, + null); + } + protected void addBase(long base, Vector args) { + } + protected void addFixed(Boolean fixed, Vector args) { + } + protected void addImpliedArgs(boolean debug, LinkType linkType, Vector args) { + } + protected void addIncremental(boolean incremental, Vector args) { + } + protected void addMap(boolean map, Vector args) { + } + protected void addStack(int stack, Vector args) { + } + /* (non-Javadoc) + * @see net.sf.antcontrib.cpptasks.compiler.CommandLineLinker#addEntry(int, java.util.Vector) + */ + protected void addEntry(String entry, Vector args) { + } + + protected String getCommandFileSwitch(String cmdFile) { + // + // tlib requires quotes around paths containing - + // ilink32 doesn't like them + StringBuffer buf = new StringBuffer("@"); + BorlandProcessor.quoteFile(buf, cmdFile); + return buf.toString(); + } + public File[] getLibraryPath() { + return CUtil.getPathFromEnvironment("LIB", ";"); + } + public String[] getLibraryPatterns(String[] libnames, LibraryTypeEnum libType) { + return BorlandProcessor.getLibraryPatterns(libnames, libType); + } + public Linker getLinker(LinkType type) { + return BorlandLinker.getInstance().getLinker(type); + } + public int getMaximumCommandLength() { + return 1024; + } + public String[] getOutputFileSwitch(String outFile) { + return BorlandProcessor.getOutputFileSwitch(outFile); + } + public boolean isCaseSensitive() { + return BorlandProcessor.isCaseSensitive(); + } + /** + * Gets identifier for the linker. + * + * TLIB will lockup when attempting to get version + * information. Since the Librarian version isn't critical + * just return a stock response. + */ + public String getIdentifier() { + return "TLIB 4.5 Copyright (c) 1987, 1999 Inprise Corporation"; + } + + /** + * Prepares argument list for exec command. + * + * @param outputFile + * linker output file + * @param sourceFiles + * linker input files (.obj, .o, .res) + * @param args + * linker arguments + * @return arguments for runTask + */ + protected String[] prepareArguments( + CCTask task, + String outputDir, + String outputName, + String[] sourceFiles, + CommandLineLinkerConfiguration config) { + String[] preargs = config.getPreArguments(); + String[] endargs = config.getEndArguments(); + StringBuffer buf = new StringBuffer(); + Vector execArgs = new Vector(preargs.length + endargs.length + 10 + + sourceFiles.length); + + execArgs.addElement(this.getCommand()); + String outputFileName = new File(outputDir, outputName).toString(); + execArgs.addElement(quoteFilename(buf, outputFileName)); + + for (int i = 0; i < preargs.length; i++) { + execArgs.addElement(preargs[i]); + } + + // + // add a place-holder for page size + // + int pageSizeIndex = execArgs.size(); + execArgs.addElement(null); + + int objBytes = 0; + + for (int i = 0; i < sourceFiles.length; i++) { + String last4 = sourceFiles[i] + .substring(sourceFiles[i].length() - 4).toLowerCase(); + if (last4.equals(".def")) { + } else { + if (last4.equals(".res")) { + } else { + if (last4.equals(".lib")) { + } else { + execArgs.addElement("+" + quoteFilename(buf, sourceFiles[i])); + objBytes += new File(sourceFiles[i]).length(); + } + } + } + } + + for (int i = 0; i < endargs.length; i++) { + execArgs.addElement(endargs[i]); + } + + String[] execArguments = new String[execArgs.size()]; + execArgs.copyInto(execArguments); + + int minPageSize = objBytes >> 16; + int pageSize = 0; + for(int i = 4; i <= 15; i++) { + pageSize = 1 << i; + if (pageSize > minPageSize) break; + } + execArguments[pageSizeIndex] = "/P" + Integer.toString(pageSize); + + return execArguments; + } + + /** + * Prepares argument list to execute the linker using a response file. + * + * @param outputFile + * linker output file + * @param args + * output of prepareArguments + * @return arguments for runTask + */ + protected String[] prepareResponseFile(File outputFile, String[] args) + throws IOException { + String[] cmdargs = BorlandProcessor.prepareResponseFile(outputFile, args, " & \n"); + cmdargs[cmdargs.length - 1] = getCommandFileSwitch(cmdargs[cmdargs.length -1]); + return cmdargs; + } + + /** + * Builds a library + * + */ + public void link(CCTask task, + File outputFile, + String[] sourceFiles, + CommandLineLinkerConfiguration config) + throws BuildException + { + // + // delete any existing library + outputFile.delete(); + // + // build a new library + super.link(task, outputFile, sourceFiles, config); + } + + /** + * Encloses problematic file names within quotes. + * @param buf string buffer + * @param filename source file name + * @returns filename potentially enclosed in quotes. + */ + protected String quoteFilename(StringBuffer buf,String filename) { + buf.setLength(0); + BorlandProcessor.quoteFile(buf, filename); + return buf.toString(); + } + +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/BorlandLinker.java b/src/net/sf/antcontrib/cpptasks/borland/BorlandLinker.java new file mode 100644 index 0000000..315761f --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/BorlandLinker.java @@ -0,0 +1,293 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import java.io.File; +import java.io.IOException; +import java.util.Enumeration; +import java.util.Vector; + +import net.sf.antcontrib.cpptasks.CCTask; +import net.sf.antcontrib.cpptasks.TargetMatcher; +import net.sf.antcontrib.cpptasks.VersionInfo; +import net.sf.antcontrib.cpptasks.compiler.CommandLineLinker; +import net.sf.antcontrib.cpptasks.compiler.CommandLineLinkerConfiguration; +import net.sf.antcontrib.cpptasks.compiler.LinkType; +import net.sf.antcontrib.cpptasks.compiler.Linker; +import net.sf.antcontrib.cpptasks.platforms.WindowsPlatform; +import net.sf.antcontrib.cpptasks.types.LibraryTypeEnum; + +/** + * Adapter for the Borland(r) ilink32 linker + * + * @author Curt Arnold + */ +public final class BorlandLinker extends CommandLineLinker { + private static final BorlandLinker dllLinker = new BorlandLinker(".dll"); + private static final BorlandLinker instance = new BorlandLinker(".exe"); + public static BorlandLinker getInstance() { + return instance; + } + private BorlandLinker(String outputSuffix) { + super("ilink32", "-r", new String[]{".obj", ".lib", ".res"}, + new String[]{".map", ".pdb", ".lnk"}, outputSuffix, false, null); + } + protected void addBase(long base, Vector args) { + if (base >= 0) { + String baseAddr = Long.toHexString(base); + args.addElement("-b:" + baseAddr); + } + } + protected void addFixed(Boolean fixed, Vector args) { + } + protected void addImpliedArgs(boolean debug, LinkType linkType, Vector args) { + if (linkType.isExecutable()) { + if (linkType.isSubsystemConsole()) { + args.addElement("/ap"); + } else { + if (linkType.isSubsystemGUI()) { + args.addElement("/Tpe"); + } + } + } + if (linkType.isSharedLibrary()) { + args.addElement("/Tpd"); + args.addElement("/Gi"); + } + if (debug) { + args.addElement("-v"); + } + } + protected void addIncremental(boolean incremental, Vector args) { + } + protected void addMap(boolean map, Vector args) { + if (!map) { + args.addElement("-x"); + } + } + protected void addStack(int stack, Vector args) { + if (stack >= 0) { + String stackStr = Integer.toHexString(stack); + args.addElement("-S:" + stackStr); + } + } + /* (non-Javadoc) + * @see net.sf.antcontrib.cpptasks.compiler.CommandLineLinker#addEntry(int, java.util.Vector) + */ + protected void addEntry(String entry, Vector args) { + } + + public String getCommandFileSwitch(String commandFile) { + return "@" + commandFile; + } + public String getIdentifier() { + return "Borland Linker"; + } + public File[] getLibraryPath() { + return BorlandProcessor.getEnvironmentPath("ilink32", 'L', + new String[]{"..\\lib"}); + } + public String[] getLibraryPatterns(String[] libnames, LibraryTypeEnum libType) { + return BorlandProcessor.getLibraryPatterns(libnames, libType); + } + public Linker getLinker(LinkType type) { + if (type.isStaticLibrary()) { + return BorlandLibrarian.getInstance(); + } + if (type.isSharedLibrary()) { + return dllLinker; + } + return instance; + } + public int getMaximumCommandLength() { + return 1024; + } + public String[] getOutputFileSwitch(String outFile) { + return BorlandProcessor.getOutputFileSwitch(outFile); + } + protected String getStartupObject(LinkType linkType) { + if (linkType.isSharedLibrary()) { + return "c0d32.obj"; + } + if (linkType.isSubsystemGUI()) { + return "c0w32.obj"; + } + if (linkType.isSubsystemConsole()) { + return "c0x32.obj"; + } + return null; + } + public boolean isCaseSensitive() { + return BorlandProcessor.isCaseSensitive(); + } + /** + * Prepares argument list for exec command. + * + * @param outputFile + * linker output file + * @param sourceFiles + * linker input files (.obj, .o, .res) + * @param args + * linker arguments + * @return arguments for runTask + */ + protected String[] prepareArguments( + CCTask task, + String outputDir, + String outputName, + String[] sourceFiles, + CommandLineLinkerConfiguration config) { + String[] preargs = config.getPreArguments(); + String[] endargs = config.getEndArguments(); + Vector execArgs = new Vector(preargs.length + endargs.length + 10 + + sourceFiles.length); + execArgs.addElement(this.getCommand()); + for (int i = 0; i < preargs.length; i++) { + execArgs.addElement(preargs[i]); + } + for (int i = 0; i < endargs.length; i++) { + execArgs.addElement(endargs[i]); + } + // + // see if the input files have any known startup obj files + // + String startup = null; + for (int i = 0; i < sourceFiles.length; i++) { + String filename = new File(sourceFiles[i]).getName().toLowerCase(); + if (startup != null && filename.substring(0, 2).equals("c0") + && filename.substring(3, 5).equals("32") + && filename.substring(filename.length() - 4).equals(".obj")) { + startup = sourceFiles[i]; + } + } + // + // c0w32.obj, c0x32.obj or c0d32.obj depending on + // link type + if (startup == null) { + startup = config.getStartupObject(); + } + execArgs.addElement(startup); + Vector resFiles = new Vector(); + Vector libFiles = new Vector(); + String defFile = null; + StringBuffer buf = new StringBuffer(); + for (int i = 0; i < sourceFiles.length; i++) { + String last4 = sourceFiles[i] + .substring(sourceFiles[i].length() - 4).toLowerCase(); + if (last4.equals(".def")) { + defFile = quoteFilename(buf, sourceFiles[i]); + } else { + if (last4.equals(".res")) { + resFiles.addElement(quoteFilename(buf, sourceFiles[i])); + } else { + if (last4.equals(".lib")) { + libFiles.addElement(quoteFilename(buf, sourceFiles[i])); + } else { + execArgs.addElement(quoteFilename(buf, sourceFiles[i])); + } + } + } + } + // + // output file name + // + String outputFileName = new File(outputDir, outputName).toString(); + execArgs.addElement("," + quoteFilename(buf, outputFileName)); + if (config.getMap()) { + int lastPeriod = outputFileName.lastIndexOf('.'); + String mapName; + if (lastPeriod < outputFileName.length() - 4) { + mapName = outputFileName + ".map"; + } else { + mapName = outputFileName.substring(0, lastPeriod) + ".map"; + } + execArgs.addElement("," + quoteFilename(buf, mapName) + ","); + } else { + execArgs.addElement(",,"); + } + // + // add all the libraries + // + Enumeration libEnum = libFiles.elements(); + boolean hasImport32 = false; + boolean hasCw32 = false; + while (libEnum.hasMoreElements()) { + String libName = (String) libEnum.nextElement(); + if (libName.equalsIgnoreCase("import32.lib")) { + hasImport32 = true; + } + if (libName.equalsIgnoreCase("cw32.lib")) { + hasImport32 = true; + } + execArgs.addElement(quoteFilename(buf, libName)); + } + if (!hasCw32) { + execArgs.addElement(quoteFilename(buf, "cw32.lib")); + } + if (!hasImport32) { + execArgs.addElement(quoteFilename(buf, "import32.lib")); + } + if (defFile == null) { + execArgs.addElement(",,"); + } else { + execArgs.addElement("," + quoteFilename(buf, defFile) + ","); + } + Enumeration resEnum = resFiles.elements(); + while (resEnum.hasMoreElements()) { + String resName = (String) resEnum.nextElement(); + execArgs.addElement(quoteFilename(buf, resName)); + } + String[] execArguments = new String[execArgs.size()]; + execArgs.copyInto(execArguments); + return execArguments; + } + /** + * Prepares argument list to execute the linker using a response file. + * + * @param outputFile + * linker output file + * @param args + * output of prepareArguments + * @return arguments for runTask + */ + protected String[] prepareResponseFile(File outputFile, String[] args) + throws IOException { + String cmdargs[] = BorlandProcessor.prepareResponseFile(outputFile, args, " + \n"); + cmdargs[cmdargs.length - 1] = getCommandFileSwitch(cmdargs[cmdargs.length -1]); + return cmdargs; + } + + /** + * Adds source or object files to the bidded fileset to + * support version information. + * + * @param versionInfo version information + * @param linkType link type + * @param isDebug true if debug build + * @param executableName name of generated executable + * @param objDir directory for generated files + * @param matcher bidded fileset + */ + public void addVersionFiles(final VersionInfo versionInfo, + final LinkType linkType, + final File outputFile, + final boolean isDebug, + final File objDir, + final TargetMatcher matcher) throws IOException { + WindowsPlatform.addVersionFiles(versionInfo, linkType, outputFile, isDebug, objDir, matcher); + } + +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/BorlandProcessor.java b/src/net/sf/antcontrib/cpptasks/borland/BorlandProcessor.java new file mode 100644 index 0000000..bbfeba8 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/BorlandProcessor.java @@ -0,0 +1,219 @@ +/* + * + * Copyright 2002-2005 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.io.Reader; +import java.util.Vector; +import java.io.FileWriter; + +import net.sf.antcontrib.cpptasks.CUtil; +import net.sf.antcontrib.cpptasks.types.LibraryTypeEnum; +/** + * A add-in class for Borland(r) processor adapters + * + * + */ +public final class BorlandProcessor { + public static void addWarningSwitch(Vector args, int level) { + switch (level) { + case 0 : + args.addElement("-w-"); + break; + case 5 : + args.addElement("-w!"); + break; + default : + args.addElement("-w"); + break; + } + } + public static void getDefineSwitch(StringBuffer buffer, String define, + String value) { + buffer.append("-D"); + buffer.append(define); + if (value != null && value.length() > 0) { + buffer.append('='); + buffer.append(value); + } + } + /** + * This method extracts path information from the appropriate .cfg file in + * the install directory. + * + * @param toolName + * Tool name, for example, "bcc32", "brc32", "ilink32" + * @param switchChar + * Command line switch character, for example "L" for libraries + * @param defaultRelativePaths + * default paths relative to executable directory + * @return path + */ + public static File[] getEnvironmentPath(String toolName, char switchChar, + String[] defaultRelativePath) { + if (toolName == null) { + throw new NullPointerException("toolName"); + } + if (defaultRelativePath == null) { + throw new NullPointerException("defaultRelativePath"); + } + String[] path = defaultRelativePath; + File exeDir = CUtil.getExecutableLocation(toolName + ".exe"); + if (exeDir != null) { + File cfgFile = new File(exeDir, toolName + ".cfg"); + if (cfgFile.exists()) { + try { + Reader reader = new BufferedReader(new FileReader(cfgFile)); + BorlandCfgParser cfgParser = new BorlandCfgParser( + switchChar); + path = cfgParser.parsePath(reader); + reader.close(); + } catch (IOException ex) { + // + // could be logged + // + } + } + } else { + // + // if can't find the executable, + // assume current directory to resolve relative paths + // + exeDir = new File(System.getProperty("user.dir")); + } + int nonExistant = 0; + File[] resourcePath = new File[path.length]; + for (int i = 0; i < path.length; i++) { + resourcePath[i] = new File(path[i]); + if (!resourcePath[i].isAbsolute()) { + resourcePath[i] = new File(exeDir, path[i]); + } + // + // if any of the entries do not exist or are + // not directories, null them out + if (!(resourcePath[i].exists() && resourcePath[i].isDirectory())) { + resourcePath[i] = null; + nonExistant++; + } + } + // + // if there were some non-existant or non-directory + // entries in the configuration file then + // create a shorter array + if (nonExistant > 0) { + File[] culled = new File[resourcePath.length - nonExistant]; + int index = 0; + for (int i = 0; i < resourcePath.length; i++) { + if (resourcePath[i] != null) { + culled[index++] = resourcePath[i]; + } + } + resourcePath = culled; + } + return resourcePath; + } + public static String getIncludeDirSwitch(String includeOption, + String includeDir) { + StringBuffer buf = new StringBuffer(includeOption); + quoteFile(buf, includeDir); + return buf.toString(); + } + public static String[] getLibraryPatterns(String[] libnames, LibraryTypeEnum libType) { + StringBuffer buf = new StringBuffer(); + String[] patterns = new String[libnames.length]; + for (int i = 0; i < libnames.length; i++) { + buf.setLength(0); + buf.append(libnames[i]); + buf.append(".lib"); + patterns[i] = buf.toString(); + } + return patterns; + } + public static String[] getOutputFileSwitch(String outFile) { + return new String[0]; + } + public static void getUndefineSwitch(StringBuffer buffer, String define) { + buffer.append("-U"); + buffer.append(define); + } + public static boolean isCaseSensitive() { + return false; + } + public static void quoteFile(StringBuffer buf, String outPath) { + if (outPath.charAt(0) != '\"' + && (outPath.indexOf(' ') >= 0 + || outPath.indexOf('-') >= 0 + || outPath.indexOf('/') >= 0)) { + buf.append('\"'); + buf.append(outPath); + buf.append('\"'); + } else { + buf.append(outPath); + } + } + + /** + * Prepares argument list to execute the linker using a response file. + * + * @param outputFile + * linker output file + * @param args + * output of prepareArguments + * @return arguments for runTask + */ + public static String[] prepareResponseFile(File outputFile, + String[] args, + String continuation) + throws IOException { + String baseName = outputFile.getName(); + File commandFile = new File(outputFile.getParent(), baseName + ".rsp"); + FileWriter writer = new FileWriter(commandFile); + for (int i = 1; i < args.length - 1; i++) { + writer.write(args[i]); + // + // if either the current argument ends with + // or next argument starts with a comma then + // don't split the line + if (args[i].endsWith(",") || args[i + 1].startsWith(",")) { + writer.write(' '); + } else { + // + // split the line to make it more readable + // + writer.write(continuation); + } + } + // + // write the last argument + // + if (args.length > 1) { + writer.write(args[args.length - 1]); + } + writer.close(); + String[] execArgs = new String[2]; + execArgs[0] = args[0]; + // + // left for the caller to decorate + execArgs[1] = commandFile.toString(); + return execArgs; + } + + private BorlandProcessor() { + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/BorlandResourceCompiler.java b/src/net/sf/antcontrib/cpptasks/borland/BorlandResourceCompiler.java new file mode 100644 index 0000000..debfa2b --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/BorlandResourceCompiler.java @@ -0,0 +1,129 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import java.io.File; +import java.util.Vector; +import net.sf.antcontrib.cpptasks.CCTask; +import net.sf.antcontrib.cpptasks.compiler.CommandLineCompiler; +import net.sf.antcontrib.cpptasks.compiler.CommandLineCompilerConfiguration; +import net.sf.antcontrib.cpptasks.compiler.LinkType; +import net.sf.antcontrib.cpptasks.compiler.Linker; +import net.sf.antcontrib.cpptasks.compiler.Processor; +import net.sf.antcontrib.cpptasks.compiler.ProgressMonitor; +import net.sf.antcontrib.cpptasks.parser.CParser; +import net.sf.antcontrib.cpptasks.parser.Parser; +import net.sf.antcontrib.cpptasks.OptimizationEnum; + +import org.apache.tools.ant.BuildException; +import org.apache.tools.ant.types.Environment; +/** + * Adapter for the Borland(r) brc32 Resource compiler. + * + * @author Curt Arnold + */ +public class BorlandResourceCompiler extends CommandLineCompiler { + private static final BorlandResourceCompiler instance = new BorlandResourceCompiler( + false, null); + public static BorlandResourceCompiler getInstance() { + return instance; + } + private BorlandResourceCompiler(boolean newEnvironment, Environment env) { + super("brc32", "c:\\__bogus\\__bogus.rc", new String[]{".rc"}, + new String[]{".h", ".hpp", ".inl"}, ".res", false, null, + newEnvironment, env); + } + protected void addImpliedArgs(final Vector args, + final boolean debug, + final boolean multithreaded, + final boolean exceptions, + final LinkType linkType, + final Boolean rtti, + final OptimizationEnum optimization) { + // + // compile only + // + args.addElement("-r"); + } + protected void addWarningSwitch(Vector args, int level) { + } + public Processor changeEnvironment(boolean newEnvironment, Environment env) { + if (newEnvironment || env != null) { + return new BorlandResourceCompiler(newEnvironment, env); + } + return this; + } + public void compile(CCTask task, File outputDir, String[] sourceFiles, + String[] args, String[] endArgs, boolean relentless, + CommandLineCompilerConfiguration config, ProgressMonitor monitor) + throws BuildException { + super.compile(task, outputDir, sourceFiles, args, endArgs, relentless, + config, monitor); + } + /** + * The include parser for C will work just fine, but we didn't want to + * inherit from CommandLineCCompiler + */ + protected Parser createParser(File source) { + return new CParser(); + } + protected int getArgumentCountPerInputFile() { + return 2; + } + protected void getDefineSwitch(StringBuffer buffer, String define, + String value) { + buffer.append("-d"); + buffer.append(define); + if (value != null && value.length() > 0) { + buffer.append('='); + buffer.append(value); + } + } + protected File[] getEnvironmentIncludePath() { + return BorlandProcessor.getEnvironmentPath("brc32", 'i', + new String[]{"..\\include"}); + } + protected String getIncludeDirSwitch(String includeDir) { + return BorlandProcessor.getIncludeDirSwitch("-i", includeDir); + } + protected String getInputFileArgument(File outputDir, String filename, + int index) { + if (index == 0) { + String[] outputFileNames = getOutputFileNames(filename, null); + String fullOutputName = new File(outputDir, outputFileNames[0]) + .toString(); + return "-fo" + fullOutputName; + } + return filename; + } + public Linker getLinker(LinkType type) { + return BorlandLinker.getInstance().getLinker(type); + } + public int getMaximumCommandLength() { + return 1024; + } + protected int getMaximumInputFilesPerCommand() { + return 1; + } + protected int getTotalArgumentLengthForInputFile(File outputDir, + String inputFile) { + String arg1 = getInputFileArgument(outputDir, inputFile, 0); + String arg2 = getInputFileArgument(outputDir, inputFile, 1); + return arg1.length() + arg2.length() + 2; + } + protected void getUndefineSwitch(StringBuffer buffer, String define) { + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/CBuilderXProjectWriter.java b/src/net/sf/antcontrib/cpptasks/borland/CBuilderXProjectWriter.java new file mode 100644 index 0000000..dfe5ec6 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/CBuilderXProjectWriter.java @@ -0,0 +1,542 @@ +/* + * + * Copyright 2004-2005 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; + +import java.io.File; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.OutputStream; +import java.util.Hashtable; +import java.util.Iterator; +import java.util.List; +import java.util.Locale; + +import net.sf.antcontrib.cpptasks.CCTask; +import net.sf.antcontrib.cpptasks.CUtil; +import net.sf.antcontrib.cpptasks.TargetInfo; +import net.sf.antcontrib.cpptasks.compiler.CommandLineCompilerConfiguration; +import net.sf.antcontrib.cpptasks.compiler.CommandLineLinkerConfiguration; +import net.sf.antcontrib.cpptasks.compiler.ProcessorConfiguration; +import net.sf.antcontrib.cpptasks.gcc.GccCCompiler; +import net.sf.antcontrib.cpptasks.ide.ProjectDef; +import net.sf.antcontrib.cpptasks.ide.ProjectWriter; + +import org.apache.tools.ant.BuildException; +import org.apache.xml.serialize.OutputFormat; +import org.apache.xml.serialize.Serializer; +import org.apache.xml.serialize.XMLSerializer; +import org.xml.sax.ContentHandler; +import org.xml.sax.SAXException; +import org.xml.sax.helpers.AttributesImpl; + +/** + * Writes a CBuilderX 1.0 project file. + * + * @author curta + * + */ +public final class CBuilderXProjectWriter + implements ProjectWriter { + /** + * Constructor. + */ + public CBuilderXProjectWriter() { + } + + /** + * Writes a project definition file. + * + * @param fileName + * project name for file, should has .cbx extension + * @param task + * cc task for which to write project + * @param projectDef + * project element + * @param sources source files + * @param targets compilation targets + * @param linkTarget link target + * @throws IOException if I/O error + * @throws SAXException if XML serialization error + */ + public void writeProject(final File fileName, + final CCTask task, + final ProjectDef projectDef, + final List sources, + final Hashtable targets, + final TargetInfo linkTarget) throws + IOException, + SAXException { + + String projectName = projectDef.getName(); + if (projectName == null) { + projectName = fileName.getName(); + } + final String basePath = fileName.getAbsoluteFile().getParent(); + + File projectFile = new File(fileName + ".cbx"); + if (!projectDef.getOverwrite() && projectFile.exists()) { + throw new BuildException("Not allowed to overwrite project file " + + projectFile.toString()); + } + + CommandLineCompilerConfiguration compilerConfig = + getBaseCompilerConfiguration(targets); + if (compilerConfig == null) { + throw new BuildException( + "Unable to generate C++ BuilderX project when gcc or bcc is not used."); + } + + OutputStream outStream = new FileOutputStream(projectFile); + OutputFormat format = new OutputFormat("xml", "UTF-8", true); + Serializer serializer = new XMLSerializer(outStream, format); + ContentHandler content = serializer.asContentHandler(); + content.startDocument(); + AttributesImpl emptyAttrs = new AttributesImpl(); + content.startElement(null, "project", "project", emptyAttrs); + PropertyWriter propertyWriter = new PropertyWriter(content); + propertyWriter.write("build.config", "active", "0"); + propertyWriter.write("build.config", "count", "0"); + propertyWriter.write("build.config", "excludedefaultforzero", "0"); + propertyWriter.write("build.config.0", "builddir", "Debug"); + propertyWriter.write("build.config.0", "key", "Debug_Build"); + propertyWriter.write("build.config.0", "linux.builddir", + "linux/Debug_Build"); + propertyWriter.write("build.config.0", "settings.MinGW", + "default;debug"); + propertyWriter.write("build.config.0", "settings.gnuc++", + "default;debug"); + propertyWriter.write("build.config.0", "settings.intellinia32", + "default;debug"); + propertyWriter.write("build.config.0", "settings.mswin32", + "default;debug"); + propertyWriter.write("build.config.0", "type", "Toolset"); + propertyWriter.write("build.config.0", "win32.builddir", + "windows/Debug_Build"); + propertyWriter.write("build.node", "name", projectDef.getName()); + final String buildType = getBuildType(task); + propertyWriter.write("build.node", "type", buildType); + propertyWriter.write("build.platform", "active", + getActivePlatform(task)); + propertyWriter.write("build.platform", "linux.Debug_Build.toolset", + "gnuc++"); + propertyWriter.write("build.platform", "linux.Release_Build.toolset", + "gnuc++"); + propertyWriter.write("build.platform", "linux.default", "gnuc++"); + propertyWriter.write("build.platform", "linux.gnuc++.enabled", "1"); + propertyWriter.write("build.platform", "linux.mswin32.enabled", "1"); + propertyWriter.write("build.platform", "linux.win32b.enabled", "1"); + propertyWriter.write("build.platform", "solaris.default", "gnuc++"); + propertyWriter.write("build.platform", "solaris.enabled", "1"); + String toolset = getWin32Toolset(compilerConfig); + propertyWriter.write("build.platform", "win32.default", toolset); + propertyWriter.write("build.platform", "win32." + toolset + ".enabled", "1"); + + propertyWriter.write("cbproject", "version", "X.1.0"); + if ("dllproject".equals(buildType)) { + propertyWriter.write("gnuc++.g++compile", + "option.fpic_using_GOT.enabled", "1"); + propertyWriter.write("gnuc++.g++link", "option.shared.enabled", "1"); + propertyWriter.write("intellinia32.icc", "option.minus_Kpic.enabled", + "1"); + propertyWriter.write("intellinia32.icclink", + "option.minus_shared.enabled", "1"); + } + // + // assume the first target is representative of all compilation tasks + // + writeCompileOptions(basePath, propertyWriter, compilerConfig); + writeLinkOptions(basePath, propertyWriter, linkTarget); + propertyWriter.write("linux.gnuc++.Debug_Build", "saved", "1"); + if ("dllproject".equals(buildType)) { + propertyWriter.write("runtime", "ExcludeDefaultForZero", "1"); + //propertyWriter.write("unique", "id", "852"); + } else if ("exeproject".equals(buildType)) { + propertyWriter.write("runtime.0", "BuildTargetOnRun", + "com.borland.cbuilder.build." + + "CBProjectBuilder$ProjectBuildAction;make"); + propertyWriter.write("runtime.0", "ConfigurationName", + projectDef.getName()); + propertyWriter.write("runtime.0", "RunnableType", + "com.borland.cbuilder.runtime.ExecutableRunner"); + } + AttributesImpl fileAttributes = new AttributesImpl(); + fileAttributes.addAttribute(null, "path", "path", "#PCDATA", ""); + AttributesImpl gccAttributes = null; + if (!"g++".equals(compilerConfig.getCommand())) { + gccAttributes = new AttributesImpl(); + gccAttributes.addAttribute(null, "category", "category", "#PCDATA", + "build.basecmd"); + gccAttributes.addAttribute(null, "name", "name", "#PCDATA", + "linux.gnuc++.Debug_Build.g++_key"); + gccAttributes.addAttribute(null, "value", "value", "#PCDATA", + compilerConfig.getCommand()); + } + + Iterator targetIter = targets.values().iterator(); + while (targetIter.hasNext()) { + TargetInfo info = (TargetInfo) targetIter.next(); + File[] targetsources = info.getSources(); + for (int i = 0; i < targetsources.length; i++) { + String relativePath = CUtil.getRelativePath(basePath, + targetsources[i]); + fileAttributes.setValue(0, relativePath); + content.startElement(null, "file", "file", fileAttributes); + + // + // if file ends with .c, use gcc instead of g++ + // + if (gccAttributes != null) { + content.startElement(null, "property", "property", gccAttributes); + content.endElement(null, "property", "property"); + } + content.endElement(null, "file", "file"); + } + } + content.endElement(null, "project", "project"); + content.endDocument(); + } + + /** + * Gets build type from link target. + * @param task CCTask current task + * @return String build type + */ + private String getBuildType(final CCTask task) { + String outType = task.getOuttype(); + if ("executable".equals(outType)) { + return "exeproject"; + } else if ("static".equals(outType)) { + return "libraryproject"; + } + return "dllproject"; + } + + /** + * Gets active platform. + * @param task CCTask cc task + * @return String platform identifier + */ + private String getActivePlatform(final CCTask task) { + String osName = System.getProperty("os.name").toLowerCase(Locale.US); + if (osName.indexOf("windows") >= 0) { + return "win32"; + } + return "linux"; + } + + private String getWin32Toolset(final CommandLineCompilerConfiguration compilerConfig) { + if (compilerConfig != null && compilerConfig.getCompiler() instanceof BorlandCCompiler) { + return "win32b"; + } + return "MinGW"; + } + + /** + * Utility class to generate property elements. + */ + private static class PropertyWriter { + /** + * Content handler. + */ + private ContentHandler content; + + /** + * Attributes list. + */ + private AttributesImpl propertyAttributes; + + /** + * Constructor. + * + * @param contentHandler ContentHandler content handler + */ + public PropertyWriter(final ContentHandler contentHandler) { + content = contentHandler; + propertyAttributes = new AttributesImpl(); + propertyAttributes.addAttribute(null, "category", "category", + "#PCDATA", ""); + propertyAttributes + .addAttribute(null, "name", "name", "#PCDATA", ""); + propertyAttributes.addAttribute(null, "value", "value", "#PCDATA", + ""); + } + + /** + * Write property element. + * + * @param category String category + * @param name String property name + * @param value String property value + * @throws SAXException if I/O error or illegal content + */ + public final void write(final String category, + final String name, + final String value) throws SAXException { + propertyAttributes.setValue(0, category); + propertyAttributes.setValue(1, name); + propertyAttributes.setValue(2, value); + content.startElement(null, "property", "property", + propertyAttributes); + content.endElement(null, "property", "property"); + } + } + + /** + * Gets the first recognized compiler from the + * compilation targets. + * @param targets compilation targets + * @return representative (hopefully) compiler configuration + */ + private CommandLineCompilerConfiguration + getBaseCompilerConfiguration(final Hashtable targets) { + // + // find first target with an gcc or bcc compilation + // + CommandLineCompilerConfiguration compilerConfig = null; + // + // get the first target and assume that it is representative + // + Iterator targetIter = targets.values().iterator(); + while (targetIter.hasNext()) { + TargetInfo targetInfo = (TargetInfo) targetIter.next(); + ProcessorConfiguration config = targetInfo.getConfiguration(); + String identifier = config.getIdentifier(); + // + // for the first gcc or bcc compiler + // + if (config instanceof CommandLineCompilerConfiguration) { + compilerConfig = (CommandLineCompilerConfiguration) config; + if (compilerConfig.getCompiler() instanceof GccCCompiler || + compilerConfig.getCompiler() instanceof BorlandCCompiler) { + return compilerConfig; + } + } + } + return null; + } + + /** + * Writes elements corresponding to compilation options. + * + * @param baseDir String base directory + * @param writer PropertyWriter property writer + * @param compilerConfig representative configuration + * @throws SAXException if I/O error or illegal content + */ + private void writeCompileOptions(final String baseDir, + final PropertyWriter writer, + final CommandLineCompilerConfiguration + compilerConfig) throws SAXException { + boolean isBcc = false; + boolean isUnix = true; + String compileID = "linux.Debug_Build.gnuc++.g++compile"; + if (compilerConfig.getCompiler() instanceof BorlandCCompiler) { + compileID = "win32.Debug_Build.win32b.bcc32"; + isUnix = false; + isBcc = true; + } + + File[] includePath = compilerConfig.getIncludePath(); + int includeIndex = 1; + if (isUnix) { + writer.write(compileID, + "option.I.arg." + (includeIndex++), + "/usr/include"); + writer.write(compileID, + "option.I.arg." + (includeIndex++), + "/usr/include/g++-3"); + } + for (int i = 0; i < includePath.length; i++) { + String relPath = CUtil.getRelativePath(baseDir, includePath[i]); + writer.write(compileID, + "option.I.arg." + (includeIndex++), + relPath); + } + if (includePath.length > 0) { + writer.write(compileID, + "option.I.enabled", + "1"); + } + + String defineBase = "option.D_MACRO_VALUE"; + if (isBcc) { + defineBase = "option.D"; + } + String defineOption = defineBase + ".arg."; + int defineIndex = 1; + int undefineIndex = 1; + String[] preArgs = compilerConfig.getPreArguments(); + for (int i = 0; i < preArgs.length; i++) { + if (preArgs[i].startsWith("-D")) { + writer.write(compileID, + defineOption + (defineIndex++), + preArgs[i].substring(2)); + } else if (preArgs[i].startsWith("-U")) { + writer.write(compileID, + "option.U.arg." + + (undefineIndex++), preArgs[i] + .substring(2)); + } else if (!(preArgs[i].startsWith("-I") + || preArgs[i].startsWith("-o"))) { + // + // any others (-g, -fno-rtti, -w, -Wall, etc) + // + writer.write(compileID, + "option." + preArgs[i].substring(1) + ".enabled", + "1"); + } + } + if (defineIndex > 1) { + writer.write(compileID, + defineBase + ".enabled", + "1"); + } + if (undefineIndex > 1) { + writer.write(compileID, + "option.U.enabled", + "1"); + } + } + + /** + * Writes elements corresponding to link options. + * + * @param baseDir String base directory + * @param writer PropertyWriter property writer + * @param linkTarget TargetInfo link target + * @throws SAXException if I/O error or illegal content + */ + private void + writeLinkOptions(final String baseDir, + final PropertyWriter writer, + final TargetInfo linkTarget) throws SAXException { + if (linkTarget != null) { + ProcessorConfiguration config = linkTarget.getConfiguration(); + if (config instanceof CommandLineLinkerConfiguration) { + CommandLineLinkerConfiguration linkConfig = + (CommandLineLinkerConfiguration) config; + + if (linkConfig.getLinker() instanceof BorlandLinker) { + String linkID = "win32.Debug_Build.win32b.ilink32"; + writeIlinkArgs(writer, linkID, linkConfig.getPreArguments()); + writeIlinkArgs(writer, linkID, linkConfig.getEndArguments()); + writer.write(linkID, "param.libfiles.1", "cw32mt.lib"); + writer.write(linkID, "param.libfiles.2", "import32.lib"); + int libIndex = 3; + String[] libNames = linkConfig.getLibraryNames(); + for(int i = 0; i < libNames.length; i++) { + writer.write(linkID, "param.libfiles." + (libIndex++), + libNames[i]); + } + String startup = linkConfig.getStartupObject(); + if (startup != null) { + writer.write(linkID, "param.objfiles.1", startup); + } + } else { + String linkID = "linux.Debug_Build.gnuc++.g++link"; + writeLdArgs(writer, linkID, linkConfig.getPreArguments()); + writeLdArgs(writer, linkID, linkConfig.getEndArguments()); + } + } + } + } + + /** + * Writes ld linker options to project file. + * + * @param writer PropertyWriter property writer + * @param linkID String linker identifier + * @param preArgs String[] linker arguments + * @throws SAXException thrown if unable to write option + */ + private void writeLdArgs(final PropertyWriter writer, + final String linkID, + final String[] preArgs) throws SAXException { + int objnameIndex = 1; + int libnameIndex = 1; + int libpathIndex = 1; + for (int i = 0; i < preArgs.length; i++) { + if (preArgs[i].startsWith("-o")) { + writer.write(linkID, + "option.o.arg." + + (objnameIndex++), preArgs[i] + .substring(2)); + } else if (preArgs[i].startsWith("-l")) { + writer.write(linkID, + "option.l.arg." + + (libnameIndex++), preArgs[i] + .substring(2)); + } else if (preArgs[i].startsWith("-L")) { + writer.write(linkID, + "option.L.arg." + + (libpathIndex++), preArgs[i] + .substring(2)); + } else { + // + // any others + // + writer.write(linkID, "option." + preArgs[i].substring(1) + ".enabled", + "1"); + } + } + if (objnameIndex > 1) { + writer.write(linkID, + "option.o.enabled", + "1"); + } + if (libnameIndex > 1) { + writer.write(linkID, + "option.l.enabled", + "1"); + } + if (libpathIndex > 1) { + writer.write(linkID, + "option.L.enabled", + "1"); + } + } + + /** + * Writes ilink32 linker options to project file. + * + * @param writer PropertyWriter property writer + * @param linkID String linker identifier + * @param preArgs String[] linker arguments + * @throws SAXException thrown if unable to write option + */ + private void writeIlinkArgs(final PropertyWriter writer, + final String linkID, + final String[] args) throws SAXException { + for (int i = 0; i < args.length; i++) { + if (args[i].charAt(0) == '/' || args[i].charAt(0) == '-') { + int equalsPos = args[i].indexOf('='); + if (equalsPos > 0) { + String option = "option." + args[i].substring(0, equalsPos -1); + writer.write(linkID, + option + ".enabled", + "1"); + writer.write(linkID, + option + ".value", + args[i].substring(equalsPos + 1)); + } else { + writer.write(linkID, "option." + args[i].substring(1) + ".enabled", "1"); + } + } + } + } + +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/CVS/Entries b/src/net/sf/antcontrib/cpptasks/borland/CVS/Entries new file mode 100644 index 0000000..f185634 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/CVS/Entries @@ -0,0 +1,12 @@ +/BorlandCCompiler.java/1.17/Fri Apr 23 20:15:46 2004// +/BorlandCfgParser.java/1.7/Sat Feb 28 19:00:01 2004// +/BorlandLibrarian.java/1.19/Sun Feb 13 04:58:21 2005// +/BorlandLinker.java/1.23/Tue Mar 1 22:33:39 2005// +/BorlandProcessor.java/1.19/Sun Feb 13 04:58:21 2005// +/BorlandResourceCompiler.java/1.22/Tue May 11 03:50:12 2004// +/CBuilderXProjectWriter.java/1.8/Mon Aug 15 14:51:54 2005// +/CfgFilenameState.java/1.6/Sat Feb 28 19:00:01 2004// +/ConsumeToSpaceOrNewLine.java/1.6/Sat Feb 28 19:00:01 2004// +/QuoteBranchState.java/1.6/Sat Feb 28 19:00:01 2004// +/package.html/1.1/Sat Jun 26 02:45:17 2004// +D diff --git a/src/net/sf/antcontrib/cpptasks/borland/CVS/Repository b/src/net/sf/antcontrib/cpptasks/borland/CVS/Repository new file mode 100644 index 0000000..c06cbfe --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/CVS/Repository @@ -0,0 +1 @@ +cpptasks/src/net/sf/antcontrib/cpptasks/borland diff --git a/src/net/sf/antcontrib/cpptasks/borland/CVS/Root b/src/net/sf/antcontrib/cpptasks/borland/CVS/Root new file mode 100644 index 0000000..1ac95cd --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/CVS/Root @@ -0,0 +1 @@ +:pserver:anonymous@cvs.sourceforge.net:/cvsroot/ant-contrib diff --git a/src/net/sf/antcontrib/cpptasks/borland/CfgFilenameState.java b/src/net/sf/antcontrib/cpptasks/borland/CfgFilenameState.java new file mode 100644 index 0000000..82767cb --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/CfgFilenameState.java @@ -0,0 +1,46 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import net.sf.antcontrib.cpptasks.parser.AbstractParser; +import net.sf.antcontrib.cpptasks.parser.AbstractParserState; +import net.sf.antcontrib.cpptasks.parser.FilenameState; +public class CfgFilenameState extends FilenameState { + private char terminator; + public CfgFilenameState(AbstractParser parser, char[] terminators) { + super(parser, terminators); + terminator = terminators[0]; + } + public AbstractParserState consume(char ch) { + // + // if a ';' is encountered then + // close the previous filename by sending a + // recognized terminator to our super class + // and stay in this state for more filenamese + if (ch == ';') { + super.consume(terminator); + return this; + } + AbstractParserState newState = super.consume(ch); + // + // change null (consume to end of line) + // to look for next switch character + if (newState == null) { + newState = getParser().getNewLineState(); + } + return newState; + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/ConsumeToSpaceOrNewLine.java b/src/net/sf/antcontrib/cpptasks/borland/ConsumeToSpaceOrNewLine.java new file mode 100644 index 0000000..5656af8 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/ConsumeToSpaceOrNewLine.java @@ -0,0 +1,30 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import net.sf.antcontrib.cpptasks.parser.AbstractParser; +import net.sf.antcontrib.cpptasks.parser.AbstractParserState; +public class ConsumeToSpaceOrNewLine extends AbstractParserState { + public ConsumeToSpaceOrNewLine(AbstractParser parser) { + super(parser); + } + public AbstractParserState consume(char ch) { + if (ch == ' ' || ch == '\t' || ch == '\n') { + return getParser().getNewLineState(); + } + return this; + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/QuoteBranchState.java b/src/net/sf/antcontrib/cpptasks/borland/QuoteBranchState.java new file mode 100644 index 0000000..ec3bc84 --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/QuoteBranchState.java @@ -0,0 +1,35 @@ +/* + * + * Copyright 2002-2004 The Ant-Contrib project + * + * 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 net.sf.antcontrib.cpptasks.borland; +import net.sf.antcontrib.cpptasks.parser.AbstractParser; +import net.sf.antcontrib.cpptasks.parser.AbstractParserState; +public class QuoteBranchState extends AbstractParserState { + private AbstractParserState quote; + private AbstractParserState unquote; + public QuoteBranchState(AbstractParser parser, AbstractParserState quote, + AbstractParserState unquote) { + super(parser); + this.quote = quote; + this.unquote = unquote; + } + public AbstractParserState consume(char ch) { + if (ch == '"') { + return quote; + } + return unquote.consume(ch); + } +} diff --git a/src/net/sf/antcontrib/cpptasks/borland/package.html b/src/net/sf/antcontrib/cpptasks/borland/package.html new file mode 100644 index 0000000..a91e91f --- /dev/null +++ b/src/net/sf/antcontrib/cpptasks/borland/package.html @@ -0,0 +1,27 @@ + + + + + + + +Adapter for Borland tools. + + + -- cgit v1.2.3