• 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 Design
  3. Error loading OCEAN scripts in nograph mode - strcat: argument...

Stats

  • Locked Locked
  • Replies 4
  • Subscribers 126
  • Views 2917
  • Members are here 0
This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

Error loading OCEAN scripts in nograph mode - strcat: argument #1 should be either a string or a symbol (type template = "S") - nil

shridmaster
shridmaster over 1 year ago

strcat: argument #1 should be either a string or a symbol (type template = "S") - nil

This error seems to come up frequently when trying to run very simple scripts, and now it's come up in multiple scenarios and I'm wondering if there's some larger issue with how our system is installed. Virtuoso version number is IC6.1.8-64b.500.34.

I'm attempting to create scripts to run simulations for parametric sweeps. I created a schematic, set it up in ADE L, and exported it to a .ocn file. If I run that file with load("oceanScript.ocn") from the GUI CIW it works just fine.

To turn it into a parametric sweep, I edit the file and wrap the simulation as a procedure and then run it in a loop. First off, this alone ran into issues, where running it in a foreach loop gives me that strcat error after the first iteration (i.e the simulation runs once, then in the second loop it does not and gives that error), but running it in a for loop works fine. I cannot for the life of me figure out why a foreach loop and for loop would give problems, and where in the code this strcat error is actually happening. I wrote about how I set up this script on my blog, it links to a github repo with the code for this: https://positivefb.com/gm-id-methodology/

I now want to be able to run a similar script from the terminal (to avoid keeping the device testbench open in a window and cluttering things up). Things like noise analysis and process corners would take an immense amount of time to batch run, so I'd like to run smaller more limited simulations for specific dimensions or conditions as I need. So to test it I ran the previous script, which runs fine from the GUI, in the nograph version with the following command

> virtuoso -64 -nograph -restore termtest.ocn -log termtest.log

That gave me the same strcat error. Doing load("termtest.ocn") from the GUI works just fine though. The script doesn't open any GUI elements, it simply runs the sim, outputs to an outfile, then combines it with a CSV created in the previous iteration. I've also tried putting the load command into a text file and running the text file in nograph mode, like was suggested in another thread.

What am I doing wrong here, why does this error constantly come up in so many situations? Thanks in advance!

Script here:

simulator( 'spectre )
design( "/home/sambady/simulation/gmid_dgnfet/spectre/schematic/netlist/netlist" )
resultsDir( "/home/sambady/simulation/gmid_dgnfet/spectre/schematic" )
modelFile(
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "mainlib")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "FET_tt_pre")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "Res_nom")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "MOSCap_nom")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "APMOMCap_nom")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "MIMCap_nom")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "Ind_nom")
'("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "DioCap_nom")
)

;Convert constant variables to waves. Final wave will be length of refwave
procedure(
vartowave(var refwave)
varwave0 = ((refwave+1) * var) ;+1 to avoid any divide by zeros
varwave1 = (varwave0 / (refwave+1))
varwave1 ;return variable as a wave with length of refwave
)

;;;;;;;;;;;;;
;Procedure wrapper for simulation generated by ADE
;;;;;;;;;;;;;
procedure(
simsweep( outputfile length_in vsb_in vgs_in )
analysis( 'dc ?saveOppoint t ?param "vds" ?start "10m" ?stop "2.5" ?step "10m" )
desVar( "F" 5 )
desVar( "L" length_in )
desVar( "vds" 1 )
desVar( "vgs" vgs_in )
desVar( "vsb" vsb_in )
desVar( "W" 10u )
envOption(
'analysisOrder list("dc")
)
saveOpPoint( "/MN0" ?operatingPoints "ids vgs vds vbs vgd vth vdsat gm gds gmbs cjd cjs cgg cgd cgs cgb cdg cdd cds cdb csg csd css csb cbg cbd cbs cbb ron id pwr gmoverid ueff vsb gmb vgt vdss self_gain rout vearly ft region" )
temp( 27 )
run()
print("RUNDONE")
vgs = OS("/MN0" "vgs")
vds = OS("/MN0" "vds")
vsb = OS("/MN0" "vsb")
gm = OS("/MN0" "gm")
Id = OS("/MN0" "ids")
gmId = (gm / Id)
Jd = (Id / VAR("W"))
cgg = OS("/MN0" "cgg")
wt = (gm / cgg)
gds = OS("/MN0" "gds")
Avo = (gm / gds)
FoM = (Avo * wt)

length_wave = vartowave( VAR("L") vds ) ;convert length to wave so it can be a filterable column in the data
width_wave = vartowave( VAR("W") vds )

ocnPrint( ?output outputfile ?numberNotation 'engineering ?numSpaces 4 length_wave width_wave vgs vsb gm Id gds cgg gmId Jd wt Avo FoM) ;output DC sweep to temp file
)

resultscsv = outfile( "./dgnfet_gmid.csv" "w") ;Create empty CSV
close(resultscsv)

;;;;;;;;;;;;;
;Create lengths, vsb, and vds to iterate through. Modify this however you want for whatever you need
;;;;;;;;;;;;;
len_list = list( 280e-9 )
for( i 6 7
next = 50e-9 * i
len_list = cons( next len_list )
)
vsb_list = list( 0 ) ;I don't particularly care about body effect right now, I generally neglect it in my designs
vgs_list = nil
for( i 1 2
next = 50e-3 * i
vgs_list = cons( next vgs_list )
)

;;;;;;;;;;;;;
;Loops iterating through each variable, running sim, and saving to CSV. This is the meat of it
;;;;;;;;;;;;;

for( k 1 length(vsb_list)
for( j 1 length(len_list)
for( i 1 length(vgs_list)
tempout = outfile( "./adel_out.out" "w")
simsweep(tempout nthelem(j len_list) nthelem(k vsb_list) nthelem(i vgs_list)) ;simulation run and saved to temporary output file
close(tempout)

system(sprintf(nil "sed -i '2 r ./test.csv' adel_out.out")) ;existing CSV inserted into output file below header
system(sprintf(nil "sed -i '/^[[:space:]]*$/d' adel_out.out")) ;empty lines deleted
system(sprintf(nil "sed -i '1d' adel_out.out")) ;header deleted
system(sprintf(nil "rm -rf ./test.csv")) ;old CSV deleted
system(sprintf(nil "mv ./adel_out.out ./test.csv")) ;new output file renamed as CSV
)
)
)
;;;;;;;;;;;;;

Relevant portion of the log file:

o Simulation started at: 2:13:52 PM, Wed Mar 20, 2024, ended at: 2:13:53 PM, Wed
\o Mar 20, 2024, with elapsed time (wall clock): 201 ms.
\o spectre completes with 1 error, 0 warnings, and 0 notices.
\o Cannot start up spectre.
\o The specified cds.lib while running the simulation via ADE no longer exists.
\o In absence of the design information, name mapping between extracted names and schematic names won't be carried out.
\o WARNING (OCN-6040): The specified directory does not exist, or the directory does not contain valid PSF results.
\o Ensure that the path to the directory is correct and the directory has a logFile and PSF result files.
\o "RUNDONE" You must openResults() on a valid psf directory before
\o using this command. Make sure your openResults() worked.
\o Use ocnHelp('results) for more information.
\o You must openResults() on a valid psf directory before
\o using this command. Make sure your openResults() worked.
\o Use ocnHelp('results) for more information.
\o You must openResults() on a valid psf directory before
\o using this command. Make sure your openResults() worked.
\o Use ocnHelp('results) for more information.
\o You must openResults() on a valid psf directory before
\o using this command. Make sure your openResults() worked.
\o Use ocnHelp('results) for more information.
\o You must openResults() on a valid psf directory before
\o using this command. Make sure your openResults() worked.
\o Use ocnHelp('results) for more information.
\o You must openResults() on a valid psf directory before
\o using this command. Make sure your openResults() worked.
\o Use ocnHelp('results) for more information.
\e *Error* strcat: argument #1 should be either a string or a symbol (type template = "S") - nil
\e *Error* load: error while loading file - "termtest.ocn" at line 99

  • Cancel
  • Andrew Beckett
    Andrew Beckett over 1 year ago

    The issue is as a result of the fact that spectre failed to run (probably for a reason further up the log file):

    \o spectre completes with 1 error, 0 warnings, and 0 notices.
    \o Cannot start up spectre.

    Because of this, the OS() function fails (and doesn't fail very gracefully). If you add _stacktrace=50 to your script, you'll see that it's the OS() call that's failing, but that's not surprising if there's no simulation result.

    I saw exactly the same problem when I had a simulation that wouldn't run (I missed out the model files needed for my example) using your script.

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Cancel
  • shridmaster
    shridmaster over 1 year ago in reply to Andrew Beckett

    Andrew,

    Thank you, I've found the source of error. There is an error further up in the log file

    \o Error found by spectre during circuit read-in.
    \o ERROR (SFE-23): "input.scs" 13: The instance `MN0' is referencing an
    \o undefined model or subcircuit, `dgnfet'. Either include the file
    \o containing the definition of `dgnfet', or define `dgnfet' before
    \o running the simulation.

    I found something interesting, which is that if I close Virtuoso, open it in the GUI, and run the simple simulation script, it also fails with the same error. However, if I open the cell and run the sim in ADE, the script now works. The source of error may be in how it loads the libraries, particularly the path to them. This is how the script does it:

    modelFile(
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "mainlib")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "FET_tt_pre")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "Res_nom")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "MOSCap_nom")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "APMOMCap_nom")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "MIMCap_nom")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "Ind_nom")
    '("$SPECTRE_MODEL_PATH/design_wrapper.lib.scs" "DioCap_nom")
    )

    I have access to a school server, completely separate from this one, and the virtuoso -nograph works fine, and I looked and indeed the modelfile path is entirely written out.

    On my work setup, "SPECTRE_MODEL_PATH" is only created when opening the schematic, confirmed in the log. So I replaced that string with the actual full path and it works!

    • Cancel
    • Vote Up 0 Vote Down
    • Cancel
  • Andrew Beckett
    Andrew Beckett over 1 year ago in reply to shridmaster

    My guess is that something in the PDK (maybe in the libInit.il of the technology library) is doing a setShellEnvVar("SPECTRE_MODEL_PATH" "/some/directory"). That wouldn't be triggered if your OCEAN script is using design("/path/to/netlist"). If instead it used design("lib" "cell" "view") then it probably would get triggered (that would trigger the netlisting to be done as well).

    Alternatively, you could explicitly call setShellEnvVar() at the beginning of your OCEAN script to set the path appropriately?

    Andrew

    • Cancel
    • Vote Up 0 Vote Down
    • Cancel
  • shridmaster
    shridmaster over 1 year ago in reply to Andrew Beckett

    This is excellent information, exactly what I needed. I'll give this a try, thank you so much for your help!

    • Cancel
    • Vote Up 0 Vote Down
    • 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