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}
 60
 61u_int64_t readInt(std::string &s) {
 62    if (s.rfind("0x", 0) == 0) {
 63        return std::stoull(s.substr(2), 0, 16);
 64    } else {
 65        return std::stoull(s, 0, 10);
 66    }
 67}
 68
 69void pushNumber(std::vector<std::string> &v) {
 70    u_int64_t a;
 71    if ((v.size()<1) || (v.size() > (Fr_N64+1))) {
 72        printf("Invalid Size: %d  -  %d \n", v.size(), Fr_N64);
 73        throw std::runtime_error("Invalid number of parameters for number");
 74    }
 75    FrElement e;
 76    a = readInt(v[0]);
 77    *(u_int64_t *)(&e) = a;
 78    for (int i=0; i<Fr_N64; i++) {
 79        if (i+1 < v.size()) {
 80            a = readInt(v[i+1]);
 81        } else {
 82            a = 0;
 83        }
 84        e.longVal[i] = a;
 85    }
 86    stack.push_back(e);
 87}
 88
 89void callFunction(FunctionSpec fs) {
 90    if (stack.size() < fs.nOps) {
 91        throw new std::runtime_error("Not enough elements in stack");
 92    }
 93    if (fs.nOps == 1) {
 94        FrElement a = stack.back();
 95        stack.pop_back();
 96        FrElement c;
 97        (*(Func1)fs.fn)(&c, &a);
 98        stack.push_back(c);
 99    } else if (fs.nOps == 2) {
100        FrElement b = stack.back();
101        stack.pop_back();
102        FrElement a = stack.back();
103        stack.pop_back();
104        FrElement c;
105        (*(Func2)fs.fn)(&c, &a, &b);
106        stack.push_back(c);
107    } else {
108        assert(false);
109    }
110}
111
112void processLine(std::string &line) {
113    std::regex re("(\\s*[,;]\\s*)|\\s+"); // whitespace
114
115    std::sregex_token_iterator begin( line.begin(), line.end(), re ,-1);
116    std::sregex_token_iterator end;
117    std::vector<std::string> tokens;
118
119    std::copy(begin, end, std::back_inserter(tokens));
120
121    // Remove initial empty tokens
122    while ((tokens.size() > 0)&&(tokens[0] == "")) {
123        tokens.erase(tokens.begin());
124    }
125
126    // Empty lines are valid but are not processed
127    if (tokens.size() == 0) return;
128
129    auto search = functions.find(tokens[0]);
130    if (search == functions.end()) {
131        pushNumber(tokens);
132    } else {
133        if (tokens.size() != 1) {
134            throw std::runtime_error("Functions does not accept parameters");
135        }
136        callFunction(search->second);
137    }
138}
139
140int main(void)
141{
142    Fr_init();
143    fillMap();
144    std::string line;
145    int i=0;
146    while (std::getline(std::cin, line)) {
147        processLine(line);
148        // if (i%1000 == 0) printf("%d\n", i);
149        // printf("%d\n", i);
150        i++;
151    }
152    // Print the elements in the stack
153    //
154    for (int i=0; i<stack.size(); i++) {
155        char *s;
156        s = Fr_element2str(&stack[i]);
157        printf("%s\n", s);
158        free(s);
159    }
160    return EXIT_SUCCESS;
161}
162
163
164
165/*
166
167
168#include <stdlib.h>
169#include <string.h>
170#include "fr.h"
171
172typedef void (*Func2)(PFrElement, PFrElement, PFrElement);
173
174typedef struct {
175    const char *fnName;
176    Func2 fn;
177} FN;
178
179
180#define NFN 2
181FN fns[NFN] = {
182    {"add", Fr_add},
183    {"mul", Fr_mul},
184};
185
186int main(int argc, char **argv) {
187
188    if (argc <= 1) {
189        fprintf( stderr, "invalid number of parameters");
190        return 1;
191    }
192
193    for (int i=0; i< NFN;i++) {
194        if (strcmp(argv[1], fns[i].fnName) == 0) {
195            if (argc != 4) {
196                fprintf( stderr, "invalid number of parameters");
197                return 1;
198            }
199            FrElement a;
200            FrElement b;
201
202            Fr_str2element(&a, argv[2]);
203            Fr_str2element(&b, argv[3]);
204            FrElement c;
205            fns[i].fn(&c, &a, &b);
206
207            char *s;
208            s = Fr_element2str(&c);
209            printf("%s", s);
210            free(s);
211            return 0;
212        }
213    }
214    fprintf( stderr, "invalid operation %s", argv[1]);
215    return 1;
216}
217
218*/