C the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
C MA 02111-1307, USA.
-C Dummy file, all code is currently in aes.asm
+C Register usage:
+C
+C The aes state is kept in %eax, %ebx, %ecx and %edx
+C
+C %esi is used as temporary, to point to the input, and to the
+C subkeys, etc.
+C
+C %ebp is used as the round counter, and as a temporary in the final round.
+C
+C %edi is a temporary, often used as an accumulator.
+
+ .file "aes-encrypt.asm"
+
+ C aes_encrypt(struct aes_context *ctx,
+ C unsigned length, uint8_t *dst,
+ C uint8_t *src)
+ .text
+ .align 16
+ .globl aes_encrypt
+ .type aes_encrypt,@function
+aes_encrypt:
+ C // save all registers that need to be saved
+ pushl %ebx C 16(%esp)
+ pushl %ebp C 12(%esp)
+ pushl %esi C 8(%esp)
+ pushl %edi C 4(%esp)
+
+ C ctx = 20(%esp)
+ C length = 24(%esp)
+ C dst = 28(%esp)
+ C src = 32(%esp)
+
+ movl 24(%esp), %ebp
+ C What's the right way to set the flags?
+ addl $0, %ebp
+ jz .Lencrypt_end
+
+.Lencrypt_block_loop:
+ movl 32(%esp),%esi C address of plaintext
+ movl (%esi),%eax C load plaintext into registers
+ movl 4(%esi),%ebx
+ movl 8(%esi),%ecx
+ movl 12(%esi),%edx
+
+ addl $16, 32(%esp) C Increment src pointer
+C .Laes_got_plain:
+ movl 20(%esp),%esi C address of context struct ctx
+ xorl (%esi),%eax C add first key to plaintext
+ xorl 4(%esi),%ebx
+ xorl 8(%esi),%ecx
+ xorl 12(%esi),%edx
+C .Laes_xored_initial:
+ C FIXME: Use %esi instead
+ movl 20(%esp),%ebp C address of context struct
+ movl AES_NROUNDS (%ebp),%ebp C get number of rounds to do from struct
+
+ subl $1,%ebp
+ addl $16,%esi C point to next key
+.Laes_encrypt_loop:
+ pushl %esi C save this first: we'll clobber it later
+
+ C Computation of the new %eax is broken, in the first test case,
+ C first round, we get 0xb3b638c6, not dfd5b20f, just
+ C before adding the subkey
+
+ C First column, IDXi = 0, 1, 2, 3
+ C T[0] = table[0][B0(%eax)]
+ C ^ table[1][B1(%ebx)]
+ C ^ table[2][B2(%ebx)]
+ C ^ table[3][B3(%ebx)]
+ C
+ C a b c d
+ movl %eax, %esi
+ andl $0xff, %esi
+ shll $2,%esi C index in table
+ movl AES_TABLE0 + _aes_encrypt_table (%esi),%edi
+ movl %ebx, %esi
+ shrl $6,%esi
+ andl $0x000003fc,%esi C clear all but offset bytes
+ xorl AES_TABLE1 + _aes_encrypt_table (%esi),%edi
+ movl %ecx,%esi C third one
+ shrl $14,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE2 + _aes_encrypt_table (%esi),%edi
+ movl %edx,%esi C fourth one
+ shrl $22,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE3 + _aes_encrypt_table (%esi),%edi
+ pushl %edi C save first on stack
+
+ C // Second column
+ C b c d a
+ movl %ebx,%esi C copy first in
+ andl $0x000000ff,%esi C clear all but offset
+ shll $2,%esi C index in table
+ movl AES_TABLE0 + _aes_encrypt_table (%esi),%edi
+ movl %ecx,%esi C second one
+ shrl $6,%esi
+ andl $0x000003fc,%esi C clear all but offset bytes
+ xorl AES_TABLE1 + _aes_encrypt_table (%esi),%edi
+ movl %edx,%esi C third one
+ shrl $14,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE2 + _aes_encrypt_table (%esi),%edi
+ movl %eax,%esi C fourth one
+ shrl $22,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE3 + _aes_encrypt_table (%esi),%edi
+ pushl %edi C save first on stack
+
+ C // Third column
+ C c d a b
+ movl %ecx,%esi C copy first in
+ andl $0x000000ff,%esi C clear all but offset
+ shll $2,%esi C index in table
+ movl AES_TABLE0 + _aes_encrypt_table (%esi),%edi
+ movl %edx,%esi C second one
+ shrl $6,%esi
+ andl $0x000003fc,%esi C clear all but offset bytes
+ xorl AES_TABLE1 + _aes_encrypt_table (%esi),%edi
+ movl %eax,%esi C third one
+ shrl $14,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE2 + _aes_encrypt_table (%esi),%edi
+ movl %ebx,%esi C fourth one
+ shrl $22,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE3 + _aes_encrypt_table (%esi),%edi
+ pushl %edi C save first on stack
+
+ C // Fourth column
+ C d a b c
+ movl %edx,%esi C copy first in
+ andl $0x000000ff,%esi C clear all but offset
+ shll $2,%esi C index in table
+ movl AES_TABLE0 + _aes_encrypt_table (%esi),%edi
+ movl %eax,%esi C second one
+ shrl $6,%esi
+ andl $0x000003fc,%esi C clear all but offset bytes
+ xorl AES_TABLE1 + _aes_encrypt_table (%esi),%edi
+ movl %ebx,%esi C third one
+ shrl $14,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE2 + _aes_encrypt_table (%esi),%edi
+ movl %ecx,%esi C fourth one
+ shrl $22,%esi
+ andl $0x000003fc,%esi
+ xorl AES_TABLE3 + _aes_encrypt_table (%esi),%edi
+
+ movl %edi,%edx
+ popl %ecx
+ popl %ebx
+ popl %eax
+ popl %esi
+C .Laes_got_t:
+ xorl (%esi),%eax C add current session key to plaintext
+ xorl 4(%esi),%ebx
+ xorl 8(%esi),%ecx
+ xorl 12(%esi),%edx
+ addl $16,%esi C point to next key
+ decl %ebp
+ jnz .Laes_encrypt_loop
+
+ C // last round
+ C // first column
+ C a b c d
+ movl %eax,%edi
+ andl $0x000000ff,%edi
+ movl %ebx,%ebp
+ andl $0x0000ff00,%ebp
+ orl %ebp,%edi
+ movl %ecx,%ebp
+ andl $0x00ff0000,%ebp
+ orl %ebp,%edi
+ movl %edx,%ebp
+ andl $0xff000000,%ebp
+ orl %ebp,%edi
+ pushl %edi
+
+ C // second column
+ C d a b c
+ movl %eax,%edi
+ andl $0x0000ff00,%edi
+ movl %ebx,%ebp
+ andl $0x00ff0000,%ebp
+ orl %ebp,%edi
+ movl %ecx,%ebp
+ andl $0xff000000,%ebp
+ orl %ebp,%edi
+ movl %edx,%ebp
+ andl $0x000000ff,%ebp
+ orl %ebp,%edi
+ pushl %edi
+
+ C c d a b
+ C // third column
+ movl %eax,%edi
+ andl $0x00ff0000,%edi
+ movl %ebx,%ebp
+ andl $0xff000000,%ebp
+ orl %ebp,%edi
+ movl %ecx,%ebp
+ andl $0x000000ff,%ebp
+ orl %ebp,%edi
+ movl %edx,%ebp
+ andl $0x0000ff00,%ebp
+ orl %ebp,%edi
+ pushl %edi
+
+ C // fourth column
+ C b c d a
+ movl %eax,%edi
+ andl $0xff000000,%edi
+ movl %ebx,%ebp
+ andl $0x000000ff,%ebp
+ orl %ebp,%edi
+ movl %ecx,%ebp
+ andl $0x0000ff00,%ebp
+ orl %ebp,%edi
+ movl %edx,%ebp
+ andl $0x00ff0000,%ebp
+ orl %ebp,%edi
+ movl %edi,%edx
+ popl %ecx
+ popl %ebx
+ popl %eax
+ xchgl %ebx,%edx
+
+ C // S-box substitution
+ mov $4,%edi
+.Lsubst:
+ movl %eax,%ebp
+ andl $0x000000ff,%ebp
+ movb AES_SBOX + _aes_encrypt_table (%ebp),%al
+ roll $8,%eax
+
+ movl %ebx,%ebp
+ andl $0x000000ff,%ebp
+ movb AES_SBOX + _aes_encrypt_table (%ebp),%bl
+ roll $8,%ebx
+
+ movl %ecx,%ebp
+ andl $0x000000ff,%ebp
+ movb AES_SBOX + _aes_encrypt_table (%ebp),%cl
+ roll $8,%ecx
+
+ movl %edx,%ebp
+ andl $0x000000ff,%ebp
+ movb AES_SBOX + _aes_encrypt_table (%ebp),%dl
+ roll $8,%edx
+
+ decl %edi
+ jnz .Lsubst
+
+C .Laes_got_tlast:
+ xorl (%esi),%eax C add last key to plaintext
+ xorl 4(%esi),%ebx
+ xorl 8(%esi),%ecx
+ xorl 12(%esi),%edx
+C .Laes_got_result:
+ C // store encrypted data back to caller's buffer
+ movl 28(%esp),%edi
+ movl %eax,(%edi)
+ movl %ebx,4(%edi)
+ movl %ecx,8(%edi)
+ movl %edx,12(%edi)
+
+ addl $16, 28(%esp) C Increment destination pointer
+ subl $16, 24(%esp)
+ jnz .Lencrypt_block_loop
+
+.Lencrypt_end:
+ popl %edi
+ popl %esi
+ popl %ebp
+ popl %ebx
+ ret
+.eore:
+ .size aes_encrypt,.eore-aes_encrypt
include_src(<x86/aes_tables.asm>)
- .text
-
-C Register usage:
-C
-C The aes state is kept in %eax, %ebx, %ecx and %edx
-C
-C %esi is used as temporary, to point to the input, and to the
-C subkeys, etc.
-C
-C %ebp is used as the round counter, and as a temporary in the final round.
-C
-C %edi is a temporary, often used as an accumulator.
-
- C aes_encrypt(struct aes_context *ctx,
- C unsigned length, uint8_t *dst,
- C uint8_t *src)
- .align 16
-.globl aes_encrypt
- .type aes_encrypt,@function
-aes_encrypt:
- C // save all registers that need to be saved
- pushl %ebx C 16(%esp)
- pushl %ebp C 12(%esp)
- pushl %esi C 8(%esp)
- pushl %edi C 4(%esp)
-
- C ctx = 20(%esp)
- C length = 24(%esp)
- C dst = 28(%esp)
- C src = 32(%esp)
-
- movl 24(%esp), %ebp
- C What's the right way to set the flags?
- addl $0, %ebp
- jz .Lencrypt_end
-
-.Lencrypt_block_loop:
- movl 32(%esp),%esi C address of plaintext
- movl (%esi),%eax C load plaintext into registers
- movl 4(%esi),%ebx
- movl 8(%esi),%ecx
- movl 12(%esi),%edx
-
- addl $16, 32(%esp) C Increment src pointer
-C .Laes_got_plain:
- movl 20(%esp),%esi C address of context struct ctx
- xorl (%esi),%eax C add first key to plaintext
- xorl 4(%esi),%ebx
- xorl 8(%esi),%ecx
- xorl 12(%esi),%edx
-C .Laes_xored_initial:
- C FIXME: Use %esi instead
- movl 20(%esp),%ebp C address of context struct
- movl AES_NROUNDS (%ebp),%ebp C get number of rounds to do from struct
-
- subl $1,%ebp
- addl $16,%esi C point to next key
-.Laes_encrypt_loop:
- pushl %esi C save this first: we'll clobber it later
-
- C Computation of the new %eax is broken, in the first test case,
- C first round, we get 0xb3b638c6, not dfd5b20f, just
- C before adding the subkey
-
- C First column, IDXi = 0, 1, 2, 3
- C T[0] = table[0][B0(%eax)]
- C ^ table[1][B1(%ebx)]
- C ^ table[2][B2(%ebx)]
- C ^ table[3][B3(%ebx)]
- C
- C a b c d
- movl %eax, %esi
- andl $0xff, %esi
- shll $2,%esi C index in dtbl1
- C movl dtbl1(%esi),%edi
- movl AES_TABLE0 + _aes_encrypt_table (%esi),%edi
- movl %ebx, %esi
- shrl $6,%esi
- andl $0x000003fc,%esi C clear all but offset bytes
- xorl AES_TABLE1 + _aes_encrypt_table (%esi),%edi
- movl %ecx,%esi C third one
- shrl $14,%esi
- andl $0x000003fc,%esi
- xorl AES_TABLE2 + _aes_encrypt_table (%esi),%edi
- movl %edx,%esi C fourth one
- shrl $22,%esi
- andl $0x000003fc,%esi
- xorl AES_TABLE3 + _aes_encrypt_table (%esi),%edi
- pushl %edi C save first on stack
-
- C // Second column
- C b c d a
- movl %ebx,%esi C copy first in
- andl $0x000000ff,%esi C clear all but offset
- shll $2,%esi C index in dtbl1
- movl dtbl1(%esi),%edi
- movl %ecx,%esi C second one
- shrl $6,%esi
- andl $0x000003fc,%esi C clear all but offset bytes
- xorl dtbl2(%esi),%edi
- movl %edx,%esi C third one
- shrl $14,%esi
- andl $0x000003fc,%esi
- xorl dtbl3(%esi),%edi
- movl %eax,%esi C fourth one
- shrl $22,%esi
- andl $0x000003fc,%esi
- xorl dtbl4(%esi),%edi
- pushl %edi C save first on stack
-
- C // Third column
- C c d a b
- movl %ecx,%esi C copy first in
- andl $0x000000ff,%esi C clear all but offset
- shll $2,%esi C index in dtbl1
- movl dtbl1(%esi),%edi
- movl %edx,%esi C second one
- shrl $6,%esi
- andl $0x000003fc,%esi C clear all but offset bytes
- xorl dtbl2(%esi),%edi
- movl %eax,%esi C third one
- shrl $14,%esi
- andl $0x000003fc,%esi
- xorl dtbl3(%esi),%edi
- movl %ebx,%esi C fourth one
- shrl $22,%esi
- andl $0x000003fc,%esi
- xorl dtbl4(%esi),%edi
- pushl %edi C save first on stack
-
- C // Fourth column
- C d a b c
- movl %edx,%esi C copy first in
- andl $0x000000ff,%esi C clear all but offset
- shll $2,%esi C index in dtbl1
- movl dtbl1(%esi),%edi
- movl %eax,%esi C second one
- shrl $6,%esi
- andl $0x000003fc,%esi C clear all but offset bytes
- xorl dtbl2(%esi),%edi
- movl %ebx,%esi C third one
- shrl $14,%esi
- andl $0x000003fc,%esi
- xorl dtbl3(%esi),%edi
- movl %ecx,%esi C fourth one
- shrl $22,%esi
- andl $0x000003fc,%esi
- xorl dtbl4(%esi),%edi
-
- movl %edi,%edx
- popl %ecx
- popl %ebx
- popl %eax
- popl %esi
-C .Laes_got_t:
- xorl (%esi),%eax C add current session key to plaintext
- xorl 4(%esi),%ebx
- xorl 8(%esi),%ecx
- xorl 12(%esi),%edx
- addl $16,%esi C point to next key
- decl %ebp
- jnz .Laes_encrypt_loop
-
- C // last round
- C // first column
- C a b c d
- movl %eax,%edi
- andl $0x000000ff,%edi
- movl %ebx,%ebp
- andl $0x0000ff00,%ebp
- orl %ebp,%edi
- movl %ecx,%ebp
- andl $0x00ff0000,%ebp
- orl %ebp,%edi
- movl %edx,%ebp
- andl $0xff000000,%ebp
- orl %ebp,%edi
- pushl %edi
-
- C // second column
- C d a b c
- movl %eax,%edi
- andl $0x0000ff00,%edi
- movl %ebx,%ebp
- andl $0x00ff0000,%ebp
- orl %ebp,%edi
- movl %ecx,%ebp
- andl $0xff000000,%ebp
- orl %ebp,%edi
- movl %edx,%ebp
- andl $0x000000ff,%ebp
- orl %ebp,%edi
- pushl %edi
-
- C c d a b
- C // third column
- movl %eax,%edi
- andl $0x00ff0000,%edi
- movl %ebx,%ebp
- andl $0xff000000,%ebp
- orl %ebp,%edi
- movl %ecx,%ebp
- andl $0x000000ff,%ebp
- orl %ebp,%edi
- movl %edx,%ebp
- andl $0x0000ff00,%ebp
- orl %ebp,%edi
- pushl %edi
-
- C // fourth column
- C b c d a
- movl %eax,%edi
- andl $0xff000000,%edi
- movl %ebx,%ebp
- andl $0x000000ff,%ebp
- orl %ebp,%edi
- movl %ecx,%ebp
- andl $0x0000ff00,%ebp
- orl %ebp,%edi
- movl %edx,%ebp
- andl $0x00ff0000,%ebp
- orl %ebp,%edi
- movl %edi,%edx
- popl %ecx
- popl %ebx
- popl %eax
- xchgl %ebx,%edx
-
- C // S-box substitution
- mov $4,%edi
-.Lsubst:
- movl %eax,%ebp
- andl $0x000000ff,%ebp
- movb AES_SBOX + _aes_encrypt_table (%ebp),%al
- roll $8,%eax
-
- movl %ebx,%ebp
- andl $0x000000ff,%ebp
- movb sbox(%ebp),%bl
- roll $8,%ebx
-
- movl %ecx,%ebp
- andl $0x000000ff,%ebp
- movb sbox(%ebp),%cl
- roll $8,%ecx
-
- movl %edx,%ebp
- andl $0x000000ff,%ebp
- movb sbox(%ebp),%dl
- roll $8,%edx
-
- decl %edi
- jnz .Lsubst
-
-C .Laes_got_tlast:
- xorl (%esi),%eax C add last key to plaintext
- xorl 4(%esi),%ebx
- xorl 8(%esi),%ecx
- xorl 12(%esi),%edx
-C .Laes_got_result:
- C // store encrypted data back to caller's buffer
- movl 28(%esp),%edi
- movl %eax,(%edi)
- movl %ebx,4(%edi)
- movl %ecx,8(%edi)
- movl %edx,12(%edi)
-
- addl $16, 28(%esp) C Increment destination pointer
- subl $16, 24(%esp)
- jnz .Lencrypt_block_loop
-
-.Lencrypt_end:
- popl %edi
- popl %esi
- popl %ebp
- popl %ebx
- ret
-.eore:
- .size aes_encrypt,.eore-aes_encrypt
C aes_encrypt(struct aes_context *ctx,