class_signature now contains flags
[swftools.git] / lib / as3 / code.c
index 30143f7..49f794e 100644 (file)
@@ -196,9 +196,8 @@ opcode_t opcodes[]={
 {0xa7, "urshift", "",          -2, 1, 0, 0},
 
 /* opcodes not documented, but seen in the wild */
-//0x53: seen in builtin.abc- followed by 0x01 (might be the number of stack params)
-{0x53, "xxx1", "",             -1, 0, 0, 0},
-{0x01, "xxx2", "",              0, 0, 0, 0},
+//0x53: seen in builtin.abc
+{0x53, "applytype", "n",       -1, 1, 0, OP_STACK_ARGS},
 
 /* dummy instruction. Warning: this one is not actually supported by flash */
 {0xff, "__break__", "",             0, 0, 0, OP_RETURN},
@@ -1046,3 +1045,63 @@ code_t* code_append(code_t*code, code_t*toappend)
     return code_end(toappend);
 }
 
+lookupswitch_t*lookupswitch_dup(lookupswitch_t*l)
+{
+    lookupswitch_t*n = malloc(sizeof(lookupswitch_t));
+    fprintf(stderr, "lookupswitch dupping not supported yet\n");
+    n->targets = list_clone(l->targets);
+    return 0;
+}
+
+code_t*code_dup(code_t*c)
+{
+    /* misses branch relocation */
+    fprintf(stderr, "dupping not supported yet\n");
+    return 0;
+    if(!c) return 0;
+
+    while(c->prev) c = c->prev;
+
+    code_t*last = 0;
+    while(c) {
+        NEW(code_t, n);
+        memcpy(n, c, sizeof(code_t));
+
+        opcode_t*op = opcode_get(c->opcode);
+        char*p = op?op->params:"";
+        int pos=0;
+        while(*p) {
+            if(*p == '2') { //multiname
+                c->data[pos] = multiname_clone(c->data[pos]);
+            } else if(*p == 's' || *p == 'D') {
+                c->data[pos] = strdup(c->data[pos]);
+            } else if(*p == 'f') {
+                double old = *(double*)c->data[pos];
+                c->data[pos] = malloc(sizeof(double));
+                *(double*)c->data[pos] = old;
+            } else if(strchr("S", *p)) {
+                c->data[pos] = lookupswitch_dup(c->data[pos]);
+            }
+            p++;pos++;
+        }
+
+        n->prev = last;
+        if(last) {
+            last->next = n;
+        }
+        last = n;
+        c = c->next;
+    }
+    return last;
+}
+
+code_t*code_cutlast(code_t*c)
+{
+    assert(!c->next);
+    code_t*prev = c->prev;
+    c->prev = 0;
+    prev->next=0;
+    code_free(c);
+    return prev;
+}
+