#81923 - 2002-03-09 08:25 AM
KiXtart Starter's Guide
|
Kdyer
KiX Supporter
Registered: 2001-01-03
Posts: 6241
Loc: Tigard, OR
|
KiXtart Starter's Guide.
Posted with permission.
Thanks to Bryce!
MS-Word Version of this document is available within this archive.
KIX Starters Guide
This is a work in progress 9/21/2000 9:40 AM……..
1. An introduction to KIX A. "Hello World!"
2. How to run your KIX Script A. Choose your OS Please…. 1. Win9x 2. NT B. From a Command line C. From a batch File 1. Advanced Logon.bat D. The netlogon folder 1. The KIXRPC Service. 2. How to get all your Domain controller's in a row a. The Microsoft way. b. Just Copy it by hand.
3. Basic SYNTAX A. IF … Then / Select Case B. Nested C. $Variables
4. Macros A. @error @serror B. Other helpful macros
5. Return Codes A. How to use them B. Error checking
6. This piece of @#&^! Won't run! A. BAD CODE!!! BAD CODE!!! Now go stand in the corner!
7. Basic Logon Script
1. An introduction to KIX
KixTart is a 32bit-script language that many people use as a logon script for their NT networks. It also can be thought of as a batch file on steroids, having many uses beyond a mere logon script.
The purpose of this document is to lend a helping hand to a newcomer, with tip and tricks that will help you use Kix for you own personal needs. It is meant to complement the manual "Kix95.doc" not replace it.
I strongly suggest that you print and place the Kix manual in a binder and keep it near your desk at all times!
Code/batch files will be designated with a beginning --------start-------- and an ending --------end-------- Anything between these two markers will be KIX code / Batch File.
Example: ;--------start-------- Kix code here … … ……. ;-------- end -------
A. "Hello World!"
First lets do a simple Kix script, to give you an Idea how easy this script language can be.
Run a DOS prompt. Go to the directory where you have the KIX32.EXE file located. And type this
notepad hello.kix
this will launch Notepad.exe and it will ask you if you want to create a new file, answer yes.
Inside Notepad type the following
;--------start Hello.kix-------- "Hello World" ;-------- end Hello.kix--------
save "hello.kix" and close notepad.
At the DOS prompt type
Kix32 hello
You will get the following display.
U:\>kix32 hello
Hello World U:\>
Congratulations! You have just ran you first KIX code.
2. How to run your KIX Script
There are a number of ways to run your Kix script. In the following chapter we will go into detail on the command line, from a batch file, and how it works running it for a logon script.
A. Choose your OS Please….
1. Win9x To run Kix under Windows 95, 98 you need to have the following files.
kix32.exe kx95.dll kx16.dll kx32.dll
Also you will need the KIXRPC service running for all of the functions to work in Win9x, you can find more about this service in 2.D.1
2. NT To run KIX under Windows NT, you need the following files.
kix32.exe
B. From a Command line One of the best ways to run Kix from a command line is to copy the necessary files in to the system path.
For Win9x computers I prefer the "c:\windows\system". For NT computers the "c:\winnt\system32" is a good location.
Once the proper files are copied to the proper location all you have to do to run KIX is
Kix32 script.kix
By default Kix automatically looks for the following file extensions .kix and .scr, so typing
Kix32 script
will work as long as the script is in the local directory.
C. From a Batch File. Running kix from a batch file is the most preferred way of running a login script.
A typical login.bat file might look like this
--------start-------- %0\..\kix32 %0\..\logon.kix -------- end --------
1. Advanced Logon.bat
The following batch file is what the author uses to run his login.kix script. It copies the necessary kix32.exe and related DLL's (depending on OS) to the proper system directory. This not only places the kix32.exe in the path, but increases the run time of the logon script for slow wan connections.
::--------start AdvancedLogon.bat-------- @Echo Off
CLS ECHO Verifying / Updating Script Software Installation, Please Wait...
IF "%OS%" == "Windows_NT" GOTO WinNT
c:\windows\command\XCOPY %0\..\KIX32.EXE %WINDIR%\SYSTEM\ /D /H /I /R /V > NUL c:\windows\command\XCOPY %0\..\KX16.DLL %WINDIR%\SYSTEM\ /D /H /I /R /V > NUL c:\windows\command\XCOPY %0\..\KX32.DLL %WINDIR%\SYSTEM\ /D /H /I /R /V > NUL c:\windows\command\XCOPY %0\..\KX95.DLL %WINDIR%\SYSTEM\ /D /H /I /R /V > NUL ECHO Loading Logon Script, Please Wait... %WINDIR%\SYSTEM\KIX32.EXE %0\..\logon.kix GOTO End
:WinNT XCOPY %0\..\KIX32.EXE %WINDIR%\SYSTEM32\ /D /H /I /R /V > NUL ECHO Loading Logon Script, Please Wait... %WINDIR%\SYSTEM32\KIX32.EXE %0\..\logon.KIX GOTO end
:End ::-------- end AdvancedLogon.bat--------
D. The NETLOGON folder
In order for a logon script to work the client will make a connection to a Domain Controllers \\server\netlogon share. You will keep all of your Kix EXE and DLL's in this folder.
1. The KIXRPC Service.
In order to use some of the more advanced macro features in a win9x environment, you will need the Kixrpc service running on the domain controller that the user is currently logging in to.
The Kix Manual has excellent instructions on how to install this service on to your Domain Controllers.
2. How to get all your Domain Controller's in a row.
In order for a person to logon to your network they will first make a connection to either a PDC or a BDC (Domain Controllers).
Since the possibility exists for user A to logon using the PDC while user B is logging using the BDC, you must have the current logon script on ALL Domain controllers.
a. The Microsoft way.
You can use Directory replication to push out the same logon script from the PDC to all BDC's. This is the preferred method for a LARGE domain and is really beyond the scope of this document. You can find more on this in MS knowledge base article #Q101602
b. Just copy it by hand.
Now if your number of Domain Controllers is small (I will leave it up to the reader to define what small is), you can just copy the current logon script to all domain controllers by hand.
Here is a Kix script that I use to do this for me.
;--------start repl.kix-------- break on cls
;----------------------------------------------------------------------------- ; login script replication to all domain controllers ; ; Please create a file "controllers.txt" and place it in the same directory ; as this script. the contents of "Controllers.txt" should be like the ; following ; ; \\server1 ; \\server2 ; \\server3 ; \\server4 ; ; Each server is a Domain Controller ; ; You can share the "%systemroot%\system32\repl\import\scripts" on each domain ; controller and change $target to point to that share if one or more of your ; Domain controllers are not using the WINNT directory, or if not installed ; to the c: ; ; You will also need the program xnet.exe in the current directory. It came ; with the kix32 program. ;-----------------------------------------------------------------------------
$file = "Controllers.txt" $logonscript = "logon.kix" $logonbat = "logon.bat" $target = "\c$\winnt\system32\repl\import\scripts"
;----------------------------------------------------------------------------- ; DO NOT EDIT BELOW THIS LINE ;-----------------------------------------------------------------------------
$q = open(1,$file) if @error <> 0 ? "List of servers was not found!!" ? "PROGRAM ENDING" ? ? @serror + ' "$file"' exit endif
gosub Kix_UpGrade
$server = readline(1) while @error = 0 ? "============================================================================" ? "Copying $logonscript & $logonbat to $server$target"
copy $logonscript $server + $target if @error <> 0 ? "There was an error copying $logonscript to $server$target" ? @serror else ? " $logonscript copied OK" endif
copy $logonbat $server + $target if @error <> 0 ? "There was an error copying $logonbat to $server$target" ? @serror else ? " $logonbat copied OK" endif
if $upgrade = "yes" ? ? "Upgrading Kix32 on $server$target" copy "kix32.exe" $server + $target if @error <> 0 ? " There was an error copying KIX32.EXE to $server$target" ? " @serror" else ? " kix32.exe copied OK" endif copy "kx*.dll" $server + $target if @error <> 0 ? " There was an error copying kx*.dll to $server$target" ? " @serror" else ? " ki*.dll copied OK" endif ? " Stoping the kxrpc service on $server" shell "%comspec% /c xnet stop $server\kxrpc > nul" copy "kxrpc.exe" $server + $target if @error <> 0 ? " There was an error copying kxrpc.exe to $server$target" ? " @serror" else ? " kxrpc.exe copied OK" endif ? " Starting the kxrpc service on $server" shell "%comspec% /c xnet start $server\kxrpc > nul" endif $server = readline(1) loop exit
;---------------------------- :Kix_UpGrade ;----------------------------
:wrong ? "Would you like to update Kix32 at this time? (y/n)" get $yn select case lcase($yn) = "y" $upgrade = "yes" case lcase($yn) = "n" $upgrade = "no" case 1 goto wrong endselect return ;-------- end repl.kix[/code]
3. Basic SYNTAX
SYNTAX is very important when it comes to writing your Kix script. I personally have (almost) pulled hair out trying to get a program to work, just to find the I left a " out from the 3rd line of a 30 line script. But if you follow these simple rules you should be ok.
Rule 1
If the command you are typing requires an ending argument go ahead and type it in right after you type the command
Example: shell " " Then just come back in fill in what you are shelling to. Example: substr( ) Example: if $x = $y ;code goes here endinf
the 3rd example is very important! If you are going to use an IF … THEN routine go ahead and type the ENDIF on the next line, and just go back and fill in the rest of the code. Doing it this way you will have less of a chance of forgetting the all important closing argument!
Rule 2
Use tabs and spaces, to bring some order to your code. Since Kix32 is a free-format language, tabs and spaces will not bother how your code performs. Lets take the above IF .. THEN statement as an example.
IF $x = $y ? "hey guess what! X = Y" ? "I bet that you didn't know that….." ENDIF
By preceding everything inside the IF … THEN statement with a tab, we can tell just by glancing at the code that the two print line lines are inside the IF … THEN.
Rule 3
The comment is your friend! Don't be afraid to use ; in your code.
IF $x = $y ;checking to see if $x and $y are the same if they are do nothing, if not…… ;they are the same, do nothing ELSE ? "Look's like X and Y are not the same" ENDIF
The more that you can write down that documents your train of thought (or lack of) the easier it is to spot simple logic mistakes.
A. IF … THEN / SELECT CASE
Using IF .. THEN and SELECT CASE are excellent ways to write logic gates into your code. You have already seen some basic examples of the IF … THEN statement, let go in to more detail.
IF … THEN
When you are doing a IF statement in Kix32 you are really doing a simple test of 1 variable against another.
Example 1: IF $a = 1 "$$a = 1" ENDIF
In Example 1, you are testing to see if $a = 1, if this is found to be true then it will print out "$a = 1"
(the use of double $$ is necessary, otherwise Kix32 will want to print the value of $a and not "$a". This is same for @ and % )
Many times you will be testing the return code of another command, one of the more common occurrences of this is the ingroup() command.
Example 2: IF INGROUP("Domain Users") = 1 ? "this person is in the Domain Users group" ENDIF IF INGROUP("Domain Admins") = 1 ? "this person is in the Domain Admins group" ENDIF
(It has been my experience that domain groups are case sensitive)
In this Example, we are testing to see what the return code for ingroup() will be. To get a better understanding of what I mean run the following.
;--------Start IF_ingroup.kix-------- BREAK ON CLS
$Return_Code = INGROUP("Domain Users") ? 'The return code for "INGROUP("Domain Users")" is "$Return_Code"' ;-------- end IF_ingroup.kix--------
If everything went ok, and you are a member of the Domain Users group the return code would = 1.
You can clearly see that the IF… statement works by comparing 2 variables against each other, if the outcome is true then Kix will run the next set of commands until an ENDIF is reached.
You can also tell an IF… statement to do something if the outcome is false by using the ELSE command.
;--------Start IF_ELSE.kix-------- $a = "thing1" $b = "thing2" IF $a = $b ? "$$a = $$b" ;if $a = $b is true then this line will be executed ELSE ? "$$a doesn't = $$b" ;if $a = $b is false then this line will be executed ENDIF ;-------- end IF_ELSE.kix--------
Let take this one step further. Since we are comparing two variables against each other and checking to see if the outcome is false or true, you can use any operator, you have all ready seen the =, but you may use any of the following.
< Less than > Greater Than = Equal <> NOT Equal <= Less then or Equal to >= Greater then or Equal to AND OR
Here are a few examples
1. If $a > $b ;$a is greater than $b endif
2. IF $a <> $b ; $a doesn't = $b ENDIF
3. IF $a = $b AND $c = $d ;this is only true if $a equals $b AND $c equals $d ENDIF
SELECT … CASE
Just like IF … THEN you can use SELECT … CASE to form logic gates inside your script.
Unlike IF … THEN once a CASE is found to be true inside a SELECT … CASE, all other CASE's are ignored in the current select case.
EXAMPLE:
SELECT CASE $a = 1 ? "hey look at that $$a = 1" CASE $a = 2 ? "hey look at that $$a = 2" CASE $a = 1 ; $a = 1 here too, but since this case is all ready ; been true at the very first case, you will never see this case come true. CASE 1 ;by placing "CASE 1" at the end of a SELECT … CASE this means that since ;all other CASE's were false this one will be true. ENDSELECT
That makes SELECT … CASE very good for a situation where you have 1 single variable that may have several possible values to it, but you only want it to react to a certain value and once one is found ignore all others.
EXAMPLE:
;--------Start select.kix-------- $test = 1
SELECT Case $test = 1 $test = 2 Case $test = 2 $test = 1 ENDSELECT
? $test ;-------- end select.kix--------
what does $test equal at the end of this script? If you say 2, you are correct
lets walk through this script
Line 1 $test = 1 we set the variable $test to = 1
Lines 3 - 8. then call a SELECT … CASE.
The very first CASE (line 4) is true so we then set $test to equal 2
Remember since this is a SELECT … CASE once we have found a CASE that is true we ignore all other CASE's. So having reset $test to equal 2 we then end the SELECT … CASE so the 2nd case on line 6 never has a chance to be true..
As in the IF …THEN statement you can use the following operators to prove a CASE true.
< Less than > Greater Than = Equal <> NOT Equal <= Less then or Equal to >= Greater then or Equal to AND OR
B. Nested SYNTAX
Nested means that you are calling another IF .. THEN / SELECT … CASE from inside a IF .. THEN / SELECT … CASE.
Are you confused yet !!!
You can nest IF .. THEN / SELECT … CASE as deep as you want, or until your mind screams NO MORE!!! lets do a few Examples.
EXAMPLE 1: $test1 = 1 $test2 = 2 IF $test1 = 1 IF $test2 = 2 ? "this line will only print if $$test1 = 1 and then $$test2 = 2" ELSE ? You were close! $$test1 = 1, but $$test2 doesn't = 2" ENDIF ELSE ? "$$test1 doesn't even equal 1 so we were never even able to test to see what $$test2 equaled." ENDIF
You can even mix and match IF … THEN with SELECT … CASE. The following Example is one that I find useful.
;--------Start drive_mapping.kix-------- SELECT CASE @INWIN = ("1") ;Windows NT IF INGROUP("Domain Admins") = 1 USE x: "\\server\NT_admin" ENDIF IF INGROUP("Domain Users") = 1 USE y: "\\server\NT_users" ENDIF CASE @INWIN = ("2") ;Windows 9x IF INGROUP("Domain Admins") = 1 USE x: "\\server\Windows_admin" ENDIF IF INGROUP("Domain Users") = 1 USE y: "\\server\Windows_users" ENDIF ENDSELECT ;-------- end drive_mapping.kix--------
Drive_Mapping.kix uses a select case to decide if the user is on a NT computer or a Win9x computer. Once the proper CASE has been proven true I then use IF… statements to check if they are in groups. If a IF… statement is proven true, they then get drive's mapped based on the group that they are in.
So not only they get different drive mappings based on what groups they are a member of, but also different drive mappings based on what type of computer that they are logging from.
C. $Variables (Integers & Strings)
Using $variables in KIX is as inevitable as the sun setting at the end of the day. You have already see several variables in use, but lets dig a little deeper and shed some light of some of the more trickier spots of using a variable in KIX.
First off lets define the type of variables that KIX can use.
Variables That Kix can use are (as of 3.62. this might change with future versions) a. Integers b. Strings.
Sounds straight forward, but this can throw some people for a loop.
Integers First off an integer is a number like 1, 24, 1000, 27. You get the idea.
KIX can not work with decimals!! Any attempt to use a decimal will just result in Kix using the integer value of the number. A way to get around this is to drop the decimal and treat the whole thing as an integer, and put the decimal back in when you are done.
To set a variable to equal an interger your code would look something like this.
$a = 27
Notice that the "" are missing. This is to let kix know that the value of $a is an integer and not a string . This is very important so that Kix knows the difference.
;--------Start Interger.kix-------- break on cls ? "this Program will start in 3 seconds" ? 'Press "Ctrl+C" to stop this program' sleep 3
$a = 1 ;notice no ""
:bigloop $a = $a + 1 ? $a goto bigloop
;-------- end Interger.kix--------
After running the above script you will see Kix count from 1 to 2146438647 (if you didn't press CTRL+C to exit the program)
Now lets run this one….
--------Start NonInterger.kix--------
code:
break on cls
$a = "1" ;notice the ""
while len("$a"); < 100 $a = $a + 1 ? $a loop
-------- end NonInterger.kix--------
In this script we set $a to equal "1" notice that this was a string and not an integer, and we got very different results!
1 11 111 1111 11111 …
When doing math calculations with Kix it is very important to make sure that the variable you are working with is an integer and not a string. This is where the val() command comes in to play.
$a = "1" $a = val("$a")
in the first line we set $a to equal the string "1" the second line we then reset $a to equal the integer value of $a (as a side note this may seem a little confusing at first, but keep in mind that when we are run the 2nd line $a still equals the string "1". After the 2nd line has run then $a will equal the integer value of 1)
as you can see the use of val() is a great way to make sure that you are working with an integer and not a string. One of the places that you would use this is in something like the following.
;--------Start AddInteger.kix-------- break on cls
? "Please inter a number between 1 - 5" get $choice
$number = val("$choice")
Select case $number = 1 ? "You Picked 1" $add = $number + 10 ? "$number + 10 = $add" case $number = 2 ? "You Picked 2" $add = $number + 10 ? "$number + 10 = $add" case $number = 3 ? "You Picked 3" $add = $number + 10 ? "$number + 10 = $add" case $number = 4 ? "You Picked 4" $add = $number + 10 ? "$number + 10 = $add" case $number = 5 ? "You Picked 5" $add = $number + 10 ? "$number + 10 = $add" case 1 ? "I am sorry that is not a number between 1 and 5!" endselect ;-------- end AddInteger.kix--------
As you can see it is very important to pay close attention when working with integers in Kix.
Strings
Ok we have gone over what an integer-variable is, now let go over what a string-variable is.
1. A string-variable is anything that is in quotes.
That’s it, that’s the big secret!!
$a = "String" This is a string-variable. $b = 27 This is an integer-variable.
And to convert a Integer-Variable into a String-Variable just place it in quotes.
$a = 27 $string = "$a"
the variable $string now equals "27".
4. MACROS
Kix comes with several built in macros that contain some extremely helpful information. (the following was taken from the Kix manual)
Macro Definition ADDRESS Address of the network adapter COMMENT User comment CURDIR Current directory DATE Date (in the format YYYY/MM/DD) DAY Day of the week (Monday, Tuesday, and so on) DOMAIN Domain or workgroup the computer belongs to DOS Version of Windowsnbsp;NT ERROR Return code of the most recent command or function. A return code of 0 means the command or function was successful. Any other value indicates an error. FULLNAME Full name of current user HOMEDIR Short name of the directory part of home directory HOMEDRIVE* Drive letter of drive containing home directory HOMESHR Server and share name part of home directory HOSTNAME Fully qualified TCP/IP host name (including TCP/IP domain name) INWIN Operating system: 1nbsp;=nbsp;Windowsnbsp;NT; 2nbsp;=nbsp;Windowsnbsp;9x IPADDRESSx TCP/IP address (possible values for x are 0 - 3#41. [b]Note[/b]Addresses are padded so that the resulting string always consists of four sets of three characters separated by periods. For example, if your IP address is 123.45.6.7, @IPADDRESS0 is 123. 45. 6. 7. KIX Version of KiXtart LANROOT Directory where network software resides (usually Systemroot\System32) LDOMAIN* Logon domain LDRIVE Drive that is redirected to \\logonserver\NETLOGON LM Version of network software LONGHOMEDIR Long name of the directory part of home directory LSERVER Logon server MAXPWAGE Maximum password age MDAYNO Day of the month (1-31) MONTHNO Months since January (1-12) MONTH Name of the month PRIMARYGROUP* urrent user's primary group PRIV User's privilege level (GUEST, USER, ADMIN) PWAGE Password age RAS Number of active Remote Access Service (RAS) connections RSERVER* KXRPC server used for the current session SCRIPTDIR Directory of current script SERROR Error text corresponding with @ERROR SID* Current user's Windowsamp;nbsp;NT Security Identifier (SID) SITE** Name of the site in which the system resides STARTDIR Directory from which KiXtart was started SYSLANG Full English name of the language of the operating system specified in the format defined by ISO Standard 639. (example : "0413Dutch (Standard)"). TIME Current time (in the format HH:MM:SS) USERID Current user's Windowsnbsp;NT user ID USERLANG Full English name of the language selected by the current user specified in the format defined by ISO Standard 639. (example : "0413Dutch (Standard)"). WDAYNO Days since Sunday (1 – 7) WKSTA Computer name WUSERID Current user's Windows user ID YDAYNO Days since January 1 (1 – 365) YEAR Current year
*Available on computers running Windows 9x only if the KiXtart RPC service is running. ** Only available on clients with full Active Directory support.
To use a macro in your code you would precede the macro name with a @. For example
? @fullname ? @userid
Would print out the contents of the Full Name fields in user manager on the first line, and on the next line would be the users logon id. [ 28. July 2003, 08:27: Message edited by: kdyer ]
|
Top
|
|
|
|
Moderator: Jochen, Radimus, Glenn Barnas, Allen, Arend_, ShaneEP, Mart
|
0 registered
and 370 anonymous users online.
|
|
|