Skip to content

Instantly share code, notes, and snippets.

@Yardanico
Created October 22, 2017 15:43
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Yardanico/df4f82014e4510d568f4cea7dfda7d32 to your computer and use it in GitHub Desktop.
Save Yardanico/df4f82014e4510d568f4cea7dfda7d32 to your computer and use it in GitHub Desktop.
template unpackInt*(s: Stream, format: string): int =
## Unpack one or more bytes into an ``int``.
## The format can be "b", "B" or endiannes
## followed by input type: "<I", ">h", "!H"
##
## .. code-block:: nim
## unpackInt("\x7f\xff", ">h") == 32767
##
## ====== ====================== ====
## symbol endianness size
## ====== ====================== ====
## = native
## < little-endian
## > big-endian
## ! network (big-endian)
## ====== ====================== ====
##
## ====== ====================== ====
## symbol input type size
## ====== ====================== ====
## b char 1
## B unsigned char 1
## h short 2
## H unsigned short 2
## i int 4
## I unsigned int 4
## l long 4
## L unsigned long 4
## ==== ==== ====
##
var result = 0
case format[0]
of 'b':
result = s.readInt8.int
of 'B':
result = s.readUInt8.int
of '=':
case format[1]
of 'h':
result = s.readInt16.int
of 'H':
result = s.readUInt16.int
else:
discard
of '<':
var result: int
case format[1]
of 'h':
var x = s.readInt16
littleEndian16(addr x, addr x)
result = x.int
of 'H':
var x = s.readUInt16
littleEndian16(addr x, addr x)
result = x.int
of 'i', 'l':
var x = s.readInt32
littleEndian32(addr x, addr x)
result = x.int
of 'I', 'L':
var x = s.readUInt32
littleEndian32(addr x, addr x)
result = x.int
else:
raise newException(Exception, "")
of '>', '!':
case format[1]
of 'h':
var x = s.readInt16
bigEndian16(addr x, addr x)
result = x.int
of 'H':
var x = s.readUInt16
bigEndian16(addr x, addr x)
result = x.int
of 'i', 'l':
var x = s.readInt32
bigEndian32(addr x, addr x)
result = x.int
of 'I', 'L':
var x = s.readUInt32
bigEndian32(addr x, addr x)
result = x.int
else:
raise newException(Exception, "")
else:
discard
result
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment