← 返回首页

【Skill脚本分享】一键添加Guard Ring

skill_writer Lv.3 skill 2026-06-01 20:05 👁 244 次浏览

SKILL 脚本:一键添加 Guard Ring 实现详解

Guard Ring 的手动添加在大型版图中非常耗时。本文提供一个完整的 SKILL 脚本,实现选中器件后一键生成 guard ring,并支持自定义参数。

脚本功能概述

  • 支持选中单个或多个 instance
  • 自动计算包围矩形并添加 guard ring
  • 支持 P+ ring 和 N+ ring 双环模式
  • 自动添加 contact 和 metal 连接
  • 支持批量处理整个 cell 的所有器件

核心代码实现

; ============================================================
; GuardRing Generator - LayoutForge SKILL Script
; 用法: 选中器件后执行 addGuardRing()
; ============================================================

procedure(addGuardRing(@optional (cv nil) (ringType "P+") (width 0.5) (space 0.2))
  ; 获取当前 cellview
  when(cv == nil
    cv = geGetEditCellView()
  )
  when(cv == nil
    warn("No cellview open\n")
    return(nil)
  )

  ; 获取选中的器件
  let((instList bBoxList x0 y0 x1 y1 ringLayer contacts)
    instList = geGetSelectedSet()
    when(instList == nil || length(instList) == 0
      warn("请先选中需要添加 guard ring 的器件\n")
      return(nil)
    )

    ; 计算所有选中器件的联合 bounding box
    x0 = 1e9
    y0 = 1e9
    x1 = -1e9
    y1 = -1e9
    foreach(inst instList
      bBoxList = inst~>bBox
      x0 = min(x0 xCoord(car(bBoxList)))
      y0 = min(y0 yCoord(car(bBoxList)))
      x1 = max(x1 xCoord(cadr(bBoxList)))
      y1 = max(y1 yCoord(cadr(bBoxList)))
    )

    ; 扩展 guard ring 区域
    x0 = x0 - space - width
    y0 = y0 - space - width
    x1 = x1 + space + width
    y1 = y1 + space + width

    ; 选择 layer
    if(ringType == "P+"
      then ringLayer = list("PIMP" "drawing")
      else ringLayer = list("NIMP" "drawing")
    )

    ; 创建 guard ring 外框(使用 ring 形状)
    let((outerBox innerBox ringRects)
      outerBox = list(x0:y0 x1:y1)
      innerBox = list((x0+width):(y0+width) (x1-width):(y1-width))

      ; 用四个矩形构成环形
      dbCreateRect(cv ringLayer
        list((x0:y0) (x1:(y0+width)))  ; bottom
      )
      dbCreateRect(cv ringLayer
        list((x0:(y1-width)) (x1:y1))  ; top
      )
      dbCreateRect(cv ringLayer
        list((x0:y0) ((x0+width):y1))  ; left
      )
      dbCreateRect(cv ringLayer
        list(((x1-width):y0) (x1:y1))  ; right
      )
    )

    ; 添加 contact
    let((contactLayer metalLayer xPos yPos)
      contactLayer = list("M1" "drawing")
      metalLayer = list("M1" "drawing")

      ; 底边 contacts
      for(xPos x0+0.5 x1-0.5 2.0
        yPos = y0 + width/2
        dbCreateRect(cv contactLayer
          list((xPos-0.1):(yPos-0.1) (xPos+0.1):(yPos+0.1))
        )
      )
    )

    printf("Guard Ring (%s) added: [%.3f, %.3f] to [%.3f, %.3f]\n"
      ringType x0 y0 x1 y1)
  )
)

procedure(addDoubleGuardRing(@optional (cv nil))
  when(cv == nil cv = geGetEditCellView())
  ; 外层 P+ ring
  addGuardRing(cv "P+" 0.5 0.2)
  ; 内层 N+ ring
  addGuardRing(cv "N+" 0.5 0.2)
  printf("Double guard ring (P+ + N+) added successfully\n")
)

使用方法

  1. 在 Virtuoso CIW 中执行 load("guard_ring.il")
  2. 在版图编辑器中选中需要保护的器件
  3. 执行 addGuardRing() 添加单环或 addDoubleGuardRing() 添加双环
  4. 参数可自定义:宽度、间距、layer 等

扩展功能建议

  • 添加图形界面(hiCreateAppForm),让用户在 UI 中选择参数
  • 支持自动识别器件类型,选择对应的 guard ring 类型
  • 集成到 Virtuoso menu 中,一键调用
  • 添加 DRC 自检,确保 guard ring 不与周围器件冲突

提示:不同工艺的 guard ring 规则差异很大,使用前务必确认工艺 rule file 中的 guard ring 相关设计规则。

#DRC #Guard Ring #SKILL脚本 #Virtuoso #寄生参数 #版图设计 #经验分享

💬 评论 (3)

登录 后发表评论
skill_writer Lv.3 2026-05-27 20:59
支持的,只要修改layer参数就行。SMIC的NW层和TSMC一样。
drc_hunter Lv.4 2026-05-27 21:59
收藏了!请问支持SMIC工艺吗?
layout_master Lv.5 2026-05-27 22:59
好脚本!我之前也写过类似的,不过你的版本更完善。建议加上多层Guard Ring的支持。