arnaucube
arnaucube/circomPublic Self-hosted repository
circom/ports/c/buildasm/tester.cpp
ports/c/buildasm/tester.cppRaw
  1#include <string>
  2#include <iostream>
  3
  4#include <regex>
  5#include <string>
  6#include <iostream>
  7#include <stdexcept>
  8#include <sstream>
  9
 10#include <stdio.h>      /* printf, NULL */
 11#include <stdlib.h>
 12#include <cassert>
 13
 14
 15#include "fr.h"
 16
 17
 18typedef void (*Func1)(PFrElement, PFrElement);
 19typedef void (*Func2)(PFrElement, PFrElement, PFrElement);
 20typedef void *FuncAny;
 21
 22typedef struct {
 23    FuncAny fn;
 24    int nOps;
 25} FunctionSpec;
 26
 27std::map<std::string, FunctionSpec> functions;
 28std::vector<FrElement> stack;
 29
 30void addFunction(std::string name, FuncAny f, int nOps) {
 31    FunctionSpec fs;
 32    fs.fn = f;
 33    fs.nOps = nOps;
 34    functions[name] = fs;
 35}
 36
 37void fillMap() {
 38    addFunction("add", (FuncAny)Fr_add, 2);
 39    addFunction("sub", (FuncAny)Fr_sub, 2);
 40    addFunction("neg", (FuncAny)Fr_neg, 1);
 41    addFunction("mul", (FuncAny)Fr_mul, 2);
 42    addFunction("square", (FuncAny)Fr_square, 1);
 43    addFunction("idiv", (FuncAny)Fr_idiv, 2);
 44    addFunction("inv", (FuncAny)Fr_inv, 1);
 45    addFunction("div", (FuncAny)Fr_div, 2);
 46    addFunction("band", (FuncAny)Fr_band, 2);
 47    addFunction("bor", (FuncAny)Fr_bor, 2);
 48    addFunction("bxor", (FuncAny)Fr_bxor, 2);
 49    addFunction("bnot", (FuncAny)Fr_bnot, 1);
 50    addFunction("eq", (FuncAny)Fr_eq, 2);
 51    addFunction("neq", (FuncAny)Fr_neq, 2);
 52    addFunction("lt", (FuncAny)Fr_lt, 2);
 53    addFunction("gt", (FuncAny)Fr_gt, 2);
 54    addFunction("leq", (FuncAny)Fr_leq, 2);
 55    addFunction("geq", (FuncAny)Fr_geq, 2);
 56    addFunction("land", (FuncAny)Fr_land, 2);
 57    addFunction("lor", (FuncAny)Fr_lor, 2);
 58    addFunction("lnot", (FuncAny)Fr_lnot, 1);
 59    addFunction("shl", (FuncAny)Fr_shl, 2);
 60    addFunction("shr", (FuncAny)Fr_shr, 2);
 61}
 62
 63u_int64_t readInt(std::string &s) {
 64    if (s.rfind("0x", 0) == 0) {
 65        return std::stoull(s.substr(2), 0, 16);
 66    } else {
 67        return std::stoull(s, 0, 10);
 68    }
 69}
 70
 71void pushNumber(std::vector<std::string> &v) {
 72    u_int64_t a;
 73    if ((v.size()<1) || (v.size() > (Fr_N64+1))) {
 74        printf("Invalid Size: %d  -  %d \n", v.size(), Fr_N64);
 75        throw std::runtime_error("Invalid number of parameters for number");
 76    }
 77    FrElement e;
 78    a = readInt(v[0]);
 79    *(u_int64_t *)(&e) = a;
 80    for (int i=0; i<Fr_N64; i++) {
 81        if (i+1 < v.size()) {
 82            a = readInt(v[i+1]);
 83        } else {
 84            a = 0;
 85        }
 86        e.longVal[i] = a;
 87    }
 88    stack.push_back(e);
 89}
 90
 91void callFunction(FunctionSpec fs) {
 92    if (stack.size() < fs.nOps) {
 93        throw new std::runtime_error("Not enough elements in stack");
 94    }
 95    if (fs.nOps == 1) {
 96        FrElement a = stack.back();
 97        stack.pop_back();
 98        FrElement c;
 99        (*(Func1)fs.fn)(&c, &a);
100        stack.push_back(c);
101    } else if (fs.nOps == 2) {
102        FrElement b = stack.back();
103        stack.pop_back();
104        FrElement a = stack.back();
105        stack.pop_back();
106        FrElement c;
107        (*(Func2)fs.fn)(&c, &a, &b);
108        stack.push_back(c);
109    } else {
110        assert(false);
111    }
112}
113
114void processLine(std::string &line) {
115    std::regex re("(\\s*[,;]\\s*)|\\s+"); // whitespace
116
117    std::sregex_token_iterator begin( line.begin(), line.end(), re ,-1);
118    std::sregex_token_iterator end;
119    std::vector<std::string> tokens;
120
121    std::copy(begin, end, std::back_inserter(tokens));
122
123    // Remove initial empty tokens
124    while ((tokens.size() > 0)&&(tokens[0] == "")) {
125        tokens.erase(tokens.begin());
126    }
127
128    // Empty lines are valid but are not processed
129    if (tokens.size() == 0) return;
130
131    auto search = functions.find(tokens[0]);
132    if (search == functions.end()) {
133        pushNumber(tokens);
134    } else {
135        if (tokens.size() != 1) {
136            throw std::runtime_error("Functions does not accept parameters");
137        }
138        callFunction(search->second);
139    }
140}
141
142int main(void)
143{
144    Fr_init();
145    fillMap();
146    std::string line;
147    int i=0;
148    while (std::getline(std::cin, line)) {
149        processLine(line);
150        // if (i%1000 == 0) printf("%d\n", i);
151        // printf("%d\n", i);
152        i++;
153    }
154    // Print the elements in the stack
155    //
156    for (int i=0; i<stack.size(); i++) {
157        char *s;
158        s = Fr_element2str(&stack[i]);
159        printf("%s\n", s);
160        free(s);
161    }
162    return EXIT_SUCCESS;
163}
164
165
166
167/*
168
169
170#include <stdlib.h>
171#include <string.h>
172#include "fr.h"
173
174typedef void (*Func2)(PFrElement, PFrElement, PFrElement);
175
176typedef struct {
177    const char *fnName;
178    Func2 fn;
179} FN;
180
181
182#define NFN 2
183FN fns[NFN] = {
184    {"add", Fr_add},
185    {"mul", Fr_mul},
186};
187
188int main(int argc, char **argv) {
189
190    if (argc <= 1) {
191        fprintf( stderr, "invalid number of parameters");
192        return 1;
193    }
194
195    for (int i=0; i< NFN;i++) {
196        if (strcmp(argv[1], fns[i].fnName) == 0) {
197            if (argc != 4) {
198                fprintf( stderr, "invalid number of parameters");
199                return 1;
200            }
201            FrElement a;
202            FrElement b;
203
204            Fr_str2element(&a, argv[2]);
205            Fr_str2element(&b, argv[3]);
206            FrElement c;
207            fns[i].fn(&c, &a, &b);
208
209            char *s;
210            s = Fr_element2str(&c);
211            printf("%s", s);
212            free(s);
213            return 0;
214        }
215    }
216    fprintf( stderr, "invalid operation %s", argv[1]);
217    return 1;
218}
219
220*/