Create your own
Lesson illustration

Decomposing Hardware Traits and Tracing Their Drivers, Kernel Changes, and Discussions

Welcome back. In the previous lesson, you built a manual-fact ledger and learned to stop when a hardware claim is unclear, incomplete, or contradictory. That gives you a safe answer to: “What does this switch actually do?”

This lesson adds a second kind of investigation: comparison. You will split the driver into small hardware traits, then find upstream drivers, kernel changes, and mailing-list discussions that are relevant to each trait. The objective is not to find code to copy. It is to find narrowly applicable implementation patterns and the reasoning behind them, while keeping your switch’s documented behavior separate from another chip’s behavior.

By the end, you should have a trait research log that tells an agent exactly what to investigate, which upstream references are useful, which differences block reuse, and when it must ask a human rather than infer an answer.


A hardware trait is a bounded behavior, not a driver file

A DSA driver may have one main C file, one tagger, a binding YAML file, and perhaps PHY support. Those are source-file boundaries. They are not good investigation boundaries.

A hardware trait is one independently checkable part of the switch’s behavior. It has:

  1. A specific hardware question.
  2. A manual-evidence requirement.
  3. A DSA or kernel integration question.
  4. A small set of plausible upstream comparators.
  5. Explicit differences that might make a comparator unsafe.

For example, “CPU-port tagging” is a trait. “The tagger source file” is not. CPU-port tagging includes at least these separate questions:

  • Where is the tag placed: before Ethernet headers, before EtherType, or at the packet tail?
  • Does hardware insert it on traffic toward the CPU, consume it on traffic from the CPU, or both?
  • Which fields identify source and destination ports?
  • Is tag length fixed or variable?
  • Does the tag change frame length, FCS treatment, MTU requirements, checksum handling, or packet parsing?
  • Which chip mode, strap, or register setting enables it?

A comparable upstream tagger may be useful for how Linux adjusts an sk_buff, handles headroom, or maps a source-port field to a DSA port. It cannot prove that your chip uses the same tag position, byte order, field encoding, or enable sequence.

The same rule applies throughout the driver:

Similar code can establish a candidate Linux pattern. Only evidence for your hardware can establish your hardware behavior.

The Kernel DSA Architecture documentation provides the shared vocabulary needed to make this split. Read it as a description of the DSA-side contract, then verify API details against the exact target kernel tree for the V1 revision.

Architecture

Read the Linux kernel’s DSA Architecture documentation to separate switch roles, tagging mechanics, registration responsibilities, and bridge or VLAN operations into distinct investigation traits.

In the “Design principles” section, read the port-role model. Distinguish the conduit or CPU-facing connection from user ports and possible DSA cascade ports. Then, in “Switch tagging protocols,” read the tag contract, followed by the three tag-placement categories and the discussion of headroom, tailroom, and MTU handling. Focus on what the DSA tagger must do after the hardware format is known; do not treat these general categories as proof of your switch’s format. In “Driver development,” under “Probing, registration and device lifetime,” read the registration and shutdown discussion. Under “Switch configuration,” read from the core callbacks. Note which traits affect setup, isolation, tag selection, and teardown. Finally, in “Bridge layer” and “Bridge VLAN filtering,” scan the callback descriptions. Use them to identify separate forwarding, learning, FDB, bridge, STP, and VLAN traits rather than treating “bridge offload” as one indivisible feature.

A useful first trait inventory for a DSA V1 is below. Do not assume every row applies to the target switch. Mark a row OUT OF SCOPE if V1 does not expose it and no review comment requires it.

TraitHardware questionTypical V1 surfacesHigh-risk assumption to avoid
Chip accessHow are registers addressed, synchronized, and error-checked?Bus read/write helpers, probeA similar indirect-access engine has identical completion or error semantics
Port topologyWhich logical ports are CPU, user, internal PHY, unused, or cascade ports?num_ports, port tables, Device TreeA port number in another package or board layout applies here
CPU-port interfaceWhich MAC mode, clocks, delays, and link-management method apply?CPU port node, phy-mode, phylink setupThe board’s straps match a reference board
Packet taggingWhat is inserted, consumed, and encoded in each direction?Tagger, get_tag_protocolSame vendor means same tag format
Reset and bootstrapWhat is reset, when is it complete, and what state remains?Probe, setup, reset controllerAnother driver’s delay or polling loop is safe
Initial isolationWhat forwarding state protects ports before bridge configuration?setup, port setupDefault bootloader forwarding state is safe
PHY and link managementAre PHYs internal or external, and how is link state read or configured?MDIO callbacks, phylink, PHY driverA PHY driver’s behavior proves switch MAC behavior
VLAN, FDB, and MDB tablesWhat table model and resource limits exist?VLAN/FDB callbacks, bridge operationsSimilar table names have identical keys or isolation rules
Interrupts and statusWhich bits mask, acknowledge, clear, or latch events?IRQ handler, status helpersRead-clear and write-one-to-clear behave alike
Statistics and tablesWhat widths, clear behavior, and access ordering apply?ethtool statistics, table accessCounter reads are safe concurrently or never wrap

This decomposition avoids a common AI-agent failure: it sees a broad review comment such as “please use the standard DSA flow” and makes a large rewrite touching probe, tagger, binding, and VLAN code together. Instead, it should identify the exact traits involved and investigate each one separately.


Build a trait card before searching for analogies

For every trait that is connected to V1 or a reviewer comment, create a short card. The card is a research request, not yet a design decision.

id: "TR-TAG-001"
trait: "CPU-port packet tagging"

question: >-
  What framing and port-selection behavior does the target switch require
  for packets sent to and received from the CPU-facing Ethernet link?

v1_locations:
  - "net/dsa/tag_<driver>.c: <function or hunk>"
  - "drivers/net/dsa/<driver>.c: <get tag protocol callback>"
review_tasks:
  - "RV-<id>"

hardware_evidence_needed:
  - "RX packet-layout description"
  - "TX packet-layout description"
  - "Tag enable conditions"
  - "Port-number encoding"
  - "Frame-size, FCS, and checksum notes if documented"

kernel_questions:
  - "Which target-tree DSA tag protocol interface is required?"
  - "Does tag placement require headroom, tailroom, or special parsing?"
  - "Which offload assumptions must the tagger preserve?"

comparison_dimensions:
  - "tag position"
  - "RX and TX directionality"
  - "tag length"
  - "source and destination field semantics"
  - "CPU-port mode"
  - "target-kernel tagger API"

blocked_by:
  - "MF-TAG-<id>, if packet direction or field meaning is unclear"

The comparison_dimensions field is especially important. It prevents the agent from writing “Driver X has a 4-byte tag too” and treating that as meaningful similarity. Equal length alone says almost nothing. A tag can have the same length while placing fields in different bytes, using different port numbering, or having opposite TX and RX meaning.

For each trait, write the narrowest question first. Avoid vague cards such as:

Investigate VLAN support.

Prefer:

Determine whether the hardware assigns a filtering domain per VLAN, per bridge, per port, or through a shared global table, and whether V1’s callback set can represent that model safely.

That question tells the agent which manual material to find and which comparable drivers may be relevant.


Find comparators by mechanism, not by vendor name

Start with three kinds of candidate reference for each trait.

  1. Family neighbor
    A driver for the same vendor, hardware family, bus controller, or tag format. It may reveal naming, register-access conventions, or known silicon workarounds. It is still only a lead until the target chip’s manual supports the same behavior.

  2. Mechanism neighbor
    A driver from any vendor that uses the same DSA-relevant mechanism: tail tagging, internal PHY access, a shared VLAN table, indirect FDB access, or a particular phylink arrangement. This is often more useful than a vendor neighbor for Linux-side code structure.

  3. Target-kernel API neighbor
    A driver changed recently near the target kernel version and using the same callback or helper. This helps avoid copying an obsolete DSA interface from an older branch.

Use the local target kernel tree first. It gives reproducible results and avoids mixing code from a newer development branch into a V1 repair based on an older submission base.

# Locate candidate users of a DSA callback or feature.
git grep -n -E 'get_tag_protocol|change_tag_protocol' drivers/net/dsa net/dsa
git grep -n -E 'port_vlan_add|port_vlan_del|port_fdb_add' drivers/net/dsa
git grep -n 'dsa_switch_shutdown' drivers/net/dsa

# Find the history of one candidate implementation.
git log --follow -p -- drivers/net/dsa/<candidate>.c
git log --follow -p -- net/dsa/tag_<candidate>.c

# Find why an exact helper, callback, or lifecycle rule was introduced.
git log -S'dsa_switch_shutdown' -p -- drivers/net/dsa net/dsa
git log -S'<relevant helper name>' -p -- drivers/net/dsa net/dsa

# Inspect commit metadata, including any recorded discussion reference.
git show --format=fuller <commit-id>

When an upstream commit contains a discussion reference, record the exact commit ID, message ID or thread locator, author, date, and patch version. Read the discussion for rationale: perhaps a maintainer explains why an allocation must happen in setup, why a YAML property was rejected, or why a callback cannot safely return success.

A mailing-list statement is useful context, but it is not a timeless rule. Check whether:

  • it concerns the same kernel API generation;
  • a later patch or follow-up changed the conclusion;
  • it depends on a particular hardware limitation;
  • the final merged code actually matches the proposal.

The provided MT7628 patch-series history is a concise example of the kind of evidence you should preserve. It shows that one DSA support series can have independent review-driven changes in bindings, tagger code, MDIO handling, teardown, reset error paths, and object lifetime.

net: dsa: mt7628 embedded switch initial support [LWN.net]

Read this LWN-hosted patch-series record as an example of how upstream review separates DSA support into independent traits and how version histories preserve the reason for a change.

Read the stated scope first. It establishes what this particular driver claims to support, including its explicit bridge-offload limitation. Then read the revision notes from “Changes since v4” through “Changes since v1.” In particular, follow the v4 and v3 changes. Notice that the series treats MDIO object lifetime, VLAN behavior, reset error checking, binding schema structure, and integrated-PHY topology as separate issues. Finally, inspect the changed-file list. It shows that binding YAML, main switch driver, PHY support, and the DSA tagger are separate implementation components. Do not infer that your switch needs the same files, topology, or fixes; use the series only as a model for recording narrowly scoped changes and their review history.

The MT7628 series supports several process lessons:

  • A binding correction does not establish a hardware correction.
  • A tagger cleanup does not establish that the target switch has the same tag format.
  • A lifetime fix may be broadly relevant as a device-model pattern, but its exact allocation and teardown conditions still need target-tree analysis.
  • “No external MDIO bus” is a chip-specific claim. It must never be transferred to another switch merely because both have integrated PHYs.

Compare traits with explicit similarities and differences

The table below gives a focused search strategy for common DSA traits. Treat it as a query plan, not a list of features your driver must implement.

TraitSearch for upstream code that sharesConfirm from your manual before reuseDifferences that block transfer
Register accessSame bus type, indirect register engine, timeout pattern, locking modelCommand format, completion bit, error status, sleepabilityDifferent busy semantics, bank selection, read-clear status, or atomic context
CPU-port interfaceSame phylink or fixed-link model, similar MAC-side interfaceSupported mode, clock direction, delays, strap state, link sourceDifferent board wiring, in-band status support, or CPU-port number
TaggingSame tag placement and target-tree tagger interfaceExact bytes, field encoding, RX/TX behavior, maximum overheadSame tag length but different port fields, frame position, or checksum behavior
ResetSimilar device-managed reset use and error unwindingReset scope, completion indication, required ordering, retained stateDifferent reset controller, self-clearing behavior, or post-reset register state
Internal PHYSimilar user-MDIO access or built-in PHY topologyPHY addresses, MDIO visibility, link-status source, initialization needsPHY access is indirect, external, or controlled by another block
Isolation and bridgingSimilar port matrix, private VLAN, FID, or bridge-domain modelInitial forwarding state, learning behavior, CPU-port flooding rulesGlobal rather than per-port control, limited domains, no independent FIDs
VLAN and FDBSimilar table access and VLAN resource accountingKey fields, table size, command completion, VID and FID semanticsDifferent table key, asynchronous engine, global table, or shared resource
IRQ and statusSimilar threaded IRQ or polling structureMasking, acknowledgement, clear operation, and source ownershipRead-clear versus write-one-to-clear, level versus edge behavior
StatisticsSimilar ethtool layout and counter collection modelWidth, wrap behavior, latch requirements, clear side effectsCounter read resets data, requires a table command, or is not per-port

A comparison is acceptable only when its shared dimensions are documented. A useful record looks like this:

comparator:
  name: "<upstream driver or commit>"
  kind: "mechanism neighbor"
  target_tree_ref: "<commit ID or target branch path>"
  trait: "CPU-port packet tagging"

  demonstrated_pattern: >-
    The tagger reserves packet expansion space and updates packet layout
    according to the selected tag placement.

  similarities_confirmed:
    - "Both formats are documented as tail tags."
    - "Both require destination selection on CPU-originated frames."
    - "Both drivers use the target kernel's DSA tagger interface."

  differences_confirmed:
    - "Target tag source-port field encoding is not yet established."
    - "Comparator documents fixed tag length; target manual does not."
    - "Comparator's checksum note does not mention the target hardware."

  permitted_use: >-
    Inspect its target-kernel packet-buffer handling and test expectations.
    Do not copy field masks, tag length, destination encoding, or checksum
    logic.

  prohibited_claim: >-
    The comparator does not prove that the target switch is compatible with
    its tag protocol.

This is more valuable than a similarity score. A numerical score can hide the one difference that makes copying unsafe: a different field polarity, port numbering base, or reset completion condition.


Apply four gates before transferring any pattern

Before the agent converts a comparator into a code proposal, require these gates in order.

1. Hardware gate

The target manual must establish the required target behavior. For a tagger, that means the direction, layout, and field semantics needed by the proposed code. For reset, it means the reset effect and completion conditions.

If the manual record is UNCLEAR, INCOMPLETE, or CONFLICT, the agent may continue researching comparable code but must not implement the unproven behavior.

2. DSA-contract gate

The target kernel’s DSA contract must support the intended behavior. This includes callback lifetime, return-value rules, required isolation, tagger interface, and helper expectations.

A comparator from a different kernel era can explain why an operation exists but can still be unusable code.

3. Platform and binding gate

The board’s Device Tree and documented board configuration must support the proposal. A chip may support several CPU-port modes, while the board permits only one. The binding must describe properties that V1 consumes correctly and that are valid for the target kernel schema.

4. Lifecycle gate

The code must safely handle success, partial setup, failure, remove, and shutdown. A pattern that is functionally correct in normal probe may still leak an object or call DSA teardown twice on an error path.

If any gate fails, record the result as one of these outcomes:

OutcomeMeaningAgent action
USABLE PATTERNHardware facts, target-kernel contract, and lifecycle preconditions all matchPropose a minimal change and send it through the normal check loop
RESEARCH LEADComparator suggests where to look, but target evidence is missingAdd manual or target-tree investigation tasks; do not edit
REJECTED COMPARATORA documented difference makes it inapplicablePreserve the reason and stop using it as support
HUMAN QUESTIONA missing hardware or board fact blocks a decisionAsk the focused question format from the previous lesson

This is how you prevent “upstream does it this way” from appearing as a substitute for evidence in a reviewer response.


A practical 35-minute research pass

Use the following pass for the V1 series now. Keep it deliberately small: three traits are enough for the first run.

  1. Choose three review-linked traits — 5 minutes
    Prioritize a hardware-dependent concern, a DSA integration concern, and a binding or lifecycle concern. For example: CPU-port tagging, reset sequencing, and internal-PHY topology.

  2. Create one trait card for each — 5 minutes
    Include V1 locations, reviewer task IDs, missing manual fact IDs, and comparison dimensions. Do not decide on a fix.

  3. Find one family neighbor and one mechanism neighbor per trait — 10 minutes
    Use the target kernel tree. Record candidate paths or commits, not just driver names.

  4. Inspect the relevant history and discussion metadata — 8 minutes
    Look for why the callback, helper, or cleanup path changed. Record the exact commit and the thread reference if available.

  5. Write the comparison boundaries — 5 minutes
    List confirmed similarities, confirmed differences, and unknowns. Unknowns are blockers, not similarities.

  6. Choose the next action — 2 minutes
    Select one: inspect target-kernel API details, extract another manual fact, repair an independent issue, or ask a human question.

Keep the output in a version-controlled research file, for example:

evidence/
  manual-facts.yaml
  trait-research.yaml
  upstream-history/
    <trait>-commits.md
    <trait>-threads.md
questions/
  hardware-questions.md

The agent should be allowed to add research records and propose candidates. It should not change kernel code merely because it has found a close-looking driver.

When a failure is outside this lesson’s scope, use the course map rather than improvising:

  • A missing, ambiguous, or conflicting manual claim returns to the previous lesson’s fact-ledger method.
  • A callback, lock, sleepability, setup, shutdown, MDIO, or phylink question belongs in Module 4.
  • A YAML schema, example, compatibility, or property-handling question belongs in Module 4’s binding lesson.
  • Repeatable builds, saved logs, guarded worktrees, and agent permissions belong in Module 5.
  • A Sashiko finding is handled through Module 6 after the normal checks pass.

Key takeaways

A good upstream comparison is narrow, documented, and honest about its limits.

  • Split V1 into hardware traits such as tag format, reset behavior, CPU-port interface, PHY topology, forwarding isolation, and table access.
  • Search for comparators by mechanism and target-kernel API use, not only by vendor or source-file similarity.
  • Use driver code to learn implementation patterns, commits to learn change history, and mailing-list discussions to learn rationale.
  • Require documented target-hardware behavior, target-kernel compatibility, board or binding validity, and safe lifecycle handling before reusing a pattern.
  • Record confirmed similarities, confirmed differences, and unknowns separately. An unknown is never permission to copy.
  • When manual evidence is insufficient, keep the comparison as a research lead and ask a focused human question rather than implementing a plausible guess.

Next, you will combine these results into one evidence table that keeps manual facts, V1 behavior, DSA rules, upstream patterns, assumptions, and open hardware questions visibly separate.

Can't find a good explanation? Sign up and we'll make it for you

Sign up