MWCC/command_line/CmdLine/Src/CLFileOps.c

804 lines
28 KiB
C

#include "cmdline.h"
extern char STSbuf[256];
static int OutputTextData(File *file, SInt16 stage, OSType maccreator, OSType mactype) {
int ret = 0;
SInt32 size;
if (file->textdata) {
size = GetHandleSize(file->textdata);
if (stage != CmdLineStageMask_Dp || optsCmdLine.toDisk & CmdLineStageMask_Dp) {
if (!(file->writeToDisk & stage)) {
ret = ShowHandle(file->textdata, size, 0);
} else {
if (optsCmdLine.verbose)
CLReport(15, OS_SpecToStringRelative(&file->outfss, NULL, STSbuf, sizeof(STSbuf)));
ret = WriteHandleToFile(&file->outfss, file->textdata, size, maccreator, mactype);
file->wroteToDisk |= stage;
}
} else {
if (optsCompiler.outMakefile[0]) {
ret = AppendHandleToFile(&clState.makefileSpec, file->textdata, size, maccreator, mactype);
} else {
ret = ShowHandle(file->textdata, size, 0);
}
}
DisposeHandle(file->textdata);
file->textdata = NULL;
}
return ret;
}
static int fstrcat(char *file, const char *add, SInt32 length) {
if (strlen(file) + strlen(add) >= length) {
return 0;
} else {
strcat(file, add);
return 1;
}
}
static void extstrcat(char *file, const char *ext) {
if (!fstrcat(file, ext, 64))
strcpy(file + 63 - strlen(ext), ext);
}
int GetOutputFile(File *file, SInt16 stage) {
int err;
char tempoutfilename[256];
char *targetoutfilename;
Boolean specifiedName;
const char *ext;
const CWObjectFlags *cof;
char tmpname[256];
char *env;
char *extptr;
char *fnptr;
char text[64];
char *inname;
OSPathSpec tmppath;
if (optsCmdLine.toDisk & stage)
file->writeToDisk |= stage;
if (file->outfileowner == stage) {
targetoutfilename = file->outfilename;
specifiedName = file->outfilename[0] && !(file->tempOnDisk & stage);
if (specifiedName) {
file->writeToDisk |= stage;
file->tempOnDisk &= ~stage;
}
} else {
targetoutfilename = tempoutfilename;
specifiedName = 0;
}
if (!(stage & (optsCmdLine.toDisk | file->writeToDisk | file->tempOnDisk))) {
if ((stage == CmdLineStageMask_Cg) && (optsCmdLine.stages & CmdLineStageMask_Ds) && (optsCmdLine.state == OptsCmdLineState_2) && optsCompiler.keepObjects)
file->writeToDisk |= stage;
else
file->tempOnDisk |= stage;
}
if (!specifiedName && (stage & (optsCmdLine.toDisk | file->writeToDisk | file->tempOnDisk))) {
cof = Plugin_CL_GetObjectFlags(file->compiler);
if (stage == CmdLineStageMask_Pp) {
ext = optsCompiler.ppFileExt[0] ? optsCompiler.ppFileExt : cof->ppFileExt;
} else if (stage == CmdLineStageMask_Ds) {
ext = optsCompiler.disFileExt[0] ? optsCompiler.disFileExt : cof->disFileExt;
} else if (stage == CmdLineStageMask_Dp) {
ext = optsCompiler.depFileExt[0] ? optsCompiler.depFileExt : cof->depFileExt;
} else if (stage == CmdLineStageMask_Cg) {
ext = optsCompiler.objFileExt[0] ? optsCompiler.objFileExt : cof->objFileExt;
if (!(file->objectflags & 0x80000000) && !specifiedName)
ext = NULL;
} else {
ext = NULL;
}
if (ext && ext[0]) {
if (ext[0] != '.') {
snprintf(text, sizeof(text), ".%s", ext);
} else {
strncpy(text, ext, sizeof(text) - 1);
text[sizeof(text) - 1] = 0;
}
if ((file->tempOnDisk & stage) && !(optsCmdLine.stages & CmdLineStageMask_Dp)) {
env = getenv("TEMP");
if (!env || !env[0] || OS_MakePathSpec(NULL, env, &tmppath))
env = getenv("TMP");
if (!env || !env[0] || OS_MakePathSpec(NULL, env, &tmppath))
env = getenv("TMPDIR");
if (!env || !env[0] || OS_MakePathSpec(NULL, env, &tmppath))
env = "/tmp";
if (!env || !env[0] || OS_MakePathSpec(NULL, env, &tmppath))
env = ".";
snprintf(tmpname, sizeof(tmpname), "%s%c%s", env, OS_PATHSEP, OS_GetFileNamePtr(file->srcfilename));
inname = tmpname;
} else if (!optsCompiler.relPathInOutputDir) {
inname = OS_GetFileNamePtr(file->srcfilename);
} else {
inname = file->srcfilename;
}
fnptr = OS_GetFileNamePtr(inname);
extptr = strrchr(fnptr, '.');
if (!extptr || ext[0] == '.')
extptr = fnptr + strlen(fnptr);
if (extptr - fnptr + strlen(text) >= sizeof(text))
extptr = &fnptr[sizeof(text) - 1] - strlen(text);
snprintf(targetoutfilename, 256, "%.*s%s", extptr - inname, inname, text);
} else {
*targetoutfilename = 0;
file->writeToDisk &= ~stage;
file->tempOnDisk &= ~stage;
}
}
if (stage & (file->writeToDisk | file->tempOnDisk)) {
err = OS_MakeSpecWithPath(&gTarg->outputDirectory, targetoutfilename, !optsCompiler.relPathInOutputDir, &file->outfss);
if (!err) {
if (OS_EqualSpec(&file->srcfss, &file->outfss)) {
if (specifiedName) {
CLReportError(102, targetoutfilename);
file->writeToDisk &= ~stage;
file->tempOnDisk &= ~stage;
return 0;
}
file->writeToDisk &= ~stage;
file->tempOnDisk &= ~stage;
}
} else {
CLReportOSError(9, err, targetoutfilename, OS_PathSpecToString(&gTarg->outputDirectory, STSbuf, sizeof(STSbuf)));
}
return err == 0;
}
return 1;
}
static int SyntaxCheckFile(File *file) {
return SendCompilerRequest(file->compiler, file, 0) != 0;
}
static int PreprocessFile(File *file) {
const CWObjectFlags *cof;
if (!(file->dropinflags & kCanpreprocess)) {
CLReportWarning(53, Plugin_GetDropInName(file->compiler), file->srcfilename);
return 1;
}
if (!SendCompilerRequest(file->compiler, file, 1))
return 0;
if (!GetOutputFile(file, CmdLineStageMask_Pp))
return 0;
if (file->textdata) {
cof = Plugin_CL_GetObjectFlags(file->compiler);
return OutputTextData(
file, CmdLineStageMask_Pp,
optsCompiler.ppFileCreator ? optsCompiler.ppFileCreator : cof->ppFileCreator,
optsCompiler.ppFileType ? optsCompiler.ppFileType : cof->ppFileType);
}
CLReportError(96, "preprocessing", file->srcfilename);
return 0;
}
static int DependencyMapFile(File *file, Boolean compileifnecessary) {
OSHandle mf;
const CWObjectFlags *cof;
cof = Plugin_CL_GetObjectFlags(file->compiler);
if (!(optsCmdLine.stages & (CmdLineStageMask_Pp | CmdLineStageMask_Cg)) && compileifnecessary) {
if (!SendCompilerRequest(file->compiler, file, CmdLineStageMask_Dp))
return 0;
}
if (!GetOutputFile(file, CmdLineStageMask_Cg))
return 0;
Deps_ListDependencies(&gTarg->incls, file, &mf);
file->textdata = OS_CreateMacHandle(&mf);
if (!GetOutputFile(file, CmdLineStageMask_Dp))
return 0;
if (OutputTextData(
file, CmdLineStageMask_Dp,
optsCompiler.depFileCreator ? optsCompiler.depFileCreator : cof->depFileCreator,
optsCompiler.depFileType ? optsCompiler.depFileType : cof->depFileType)) {
return 1;
} else {
return 0;
}
}
static int RecordBrowseInfo(File *file) {
const CWObjectFlags *cof;
if (!file->recordbrowseinfo)
return 1;
if (!file->browsedata) {
CLReportError(101, Plugin_GetDropInName(file->compiler), OS_SpecToStringRelative(&file->srcfss, NULL, STSbuf, sizeof(STSbuf)));
return 0;
}
if ((optsCmdLine.toDisk & CmdLineStageMask_Cg) && optsCompiler.browserEnabled) {
cof = Plugin_CL_GetObjectFlags(file->compiler);
if (!WriteBrowseData(file, optsCompiler.brsFileCreator ? optsCompiler.brsFileCreator : cof->brsFileCreator, optsCompiler.brsFileType ? optsCompiler.brsFileType : cof->brsFileType))
return 0;
}
return 1;
}
static int RecordObjectData(File *file) {
const CWObjectFlags *cof = Plugin_CL_GetObjectFlags(file->compiler);
if (!file->objectdata)
return 1;
if (!WriteObjectFile(file, optsCompiler.objFileCreator ? optsCompiler.objFileCreator : cof->objFileCreator, optsCompiler.objFileType ? optsCompiler.objFileType : cof->objFileType))
return 0;
return 1;
}
int StoreObjectFile(File *file) {
if (file->wroteToDisk & CmdLineStageMask_Cg)
return 1;
if (!file->objectdata && !file->browsedata)
return 1;
if (GetOutputFile(file, CmdLineStageMask_Cg)) {
if (!((file->writeToDisk | file->tempOnDisk) & CmdLineStageMask_Cg))
return 1;
if (!RecordBrowseInfo(file) || !RecordObjectData(file))
return 0;
file->wroteToDisk |= CmdLineStageMask_Cg;
return 1;
}
return 0;
}
static int CompileFile(File *file) {
int ret = 1;
if (!(file->dropinflags & kCanprecompile) && ((optsCompiler.forcePrecompile == 1) || (file->mappingflags & kPrecompile))) {
CLReportWarning(54, Plugin_GetDropInName(file->compiler), file->srcfilename);
return 1;
}
if (optsCompiler.browserEnabled) {
SInt16 id;
int ret;
char fullpath[256];
memset(file->browseoptions, 1, sizeof(file->browseoptions));
OS_SpecToString(&file->srcfss, fullpath, sizeof(fullpath));
ret = Browser_SearchAndAddFile(&clState.browseTableHandle, fullpath, &id);
if (!ret)
return 0;
file->recordbrowseinfo = ret < 0;
file->browseFileID = id;
if (optsCmdLine.verbose > 1)
CLReport(22, file->srcfilename, file->browseFileID);
} else {
memset(file->browseoptions, 0, sizeof(file->browseoptions));
file->recordbrowseinfo = 0;
file->recordbrowseinfo = 0;
file->browseFileID = 0;
}
if (!SendCompilerRequest(file->compiler, file, 2)) {
ret = 0;
} else {
if ((!file->hasobjectcode || !file->objectdata) && (file->dropinflags & kGeneratescode) && (file->objectUsage & 2)) {
CLReportError(96, "compiling", file->srcfilename);
ret = 0;
} else if (optsCmdLine.state == OptsCmdLineState_2 && !StoreObjectFile(file)) {
ret = 0;
}
}
return ret;
}
static int DisassembleWithLinker(File *file, Plugin *linker, SInt32 linkerDropinFlags) {
char filename[256];
int ret;
if (file->writeToDisk & CmdLineStageMask_Ds) {
OS_SpecToString(&file->outfss, filename, sizeof(filename));
ret = ExecuteLinker(linker, linkerDropinFlags, file, (optsCmdLine.toDisk & CmdLineStageMask_Ds) ? NULL : filename, NULL);
file->wroteToDisk |= CmdLineStageMask_Ds;
return ret;
}
return ExecuteLinker(linker, linkerDropinFlags, file, NULL, NULL);
}
static int DisassembleFile(File *file) {
Plugin *disasm;
if (!file->hasobjectcode && !file->hasresources) {
CLReportError(56, file->srcfilename);
return 0;
}
if (!GetOutputFile(file, CmdLineStageMask_Ds))
return 0;
if (file->dropinflags & kCandisassemble) {
if (!SendDisassemblerRequest(file->compiler, file))
return 0;
if (file->textdata) {
const CWObjectFlags *cof = Plugin_CL_GetObjectFlags(file->compiler);
return OutputTextData(
file, CmdLineStageMask_Ds,
optsCompiler.disFileCreator ? optsCompiler.disFileCreator : cof->disFileCreator,
optsCompiler.disFileType ? optsCompiler.disFileType : cof->disFileType);
}
CLReportError(96, "disassembling", file->srcfilename);
return 0;
} else {
if ((gTarg->linkerDropinFlags & dropInExecutableTool) && !(gTarg->linkerDropinFlags & cantDisassemble))
return DisassembleWithLinker(file, gTarg->linker, gTarg->linkerDropinFlags);
if ((gTarg->preLinkerDropinFlags & dropInExecutableTool) && !(gTarg->preLinkerDropinFlags & cantDisassemble))
return DisassembleWithLinker(file, gTarg->preLinker, gTarg->preLinkerDropinFlags);
if (gTarg->linker && !(gTarg->linkerDropinFlags & cantDisassemble)) {
if (SendDisassemblerRequest(gTarg->linker, file)) {
if (file->textdata && GetHandleSize(file->textdata) > 0) {
const CWObjectFlags *cof = Plugin_CL_GetObjectFlags(file->compiler);
return OutputTextData(
file, CmdLineStageMask_Ds,
optsCompiler.disFileCreator ? optsCompiler.disFileCreator : cof->disFileCreator,
optsCompiler.disFileType ? optsCompiler.disFileType : cof->disFileType);
}
CLReportError(96, "disassembling", file->srcfilename);
}
return 0;
}
if (gTarg->preLinker && !(gTarg->preLinkerDropinFlags & cantDisassemble)) {
if (SendDisassemblerRequest(gTarg->preLinker, file)) {
if (file->textdata && GetHandleSize(file->textdata) > 0) {
const CWObjectFlags *cof = Plugin_CL_GetObjectFlags(file->compiler);
return OutputTextData(
file, CmdLineStageMask_Ds,
optsCompiler.disFileCreator ? optsCompiler.disFileCreator : cof->disFileCreator,
optsCompiler.disFileType ? optsCompiler.disFileType : cof->disFileType);
}
CLReportError(96, "disassembling", file->srcfilename);
}
return 0;
}
if (gTarg->linker)
CLReportError(58, Plugin_GetDropInName(gTarg->linker), Plugin_GetDropInName(file->compiler), file->srcfilename);
else
CLReportError(57, Plugin_GetDropInName(file->compiler), file->srcfilename);
return 0;
}
}
static int CompileEntry(File *file, Boolean *compiled) {
UInt32 beginWork;
UInt32 endWork;
struct BuildInfo *tinfo = &gTarg->info;
*compiled = 0;
if (optsCmdLine.dryRun) {
*compiled = 1;
return 1;
}
if (!(file->sourceUsage & 1)) {
if (file->mappingflags & kRsrcfile)
*compiled = 1;
return 1;
}
#line 835
OPTION_ASSERT(file->compiler);
*compiled = 1;
beginWork = OS_GetMilliseconds();
Browser_Initialize(&clState.browseTableHandle);
Deps_ChangeSpecialAccessPath(&file->srcfss, 1);
if ((optsCmdLine.stages == 0) && !SyntaxCheckFile(file))
return 0;
if ((optsCmdLine.stages & CmdLineStageMask_Pp) && !PreprocessFile(file))
return 0;
if ((optsCmdLine.stages & (CmdLineStageMask_Cg | CmdLineStageMask_Ds)) && !CompileFile(file))
return 0;
if ((optsCmdLine.stages & CmdLineStageMask_Dp) && !DependencyMapFile(file, 1))
return 0;
if ((optsCmdLine.stages & CmdLineStageMask_Ds) && !DisassembleFile(file))
return 0;
if (optsCmdLine.verbose && (optsCmdLine.stages & CmdLineStageMask_Cg)) {
const char *cun;
const char *dun;
const char *uun;
CLReport(25, file->compiledlines);
tinfo->linesCompiled += file->compiledlines;
cun = dun = uun = "bytes";
CLReport(26, file->codesize, cun, file->idatasize, dun, file->udatasize, uun);
}
tinfo->codeSize += file->codesize;
tinfo->iDataSize += file->idatasize;
tinfo->uDataSize += file->udatasize;
Browser_Terminate(&clState.browseTableHandle);
endWork = OS_GetMilliseconds();
if (optsCmdLine.timeWorking) {
if (optsCmdLine.verbose)
CLReport(24, (endWork - beginWork) / 1000.0, "compile", "", "", "");
else
CLReport(24, (endWork - beginWork) / 1000.0, "compile", "'", file->srcfilename, "'");
}
return 1;
}
static void DumpFileAndPathInfo(void) {
int i;
int n;
CLReport(84, "Framework search paths ([d] = default, [r] = recursive)");
n = Paths_Count(&FrameworkPaths);
if (!n) {
CLReport(85, "(none)", "");
} else {
for (i = 0; i < n; i++) {
Path *path = Paths_GetPath(&FrameworkPaths, i);
#line 961
OPTION_ASSERT(path != NULL);
CLReport(85,
OS_PathSpecToString(path->spec, STSbuf, sizeof(STSbuf)),
((path->flags & 2) && path->recursive) ? " [d] [r]" : (path->flags & 2) ? " [d]" : path->recursive ? " [r]" : ""
);
if (path->recursive && optsCmdLine.verbose > 2) {
UInt16 j;
for (j = 0; j < Paths_Count(path->recursive); j++) {
Path *sub = Paths_GetPath(path->recursive, j);
#line 976
OPTION_ASSERT(sub);
CLReport(85, "\t", OS_PathSpecToString(sub->spec, STSbuf, sizeof(STSbuf)));
}
}
}
}
n = Frameworks_GetCount();
if (Frameworks_GetCount()) {
CLReport(84, "Included frameworks");
for (i = 0; i < n; i++) {
char version[80];
Paths_FWInfo *info = Frameworks_GetInfo(i);
#line 993
OPTION_ASSERT(info);
version[0] = 0;
strcpy(version, "\t(");
if (!info->version.s[0]) {
strcat(version, "Current)");
} else {
strncat(version, info->version.s, sizeof(version) - 4);
strcat(version, ")");
}
CLReport(85, info->name.s, version);
}
}
if (clState.plugintype == CWDROPINCOMPILERTYPE)
CLReport(84, "User include search paths ([d] = default, [r] = recursive)");
else
CLReport(84, "Library search paths ([d] = default, [r] = recursive)");
if (!Paths_Count(&gTarg->userPaths) && clState.plugintype == CWDROPINCOMPILERTYPE) {
CLReport(85, "(none)", "");
} else {
for (i = 0; i < Paths_Count(&gTarg->userPaths); i++) {
Path *path = Paths_GetPath(&gTarg->userPaths, i);
#line 1024
OPTION_ASSERT(path != NULL);
CLReport(85,
OS_PathSpecToString(path->spec, STSbuf, sizeof(STSbuf)),
((path->flags & 2) && path->recursive) ? " [d] [r]" : (path->flags & 2) ? " [d]" : path->recursive ? " [r]" : ""
);
if (path->recursive && optsCmdLine.verbose > 2) {
UInt16 j;
for (j = 0; j < Paths_Count(path->recursive); j++) {
Path *sub = Paths_GetPath(path->recursive, j);
#line 1039
OPTION_ASSERT(sub);
CLReport(85, "\t", OS_PathSpecToString(sub->spec, STSbuf, sizeof(STSbuf)));
}
}
}
}
if (clState.plugintype == CWDROPINCOMPILERTYPE)
CLReport(84, "System include search paths ([d] = default, [r] = recursive)");
if (!Paths_Count(&gTarg->sysPaths))
CLReport(85, "(none)", "");
for (i = 0; i < Paths_Count(&gTarg->sysPaths); i++) {
Path *path = Paths_GetPath(&gTarg->sysPaths, i);
#line 1054
OPTION_ASSERT(path != NULL);
CLReport(85,
OS_PathSpecToString(path->spec, STSbuf, sizeof(STSbuf)),
((path->flags & 2) && path->recursive) ? " [d] [r]" : (path->flags & 2) ? " [d]" : path->recursive ? " [r]" : ""
);
if (path->recursive && optsCmdLine.verbose > 2) {
UInt16 j;
for (j = 0; j < Paths_Count(path->recursive); j++) {
Path *sub = Paths_GetPath(path->recursive, j);
#line 1069
OPTION_ASSERT(sub);
CLReport(85, "\t", OS_PathSpecToString(sub->spec, STSbuf, sizeof(STSbuf)));
}
}
}
if (clState.plugintype == CWDROPINCOMPILERTYPE)
CLReport(84, "Files in project (relative to CWD)");
else
CLReport(84, "Link order for project (relative to CWD)");
for (i = 0; i < Files_Count(&gTarg->files); i++) {
File *file = Files_GetFile(&gTarg->files, i);
if (!VFiles_Find(gTarg->virtualFiles, file->srcfilename))
CLReport(85, OS_SpecToStringRelative(&file->srcfss, NULL, STSbuf, sizeof(STSbuf)), "");
else
CLReport(85, file->srcfilename, "\t(virtual file)");
}
}
int CompileFilesInProject(void) {
struct BuildInfo *tinfo;
SInt32 index;
SInt32 startTime;
SInt32 endTime;
int ignored;
int compiled;
Boolean failed;
failed = 0;
startTime = OS_GetMilliseconds();
InitializeIncludeCache();
if (optsCmdLine.verbose > 1)
DumpFileAndPathInfo();
if (!SendTargetInfoRequest(gTarg, gTarg->linker, gTarg->linkerDropinFlags))
return Result_Failed;
ignored = 0;
compiled = 0;
for (index = 0; index < Files_Count(&gTarg->files); index++) {
int ret;
File *file;
Boolean wascompiled;
file = Files_GetFile(&gTarg->files, index);
if (!file->outfileowner)
file->outfileowner = CmdLineStageMask_Cg;
ret = CompileEntry(file, &wascompiled);
if (ret) {
if (wascompiled)
compiled++;
if (!wascompiled)
ignored++;
if (CheckForUserBreak())
return Result_Cancelled;
}
if (!ret) {
if (optsCompiler.noFail) {
failed = 1;
clState.countWarnings = 0;
clState.countErrors = 0;
clState.withholdWarnings = 0;
clState.withholdErrors = 0;
} else {
return CheckForUserBreak() ? Result_Cancelled : Result_Failed;
}
}
}
if (optsCmdLine.stages & CmdLineStageMask_Dp) {
for (index = 0; index < Files_Count(&gTarg->pchs); index++) {
int ret;
File *file;
file = Files_GetFile(&gTarg->pchs, index);
ret = DependencyMapFile(file, 0);
if (!ret) {
if (optsCompiler.noFail) {
failed = 1;
clState.countWarnings = 0;
clState.countErrors = 0;
clState.withholdWarnings = 0;
clState.withholdErrors = 0;
} else {
return CheckForUserBreak() ? Result_Cancelled : Result_Failed;
}
}
}
}
CleanupIncludeCache();
tinfo = &gTarg->info;
if (optsCmdLine.verbose && compiled > 1) {
const char *cun;
const char *dun;
const char *uun;
cun = dun = uun = "bytes";
CLReport(27, tinfo->codeSize, cun, tinfo->iDataSize, dun, tinfo->uDataSize, uun);
}
endTime = OS_GetMilliseconds();
if (optsCmdLine.timeWorking)
CLReport(24, (endTime - startTime) / 1000.0, "compile", "", "", "project");
if (ignored > 0 && compiled == 0 && (gTarg->preLinker || gTarg->linker))
CLReportError(29);
if (failed)
return Result_Failed;
return CheckForUserBreak() ? Result_Cancelled : Result_Success;
}
static int PostLinkFilesInProject(void) {
SInt32 index;
SInt32 startTime;
SInt32 endTime;
File *file;
FSSpec fss;
startTime = OS_GetMilliseconds();
for (index = 0; index < Files_Count(&gTarg->files); index++) {
file = Files_GetFile(&gTarg->files, index);
OS_OSSpec_To_FSSpec(&file->srcfss, &fss);
gTarg->targetinfo->outfile = fss;
gTarg->targetinfo->runfile = fss;
gTarg->targetinfo->symfile = fss;
if (!SendLinkerRequest(gTarg->postLinker, gTarg->postLinkerDropinFlags, gTarg->targetinfo)) {
return CheckForUserBreak() ? Result_Cancelled : Result_Failed;
} else {
if (CheckForUserBreak())
return Result_Cancelled;
}
}
endTime = OS_GetMilliseconds();
if (optsCmdLine.timeWorking)
CLReport(24, (endTime - startTime) / 1000.0, "compile", "", "", "project");
return CheckForUserBreak() ? Result_Cancelled : Result_Success;
}
int LinkProject(void) {
SInt32 startTime;
SInt32 endTime;
startTime = OS_GetMilliseconds();
if (!SendTargetInfoRequest(gTarg, gTarg->linker, gTarg->linkerDropinFlags))
return Result_Failed;
if (!SetupTemporaries())
return Result_Failed;
if (gTarg->preLinker && optsLinker.callPreLinker && optsCmdLine.state == OptsCmdLineState_3) {
SInt32 subStart;
SInt32 subEnd;
subStart = OS_GetMilliseconds();
if (gTarg->preLinkerDropinFlags & dropInExecutableTool) {
if (!ExecuteLinker(gTarg->preLinker, gTarg->preLinkerDropinFlags, NULL, NULL, NULL))
return Result_Failed;
} else if (!optsCmdLine.dryRun) {
if (!SendLinkerRequest(gTarg->preLinker, gTarg->preLinkerDropinFlags, gTarg->targetinfo))
return CheckForUserBreak() ? Result_Cancelled : Result_Failed;
}
subEnd = OS_GetMilliseconds();
if (optsCmdLine.timeWorking)
CLReport(24, (subEnd - subStart) / 1000.0, "prelink project", "", "", "");
}
if (gTarg->linker && optsLinker.callLinker && optsCmdLine.state == OptsCmdLineState_3) {
SInt32 subStart;
SInt32 subEnd;
subStart = OS_GetMilliseconds();
if (gTarg->linkerDropinFlags & dropInExecutableTool) {
if (!ExecuteLinker(gTarg->linker, gTarg->linkerDropinFlags, NULL, NULL, NULL))
return Result_Failed;
} else if (!optsCmdLine.dryRun) {
if (!SendLinkerRequest(gTarg->linker, gTarg->linkerDropinFlags, gTarg->targetinfo))
return CheckForUserBreak() ? Result_Cancelled : Result_Failed;
}
subEnd = OS_GetMilliseconds();
if (optsCmdLine.timeWorking)
CLReport(24, (subEnd - subStart) / 1000.0, "link project", "", "", "");
}
if (gTarg->postLinker && optsLinker.callPostLinker && optsCmdLine.state == OptsCmdLineState_3) {
SInt32 subStart;
SInt32 subEnd;
FSSpec fss;
OSSpec outfile;
subStart = OS_GetMilliseconds();
if (gTarg->postLinkerDropinFlags & dropInExecutableTool) {
if (!ExecuteLinker(gTarg->postLinker, gTarg->postLinkerDropinFlags, NULL, NULL, NULL))
return Result_Failed;
} else if (!optsCmdLine.dryRun) {
if (!SendTargetInfoRequest(gTarg, gTarg->linker, gTarg->linkerDropinFlags))
return Result_Failed;
if (gTarg->targetinfo->outputType == linkOutputFile)
fss = gTarg->targetinfo->outfile;
if (gTarg->targetinfo->outputType != linkOutputNone) {
if (!SendLinkerRequest(gTarg->postLinker, gTarg->postLinkerDropinFlags, gTarg->targetinfo))
return CheckForUserBreak() ? Result_Cancelled : Result_Failed;
if (!SendTargetInfoRequest(gTarg, gTarg->postLinker, gTarg->postLinkerDropinFlags))
return Result_Failed;
}
}
subEnd = OS_GetMilliseconds();
if (optsCmdLine.timeWorking)
CLReport(24, (subEnd - subStart) / 1000.0, "postlink project", "", "", "");
if (!optsLinker.keepLinkerOutput && gTarg->targetinfo->outputType == linkOutputFile) {
if (optsCmdLine.verbose > 1) {
OS_FSSpec_To_OSSpec(&fss, &outfile);
CLReport(19, OS_SpecToString(&outfile, STSbuf, sizeof(STSbuf)));
}
FSpDelete(&fss);
}
}
if (!DeleteTemporaries())
return Result_Failed;
endTime = OS_GetMilliseconds();
if (optsCmdLine.timeWorking)
CLReport(24, (endTime - startTime) / 1000.0, "finish link stage", "", "", "");
return Result_Success;
}