Practice

Packing Camera Capture

At Fenwick Mail Centre, a small camera photographs every box above belt 6. It sends each pixel as two bytes over an 8-bit parallel bus.

One damaged image line arrived one byte short. The old capture block missed the fault, so every colour after it shifted by one byte.

On the preview screen, orange packing tape turned blue halfway across each box.

The error lasted until someone powered the sorter off and on. Boxes kept moving, but their saved images could not be trusted.

Your task: build the camera capture stage. Pair bytes again at every line, publish complete RGB565 pixels, and report any line that ends with half a pixel.

Interface

PortDirectionTypeDescription
pclk_iin1 bitPixel clock from the camera and the only DUT clock
rst_iin1 bitSynchronous reset (active high)
vsync_iin1 bitFrame separator, high between frames while href_i is low
href_iin1 bitHigh while a line's bytes stream
d_iin8-bit vectorOne byte per clock while href_i is high
pixel_oout16-bit vectorLast completed RGB565 pixel, held
pixel_valid_oout1 bitCompleted pixel (one-pclk pulse)
frame_start_oout1 bitFirst captured byte of a frame (one-pclk pulse)
line_end_oout1 bitLine closed (one-pclk pulse)
frame_err_oout1 bitLine closed on a half pixel (one-pclk pulse)

Behavior

  • The camera changes vsync_i, href_i, and d_i after falling pclk_i edges
  • The capture stage samples all inputs only on rising pclk_i edges
  • While href_i is high, every rising edge carries one byte
  • Each RGB565 pixel contains two bytes, with the high byte first
  • Nothing is captured while href_i is low or vsync_i is high
  • Each sampled low-to-high transition on href_i resets byte pairing
  • Every line therefore starts with a high byte, regardless of the previous line
  • One clock after a pixel's second byte is sampled, pixel_o updates and pixel_valid_o pulses
  • pixel_o holds its value between completed pixels
  • pixel_valid_o is low except during its one-pclk pulses
  • Each observed vsync_i pulse marks the next captured line as the first line of a new frame
  • frame_start_o pulses one clock after that line's first byte is sampled
  • frame_start_o pulses only once per frame
  • When href_i falls after an even byte count, line_end_o pulses one clock later
  • When href_i falls after an odd byte count, line_end_o and frame_err_o pulse together one clock later
  • A half pixel at the end of a damaged line is discarded and never published
  • The next line starts fresh with high-byte-first pairing
  • After reset, capture stays idle until a vsync_i pulse has been observed, and pixel_o reads zero until the first published pixel
  • Any lines seen before the first vsync_i pulse are ignored
  • rst_i high at a rising edge clears capture progress and returns the stage to its initial waiting state
  • pixel_o, pixel_valid_o, frame_start_o, line_end_o, and frame_err_o are registered outputs

What the bench checks

  • The testbench changes camera inputs after falling edges and checks every output cycle by cycle against a reference model
  • It sends byte patterns that expose swapped, shifted, or wrongly paired bytes, with the first byte expected in bits 15 through 8
  • It sends an odd-length line and checks that line_end_o and frame_err_o pulse together one clock after the fall
  • It checks that the dangling half pixel is discarded and never reaches pixel_o
  • It follows the damaged line with a clean one and checks that pairing re-anchors on the href_i rise
  • It sends lines before the first vsync_i pulse and checks that they are ignored
  • It resets mid-line with a pixel one clock from publishing and checks that nothing of that line comes out

Constraints

TIMING: everything is synchronous to pclk_i; camera inputs change after falling edges, capture samples only on rising edges, and all outputs are registered.

SCOPE: this models the digital capture contract on the pixel clock. Input-delay constraints, the sensor's analog side, and moving pixels into another clock domain are out of scope.

Do not add ports.

Loading editor...

Click Run to execute your code. Output will appear here.