diff options
author | 2021-09-15 21:25:21 -0400 | |
---|---|---|
committer | 2021-09-15 21:26:26 -0400 | |
commit | 43133765c1f5c0c72850a99ba708e328bf8b0d7e (patch) | |
tree | 2917e5d4fbd6b63ce01b6b875d38df5c9d620fba /src/lib/util/plaparse.cpp | |
parent | caa9d4654e2fc5e94d5489d9ed662307926850c3 (diff) |
Convert JED, PLA and JEDBIN parsers to (mostly) use ioprocs instead of raw memory interfaces
Diffstat (limited to 'src/lib/util/plaparse.cpp')
-rw-r--r-- | src/lib/util/plaparse.cpp | 268 |
1 files changed, 141 insertions, 127 deletions
diff --git a/src/lib/util/plaparse.cpp b/src/lib/util/plaparse.cpp index 09b7724375e..a085a27b635 100644 --- a/src/lib/util/plaparse.cpp +++ b/src/lib/util/plaparse.cpp @@ -12,6 +12,8 @@ #include "plaparse.h" +#include "ioprocs.h" + #include <cstdio> #include <cstdlib> #include <cstring> @@ -61,19 +63,27 @@ static bool iscrlf(char c) character stream -------------------------------------------------*/ -static uint32_t suck_number(const uint8_t **src, const uint8_t *srcend) +static uint32_t suck_number(util::random_read &src) { uint32_t value = 0; // find first digit - while (*src < srcend && !iscrlf(**src) && !isdigit(**src)) - (*src)++; - - // loop over and accumulate digits - while (*src < srcend && isdigit(**src)) + uint8_t ch; + uint64_t actual; + bool found = false; + while (!src.read(&ch, 1, actual) && actual == 1) { - value = value * 10 + (**src) - '0'; - (*src)++; + // loop over and accumulate digits + if (isdigit(ch)) + { + found = true; + value = value * 10 + ch - '0'; + } + else if (found || iscrlf(ch)) + { + src.seek(-1, SEEK_CUR); + break; + } } return value; @@ -89,7 +99,7 @@ static uint32_t suck_number(const uint8_t **src, const uint8_t *srcend) process_terms - process input/output matrix -------------------------------------------------*/ -static bool process_terms(jed_data *data, const uint8_t **src, const uint8_t *srcend, parse_info *pinfo) +static bool process_terms(jed_data *data, util::random_read &src, uint8_t &ch, parse_info *pinfo) { uint32_t curinput = 0; uint32_t curoutput = 0; @@ -99,65 +109,65 @@ static bool process_terms(jed_data *data, const uint8_t **src, const uint8_t *sr // PLA format documentation also describes them as simply 0, 1, 2, 3 static const char symbols[] = { "01-~" }; - while (*src < srcend && **src != '.' && **src != '#') + while (ch != '.' && ch != '#') { if (!outputs) { // and-matrix - if (strrchr(symbols, **src)) + if (strrchr(symbols, ch)) curinput++; - switch (**src) + switch (ch) { - case '0': - jed_set_fuse(data, data->numfuses++, 0); - jed_set_fuse(data, data->numfuses++, 1); + case '0': + jed_set_fuse(data, data->numfuses++, 0); + jed_set_fuse(data, data->numfuses++, 1); - if (LOG_PARSE) printf("01"); - break; + if (LOG_PARSE) printf("01"); + break; - case '1': - jed_set_fuse(data, data->numfuses++, 1); - jed_set_fuse(data, data->numfuses++, 0); + case '1': + jed_set_fuse(data, data->numfuses++, 1); + jed_set_fuse(data, data->numfuses++, 0); - if (LOG_PARSE) printf("10"); - break; + if (LOG_PARSE) printf("10"); + break; - // anything goes - case '-': - jed_set_fuse(data, data->numfuses++, 1); - jed_set_fuse(data, data->numfuses++, 1); + // anything goes + case '-': + jed_set_fuse(data, data->numfuses++, 1); + jed_set_fuse(data, data->numfuses++, 1); - if (LOG_PARSE) printf("11"); - break; + if (LOG_PARSE) printf("11"); + break; - // this product term is inhibited - case '~': - jed_set_fuse(data, data->numfuses++, 0); - jed_set_fuse(data, data->numfuses++, 0); + // this product term is inhibited + case '~': + jed_set_fuse(data, data->numfuses++, 0); + jed_set_fuse(data, data->numfuses++, 0); - if (LOG_PARSE) printf("00"); - break; + if (LOG_PARSE) printf("00"); + break; - case ' ': case '\t': - if (curinput > 0) - { - outputs = true; - if (LOG_PARSE) printf(" "); - } - break; + case ' ': case '\t': + if (curinput > 0) + { + outputs = true; + if (LOG_PARSE) printf(" "); + } + break; - default: - break; + default: + break; } } else { // or-matrix - if (strrchr(symbols, **src)) + if (strrchr(symbols, ch)) { curoutput++; - if (**src == '1') + if (ch == '1') { jed_set_fuse(data, data->numfuses++, 0); if (LOG_PARSE) printf("0"); @@ -171,7 +181,7 @@ static bool process_terms(jed_data *data, const uint8_t **src, const uint8_t *sr } } - if (iscrlf(**src) && outputs) + if (iscrlf(ch) && outputs) { outputs = false; if (LOG_PARSE) printf("\n"); @@ -183,7 +193,14 @@ static bool process_terms(jed_data *data, const uint8_t **src, const uint8_t *sr curoutput = 0; } - (*src)++; + uint64_t actual; + if (src.read(&ch, 1, actual)) + return false; + if (actual != 1) + { + ch = 0; + break; + } } return true; @@ -195,7 +212,7 @@ static bool process_terms(jed_data *data, const uint8_t **src, const uint8_t *sr process_field - process a single field -------------------------------------------------*/ -static bool process_field(jed_data *data, const uint8_t **src, const uint8_t *srcend, parse_info *pinfo) +static bool process_field(jed_data *data, util::random_read &src, parse_info *pinfo) { // valid keywords static const char *const keywords[] = { "i", "o", "p", "phase", "e", "\0" }; @@ -213,14 +230,15 @@ static bool process_field(jed_data *data, const uint8_t **src, const uint8_t *sr // find keyword char dest[0x10]; memset(dest, 0, sizeof(dest)); - const uint8_t *seek = *src; int destptr = 0; - while (seek < srcend && isalpha(*seek) && destptr < sizeof(dest) - 1) + uint8_t seek; + uint64_t actual; + while (!src.read(&seek, 1, actual) && actual == 1 && isalpha(seek)) { - dest[destptr] = tolower(*seek); - seek++; - destptr++; + dest[destptr++] = tolower(seek); + if (destptr == sizeof(dest)) + break; } uint8_t find = 0; @@ -230,58 +248,55 @@ static bool process_field(jed_data *data, const uint8_t **src, const uint8_t *sr if (find == KW_INVALID) return false; - (*src) += strlen(keywords[find]); - // handle it switch (find) { - // number of inputs - case KW_INPUTS: - pinfo->inputs = suck_number(src, srcend); - if (pinfo->inputs == 0 || pinfo->inputs >= (JED_MAX_FUSES/2)) - return false; - - if (LOG_PARSE) printf("Inputs: %u\n", pinfo->inputs); - break; - - // number of outputs - case KW_OUTPUTS: - pinfo->outputs = suck_number(src, srcend); - if (pinfo->outputs == 0 || pinfo->outputs >= (JED_MAX_FUSES/2)) - return false; - - if (LOG_PARSE) printf("Outputs: %u\n", pinfo->outputs); - break; - - // number of product terms (optional) - case KW_TERMS: - pinfo->terms = suck_number(src, srcend); - if (pinfo->terms == 0 || pinfo->terms >= (JED_MAX_FUSES/2)) - return false; - - if (LOG_PARSE) printf("Terms: %u\n", pinfo->terms); - break; - - // output polarity (optional) - case KW_PHASE: - if (LOG_PARSE) printf("Phase...\n"); - while (*src < srcend && !iscrlf(**src) && pinfo->xorptr < (JED_MAX_FUSES/2)) + // number of inputs + case KW_INPUTS: + pinfo->inputs = suck_number(src); + if (pinfo->inputs == 0 || pinfo->inputs >= (JED_MAX_FUSES/2)) + return false; + + if (LOG_PARSE) printf("Inputs: %u\n", pinfo->inputs); + break; + + // number of outputs + case KW_OUTPUTS: + pinfo->outputs = suck_number(src); + if (pinfo->outputs == 0 || pinfo->outputs >= (JED_MAX_FUSES/2)) + return false; + + if (LOG_PARSE) printf("Outputs: %u\n", pinfo->outputs); + break; + + // number of product terms (optional) + case KW_TERMS: + pinfo->terms = suck_number(src); + if (pinfo->terms == 0 || pinfo->terms >= (JED_MAX_FUSES/2)) + return false; + + if (LOG_PARSE) printf("Terms: %u\n", pinfo->terms); + break; + + // output polarity (optional) + case KW_PHASE: + if (LOG_PARSE) printf("Phase...\n"); + while (!src.read(&seek, 1, actual) && actual == 1 && !iscrlf(seek) && pinfo->xorptr < (JED_MAX_FUSES/2)) + { + if (seek == '0' || seek == '1') { - if (**src == '0' || **src == '1') - { - // 0 is negative - if (**src == '0') - pinfo->xorval[pinfo->xorptr/32] |= 1 << (pinfo->xorptr & 31); - pinfo->xorptr++; - } - (*src)++; + // 0 is negative + if (seek == '0') + pinfo->xorval[pinfo->xorptr/32] |= 1 << (pinfo->xorptr & 31); + pinfo->xorptr++; } - break; + } + break; - // end of file (optional) - case KW_END: - if (LOG_PARSE) printf("End of file\n"); - break; + // end of file (optional) + case KW_END: + if (LOG_PARSE) printf("End of file\n"); + break; } return true; @@ -295,54 +310,53 @@ static bool process_field(jed_data *data, const uint8_t **src, const uint8_t *sr -------------------------------------------------*/ /** - * @fn int pla_parse(const void *data, size_t length, jed_data *result) + * @fn int pla_parse(util::random_read &src, jed_data *result) * * @brief Pla parse. * - * @param data The data. - * @param length The length. + * @param src The source file. * @param [out] result If non-null, the result. * * @return An int. */ -int pla_parse(const void *data, size_t length, jed_data *result) +int pla_parse(util::random_read &src, jed_data *result) { - const auto *src = (const uint8_t *)data; - const uint8_t *srcend = src + length; - parse_info pinfo; memset(&pinfo, 0, sizeof(pinfo)); result->numfuses = 0; memset(result->fusemap, 0, sizeof(result->fusemap)); - while (src < srcend) + uint8_t ch; + uint64_t actual; + while (!src.read(&ch, 1, actual) && actual == 1) { - switch (*src) + switch (ch) { - // comment line - case '#': - while (src < srcend && !iscrlf(*src)) - src++; - break; + // comment line + case '#': + while (!src.read(&ch, 1, actual) && actual == 1) + { + if (iscrlf(ch)) + break; + } + break; - // keyword - case '.': - src++; - if (!process_field(result, &src, srcend, &pinfo)) - return JEDERR_INVALID_DATA; - break; + // keyword + case '.': + if (!process_field(result, src, &pinfo)) + return JEDERR_INVALID_DATA; + break; - // terms - case '0': case '1': case '-': case '~': - if (!process_terms(result, &src, srcend, &pinfo)) - return JEDERR_INVALID_DATA; - break; + // terms + case '0': case '1': case '-': case '~': + if (!process_terms(result, src, ch, &pinfo)) + return JEDERR_INVALID_DATA; + continue; - default: - src++; - break; + default: + break; } } |