8.3 KiB
Week 6 Quiz: Static Variables, GPIO Input, and Binary Patching
Instructions
Choose the best answer for each question. There is only one correct answer per question.
Questions
Question 1
What is the key difference between a static local variable and a regular local (automatic) variable in C?
A) Static variables are stored on the stack; automatic variables are stored in flash
B) Static variables retain their value between function calls; automatic variables are re-created each time
C) Static variables can only be used in main(); automatic variables can be used anywhere
D) Static variables are always initialized to a random value; automatic variables default to 0
📖 Reference: Week 6, Part 1 – "Static Variables vs Regular Variables" (static variables persist across function calls and loop iterations; automatic variables are re-created each time)
Correct Answer: B
Question 2
Where in memory is an initialized static variable stored on the Pico 2?
A) On the stack (high RAM addresses growing downward)
B) In the .text section alongside executable code
C) In the .data section — initial values in flash, runtime copy in SRAM
D) In CPU registers only — static variables are never stored in RAM
📖 Reference: Week 6, Part 3 – "Compiler Optimizations" and Part 7 – "Analyze the Static Variable" (static variable lives at fixed RAM address
0x200005a8in the.datasection)
Correct Answer: C
Question 3
Why did the compiler optimize away regular_fav_num and replace it with a constant movs r1, #0x2a in the binary?
A) The compiler detected that regular_fav_num is never modified after initialization
B) The variable is too small (8 bits) for the compiler to allocate memory
C) The variable is assigned 42, printed, then incremented — but the increment has no observable effect since the variable is re-created each loop iteration
D) ARM processors cannot store local variables in RAM
📖 Reference: Week 6, Part 7, Step 13 – "Analyze the Regular Variable" (compiler optimized away the variable because its value is always 42 when printed; the post-print increment has no observable effect)
Correct Answer: C
Question 4
What does the ubfx r3, r3, #0xf, #0x1 instruction do?
A) Stores the byte in r3 at GPIO address 0xF
B) Extracts bit 15 (a single bit) from r3 and stores the result in r3
C) Sets all bits in r3 except bit 15
D) Performs an unsigned division of r3 by 15
📖 Reference: Week 6, Part 7, Step 15 – "Analyze the GPIO Logic" (table:
ubfx r3,r3,#0xf,#0x1extracts bit 15, which is GPIO 15 = button)
Correct Answer: B
Question 5
A pull-up resistor on GPIO 15 means the pin reads HIGH when the button is not pressed. What instruction does the compiler use to implement the !gpio_get(BUTTON_GPIO) inversion?
A) sub r3, r3, #0x1 — subtracts 1 from the button state
B) mvn r3, r3 — performs a bitwise NOT on all 32 bits
C) eor r3, r3, #0x1 — XOR with 1 to flip the least significant bit
D) cmp r3, #0x0 followed by a conditional branch
📖 Reference: Week 6, Part 7, Step 15 – GPIO logic table (
eor r3,r3,#0x1implements the ternary operator? 0 : 1by XORing with 1)
Correct Answer: C
Question 6
The static variable static_fav_num is a uint8_t. What happens when it reaches 255 and is incremented by 1?
A) The program crashes with an overflow exception
B) The value wraps around to 0 due to unsigned integer overflow
C) The value becomes 256 because the compiler promotes it to uint16_t
D) The value stays at 255 (saturation arithmetic)
📖 Reference: Week 6, Part 5, Step 5 – "Watch for Overflow" (output shows: 254, 255, 0, 1 — demonstrating unsigned integer wrap-around)
Correct Answer: B
Question 7
When patching the movs r1, #0x2a instruction at address 0x10000264, what is the correct file offset in the .bin file?
A) 0x10000264 — binary addresses and file offsets are the same
B) 0x264 — subtract the base address 0x10000000 from the instruction address
C) 0x265 — the immediate value is in the second byte of the instruction
D) 0x002640 — multiply by 16 because hex addresses use nibbles
📖 Reference: Week 6, Part 8, Step 18 – “Calculate the File Offset” (file_offset = address − 0x10000000; 0x10000264 → 0x264)
Correct Answer: B
Question 8
In the Thumb instruction movs r1, #0x2a, the bytes in the binary are 2A 21. What does each byte represent?
A) 2A is the register number; 21 is the value
B) 2A is the immediate value (42); 21 is the opcode for movs r1, #imm8
C) 2A 21 is the two-byte little-endian encoding of the value 8490
D) 2A is the opcode; 21 is the register and immediate combined
📖 Reference: Week 6, Part 8, Step 19 – "How Thumb encoding works" callout (immediate value is the first byte, opcode
21is the second byte)
Correct Answer: B
Question 9
The SDK function gpio_pull_up(15) does not appear in the disassembly. Instead, GDB shows a call to gpio_set_pulls(15, 1, 0). Why?
A) gpio_pull_up is a deprecated function that was removed from the SDK
B) The compiler inlined gpio_pull_up — it's a small wrapper that calls gpio_set_pulls with up=true, down=false
C) The linker renamed the function to avoid symbol conflicts
D) GDB incorrectly resolves the function name
📖 Reference: Week 6, Part 3 – "Function Inlining" and Part 6, Step 6 – disassembly showing
bl gpio_set_pullswith argsr0=15, r1=1, r2=0
Correct Answer: B
Question 10
You want to permanently change the static variable's initial value from 42 to 100 in the binary. Which approach is correct?
A) Modify the movs r1, #0x2a instruction at 0x10000264 because that is where the static variable is initialized
B) Use GDB to set *(char*)0x200005a8 = 100 — this permanently changes the flash
C) Find the initialization value in the .data section of flash, calculate its file offset, and patch it from 0x2A to 0x64 in the hex editor
D) Change the push {r4, lr} instruction to load 100 into r4 before main starts
📖 Reference: Week 6, Practice Exercise 1 – "Change Static Variable Initial Value" (the initial value lives in the
.datasection in flash; the startup code copies it to RAM beforemain()runs)
Correct Answer: C
Answer Key
- B - Static variables persist between function calls; automatic variables are re-created each time
- C - The
.datasection holds initial values in flash; they are copied to SRAM at startup - C - The post-print increment has no observable effect because the variable resets each loop iteration
- B - UBFX (Unsigned Bit Field Extract) extracts bit 15 (one bit) — the button GPIO state
- C -
eor.w r3, r3, #1flips the least significant bit, implementing logical NOT for a single-bit value - B -
uint8_twraps from 255 to 0 — unsigned overflow is well-defined in C - B - File offset = address − base (
0x10000264−0x10000000=0x264) - B - In Thumb
movs rD, #imm8, the first byte is the immediate, the second byte is the opcode - B - The compiler inlines
gpio_pull_upas a call togpio_set_pullswithup=true, down=false - C - Static variable initial values live in the
.datasection of flash and must be patched there
Scoring Guide
- 10 correct: Excellent! You have a strong grasp of Week 6 concepts
- 8-9 correct: Very good! Review the topics you missed
- 6-7 correct: Good start. Go back and review the key concepts
- 5 or fewer: Review the Week 6 material again and try the practice exercises
Topics Covered
This quiz tests your understanding of:
- Static vs automatic (local) variables and their storage duration
.datasection: flash initialization values copied to SRAM at startup- Compiler optimizations: dead code elimination and constant propagation
- UBFX (Unsigned Bit Field Extract) for reading individual GPIO pins
- XOR (EOR) for implementing logical NOT on single-bit values
- Unsigned integer overflow and
uint8_twrap-around behavior - File offset calculation: address minus base address
0x10000000 - Thumb instruction encoding:
movs rD, #imm8byte layout - Function inlining:
gpio_pull_up→gpio_set_pulls - Binary patching strategy for static variable initial values