• Skip to main content
  • Skip to search
  • Skip to footer
Cadence Home
  • This search text may be transcribed, used, stored, or accessed by our third-party service providers per our Cookie Policy and Privacy Policy.

  1. Community Forums
  2. Custom IC SKILL
  3. How to instantiate Pcell with different cell name?

Stats

  • Replies 8
  • Subscribers 143
  • Views 483
  • Members are here 0

How to instantiate Pcell with different cell name?

Yuto Lau
Yuto Lau 2 days ago

Hi,

I tried to use the pcell "bussetp.il" introduced from link https://support.cadence.com/apex/ArticleAttachmentPortal?id=a1Od0000000nX1lEAE&pageName=ArticleContent. It can convert decimal input to binary output bus with defined analog voltage.

However, when I instantiated this cell multiple times in the same test bench but with different "buswidth" setting (e.g. one is with buswidth of 3 the other is with buswidth of 8). The simulation was terminated with error message as below

"ERROR (SFE-3): "netlist" 388: Cannot create subcircuit definition `bussetp' because a subcircuit with the same name has already been defined in line `365' of `netlist'. Either rename the existing subcircuit definition or remove the previous subcircuit definition, and rerun the simulation."

I found that in the netlist, cell "bussetp" was defined twice, with the same cell name and subckt name, but the netlist were different. One is with 3 pairs of vcvs, the other is with 8 pairs of vcvs as shown below.

How can I modify the SKILL script so that simulator will assign different cell name to the pcells with different configuration? Or please point me to the material about that.

Thanks and regards,

Yutao

Below is the netlist showing the pcell is defined twice but with different netlist content.

// Library name: tb_nsf
// Cell name: bussetp
// View name: schematic
subckt bussetp bus\<7\> bus\<6\> bus\<5\> bus\<4\> bus\<3\> bus\<2\> \
bus\<1\> bus\<0\> hi lo 0
parameters busvalue=0
vlo7 (mid7 0 lo 0) vcvs gain=1-((busvalue&128)>>7)
vhi7 (bus\<7\> mid7 hi 0) vcvs gain=(busvalue&128)>>7
vlo6 (mid6 0 lo 0) vcvs gain=1-((busvalue&64)>>6)
vhi6 (bus\<6\> mid6 hi 0) vcvs gain=(busvalue&64)>>6
vlo5 (mid5 0 lo 0) vcvs gain=1-((busvalue&32)>>5)
vhi5 (bus\<5\> mid5 hi 0) vcvs gain=(busvalue&32)>>5
vlo4 (mid4 0 lo 0) vcvs gain=1-((busvalue&16)>>4)
vhi4 (bus\<4\> mid4 hi 0) vcvs gain=(busvalue&16)>>4
vlo3 (mid3 0 lo 0) vcvs gain=1-((busvalue&8)>>3)
vhi3 (bus\<3\> mid3 hi 0) vcvs gain=(busvalue&8)>>3
vlo2 (mid2 0 lo 0) vcvs gain=1-((busvalue&4)>>2)
vhi2 (bus\<2\> mid2 hi 0) vcvs gain=(busvalue&4)>>2
vlo1 (mid1 0 lo 0) vcvs gain=1-((busvalue&2)>>1)
vhi1 (bus\<1\> mid1 hi 0) vcvs gain=(busvalue&2)>>1
vlo0 (mid0 0 lo 0) vcvs gain=1-((busvalue&1)>>0)
vhi0 (bus\<0\> mid0 hi 0) vcvs gain=(busvalue&1)>>0
ends bussetp
// End of subcircuit definition.

// Library name: tb_nsf
// Cell name: bussetp
// View name: schematic
subckt bussetp bus\<2\> bus\<1\> bus\<0\> hi lo 0
parameters busvalue=0
vlo2 (mid2 0 lo 0) vcvs gain=1-((busvalue&4)>>2)
vhi2 (bus\<2\> mid2 hi 0) vcvs gain=(busvalue&4)>>2
vlo1 (mid1 0 lo 0) vcvs gain=1-((busvalue&2)>>1)
vhi1 (bus\<1\> mid1 hi 0) vcvs gain=(busvalue&2)>>1
vlo0 (mid0 0 lo 0) vcvs gain=1-((busvalue&1)>>0)
vhi0 (bus\<0\> mid0 hi 0) vcvs gain=(busvalue&1)>>0
ends bussetp
// End of subcircuit definition.

  • Sign in to reply
  • Cancel
Parents
  • Andrew Beckett
    Andrew Beckett 2 days ago

    That shouldn't happen (the article was written by me, by the way). The spectre netlister should produce a unique suffix for each variant. It should look like this:

    // Library name: mylib
    // Cell name: bussetp
    // View name: schematic
    subckt bussetp_pcell_0 bus\<2\> bus\<1\> bus\<0\> hi lo
    parameters busvalue=0
        vlo2 (mid2 0 lo 0) vcvs gain=1-((busvalue&4)>>2)
        vhi2 (bus\<2\> mid2 hi 0) vcvs gain=(busvalue&4)>>2
        vlo1 (mid1 0 lo 0) vcvs gain=1-((busvalue&2)>>1)
        vhi1 (bus\<1\> mid1 hi 0) vcvs gain=(busvalue&2)>>1
        vlo0 (mid0 0 lo 0) vcvs gain=1-((busvalue&1)>>0)
        vhi0 (bus\<0\> mid0 hi 0) vcvs gain=(busvalue&1)>>0
    ends bussetp_pcell_0
    // End of subcircuit definition.
    
    // Library name: mylib
    // Cell name: bussetp
    // View name: schematic
    subckt bussetp_pcell_1 bus\<7\> bus\<6\> bus\<5\> bus\<4\> bus\<3\> \
            bus\<2\> bus\<1\> bus\<0\> hi lo
    parameters busvalue=0
        vlo7 (mid7 0 lo 0) vcvs gain=1-((busvalue&128)>>7)
        vhi7 (bus\<7\> mid7 hi 0) vcvs gain=(busvalue&128)>>7
        vlo6 (mid6 0 lo 0) vcvs gain=1-((busvalue&64)>>6)
        vhi6 (bus\<6\> mid6 hi 0) vcvs gain=(busvalue&64)>>6
        vlo5 (mid5 0 lo 0) vcvs gain=1-((busvalue&32)>>5)
        vhi5 (bus\<5\> mid5 hi 0) vcvs gain=(busvalue&32)>>5
        vlo4 (mid4 0 lo 0) vcvs gain=1-((busvalue&16)>>4)
        vhi4 (bus\<4\> mid4 hi 0) vcvs gain=(busvalue&16)>>4
        vlo3 (mid3 0 lo 0) vcvs gain=1-((busvalue&8)>>3)
        vhi3 (bus\<3\> mid3 hi 0) vcvs gain=(busvalue&8)>>3
        vlo2 (mid2 0 lo 0) vcvs gain=1-((busvalue&4)>>2)
        vhi2 (bus\<2\> mid2 hi 0) vcvs gain=(busvalue&4)>>2
        vlo1 (mid1 0 lo 0) vcvs gain=1-((busvalue&2)>>1)
        vhi1 (bus\<1\> mid1 hi 0) vcvs gain=(busvalue&2)>>1
        vlo0 (mid0 0 lo 0) vcvs gain=1-((busvalue&1)>>0)
        vhi0 (bus\<0\> mid0 hi 0) vcvs gain=(busvalue&1)>>0
    ends bussetp_pcell_1
    // End of subcircuit definition.

    Note the different subckt names.

    Have you got a custom nlSetPcellName function in your environment? Try getd('nlSetPcellName) to see if that returns non-nil (you could also try pp(nlSetPcellName) to pretty-print it). I'm wondering whether the default behaviour has been overridden.

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
  • Yuto Lau
    Yuto Lau 2 days ago in reply to Andrew Beckett

    Hi Andrew,

    Really appreciate your replay and suggestion. 

    After putting "getd('nlSetPcellName)" into CIW, it returns "funobj:nlSetPcellName". I don't quite understand this return result.

    After putting "pp(nlSetPcellName)", it returns  SKILL script for "procedure(nlSetPcellName(cv paramNames paramValues)" and "nil" at the end.

    Also, the version I am using is IC23.1-64b.ISR15.37 for your infomation.

    Regards,

    Yutao

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
  • Andrew Beckett
    Andrew Beckett 2 days ago in reply to Yuto Lau

    Yutao,

    That means that somebody has defined a custom function which prevents the unique naming of different variants (this is what happens if it returns nil). That's incorrect. 

    You should find out who defined that in your environment - it's a custom addition.

    You could add this at the end of the .cdsinit to disable it (this undefines the function):

    putd('nlSetPcellName nil)

    However, it's probably wise to find the definition of the function (which is presumably loaded from a .cdsinit or libInit.il file) and remove that incorrect definition of the function. If the function isn't defined, you would get the default unique naming per variant as I showed in my example above.

    Regards,

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
Reply
  • Andrew Beckett
    Andrew Beckett 2 days ago in reply to Yuto Lau

    Yutao,

    That means that somebody has defined a custom function which prevents the unique naming of different variants (this is what happens if it returns nil). That's incorrect. 

    You should find out who defined that in your environment - it's a custom addition.

    You could add this at the end of the .cdsinit to disable it (this undefines the function):

    putd('nlSetPcellName nil)

    However, it's probably wise to find the definition of the function (which is presumably loaded from a .cdsinit or libInit.il file) and remove that incorrect definition of the function. If the function isn't defined, you would get the default unique naming per variant as I showed in my example above.

    Regards,

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
Children
  • Yuto Lau
    Yuto Lau 2 days ago in reply to Andrew Beckett

    Hi Andrew,

    Thanks for your explanation.

    I attach the detail script below, which returns after inputting "pp(nlSetPcellName)" in CIW.

    procedure(nlSetPcellName(cv paramNames paramValues)
    let((name value
    (pcell_suffix "")
    )
    foreach((name value) paramNames paramValues
    when((name == "variant")
    (pcell_suffix = strcat(pcell_suffix "_"
    lowerCase(value)
    ))
    )
    )
    strcat((cv->cellName) pcell_suffix)
    )
    )

    After netlisting the test bench, above script grows to cover analog_cell, mcap etc, I am afraid it is generated by the PDK.

    I will talk with AE and see how to deal with it.

    Regards,

    Yutao

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
  • Yuto Lau
    Yuto Lau 2 days ago in reply to Yuto Lau

    Hi Andrew,

    Just some follow-up.

    I find nlSetPcellName function is used in a simrc file provided from PDK. I am not sure if I can remove that.

    I added "putd('nlSetPcellName nil)" in .cdsini file in my home directory. But it does NOT work.

    Thanks and regards,

    Yutao

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
  • Andrew Beckett
    Andrew Beckett 2 days ago in reply to Yuto Lau

    Hi Yutao,

    If it's defined in the .simrc or generated dynamically, then overriding this in the .cdsinit won't work.

    This is a bug in the PDK. It is assuming that the only pcells are those in the PDK and from the code above it relies on having a parameter called variant which is fairly unlikely. There will be other PCells that are incorrectly netlisted too, I think, if this happens.

    I think there is an argument that Virtuoso should treat a return value of nil as using the default naming that would be otherwise used. I will ask R&D about that - but the right thing to do here anyway is to get the PDK provider to fix this. It's clearly wrong what is being done right now.

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
  • Yuto Lau
    Yuto Lau 1 day ago in reply to Andrew Beckett

    Hi Andrew,

    Really appreciate your support. I learn quite a lot on SKILL along the way.

    It turns out that it is our CAD team use the function to unify subckt format.

    They suggest me to include "bussetp" into a local .simrc file.

    I did it and now I can see different subckt name.

    But I think this is a temporary solution. 

    For long term, is it better to have default subckt naming mechanism still working even after user specify customize subckt naming. 

    What do you think?

    Thanks and regards,

    Yutao

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel
  • Andrew Beckett
    Andrew Beckett 10 hours ago in reply to Yuto Lau

    Yutao,

    It's not clear how you can have the default naming mechanism in place if you've explicitly overridden it to have a different naming convention.

    What I've proposed to R&D (via CCR #3216014) is that if the function returns nil, it should use the default naming (right now it use the cell name with no uniquification). Another idea is to provide some means to limit the nlSetPcellName to specific libraries. Anyway, this would need to be considered for a future release.

    In the example you gave above, it would return strcat((cv->cellName) pcell_suffix) where pcell_suffix is "", so it's explicitly returning the cellName. That's pretty hard to determine that it shouldn't do this (yes, maybe we could special case against the function returning the cellName unaltered, but there's no guarantee that the returned name is not unique. 

    I think the implementation of the nlSetPcellName in the case from your CAD team looks questionable to me, and I think they should fix it.

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Sign in to reply
    • Cancel

Community Guidelines

The Cadence Design Communities support Cadence users and technologists interacting to exchange ideas, news, technical information, and best practices to solve problems and get the most from Cadence technology. The community is open to everyone, and to provide the most value, we require participants to follow our Community Guidelines that facilitate a quality exchange of ideas and information. By accessing, contributing, using or downloading any materials from the site, you agree to be bound by the full Community Guidelines.

© 2025 Cadence Design Systems, Inc. All Rights Reserved.

  • Terms of Use
  • Privacy
  • Cookie Policy
  • US Trademarks
  • Do Not Sell or Share My Personal Information