2 * $DragonFly: src/lib/libskey/put.c,v 1.5 2008/09/30 16:57:05 swildner Exp $
11 static unsigned long extract (char *s
,int start
,int length
);
12 static void standard (char *word
);
13 static void insert (char *s
, int x
, int start
, int length
);
14 static int wsrch (char *w
,int low
,int high
);
16 /* Dictionary for integer-word translations */
17 static char Wp
[2048][4] = {
2068 /* Encode 8 bytes in 'c' as a string of English words.
2069 * Returns a pointer to a static buffer
2072 btoe(char *engout
, char *c
)
2074 char cp
[9]; /* add in room for the parity 2 bits*/
2079 /* compute parity */
2080 for(p
= 0,i
= 0; i
< 64;i
+= 2)
2081 p
+= extract(cp
,i
,2);
2083 cp
[8] = (char)p
<< 6;
2084 strncat(engout
,&Wp
[extract(cp
, 0,11)][0],4);
2086 strncat(engout
,&Wp
[extract(cp
,11,11)][0],4);
2088 strncat(engout
,&Wp
[extract(cp
,22,11)][0],4);
2090 strncat(engout
,&Wp
[extract(cp
,33,11)][0],4);
2092 strncat(engout
,&Wp
[extract(cp
,44,11)][0],4);
2094 strncat(engout
,&Wp
[extract(cp
,55,11)][0],4);
2096 printf("engout is %s\n\r",engout
);
2101 /* convert English to binary
2102 * returns 1 OK - all good words and parity is OK
2103 * 0 word not in data base
2104 * -1 badly formed in put ie > 4 char word
2105 * -2 words OK but parity is wrong
2108 etob(char *out
, char *e
)
2111 int i
, v
,l
, low
,high
;
2119 strncpy(input
,e
,sizeof(input
));
2121 memset(b
, 0, sizeof(b
));
2123 for(i
=0,p
=0;i
<6;i
++,p
+=11){
2124 while ((word
= strsep(&cp
, " ")) != NULL
&& *word
== '\0')
2139 if( (v
= wsrch(word
,low
,high
)) < 0 )
2141 insert(b
,v
,(int)p
,11);
2144 /* now check the parity of what we got */
2145 for(p
= 0, i
= 0; i
< 64; i
+=2)
2146 p
+= extract(b
, i
, 2);
2148 if( (p
& 3) != extract(b
, 64,2) )
2155 /* Display 8 bytes as a series of 16-bit hex digits */
2157 put8(char *out
, char *s
)
2159 sprintf(out
,"%02X%02X %02X%02X %02X%02X %02X%02X",
2160 s
[0] & 0xff,s
[1] & 0xff,s
[2] & 0xff,
2161 s
[3] & 0xff,s
[4] & 0xff,s
[5] & 0xff,
2162 s
[6] & 0xff,s
[7] & 0xff);
2166 /* Encode 8 bytes in 'cp' as stream of ascii letters.
2167 * Provided as a possible alternative to btoe()
2173 static char out
[31];
2175 /* code out put by characters 6 bits each added to 0x21 (!)*/
2176 for(i
=0;i
<= 10;i
++){
2177 /* last one is only 4 bits not 6*/
2178 out
[i
] = '!'+ extract(cp
,6*i
,i
>= 10 ? 4:6);
2185 /* Internal subroutines for word encoding/decoding */
2187 /* Dictionary binary search */
2189 wsrch(char *w
, int low
, int high
)
2195 if((j
= strncmp(w
,Wp
[i
],4)) == 0)
2196 return i
; /* Found it */
2198 /* Avoid effects of integer truncation in /2 */
2199 if(strncmp(w
,Wp
[high
],4) == 0)
2205 return -1; /* I don't *think* this can happen...*/
2207 high
= i
; /* Search lower half */
2209 low
= i
; /* Search upper half */
2213 insert(char *s
, int x
, int start
, int length
)
2221 assert(length
<= 11);
2223 assert(length
>= 0);
2224 assert(start
+length
<= 66);
2226 shift
= ((8 -(( start
+ length
) % 8))%8);
2227 y
= (long) x
<< shift
;
2228 cl
= (y
>> 16) & 0xff;
2229 cc
= (y
>> 8) & 0xff;
2231 if(shift
+ length
> 16){
2233 s
[start
/8 +1] |= cc
;
2234 s
[start
/8 +2] |= cr
;
2235 } else if(shift
+length
> 8){
2237 s
[start
/8 + 1] |= cr
;
2244 standard(char *word
)
2250 *word
= toupper(*word
);
2261 /* Extract 'length' bits from the char array 's' starting with bit 'start' */
2262 static unsigned long
2263 extract(char *s
, int start
, int length
)
2270 assert(length
<= 11);
2272 assert(length
>= 0);
2273 assert(start
+length
<= 66);
2278 x
= ((long)(cl
<<8 | cc
) <<8 | cr
) ;
2279 x
= x
>> (24 - (length
+ (start
%8)));
2280 x
=( x
& (0xffff >> (16-length
) ) );