ONE-xicons
© Copyright 2022 Werk II Medien- und Informationsgesellschaft mbH. Alle Rechte vorbehalten.

cScript Grammatik

Im folgenden finden Sie eine EBFN-Beschreibung von cScript.

EBNF

Die Elemente einer EBFN (Extended Backus-Naur Form) werden wie folgt gelesen:

Jede Beschreibung ist zusätzlich in Textschreibweise angegeben. Hier gilt:

prog

Am Anfang eines cScript-Programmes stehen die (optionalen) Definitionen von #pragma-Funktionsvariablen.
Danach dürfen beliebig viele Includes folgen.
Dann kommen die eigentlichen Definitionen des Programmes bestehend aus Deklarationen globaler Variablen und aus Funktionen.

Einstiegspunkt für die Bearbeitung ist immer die Funktion int main (). Die Funktion main darf in keinem cScript fehlen..

pragma include dcl ; func prog ::= pragma* include* ( dcl ';' | func )*

Hier das kürzeste mögliche cScript-Programm:

int main ()
{
	return 0;
}

pragma

Definition von Funktionsvariablen.

Funktionsvariablen werden ab v4.1 der priint:comet Plugíns unterstützt. In früheren Versionen der Plugins können sie zu Fehlern in der Skriptausführung führen.

#pragma var functionVariable pragma ::= '#pragma var' functionVariable Verwendet in: prog

functionVariable

## UnsignedInt " Ident // UnquotedString " possibleValue functionVariable ::= '##' UnsignedInt | '"' Ident ( '//' UnquotedString )? '"' possibleValue+ Verwendet in: pragma

possibleValue

## UnsignedInt " UnquotedString // UnquotedString " possibleValue ::= '##' UnsignedInt | '"' UnquotedString ( '//' UnquotedString )? '"' Verwendet in: functionVariable

include

Includes sind cScript-Textteile, die vor der Ausführung des cScript-Programmes in den Quelltext eingesetzt werden. Dabei werden der Reihe nach alle Includes durch den jeweils definierten Text ersetzt. Enthalten die Includes wieder Includes, werden auch die ersetzt. Mehrfachersetzungen werden dabei automatisch vermieden. Hier finden Sie weitere Informationen zu Includes.

#include "internal/frameinfos.h" "internal/panels.h" "internal/products.h" "internal/publications.h" "internal/tables.h" "internal/text.h" "internal/textattributes.h" "internal/types.h" pool_include path include ::= '#include' ( '"internal/frameinfos.h"'   | '"internal/panels.h"'   | '"internal/products.h"'   | '"internal/publications.h"'   | '"internal/tables.h"'   | '"internal/text.h"'   | '"internal/textattributes.h"'   | '"internal/types.h"'   | pool_include   | path ) Verwendet in: prog

pool_include

Das Nicht-Terminal 'TABLE' ist ein String, der die Textquelle des Includes im Datenpool beschreibt, mehr dazu siehe hier.

" < pool_type > [ pool_type ] . pool_type _ / TABLE " pool_include ::= '"' ( '<' pool_type '>' | '[' pool_type ']' | '.' pool_type '_' ) '/' TABLE '"' Verwendet in: include

pool_type

xml sql soap pool_type ::= 'xml' | 'sql' | 'soap' Verwendet in: pool_include

path

String path ::= String Verwendet in: include

dcl

Variablen-Deklarationen. Wenn Sie den Wert einer Zeiger-Variable (*) nicht als Ergebnis einer Funktion erhalten, müssen diese Variablen mit einer geeigneten Funktion allokiert werden, bevor auf deren Inhalt zugegriffen werden darf.

Obwohl allokierter Speicher bei Skriptende automatisch aufgeräumt wird, ist es gute Praxis, reservierten Speicher mit der passenden release-Funktion wieder freizugeben, sobald eine Variable nicht mehr benötigt wird. Denken Sie daran:

Array-Variablen ([]) sind zwar technisch gesehen ebenfalls Zeiger. Die Speicherverwaltung von Arrays wird aber von cScript selbst übernommen. Array-Variablen benötigen also kein alloc oder release!

Die Inhalte von Arrays werden nicht automatisch initialisiert!

dtype var_decl , char string_decl , dcl ::= dtype var_decl ( ',' var_decl )* | 'char' string_decl ( ',' string_decl )* Verwendet in: func_def prog

Hier einige Deklarationen von Variablen.

float square (float f) { return f * f;}

int 		i1		= 12, i2, nn [12];	// Die 12 Werte von nn sind nicht initialisiert!
float 		p1		= mm2pt (1.0);		// Berechneter Wert
float 		p2		= square (4.0);		// Mit eigener Funktion berechneter Wert
char 	* 	s1		= "abc";			// Konstante! Darf nicht verändert werden!
char  		s2[]	= "def";			// Konstante! Darf nicht verändert werden!
char  		s4 [4], *s5 = alloc (512);	// s4 NICHT freigeben! s5 mit release (s5) wieder freigeben
Table		T		= table::alloc ();	// mit table::release (T) wieder freigeben

dtype

Die Datentypen float und int von cScript sind 64-Bit-Werte. Neben diesen Grundtypen gibt es eine Reihe weiterer Datentypen. Eine vollständige Liste der bekannten Datentypen finden Sie hier. Diese Datentypen dienen der besseren Lesbarkeit. Intern sind sie alle als int* definiert. Bei der Deklaration von Variablen mit diesen Datentypen werden die Variablen mit 0 initialisiert. Vor der Verwendung von Variablen mit Datentypen ungleich int oder float müssen diese Variablen allokiert worden sein!

int float cscript/index.html#Typedefs dtype ::= 'int' | 'float' | 'cscript/index.html#Typedefs' Verwendet in: dcl func param

var_decl

* Ident [ Integer ] Ident = expr * Ident = expr var_decl ::= '*'* Ident ( '[' Integer ']' )? | Ident '=' expr | '*' Ident '=' expr Verwendet in: dcl

string_decl

* Ident [ Integer ] * Ident = string_expr Ident [ ] = string_expr string_decl ::= '*'* Ident ( '[' Integer ']' )? | '*' Ident '=' string_expr | Ident '[' ']' '=' string_expr Verwendet in: dcl

func

dtype * func_def char * func_def func ::= dtype '*'* func_def | 'char' '*'+ func_def Verwendet in: prog

func_def

Ident ( params ) { dcl ; stmt return ; } func_def ::= Ident '(' params ')' '{' ( dcl ';' )* stmt* return ';' '}' Verwendet in: func

params

param , params ::= ( param ( ',' param )* )? Verwendet in: func_def

param

dtype * Ident char * Ident param ::= dtype '*'* Ident | 'char' '*'+ Ident Verwendet in: params

stmt

Ausdrücke in Bedingungen (if, while, for) werden immer vollständig berechnet! Die in C oder C++ gerne verwendeten Test für nicht-leere char*-Strings wie

if (str && *str)

führen in cScript zu Fehlern und müssen etwa durch

if (str)
{
    if (*str)
    {
    }
}

ersetzt werden.

{ stmt } if ( expr ) stmt else stmt while ( expr ) stmt for ( assg ; expr ; assg ) stmt break ; return ; assg ; Ident ( expr , ) ; ; stmt ::= 'if' '(' expr ')' stmt ( 'else' stmt )+ | 'while' '(' expr ')' stmt | 'for' '(' assg+ ';' expr+ ';' assg+ ')' stmt | 'break' ';' | return ';' | assg ';' | Ident '(' ( expr ( ',' expr )* )? ')' ';' | '{' stmt* '}' | ';' Verwendet in: func_def stmt

return

return expr return ::= 'return' expr Verwendet in: func_def stmt

assg

* Ident [ int_expr ] = expr assg ::= '*'+ Ident ( '[' int_expr ']' )+ '=' expr Verwendet in: stmt

expr

int_expr float_expr string_expr Ident Ident [ int_expr ] Ident ( expr , ) ( expr ) expr ::= int_expr | float_expr | string_expr | Ident | Ident '[' int_expr ']' | Ident '(' ( expr ( ',' expr )* )? ')' | '(' expr ')' Verwendet in: assg expr return stmt var_decl

int_expr

Integer - int_expr & Ident ( int ) float_expr int_expr binop int_expr int_expr relop int_expr int_expr logical_op int_expr int_expr ::= Integer | '-' int_expr | '&' Ident | '(' 'int' ')' float_expr | int_expr binop int_expr | int_expr relop int_expr | int_expr logical_op int_expr Verwendet in: assg expr float_expr int_expr

float_expr

cScript führt keine automatischen Typumwandlungen durch! Achten Sie darauf, an Stellen, die ein float erwarten, auch tatsächlich ein float zu übergeben! Z.B. ist 1401 eine Ganzzahl, die entsprechende Kommazahl geben Sie mit 1401. oder 1401.0 an.

Float - float_expr ( float ) int_expr float_expr relop float_expr
float_expr ::= Float | '-' float_expr | '(' 'float' ')' int_expr | float_expr relop float_expr Verwendet in: expr float_expr int_expr

string_expr

String string_expr ::= String Verwendet in: expr string_decl

binop

Ausdrücke werden von rechts nach links ausgewertet!

Weil sie von hinten nach vorne berechnet werden, ergeben die rot markierten Ausdrücke scheinbar falsche Resultate. Mit Klammerungen erhalten Sie die erwarteten Resultate.

x = 3 - 1 + 2;      // ergibt 0 statt 4
  = 3 - 1 + 2
  = 3 - 3
  = 0


x = (3 - 1) + 2;    // ergibt 4
  = 2 + 2
  = 4

x = 20 / 10 * 2;    // ergibt 1 statt 4
  = 20 / 10 * 2
  = 20 / 20
  = 1


x = (20 / 10) * 2;  // ergibt 4
  = 2 * 2
  = 4

+ * / binop ::= '+' | '–' | '*' | '/' Verwendet in: int_expr

relop

== != <= < >= > relop ::= '==' | '!=' | '<=' | '<' | '>=' | '>' Verwendet in: float_expr int_expr

logical_op

&& || logical_op ::= '&&' | '||' Verwendet in: int_expr

Ident

Letter Letter Decimal _ Ident ::= Letter ( Letter | Decimal | '_' )* Verwendet in: assg expr func_def functionVariable int_expr param stmt string_decl var_decl

UnsignedInt

Decimal UnsignedInt ::= Decimal+ Verwendet in: functionVariable possibleValue

Integer

- Decimal 0x 0X Hex Integer ::= '-'? ( Decimal+ | ( '0x' | '0X' ) Hex+ ) Verwendet in: int_expr string_decl var_decl

Float

cScript führt keine automatischen Typumwandlungen durch! Achten Sie darauf, an Stellen, die ein float erwarten, auch tatsächlich ein float zu übergeben! Z.B. ist 1401 eine Ganzzahl, die entsprechende Kommazahl geben Sie mit 1401. oder 1401.0 an.

- Decimal . Decimal Float ::= '-'? Decimal* '.' Decimal+ Verwendet in: float_expr

String

" UnquotedString " String ::= '"' UnquotedString '"' Verwendet in: path string_expr

UnquotedString

[^"\] "" \x \X Hex Hex \ any ascii char UnquotedString ::= ( [^"\] | '""' | ( '\x' | '\X' ) Hex Hex | '\' 'any ascii char' )* Verwendet in: String functionVariable possibleValue

Hex

Decimal [a-f] [A-F] Hex ::= Decimal | [a-fA-F] Verwendet in: Integer UnquotedString

Decimal

[0-9] Decimal ::= [0-9] Verwendet in: Float Hex Ident Integer UnsignedInt

Letter

[a-z] [A-Z] Letter ::= [a-zA-Z] Verwendet in: Ident   ... generated by Railroad Diagram Generator R R