liveBook · Manning

Chapter 5: Data in depth

What you will learn in chapter 5 of Rust in Action: Systems programming concepts and techniques

The chapter introduces its focus on data representation and computation and previews the topics and projects ahead.

After this chapter you will be able to

What it builds on

Section by section

Introduction

The chapter introduces its focus on data representation and computation and previews the topics and projects ahead.

5.1 Bit patterns and types

The section shows how types and encodings give bit patterns meaning, then uses a bit-preserving reinterpretation to introduce Rust’s unsafe blocks.

Key terms: bit pattern, type system, binary files, text files, encoding, opaque, f32, u32, std::mem::transmute(), std::fmt::Binary

5.2 Life of an integer

This section explains how fixed-width integer ranges cause overflow, how overflow can affect Rust programs, and the tradeoffs in preventing it.

Key terms: integer, u16, bits, integer overflow, panic, -O, u8, fixed-sized types, runtime, i64

5.2.1 Understanding endianness

This section explains how CPUs can order the bytes of multibyte integers differently and distinguishes that byte order from the numbering of bits within a byte.

Key terms: endianness, big endian, little endian, most significant, bit numbering, bit endianness, MSB, most significant bit, most significant byte

5.3 Representing decimal numbers

The section motivates a compact decimal-number format by showing that numbers confined to a known range may not need the full range of f32 or f64.

Key terms: f32, f64, decimal number format, 0..=1, -1..=1

5.4 Floating-point numbers

The section uses scientific notation to explain how floating-point numbers represent a wide range of values with a fixed-width format.

Key terms: scientific notation, fixed-width format, scale, sign bit, exponent, mantissa, significand, radix, base

5.4.1 Looking inside an f32

Introduces the three-field layout of an f32, shows how those fields decode to a number, and notes two surprising floating-point comparisons.

Key terms: f32, sign_bit, mantissa, exponent, Radix, Bias, sign bits, 0, –0, NAN values

5.4.2 Isolating the sign bit

This subsection shows how to isolate the sign bit of an f32 by interpreting its bits as a u32 and shifting them right.

Key terms: sign bit, f32, u32, right shift, 31 places

5.4.3 Isolating the exponent

This subsection shows how to extract an f32’s exponent bits and decode them by removing the exponent bias.

Key terms: f32, u32, right shift, mantissa, AND mask, sign bit, exponent, bias, 127, signed integer

5.4.4 Isolate the mantissa

This section explains how to decode an f32 mantissa, how special exponent patterns change its interpretation, and why negative floating-point literals can need parentheses in method calls.

Key terms: mantissa, implicit 24th bit, AND mask, weight, subnormal numbers, denormal numbers, infinity, Not a Number, NAN, unary minus

5.4.5 Dissecting a floating-point number

This subsection uses an f32 round trip to show how its bit fields become an ordinary number.

Key terms: f32, fields, raw bit pattern, scientific notation

5.5 Fixed-point number formats

The section introduces Q7 as a compact fixed-point format, shows how its Rust type converts to and from floating-point values, and gives brief guidance on Rust modules.

Key terms: fixed point, floating-point, floating point unit (FPU), Q7, Q format, i8, tuple struct, #[derive(...)], Copy, From<T> for U

5.6 Generating random probabilities from random bytes

The section compares division with a bit-manipulation approach for turning a random byte into an f32 value between 0 and 1.

Key terms: u8, f32, mem::transmute, division, exponent, mantissa, bit manipulation, normalization

5.7 Implementing a CPU to establish that functions are also data

Introduces the idea that computer instructions are encoded as numbers, allowing one computer to emulate another in software.

Key terms: instructions, instruction sets, emulate

5.7.1 CPU RIA/1: The Adder

This section introduces a minimal CHIP-8 CPU emulator that adds two register values, explaining its opcode and the steps its main loop takes.

Key terms: registers, operands, opcode, addition, operation, 0x8014, u16, nibble, high byte, low byte

5.7.2 Full code listing for CPU RIA/1: The Adder

This subsection points readers to the Adder proto-emulator’s full source listing but provides no code or output to assess.

5.7.3 CPU RIA/2: The Multiplier

This section expands the CPU emulator from executing one addition instruction to running instructions from memory in sequence, while explaining its register layout, opcode reading, and overflow flag.

Key terms: main loop, position_in_memory, opcode, current_instruction, registers, memory, u16, CHIP-8, read_opcode(), u8

5.7.4 CPU RIA/3: The Caller

This section adds function calls to CPU RIA/3 by storing executable instructions in memory and using a stack to return from them.

Key terms: function, opcode, [u16;3], [u8;6], RAM, copy_from_slice(), CALL opcode, RETURN opcode, stack, stack pointer

5.7.5 CPU 4: Adding the rest

This section explains how the CHIP-8 CPU changes control flow without having loop instructions.

Key terms: control flow, registers, position_in_memory, compiler writer

5.8 Summary

Where this is used later

Concepts explained in this chapter

← Chapter 4: Lifetimes, ownership, and borrowing Chapter 6: Memory →

These guides are generated from the text of Manning books by Manning's knowledge graph and link to the sections they draw on. The full books are available on liveBook and at manning.com.