crackNum: Crack various integer and floating-point data formats

[ bsd3, program, tools ] [ Propose Tags ] [ Report a vulnerability ]

Crack IEEE-754 and other float formats and arbitrary sized words and integers, showing the layout.

For details, please see: http://github.com/LeventErkok/crackNum/


[Skip to Readme]

Downloads

Maintainer's Corner

Package maintainers

For package maintainers and hackage trustees

Candidates

  • No Candidates
Versions [RSS] 1.0, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0, 2.1, 2.2, 2.3, 2.4, 3.0, 3.1, 3.2, 3.3, 3.4, 3.5, 3.6, 3.7, 3.8, 3.9, 3.10, 3.11, 3.12, 3.13, 3.14, 3.15, 3.16, 3.17, 3.18, 3.19, 3.20, 3.21, 3.22, 3.23, 3.24, 3.25, 3.26, 3.27, 3.28, 3.29, 3.30, 3.31, 4.0, 4.1, 4.2 (info)
Change log CHANGES.md
Dependencies base (>=4.11 && <5), deepseq, directory, filepath, ghc, libBF, process, sbv (>=11.0), tasty, tasty-golden [details]
License BSD-3-Clause
Copyright Levent Erkok
Author Levent Erkok
Maintainer erkokl@gmail.com
Uploaded by LeventErkok at 2026-08-18T23:12:55Z
Category Tools
Home page http://github.com/LeventErkok/CrackNum
Source repo head: git clone https://github.com/LeventErkok/crackNum.git
Distributions Arch:3.6, LTSHaskell:3.15, Stackage:4.2
Reverse Dependencies 2 direct, 35 indirect [details]
Executables crackNum
Downloads 18686 total (92 in the last 30 days)
Rating 2.0 (votes: 1) [estimated by Bayesian average]
Your Rating
  • λ
  • λ
  • λ
Status Docs not available [build log]
Last success reported on 2026-08-19 [all 1 reports]

Readme for crackNum-3.25

[back to package description]

Decode/Encode Integers, Words, and IEEE754 and other float formats

On Hackage: http://hackage.haskell.org/package/crackNum

crackNum shows you exactly how a number is laid out in memory: the bit pattern, its fields, the classification, and the value in binary, octal, decimal, and hex. It works in both directions:

  • Encoding: give it a value (2.5, -2.3e6, NaN, 0x3.2p5), and it shows the bit-pattern it turns into, together with the rounding that took place.
  • Decoding: give it a bit-pattern (0xdeadbeef, 0b0110, 32'hfdc71fc6), and it shows the value it stands for.

Installation

$ cabal install crackNum

crackNum uses SBV and delegates the actual floating-point reasoning to an SMT solver, so you also need z3 on your PATH.

Supported formats

Flag Format Exponent Significand (incl. implicit bit)
-fhp Half precision (IEEE-754 binary16) 5 11
-fbp Brain float (bfloat16) 8 8
-ftf32 TensorFloat-32 8 11
-fsp Single precision (binary32) 8 24
-fdp Double precision (binary64) 11 53
-fqp Quad precision (binary128) 15 113
-fe5m2 FP8, IEEE-754 style 5 3
-fe4m3 FP8, alternate (no infinities) 4 4
-ffp4 FP4 (E2M1) 2 2
-ffp4e0m3 FP4 (E0M3), sign-magnitude 0 3
-fa+b Arbitrary IEEE-754 float a b

FP4 (E0M3) is the odd one out: with no exponent bits at all it is really a 4-bit sign-magnitude integer, holding a sign and a 3-bit magnitude. It covers -7 to 7, with both a positive and a negative zero, and has neither NaN nor Inf.

Integers come in two flavors: -iN for a signed N-bit 2's complement integer, and -wN for an unsigned N-bit word. Both N and the arbitrary float sizes can be as large as you like, within machine-word limits.

Note that TF32 is cracked as its 19 architectural bits; hardware typically carries these in a 32-bit container with the remaining bits unused.

Rounding mode is selected with -r, and defaults to RNE if not given: RNE (nearest, ties to even), RNA (nearest, ties away), RTP (towards positive infinity), RTN (towards negative infinity), and RTZ (towards zero).

Example: Encode a decimal number as a single-precision IEEE754 number

$ crackNum -fsp -- -2.3e6
Satisfiable. Model:
  ENCODED = -2300000.0 :: Float
                  3  2          1         0
                  1 09876543 21098765432109876543210
                  S ---E8--- ----------S23----------
   Binary layout: 1 10010100 00011000110000110000000
      Hex layout: CA0C 6180
       Precision: Single
            Sign: Negative
        Exponent: 21 (Stored: 148, Bias: 127)
  Classification: FP_NORMAL
          Binary: -0b1.0001100011000011p+21
           Octal: -0o1.061414p+21
         Decimal: -2300000.0
             Hex: -0x2.3186p+20
   Rounding mode: RNE: Round nearest ties to even.
            Note: Conversion from "-2.3e6" was exact. No rounding happened.

Example: Encode with a different rounding mode

$ crackNum -fsp 1.3 -rRTZ
Satisfiable. Model:
  ENCODED = 1.3 :: Float
                  3  2          1         0
                  1 09876543 21098765432109876543210
                  S ---E8--- ----------S23----------
   Binary layout: 0 01111111 01001100110011001100110
      Hex layout: 3FA6 6666
       Precision: Single
            Sign: Positive
        Exponent: 0 (Stored: 127, Bias: 127)
  Classification: FP_NORMAL
          Binary: 0b1.0100110011001100110011
           Octal: 0o1.23146314
         Decimal: 1.3
             Hex: 0x1.4ccccc
   Rounding mode: RTZ: Round towards zero.
            Note: Conversion from "1.3" was not faithful. Status: Inexact.

Example: Decode a single-precision IEEE754 number float from memory-layout

$ crackNum -fsp  0xfc00 abc1
Satisfiable. Model:
  DECODED = -2.6723903e36 :: Float
                  3  2          1         0
                  1 09876543 21098765432109876543210
                  S ---E8--- ----------S23----------
   Binary layout: 1 11111000 00000001010101111000001
      Hex layout: FC00 ABC1
       Precision: Single
            Sign: Negative
        Exponent: 121 (Stored: 248, Bias: 127)
  Classification: FP_NORMAL
          Binary: -0b1.00000001010101111000001p+121
           Octal: -0o2.00527404p+120
         Decimal: -2.6723903e36
             Hex: -0x2.02af04p+120

Example: Encode as an E4M3 FP8 float

$ crackNum -fe4m3 2.5
Satisfiable. Model:
  ENCODED = 2.5 :: E4M3
                  7 6543 210
                  S -E4- S3-
   Binary layout: 0 1000 010
      Hex layout: 42
       Precision: 4 exponent bits, 3 significand bits
            Sign: Positive
        Exponent: 1 (Stored: 8, Bias: 7)
  Classification: FP_NORMAL
          Binary: 0b1.01p1
           Octal: 0o2.4
         Decimal: 2.5
             Hex: 0x2.8

Example: Decode an FP4 (E2M1) float

$ crackNum -ffp4 0b0111
Satisfiable. Model:
  DECODED = 6.0 :: FP4
                  3 21 0
                  S E2 S
   Binary layout: 0 11 1
      Hex layout: 7
       Precision: 2 exponent bits, 1 significand bit
            Sign: Positive
        Exponent: 2 (Stored: 3, Bias: 1)
  Classification: FP_NORMAL
          Binary: 0b1.1p+2
           Octal: 0o6
         Decimal: 6.0
             Hex: 0x6

Example: Decode an FP4 (E0M3) sign-magnitude integer

$ crackNum -ffp4e0m3 0b1101
Satisfiable. Model:
  DECODED = -5 :: FP4E0M3
                  3 210
                  S -M-
   Binary layout: 1 101
      Hex layout: D
            Type: 4-bit sign-magnitude integer
            Sign: Negative
          Binary: -0b101
           Octal: -0o5
         Decimal: -5
             Hex: -0x5

Example: Encode an FP4 (E0M3) sign-magnitude integer

$ crackNum -ffp4e0m3 -- -5
Satisfiable. Model:
  ENCODED = -5 :: FP4E0M3
                  3 210
                  S -M-
   Binary layout: 1 101
      Hex layout: D
            Type: 4-bit sign-magnitude integer
            Sign: Negative
          Binary: -0b101
           Octal: -0o5
         Decimal: -5
             Hex: -0x5
   Rounding mode: RNE: Round nearest ties to even.
            Note: Conversion from "-5" was exact. No rounding happened.

Example: Encode a TensorFloat-32 number

$ crackNum -ftf32 2.5
Satisfiable. Model:
  ENCODED = 2.5 :: FloatingPoint 8 11
                  1          0
                  8 76543210 9876543210
                  S ---E8--- ---S10----
   Binary layout: 0 10000000 0100000000
      Hex layout: 2 0100
       Precision: 8 exponent bits, 10 significand bits
            Sign: Positive
        Exponent: 1 (Stored: 128, Bias: 127)
  Classification: FP_NORMAL
          Binary: 0b1.01p1
           Octal: 0o2.4
         Decimal: 2.5
             Hex: 0x2.8
   Rounding mode: RNE: Round nearest ties to even.
            Note: Conversion from "2.5" was exact. No rounding happened.

Example: Decode a custom (2+3) float from memory-layout

$ crackNum -f2+3 0b10011
Satisfiable. Model:
  DECODED = -0.75 :: FloatingPoint 2 3
                  4 32 10
                  S E2 S2
   Binary layout: 1 00 11
      Hex layout: 13
       Precision: 2 exponent bits, 2 significand bits
            Sign: Negative
        Exponent: 0 (Subnormal, with fixed exponent value. Stored: 0, Bias: 1)
  Classification: FP_SUBNORMAL
          Binary: -0b1.1p-1
           Octal: -0o6p-3
         Decimal: -0.75
             Hex: -0xcp-4

Example: Encode an integer as a 7-bit signed word

$ crackNum -i7 12
Satisfiable. Model:
  ENCODED = 12 :: IntN 7
                  654 3210
   Binary layout: 000 1100
      Hex layout: 0C
            Type: Signed 7-bit 2's complement integer
            Sign: Positive
          Binary: 0b1100
           Octal: 0o14
         Decimal: 12
             Hex: 0xc

Example: Decode a 4-bit unsigned word

$ crackNum -w4 0xE
Satisfiable. Model:
  DECODED = 14 :: WordN 4
                  3210
   Binary layout: 1110
      Hex layout: E
            Type: Unsigned 4-bit word
          Binary: 0b1110
           Octal: 0o16
         Decimal: 14
             Hex: 0xe

Example: Decode two half-precision floats in two lanes

$ crackNum -l2 -fhp 32\'hfdc71fc6
== Lane 1 ============================================================
Satisfiable. Model:
  DECODED = NaN :: FloatingPoint 5 11
                  1       0
                  5 43210 9876543210
                  S -E5-- ---S10----
   Binary layout: 1 11111 0111000111
      Hex layout: FDC7
       Precision: Half (5 exponent bits, 10 significand bits.)
            Sign: Negative
        Exponent: 16 (Stored: 31, Bias: 15)
  Classification: FP_NAN (Signaling)
           Value: NaN
            Note: Representation for NaN's is not unique
== Lane 0 ============================================================
Satisfiable. Model:
  DECODED = 0.0075912476 :: FloatingPoint 5 11
                  1       0
                  5 43210 9876543210
                  S -E5-- ---S10----
   Binary layout: 0 00111 1111000110
      Hex layout: 1FC6
       Precision: Half (5 exponent bits, 10 significand bits.)
            Sign: Positive
        Exponent: -8 (Stored: 7, Bias: 15)
  Classification: FP_NORMAL
          Binary: 0b1.111100011p-8
           Octal: 0o3.706p-9
         Decimal: 0.0075912476
             Hex: 0x1.f18p-8

If you use the verilog notation (N'h...), the number of lanes is inferred from the width, so -l is optional in that case.

Graphical interface (optional)

Optionally, crackNum comes with a GUI: pick a format on the left, type a value, and see the encoding/decoding in detail. It is entirely optional — crackNum is fully functional as a command-line tool without it. The GUI is just a thin front-end that calls the crackNum binary underneath, so it supports exactly the same formats.

crackNum GUI

macOS — a native Swift/AppKit app (GUI/swiftGUI/). It is not part of the Hackage package, so you need a clone of the repository to build it. You also need the Swift compiler that comes with the Xcode Command Line Tools (xcode-select --install):

$ git clone https://github.com/LeventErkok/crackNum.git
$ cd crackNum/GUI/swiftGUI
$ make install      # builds CrackNum.app and copies it into /Applications

Linux — a Tcl/Tk script (GUI/tclGUI/crackNum.tcl). The script ships with the package and is installed alongside the binary, so there is nothing to build; you only need wish (Tk 8.6+):

$ nix profile install nixpkgs#tk   # or: sudo apt install tk / sudo dnf install tk

Then crackNum --gui just works. If you want to run a modified copy of the script, either put it on your PATH as crackNum.tcl, or point at it directly with CRACKNUM_TCL=/path/to/crackNum.tcl.

On both platforms, launch the GUI from the command line via the --gui option, which forwards any format/rounding flags and value to the app:

$ crackNum --gui                 -- open the graphical interface
$ crackNum --gui -fsp 2.5        -- open it with single-precision selected, and 2.5 cracked
$ crackNum --gui 0xdeadbeef      -- open it pre-filled with a value to decode

Bad flags are diagnosed before the GUI comes up: crackNum -ft32 4 --gui reports the unknown format instead of opening an empty window.

Usage info

Usage: crackNum value OR binary/hex-pattern
  -i N                 Signed   integer of N-bits
  -w N                 Unsigned integer of N-bits
  -f fp                Floating point format fp
  -r rm                Rounding mode to use. If not given, Nearest-ties-to-Even.
  -l lanes             Number of lanes to decode
  -h, -?    --help     print help, with examples
  -v        --version  print version info
  -d        --debug    debug mode, developers only
            --gui      launch the graphical interface

Examples:
 Encoding:
   crackNum -i4       -- -2                    -- encode as 4-bit signed integer
   crackNum -w4       2                        -- encode as 4-bit unsigned integer
   crackNum -f3+4     2.5                      -- encode as float with 3 bits exponent, 4 bits significand
   crackNum -f3+4     2.5 -rRTZ                -- encode as above, but use RTZ rounding mode.
   crackNum -fbp      2.5                      -- encode as a brain-precision float
   crackNum -ftf32    2.5                      -- encode as a TensorFloat-32 float
   crackNum -fdp      2.5                      -- encode as a double-precision float
   crackNum -fqp      2.5                      -- encode as a quad-precision float
   crackNum -fe4m3    2.5                      -- encode as an E4M3 FP8 float
   crackNum -fe5m2    2.5                      -- encode as an E5M2 FP8 float
   crackNum -ffp4     2.5                      -- encode as an FP4 (E2M1) float
   crackNum -ffp4e0m3 3.5                      -- encode as an FP4 (E0M3) sign-magnitude integer
   crackNum -fsp      0x3.2p5                  -- encode as single-precision from hex-float

 Decoding:
   crackNum -i4       0b0110                   -- decode as 4-bit signed integer, from binary
   crackNum -w4       0xE                      -- decode as 4-bit unsigned integer, from hex
   crackNum -f3+4     0b0111001                -- decode as float with 3 bits exponent, 4 bits significand
   crackNum -fbp      0x000F                   -- decode as a brain-precision float
   crackNum -ftf32    19\'h0000F               -- decode as a TensorFloat-32 float
   crackNum -fdp      0x8000000000000000       -- decode as a double-precision float
   crackNum -fhp      0x8000                   -- decode as a half-precision float
   crackNum -ffp4     0b0111                   -- decode as an FP4 (E2M1) float
   crackNum -ffp4e0m3 0b1101                   -- decode as an FP4 (E0M3) sign-magnitude integer
   crackNum -l4 -fhp  64\'hbdffaaffdc71fc60    -- decode as half-precision float over 4 lanes using verilog notation

 GUI:
   crackNum --gui                     -- launch the graphical interface
   crackNum --gui 0xdeadbeef          -- launch the GUI, pre-filled with the given value

 Notes:
   - For encoding:
       - Use -- to separate your argument if it's a negative number.
       - For floats: You can pass in NaN, Inf, -0, -Inf etc as the argument
                     along with a decimal (2.3, -4.1e5) or hexadecimal float (0x2.4p3)
       - FP4 (E2M1) has neither NaN nor Inf, so those inputs are rejected. Finite
         values outside its range of [-6, 6] saturate to the nearest end-point.
       - FP4 (E0M3) is a sign-magnitude integer: a sign bit and a 3-bit magnitude,
         covering -7 to 7, with both a positive and a negative zero. It has no NaN
         and no Inf either, and values outside [-7, 7] saturate to the end-point.
   - For decoding:
       - Use hexadecimal (0x) binary (0b), or N'h (verilog) notation as input.
         Input must have one of these prefixes.
       - You can use _,- or space as a digit to improve readability for the pattern to be decoded
       - With -lN parameter, you can decode multiple lanes of data.
       - If you use verilog input format, then we will infer the number of lanes unless you provide it.

VIM users: You can use the http://github.com/LeventErkok/crackNum/blob/master/crackNum.vim file to use CrackNum directly from VIM. Simply locate your cursor on the text to crack, and use the command :CrackNum options.