pepper-project / pequin

A system for verifying outsourced computations, and applying SNARKs. Simplified release of the main Pepper codebase.
Other
122 stars 46 forks source link

printf("%Zd") does not compile inside a conditional inside a for loop: java.lang.RuntimeException #56

Open noresistence opened 5 years ago

noresistence commented 5 years ago

When using printf("%Zd", somevariable) inside a conditional (that depends on some value from a struct) inside a for loop, the Java Compiler throws a RuntimeError.

example.c

#include <stdint.h>

typedef struct s {
    uint32_t i;
} struct_t;

struct In {struct_t s;};

struct Out {uint8_t out;};

void compute(struct In *input, struct Out *output) {
    uint32_t i;

    struct_t s = input->s;

    for (i = 0; i < 30; i++) {
        if (i < s.i) {
            printf("%Zd", i);
        }
    }
}

Error

Compiling example.c
Expanding circuit to file example.c.ZAATAR.circuit
Exception in thread "main" java.lang.RuntimeException
        at SFE.Compiler.LvalExpression.changeReference(LvalExpression.java:295)
        at SFE.Compiler.Operators.PointerAccessOperator.resolve(PointerAccessOperator.java:74)
        at SFE.Compiler.Operators.PointerAccessOperator.resolve(PointerAccessOperator.java:37)
        at SFE.Compiler.FloatConstant.toFloatConstant(FloatConstant.java:112)
        at SFE.Compiler.IntConstant.toIntConstant(IntConstant.java:78)
        at SFE.Compiler.PrintfStatement.parseFormatString(PrintfStatement.java:42)
        at SFE.Compiler.PrintfStatement.<init>(PrintfStatement.java:25)
        at ccomp.parser_hw.CCompiler.builtinFunctionCall(CCompiler.java:1651)
        at ccomp.parser_hw.CCompiler.genericFunctionCall(CCompiler.java:1009)
        at ccomp.parser_hw.CCompiler.getExpr(CCompiler.java:958)
        at ccomp.parser_hw.CCompiler.getExpr(CCompiler.java:793)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:660)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:635)
        at ccomp.parser_hw.CCompiler.getExpr(CCompiler.java:851)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:660)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:635)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:635)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:695)
        at ccomp.parser_hw.CCompiler.expandStatement(CCompiler.java:635)
        at ccomp.parser_hw.CCompiler.access$1100(CCompiler.java:114)
        at ccomp.parser_hw.CCompiler$CMainStatement.toAssignmentStatements(CCompiler.java:491)
        at SFE.Compiler.BlockStatement.toAssignmentStatements(BlockStatement.java:111)
        at SFE.Compiler.FunctionBody.toAssignmentStatements(FunctionBody.java:31)
        at zcc.ZCC.compile(ZCC.java:260)
        at zcc.ZCC.main(ZCC.java:127)

Variants

Omitting either the for or the if clause, the error will not be thrown.

The error also appears if instead of printing the loop variable i, another variable is used as parameter of printf. For example:

void compute(struct In *input, struct Out *output) {
    uint32_t i;

    struct_t s = input->s;
    uint8_t x = 0;

    for (i = 0; i < 30; i++) {
        if (i < s.i) {
            printf("%Zd", x);
        }
    }
}
noresistence commented 5 years ago

If the printf statement is inside a function, which in turn is called inside a conditional branch inside a for loop, the RuntimeException is also thrown during setup.