diff options
Diffstat (limited to 'src/utils/ByteUtils.scala')
-rw-r--r-- | src/utils/ByteUtils.scala | 56 |
1 files changed, 11 insertions, 45 deletions
diff --git a/src/utils/ByteUtils.scala b/src/utils/ByteUtils.scala index 85c6058..ffc2e20 100644 --- a/src/utils/ByteUtils.scala +++ b/src/utils/ByteUtils.scala @@ -1,5 +1,7 @@ package ixee.cryptopals.utils +import ConversionUtils.tup + object ByteUtils { trait SizedNumeric[T] { def manifest: Manifest[T] @@ -17,6 +19,7 @@ object ByteUtils { def @<<(t: T, x: Int): T def @|(a: T, b: T): T def @&(a: T, b: T): T + def @^(a: T, b: T): T def @+(a: T, b: T): T } @@ -25,6 +28,7 @@ object ByteUtils { def @<<(t: Byte, x: Int): Byte = (t << x).toByte def @|(a: Byte, b: Byte): Byte = (a | b).toByte def @&(a: Byte, b: Byte): Byte = (a & b).toByte + def @^(a: Byte, b: Byte): Byte = (a ^ b).toByte def @+(a: Byte, b: Byte): Byte = (a + b).toByte } @@ -33,6 +37,7 @@ object ByteUtils { def @<<(t: Int, x: Int): Int = (t << x) def @|(a: Int, b: Int): Int = a | b def @&(a: Int, b: Int): Int = a & b + def @^(a: Int, b: Int): Int = a ^ b def @+(a: Int, b: Int): Int = a + b } @@ -41,11 +46,13 @@ object ByteUtils { def @<<(b: Int): T = implicitly[BitOps[T]].@<<(x, b) def @|(b: T): T = implicitly[BitOps[T]].@|(x, b) def @&(b: T): T = implicitly[BitOps[T]].@&(x, b) + def @^(b: T): T = implicitly[BitOps[T]].@^(x, b) def @+(b: T): T = implicitly[BitOps[T]].@+(x, b) } implicit class SizedWithByteInfo[T : SizedNumeric](x: T) { def byteSize = implicitly[SizedNumeric[T]].byteSize + def octetSize = byteSize * 2 def bitSize = implicitly[SizedNumeric[T]].bitSize def toLong = implicitly[SizedNumeric[T]].toLong(x) def liftedTo[U : SizedNumeric]: U = { @@ -57,36 +64,12 @@ object ByteUtils { uSize.buildFrom(x) } + def hex: String = s"%0${octetSize}x" format x def truncatedTo[U : SizedNumeric]: U = { implicitly[SizedNumeric[U]].truncate(x) } } - implicit class RichIterableByte(iter: Iterable[Byte]) { - def to[T : SizedNumeric : BitOps]: T = { - // Need to know length, so we must force the iter - iter.hasDefiniteSize match { - case true => throw new IllegalArgumentException("Argument is not finite!") - case false => { - val numeric = implicitly[SizedNumeric[T]] - if(b.length < numeric.byteSize) { - throw new RuntimeException("Byte input is not long enough") - } - - var out: Long = b(0) - for(i <- 1 until numeric.byteSize) { - out << 8 - out = b(i) | out - } - numeric.fromLong(out) - } - } - } - - def xor(other: Iterable[Byte]): Iterable[Byte] = - iter.zip(other).map(_ ^@ _) - - } def sizedNumeric[T : Manifest](bytes: Int)(from: Long => T)(to: T => Long) = new SizedNumeric[T] { def manifest = implicitly[Manifest[T]] def byteSize = bytes @@ -99,25 +82,8 @@ object ByteUtils { implicit val shortized = sizedNumeric(2) { x: Long => x.toShort } { _.toLong } implicit val byteSized = sizedNumeric(1) { x: Long => x.toByte } { _.toLong } - def toArrayBuf[T : SizedNumeric : BitOps](x: T): Array[Byte] = { - val buf = new Array[Byte](x.byteSize) - for(i <- 0 until x.byteSize) { - val shiftAmount: Int = (x.byteSize - i - 1) << 3 - buf(i) = (x @>>> shiftAmount).truncatedTo[Byte] - } - buf - } - - def toBinaryString[T : SizedNumeric](x: T)(implicit a: BitOps[T]): String = { - val buf = new StringBuilder(x.bitSize) - for(i <- 0 until x.bitSize) { - val shiftAmount: Int = x.bitSize - i - 1 - buf.append((x @>>> shiftAmount) @& 0x01.liftedTo[T]) - } - buf.toString() - } - - def toHexString[T : SizedNumeric : BitOps](x: Iterable[T]): String = { - + implicit class SeqByteOps(seq: Seq[Byte]) { + def xor(other: Seq[Byte]): Seq[Byte] = + seq.zip(other).map(tup(_ @^ _)) } } |