summaryrefslogtreecommitdiff
path: root/unsorted/ParserHelpers.c
diff options
context:
space:
mode:
authorAsh Wolf <ninji@wuffs.org>2022-10-14 23:15:32 +0100
committerAsh Wolf <ninji@wuffs.org>2022-10-14 23:15:32 +0100
commit775b6861666af36d317fb577cf489e2c6377f878 (patch)
tree2ae8c829eb861c85a6e2b5acf42f51919a0d78f2 /unsorted/ParserHelpers.c
parentb8df05413a4e8b299de07b915cddce73a3bb16e3 (diff)
downloadMWCC-775b6861666af36d317fb577cf489e2c6377f878.tar.gz
MWCC-775b6861666af36d317fb577cf489e2c6377f878.zip
add tons of stuff
Diffstat (limited to '')
-rw-r--r--unsorted/ParserHelpers.c534
1 files changed, 534 insertions, 0 deletions
diff --git a/unsorted/ParserHelpers.c b/unsorted/ParserHelpers.c
new file mode 100644
index 0000000..c8d4c55
--- /dev/null
+++ b/unsorted/ParserHelpers.c
@@ -0,0 +1,534 @@
+#include "mwcc_decomp.h"
+#include <errno.h>
+
+SInt16 lastStage;
+Boolean dashIMinusMovesPaths;
+Boolean usedDashIMinus;
+Boolean namingSysPaths;
+static char STSbuf[256];
+
+int FindFileInPath(const char *filename, OSSpec *fss) {
+ CWFileInfo fi;
+ CWResult result;
+
+ fi.fullsearch = 1;
+ fi.dependencyType = 0;
+ fi.suppressload = 1;
+ fi.isdependentoffile = kCurrentCompiledFile;
+
+ result = CWFindAndLoadFile(parseopts.context, filename, &fi);
+ if (!result) {
+ OS_FSSpec_To_OSSpec(&fi.filespec, fss);
+ return 1;
+ } else {
+ return 0;
+ }
+}
+
+char *GetEnvVar(const char *name, Boolean warn, const char **match) {
+ const char *nptr;
+ const char *last;
+ char *ret;
+
+ nptr = name;
+ last = name;
+ while (*nptr) {
+ ret = getenv(nptr);
+ if (ret) {
+ if (match)
+ *match = nptr;
+ return ret;
+ }
+ last = nptr;
+ nptr = &nptr[1 + strlen(nptr)];
+ }
+
+ if (warn)
+ CLPReportWarning(52, last);
+ *match = 0;
+ return 0;
+}
+
+static Boolean MatchesExtension(const char *list, const char *filename) {
+ char *fn;
+ const char *eptr;
+ const char *ptr;
+
+ fn = OS_GetFileNamePtr((char *) filename);
+ eptr = strrchr(fn, '.');
+ if (!eptr)
+ return 0;
+ if (!list)
+ return 1;
+
+ ptr = eptr;
+ while (*list) {
+ if (*list == '|' && !*ptr)
+ return 1;
+
+ if (my_tolower(*list) == my_tolower(*ptr)) {
+ list++;
+ ptr++;
+ continue;
+ }
+
+ while (*list && *list != '|')
+ list++;
+ if (*list)
+ list++;
+ ptr = eptr;
+ }
+
+ return !*list && !*ptr;
+}
+
+int Opt_AddAccessPath(const char *opt, void *var, const char *arg) {
+ OSPathSpec spec;
+ int err;
+
+ arg = arg ? arg : opt;
+ if (!arg)
+ return 0;
+ if (!arg[0])
+ return 1;
+
+ if (strlen(arg) >= 256) {
+ CLPReportError(13, arg + strlen(arg) - 32, 256);
+ return 0;
+ }
+
+ err = OS_MakePathSpec(0, arg, &spec);
+ if (err == ENOENT || err == ENOENT) {
+ CLPReportWarning(45, arg);
+ return 1;
+ } else if (err != 0) {
+ CLPOSAlert(45, err, arg);
+ return 1;
+ }
+
+ // this 'if' gets optimised unnecessarily
+ if (!AddAccessPath(&spec, namingSysPaths, 0, var != NULL))
+ return 0;
+ else
+ return 1;
+}
+
+int Opt_AddFrameworkPath(const char *opt, void *var, const char *arg) {
+ OSPathSpec spec;
+ int err;
+
+ arg = arg ? arg : opt;
+ if (!arg)
+ return 0;
+ if (!arg[0])
+ return 1;
+
+ if (strlen(arg) >= 256) {
+ CLPReportError(13, arg + strlen(arg) - 32, 256);
+ return 0;
+ }
+
+ err = OS_MakePathSpec(0, arg, &spec);
+ if (err == ENOENT || err == ENOENT) {
+ CLPReportWarning(45, arg);
+ return 1;
+ } else if (err != 0) {
+ CLPOSAlert(45, err, arg);
+ return 1;
+ } else {
+ Frameworks_AddPath(&spec);
+ return 1;
+ }
+}
+
+int Opt_AddFramework(const char *opt, void *var, const char *arg) {
+ if (!Frameworks_AddFramework(arg ? arg : opt, 0, 0))
+ return 0;
+ else
+ return 1;
+}
+
+void ListParseMessage(void (*errprint)(const char *, va_list), const char *envvar, SInt16 id, ...) {
+ char buf[1024];
+ va_list ap;
+
+ if (envvar && envvar[0])
+ sprintf(buf, "In environment variable '%s':\n", envvar);
+ else
+ buf[0] = 0;
+
+ CLPGetErrorString(id, buf + strlen(buf));
+ va_start(ap, id);
+ errprint(buf, ap);
+ va_end(ap);
+}
+
+int AddAccessPathList(const char *list, char sep1, char sep2, int source, char *text, Boolean system, SInt32 position, Boolean recursive) {
+ char tmp[256];
+ Boolean recurse;
+ OSPathSpec spec;
+ int err;
+ short type;
+ char *ptr;
+
+ type = (Boolean) ((system == 1) ? 1 : 0) | (!source ? 0 : 2);
+ recurse = (list[0] == '+');
+ if (recurse)
+ ++list;
+
+ if (!strchr(list, sep1))
+ sep1 = sep2;
+
+ while (*list) {
+ ptr = tmp;
+ while (*list && *list != sep1 && (ptr + 1) < &tmp[256]) {
+ *(ptr++) = *(list++);
+ }
+ *ptr = 0;
+
+ if ((ptr + 1) >= &tmp[256]) {
+ ListParseMessage(
+ CLPReportError_V,
+ (source == 1) ? text : NULL,
+ 9,
+ tmp,
+ tmp + strlen(tmp) - 16,
+ 256);
+ return 0;
+ }
+
+ err = OS_MakePathSpec(0, tmp, &spec);
+ if (err) {
+ ListParseMessage(
+ CLPReportWarning_V,
+ (source == 1) ? text : NULL,
+ 45,
+ tmp);
+ } else {
+ AddAccessPath(&spec, type, position, recurse ^ recursive);
+ }
+
+ if (*list)
+ ++list;
+ recurse = *list == '+';
+ if (recurse)
+ ++list;
+ }
+
+ return 1;
+}
+
+int Opt_FindAndAddFile(const char *opt, void *var, const char *arg) {
+ OSSpec spec;
+ int err;
+ Boolean isfile;
+
+ arg = arg ? arg : opt;
+ if (!arg)
+ return 0;
+ if (!*arg)
+ return 1;
+
+ parseopts.userSpecifiedFiles++;
+ err = OS_MakeSpec(arg, &spec, &isfile);
+ if (!err)
+ err = OS_Status(&spec);
+
+ if (!err && !isfile) {
+ CLPReportError(47, arg);
+ parseopts.unusedFiles++;
+ return 0;
+ } else if (err && err != ENOENT) {
+ CLPOSAlert(44, err, arg);
+ parseopts.unusedFiles++;
+ return 0;
+ } else if (err && parseopts.alwaysUsePaths) {
+ err = FindFileInPath(arg, &spec) ? 0 : ENOENT;
+ }
+
+ if (err) {
+ CLPReportError(44, arg);
+ parseopts.unusedFiles++;
+ return 0;
+ }
+
+ if (var && !MatchesExtension((const char *) var, arg))
+ CLPReportWarning(76, arg, var);
+
+ if (!AddFileToProject(&spec, lastStage, parseopts.lastoutputname, 1, -1)) {
+ parseopts.unusedFiles++;
+ return 0;
+ } else {
+ parseopts.lastoutputname[0] = 0;
+ return 1;
+ }
+}
+
+int Opt_FindAndAddFileRef(const char *opt, void *var, const char *arg) {
+ OSSpec spec;
+ int err;
+ Boolean isfile;
+
+ arg = arg ? arg : opt;
+ if (!arg)
+ return 0;
+ if (!*arg)
+ return 1;
+
+ parseopts.userSpecifiedFiles++;
+ if (var && !MatchesExtension((const char *) var, arg))
+ CLPReportWarning(76, arg, var);
+
+ err = OS_MakeSpec(arg, &spec, &isfile);
+ if (!err)
+ err = OS_Status(&spec);
+
+ if (!err && !isfile) {
+ CLPReportError(47, arg);
+ parseopts.unusedFiles++;
+ return 0;
+ } else if (err && parseopts.alwaysUsePaths) {
+ err = FindFileInPath(arg, &spec) ? 0 : ENOENT;
+ }
+
+ if (!AddFileToProject(&spec, 0, 0, err == 0, -1)) {
+ parseopts.unusedFiles++;
+ return 0;
+ } else {
+ return AddAccessPath(&spec.path, 1, -1, 0) != 0;
+ }
+}
+
+int Opt_AddUnixLibraryFile(const char *opt, void *var, const char *name) {
+ OSSpec spec;
+ Boolean failed;
+ const char *eptr;
+ const char *eend;
+ char tmpname[64];
+
+ if (strlen(name) >= 56) {
+ CLPReportError(13, name + strlen(name) - 32, 64);
+ return 0;
+ }
+
+ failed = 1;
+ if (!var)
+ var = ".lib|.a";
+
+ eptr = (const char *) var;
+ while (eptr && *eptr) {
+ eend = eptr;
+ while (*eend && *eend != '|')
+ ++eend;
+
+ sprintf(tmpname, "lib%s%*.*s", name, eend - eptr, eend - eptr, eptr);
+ if (FindFileInPath(tmpname, &spec)) {
+ failed = 0;
+ break;
+ }
+
+ if (*eend)
+ eptr = eend + 1;
+ else
+ eptr = eend;
+ }
+
+ if (failed) {
+ failed = !FindFileInPath(name, &spec);
+ if (failed)
+ CLPReportError(49, name, var, name);
+ }
+
+ if (!failed) {
+ if (!AddFileToProject(&spec, 0, 0, 1, -1)) {
+ parseopts.unusedFiles++;
+ failed = 1;
+ }
+ }
+
+ return !failed;
+}
+
+int AddFileList(const char *list, char sep1, char sep2, int source, char *text, SInt32 position) {
+ char tmp[256];
+ OSSpec spec;
+ char *ptr;
+
+ if (!strchr(list, sep1))
+ sep1 = sep2;
+
+ while (*list) {
+ ptr = tmp;
+ while (*list && *list != sep1 && (ptr + 1) < &tmp[256]) {
+ *(ptr++) = *(list++);
+ }
+ *ptr = 0;
+
+ if ((ptr + 1) >= &tmp[256]) {
+ ListParseMessage(
+ CLPReportError_V,
+ (source == 1) ? text : 0,
+ 9,
+ tmp,
+ tmp + strlen(tmp) - 16,
+ 256
+ );
+ return 0;
+ }
+
+ if (!FindFileInPath(tmp, &spec)) {
+ if (OS_IsDir(&spec)) {
+ ListParseMessage(
+ CLPReportError_V,
+ (source == 1) ? text : 0,
+ 16,
+ tmp
+ );
+ } else {
+ ListParseMessage(
+ CLPReportWarning_V,
+ (source == 1) ? text : 0,
+ 44,
+ tmp
+ );
+ }
+ } else {
+ AddFileToProject(&spec, 0, 0, 1, position);
+ }
+
+ if (*list)
+ ++list;
+ }
+
+ return 1;
+}
+
+int IsFileInOutputDirectory(const OSSpec *file) {
+ OSPathSpec outdir;
+ GetOutputFileDirectory(&outdir);
+ return OS_EqualPathSpec(&outdir, &file->path);
+}
+
+void GetCFileNameInOutputDirectory(const char *input, char *name, int maxlen) {
+ char filename[64];
+ OSSpec spec;
+ int err;
+
+ err = OS_MakeFileSpec(input, &spec);
+ if (err) {
+ CLPOSAlert(64, err, input);
+ name[0] = 0;
+ return;
+ }
+
+ if (!IsFileInOutputDirectory(&spec)) {
+ CLPReportWarning(61, OS_SpecToStringRelative(&spec, 0, STSbuf, sizeof(STSbuf)));
+ }
+
+ OS_NameSpecToString(&spec.name, filename, 256);
+ if (strlen(filename) >= maxlen) {
+ CLPReportWarning(65, filename, maxlen - 1);
+ filename[maxlen - 1] = 0;
+ }
+
+ strcpy(name, filename);
+}
+
+void GetPFileNameInOutputDirectory(const char *input, unsigned char *name, int len) {
+ GetCFileNameInOutputDirectory(input, (char *) name, len);
+ c2pstr((char *) name);
+}
+
+void AddStringLenToHandle(Handle *h, const char *str, int len) {
+ SInt32 old;
+
+ if (!*h) {
+ if ((*h = NewHandle(len + 1))) {
+ HLock(*h);
+ memcpy(**h, str, len);
+ (**h)[len] = 0;
+ HUnlock(*h);
+ } else {
+ exit(-23);
+ }
+ } else {
+ old = GetHandleSize(*h) - 1;
+ SetHandleSize(*h, old + len + 1);
+ if (MemError() == noErr) {
+ HLock(*h);
+ memcpy(**h + old, str, len);
+ (**h)[old + len] = 0;
+ HUnlock(*h);
+ } else {
+ exit(-23);
+ }
+ }
+}
+
+void AddStringToHandle(Handle *h, const char *str) {
+ AddStringLenToHandle(h, str, strlen(str));
+}
+
+int Opt_PrintVersion(const char *opt, void *var, const char *arg) {
+ ShowVersion(0);
+ return 1;
+}
+
+void GetFirstSourceFilenameBase(char *buffer, char *defaul) {
+ int cnt;
+ OSSpec spec;
+ char compiler[32];
+ int x;
+ char *ext;
+
+ cnt = GetFileCount();
+ for (x = 0; x < cnt; x++) {
+ if (GetFileInfo(x, &spec, compiler)) {
+ if (compiler[0]) {
+ if (!strstr(compiler, "Lib")) {
+ OS_NameSpecToString(&spec.name, buffer, 256);
+ ext = strrchr(buffer, '.');
+ if (ext)
+ *ext = 0;
+ memmove(buffer, buffer, strlen(buffer) + 1);
+ return;
+ }
+ }
+ }
+ }
+
+ strcpy(buffer, defaul);
+}
+
+int Opt_SavePrefs(const char *opt, void *var, const char *arg) {
+ Parser_StorePanels(parseopts.context);
+ return 1;
+}
+
+int ParseNumber(const char *arg, Boolean emit_error, SInt32 *ret, const char **endptr) {
+ char *end;
+
+ if (arg[0] == '0' && (arg[1] == 'x' || arg[1] == 'X')) {
+ *ret = strtol(arg + 2, &end, 16);
+ } else if (arg[0] == '0') {
+ *ret = strtol(arg + 1, &end, 8);
+ } else {
+ *ret = strtol(arg, &end, 10);
+ }
+
+ if (endptr)
+ *endptr = end;
+
+ if (*end && emit_error) {
+ CLPReportError(5, "", arg);
+ return 0;
+ }
+
+ return 1;
+}
+
+int Opt_MaybeMoveAccessPaths(const char *opt, void *var, const char *arg) {
+ if (dashIMinusMovesPaths && !usedDashIMinus)
+ MoveSystemPathsIntoUserList();
+ return 1;
+}