github.com/slspeek/camlistore_namedsearch@v0.0.0-20140519202248-ed6f70f7721a/third_party/code.google.com/p/go.crypto/blowfish/block.go (about)

     1  // Copyright 2010 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package blowfish
     6  
     7  // ExpandKey performs a key expansion on the given *Cipher. Specifically, it
     8  // performs the Blowfish algorithm's key schedule which sets up the *Cipher's
     9  // pi and substitution tables for calls to Encrypt. This is used, primarily,
    10  // by the bcrypt package to reuse the Blowfish key schedule during its
    11  // set up. It's unlikely that you need to use this directly.
    12  func ExpandKey(key []byte, c *Cipher) {
    13  	j := 0
    14  	for i := 0; i < 18; i++ {
    15  		var d uint32
    16  		for k := 0; k < 4; k++ {
    17  			d = d<<8 | uint32(key[j])&0x000000FF
    18  			j++
    19  			if j >= len(key) {
    20  				j = 0
    21  			}
    22  		}
    23  		c.p[i] ^= d
    24  	}
    25  
    26  	var l, r uint32
    27  	for i := 0; i < 18; i += 2 {
    28  		l, r = encryptBlock(l, r, c)
    29  		c.p[i], c.p[i+1] = l, r
    30  	}
    31  
    32  	for i := 0; i < 256; i += 2 {
    33  		l, r = encryptBlock(l, r, c)
    34  		c.s0[i], c.s0[i+1] = l, r
    35  	}
    36  	for i := 0; i < 256; i += 2 {
    37  		l, r = encryptBlock(l, r, c)
    38  		c.s1[i], c.s1[i+1] = l, r
    39  	}
    40  	for i := 0; i < 256; i += 2 {
    41  		l, r = encryptBlock(l, r, c)
    42  		c.s2[i], c.s2[i+1] = l, r
    43  	}
    44  	for i := 0; i < 256; i += 2 {
    45  		l, r = encryptBlock(l, r, c)
    46  		c.s3[i], c.s3[i+1] = l, r
    47  	}
    48  }
    49  
    50  // This is similar to ExpandKey, but folds the salt during the key
    51  // schedule. While ExpandKey is essentially expandKeyWithSalt with an all-zero
    52  // salt passed in, reusing ExpandKey turns out to be a place of inefficiency
    53  // and specializing it here is useful.
    54  func expandKeyWithSalt(key []byte, salt []byte, c *Cipher) {
    55  	j := 0
    56  	expandedKey := make([]uint32, 18)
    57  	for i := 0; i < 18; i++ {
    58  		var d uint32
    59  		for k := 0; k < 4; k++ {
    60  			d = d<<8 | uint32(key[j])&0x000000FF
    61  			j++
    62  			if j >= len(key) {
    63  				j = 0
    64  			}
    65  		}
    66  		expandedKey[i] = d
    67  		c.p[i] ^= d
    68  	}
    69  
    70  	j = 0
    71  	expandedSalt := make([]uint32, 18)
    72  	for i := 0; i < 18; i++ {
    73  		var d uint32
    74  		for k := 0; k < 4; k++ {
    75  			d = d<<8 | uint32(salt[j])&0x000000FF
    76  			j++
    77  			if j >= len(salt) {
    78  				j = 0
    79  			}
    80  		}
    81  		expandedSalt[i] = d
    82  	}
    83  
    84  	var l, r uint32
    85  	for i := 0; i < 18; i += 2 {
    86  		l ^= expandedSalt[i&2]
    87  		r ^= expandedSalt[(i&2)+1]
    88  		l, r = encryptBlock(l, r, c)
    89  		c.p[i], c.p[i+1] = l, r
    90  	}
    91  
    92  	for i := 0; i < 256; i += 4 {
    93  		l ^= expandedSalt[2]
    94  		r ^= expandedSalt[3]
    95  		l, r = encryptBlock(l, r, c)
    96  		c.s0[i], c.s0[i+1] = l, r
    97  
    98  		l ^= expandedSalt[0]
    99  		r ^= expandedSalt[1]
   100  		l, r = encryptBlock(l, r, c)
   101  		c.s0[i+2], c.s0[i+3] = l, r
   102  
   103  	}
   104  
   105  	for i := 0; i < 256; i += 4 {
   106  		l ^= expandedSalt[2]
   107  		r ^= expandedSalt[3]
   108  		l, r = encryptBlock(l, r, c)
   109  		c.s1[i], c.s1[i+1] = l, r
   110  
   111  		l ^= expandedSalt[0]
   112  		r ^= expandedSalt[1]
   113  		l, r = encryptBlock(l, r, c)
   114  		c.s1[i+2], c.s1[i+3] = l, r
   115  	}
   116  
   117  	for i := 0; i < 256; i += 4 {
   118  		l ^= expandedSalt[2]
   119  		r ^= expandedSalt[3]
   120  		l, r = encryptBlock(l, r, c)
   121  		c.s2[i], c.s2[i+1] = l, r
   122  
   123  		l ^= expandedSalt[0]
   124  		r ^= expandedSalt[1]
   125  		l, r = encryptBlock(l, r, c)
   126  		c.s2[i+2], c.s2[i+3] = l, r
   127  	}
   128  
   129  	for i := 0; i < 256; i += 4 {
   130  		l ^= expandedSalt[2]
   131  		r ^= expandedSalt[3]
   132  		l, r = encryptBlock(l, r, c)
   133  		c.s3[i], c.s3[i+1] = l, r
   134  
   135  		l ^= expandedSalt[0]
   136  		r ^= expandedSalt[1]
   137  		l, r = encryptBlock(l, r, c)
   138  		c.s3[i+2], c.s3[i+3] = l, r
   139  	}
   140  }
   141  
   142  func encryptBlock(l, r uint32, c *Cipher) (uint32, uint32) {
   143  	xl, xr := l, r
   144  	xl ^= c.p[0]
   145  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[1]
   146  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[2]
   147  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[3]
   148  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[4]
   149  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[5]
   150  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[6]
   151  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[7]
   152  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[8]
   153  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[9]
   154  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[10]
   155  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[11]
   156  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[12]
   157  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[13]
   158  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[14]
   159  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[15]
   160  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[16]
   161  	xr ^= c.p[17]
   162  	return xr, xl
   163  }
   164  
   165  func decryptBlock(l, r uint32, c *Cipher) (uint32, uint32) {
   166  	xl, xr := l, r
   167  	xl ^= c.p[17]
   168  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[16]
   169  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[15]
   170  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[14]
   171  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[13]
   172  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[12]
   173  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[11]
   174  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[10]
   175  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[9]
   176  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[8]
   177  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[7]
   178  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[6]
   179  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[5]
   180  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[4]
   181  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[3]
   182  	xr ^= ((c.s0[byte(xl>>24)] + c.s1[byte(xl>>16)]) ^ c.s2[byte(xl>>8)]) + c.s3[byte(xl)] ^ c.p[2]
   183  	xl ^= ((c.s0[byte(xr>>24)] + c.s1[byte(xr>>16)]) ^ c.s2[byte(xr>>8)]) + c.s3[byte(xr)] ^ c.p[1]
   184  	xr ^= c.p[0]
   185  	return xr, xl
   186  }
   187  
   188  func zero(x []uint32) {
   189  	for i := range x {
   190  		x[i] = 0
   191  	}
   192  }