mirror of https://git.wuffs.org/MWCC
514 lines
19 KiB
C++
514 lines
19 KiB
C++
#include "plugin_internal.h"
|
|
|
|
// Forward declarations
|
|
CWResult OSErrtoCWResult(OSErr err);
|
|
|
|
static Boolean ValidateContext(CWPluginContext context) {
|
|
return context
|
|
&& (context->shellSignature == CWFOURCHAR('C','W','I','E'))
|
|
&& (context->request != reqInitialize)
|
|
&& (context->request != reqTerminate)
|
|
&& (context->request != reqIdle);
|
|
}
|
|
|
|
static Boolean ValidateInitTermContext(CWPluginContext context) {
|
|
return context
|
|
&& (context->shellSignature == CWFOURCHAR('C','W','I','E'))
|
|
&& ((context->request == reqInitialize)
|
|
|| (context->request == reqTerminate)
|
|
|| (context->request == reqIdle));
|
|
}
|
|
|
|
static Boolean IsVCSContext(CWPluginContext context) {
|
|
return context && (context->pluginType == CWDROPINVCSTYPE);
|
|
}
|
|
|
|
CW_CALLBACK CWGetPluginRequest(CWPluginContext context, SInt32 *request) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (request == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*request = context->request;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetAPIVersion(CWPluginContext context, SInt32 *version) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (version == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*version = context->apiVersion;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetIDEInfo(CWPluginContext context, CWIDEInfo *info) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (info == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*info = *context->shellInfo;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetCallbackOSError(CWPluginContext context, CWOSResult *error) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (error == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*error = context->callbackOSError;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWSetPluginOSError(CWPluginContext context, CWOSResult error) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
|
|
context->pluginOSError = error;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetProjectFile(CWPluginContext context, CWFileSpec *projectSpec) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (projectSpec == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*projectSpec = context->projectFile;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetTargetDataDirectory(CWPluginContext context, CWFileSpec *targetDataDirectorySpec) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (targetDataDirectorySpec == NULL)
|
|
return cwErrInvalidParameter;
|
|
if (context->targetDataDirectorySpec == NULL)
|
|
return cwErrInvalidCallback;
|
|
|
|
*targetDataDirectorySpec = *context->targetDataDirectorySpec;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetTargetName(CWPluginContext context, char *name, short maxLength) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
|
|
if (context->apiVersion >= 8)
|
|
return context->callbacks->cbGetTargetName(context, name, maxLength);
|
|
else
|
|
return cwErrRequestFailed;
|
|
}
|
|
|
|
CW_CALLBACK CWGetProjectFileCount(CWPluginContext context, SInt32 *count) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (count == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*count = context->numFiles;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetOutputFileDirectory(CWPluginContext context, CWFileSpec *outputFileDirectory) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (outputFileDirectory == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*outputFileDirectory = context->outputFileDirectory;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetOverlay1GroupsCount(CWPluginContext context, SInt32 *count) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (count == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
*count = context->numOverlayGroups;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetFileInfo(CWPluginContext context, SInt32 whichfile, Boolean checkFileLocation, CWProjectFileInfo *fileinfo) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (fileinfo == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
return context->callbacks->cbGetFileInfo(context, whichfile, checkFileLocation, fileinfo);
|
|
}
|
|
|
|
CW_CALLBACK CWFindAndLoadFile(CWPluginContext context, const char *filename, CWFileInfo *fileinfo) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (filename == NULL)
|
|
return cwErrInvalidParameter;
|
|
if (fileinfo == NULL)
|
|
return cwErrInvalidParameter;
|
|
|
|
return context->callbacks->cbFindAndLoadFile(context, filename, fileinfo);
|
|
}
|
|
|
|
static CWResult EnsureCachedAccessPaths(CWPluginContext context) {
|
|
if (!context->accessPathList) {
|
|
CWResult res = context->callbacks->cbCacheAccessPathList(context);
|
|
if (res)
|
|
return res;
|
|
if (!context->accessPathList)
|
|
return cwErrRequestFailed;
|
|
}
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetAccessPathListInfo(CWPluginContext context, CWAccessPathListInfo *pathListInfo) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (pathListInfo == NULL)
|
|
return cwErrInvalidParameter;
|
|
if (context->apiVersion < 10)
|
|
return cwErrInvalidCallback;
|
|
CWResult res = EnsureCachedAccessPaths(context);
|
|
if (res)
|
|
return res;
|
|
pathListInfo->systemPathCount = context->accessPathList->systemPathCount;
|
|
pathListInfo->userPathCount = context->accessPathList->userPathCount;
|
|
pathListInfo->alwaysSearchUserPaths = context->accessPathList->alwaysSearchUserPaths;
|
|
pathListInfo->convertPaths = context->accessPathList->convertPaths;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetAccessPathInfo(CWPluginContext context, CWAccessPathType pathType, SInt32 whichPath, CWAccessPathInfo *pathInfo) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (pathInfo == NULL)
|
|
return cwErrInvalidParameter;
|
|
if (context->apiVersion < 10)
|
|
return cwErrInvalidCallback;
|
|
CWResult res = EnsureCachedAccessPaths(context);
|
|
if (res)
|
|
return res;
|
|
|
|
IDEAccessPath *paths;
|
|
SInt32 count;
|
|
switch (pathType) {
|
|
case cwSystemPath:
|
|
paths = context->accessPathList->systemPaths;
|
|
count = context->accessPathList->systemPathCount;
|
|
break;
|
|
case cwUserPath:
|
|
paths = context->accessPathList->userPaths;
|
|
count = context->accessPathList->userPathCount;
|
|
break;
|
|
default:
|
|
return cwErrInvalidParameter;
|
|
}
|
|
|
|
if (whichPath < 0 || whichPath >= count)
|
|
return cwErrInvalidParameter;
|
|
|
|
IDEAccessPath *path = &paths[whichPath];
|
|
pathInfo->pathSpec = path->pathSpec;
|
|
pathInfo->recursive = path->recursive;
|
|
pathInfo->subdirectoryCount = path->subdirectoryCount;
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetAccessPathSubdirectory(CWPluginContext context, CWAccessPathType pathType, SInt32 whichPath,
|
|
SInt32 whichSubdirectory, CWFileSpec *subdirectory) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (subdirectory == NULL)
|
|
return cwErrInvalidParameter;
|
|
if (context->apiVersion < 10)
|
|
return cwErrInvalidCallback;
|
|
CWResult res = EnsureCachedAccessPaths(context);
|
|
if (res)
|
|
return res;
|
|
|
|
IDEAccessPath *paths;
|
|
SInt32 count;
|
|
switch (pathType) {
|
|
case cwSystemPath:
|
|
paths = context->accessPathList->systemPaths;
|
|
count = context->accessPathList->systemPathCount;
|
|
break;
|
|
case cwUserPath:
|
|
paths = context->accessPathList->userPaths;
|
|
count = context->accessPathList->userPathCount;
|
|
break;
|
|
default:
|
|
return cwErrInvalidParameter;
|
|
}
|
|
|
|
if (whichPath < 0 || whichPath >= count)
|
|
return cwErrInvalidParameter;
|
|
|
|
IDEAccessPath *path = &paths[whichPath];
|
|
if (whichSubdirectory < 0 || whichSubdirectory >= path->subdirectoryCount)
|
|
return cwErrInvalidParameter;
|
|
|
|
*subdirectory = path->subdirectories[whichSubdirectory];
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetFileText(CWPluginContext context, const CWFileSpec *filespec, const char **text, SInt32 *textLength,
|
|
short *filedatatype) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!filespec)
|
|
return cwErrInvalidParameter;
|
|
if (!text)
|
|
return cwErrInvalidParameter;
|
|
if (!textLength)
|
|
return cwErrInvalidParameter;
|
|
if (!filedatatype)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetFileText(context, filespec, text, textLength, filedatatype);
|
|
}
|
|
|
|
CW_CALLBACK CWReleaseFileText(CWPluginContext context, const char *text) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
|
|
if (text)
|
|
return context->callbacks->cbReleaseFileText(context, text);
|
|
else
|
|
return cwNoErr;
|
|
}
|
|
|
|
CW_CALLBACK CWGetSegmentInfo(CWPluginContext context, SInt32 whichsegment, CWProjectSegmentInfo *segmentinfo) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!segmentinfo)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetSegmentInfo(context, whichsegment, segmentinfo);
|
|
}
|
|
|
|
CW_CALLBACK CWGetOverlay1GroupInfo(CWPluginContext context, SInt32 whichgroup, CWOverlay1GroupInfo *groupinfo) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!groupinfo)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetOverlay1GroupInfo(context, whichgroup, groupinfo);
|
|
}
|
|
|
|
CW_CALLBACK
|
|
CWGetOverlay1Info(CWPluginContext context, SInt32 whichgroup, SInt32 whichoverlay, CWOverlay1Info *overlayinfo) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!overlayinfo)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetOverlay1Info(context, whichgroup, whichoverlay, overlayinfo);
|
|
}
|
|
|
|
CW_CALLBACK CWGetOverlay1FileInfo(CWPluginContext context, SInt32 whichgroup, SInt32 whichoverlay, SInt32 whichoverlayfile,
|
|
CWOverlay1FileInfo *fileinfo) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!fileinfo)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetOverlay1FileInfo(context, whichgroup, whichoverlay, whichoverlayfile, fileinfo);
|
|
}
|
|
|
|
CW_CALLBACK CWReportMessage(CWPluginContext context, const CWMessageRef *msgRef, const char *line1, const char *line2,
|
|
short errorlevel, SInt32 errorNumber) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbReportMessage(context, msgRef, line1, line2, errorlevel, errorNumber);
|
|
}
|
|
|
|
CW_CALLBACK CWAlert(CWPluginContext context, const char *msg1, const char *msg2, const char *msg3, const char *msg4) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbAlert(context, msg1, msg2, msg3, msg4);
|
|
}
|
|
|
|
CW_CALLBACK CWShowStatus(CWPluginContext context, const char *line1, const char *line2) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbShowStatus(context, line1, line2);
|
|
}
|
|
|
|
CW_CALLBACK CWUserBreak(CWPluginContext context) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbUserBreak(context);
|
|
}
|
|
|
|
CW_CALLBACK CWGetNamedPreferences(CWPluginContext context, const char *prefsname, CWMemHandle *prefsdata) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!prefsname)
|
|
return cwErrInvalidParameter;
|
|
if (!prefsdata)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetNamedPreferences(context, prefsname, prefsdata);
|
|
}
|
|
|
|
CW_CALLBACK CWStorePluginData(CWPluginContext context, SInt32 whichfile, CWDataType type, CWMemHandle prefsdata) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbStorePluginData(context, whichfile, type, prefsdata);
|
|
}
|
|
|
|
CW_CALLBACK CWGetPluginData(CWPluginContext context, SInt32 whichfile, CWDataType type, CWMemHandle *prefsdata) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetPluginData(context, whichfile, type, prefsdata);
|
|
}
|
|
|
|
CW_CALLBACK CWSetModDate(CWPluginContext context, const CWFileSpec *filespec, CWFileTime *moddate, Boolean isGenerated) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!filespec)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbSetModDate(context, filespec, moddate, isGenerated);
|
|
}
|
|
|
|
CW_CALLBACK CWAddProjectEntry(CWPluginContext context, const CWFileSpec *fileSpec, Boolean isGenerated,
|
|
const CWNewProjectEntryInfo *projectEntryInfo, SInt32 *whichfile) {
|
|
if (IsVCSContext(context) || !ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!fileSpec)
|
|
return cwErrInvalidParameter;
|
|
if (context->apiVersion < 8)
|
|
return cwErrRequestFailed;
|
|
return context->callbacks->cbAddProjectEntry(context, fileSpec, isGenerated, projectEntryInfo, whichfile);
|
|
}
|
|
|
|
CW_CALLBACK CWCreateNewTextDocument(CWPluginContext context, const CWNewTextDocumentInfo *docinfo) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!docinfo)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbCreateNewTextDocument(context, docinfo);
|
|
}
|
|
|
|
CW_CALLBACK CWAllocateMemory(CWPluginContext context, SInt32 size, Boolean isPermanent, void **ptr) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!ptr)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbAllocateMemory(context, size, isPermanent, ptr);
|
|
}
|
|
|
|
CW_CALLBACK CWFreeMemory(CWPluginContext context, void *ptr, Boolean isPermanent) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!ptr)
|
|
return cwNoErr;
|
|
return context->callbacks->cbFreeMemory(context, ptr, isPermanent);
|
|
}
|
|
|
|
CW_CALLBACK CWAllocMemHandle(CWPluginContext context, SInt32 size, Boolean useTempMemory, CWMemHandle *handle) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!handle)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbAllocMemHandle(context, size, useTempMemory, handle);
|
|
}
|
|
|
|
CW_CALLBACK CWFreeMemHandle(CWPluginContext context, CWMemHandle handle) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbFreeMemHandle(context, handle);
|
|
}
|
|
|
|
CW_CALLBACK CWGetMemHandleSize(CWPluginContext context, CWMemHandle handle, SInt32 *size) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!size)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbGetMemHandleSize(context, handle, size);
|
|
}
|
|
|
|
CW_CALLBACK CWResizeMemHandle(CWPluginContext context, CWMemHandle handle, SInt32 newSize) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbResizeMemHandle(context, handle, newSize);
|
|
}
|
|
|
|
CW_CALLBACK CWLockMemHandle(CWPluginContext context, CWMemHandle handle, Boolean moveHi, void **ptr) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (!ptr)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbLockMemHandle(context, handle, moveHi, ptr);
|
|
}
|
|
|
|
CW_CALLBACK CWUnlockMemHandle(CWPluginContext context, CWMemHandle handle) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbUnlockMemHandle(context, handle);
|
|
}
|
|
|
|
CW_CALLBACK CWDonePluginRequest(CWPluginContext, CWResult resultCode) {
|
|
return resultCode;
|
|
}
|
|
|
|
CW_CALLBACK CWPreDialog(CWPluginContext context) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbPreDialog(context);
|
|
}
|
|
|
|
CW_CALLBACK CWPostDialog(CWPluginContext context) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbPostDialog(context);
|
|
}
|
|
|
|
CW_CALLBACK CWPreFileAction(CWPluginContext context, const CWFileSpec *theFile) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbPreFileAction(context, theFile);
|
|
}
|
|
|
|
CW_CALLBACK CWPostFileAction(CWPluginContext context, const CWFileSpec *theFile) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbPostFileAction(context, theFile);
|
|
}
|
|
|
|
CW_CALLBACK CWCheckoutLicense(CWPluginContext context, const char *featureName, const char *licenseVersion, SInt32 flags, void *reserved, SInt32 *cookie) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbCheckoutLicense(context, featureName, licenseVersion, flags, reserved, cookie);
|
|
}
|
|
|
|
CW_CALLBACK CWCheckinLicense(CWPluginContext context, SInt32 cookie) {
|
|
if (!ValidateContext(context) && !ValidateInitTermContext(context))
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbCheckinLicense(context, cookie);
|
|
}
|
|
|
|
CW_CALLBACK CWResolveRelativePath(CWPluginContext context, const CWRelativePath *relativePath, CWFileSpec *fileSpec, Boolean create) {
|
|
if (!ValidateContext(context))
|
|
return cwErrInvalidParameter;
|
|
if (relativePath == NULL)
|
|
return cwErrInvalidParameter;
|
|
if (fileSpec == NULL)
|
|
return cwErrInvalidParameter;
|
|
return context->callbacks->cbResolveRelativePath(context, relativePath, fileSpec, create);
|
|
}
|
|
|
|
CW_CALLBACK CWMacOSErrToCWResult(CWPluginContext context, OSErr err) {
|
|
return OSErrtoCWResult(err);
|
|
}
|
|
|
|
CWResult OSErrtoCWResult(OSErr err) {
|
|
switch (err) {
|
|
case noErr: return cwNoErr;
|
|
case userCanceledErr: return cwErrUserCanceled;
|
|
case paramErr: return cwErrInvalidParameter;
|
|
case memFullErr: return cwErrOutOfMemory;
|
|
case fnfErr: return cwErrFileNotFound;
|
|
default: return cwErrRequestFailed;
|
|
}
|
|
}
|
|
|