[PATCH 10/41] serpent, transform: rework GET_32BIT_MSB_FIRST, PUT_...

Ian Jackson ijackson at chiark.greenend.org.uk
Thu Jul 25 18:40:36 BST 2013


The macros GET_32BIT_MSB_FIRST and PUT_32BIT_MSB_FIRST duplicate
functionality available in unaligned.h, namely get_uint32 and
put_uint32.  Replace all uses outside serpent.c with calls to
get_uint32 and put_uint32.

We are going to make our serpent implementation compile-time
bytesexual, so we do retain a separate implementation of this
functionality in a form which will make that easier.  In particular,
they take arguments for the base and length of the array in
which 32-bit we are making the 32-bit access.

Also, this disentangles serpent.c from secnet.h.  To make serpent.c
easier to reuse, remove the #include of secnet.h (and replace it with
stdint.h, which we do need and were getting via secnet.h).

No functional change.

Signed-off-by: Ian Jackson <ijackson at chiark.greenend.org.uk>
---
 secnet.h    |   15 ---------------
 serpent.c   |   58 +++++++++++++++++++++++++++++++++++++++-------------------
 transform.c |   14 +++++++-------
 3 files changed, 46 insertions(+), 41 deletions(-)

diff --git a/secnet.h b/secnet.h
index 6ac64e3..037ef80 100644
--- a/secnet.h
+++ b/secnet.h
@@ -12,21 +12,6 @@
 #include <sys/time.h>
 #include <netinet/in.h>
 
-/*
- * Macros added by SGT for endianness-independence
- */
-#define GET_32BIT_MSB_FIRST(cp) \
-  (((unsigned long)(unsigned char)(cp)[0] << 24) | \
-  ((unsigned long)(unsigned char)(cp)[1] << 16) | \
-  ((unsigned long)(unsigned char)(cp)[2] << 8) | \
-  ((unsigned long)(unsigned char)(cp)[3]))
-
-#define PUT_32BIT_MSB_FIRST(cp, value) ( \
-  (cp)[0] = (char)((value) >> 24), \
-  (cp)[1] = (char)((value) >> 16), \
-  (cp)[2] = (char)((value) >> 8), \
-  (cp)[3] = (char)(value) )
-
 typedef char *string_t;
 typedef const char *cstring_t;
 typedef enum {False,True} bool_t;
diff --git a/serpent.c b/serpent.c
index 34ef6aa..3847437 100644
--- a/serpent.c
+++ b/serpent.c
@@ -20,11 +20,31 @@
  *
  */
 
-#include "secnet.h"
+#include <stdint.h>
 
 #include "serpent.h"
 #include "serpentsboxes.h"
 
+#define GETPUT_CP(bytenum) \
+    (((basep) + (lenbytes) - (offset) - 4)[(bytenum)])
+
+static uint32_t serpent_get_32bit(const uint8_t *basep,
+				  int lenbytes, int offset)
+{
+    return (((uint32_t)GETPUT_CP(0) << 24) |
+	    ((uint32_t)GETPUT_CP(1) << 16) |
+	    ((uint32_t)GETPUT_CP(2) << +8) |
+	    ((uint32_t)GETPUT_CP(3)));
+}
+
+static void serpent_put_32bit(uint8_t *basep, int lenbytes, int offset, uint32_t value)
+{
+    GETPUT_CP(0) = (char)((value) >> 24);
+    GETPUT_CP(1) = (char)((value) >> 16);
+    GETPUT_CP(2) = (char)((value) >> 8);
+    GETPUT_CP(3) = (char)(value);
+}
+
 void serpent_makekey(struct keyInstance *key, int keyLen,
 	    const uint8_t *keyMaterial)
 {
@@ -33,9 +53,9 @@ void serpent_makekey(struct keyInstance *key, int keyLen,
     uint32_t w[132],k[132];
 
     for(i=0; i<keyLen/32; i++)
-	w[i]=GET_32BIT_MSB_FIRST(keyMaterial + (keyLen/8 - i*4) - 4);
+	w[i]=serpent_get_32bit(keyMaterial, keyLen/8, i*4);
     if(keyLen<256)
-	w[i]=(GET_32BIT_MSB_FIRST(keyMaterial + (keyLen/8 - i*4) - 4)
+	w[i]=(serpent_get_32bit(keyMaterial, keyLen/8, i*4)
               & ((1L<<((keyLen&31)))-1)) | (1L<<((keyLen&31)));
     for(i++; i<8; i++)
 	w[i]=0;
@@ -92,10 +112,10 @@ void serpent_encrypt(struct keyInstance *key,
     register uint32_t x0, x1, x2, x3;
     register uint32_t y0, y1, y2, y3;
 
-    x0=GET_32BIT_MSB_FIRST(plaintext+12);
-    x1=GET_32BIT_MSB_FIRST(plaintext+8);
-    x2=GET_32BIT_MSB_FIRST(plaintext+4);
-    x3=GET_32BIT_MSB_FIRST(plaintext);
+    x0=serpent_get_32bit(plaintext,16,+0);
+    x1=serpent_get_32bit(plaintext,16,+4);
+    x2=serpent_get_32bit(plaintext,16,+8);
+    x3=serpent_get_32bit(plaintext,16,12);
 
     /* Start to encrypt the plaintext x */
     keying(x0, x1, x2, x3, key->subkeys[ 0]);
@@ -197,10 +217,10 @@ void serpent_encrypt(struct keyInstance *key,
     keying(x0, x1, x2, x3, key->subkeys[32]);
     /* The ciphertext is now in x */
 
-    PUT_32BIT_MSB_FIRST(ciphertext+12, x0);
-    PUT_32BIT_MSB_FIRST(ciphertext+8, x1);
-    PUT_32BIT_MSB_FIRST(ciphertext+4, x2);
-    PUT_32BIT_MSB_FIRST(ciphertext, x3);
+    serpent_put_32bit(ciphertext,16,+0, x0);
+    serpent_put_32bit(ciphertext,16,+4, x1);
+    serpent_put_32bit(ciphertext,16,+8, x2);
+    serpent_put_32bit(ciphertext,16,12, x3);
 }
 
 void serpent_decrypt(struct keyInstance *key,
@@ -210,10 +230,10 @@ void serpent_decrypt(struct keyInstance *key,
     register uint32_t x0, x1, x2, x3;
     register uint32_t y0, y1, y2, y3;
 
-    x0=GET_32BIT_MSB_FIRST(ciphertext+12);
-    x1=GET_32BIT_MSB_FIRST(ciphertext+8);
-    x2=GET_32BIT_MSB_FIRST(ciphertext+4);
-    x3=GET_32BIT_MSB_FIRST(ciphertext);
+    x0=serpent_get_32bit(ciphertext,16,+0);
+    x1=serpent_get_32bit(ciphertext,16,+4);
+    x2=serpent_get_32bit(ciphertext,16,+8);
+    x3=serpent_get_32bit(ciphertext,16,12);
 
     /* Start to decrypt the ciphertext x */
     keying(x0, x1, x2, x3, key->subkeys[32]);
@@ -315,8 +335,8 @@ void serpent_decrypt(struct keyInstance *key,
     keying(x0, x1, x2, x3, key->subkeys[ 0]);
     /* The plaintext is now in x */
 
-    PUT_32BIT_MSB_FIRST(plaintext+12, x0);
-    PUT_32BIT_MSB_FIRST(plaintext+8, x1);
-    PUT_32BIT_MSB_FIRST(plaintext+4, x2);
-    PUT_32BIT_MSB_FIRST(plaintext, x3);
+    serpent_put_32bit(plaintext,16,+0, x0);
+    serpent_put_32bit(plaintext,16,+4, x1);
+    serpent_put_32bit(plaintext,16,+8, x2);
+    serpent_put_32bit(plaintext,16,12, x3);
 }
diff --git a/transform.c b/transform.c
index 6618ec5..08ddad6 100644
--- a/transform.c
+++ b/transform.c
@@ -59,9 +59,9 @@ static bool_t transform_setkey(void *sst, uint8_t *key, int32_t keylen)
 
     serpent_makekey(&ti->cryptkey,256,key);
     serpent_makekey(&ti->mackey,256,key+32);
-    ti->cryptiv=GET_32BIT_MSB_FIRST(key+64);
-    ti->maciv=GET_32BIT_MSB_FIRST(key+68);
-    ti->sendseq=GET_32BIT_MSB_FIRST(key+72);
+    ti->cryptiv=get_uint32(key+64);
+    ti->maciv=get_uint32(key+68);
+    ti->sendseq=get_uint32(key+72);
     ti->lastrecvseq=ti->sendseq;
     ti->keyed=True;
 
@@ -121,7 +121,7 @@ static uint32_t transform_forward(void *sst, struct buffer_if *buf,
        it we've have to add 16 bytes to each message, not 4, so that the
        message stays a multiple of 16 bytes long.) */
     memset(iv,0,16);
-    PUT_32BIT_MSB_FIRST(iv, ti->maciv);
+    put_uint32(iv, ti->maciv);
     serpent_encrypt(&ti->mackey,iv,macacc);
 
     /* CBCMAC: encrypt in CBC mode. The MAC is the last encrypted
@@ -138,7 +138,7 @@ static uint32_t transform_forward(void *sst, struct buffer_if *buf,
     /* Serpent-CBC. We expand the ID as for CBCMAC, do the encryption,
        and prepend the IV before increasing it. */
     memset(iv,0,16);
-    PUT_32BIT_MSB_FIRST(iv, ti->cryptiv);
+    put_uint32(iv, ti->cryptiv);
     serpent_encrypt(&ti->cryptkey,iv,iv);
 
     /* CBC: each block is XORed with the previous encrypted block (or the IV)
@@ -187,7 +187,7 @@ static uint32_t transform_reverse(void *sst, struct buffer_if *buf,
     memset(iv,0,16);
     {
 	uint32_t ivword = buf_unprepend_uint32(buf);
-	PUT_32BIT_MSB_FIRST(iv, ivword);
+	put_uint32(iv, ivword);
     }
     /* Assert bufsize is multiple of blocksize */
     if (buf->size&0xf) {
@@ -208,7 +208,7 @@ static uint32_t transform_reverse(void *sst, struct buffer_if *buf,
     /* CBCMAC */
     macexpected=buf_unappend(buf,16);
     memset(iv,0,16);
-    PUT_32BIT_MSB_FIRST(iv, ti->maciv);
+    put_uint32(iv, ti->maciv);
     serpent_encrypt(&ti->mackey,iv,macacc);
 
     /* CBCMAC: encrypt in CBC mode. The MAC is the last encrypted
-- 
1.7.2.5




More information about the sgo-software-discuss mailing list