// vim: set fdm=marker: // constants {{{ .constant OBJREF 0xCAFEBABE // 512 - 1 for modulo hack SIZE_MODULO 511 SIZE_EQUIV 448 BIT_PAD_START 0x80 MASK_8 0xFF MASK_31 0x7FFFFFFF MASK_SIGN 0x80000000 BASE_H0 0x67452301 BASE_H1 0xEFCDAB89 BASE_H2 0x98BADCFE BASE_H3 0x10325476 NOT_PATTERN 0xFFFFFFFF XOR_PATTERN_1 0xAAAAAAAA XOR_PATTERN_2 0x55555555 // Precalculated left-shift multipliers SHL_24 0x01000000 SHL_16 0x00010000 SHL_8 0x00000100 // FUCK ME SINES_0 0xd76aa478 SINES_1 0xe8c7b756 SINES_2 0x242070db SINES_3 0xc1bdceee SINES_4 0xf57c0faf SINES_5 0x4787c62a SINES_6 0xa8304613 SINES_7 0xfd469501 SINES_8 0x698098d8 SINES_9 0x8b44f7af SINES_10 0xffff5bb1 SINES_11 0x895cd7be SINES_12 0x6b901122 SINES_13 0xfd987193 SINES_14 0xa679438e SINES_15 0x49b40821 SINES_16 0xf61e2562 SINES_17 0xc040b340 SINES_18 0x265e5a51 SINES_19 0xe9b6c7aa SINES_20 0xd62f105d SINES_21 0x02441453 SINES_22 0xd8a1e681 SINES_23 0xe7d3fbc8 SINES_24 0x21e1cde6 SINES_25 0xc33707d6 SINES_26 0xf4d50d87 SINES_27 0x455a14ed SINES_28 0xa9e3e905 SINES_29 0xfcefa3f8 SINES_30 0x676f02d9 SINES_31 0x8d2a4c8a SINES_32 0xfffa3942 SINES_33 0x8771f681 SINES_34 0x6d9d6122 SINES_35 0xfde5380c SINES_36 0xa4beea44 SINES_37 0x4bdecfa9 SINES_38 0xf6bb4b60 SINES_39 0xbebfbc70 SINES_40 0x289b7ec6 SINES_41 0xeaa127fa SINES_42 0xd4ef3085 SINES_43 0x04881d05 SINES_44 0xd9d4d039 SINES_45 0xe6db99e5 SINES_46 0x1fa27cf8 SINES_47 0xc4ac5665 SINES_48 0xf4292244 SINES_49 0x432aff97 SINES_50 0xab9423a7 SINES_51 0xfc93a039 SINES_52 0x655b59c3 SINES_53 0x8f0ccc92 SINES_54 0xffeff47d SINES_55 0x85845dd1 SINES_56 0x6fa87e4f SINES_57 0xfe2ce6e0 SINES_58 0xa3014314 SINES_59 0x4e0811a1 SINES_60 0xf7537e82 SINES_61 0xbd3af235 SINES_62 0x2ad7d2bb SINES_63 0xeb86d391 .end-constant // }}} // main {{{ .main .var msg_chars msg_len_byte msg_len_word msg_len_true msg_buf i combined .end-var BIPUSH 0 ISTORE msg_chars // INPUT LOOP input_loop: IN DUP IFEQ input_eof IINC msg_chars 1 GOTO input_loop input_eof: POP // last zero // calculate required buf length in bytes LDC_W OBJREF ILOAD msg_chars INVOKEVIRTUAL calculate_size ISTORE msg_len_byte // We need to go shift characters together, but for that i want filled shit // lets **add** a few characters :) ILOAD msg_len_byte ILOAD msg_chars ISUB // We always have at least one character to pad! BIPUSH 1 ISUB ISTORE i LDC_W BIT_PAD_START // The 1 bit that's required pad_loop: ILOAD i IFEQ pad_done BIPUSH 0 IINC i -1 GOTO pad_loop pad_done: // Calculate heap size LDC_W OBJREF ILOAD msg_len_byte BIPUSH 2 INVOKEVIRTUAL shr ISTORE msg_len_word // Allocate heap ILOAD msg_len_word BIPUSH 2 // remaining 64 bits IADD ISTORE msg_len_true ILOAD msg_len_true NEWARRAY ISTORE msg_buf // Index for storing ILOAD msg_len_word BIPUSH 1 ISUB ISTORE i fill_loop: // pops off stack, stores in leftmost byte, clears rest LDC_W OBJREF SWAP LDC_W SHL_24 SWAP // swap x, y for mul for speed! INVOKEVIRTUAL mul SWAP // shift next byte 16, combine LDC_W OBJREF SWAP LDC_W SHL_16 SWAP INVOKEVIRTUAL mul IOR SWAP // shift next byte 8, combine LDC_W OBJREF SWAP LDC_W SHL_8 SWAP INVOKEVIRTUAL mul IOR // final byte, no shift IOR // Value done! // store it! ILOAD i ILOAD msg_buf IASTORE IINC i -1 ILOAD i IFLT fill_done GOTO fill_loop fill_done: // Finally we need the *bit size* at the end // bit size LDC_W OBJREF ILOAD msg_chars BIPUSH 8 INVOKEVIRTUAL mul // load in last 2 bytes (lol 32bit only fuck you) ILOAD msg_len_word ILOAD msg_buf IASTORE LDC_W OBJREF ILOAD msg_buf ILOAD msg_len_true INVOKEVIRTUAL md5sum HALT .end-main // }}} // calculate_size {{{ .method calculate_size(initial_size) .var size .end-var // Need to find length (with at least one padding) that satisfies bitlength // x % 512 == 448 BIPUSH 1 LDC_W OBJREF ILOAD initial_size BIPUSH 8 INVOKEVIRTUAL mul IADD ISTORE size loop: ILOAD size LDC_W SIZE_MODULO IAND LDC_W SIZE_EQUIV IF_ICMPEQ found // Add one, very fast! IINC size 1 GOTO loop found: LDC_W OBJREF ILOAD size BIPUSH 3 INVOKEVIRTUAL shr IRETURN .end-method // }}} // md5sum {{{ .method md5sum(buf, len) .var offset i h0 h1 h2 h3 a b c d f g temp round_shifts round_sines .end-var // INITIALIZE STATE BIPUSH 0 ISTORE offset LDC_W BASE_H0 ISTORE h0 LDC_W BASE_H1 ISTORE h1 LDC_W BASE_H2 ISTORE h2 LDC_W BASE_H3 ISTORE h3 LDC_W OBJREF INVOKEVIRTUAL get_round_shifts ISTORE round_shifts LDC_W OBJREF INVOKEVIRTUAL get_sines ISTORE round_sines // todo offset loop offset_loop: // init hash values ILOAD h0 ISTORE a ILOAD h1 ISTORE b ILOAD h2 ISTORE c ILOAD h3 ISTORE d // loop 64 rounds BIPUSH 0 ISTORE i main_loop: ILOAD i BIPUSH 64 IF_ICMPEQ main_loop_end // determine round_type ILOAD i BIPUSH 16 ISUB DUP IFLT round_f BIPUSH 16 ISUB DUP IFLT round_g BIPUSH 16 ISUB DUP IFLT round_h GOTO round_i round_f: // f = (b & c) | ((~b) & d) // = b ~ d & b c & | // g = i LDC_W OBJREF ILOAD b INVOKEVIRTUAL not ILOAD d IAND ILOAD b ILOAD c IAND IOR ISTORE f ILOAD i ISTORE g GOTO rotate round_g: // f = ( d & b ) | ((~d) & c) // = d ~ c & d b & | // g = (5 * i + 1) % 16 LDC_W OBJREF ILOAD d INVOKEVIRTUAL not ILOAD c IAND ILOAD d ILOAD b IAND IOR ISTORE f LDC_W OBJREF ILOAD i BIPUSH 5 INVOKEVIRTUAL mul BIPUSH 1 IADD BIPUSH 15 IAND ISTORE g GOTO rotate round_h: // f = b ^ c ^ d // = b c d ^ ^ // g = (3 * i + 5) % 16 LDC_W OBJREF LDC_W OBJREF ILOAD b ILOAD c INVOKEVIRTUAL xor ILOAD d INVOKEVIRTUAL xor ISTORE f LDC_W OBJREF ILOAD i BIPUSH 3 INVOKEVIRTUAL mul BIPUSH 5 IADD BIPUSH 15 IAND ISTORE g GOTO rotate round_i: // f = c ^ (b | (~d)) // = d ~ b | c ^ // g = (7 * i) % 16 LDC_W OBJREF LDC_W OBJREF ILOAD d INVOKEVIRTUAL not ILOAD b IOR ILOAD c INVOKEVIRTUAL xor ISTORE f LDC_W OBJREF ILOAD i BIPUSH 7 INVOKEVIRTUAL mul BIPUSH 15 IAND ISTORE g GOTO rotate rotate: POP // left over from the comparison tree // temp = d ILOAD d ISTORE temp // d = c ILOAD c ISTORE d // c = b ILOAD b ISTORE c // objref for soon call LDC_W OBJREF // this chunk is the first param to rotateleft // namely a + f + k[i] + w[g] ILOAD a ILOAD f // k[i] ILOAD i ILOAD round_sines IALOAD // w[g] ILOAD g ILOAD offset IADD ILOAD buf IALOAD IADD IADD IADD // first param done // r[i] ILOAD i ILOAD round_shifts IALOAD INVOKEVIRTUAL rotate_left // b = b + rotate_left ILOAD b IADD ISTORE b // a = temp ILOAD temp ISTORE a IINC i 1 ILOAD i BIPUSH 64 IFEQ main_loop_end GOTO main_loop main_loop_end: ILOAD h0 ILOAD a IADD ISTORE h0 ILOAD h1 ILOAD b IADD ISTORE h1 ILOAD h2 ILOAD c IADD ISTORE h2 ILOAD h3 ILOAD d IADD ISTORE h3 // Increment offset by 16 words IINC offset 16 // Check if we are done ILOAD offset ILOAD len IF_ICMPEQ offset_loop_end GOTO offset_loop offset_loop_end: // #print "DONE\nhash=" LDC_W OBJREF ILOAD h0 INVOKEVIRTUAL print_bytes POP LDC_W OBJREF ILOAD h1 INVOKEVIRTUAL print_bytes POP LDC_W OBJREF ILOAD h2 INVOKEVIRTUAL print_bytes POP LDC_W OBJREF ILOAD h3 INVOKEVIRTUAL print_bytes POP #print "\n" BIPUSH 0 IRETURN .end-method // }}} // get_round_shifts {{{ .method get_round_shifts() .var shifts idx i .end-var BIPUSH 64 NEWARRAY ISTORE shifts BIPUSH 0 DUP ISTORE idx ISTORE i loop1: // 7 12 17 22 BIPUSH 7 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 12 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 17 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 22 ILOAD idx ILOAD shifts IASTORE IINC idx 1 IINC i 1 ILOAD i BIPUSH 4 ISUB IFLT loop1 BIPUSH 0 ISTORE i loop2: // 5 9 14 20 BIPUSH 5 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 9 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 14 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 20 ILOAD idx ILOAD shifts IASTORE IINC idx 1 IINC i 1 ILOAD i BIPUSH 4 ISUB IFLT loop2 BIPUSH 0 ISTORE i loop3: // 4 11 16 23 BIPUSH 4 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 11 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 16 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 23 ILOAD idx ILOAD shifts IASTORE IINC idx 1 IINC i 1 ILOAD i BIPUSH 4 ISUB IFLT loop3 BIPUSH 0 ISTORE i loop4: // 6 10 15 21 BIPUSH 6 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 10 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 15 ILOAD idx ILOAD shifts IASTORE IINC idx 1 BIPUSH 21 ILOAD idx ILOAD shifts IASTORE IINC idx 1 IINC i 1 ILOAD i BIPUSH 4 ISUB IFLT loop4 // woo finally done ILOAD shifts IRETURN .end-method // }}} // get_sines {{{ .method get_sines() .var sines idx .end-var BIPUSH 64 NEWARRAY ISTORE sines BIPUSH 0 ISTORE idx LDC_W SINES_0 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_1 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_2 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_3 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_4 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_5 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_6 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_7 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_8 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_9 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_10 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_11 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_12 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_13 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_14 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_15 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_16 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_17 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_18 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_19 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_20 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_21 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_22 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_23 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_24 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_25 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_26 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_27 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_28 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_29 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_30 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_31 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_32 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_33 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_34 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_35 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_36 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_37 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_38 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_39 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_40 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_41 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_42 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_43 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_44 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_45 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_46 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_47 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_48 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_49 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_50 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_51 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_52 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_53 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_54 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_55 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_56 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_57 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_58 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_59 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_60 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_61 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_62 ILOAD idx ILOAD sines IASTORE IINC idx 1 LDC_W SINES_63 ILOAD idx ILOAD sines IASTORE IINC idx 1 ILOAD sines IRETURN .end-method // }}} // print_buf {{{ .method print_buf(buf, len) .var i .end-var ILOAD len IFLT done BIPUSH 0 ISTORE i loop: ILOAD i ILOAD len IF_ICMPEQ done LDC_W OBJREF ILOAD i ILOAD buf IALOAD INVOKEVIRTUAL print_bytes POP #print " " IINC i 1 GOTO loop done: #print "\n" BIPUSH 0 IRETURN .end-method // }}} // print_bytes {{{ .method print_bytes(int) // byte 1 ILOAD int DUP LDC_W MASK_8 IAND LDC_W OBJREF SWAP INVOKEVIRTUAL print_byte POP // byte 2 LDC_W OBJREF SWAP BIPUSH 8 INVOKEVIRTUAL shr DUP LDC_W MASK_8 IAND LDC_W OBJREF SWAP INVOKEVIRTUAL print_byte POP // byte 3 LDC_W OBJREF SWAP BIPUSH 8 INVOKEVIRTUAL shr DUP LDC_W MASK_8 IAND LDC_W OBJREF SWAP INVOKEVIRTUAL print_byte POP // byte 4 LDC_W OBJREF SWAP BIPUSH 8 INVOKEVIRTUAL shr LDC_W OBJREF SWAP INVOKEVIRTUAL print_byte POP BIPUSH 0 IRETURN .end-method // }}} // print_byte {{{ .method print_byte(byte) // upper LDC_W OBJREF ILOAD byte BIPUSH 4 INVOKEVIRTUAL shr BIPUSH 0xF IAND DUP BIPUSH 10 ISUB IFLT normal1 // hex offset to push it into A BIPUSH 39 IADD normal1: BIPUSH 48 IADD OUT // lower ILOAD byte BIPUSH 0xF IAND DUP BIPUSH 10 ISUB IFLT normal2 // hex BIPUSH 39 IADD normal2: BIPUSH 48 IADD OUT BIPUSH 0 IRETURN .end-method // }}} // not {{{ .method not(x) LDC_W OBJREF ILOAD x LDC_W NOT_PATTERN INVOKEVIRTUAL xor IRETURN .end-method // }}} // xor {{{ .method xor(x, y) ILOAD x LDC_W XOR_PATTERN_1 IAND ILOAD y LDC_W XOR_PATTERN_1 IAND IADD LDC_W XOR_PATTERN_1 IAND ILOAD x LDC_W XOR_PATTERN_2 IAND ILOAD y LDC_W XOR_PATTERN_2 IAND IADD LDC_W XOR_PATTERN_2 IAND IOR IRETURN .end-method /// }}} // mul {{{ .method mul(x, y) // For the love of god, ensure *y* is the small number .var sum .end-var BIPUSH 0 ISTORE sum loop_mul: ILOAD y IFEQ done ILOAD sum ILOAD x IADD ISTORE sum IINC y -1 GOTO loop_mul done: ILOAD sum IRETURN .end-method // }}} // div {{{ .method div(a, b) // Stolen from mandelbread, with love .var signed res k bshift .end-var // store the signed state BIPUSH 0 ISTORE signed // get absolute of a and b ha: ILOAD a IFLT negate_a hb: ILOAD b IFLT negate_b handled: BIPUSH 0 ISTORE res // edge case if a < b, we're done ILOAD a ILOAD b ISUB IFLT apply_sign // edge case if b == 0, we error ILOAD b IFEQ division_by_zero BIPUSH 1 ISTORE k ILOAD b ISTORE bshift // build a stack of kn, kn * b, kn-1, kn-1 * b, ..., k0 (1), k0 * b (b) build_stack: ILOAD a ILOAD bshift ISUB IFLT stack_unwind // push bshift to stack and bshift += bshift ILOAD bshift DUP DUP IADD ISTORE bshift // push k to stack and k += k ILOAD k DUP DUP IADD ISTORE k GOTO build_stack stack_unwind: ISTORE k // stores k from (k * b) in size // a - (k * b) ILOAD a SWAP ISUB // duplicate a - (k * b) on stack DUP // if (a - (k * b) < 0) cant_substract IFLT cant_substract substract: // store a = a - k * b ISTORE a // calculate res ILOAD res ILOAD k IADD ISTORE res ILOAD k BIPUSH 1 IF_ICMPEQ apply_sign GOTO stack_unwind cant_substract: // pop a - (k * b) from the stack POP ILOAD k BIPUSH 1 IF_ICMPEQ apply_sign GOTO stack_unwind apply_sign: ILOAD signed IFEQ ret_res BIPUSH 0 ILOAD res ISUB IRETURN ret_res: ILOAD res IRETURN negate_a: BIPUSH 0 ILOAD a ISUB ISTORE a IINC signed 1 GOTO hb negate_b: BIPUSH 0 ILOAD b ISUB ISTORE b IINC signed 1 GOTO handled division_by_zero: BIPUSH 100 OUT BIPUSH 105 OUT BIPUSH 118 OUT BIPUSH 32 OUT BIPUSH 98 OUT BIPUSH 121 OUT BIPUSH 32 OUT BIPUSH 48 OUT BIPUSH 10 OUT ERR .end-method // }}} // shl {{{ .method shl(x, y) // multiply by 2, y times :) // dynamic version. If you know ahead of time, use the SHL_x constants and mul loop: ILOAD y IFEQ done LDC_W OBJREF ILOAD x BIPUSH 2 INVOKEVIRTUAL mul ISTORE x IINC y -1 GOTO loop done: ILOAD x IRETURN .end-method // }}} // shr {{{ .method shr(x, y) // t'is horrible, but it works! .var unsigned result .end-var // def shr(x, y) // unsigned = x & 0x7F_FF_FF_FF // result = unsigned / (2 << (y-1)) // // if x & 0x80_00_00_00 != 0 // result |= (1 << (31 - y)) // end // // result //end LDC_W OBJREF // all bits but the sign ILOAD x LDC_W MASK_31 IAND LDC_W OBJREF BIPUSH 1 ILOAD y INVOKEVIRTUAL shl INVOKEVIRTUAL div // check if sign is set ILOAD x LDC_W MASK_SIGN IAND IFEQ no_sign has_sign: LDC_W OBJREF BIPUSH 1 BIPUSH 31 ILOAD y ISUB INVOKEVIRTUAL shl IOR no_sign: IRETURN .end-method // }}} // rotate_left {{{ .method rotate_left(x, c) .var left right rightright .end-var // (((x) << (c)) | ((x) >> (32 - (c)))) // (x << c) | (x >> (32 - c)) // x c << x 32 c - >> | LDC_W OBJREF ILOAD x ILOAD c INVOKEVIRTUAL shl ISTORE left BIPUSH 32 ILOAD c ISUB ISTORE rightright LDC_W OBJREF ILOAD x ILOAD rightright INVOKEVIRTUAL shr ISTORE right ILOAD left ILOAD right IOR IRETURN .end-method // }}}