3 This file is part of the AVR-Crypto-Lib.
4 Copyright (C) 2008 Daniel Otte (daniel.otte@rub.de)
6 This program is free software: you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation, either version 3 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program. If not, see <http://www.gnu.org/licenses/>.
21 * a implementation of the PRESENT block-cipher
23 * email: daniel.otte@rub.de
30 #include <avr/pgmspace.h>
32 #include "present_common.h"
33 #include "present80.h"
36 void key_update(uint8_t* buffer, uint8_t round){
38 union __attribute__((packed)){
42 /* rotate buffer 19 right */
43 tmp.v16 = ((uint16_t*)buffer)[4];
46 ((uint16_t*)buffer)[j] = ((uint16_t*)buffer)[j-1];
48 ((uint16_t*)buffer)[0] = tmp.v16;
51 t8 = (uint16_t)buffer[9] << (5);
53 tmp.v8[1] = buffer[j];
55 buffer[j] = tmp.v8[1] | t8;
56 t8 = tmp.v8[0] & 0xe0;
58 /* rotating done now substitution */
59 buffer[0] = (present_sbox(buffer[0])&0xF0) | ((buffer[0])&0x0F);
60 /* xor with round counter */
61 buffer[8] ^= round << 7;
62 buffer[7] ^= round >> 1;
66 void key_update_inv(uint8_t* buffer, uint8_t round){
68 union __attribute__((packed)){
72 /* xor with round counter */
73 buffer[8] ^= round << 7;
74 buffer[7] ^= round >> 1;
75 /* rotating done now substitution */
76 buffer[0] = (present_sbox_inv(buffer[0])&0xF0) | ((buffer[0])&0x0F);
77 /* rotate buffer 19 left */
78 tmp.v16 = ((uint16_t*)buffer)[0];
81 ((uint16_t*)buffer)[j] = ((uint16_t*)buffer)[j+1];
83 ((uint16_t*)buffer)[4] = tmp.v16;
86 t8 = (uint16_t)buffer[0] >> (5);
88 tmp.v8[0] = buffer[j];
90 buffer[j] = tmp.v8[0] | t8;
91 t8 = tmp.v8[1] & 0x07;
95 void present80_init(const uint8_t* key, uint8_t keysize_b, present80_ctx_t* ctx){
97 memcpy(ctx->fwd_key, key, 10);
98 memcpy(ctx->rev_key, key, 10);
100 key_update(ctx->rev_key, i);
104 void present80_enc(void* buffer, present80_ctx_t* ctx){
105 present_generic_enc(buffer, (uint8_t*)ctx, 10, key_update);
108 void present80_dec(void* buffer, present80_ctx_t* ctx){
109 present_generic_dec(buffer, (uint8_t*)ctx, 10, key_update_inv);
113 void present80_enc(void* buffer, present80_ctx_t* ctx){
114 uint8_t i,j,tmp[8], k[10];
115 memcpy(k, ctx->fwd_key, 10);
116 memxor(buffer, k, 8);
120 tmp[j] = present_sbox(((uint8_t*)buffer)[j]);
122 present_p(buffer, tmp);
124 memxor(buffer, k, 8);
128 void present80_dec(void* buffer, present80_ctx_t* ctx){
129 uint8_t j,tmp[8], k[10];
131 memcpy(k, ctx->rev_key, 10);
132 memxor(buffer, k, 8);
135 present_p(tmp, buffer);
136 present_p(buffer, tmp);
139 ((uint8_t*)buffer)[j] = sbox_inv(((uint8_t*)buffer)[j]);
141 key_update_inv(k, i);
142 memxor(buffer, k, 8);