[63] | 1 | (*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*) |
---|
| 2 | (* FILENAME: Byte7.ml *) |
---|
| 3 | (* DESCRIPTION: An ADT implementing non-standard 7 bit bytes, and common *) |
---|
| 4 | (* operations on them. *) |
---|
| 5 | (* CREATED: 13/09/2010, Dominic Mulligan *) |
---|
| 6 | (* BUGS: *) |
---|
| 7 | (*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*^*) |
---|
| 8 | |
---|
[84] | 9 | open Bit;; |
---|
| 10 | open Nibble;; |
---|
| 11 | |
---|
[63] | 12 | module type BYTE7 = |
---|
| 13 | sig |
---|
| 14 | type bit |
---|
| 15 | type nibble |
---|
[86] | 16 | type byte7 = private (bit * bit * bit * nibble) |
---|
| 17 | |
---|
| 18 | val get_bit_at: int -> byte7 -> bit option |
---|
| 19 | val set_bit_at: int -> bit -> byte7 -> byte7 option |
---|
| 20 | |
---|
| 21 | val (-&-): byte7 -> byte7 -> byte7 |
---|
| 22 | val (-|-): byte7 -> byte7 -> byte7 |
---|
| 23 | val (-^-): byte7 -> byte7 -> byte7 |
---|
| 24 | val not: byte7 -> byte7 |
---|
| 25 | |
---|
| 26 | val iter_bit: (bit -> string) -> byte7 -> string |
---|
| 27 | val map_bit: (bit -> bit) -> byte7 -> byte7 |
---|
| 28 | val zip_bit: (bit -> bit -> bit) -> byte7 -> byte7 -> byte7 |
---|
| 29 | val to_string: byte7 -> string |
---|
[63] | 30 | end;; |
---|
| 31 | |
---|
[84] | 32 | module Byte7Functor(Bit: BIT) |
---|
| 33 | (Nibble: NIBBLE |
---|
[86] | 34 | with type bit = Bit.bit): BYTE7 |
---|
[63] | 35 | with type bit = Bit.bit |
---|
| 36 | and type nibble = Nibble.nibble = |
---|
| 37 | struct |
---|
| 38 | type bit = Bit.bit |
---|
| 39 | type nibble = Nibble.nibble |
---|
[86] | 40 | type byte7 = bit * bit * bit * nibble |
---|
| 41 | |
---|
| 42 | let get_bit_at index (b1,b2,b3,b) = |
---|
| 43 | if index < 4 then |
---|
| 44 | Nibble.get_bit_at index b |
---|
| 45 | else |
---|
| 46 | match index with |
---|
| 47 | 4 -> Some b3 |
---|
| 48 | | 5 -> Some b2 |
---|
| 49 | | 6 -> Some b1 |
---|
| 50 | | _ -> None |
---|
| 51 | let set_bit_at index new_val (b1,b2,b3,b) = |
---|
| 52 | if index < 4 then |
---|
| 53 | let nib = Nibble.set_bit_at index new_val b in |
---|
| 54 | match nib with |
---|
| 55 | Some nib -> Some (b1, b2, b3, nib) |
---|
| 56 | | None -> None |
---|
| 57 | else |
---|
| 58 | match index with |
---|
| 59 | 4 -> Some (b3, b2, new_val, b) |
---|
| 60 | | 5 -> Some (b3, new_val, b1, b) |
---|
| 61 | | 6 -> Some (new_val, b2, b1, b) |
---|
| 62 | | _ -> None |
---|
| 63 | |
---|
| 64 | let (-&-) (l1, l2, l3, l) (r1, r2, r3, r) = |
---|
| 65 | (Bit.(-&-) l1 r1, Bit.(-&-) l2 r2, Bit.(-&-) l3 r3, Nibble.(-&-) l r) |
---|
| 66 | let (-|-) (l1, l2, l3, l) (r1, r2, r3, r) = |
---|
| 67 | (Bit.(-|-) l1 r1, Bit.(-|-) l2 r2, Bit.(-|-) l3 r3, Nibble.(-|-) l r) |
---|
| 68 | let (-^-) (l1, l2, l3, l) (r1, r2, r3, r) = |
---|
| 69 | (Bit.(-^-) l1 r1, Bit.(-^-) l2 r2, Bit.(-^-) l3 r3, Nibble.(-^-) l r) |
---|
| 70 | let not (b1, b2, b3, b) = (Bit.not b1, Bit.not b2, Bit.not b3, Nibble.not b) |
---|
| 71 | |
---|
| 72 | let iter_bit f (b1, b2, b3, b) = |
---|
| 73 | let n_bits = f b1 ^ f b2 ^ f b3 in |
---|
| 74 | let n_byte = Nibble.iter_bit f b in |
---|
| 75 | n_bits ^ n_byte |
---|
| 76 | let map_bit f (b1, b2, b3, b) = |
---|
| 77 | (f b1, f b2, f b3, Nibble.map_bit f b) |
---|
| 78 | let zip_bit f (l1, l2, l3, l) (r1, r2, r3, r) = |
---|
| 79 | (f l1 r1, f l2 r2, f l3 r3, Nibble.zip_bit f l r) |
---|
| 80 | |
---|
| 81 | let to_string = iter_bit Bit.to_string |
---|
[63] | 82 | end;; |
---|
[84] | 83 | |
---|
| 84 | module Byte7 = Byte7Functor (Bit) (Nibble);; |
---|