0hmX/am3352

This code suite comprises TypeScript scripts that analyze, verify, and assemble complex DDR memory interface hardware, focusing on physical routing, via and pad placement, electrical clearance, and physical constraints, often involving precise geometric calculations and consistent provenance tracking.

Version
1.0.5
License
unset
Stars
0

scripts/ddr-memory-cache-board-comparison.ts

import{createHash}from'node:crypto'
import{fanoutTracePath}from'@tscircuit/props'
const hash=(v:any)=>createHash('sha256').update(JSON.stringify(v)).digest('hex')
const geometry=(route:any[])=>route.map(p=>{if(typeof p.x!=='number'||typeof p.y!=='number'||!Number.isFinite(p.x)||!Number.isFinite(p.y))throw Error('Cache/actual coordinates must be finite millimeters');const xy={x:Number(p.x.toFixed(7)),y:Number(p.y.toFixed(7))};if(p.route_type==='wire')return{route_type:p.route_type,...xy,layer:p.layer,width:p.width};if(p.route_type==='via')return{route_type:p.route_type,...xy,from_layer:p.from_layer,to_layer:p.to_layer,via_diameter:p.via_diameter,via_hole_diameter:p.via_hole_diameter};throw Error('Unsupported actual copper primitive')})
/** Only power/ground copper may differ from the complete physical escape cache.
 * Bind the actual trace through its pad -> PCB port -> source port -> source trace,
 * rather than accepting an unrelated conductor at the same coordinates. */
export function compareDdrMemoryCachePathToBoard(path:any,pin:{ball:string;signal:string;terminal:string;routed:boolean;x:number;y:number},byte:number,placement:{x:number;y:number;rotation:number},candidate:any[]){
 fanoutTracePath.parse(path)
 if(!pin.routed||path.connection!==`U1.ball_${pin.ball}`||placement.rotation!==180||![0,1].includes(byte))throw Error('Unsupported cache ball/placement')
 const first=path.route[0];if(first?.route_type!=='wire'||first.layer!=='top'||Math.hypot(first.x-pin.x,first.y-pin.y)>1e-7)throw Error('Cache launch differs from authoritative pin')
 const projected=path.route.map((p:any)=>({...p,x:placement.x-p.x,y:placement.y-p.y})),start=projected[0],same=(p:any)=>p&&p.layer===start.layer&&Math.hypot(p.x-start.x,p.y-start.y)<1e-7,pads=candidate.filter(e=>e.type==='pcb_smtpad'&&same(e))
 if(pads.length!==1)throw Error(`Ambiguous actual package pad ${byte}/${pin.ball}`)
 const pcbPorts=candidate.filter(e=>e.type==='pcb_port'&&e.pcb_port_id===pads[0].pcb_port_id),sourcePorts=candidate.filter(e=>e.type==='source_port'&&e.source_port_id===pcbPorts[0]?.source_port_id)
 if(pcbPorts.length!==1||sourcePorts.length!==1||sourcePorts[0].name!==`ball_${pin.ball}`)throw Error('Actual package pad/source ball identity differs')
 const sourcePortId=sourcePorts[0].source_port_id,owned=new Set(candidate.filter(e=>e.type==='source_trace'&&e.connected_source_port_ids?.includes(sourcePortId)).map(e=>e.source_trace_id)),actual=candidate.filter(e=>e.type==='pcb_trace'&&e.route[0]?.route_type==='wire'&&same(e.route[0])&&owned.has(e.source_trace_id))
 if(actual.length!==1)throw Error(`Ambiguous source-owned actual cache trace ${byte}/${pin.ball}`)
 const cacheGeometrySha256=hash(geometry(projected)),actualGeometrySha256=hash(geometry(actual[0].route))
 if(cacheGeometrySha256===actualGeometrySha256)return[]
 if(!['VDD','VDDQ','VSS','VSSQ'].includes(pin.signal))throw Error(`Stale signal cache ${byte}/${pin.ball} (${pin.signal}); only explicit power/ground replacements may differ`)
 return[{ball:pin.ball,signal:pin.signal,terminal:pin.terminal,actualTraceId:actual[0].pcb_trace_id,sourceTraceId:actual[0].source_trace_id,sourcePortId,cacheGeometrySha256,actualGeometrySha256,reason:'Accepted board applies an additional explicit power/ground copper replacement; this full72 escape cache alone does not reproduce it.'}]
}