pin.name
the part type's functional name for a pin ("SDA", "PTC11"), the spelling a datasheet and a firmware header use, against the package designator every other pin relation is keyed on; absent when the part type declares none
What it is ¶
pin.name(ref_des, pin, name) yields the part type’s FUNCTIONAL name for a pin, where pin is the
package designator every other pin relation is keyed on and name is what the datasheet calls it.
On an MCU that is the difference between 41 and PTC11, or between 12 and SDA.
A row is emitted only when the part type declares a name, so a format carrying no pin names answers
nothing rather than answering "". KiCad spells “this pin has no name” as ~, which reaches the IR
verbatim and is read as absent here.
For hardware engineers ¶
Two things name the same pin and neither is redundant. The designator is where it sits on the package, which is what a netlist and a layout tool speak. The name is what the pin is for, which is what a datasheet, a firmware header and a pin-assignment map speak. A review question is almost always asked in the second vocabulary and the netlist almost always answers in the first.
Until this relation existed only the designator was reachable, so “is the ADC input on the pin the IO map says” could not be asked at all, even on a design where both spellings sit in the file. That is the gap agni issue 517 opens with.
How far apart the two spellings are depends on the format:
| format | designator |
name |
|---|---|---|
| KiCad | pin number | pin name, so the two genuinely differ (1 against K) |
| Telesis | the $PINS target |
from PinLabel |
| EDIF | the port’s declared designator, or the port NAME when it declares none | the port name |
On EDIF the two can be the same string, and a query should not assume otherwise. When an EDIF
file declares no pin designator the reader falls back to the port name (readers/edif/reader.go,
issue 71), because the Model indexes pins by designator while a portRef names the port, so without
the fallback nothing resolved. A design read that way answers pin.name and pin with identical
values, which is correct rather than a defect: the format supplied one spelling and both fields
carry it. Where the file does declare designators, they differ as everywhere else.
For software engineers ¶
A field’s declared name against its offset (see the analogy guide): pin is the position in the
package and name is the identifier the header file gives it. Rows are 1:1 with named pins and
absent for the rest, so pin(?r,?p), not pin.name(?r,?p,?_) reads as “the read gave this pin no
name”, which is a statement about the SOURCE rather than about the board.
Do not treat name as unique within a component. Nothing stops a part type from declaring the same
name on several pins (a device with four GND pins is ordinary), so a join on name alone can
multiply rows. Join on (ref_des, pin) when you mean one pin.
The name is recorded exactly as the source spells it, with no normalization. PTE7 and PTE07 are
the same pin to a person and two different strings here. Anything comparing a name against a name
from another document has to canonicalize both sides first, and the traps in doing that (zero
padding, invisible format characters, multi-valued cells) are real enough to have produced a whole
run of false warnings in a shipped in-house checker.
Go projector ¶
pinFacts in stdlib/relations/facts.go calls Model.PinName(ref, des) for each pin and emits a
row only when the result is non-empty and is not ~. PinName reads the part type’s pin list
resolved at ingestion, so a design whose read supplied no part-type pin data yields no rows at all,
which is the same nothing a design of entirely unnamed pins yields. Those two are not distinguished
here; pin (the bare relation) is what says whether the read produced pins in the first place.
Datalog ¶
Every pin’s functional name:
pin.name(?r, ?p, ?n) => ?r, ?p, ?n
What a named pin is wired to, which is the join the IO-map question is built on:
pin.name(?r, ?p, ?n), pin.net(?r, ?p, ?net) => ?r, ?n, ?net
Every pin the read named but left unconnected:
pin.name(?r, ?p, ?n), not pin.net(?r, ?p, ?net) => ?r, ?p, ?n