deskshell(X) 06 January 1993 deskshell(X) Name deskshell - syntax and control constructs of the Deskshell command lan- guage Description Deskshell is a command language that allows you to manipulate most aspects of the Desktop. The Deskshell script language is used to specify the actions to be performed in a triggeraction, dropinaction, initialactions, finalactions, or menuitem rule or within an object script. For more information on rules, rule files, and objects, see the . Deskshell commands and scripts can define actions to be taken when: + an icon is triggered + an icon is dragged and dropped on a directory or the Desktop window + a directory or the Desktop is opened + a directory or the Desktop is closed + a menu item is chosen + an object is triggered in some other way Deskshell offers a flexible range of control structures and a wide selec- tion of commands. Deskshell provides the same basic functionality as the UNIX(r) Bourne shell language. Although regular UNIX commands and shellscripts can be used instead of Deskshell commands, Deskshell is recommended for the following reasons: + Deskshell commands execute faster than regular shell commands because no extra processes need to be opened (Deskshell operates within the Desktop processes). + Deskshell commands are specifically designed for the Desktop and therefore necessary for defining Desktop-specific actions. + Deskshell understands regular UNIX shell commands. Consequently, these commands can be included in Deskshell scripts if their functionality is necessary. This manual page is divided into two sections about Deskshell syntax and Deskshell control structures. For information on Deskshell commands, see the deskcommands(X) manual page. For an example of a Deskshell script, see the SCO Open Desktop Administrator's Guide. Deskshell syntax Deskshell syntax is very similar to Bourne shell language. Deskshell is a command interpreter, not a macro interpreter. This distinction, along with Deskshell's simpler syntax, eliminates some of the more awkward ele- ments of Bourne shell syntax. For example, Deskshell avoids the four different types of quoting and the need for exponentially growing numbers of backslashes that are sometimes necessary in Bourne shell language. The discussion on Deskshell syntax describes how to use strings, vari- ables, and operators in Deskshell. Deskshell strings An unquoted string is interpreted to be a sequence of characters. The following characters have global meanings in Deskshell and are therefore restricted. An unquoted string cannot contain or begin with the following characters: space, tab, or newline ' quote ( ) parentheses { } braces < less than > greater than ; semicolon | bar & ampersand $ dollarsign ` backquote ^ circumflex An unquoted string cannot begin with the following characters: # hashmark = equals The following characters are reserved for later wildcard processing: * asterisk [ open bracket ] close bracket ? question mark Quoting in Deskshell Unlike Bourne shell language, which includes four different kinds of quoting, Deskshell achieves the same functionality using only one kind of quoting: single quotes. Text within single quotes is uninterpreted by Deskshell. Quoting is only necessary to allow the special Deskshell characters to be treated literally. After a piece of text has been interpreted by Deskshell, it is never interpreted again. For example, the values of variables are never inter- preted and so can safely hold places. _________________________________________________________________________ NOTE To include a single quote in quoted text, the single quote should be repeated. echo 'Can''t delete file.' _________________________________________________________________________ Values in Deskshell All values are represented in Deskshell as strings, which are converted into numbers or Boolean values when required in specific contexts. Because all Deskshell variables are strings, Deskshell does not require variable ``typing''. When strings are converted to numbers, the first non-digit is taken as the end of the number and remaining characters are ignored. Strings starting with a minus sign ``-'' have an undefined value. When numbers or strings are converted to Boolean values, zero is taken as true and non-zero values are false. A list of numbers or strings is true if every element is zero and false if any element is non-zero. Numbers are converted to strings in conventional decimal representation. The preceding principles are illustrated by the following examples: _________________________________________________________________________ String Number Boolean _________________________________________________________________________ val 0 true 12X24 12 false (val 2 3) (0 2 3) false Deskshell variables Each Deskshell variable can have a list of strings as its value (Bourne shell supports only one string per variable). A list is represented by enclosing a sequence of strings in parentheses, for example: (mon tues wed thur fri sat sun) is a list of seven strings. _________________________________________________________________________ NOTE ( ) is an empty list with no elements. _________________________________________________________________________ Environment variables When Deskshell starts, the value of each environment variables is copied into a Deskshell variable of the same name. For example, the $PATH environment variable is copied into the Deskshell path variable. The path variable is a list of strings with a space-separated string for each path element. All other variables are set to contain no strings. Special variables The following special variables are provided in Deskshell and therefore reserved: _________________________________________________________________________ Variable Value _________________________________________________________________________ static_arg the static object in canonical (unambigu- ous) form dynamic_args a list of the dynamic objects in canonical form * the elements of dynamic_args s_desktop, d_desktop the name of the open desktops that the static and dynamic arguments are on, if any s_position, d_position the position of the static or dynamic argu- ment, or V if there is more than one argu- ment s_obj_type, d_obj_types the object types of the static and dynamic arguments, respectively trigger the trigger name desktop_name the name of the Desktop See the deskcommands(X) manual page for details of the circumstances under which these variables are set. Variable names Variable names can consist of any sequence of letters, digits, and under- scores; but they cannot start with a digit. You should not define vari- ables that are the same as environment variables or one of the special Deskshell variables. Variables are assigned with the equals ``='' operator. For example, days=(mon tues wed thur fri sat sun) sets days to the list of seven strings. Variable substitutions The value of a variable can be substituted into a Deskshell script with: $name and the number of strings in a variable with: $#name. A subset of the value can be generated by placing appropriate subscripts in parentheses after the name. For example, the assignment: days=(mon tues wed thur fri sat sun) and the command: echo $#days will produce 7, while the command: echo $days(3 1 3) will produce: wed mon wed as will: echo $days(3 0 1 8 3) Function arguments The special name * holds the list of arguments to the current function. For convenience, the forms $1, $2 ..., can be used as abbreviations for $*(1), the first argument; $*(2), the second argument, ... Deskshell operators The following table lists the operators provided in Deskshell: _________________________________________________________________________ Operator Description _________________________________________________________________________ = assignment <,>, and >> redirection << here-document `(backquote) substitution ^(circumflex) catenation | pipeline # comment &&,||,&, and ; sequencing These operators are explained in greater detail in the following sec- tions. Assignments = The assignment operator ``='' assigns a list value to a variable. For example, foo=(1 1 2 3 5) assigns the list (1 1 2 3 5) to the variable foo. Redirections <, >, and >> A redirection causes a file descriptor to be redirected to a different file. The following options are available: < The file is opened on descriptor 0 for reading only; it must already exist. > The file is opened on descriptor 1 for writing and is truncated; it is created if necessary and will be overwritten if it exists. >> The file is opened on descriptor 1 for append only; it is created if necessary and will not be overwritten if it exists. The following variants are available for each redirection; in each case < can be replaced by > or >>. _________________________________________________________________________ Variant Description _________________________________________________________________________ <filename Read from filename <[number] filename Read from filename on descriptor number <[new = number] Make new a duplicate of number <[number =] Close descriptor number Here-documents << The expression: <<name or <<[number] name causes text to be read from the script until name is found on a line of its own; the text is written to a temporary file, and then rewound and opened for reading on the specified descriptor number. Substitutions ` Many Deskshell and UNIX commands perform an action and print a result. You can trap the output of such a command, and use it in a Deskshell script with the backquote ```'' operator. For example, size= `{ls -s $1} assigns the string representing the size and name of the file in the variable $1 to the variable size. _________________________________________________________________________ NOTE The use of the curly braces causes another process to be run. _________________________________________________________________________ Certain Deskshell commands generate text output. These may be used directly, without requiring a separate process. For example, var=`(basename $list) which sets var to a list of the basenames of the files in $list without requiring another process to be run. Command substitution can be nested to any depth. _________________________________________________________________________ NOTE No final backquote ```'' is needed to end the substitution. _________________________________________________________________________ Catenations ^ Two words or lists can be catenated or joined together using the circum- flex ``^'' character. Lists can only be catenated if they both contain the same number of elements, or if one of them only contains one element or is empty, as illustrated in the following examples: _________________________________________________________________________ a b a^b _________________________________________________________________________ w x wx w (x y z) (wx wy wz) (w x y) (a b c) (wa xb yc) (w x y) ( ) (w x y) (w x y) (a b) illegal Several catenations can be included in one expression, as in: s.^(in proc out)^.main.^(c h s) which evaluates to: (s.in.main.c s.proc.main.h s.out.main.s) Deskshell allows circumflexes to be omitted in a few common cases. For example, the strict form $file^.c can be written as $file.c instead. Pipelines | A pipeline consists either of a single command or several commands separated by pipe descriptors. A pipe descriptor consists of one of the following character sequences: | |[number1] |[number1 = number2] If number2 is omitted, it is equivalent to specifying zero. If both num- ber1 and number2 and brackets are omitted, it is equivalent to specifying |[1=0]. White space can safely be inserted around the descriptor. If there is only one command, it is executed directly by Deskshell. If there is more than one, then one child thread is created for each com- mand. These are connected by pipes, one per pipe descriptor; none of the pipelines is executed by the original thread. number1 is the file descriptor to be connected to the writing end of the pipeline, and num- ber2 is to be connected to the reading end of the pipe. When a pipeline is executed, Deskshell waits for all the children to ter- minate. The individual statuses are converted to strings, and these are all stored in the status variable, in the same order as the commands in the pipeline. For example, the pipeline: true | false generates the status (0 1). Comments # If a hash character occurs at what would be the start of an unquoted string, then the hash character, and all characters up to (but excluding) the next newline, are ignored. A hash character within an unquoted string is treated like any other character. Scripts and sequences &&, ||, & , and ; A script is made up of one or more sequences, separated by the delimiters ampersand ``&'' and semi-colon ``;''. A sequence is made up of one or more pipelines, separated by the delimiters double ampersand ``&&'' and double bar ``||''. Each of these delimiters can be surrounded by white space. A sequence is executed by conditionally executing each pipeline in turn. The first pipeline in the sequence is always executed. Every other pipe- line is executed if the preceding delimiter is ``&&'' and the status is true, or if the preceding delimiter is ``||'' and the status is false. A pipeline can be executed even if the previous one is not. The status of a sequence is that of the last pipeline executed. A script is executed by each of its constituent sequences. If the com- mand sequence is terminated by &, then it is executed in a child thread with fd 0 set to /dev/null, and its returned status is ignored. In the parent thread, the name of the child thread is placed in the variable lastbackgroundaction; the parent does not wait for the child to ter- minate. If the sequence is terminated by a semicolon, it is executed in this thread. Deskshell control constructs Deskshell offers most of the control flow structures and commands pro- vided by the Bourne shell. Deskshell provides the following control con- structs: case executes a script depending on the value of the variable for executes a script for each value of a variable in a specified list if executes a script if a condition is true until executes a script until a condition is true while executes a script while a condition is true Each construct is described in greater detail in the sections immediately following this one. Deskshell function definitions The command function assigns a function name to a script. The function command has the following syntax: function name {script} It assigns name to the script. This assignment can be canceled with: function name; The script is not evaluated at this point, although it will be parsed and any syntax errors detected. Deskshell status variable When a Deskshell command is executed, it generates a numerical status between 0 and 1023. When a command is executed and generates a status, that status is con- verted to a string and stored in the variable status. When a pipeline is executed, the individual statuses are collected, and the strings all stored in the variable status, in the same order as the commands in the pipeline. For information on the returned statuses of specific commands, see the deskcommands(X) manual page. _________________________________________________________________________ NOTE Certain built-in Deskshell commands and the function command do not return a status. _________________________________________________________________________ Case constructs The Deskshell case statement executes a script depending on the value of a variable. Syntax case word; [argument : [script] ;; ] ... esac Description The double semicolon should actually occur in the script; it may be sur- rounded by white space. The word is evaluated to form a list of strings, which undergo wildcard expansion. These strings are then catenated together, separated by the value of the first string in the variable ofs, or by a single space if this variable holds no strings. The result is known as the test string. The arguments are then processed in order until a match is found; this is described in detail below. If a matching argument is found, the corre- sponding script is executed and the case statement is completed. If not, the next argument is processed. To process an argument, it is first expanded to a list of strings. The test string is then compared against each string in the list (the order is unimportant); if any match, then the argument is said to have been matched. The comparison is done as follows: + An untagged character matches only the corresponding character. + A tagged question mark matches exactly one character. + A tagged asterisk matches zero or more characters. + A tagged open bracket starts a matching set. This matches one character, which must be a character specified by the matching set. A matching set extends from the tagged open bracket to the end of the string, or to the next close bracket (this can be derived from a word other than an unquoted string). Returned status The status, if any, is that of the script executed. For constructs The Deskshell for statement executes a script for each value of a vari- able. Syntax for name in arguments ; do script ; done or: for name ; do script ; done Description The second form is equivalent to specifying: in $* after the name argument. arguments are converted to a list of strings; wildcard expansion is per- formed on the list. The script is then executed once for each string in the list, with the named variable set to that string for that iteration. The value of the name variable is undefined after the for statement com- pletes. Returned status Its status is that of the last execution of script. If constructs The Deskshell if statement executes a script if a condition is true. Syntax if script1; [then script2;] [elif script3; [then script4]] ... [else script5] fi Description The scripts following the if or the elif statements are executed in order until one completes with a true status. The script following the corre- sponding then statement, if any, is then executed. If no scripts com- plete with a true status, the script following the else statement, if any, is then executed. Returned status Its status is that of the execution of the last script. Until constructs The Deskshell until statement executes a script until a condition is true. Syntax until script1; do script2 ; done Description First script1 is executed. If the status is false, script2 is executed and the statement is restarted. If the status is true, the until state- ment is completed. Returned status Its status is that of the last execution of script1. While constructs The Deskshell while statement executes a script while a condition is true. Syntax while script1; do script2 ; done Description script1 is executed. If the status is true after it completes, then script2 is executed and the statement is restarted. If the status is false, the the while statement is completed. Returned status Its status is that of the last execution of script1. Files /usr/lib/X11/XDesktop3/<lang>.xdt/xdtsysinfo /usr/lib/X11/<lang>/app-defaults/XDesktop3 where <lang> refers to the value set in the $LANG environment variable or the value specified in the file /etc/default/lang. See also deskcommands(X), xdt3(X), tellxdt3(X)