static Instruction symbexec(const Proto* pt, int lastpc, int reg) { int pc; int last; /* stores position of last instruction that changed `reg' */ last = pt->sizecode - 1; /* points to final return (a `neutral' instruction) */ check(precheck(pt)); for (pc = 0; pc < lastpc; pc++) { Instruction i = pt->code[pc]; OpCode op = GET_OPCODE(i); int a = GETARG_A(i); int b = 0; int c = 0; check(op < NUM_OPCODES); checkreg(pt, a); switch (getOpMode(op)) { case iABC: { b = GETARG_B(i); c = GETARG_C(i); check(checkArgMode(pt, b, getBMode(op))); check(checkArgMode(pt, c, getCMode(op))); break; } case iABx: { b = GETARG_Bx(i); if (getBMode(op) == OpArgK) check(b < pt->sizek); break; } case iAsBx: { b = GETARG_sBx(i); if (getBMode(op) == OpArgR) { int dest = pc + 1 + b; check(0 <= dest && dest < pt->sizecode); if (dest > 0) { int j; /* check that it does not jump to a setlist count; this is tricky, because the count from a previous setlist may have the same value of an invalid setlist; so, we must go all the way back to the first of them (if any) */ for (j = 0; j < dest; j++) { Instruction d = pt->code[dest - 1 - j]; if (!(GET_OPCODE(d) == OP_SETLIST && GETARG_C(d) == 0)) break; } /* if 'j' is even, previous value is not a setlist (even if it looks like one) */ check((j & 1) == 0); } } break; } } if (testAMode(op)) { if (a == reg) last = pc; /* change register `a' */ } if (testTMode(op)) { check(pc + 2 < pt->sizecode); /* check skip */ check(GET_OPCODE(pt->code[pc + 1]) == OP_JMP); } switch (op) { case OP_LOADBOOL: { if (c == 1) /* does it jump? */ { check(pc + 2 < pt->sizecode); /* check its jump */ check(GET_OPCODE(pt->code[pc + 1]) != OP_SETLIST || GETARG_C(pt->code[pc + 1]) != 0); } break; } case OP_LOADNIL: { if (a <= reg && reg <= b) last = pc; /* set registers from `a' to `b' */ break; } case OP_GETUPVAL: case OP_SETUPVAL: { check(b < pt->nups); break; } case OP_GETGLOBAL: case OP_SETGLOBAL: { check(ttisstring(&pt->k[b])); break; } case OP_SELF: { checkreg(pt, a + 1); if (reg == a + 1) last = pc; break; } case OP_CONCAT: { check(b < c); /* at least two operands */ break; } case OP_TFORLOOP: { check(c >= 1); /* at least one result (control variable) */ checkreg(pt, a + 2 + c); /* space for results */ if (reg >= a + 2) last = pc; /* affect all regs above its base */ break; } case OP_FORLOOP: case OP_FORPREP: checkreg(pt, a + 3); /* go through */ case OP_JMP: { int dest = pc + 1 + b; /* not full check and jump is forward and do not skip `lastpc'? */ if (reg != NO_REG && pc < dest && dest <= lastpc) pc += b; /* do the jump */ break; } case OP_CALL: case OP_TAILCALL: { if (b != 0) { checkreg(pt, a + b - 1); } c--; /* c = num. returns */ if (c == LUA_MULTRET) { check(checkopenop(pt, pc)); } else if (c != 0) checkreg(pt, a + c - 1); if (reg >= a) last = pc; /* affect all registers above base */ break; } case OP_RETURN: { b--; /* b = num. returns */ if (b > 0) checkreg(pt, a + b - 1); break; } case OP_SETLIST: { if (b > 0) checkreg(pt, a + b); if (c == 0) { pc++; check(pc < pt->sizecode - 1); } break; } case OP_CLOSURE: { int nup, j; check(b < pt->sizep); nup = pt->p[b]->nups; check(pc + nup < pt->sizecode); for (j = 1; j <= nup; j++) { OpCode op1 = GET_OPCODE(pt->code[pc + j]); check(op1 == OP_GETUPVAL || op1 == OP_MOVE); } if (reg != NO_REG) /* tracing? */ pc += nup; /* do not 'execute' these pseudo-instructions */ break; } case OP_VARARG: { check((pt->is_vararg & VARARG_ISVARARG) && !(pt->is_vararg & VARARG_NEEDSARG)); b--; if (b == LUA_MULTRET) check(checkopenop(pt, pc)); checkreg(pt, a + b - 1); break; } default: break; } } return pt->code[last]; }
static Instruction luaG_symbexec (const Proto *pt, int lastpc, int reg) { int pc; int last; /* stores position of last instruction that changed `reg' */ last = pt->sizecode-1; /* points to final return (a `neutral' instruction) */ check(precheck(pt)); for (pc = 0; pc < lastpc; pc++) { const Instruction i = pt->code[pc]; OpCode op = GET_OPCODE(i); int a = GETARG_A(i); int b = 0; int c = 0; checkreg(pt, a); switch (getOpMode(op)) { case iABC: { b = GETARG_B(i); c = GETARG_C(i); if (testOpMode(op, OpModeBreg)) { checkreg(pt, b); } else if (testOpMode(op, OpModeBrk)) check(checkRK(pt, b)); if (testOpMode(op, OpModeCrk)) check(checkRK(pt, c)); break; } case iABx: { b = GETARG_Bx(i); if (testOpMode(op, OpModeK)) check(b < pt->sizek); break; } case iAsBx: { b = GETARG_sBx(i); break; } } if (testOpMode(op, OpModesetA)) { if (a == reg) last = pc; /* change register `a' */ } if (testOpMode(op, OpModeT)) { check(pc+2 < pt->sizecode); /* check skip */ check(GET_OPCODE(pt->code[pc+1]) == OP_JMP); } switch (op) { case OP_LOADBOOL: { check(c == 0 || pc+2 < pt->sizecode); /* check its jump */ break; } case OP_LOADNIL: { if (a <= reg && reg <= b) last = pc; /* set registers from `a' to `b' */ break; } case OP_GETUPVAL: case OP_SETUPVAL: { check(b < pt->nups); break; } case OP_GETGLOBAL: case OP_SETGLOBAL: { check(ttisstring(&pt->k[b])); break; } case OP_SELF: { checkreg(pt, a+1); if (reg == a+1) last = pc; break; } case OP_CONCAT: { /* `c' is a register, and at least two operands */ check(c < MAXSTACK && b < c); break; } case OP_TFORLOOP: checkreg(pt, a+c+5); if (reg >= a) last = pc; /* affect all registers above base */ /* go through */ case OP_FORLOOP: checkreg(pt, a+2); /* go through */ case OP_JMP: { int dest = pc+1+b; check(0 <= dest && dest < pt->sizecode); /* not full check and jump is forward and do not skip `lastpc'? */ if (reg != NO_REG && pc < dest && dest <= lastpc) pc += b; /* do the jump */ break; } case OP_CALL: case OP_TAILCALL: { if (b != 0) { checkreg(pt, a+b-1); } c--; /* c = num. returns */ if (c == LUA_MULTRET) { check(checkopenop(pt, pc)); } else if (c != 0) checkreg(pt, a+c-1); if (reg >= a) last = pc; /* affect all registers above base */ break; } case OP_RETURN: { b--; /* b = num. returns */ if (b > 0) checkreg(pt, a+b-1); break; } case OP_SETLIST: { checkreg(pt, a + (b&(LFIELDS_PER_FLUSH-1)) + 1); break; } case OP_CLOSURE: { int nup; check(b < pt->sizep); nup = pt->p[b]->nups; check(pc + nup < pt->sizecode); for (; nup>0; nup--) { OpCode op1 = GET_OPCODE(pt->code[pc+nup]); check(op1 == OP_GETUPVAL || op1 == OP_MOVE); } break; } default: break; } } return pt->code[last]; }
static Instruction symbexec (const Proto *pt, int lastpc, int reg) { int pc; int last; /* stores position of last instruction that changed `reg' */ last = pt->sizecode-1; /* points to final return (a `neutral' instruction) */ check(precheck(pt)); for (pc = 0; pc < lastpc; pc++) { Instruction i = pt->code[pc]; OpCode op = GET_OPCODE(i); int a = GETARG_A(i); int b = 0; int c = 0; check(op < NUM_OPCODES); checkreg(pt, a); switch (getOpMode(op)) { case iABC: { b = GETARG_B(i); c = GETARG_C(i); check(checkArgMode(pt, b, getBMode(op))); check(checkArgMode(pt, c, getCMode(op))); break; } case iABx: { b = GETARG_Bx(i); if (getBMode(op) == OpArgK) check(b < pt->sizek); break; } case iAsBx: { b = GETARG_sBx(i); if (getBMode(op) == OpArgR) { int dest = pc+1+b; check(0 <= dest && dest < pt->sizecode); if (dest > 0) { /* cannot jump to a setlist count */ Instruction d = pt->code[dest-1]; check(!(GET_OPCODE(d) == OP_SETLIST && GETARG_C(d) == 0)); } } break; } } if (testAMode(op)) { if (a == reg) last = pc; /* change register `a' */ } if (testTMode(op)) { check(pc+2 < pt->sizecode); /* check skip */ check(GET_OPCODE(pt->code[pc+1]) == OP_JMP); } switch (op) { case OP_LOADBOOL: { check(c == 0 || pc+2 < pt->sizecode); /* check its jump */ break; } case OP_LOADNIL: { if (a <= reg && reg <= b) last = pc; /* set registers from `a' to `b' */ break; } case OP_GETUPVAL: case OP_SETUPVAL: { check(b < pt->nups); break; } case OP_GETGLOBAL: case OP_SETGLOBAL: { check(ttisstring(&pt->k[b])); break; } case OP_SELF: { checkreg(pt, a+1); if (reg == a+1) last = pc; break; } case OP_CONCAT: { check(b < c); /* at least two operands */ break; } case OP_TFORLOOP: { check(c >= 1); /* at least one result (control variable) */ checkreg(pt, a+2+c); /* space for results */ if (reg >= a+2) last = pc; /* affect all regs above its base */ break; } case OP_FORLOOP: case OP_FORPREP: checkreg(pt, a+3); /* go through */ case OP_JMP: { int dest = pc+1+b; /* not full check and jump is forward and do not skip `lastpc'? */ if (reg != NO_REG && pc < dest && dest <= lastpc) pc += b; /* do the jump */ break; } case OP_CALL: case OP_TAILCALL: { if (b != 0) { checkreg(pt, a+b-1); } c--; /* c = num. returns */ if (c == LUA_MULTRET) { check(checkopenop(pt, pc)); } else if (c != 0) checkreg(pt, a+c-1); if (reg >= a) last = pc; /* affect all registers above base */ break; } case OP_RETURN: { b--; /* b = num. returns */ if (b > 0) checkreg(pt, a+b-1); break; } case OP_SETLIST: { if (b > 0) checkreg(pt, a + b); if (c == 0) pc++; break; } case OP_CLOSURE: { int nup; check(b < pt->sizep); nup = pt->p[b]->nups; check(pc + nup < pt->sizecode); for (; nup>0; nup--) { OpCode op1 = GET_OPCODE(pt->code[pc+nup]); check(op1 == OP_GETUPVAL || op1 == OP_MOVE); } break; } case OP_VARARG: { check((pt->is_vararg & VARARG_ISVARARG) && !(pt->is_vararg & VARARG_NEEDSARG)); b--; if (b == LUA_MULTRET) check(checkopenop(pt, pc)); checkreg(pt, a+b-1); break; } default: break; } } return pt->code[last]; }
int main (void) { pskc_t *pskc; pskc_key_t *keyp; struct tm startdate = { 1, 2, 3, 4, 5, 6 }; struct tm expirydate = { 6, 5, 4, 3, 2, 1 }; char *out; size_t len; int rc; rc = pskc_global_init (); if (rc != PSKC_OK) { printf ("pskc_global_init: %d\n", rc); return 1; } pskc_global_log (my_log); rc = pskc_init (&pskc); if (rc != PSKC_OK) { printf ("pskc_init: %d\n", rc); return 1; } pskc_set_version (pskc, "42"); pskc_set_id (pskc, "MyID"); rc = pskc_add_keypackage (pskc, &keyp); if (rc != PSKC_OK) { printf ("pskc_add_keypackage: %d\n", rc); return 1; } rc = precheck (pskc); if (rc != 0) return rc; pskc_set_device_manufacturer (keyp, "iana.foo"); pskc_set_device_serialno (keyp, "42"); pskc_set_device_model (keyp, "model"); pskc_set_device_issueno (keyp, "issueno"); pskc_set_device_devicebinding (keyp, "devbind"); pskc_set_device_startdate (keyp, &startdate); pskc_set_device_expirydate (keyp, &expirydate); pskc_set_device_userid (keyp, "userid"); pskc_set_cryptomodule_id (keyp, "cid"); pskc_set_key_id (keyp, "keyid"); pskc_set_key_algorithm (keyp, "keyalg"); pskc_set_key_issuer (keyp, "keyissuer"); pskc_set_key_algparm_suite (keyp, "keyalgparmsuite"); pskc_set_key_algparm_chall_encoding (keyp, PSKC_VALUEFORMAT_ALPHANUMERIC); pskc_set_key_algparm_chall_min (keyp, 4711); pskc_set_key_algparm_chall_max (keyp, 42); pskc_set_key_algparm_chall_checkdigits (keyp, 1); pskc_set_key_algparm_resp_encoding (keyp, PSKC_VALUEFORMAT_BASE64); pskc_set_key_algparm_resp_length (keyp, 216); pskc_set_key_algparm_resp_checkdigits (keyp, 1); pskc_set_key_profileid (keyp, "profileid"); pskc_set_key_reference (keyp, "keyref"); pskc_set_key_friendlyname (keyp, "fname"); pskc_set_key_userid (keyp, "keyuserid"); pskc_set_key_data_counter (keyp, 4711); pskc_set_key_data_time (keyp, 12345); pskc_set_key_data_timeinterval (keyp, 123456); pskc_set_key_data_timedrift (keyp, 321); pskc_set_key_policy_startdate (keyp, &startdate); pskc_set_key_policy_expirydate (keyp, &expirydate); pskc_set_key_policy_pinkeyid (keyp, "pinkeyid"); pskc_set_key_policy_pinusagemode (keyp, PSKC_PINUSAGEMODE_APPEND); pskc_set_key_policy_pinmaxfailedattempts (keyp, 123); pskc_set_key_policy_pinminlength (keyp, 24); pskc_set_key_policy_pinmaxlength (keyp, 42); pskc_set_key_policy_pinencoding (keyp, PSKC_VALUEFORMAT_BASE64); pskc_set_key_policy_keyusages (keyp, PSKC_KEYUSAGE_VERIFY); pskc_set_key_policy_numberoftransactions (keyp, 17); rc = pskc_set_key_data_secret (keyp, "foo", 3); if (rc != PSKC_OK) { printf ("pskc_set_key_data_secret: %d\n", rc); return 1; } rc = pskc_set_key_data_b64secret (keyp, "Zm9v"); if (rc != PSKC_OK) { printf ("pskc_set_key_data_b64secret: %d\n", rc); return 1; } rc = pskc_set_key_data_b64secret (keyp, "nix"); if (rc != PSKC_BASE64_ERROR) { printf ("pskc_set_key_data_b64secret: %d\n", rc); return 1; } rc = check (pskc); if (rc != 0) return rc; rc = pskc_build_xml (pskc, &out, &len); if (rc != PSKC_OK) { printf ("pskc_build_xml: %d\n", rc); return 1; } pskc_done (pskc); if (len != strlen (pskc_expect) || memcmp (pskc_expect, out, len) != 0) { printf ("generated data mismatch. expected:\n%s\ngot:\n%.*s\n", pskc_expect, (int) len, out); return 1; } rc = pskc_init (&pskc); if (rc != PSKC_OK) { printf ("pskc_init: %d\n", rc); return 1; } rc = pskc_parse_from_memory (pskc, len, out); if (rc != PSKC_OK) { printf ("pskc_parse_from_memory: %d\n", rc); return 1; } pskc_free (out); rc = check (pskc); if (rc != 0) return rc; pskc_done (pskc); pskc_global_done (); return 0; }