Printing Examples: Difference between revisions

From Flooxs
Jump to navigation Jump to search
(added examples of how to print.1d to txt files and to manipulate strings from print.1d in tcl)
 
Line 42: Line 42:
   
   
  Grid1D
  Grid1D
  [[DiffuseCommand | diffuse]] time=60 temp=1100 wet
  diffuse time=60 temp=1100 wet


The above two commands grow an oxide that will be used in the remaining examples.
The above two commands grow an oxide that will be used in the remaining examples.
   
   
  set top [ [[interfaceCmd | interface]] oxide /gas]
  set top [ [[interfaceCmd | interface]] oxide /gas]

Latest revision as of 15:50, 14 June 2020

Junction Depth and Layers

Integrate Dose and Find Junction

Grid1D

sel z = {1.0e18*exp(-x * x / 0.01) - 1.0e15}

layers

The above deck initializes the grid with a default one dimensional structure. The second command selects as the plot variable a Gaussian profile minus a background doping. The layers command integrates the selected variable and reports zero crossings. The output is:


	Top          Bottom        Integral    Material
0.00000e 00     2.62905e-01     8.83423e 12    Silicon
0.262905e-1     5.00000e 01    -4.97191e 12    Silicon

The top layer has positive sign and is silicon. The total integrated dose is 8.8e12 in this layer. From 0.26um down, the selected variable is negative. To a depth of 50um, the integrated value is about 5e12.


puts "The Junction Depth is [  interpolate silicon z=0.0]"

The above command uses the interpolate command to locate the zero crossing and report the value. For the structure above, the output is:


The Junction Depth is 2.629046e-01

Additional processing can be performed using the print.1d command.


set dep 0
foreach f [print.1d] {
    set x [lindex $f 0]
    set y [lindex $f 1]
    if {$y > 0.0} {incr dep}
}
puts $dep

Returns 227, the number of grid points that have a positive selected variable value. Other operations can be performed and are limited only by the tcl capabilities.

Interface Manipulations

Grid1D
diffuse time=60 temp=1100 wet

The above two commands grow an oxide that will be used in the remaining examples.

set top [  interface oxide /gas]
set bot [  interface oxide /silicon]
puts "Thickness is [expr $bot - $top]"

The interface commands return the location of the interface. Since we can independently locate both the top and bottom, these can be subtracted to obtain the total oxide thickness. The total oxide thickness is 0.673907.


sel z = {$Oxidant}
layers

These two commands sel the oxidant and then integrate it across all material layers. The output is:


	 Top          Bottom        Integral    Material
-3.68495e-01     3.05413e-01     1.12857e 15    Oxide
 3.05413e-01     5.00000e 01     2.67928e 12    Silicon

The oxide layer thickness is 0.674, and the dose of oxidant contained in the layer is 1.1e15. The silicon has been consumed as expected.

Printing to a txt file

You can use tcl to open up a channel to a file for writing (w) or appending (a). (You can also open up a file for reading (r), and use the "gets" command for that). The "open" function returns the channel name assigned by your computer, which you should store in a variable so you can access the channel later:

set ch [open filename.txt w]

In the line above, "set" is a tcl command which sets a variable named "ch" to whatever the command inside the brackets evaluate to, i.e. to whatever "[open filename.txt w]" evaluates to (this is what square brackets mean in tcl). Inside the brackets, "open" is a command which opens filename.txt for writing "w" and returns the channel name that your computer chooses (probably something like "file11"). Once this channel is open, and pointing to filename.txt, you can put anything in it.

puts $ch "Hello World!"
puts $ch [print.1d];# make sure you've selected something before trying to print.1d
puts $ch "$myvar1\t$myvar2"

At the end of everything, you MUST close the channel to finish writing to it. This is like "safely eject drive" before removing your flash drive on a windows machine.

close $ch

You can use scripting to automatically organize your files in directories and by naming them with variable names from floods:

set ch_storage [open TXT/$dimension/$txtfilename a]
     puts $ch_storage "$Rd\t$Nit_10"
close $ch_storage

FLOODS can have some unwanted formatting in the print.1d, or the layers command that you may not want in your text file. You can print.1d to a variable first, then manipulate that variable to get it into the format you want, and then write to a text file. For example, the procedures below are simple (i.e. working but not the most clever or efficient or universal) examples that get rid of a specified character in a string (KillChar), clean a print.1d string for writing into a text file without brackets (Clean2Txt), or join multiple txt files in 2-column format into one text file with "x, y1, y2, ..., yn" format if x is the same in the files you want to join:

#------------------------------------------------------------------------
# Kill Char gets rid of any $char's in you $str
#------------------------------------------------------------------------
proc KillChar {str char} {
   while {[string first $char $str] >= 0} {
	set str [string replace $str [string first $char $str] [string first $char $str]]
   }
   return $str
}
#set str [KillChar $str \ ];# example usage, kills spaces
#set str [KillChar $str m];# example usage, kills the letter m
#puts $str;#to see it


#------------------------------------------------------------------------------------------
# Clean2Txt prints a cleaned floods variable (eg DevPsi) into filename.txt, tab-deliniated
#------------------------------------------------------------------------------------------
proc Clean2Txt {FloodsVar filename col1 col2} {
   #Create a temporary string we can chop up
   	set tmp $FloodsVar
   	set filename_txt [open $filename.txt w]
   	#puts "We're going to take this string and write it cleanly into a file, $filename.txt\n$tmp"
           
   	set tmp [KillChar $tmp \ ];#first kill all white spaces
   	set lastline_yn 0;# initialize this flag: it is not the last line of the string
   	set cleaned_list blankline
   	for {set i 0} {$lastline_yn == 0} {incr i} {
	    eval set stri_name str$i;#create a name for your new string: str0, str1, str2, etc...
	    set $stri_name $tmp; eval set stri_value \$str$i;#create a value in your new string
	    set brace_index [string last \{ $tmp];# finds last open brace
	    set lastline_yn [string equal $brace_index 0];# 1=y, 0=n;# if last open brace is at i0, then it's the last line
   	
   	#if this not the last line, chop off lines 2 through end
   	    if {$lastline_yn == 0} {
	    	set newline_index [string first \n $tmp];# find the first newline index
	        set $stri_name [string replace $tmp $newline_index end]; eval set stri_value \$str$i;#chop from that index
   	    }
   	#get rid of last column
	    set end_of_line [string last \t $stri_value];# finds the last tab
	    set $stri_name [string replace $stri_value $end_of_line end]; eval set stri_value \$str$i
	#get rid of left bracket
	    set $stri_name [string trimleft $stri_value \{]; eval set stri_value \$str$i;# here we must eval again to update
	#finally puts the line into the txt file:
	    #puts "This is your final string $i that will goin into $filename.txt:\n$stri_value"
	    if {$i == 0} {puts $filename_txt "$col1	$col2"}
	    if {$i != 0} {puts $filename_txt "$stri_value"};# a newline is written automatically in your txt file
	#make the new tmp (deleating the first line you just wrote to the txt file)
	    set tmp [string replace $tmp 0 $newline_index]
   	}
   	puts $filename_txt "$filename\t$filename"
   close $filename_txt
   return [puts "check $filename.txt to see your cleaned table\n\n"]
}
#example of how to call:
#sel z=Hydrogen
#set H2 [print.1d y.v=0] 
#Clean2Txt $H2 H2 "x(@y=0)" "H2_log";# makes H2.txt with cleaned Hydrogen profile at y=0
#--------------or-----------------------#
#Clean2Txt $str str_name col1 col2
#-------------or------------------------#
#sel z=[expr {-Vg}]
#Clean2Txt [print.1d y.v=0] IV.Vg_is_$Vgg Vdd Vgg
#Join2Txt IV.1 IV.2 IV.all
proc Join2Txt {file1 file2 filename} {
   #if one of the files is "null", just copy the actual file to filename
   if {[file exists $file1.txt] ^ [file exists $file2.txt]} {
	if {[file exists $file1.txt]} {file copy $file1.txt $filename.txt}
	if {[file exists $file2.txt]} {file copy $file2.txt $filename.txt}
   
   #if not, then if both files exists, join them
   } elseif {[file exists $file1.txt] && [file exists $file2.txt]} {
   	#first test if you need to append just a new y, or both x and y
	file copy $file1.txt bk1.txt
	file copy $file2.txt bk2.txt
	set bk1_txt [open bk1.txt r]
	set bk2_txt [open bk2.txt r]
	while {([eof $bk1_txt] || [eof $bk2_txt]) == 0} {
		set xfrom1 [gets $bk1_txt]
		set xfrom2 [gets $bk2_txt]
		set xfrom1 [string replace $xfrom1 [string first \t $xfrom1] end]
		set xfrom2 [string replace $xfrom2 [string first \t $xfrom2] end]
		if {$xfrom1 eq $xfrom2} {set appendboth_yn 0}
		if {$xfrom1 ne $xfrom2} {
			if {![eof $bk1_txt] && ![eof $bk2_txt]} {
				set appendboth_yn 0; break
			} else {set appendboth_yn 1; break}
		}
	}
	close $bk1_txt
	close $bk2_txt
	file delete bk1.txt
	file delete bk2.txt
	#this section actually writes the new columns
	set file1_txt [open $file1.txt r]
	set file2_txt [open $file2.txt r]
	set tmp_txt [open tmp.txt w]
	set linefrom1 [gets $file1_txt]
	set linefrom2 [gets $file2_txt];# appends both x and y
	if {$appendboth_yn == 0} {set linefrom2 [string replace $linefrom2 0 [string first \t $linefrom2]]};#just x
	while {([eof $file1_txt] || [eof $file2_txt]) == 0} {
	    #add something here to account for collumns of different lengths	
	    append linefrom1 "\t$linefrom2"
	    puts $tmp_txt $linefrom1
	    set linefrom1 [gets $file1_txt]
	    set linefrom2 [gets $file2_txt]
	    if {$appendboth_yn == 0} {set linefrom2 [string replace $linefrom2 0 [string first \t $linefrom2]]}
	}
	close $tmp_txt
	close $file1_txt
	close $file2_txt
	if {[file exists $filename.txt]} {file delete $filename.txt}
	file rename tmp.txt $filename.txt
   #if neither of the files exist, print an error
   } else {
   puts "INPUT ERROR, files DNE"
   }
}
#Example:
#Clean2Txt $str1 file1
#Clean2Txt $str2 file2
#Join2Txt file1 file2 str1and2
#Example:
#Join2Txt file1 null str1alone