3 # ====================================================================
4 # Copyright (c) 2008 Andy Polyakov <appro@openssl.org>
6 # This module may be used under the terms of either the GNU General
7 # Public License version 2 or later, the GNU Lesser General Public
8 # License version 2.1 or later, the Mozilla Public License version
9 # 1.1 or the BSD License. The exact terms of either license are
10 # distributed along with this module. For further details see
11 # http://www.openssl.org/~appro/camellia/.
12 # ====================================================================
14 # Performance in cycles per processed byte (less is better) in
15 # 'openssl speed ...' benchmark:
18 # -evp camellia-128-ecb 16.7 21.0 22.7
19 # + over gcc 3.4.6 +25% +5% 0%
21 # camellia-128-cbc 15.7 20.4 21.1
23 # 128-bit key setup 128 216 205 cycles/key
24 # + over gcc 3.4.6 +54% +39% +15%
26 # Numbers in "+" rows represent performance improvement over compiler
27 # generated code. Key setup timings are impressive on AMD and Core2
28 # thanks to 64-bit operations being covertly deployed. Improvement on
29 # EM64T, pre-Core2 Intel x86_64 CPU, is not as impressive, because it
30 # apparently emulates some of 64-bit operations in [32-bit] microcode.
34 if ($flavour =~ /\./) { $output = $flavour; undef $flavour; }
36 $win64=0; $win64=1 if ($flavour =~ /[nm]asm|mingw64/ || $output =~ /\.asm$/);
38 $0 =~ m/(.*[\/\\])[^\/\\]+$/; $dir=$1;
39 ( $xlate="${dir}x86_64-xlate.pl" and -f $xlate ) or
40 ( $xlate="${dir}../../perlasm/x86_64-xlate.pl" and -f $xlate) or
41 die "can't locate x86_64-xlate.pl";
43 open STDOUT,"| $^X $xlate $flavour $output";
45 sub hi() { my $r=shift; $r =~ s/%[er]([a-d])x/%\1h/; $r; }
46 sub lo() { my $r=shift; $r =~ s/%[er]([a-d])x/%\1l/;
47 $r =~ s/%[er]([sd]i)/%\1l/;
48 $r =~ s/%(r[0-9]+)[d]?/%\1b/; $r; }
50 $t0="%eax";$t1="%ebx";$t2="%ecx";$t3="%edx";
51 @S=("%r8d","%r9d","%r10d","%r11d");
54 $Tbl="%rbp"; # size optimization
59 $arg0d=$win64?"%ecx":"%edi";
61 # const unsigned int Camellia_SBOX[4][256];
62 # Well, sort of... Camellia_SBOX[0][] is interleaved with [1][],
63 # and [2][] - with [3][]. This is done to minimize code size.
64 $SBOX1_1110=0; # Camellia_SBOX[0]
65 $SBOX4_4404=4; # Camellia_SBOX[1]
66 $SBOX2_0222=2048; # Camellia_SBOX[2]
67 $SBOX3_3033=2052; # Camellia_SBOX[3]
69 sub Camellia_Feistel {
71 my $seed=defined(@_[1])?@_[1]:0;
72 my $scale=$seed<0?-8:8;
74 my $s0=@S[($j)%4],$s1=@S[($j+1)%4],$s2=@S[($j+2)%4],$s3=@S[($j+3)%4];
77 xor $s0,$t0 # t0^=key[0]
78 xor $s1,$t1 # t1^=key[1]
79 movz `&hi("$t0")`,$i0 # (t0>>8)&0xff
80 movz `&lo("$t1")`,$i1 # (t1>>0)&0xff
81 mov $SBOX3_3033($Tbl,$i0,8),$t3 # t3=SBOX3_3033[0]
82 mov $SBOX1_1110($Tbl,$i1,8),$t2 # t2=SBOX1_1110[1]
83 movz `&lo("$t0")`,$i0 # (t0>>0)&0xff
85 movz `&hi("$t1")`,$i1 # (t1>>8)&0xff
86 xor $SBOX4_4404($Tbl,$i0,8),$t3 # t3^=SBOX4_4404[0]
88 xor $SBOX4_4404($Tbl,$i1,8),$t2 # t2^=SBOX4_4404[1]
89 movz `&hi("$t0")`,$i0 # (t0>>24)&0xff
90 movz `&lo("$t1")`,$i1 # (t1>>16)&0xff
91 xor $SBOX1_1110($Tbl,$i0,8),$t3 # t3^=SBOX1_1110[0]
92 xor $SBOX3_3033($Tbl,$i1,8),$t2 # t2^=SBOX3_3033[1]
93 movz `&lo("$t0")`,$i0 # (t0>>16)&0xff
94 movz `&hi("$t1")`,$i1 # (t1>>24)&0xff
95 xor $SBOX2_0222($Tbl,$i0,8),$t3 # t3^=SBOX2_0222[0]
96 xor $SBOX2_0222($Tbl,$i1,8),$t2 # t2^=SBOX2_0222[1]
97 mov `$seed+($i+1)*$scale`($key),$t1 # prefetch key[i+1]
98 mov `$seed+($i+1)*$scale+4`($key),$t0
100 ror \$8,$t3 # t3=RightRotate(t3,8)
107 # void Camellia_EncryptBlock_Rounds(
109 # const Byte plaintext[],
110 # const KEY_TABLE_TYPE keyTable,
116 .globl Camellia_EncryptBlock
117 .type Camellia_EncryptBlock,\@abi-omnipotent
119 Camellia_EncryptBlock:
123 adcl \$0,$arg0d # keyBitLength==128?3:4
125 .size Camellia_EncryptBlock,.-Camellia_EncryptBlock
127 .globl Camellia_EncryptBlock_Rounds
128 .type Camellia_EncryptBlock_Rounds,\@function,4
131 Camellia_EncryptBlock_Rounds:
139 #mov %rsi,$inp # put away arguments
143 shl \$6,%edi # process grandRounds
144 lea .LCamellia_SBOX(%rip),$Tbl
145 lea ($key,%rdi),$keyend
147 mov 0(%rsi),@S[0] # load plaintext
156 call _x86_64_Camellia_encrypt
175 .size Camellia_EncryptBlock_Rounds,.-Camellia_EncryptBlock_Rounds
177 .type _x86_64_Camellia_encrypt,\@abi-omnipotent
179 _x86_64_Camellia_encrypt:
181 xor 4($key),@S[0] # ^=key[0-3]
186 mov 16($key),$t1 # prefetch key[4-5]
190 for ($i=0;$i<6;$i++) { Camellia_Feistel($i,16); }
194 mov 8($key),$t3 # prefetch key[2-3]
201 xor $t3,@S[2] # s2^=s3|key[3];
202 xor $t0,@S[1] # s1^=LeftRotate(s0&key[0],1);
206 xor $t1,@S[0] # s0^=s1|key[1];
207 xor $t2,@S[3] # s3^=LeftRotate(s2&key[2],1);
212 xor @S[2],$t0 # SwapHalf
222 .byte 0xf3,0xc3 # rep ret
223 .size _x86_64_Camellia_encrypt,.-_x86_64_Camellia_encrypt
226 .globl Camellia_DecryptBlock
227 .type Camellia_DecryptBlock,\@abi-omnipotent
229 Camellia_DecryptBlock:
233 adcl \$0,$arg0d # keyBitLength==128?3:4
235 .size Camellia_DecryptBlock,.-Camellia_DecryptBlock
237 .globl Camellia_DecryptBlock_Rounds
238 .type Camellia_DecryptBlock_Rounds,\@function,4
241 Camellia_DecryptBlock_Rounds:
249 #mov %rsi,$inp # put away arguments
253 shl \$6,%edi # process grandRounds
254 lea .LCamellia_SBOX(%rip),$Tbl
255 lea ($keyend,%rdi),$key
257 mov 0(%rsi),@S[0] # load plaintext
266 call _x86_64_Camellia_decrypt
285 .size Camellia_DecryptBlock_Rounds,.-Camellia_DecryptBlock_Rounds
287 .type _x86_64_Camellia_decrypt,\@abi-omnipotent
289 _x86_64_Camellia_decrypt:
291 xor 4($key),@S[0] # ^=key[0-3]
296 mov -8($key),$t1 # prefetch key[4-5]
300 for ($i=0;$i<6;$i++) { Camellia_Feistel($i,-8); }
304 mov 0($key),$t3 # prefetch key[2-3]
311 xor $t3,@S[2] # s2^=s3|key[3];
312 xor $t0,@S[1] # s1^=LeftRotate(s0&key[0],1);
316 xor $t1,@S[0] # s0^=s1|key[1];
317 xor $t2,@S[3] # s3^=LeftRotate(s2&key[2],1);
328 mov $t2,@S[0] # SwapHalf
333 .byte 0xf3,0xc3 # rep ret
334 .size _x86_64_Camellia_decrypt,.-_x86_64_Camellia_decrypt
338 my ($rnd,$key,@T)=@_;
339 my $bias=int(@T[0])?shift(@T):0;
343 mov @T[1],`$bias+$rnd*8+0`($key)
344 mov @T[0],`$bias+$rnd*8+4`($key)
345 mov @T[3],`$bias+$rnd*8+8`($key)
346 mov @T[2],`$bias+$rnd*8+12`($key)
349 $code.=" mov @T[0],`$bias+$rnd*8+0`($key)\n";
350 $code.=" mov @T[1],`$bias+$rnd*8+8`($key)\n" if ($#T>=1);
355 my ($rnd,$key,@T)=@_;
356 my $bias=int(@T[0])?shift(@T):0;
358 $code.=" mov `$bias+$rnd*8+0`($key),@T[0]\n";
359 $code.=" mov `$bias+$rnd*8+8`($key),@T[1]\n" if ($#T>=1);
362 # shld is very slow on Intel EM64T family. Even on AMD it limits
363 # instruction decode rate [because it's VectorPath] and consequently
366 my ($i0,$i1,$rot)=@_;
377 # ... Implementing 128-bit rotate without shld gives 80% better
378 # performance EM64T, +15% on AMD64 and only ~7% degradation on
379 # Core2. This is therefore preferred.
381 my ($i0,$i1,$rot)=@_;
400 .globl Camellia_Ekeygen
401 .type Camellia_Ekeygen,\@function,3
411 mov %rdi,$keyend # put away arguments, keyBitLength
412 mov %rdx,$out # keyTable
414 mov 0(%rsi),@S[0] # load 0-127 bits
424 &_saveround (0,$out,@S); # KL<<<0
426 cmp \$128,$keyend # check keyBitLength
429 mov 16(%rsi),@S[0] # load 128-191 bits
433 mov 24(%rsi),@S[2] # load 192-255 bits
447 &_saveround (4,$out,@S); # temp storage for KR!
449 xor 0($out),@S[1] # KR^KL
455 lea .LCamellia_SIGMA(%rip),$key
456 lea .LCamellia_SBOX(%rip),$Tbl
461 &Camellia_Feistel($step++);
462 &Camellia_Feistel($step++);
464 xor 0($out),@S[1] # ^KL
469 &Camellia_Feistel($step++);
470 &Camellia_Feistel($step++);
475 lea 128($out),$out # size optimization
476 shl \$32,%r8 # @S[0]||
477 shl \$32,%r10 # @S[2]||
479 or %r11,%r10 # ||@S[3]
481 &_loadround (0,$out,-128,"%rax","%rbx"); # KL
482 &_saveround (2,$out,-128,"%r8","%r10"); # KA<<<0
483 &_rotl128 ("%rax","%rbx",15);
484 &_saveround (4,$out,-128,"%rax","%rbx"); # KL<<<15
485 &_rotl128 ("%r8","%r10",15);
486 &_saveround (6,$out,-128,"%r8","%r10"); # KA<<<15
487 &_rotl128 ("%r8","%r10",15); # 15+15=30
488 &_saveround (8,$out,-128,"%r8","%r10"); # KA<<<30
489 &_rotl128 ("%rax","%rbx",30); # 15+30=45
490 &_saveround (10,$out,-128,"%rax","%rbx"); # KL<<<45
491 &_rotl128 ("%r8","%r10",15); # 30+15=45
492 &_saveround (12,$out,-128,"%r8"); # KA<<<45
493 &_rotl128 ("%rax","%rbx",15); # 45+15=60
494 &_saveround (13,$out,-128,"%rbx"); # KL<<<60
495 &_rotl128 ("%r8","%r10",15); # 45+15=60
496 &_saveround (14,$out,-128,"%r8","%r10"); # KA<<<60
497 &_rotl128 ("%rax","%rbx",17); # 60+17=77
498 &_saveround (16,$out,-128,"%rax","%rbx"); # KL<<<77
499 &_rotl128 ("%rax","%rbx",17); # 77+17=94
500 &_saveround (18,$out,-128,"%rax","%rbx"); # KL<<<94
501 &_rotl128 ("%r8","%r10",34); # 60+34=94
502 &_saveround (20,$out,-128,"%r8","%r10"); # KA<<<94
503 &_rotl128 ("%rax","%rbx",17); # 94+17=111
504 &_saveround (22,$out,-128,"%rax","%rbx"); # KL<<<111
505 &_rotl128 ("%r8","%r10",17); # 94+17=111
506 &_saveround (24,$out,-128,"%r8","%r10"); # KA<<<111
513 &_saveround (6,$out,@S); # temp storage for KA!
515 xor `4*8+0`($out),@S[1] # KA^KR
516 xor `4*8+4`($out),@S[0]
517 xor `5*8+0`($out),@S[3]
518 xor `5*8+4`($out),@S[2]
520 &Camellia_Feistel($step++);
521 &Camellia_Feistel($step++);
523 &_loadround (0,$out,"%rax","%rbx"); # KL
524 &_loadround (4,$out,"%rcx","%rdx"); # KR
525 &_loadround (6,$out,"%r14","%r15"); # KA
527 lea 128($out),$out # size optimization
528 shl \$32,%r8 # @S[0]||
529 shl \$32,%r10 # @S[2]||
531 or %r11,%r10 # ||@S[3]
533 &_saveround (2,$out,-128,"%r8","%r10"); # KB<<<0
534 &_rotl128 ("%rcx","%rdx",15);
535 &_saveround (4,$out,-128,"%rcx","%rdx"); # KR<<<15
536 &_rotl128 ("%r14","%r15",15);
537 &_saveround (6,$out,-128,"%r14","%r15"); # KA<<<15
538 &_rotl128 ("%rcx","%rdx",15); # 15+15=30
539 &_saveround (8,$out,-128,"%rcx","%rdx"); # KR<<<30
540 &_rotl128 ("%r8","%r10",30);
541 &_saveround (10,$out,-128,"%r8","%r10"); # KB<<<30
542 &_rotl128 ("%rax","%rbx",45);
543 &_saveround (12,$out,-128,"%rax","%rbx"); # KL<<<45
544 &_rotl128 ("%r14","%r15",30); # 15+30=45
545 &_saveround (14,$out,-128,"%r14","%r15"); # KA<<<45
546 &_rotl128 ("%rax","%rbx",15); # 45+15=60
547 &_saveround (16,$out,-128,"%rax","%rbx"); # KL<<<60
548 &_rotl128 ("%rcx","%rdx",30); # 30+30=60
549 &_saveround (18,$out,-128,"%rcx","%rdx"); # KR<<<60
550 &_rotl128 ("%r8","%r10",30); # 30+30=60
551 &_saveround (20,$out,-128,"%r8","%r10"); # KB<<<60
552 &_rotl128 ("%rax","%rbx",17); # 60+17=77
553 &_saveround (22,$out,-128,"%rax","%rbx"); # KL<<<77
554 &_rotl128 ("%r14","%r15",32); # 45+32=77
555 &_saveround (24,$out,-128,"%r14","%r15"); # KA<<<77
556 &_rotl128 ("%rcx","%rdx",34); # 60+34=94
557 &_saveround (26,$out,-128,"%rcx","%rdx"); # KR<<<94
558 &_rotl128 ("%r14","%r15",17); # 77+17=94
559 &_saveround (28,$out,-128,"%r14","%r15"); # KA<<<77
560 &_rotl128 ("%rax","%rbx",34); # 77+34=111
561 &_saveround (30,$out,-128,"%rax","%rbx"); # KL<<<111
562 &_rotl128 ("%r8","%r10",51); # 60+51=111
563 &_saveround (32,$out,-128,"%r8","%r10"); # KB<<<111
575 .size Camellia_Ekeygen,.-Camellia_Ekeygen
580 112,130, 44,236,179, 39,192,229,228,133, 87, 53,234, 12,174, 65,
581 35,239,107,147, 69, 25,165, 33,237, 14, 79, 78, 29,101,146,189,
582 134,184,175,143,124,235, 31,206, 62, 48,220, 95, 94,197, 11, 26,
583 166,225, 57,202,213, 71, 93, 61,217, 1, 90,214, 81, 86,108, 77,
584 139, 13,154,102,251,204,176, 45,116, 18, 43, 32,240,177,132,153,
585 223, 76,203,194, 52,126,118, 5,109,183,169, 49,209, 23, 4,215,
586 20, 88, 58, 97,222, 27, 17, 28, 50, 15,156, 22, 83, 24,242, 34,
587 254, 68,207,178,195,181,122,145, 36, 8,232,168, 96,252,105, 80,
588 170,208,160,125,161,137, 98,151, 84, 91, 30,149,224,255,100,210,
589 16,196, 0, 72,163,247,117,219,138, 3,230,218, 9, 63,221,148,
590 135, 92,131, 2,205, 74,144, 51,115,103,246,243,157,127,191,226,
591 82,155,216, 38,200, 55,198, 59,129,150,111, 75, 19,190, 99, 46,
592 233,121,167,140,159,110,188,142, 41,245,249,182, 47,253,180, 89,
593 120,152, 6,106,231, 70,113,186,212, 37,171, 66,136,162,141,250,
594 114, 7,185, 85,248,238,172, 10, 54, 73, 42,104, 60, 56,241,164,
595 64, 40,211,123,187,201, 67,193, 21,227,173,244,119,199,128,158);
597 sub S1110 { my $i=shift; $i=@SBOX[$i]; $i=$i<<24|$i<<16|$i<<8; sprintf("0x%08x",$i); }
598 sub S4404 { my $i=shift; $i=($i<<1|$i>>7)&0xff; $i=@SBOX[$i]; $i=$i<<24|$i<<16|$i; sprintf("0x%08x",$i); }
599 sub S0222 { my $i=shift; $i=@SBOX[$i]; $i=($i<<1|$i>>7)&0xff; $i=$i<<16|$i<<8|$i; sprintf("0x%08x",$i); }
600 sub S3033 { my $i=shift; $i=@SBOX[$i]; $i=($i>>1|$i<<7)&0xff; $i=$i<<24|$i<<8|$i; sprintf("0x%08x",$i); }
605 .long 0x3bcc908b, 0xa09e667f, 0x4caa73b2, 0xb67ae858
606 .long 0xe94f82be, 0xc6ef372f, 0xf1d36f1c, 0x54ff53a5
607 .long 0xde682d1d, 0x10e527fa, 0xb3e6c1fd, 0xb05688c2
611 # tables are interleaved, remember?
612 sub data_word { $code.=".long\t".join(',',@_)."\n"; }
613 for ($i=0;$i<256;$i++) { &data_word(&S1110($i),&S4404($i)); }
614 for ($i=0;$i<256;$i++) { &data_word(&S0222($i),&S3033($i)); }
616 # void Camellia_cbc_encrypt (const void char *inp, unsigned char *out,
617 # size_t length, const CAMELLIA_KEY *key,
618 # unsigned char *ivp,const int enc);
621 $_end="8(%rsp)"; # inp+len&~15
622 $_res="16(%rsp)"; # len&15
628 .globl Camellia_cbc_encrypt
629 .type Camellia_cbc_encrypt,\@function,6
631 Camellia_cbc_encrypt:
646 # place stack frame just "above mod 1024" the key schedule,
647 # this ensures that cache associativity suffices
648 lea -64-63(%rcx),%r10
653 add \$8,%rsp # 8 is reserved for callee's ra
655 mov %rdi,$inp # inp argument
656 mov %rsi,$out # out argument
657 mov %r8,%rbx # ivp argument
658 mov %rcx,$key # key argument
659 mov 272(%rcx),$keyend # grandRounds
665 lea .LCamellia_SBOX(%rip),$Tbl
675 loop .Lcbc_prefetch_sbox
678 mov %rdx,%rcx # len argument
679 lea ($key,$keyend),$keyend
681 cmp \$0,%r9d # enc argument
685 and \$15,%rcx # length residue
692 mov 0(%rbx),@S[0] # load IV
710 call _x86_64_Camellia_encrypt
712 mov $_key,$key # "rewind" the key
732 mov @S[0],0($out) # write out IV residue
749 .long 0x9066A4F3 # rep movsb
755 jmp .Lcbc_eloop # one more time
761 and \$15,%rcx # length residue
768 mov (%rbx),%rax # load IV
779 mov %rax,0+$ivec # save IV to temporary storage
784 call _x86_64_Camellia_decrypt
786 mov $_key,$key # "rewind" the key
791 mov ($inp),%rax # load IV for next iteration
823 mov %rax,(%rdx) # write out IV residue
837 .long 0x9066A4F3 # rep movsb
840 mov %rax,(%rdx) # write out IV residue
856 .size Camellia_cbc_encrypt,.-Camellia_cbc_encrypt
858 .asciz "Camellia for x86_64 by <appro@openssl.org>"
862 # EXCEPTION_DISPOSITION handler (EXCEPTION_RECORD *rec,ULONG64 frame,
863 # CONTEXT *context,DISPATCHER_CONTEXT *disp)
871 .extern __imp_RtlVirtualUnwind
872 .type common_se_handler,\@abi-omnipotent
885 mov 120($context),%rax # pull context->Rax
886 mov 248($context),%rbx # pull context->Rip
888 mov 8($disp),%rsi # disp->ImageBase
889 mov 56($disp),%r11 # disp->HandlerData
891 mov 0(%r11),%r10d # HandlerData[0]
892 lea (%rsi,%r10),%r10 # prologue label
893 cmp %r10,%rbx # context->Rip<prologue label
896 mov 152($context),%rax # pull context->Rsp
898 mov 4(%r11),%r10d # HandlerData[1]
899 lea (%rsi,%r10),%r10 # epilogue label
900 cmp %r10,%rbx # context->Rip>=epilogue label
909 mov %rbx,144($context) # restore context->Rbx
910 mov %rbp,160($context) # restore context->Rbp
911 mov %r13,224($context) # restore context->R13
912 mov %r14,232($context) # restore context->R14
913 mov %r15,240($context) # restore context->R15
918 mov %rax,152($context) # restore context->Rsp
919 mov %rsi,168($context) # restore context->Rsi
920 mov %rdi,176($context) # restore context->Rdi
922 mov 40($disp),%rdi # disp->ContextRecord
925 .long 0xa548f3fc # cld; rep movsq
928 xor %rcx,%rcx # arg1, UNW_FLAG_NHANDLER
929 mov 8(%rsi),%rdx # arg2, disp->ImageBase
930 mov 0(%rsi),%r8 # arg3, disp->ControlPc
931 mov 16(%rsi),%r9 # arg4, disp->FunctionEntry
932 mov 40(%rsi),%r10 # disp->ContextRecord
933 lea 56(%rsi),%r11 # &disp->HandlerData
934 lea 24(%rsi),%r12 # &disp->EstablisherFrame
935 mov %r10,32(%rsp) # arg5
936 mov %r11,40(%rsp) # arg6
937 mov %r12,48(%rsp) # arg7
938 mov %rcx,56(%rsp) # arg8, (NULL)
939 call *__imp_RtlVirtualUnwind(%rip)
941 mov \$1,%eax # ExceptionContinueSearch
952 .size common_se_handler,.-common_se_handler
954 .type cbc_se_handler,\@abi-omnipotent
968 mov 120($context),%rax # pull context->Rax
969 mov 248($context),%rbx # pull context->Rip
971 lea .Lcbc_prologue(%rip),%r10
972 cmp %r10,%rbx # context->Rip<.Lcbc_prologue
975 lea .Lcbc_body(%rip),%r10
976 cmp %r10,%rbx # context->Rip<.Lcbc_body
977 jb .Lin_cbc_frame_setup
979 mov 152($context),%rax # pull context->Rsp
981 lea .Lcbc_abort(%rip),%r10
982 cmp %r10,%rbx # context->Rip>=.Lcbc_abort
983 jae .Lin_cbc_prologue
985 mov 48(%rax),%rax # $_rsp
988 .Lin_cbc_frame_setup:
995 mov %rbx,144($context) # restore context->Rbx
996 mov %rbp,160($context) # restore context->Rbp
997 mov %r12,216($context) # restore context->R12
998 mov %r13,224($context) # restore context->R13
999 mov %r14,232($context) # restore context->R14
1000 mov %r15,240($context) # restore context->R15
1005 mov %rax,152($context) # restore context->Rsp
1006 mov %rsi,168($context) # restore context->Rsi
1007 mov %rdi,176($context) # restore context->Rdi
1009 mov 40($disp),%rdi # disp->ContextRecord
1010 mov $context,%rsi # context
1011 mov \$`1232/8`,%ecx # sizeof(CONTEXT)
1012 .long 0xa548f3fc # cld; rep movsq
1015 xor %rcx,%rcx # arg1, UNW_FLAG_NHANDLER
1016 mov 8(%rsi),%rdx # arg2, disp->ImageBase
1017 mov 0(%rsi),%r8 # arg3, disp->ControlPc
1018 mov 16(%rsi),%r9 # arg4, disp->FunctionEntry
1019 mov 40(%rsi),%r10 # disp->ContextRecord
1020 lea 56(%rsi),%r11 # &disp->HandlerData
1021 lea 24(%rsi),%r12 # &disp->EstablisherFrame
1022 mov %r10,32(%rsp) # arg5
1023 mov %r11,40(%rsp) # arg6
1024 mov %r12,48(%rsp) # arg7
1025 mov %rcx,56(%rsp) # arg8, (NULL)
1026 call *__imp_RtlVirtualUnwind(%rip)
1028 mov \$1,%eax # ExceptionContinueSearch
1040 .size cbc_se_handler,.-cbc_se_handler
1044 .rva .LSEH_begin_Camellia_EncryptBlock_Rounds
1045 .rva .LSEH_end_Camellia_EncryptBlock_Rounds
1046 .rva .LSEH_info_Camellia_EncryptBlock_Rounds
1048 .rva .LSEH_begin_Camellia_DecryptBlock_Rounds
1049 .rva .LSEH_end_Camellia_DecryptBlock_Rounds
1050 .rva .LSEH_info_Camellia_DecryptBlock_Rounds
1052 .rva .LSEH_begin_Camellia_Ekeygen
1053 .rva .LSEH_end_Camellia_Ekeygen
1054 .rva .LSEH_info_Camellia_Ekeygen
1056 .rva .LSEH_begin_Camellia_cbc_encrypt
1057 .rva .LSEH_end_Camellia_cbc_encrypt
1058 .rva .LSEH_info_Camellia_cbc_encrypt
1062 .LSEH_info_Camellia_EncryptBlock_Rounds:
1064 .rva common_se_handler
1065 .rva .Lenc_prologue,.Lenc_epilogue # HandlerData[]
1066 .LSEH_info_Camellia_DecryptBlock_Rounds:
1068 .rva common_se_handler
1069 .rva .Ldec_prologue,.Ldec_epilogue # HandlerData[]
1070 .LSEH_info_Camellia_Ekeygen:
1072 .rva common_se_handler
1073 .rva .Lkey_prologue,.Lkey_epilogue # HandlerData[]
1074 .LSEH_info_Camellia_cbc_encrypt:
1080 $code =~ s/\`([^\`]*)\`/eval $1/gem;