diff --git a/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.Common.cs b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.Common.cs
new file mode 100644
index 00000000..c80d9d27
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.Common.cs
@@ -0,0 +1,281 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="ExpSyntaxAnalyzer.Common.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using Microsoft.CodeAnalysis.CSharp.Syntax;
+
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Runtime.CompilerServices;
+using System.Text;
+using System.Text.RegularExpressions;
+using System.Threading.Tasks;
+using System.Xml.Schema;
+
+using ExpKeyword = StgSharp.Script.Express.ExpressCompile.Keyword;
+
+namespace StgSharp.Modeling.Step
+{
+ internal partial class StepExpSyntaxAnalyzer
+ {
+
+ private static Regex _entityTypeCheckPattern = GetEntityTypeCheckPattern();
+
+ [GeneratedRegex( @"^[A-Z_]+$", RegexOptions.Singleline )]
+ private static partial Regex GetEntityTypeCheckPattern();
+
+ private bool IsSeparatorMatch( Token leftSeparator, Token rightSeparator )
+ {
+ return leftSeparator.Value switch
+ {
+ ExpKeyword.LeftBrace => rightSeparator.Value == ExpKeyword.RightBrace,
+ ExpKeyword.LeftParen => rightSeparator.Value == ExpKeyword.RightParen,
+ ExpKeyword.Comma => rightSeparator.Value == ExpKeyword.Comma,
+ ExpKeyword.Semicolon => rightSeparator.Value == ExpKeyword.Semicolon,
+ _ => false
+ };
+ }
+
+ private bool TryAppendIndexLeft( Token t )
+ {
+ if( t.Flag != TokenFlag.Index_Left ) {
+ return false;
+ }
+ if( _cache.TryPeekOperand( out bool isNode, out _, out ExpSyntaxNode? node ) )
+ {
+ if( node.EqualityTypeConvert is not ExpCollectionBase ) {
+ ExpInvalidSyntaxException.ThrowNonCollectionIndex( t );
+ }
+ }
+ _cache.PushOperator( t );
+ _cache.IncreaseDepth( ( int )ExpCompileStateCode.CollectionIndex );
+ return true;
+ }
+
+ private bool TryAppendIndexRight( Token t )
+ {
+ if( t.Flag != TokenFlag.Index_Right ) {
+ return false;
+ }
+
+ //reverse building
+ ClosePrefixReverse( t );
+
+ //make index node
+ _cache.PopOperand( out _, out ExpSyntaxNode? expNode );
+ if( !_cache.PopOperand( out Token colleToken, out ExpSyntaxNode? colleNode ) ) { }
+ _cache.PushOperand(
+ ExpCollectionIndexNode.Create(
+ t, ( colleNode as ExpCollectionInstanceBase )!, expNode ) );
+ return true;
+ }
+
+ private bool TryAppendMember( Token t )
+ {
+ if( t.Flag != TokenFlag.Member ) {
+ return false;
+ }
+ if( TryParseConstant( t ) ) {
+ return true;
+ }
+ if( TryParseFunction( t ) ) {
+ return true;
+ }
+ if( TryParseInstance( t ) ) {
+ return true;
+ }
+ if( TryParseKeyword( t ) ) {
+ return true;
+ }
+ if( TryParseElementName( t ) ) {
+ return true;
+ }
+
+ //Many thing miss here
+ _cache.PushOperand( ExpElementMemberNameNode.Create( t ) );
+
+ return true;
+ }
+
+ private bool TryAppendMiddleSeparator( Token t )
+ {
+ if( t.Flag != TokenFlag.Separator_Middle ) {
+ return false;
+ }
+ while( _cache.OperatorAheadOfDepth > 0 )
+ {
+ _cache.TryPopOperator( out Token op );
+ ExpSyntaxNode node = ConvertAndPushOneOperator( op );
+ }
+ switch( _cache.OperandAheadOfDepth )
+ {
+ case 0:
+ if( t.Value == ";" ) {
+ return true;
+ }
+ _cache.StatementsInDepth.Push( ExpSyntaxNode.Empty );
+ goto case 1;
+ case 1:
+ _cache.PopOperand( out _, out ExpSyntaxNode? statement );
+ _cache.StatementsInDepth.Push( statement );
+ if( t.Value == ";" ) {
+ StepEntityInitStatements.Enqueue( statement );
+ }
+ return true;
+ default:
+ ExpInvalidSyntaxException.ThrowNoOperator( t );
+ break;
+ }
+ return true;
+ }
+
+ private bool TryAppendNumAndStrLiteral( Token t )
+ {
+ if( ( t.Flag & ( TokenFlag.String | TokenFlag.Number ) ) == 0 ) {
+ return false;
+ }
+ _cache.PushOperand( ExpElementInstance.CreateLiteral( t ) );
+ return true;
+ }
+
+ private bool TryAppendPrefixSeparator( Token t )
+ {
+ if( t.Flag != TokenFlag.Separator_Left ) {
+ return false;
+ }
+ _cache.PushOperator( t );
+ _cache.IncreaseDepth( ( int )ExpCompileStateCode.Common );
+ return true;
+ }
+
+ private bool TryAppendPrefixSeparatorEnd( Token t )
+ {
+ if( t.Flag != TokenFlag.Separator_Right ) {
+ return false;
+ }
+ ClosePrefixReverse( t );
+ return true;
+ }
+
+ private bool TryAppendSymbol( Token t )
+ {
+ if( ( t.Flag & ( TokenFlag.Symbol_Unary | TokenFlag.Symbol_Binary ) ) == 0 ) {
+ return false;
+ }
+
+ int cmp = -1;
+ processPrecedence:
+ if( _cache.TryPeekOperator( out Token tmp ) )
+ {
+ cmp = CompareOperatorPrecedence( t, tmp );
+ if( cmp >= 0 )
+ {
+ _cache.PopOperator();
+ ExpSyntaxNode node = ConvertAndPushOneOperator( tmp );
+ goto processPrecedence;
+ }
+ }
+ _cache.PushOperator( t );
+ return true;
+ }
+
+ private bool TryParseConstant( Token t )
+ {
+ switch( t.Value )
+ {
+ case ExpKeyword.E:
+ _cache.PushOperand( new ExpRealNumberNode( t, MathF.E, true ) );
+ return true;
+ case ExpKeyword.Pi:
+ _cache.PushOperand( new ExpRealNumberNode( t, MathF.PI, true ) );
+ return true;
+ default:
+ if( ExpElementInstance.TryCreateLiteral( t, out ExpElementInstance? node ) )
+ {
+ _cache.PushOperand( node );
+ return true;
+ }
+ return false;
+ }
+ }
+
+ private bool TryParseElementName( Token t )
+ {
+ if( _context.TryGetType( t.Value, out ExpTypeSource? type ) )
+ {
+ _cache.PushOperand( ExpMetaRefNode.RefType( t, type ) );
+ return true;
+ }
+ if( _context.TryGetEntity( t.Value, out ExpEntitySource? entity ) )
+ {
+ _cache.PushOperand( ExpMetaRefNode.RefEntity( t, entity ) );
+ return true;
+ }
+ return false;
+ }
+
+ private bool TryParseFunction( Token t )
+ {
+ if( _entityTypeCheckPattern.IsMatch( t.Value ) ) {
+ _cache.PushOperator( t );
+ }
+ return false;
+ }
+
+ private bool TryParseInstance( Token t )
+ {
+ if( t.Value[ 0 ] == '#' )
+ {
+ _cache.PushOperand( StepEntityInstanceNode.Register( t ) );
+ return true;
+ }
+ return false;
+ }
+
+ private bool TryParseKeyword( Token t )
+ {
+ switch( t.Value )
+ {
+ case ExpKeyword.Return:
+ _cache.PushOperator( t );
+ return true;
+ case ExpKeyword.Skip:
+ _cache.PushOperand( ExpProcedureControlNode.Skip( t ) );
+ return true;
+ default:
+ return false;
+ }
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.ErrorProcess.cs b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.ErrorProcess.cs
new file mode 100644
index 00000000..d4eda496
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.ErrorProcess.cs
@@ -0,0 +1,56 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="ExpSyntaxAnalyzer.ErrorProcess.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ internal partial class StepExpSyntaxAnalyzer
+ {
+
+ public void ThrowCompileException( int errorCode )
+ {
+ switch( errorCode )
+ {
+ case 0 or 1:
+ return;
+ case TokenTypeNotMatch:
+ throw new Exception();
+ default:
+ break;
+ }
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.OperatorParser.cs b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.OperatorParser.cs
new file mode 100644
index 00000000..54e553c0
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.OperatorParser.cs
@@ -0,0 +1,148 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="ExpSyntaxAnalyzer.OperatorParser.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Model.Step.SyntaxNode;
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+using ExpKeyword = StgSharp.Script.Express.ExpressCompile.Keyword;
+
+namespace StgSharp.Modeling.Step
+{
+ internal partial class StepExpSyntaxAnalyzer
+ {
+
+ public int CompareOperatorPrecedence( Token left, Token right )
+ {
+ ExpressCompile.TryGetOperatorPrecedence( left.Value, out int leftPrecedence );
+ ExpressCompile.TryGetOperatorPrecedence( right.Value, out int rightPrecedence );
+ return leftPrecedence - rightPrecedence;
+ }
+
+ public bool TryGenerateUnaryNode( Token t, out ExpSyntaxNode node )
+ {
+ ExpSyntaxNode operand = GetNextOperandCache();
+ switch( t.Value )
+ {
+ case ExpKeyword.UnaryPlus:
+ node = ExpUnaryOperatorNode.UnaryPlus( t, operand );
+ return true;
+ case ExpKeyword.UnaryMinus:
+ node = ExpUnaryOperatorNode.UnaryMinus( t, operand );
+ return true;
+ case ExpKeyword.Not:
+ node = ExpUnaryOperatorNode.UnaryNot( t, operand );
+ return true;
+ default:
+ node = ExpSyntaxNode.Empty;
+ return false;
+ }
+ }
+
+ ///
+ /// WARNING: This method cannot process INDEXOF, FUNCTION CALLING, LOOP and any ENDING
+ /// SYMBOLS.
+ ///
+ private ExpSyntaxNode ConvertAndPushOneOperator( Token op )
+ {
+ switch( op.Flag )
+ {
+ case TokenFlag.Symbol_Unary:
+ TryGenerateUnaryNode( op, out ExpSyntaxNode? node );
+ _cache.PushOperand( node );
+ return node;
+ case TokenFlag.Symbol_Binary:
+ TryGenerateBinaryNode( op, out node );
+ _cache.PushOperand( node );
+ return node;
+ case TokenFlag.Member:
+ _cache.PopOperand( out _, out ExpSyntaxNode? p );
+ StepEntityInitCaller caller = StepEntityInitCaller.CreateCaller( op.Value );
+ node = ExpFunctionCallingNode.CallFunction( op, caller, p );
+ _cache.PushOperand( node );
+ return node;
+ default:
+ throw new NotImplementedException();
+ }
+ }
+
+ private bool TryGenerateBinaryNode( Token t, out ExpSyntaxNode node )
+ {
+ ExpSyntaxNode right = GetNextOperandCache();
+ ExpSyntaxNode left = GetNextOperandCache();
+ switch( t.Value )
+ {
+ case ExpKeyword.Add:
+ node = ExpBinaryOperatorNode.Add( t, left, right );
+ return true;
+ case ExpKeyword.Sub:
+ node = ExpBinaryOperatorNode.Sub( t, left, right );
+ return true;
+ case ExpKeyword.Mul:
+ node = ExpBinaryOperatorNode.Mul( t, left, right );
+ return true;
+ case ExpKeyword.Div:
+ node = ExpBinaryOperatorNode.Div( t, left, right );
+ return true;
+ case ExpKeyword.Equal:
+ node = ExpBinaryOperatorNode.EqualTo( t, left, right );
+ return true;
+ case ExpKeyword.NotEqual:
+ node = ExpBinaryOperatorNode.NotEqualTo( t, left, right );
+ return true;
+ case ExpKeyword.GreaterThan:
+ node = ExpBinaryOperatorNode.GreaterThan( t, left, right );
+ return true;
+ case ExpKeyword.LessThan:
+ node = ExpBinaryOperatorNode.LessThan( t, left, right );
+ return true;
+ case ExpKeyword.Assignment:
+ node = ExpBinaryOperatorNode.Assign( t, left, right );
+ return true;
+ case ExpKeyword.InstanceEqual:
+ node = ExpBinaryOperatorNode.CompareInstanceEqual( t, left, right );
+ return true;
+ case ExpKeyword.InstanceNotEqual:
+ node = ExpBinaryOperatorNode.CompareInstanceNotEqual( t, left, right );
+ return true;
+ default:
+ node = ExpSyntaxNode.Empty;
+ return false;
+ }
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.PrefixReverseAnalysing.cs b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.PrefixReverseAnalysing.cs
new file mode 100644
index 00000000..5312634d
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.PrefixReverseAnalysing.cs
@@ -0,0 +1,85 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="ExpSyntaxAnalyzer.PrefixReverseAnalysing.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Generic;
+using System.ComponentModel.DataAnnotations;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+using ExpKeyword = StgSharp.Script.Express.ExpressCompile.Keyword;
+
+namespace StgSharp.Modeling.Step
+{
+ internal partial class StepExpSyntaxAnalyzer
+ {
+
+ private void ClosePrefixReverse( Token rightSeparator )
+ {
+ Token op;
+ ExpSyntaxNode root;
+ if( _cache.OperatorAheadOfDepth == 0 )
+ {
+ if( _cache.OperandAheadOfDepth == 1 )
+ {
+ _cache.PopOperand( out _, out ExpSyntaxNode? statement );
+ _cache.StatementsInDepth.Push( statement );
+ } else
+ {
+ ExpInvalidSyntaxException.ThrowNoOperator( rightSeparator );
+ }
+ } else
+ {
+ while( _cache.TryPopOperator( out op ) ) {
+ ConvertAndPushOneOperator( op );
+ }
+ _cache.PopOperand( out _, out root );
+ _cache.StatementsInDepth.Push( root );
+ }
+
+ root = _cache.PackAllStatements();
+ _cache.DecreaseDepth();
+ if( IsSeparatorMatch( _cache.PeekOperator(), rightSeparator ) )
+ {
+ _cache.PopOperator();
+ _cache.PushOperand( root );
+ } else
+ {
+ throw new ExpCompileException(
+ rightSeparator, "Ending of block does not match its begging" );
+ }
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.cs b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.cs
new file mode 100644
index 00000000..88406407
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/ExpSyntaxAnalyzer.cs
@@ -0,0 +1,149 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="ExpSyntaxAnalyzer.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using Microsoft.CodeAnalysis.CSharp.Syntax;
+
+using StgSharp.Script;
+using StgSharp.Script.Express;
+using StgSharp.Threading;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.Diagnostics;
+using System.IO.Pipes;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+using ExpKeyword = StgSharp.Script.Express.ExpressCompile.Keyword;
+
+namespace StgSharp.Modeling.Step
+{
+ internal partial class StepExpSyntaxAnalyzer : ISyntaxAnalyzer
+ {
+
+ private const int EndLine = 1;
+ private const int TokenGenerated = 0;
+ private const int TokenTypeNotMatch = -1;
+
+ private CompileStack _cache;
+ private ExpSchema _context;
+ private ExpSyntaxNode _lastStatement;
+ private IExpElementSource _local;
+
+ public StepExpSyntaxAnalyzer()
+ {
+ _cache = new CompileStack();
+ }
+
+ public StepExpSyntaxAnalyzer( ExpSchema context, IExpElementSource local )
+ {
+ _cache = new CompileStack();
+ ArgumentNullException.ThrowIfNull( context );
+ if( context is not ExpSchema_Builtin )
+ {
+ _context = context;
+ } else
+ {
+ throw new InvalidCastException( "Not a valid Schema type" );
+ }
+ _local = local;
+ }
+
+ public ConcurrentQueue StepEntityInitStatements { get; } = new ConcurrentQueue(
+ );
+
+ ///
+ /// Append a token to top of cache. This method will automatically convert token to node
+ /// if meets separators or operators.
+ ///
+ public void AppendToken( Token expToken )
+ {
+ switch( expToken.Flag )
+ {
+ case TokenFlag.Symbol_Unary or TokenFlag.Symbol_Binary:
+ TryAppendSymbol( expToken );
+ break;
+ case TokenFlag.Number or TokenFlag.String:
+ ExpElementInstance node = ExpElementInstance.CreateLiteral( expToken );
+ _cache.PushOperand( node );
+ break;
+ case TokenFlag.Separator_Left:
+ TryAppendPrefixSeparator( expToken );
+ break;
+ case TokenFlag.Separator_Right:
+ TryAppendPrefixSeparatorEnd( expToken );
+ break;
+ case TokenFlag.Separator_Middle:
+ TryAppendMiddleSeparator( expToken );
+ break;
+ case TokenFlag.Index_Left:
+ TryAppendIndexLeft( expToken );
+ break;
+ case TokenFlag.Index_Right:
+ TryAppendIndexRight( expToken );
+ break;
+ case TokenFlag.Member:
+ TryAppendMember( expToken );
+ break;
+ default:
+ break;
+ }
+ }
+
+ public ExpSyntaxNode GetNextOperandCache()
+ {
+ if( _cache.PopOperand( out Token t, out ExpSyntaxNode? n ) )
+ {
+ return n;
+ } else
+ {
+ // process some rare case here
+ }
+
+ throw new NotImplementedException();
+ }
+
+ public enum ExpCompileStateCode
+ {
+
+ Common,
+ ForLoop,
+ RepeatLoop,
+ UntilLoop,
+ IfBranch,
+ CaseBranch,
+ CollectionIndex,
+
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/Analyser/StepDataSectionsTranmitter.cs b/StgSharp.Model/STEP/Analyser/StepDataSectionsTranmitter.cs
new file mode 100644
index 00000000..8a968c99
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/StepDataSectionsTranmitter.cs
@@ -0,0 +1,104 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepDataSectionsTranmitter.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Script;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ public class StepDataSectionTransmitter : IScriptSourceProvider
+ {
+
+ private const string EndDataText = "ENDSEC;";
+
+ private bool _isEmpty;
+ private ConcurrentQueue _cache = new ConcurrentQueue();
+ private int _line = 0;
+
+ public bool IsEmpty => _isEmpty;
+
+ public bool IsWriting { get; private set; } = true;
+
+ public int Location => _line;
+
+ public void EndWriting()
+ {
+ _cache.Enqueue( EndDataText );
+ IsWriting = false;
+ }
+
+ public string ReadLine()
+ {
+ _cache.TryDequeue( out string? line );
+ while( !IsEmpty )
+ {
+ if( _cache.TryDequeue( out line ) )
+ {
+ if( line == EndDataText )
+ {
+ _isEmpty = true;
+ return string.Empty;
+ }
+ _line++;
+ return line;
+ }
+ }
+ return string.Empty;
+ }
+
+ public string ReadLine( out int position )
+ {
+ string ret = ReadLine();
+ position = _line;
+ return ret;
+ }
+
+ public void WriteLine( string line )
+ {
+ if( line == EndDataText ) {
+ EndWriting();
+ }
+ _cache.Enqueue( line );
+ }
+
+ IScriptSourceProvider IScriptSourceProvider.Slice( int location, int count )
+ {
+ throw new NotSupportedException();
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/Analyser/StepDataTokenReader.cs b/StgSharp.Model/STEP/Analyser/StepDataTokenReader.cs
new file mode 100644
index 00000000..0ee131ce
--- /dev/null
+++ b/StgSharp.Model/STEP/Analyser/StepDataTokenReader.cs
@@ -0,0 +1,117 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepDataTokenReader.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Modeling.Step;
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Text.RegularExpressions;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ public class StepDataTokenReader : IScriptTokenReader
+ {
+
+ private ExpTokenReader _reader;
+
+ private HashSet token1Hash = [
+ "T","F","UNSPECIFIED"
+ ];
+ private Queue _cache = new Queue();
+ private StepDataSectionTransmitter _transmitter;
+
+ public StepDataTokenReader( StepDataSectionTransmitter transmitter )
+ {
+ _reader = new ExpTokenReader( transmitter );
+ _reader.TokenReaderPreProcessor = new TokenPreReader();
+ _transmitter = transmitter;
+ }
+
+ public bool IsEmpty
+ {
+ get => _reader.IsEmpty && _transmitter.IsWriting;
+ }
+
+ public Token ReadToken()
+ {
+ return _reader.ReadToken();
+ }
+
+ public bool TryReadToken( out Token t )
+ {
+ return _reader.TryReadToken( out t );
+ }
+
+ private class TokenPreReader : ExpTokenReaderPreProcessor
+ {
+
+ private static Regex NextEnumPattern = GetNextEnumPattern();
+
+ public override bool Process( string codeLine, int line, ref int current, out Token t )
+ {
+ ReadOnlySpan chars = codeLine.AsSpan( current );
+ char c = chars[ 0 ];
+ if( c != '.' )
+ {
+ t = Token.Empty;
+ return false;
+ }
+ Match match = NextEnumPattern.Match( codeLine, current );
+ if( match.Success )
+ {
+ int begin = match.Groups[ "begin" ].Index;
+ int end = match.Groups[ "end" ].Length;
+ int rest = match.Groups[ "rets" ].Length;
+ current = rest;
+ t = new Token( match.Groups[ "begin" ].Value, line, begin, TokenFlag.Enum );
+ return true;
+ } else
+ {
+ t = Token.Empty;
+ return false;
+ }
+ }
+
+ [GeneratedRegex(
+ @"(?\.[A-Za-z_]+\.)(?\s*)(?\S*)",
+ RegexOptions.Singleline )]
+ private static extern Regex GetNextEnumPattern();
+
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/ExpressStepUtil.cs b/StgSharp.Model/STEP/ExpressStepUtil.cs
new file mode 100644
index 00000000..4b15719c
--- /dev/null
+++ b/StgSharp.Model/STEP/ExpressStepUtil.cs
@@ -0,0 +1,142 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="ExpressStepUtil.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the ¡°Software¡±), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED ¡°AS IS¡±,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Modeling.Step;
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Frozen;
+using System.Collections.Generic;
+using System.Runtime.CompilerServices;
+
+namespace StgSharp.Modeling.Step
+{
+ public class ExpressStepUtil : ExpSchema
+ {
+
+ public const string AdvancedFaceText = "ADVANCED_FACE";
+ public const string Axis2Placement2DText = "AXIS2_PLACEMENT_2D";
+ public const string Axis2Placement3DText = "AXIS2_PLACEMENT_3D";
+ public const string BSplineCurveWithKnotsText = "B_SPLINE_CURVE_WITH_KNOTS";
+ public const string CartesianPointText = "CARTESIAN_POINT";
+ public const string CircleText = "CIRCLE";
+ public const string CylindricalSurfaceText = "CYLINDRICAL_SURFACE";
+ public const string DirectionText = "DIRECTION";
+ public const string EdgeCurveText = "EDGE_CURVE";
+ public const string EdgeLoopText = "EDGE_LOOP";
+ public const string EllipseText = "ELLIPSE";
+ public const string FaceBoundText = "FACE_BOUND";
+ public const string FaceOuterBoundText = "FACE_OUTER_BOUND";
+ public const string LineText = "LINE";
+ public const string OrientedEdgeText = "ORIENTED_EDGE";
+ public const string PlaneText = "PLANE";
+ public const string VectorText = "VECTOR";
+ public const string VertexPointText = "VERTEX_POINT";
+
+ private static
+ HashSet names = [
+ AdvancedFaceText,
+ Axis2Placement2DText,
+ Axis2Placement3DText,
+ BSplineCurveWithKnotsText,
+ CartesianPointText,
+ CircleText,
+ CylindricalSurfaceText,
+ DirectionText,
+ EdgeCurveText,
+ EdgeLoopText,
+ EllipseText,
+ FaceBoundText,
+ FaceOuterBoundText,
+ LineText,
+ OrientedEdgeText,
+ PlaneText,
+ VectorText,
+ VertexPointText,
+ ];
+
+ private FrozenDictionary entitiesDefine;
+
+ public ExpressStepUtil()
+ {
+ Dictionary tIndex = new Dictionary();
+ }
+
+ internal StepModel Current { get; set; }
+
+ public override void LoadFromSource( ExpSchemaSource source )
+ {
+ return;
+ }
+
+ public override bool TryGetConst( string name, out ExpElementInstance c )
+ {
+ c = null!;
+ return false;
+ }
+
+ public override bool TryGetEntity( string name, out ExpEntitySource e )
+ {
+ e = null!;
+ return false;
+ }
+
+ public override bool TryGetFunction( string name, out ExpFunctionSource f )
+ {
+ throw new NotImplementedException();
+ }
+
+ public override bool TryGetProcedure( string name, out ExpProcedureSource p )
+ {
+ p = null!;
+ return false;
+ }
+
+ public override bool TryGetRule( string name, out ExpRuleSource r )
+ {
+ r = null!;
+ return false;
+ }
+
+ public override bool TryGetSchemaInclude( string name, out ExpSchema include )
+ {
+ include = null!;
+ return false;
+ }
+
+ public override bool TryGetType( string name, out ExpTypeSource t )
+ {
+ t = null!;
+ return false;
+ }
+
+ }
+}
\ No newline at end of file
diff --git a/StgSharp.Model/STEP/StepItemType.cs b/StgSharp.Model/STEP/StepItemType.cs
new file mode 100644
index 00000000..e1431272
--- /dev/null
+++ b/StgSharp.Model/STEP/StepItemType.cs
@@ -0,0 +1,63 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepItemType.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the ¡°Software¡±), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED ¡°AS IS¡±,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Modeling.Step;
+using StgSharp.Script;
+
+using System;
+
+namespace StgSharp.Modeling.Step
+{
+ public enum StepItemType
+ {
+
+ Unknown,
+ AdvancedFace,
+ AxisPlacement2D,
+ AxisPlacement3D,
+ BSplineCurveWithKnots,
+ CartesianPoint,
+ Circle,
+ CylindricalSurface,
+ Direction,
+ EdgeCurve,
+ EdgeLoop,
+ Ellipse,
+ FaceBound,
+ FaceOuterBound,
+ Line,
+ OrientedEdge,
+ Plane,
+ Vector,
+ VertexPoint
+
+ }
+}
+
diff --git a/StgSharp.Model/STEP/StepReader.DataSectionReader.cs b/StgSharp.Model/STEP/StepReader.DataSectionReader.cs
new file mode 100644
index 00000000..ea5a4ba1
--- /dev/null
+++ b/StgSharp.Model/STEP/StepReader.DataSectionReader.cs
@@ -0,0 +1,75 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepDataReader.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Modeling.Step;
+using StgSharp.Modeling.Step;
+using StgSharp.Script;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.Diagnostics.CodeAnalysis;
+using System.IO;
+using System.IO.MemoryMappedFiles;
+using System.Text;
+using System.Text.RegularExpressions;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ public partial class StepReader
+ {
+
+ public StepDataSectionTransmitter DataTransmitter { get; } = new StepDataSectionTransmitter(
+ );
+
+ public async void ReadDataSection()
+ {
+ using( MemoryMappedViewStream ms = _memoryFile.CreateViewStream(
+ 0, _size, MemoryMappedFileAccess.Read ) )
+ {
+ StreamReader sr = new StreamReader( ms );
+ long pos = _headStart;
+ string line;
+ while( string.IsNullOrEmpty( line = sr.ReadLine()! ) ) {
+ DataTransmitter.WriteLine( line );
+ }
+ sr.Dispose();
+ }
+ }
+
+ [GeneratedRegex(
+ @"^#(?[0-9]+)\s*?=\s*?(?\S.*?)\s*;$",
+ RegexOptions.Compiled | RegexOptions.Singleline )]
+ private static partial Regex GetExpressionSplitter();
+
+ }
+}
diff --git a/StgSharp.Model/STEP/StepReader.HeadReader.cs b/StgSharp.Model/STEP/StepReader.HeadReader.cs
new file mode 100644
index 00000000..5892aca7
--- /dev/null
+++ b/StgSharp.Model/STEP/StepReader.HeadReader.cs
@@ -0,0 +1,111 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepHeadReader.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the ¡°Software¡±), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED ¡°AS IS¡±,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.IO.MemoryMappedFiles;
+using System.Runtime.Serialization;
+using System.Text;
+using System.Text.RegularExpressions;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ public partial class StepReader
+ {
+
+ private static Regex expressionSplitter = new Regex(
+ @"^(?[A-Z_]+)\s?\((?.+)\)\;", RegexOptions.Compiled );
+ /**/
+ private StepInfo _info;
+
+ public StepInfo GetInfo()
+ {
+ if( _info is not null ) {
+ return _info;
+ }
+ StepInfo info = new StepInfo();
+ List constructorList = new List();
+ using( MemoryMappedViewStream ms = _memoryFile.CreateViewStream(
+ 0, _size, MemoryMappedFileAccess.Read ) )
+ {
+ using( StreamReader sr = new StreamReader( ms ) )
+ {
+ long pos = _headStart;
+ ms.Seek( _headStart, SeekOrigin.Begin );
+ while( pos <= _headEnd )
+ {
+ string token = ReadToken( sr, ref pos );
+ if( token == "HEADER;" )
+ {
+ continue;
+ }
+
+ if( token == "ENDSEC;" )
+ {
+ break;
+ }
+
+ GroupCollection match = expressionSplitter.Match( token ).Groups;
+ constructorList.Add(
+ new StepObjectConstructor(
+ 0, match[ "CALLER" ].ToString(), match[ "PARAM" ].ToString() ) );
+ }
+ foreach( StepObjectConstructor constructor in constructorList )
+ {
+ switch( constructor.Caller )
+ {
+ case "FILE_DESCRIPTION":
+ info.Description = StepDataParser.ToString( constructor[ 0 ] );
+ info.Level = StepDataParser.ToVersion( constructor[ 1 ] );
+ break;
+ case "FILE_NAME":
+ info.Name = StepDataParser.ToString( constructor[ 0 ] );
+ info.TimeStamp = StepDataParser.ToDateTime( constructor[ 1 ] );
+ info.Author = StepDataParser.ToString( constructor[ 2 ] );
+ info.Organization = StepDataParser.ToString( constructor[ 3 ] );
+ info.PreprocessorVersion = StepDataParser.ToString(
+ constructor[ 4 ] );
+ info.OriginatingSystem = StepDataParser.ToString( constructor[ 5 ] );
+ info.Authorization = StepDataParser.ToString( constructor[ 6 ] );
+ break;
+ default:
+ break;
+ }
+ }
+ }
+ }
+ return info;
+ }
+ /**/
+
+ }
+}
\ No newline at end of file
diff --git a/StgSharp.Model/STEP/StepReader.ToModel.cs b/StgSharp.Model/STEP/StepReader.ToModel.cs
new file mode 100644
index 00000000..fb4a9799
--- /dev/null
+++ b/StgSharp.Model/STEP/StepReader.ToModel.cs
@@ -0,0 +1,106 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepReader.ToModel.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ public partial class StepReader
+ {
+
+ private volatile int _version = 0;
+ private StepDataTokenReader tokenReader;
+
+ private StepExpSyntaxAnalyzer analyzer;
+
+ private StepModel Model { get; set; }
+
+ private Task ReadToModelTask { get; set; }
+
+ public StepModel ReadToModel()
+ {
+ if( Model is not null ) {
+ return Model;
+ }
+ if( _version != 0 ) {
+ throw new InvalidOperationException(
+ "A ReadToModel method has been called and is running now, use Async version instead" );
+ }
+ Interlocked.Increment( ref _version );
+ GetInfo();
+ tokenReader = new StepDataTokenReader( DataTransmitter );
+ analyzer = new StepExpSyntaxAnalyzer();
+ Task secTask = Task.Run( ReadDataSection );
+ Task anTask = Task.Run( ReadStepToken );
+ ConcurrentQueue initStatements = analyzer.StepEntityInitStatements;
+ Model = new StepModel( _info );
+ while( initStatements.TryDequeue( out ExpSyntaxNode? statement ) || !anTask.IsCompleted )
+ {
+ if( statement is null )
+ {
+ Thread.Sleep( 0 );
+ continue;
+ }
+ StepUninitializedEntity entity = StepUninitializedEntity.FromSyntax(
+ Model, statement );
+ Model.AddUncertainEntity( entity.Id, entity );
+ }
+ Task.WaitAll( secTask, anTask );
+ return Model;
+ }
+
+ public async Task ReadToModelAsync()
+ {
+ if( ReadToModelTask is null ) {
+ ReadToModelTask = Task.Run( ReadToModel );
+ }
+ return await ReadToModelTask;
+ }
+
+ private void ReadStepToken()
+ {
+ while( !tokenReader.IsEmpty )
+ {
+ Token t = tokenReader.ReadToken();
+ analyzer.AppendToken( t );
+ }
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/StepReader.cs b/StgSharp.Model/STEP/StepReader.cs
new file mode 100644
index 00000000..0c2f685f
--- /dev/null
+++ b/StgSharp.Model/STEP/StepReader.cs
@@ -0,0 +1,172 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepReader.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp;
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.IO;
+using System.IO.MemoryMappedFiles;
+using System.Linq;
+using System.Text;
+using System.Text.RegularExpressions;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace StgSharp.Modeling.Step
+{
+ public partial class StepReader : IDisposable
+ {
+
+ private const string fileLabel = "ISO-10303-21;";
+
+ private bool disposedValue;
+ private FileStream _fileStream;
+ private long _headStart = -1, _headEnd = -1, _dataStart = -1, _size;
+ private MemoryMappedFile _memoryFile;
+
+ private StepReader() { }
+
+ private StepReader( FileStream stream, long size )
+ {
+ _fileStream = stream;
+ _size = size;
+ _memoryFile = MemoryMappedFile.CreateFromFile(
+ stream, mapName: null, size, MemoryMappedFileAccess.Read, HandleInheritability.None,
+ leaveOpen: true );
+ }
+
+ // ~StepReader()
+ // {
+ // Dispose(disposing: false);
+ // }
+
+ public void Dispose()
+ {
+ Dispose( disposing: true );
+ GC.SuppressFinalize( this );
+ }
+
+ public static bool FromFile( string path, out StepReader reader )
+ {
+ FileInfo info = new FileInfo( path );
+ if( !info.Exists )
+ {
+ reader = null!;
+ return false;
+ }
+ FileStream stream = new FileStream(
+ path, FileMode.Open, FileAccess.Read, FileShare.Read, bufferSize: 4096,
+ useAsync: true );
+ byte[] fileHead = new byte[40];
+ stream.Read( fileHead, 0, fileLabel.Length );
+ if( !Encoding.UTF8.GetString( fileHead ).Contains( fileLabel ) ) {
+ throw new InvalidDataException( "The given file is not a STEP file" );
+ }
+ reader = new StepReader( stream, info.Length );
+ reader.LocateSection();
+ return reader != null;
+ }
+
+ private void LocateSection()
+ {
+ long startPos = 0;
+ byte[] buffer = new byte[1024];
+ Span bufferSpan = buffer,
+ headerSec = Encoding.UTF8.GetBytes( "HEADER;" ),
+ endsecSec = Encoding.UTF8.GetBytes( "ENDSEC;" ),
+ dataSec = Encoding.UTF8.GetBytes( "DATA;" );
+ _fileStream.Position = 0;
+ for( ; startPos < _size; startPos += 1000 )
+ {
+ _fileStream.Read( buffer );
+ if( _headStart == -1 )
+ {
+ long pos = bufferSpan.IndexOf( headerSec );
+ if( pos >= 0 ) {
+ _headStart = startPos + pos;
+ }
+ }
+ if( _headEnd == -1 )
+ {
+ long pos = bufferSpan.IndexOf( endsecSec );
+ if( pos >= 0 ) {
+ _headEnd = startPos + pos;
+ }
+ }
+ if( _dataStart == -1 )
+ {
+ long pos = bufferSpan.IndexOf( dataSec );
+ if( pos >= 0 ) {
+ _dataStart = startPos + pos;
+ }
+ } else
+ {
+ break;
+ }
+ _fileStream.Seek( 1000, SeekOrigin.Current );
+ }
+ }
+
+ private string ReadToken( StreamReader reader, ref long posCache )
+ {
+ StringBuilder token = new StringBuilder( 100 );
+ while( token.Length == 0 || token[ token.Length - 1 ] != ';' )
+ {
+ string subString = reader.ReadLine()!;
+ if( subString == null )
+ {
+ break;
+ }
+ token.Append( subString.TrimStart() );
+ }
+ posCache += token.Length;
+ return token.ToString();
+ }
+
+ private protected virtual void Dispose( bool disposing )
+ {
+ if( !disposedValue )
+ {
+ if( disposing )
+ {
+ _fileStream.Dispose();
+ _memoryFile.Dispose();
+ }
+
+ disposedValue = true;
+ }
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/SyntaxNode/StepComplexEntityNode.cs b/StgSharp.Model/STEP/SyntaxNode/StepComplexEntityNode.cs
new file mode 100644
index 00000000..d5cf4928
--- /dev/null
+++ b/StgSharp.Model/STEP/SyntaxNode/StepComplexEntityNode.cs
@@ -0,0 +1,67 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepComplexEntityNode.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace StgSharp.Model.Step
+{
+ public class StepComplexEntityNode : ExpSyntaxNode
+ {
+
+ private ExpSyntaxNode _begin;
+
+ public StepComplexEntityNode( ExpSyntaxNode node )
+ : base( node.Source )
+ {
+ _begin = node;
+ }
+
+ public override ExpSyntaxNode Left => Empty;
+
+ public override ExpSyntaxNode Right => _begin;
+
+ public override IExpElementSource EqualityTypeConvert => throw new NotImplementedException();
+
+ public StepComplexEntityNode FromTuple( ExpSyntaxNode node )
+ {
+ if( node is not ExpTupleNode tuple ) {
+ throw new ExpInvalidSyntaxException( "Node to convert is not a complex" );
+ }
+ return new StepComplexEntityNode( tuple.Right );
+ }
+
+ }
+}
diff --git a/StgSharp.Model/STEP/SyntaxNode/StepEntityInitCaller.cs b/StgSharp.Model/STEP/SyntaxNode/StepEntityInitCaller.cs
new file mode 100644
index 00000000..a96f430d
--- /dev/null
+++ b/StgSharp.Model/STEP/SyntaxNode/StepEntityInitCaller.cs
@@ -0,0 +1,68 @@
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// file="StepEntityInitCaller.cs"
+// Project: StgSharp
+// AuthorGroup: Nitload Space
+// Copyright (c) Nitload Space. All rights reserved.
+//
+// Permission is hereby granted, free of charge, to any person
+// obtaining a copy of this software and associated documentation
+// files (the “Software”), to deal in the Software without restriction,
+// including without limitation the rights to use, copy, modify, merge,
+// publish, distribute, sublicense, and/or sell copies of the Software,
+// and to permit persons to whom the Software is furnished to do so,
+// subject to the following conditions:
+//
+// The above copyright notice and
+// this permission notice shall be included in all copies
+// or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED “AS IS”,
+// WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
+// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+// ARISING FROM, OUT OF OR IN CONNECTION WITH
+// THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+using Microsoft.CodeAnalysis.CSharp.Syntax;
+
+using StgSharp.Modeling.Step;
+using StgSharp.Script;
+using StgSharp.Script.Express;
+
+using System;
+using System.Collections.Concurrent;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace StgSharp.Model.Step.SyntaxNode
+{
+ public class StepEntityInitCaller : ExpFunctionSource
+ {
+
+ private static Dictionary _callers = new();
+
+ private StepEntityInitCaller( string name )
+ : base( name, null )
+ {
+ ReturningType = StepEntityType.Source;
+ }
+
+ public static StepEntityInitCaller CreateCaller( string name )
+ {
+ if( _callers.TryGetValue( name, out StepEntityInitCaller? caller ) ) {
+ return caller;
+ }
+ caller = new StepEntityInitCaller( name );
+ _callers.Add( name, caller );
+ return caller;
+ }
+
+ }
+}
diff --git a/StgSharp.Model/obj/x64/Debug/net8.0/StgSharp.Model.AssemblyInfo.cs b/StgSharp.Model/obj/x64/Debug/net8.0/StgSharp.Model.AssemblyInfo.cs
index 52577371..f8722827 100644
--- a/StgSharp.Model/obj/x64/Debug/net8.0/StgSharp.Model.AssemblyInfo.cs
+++ b/StgSharp.Model/obj/x64/Debug/net8.0/StgSharp.Model.AssemblyInfo.cs
@@ -14,7 +14,7 @@ using System.Reflection;
[assembly: System.Reflection.AssemblyCompanyAttribute("StgSharp.Model")]
[assembly: System.Reflection.AssemblyConfigurationAttribute("Debug")]
[assembly: System.Reflection.AssemblyFileVersionAttribute("1.0.0.0")]
-[assembly: System.Reflection.AssemblyInformationalVersionAttribute("1.0.0+b618fdf7b5295b190dcc6b7168e038d1d5a11455")]
+[assembly: System.Reflection.AssemblyInformationalVersionAttribute("1.0.0+a0f7476291d65b51de2055f8b2d69fa44348d04b")]
[assembly: System.Reflection.AssemblyProductAttribute("StgSharp.Model")]
[assembly: System.Reflection.AssemblyTitleAttribute("StgSharp.Model")]
[assembly: System.Reflection.AssemblyVersionAttribute("1.0.0.0")]
diff --git a/StgSharp.Script/Common/IScriptTokenReader.cs b/StgSharp.Script/Common/IScriptTokenReader.cs
index 43186003..88a3b380 100644
--- a/StgSharp.Script/Common/IScriptTokenReader.cs
+++ b/StgSharp.Script/Common/IScriptTokenReader.cs
@@ -33,6 +33,8 @@ namespace StgSharp.Script
public interface IScriptTokenReader
{
+ bool IsEmpty { get; }
+
Token ReadToken();
bool TryReadToken( out Token t );
diff --git a/StgSharp.Script/Express/Element/ExpFunction.cs b/StgSharp.Script/Express/Element/ExpFunction.cs
index 5451e118..e2cc7961 100644
--- a/StgSharp.Script/Express/Element/ExpFunction.cs
+++ b/StgSharp.Script/Express/Element/ExpFunction.cs
@@ -54,6 +54,8 @@ namespace StgSharp.Script.Express
public override ExpElementType ElementType => ExpElementType.Function;
+ public IExpElementSource ReturningType { get; protected set; }
+
public override IScriptSourceProvider SourceProvider => _transmitter;
public override string Name => _name;
diff --git a/StgSharp.Script/Express/ExpAstNode/ExpBinaryOperatorNode.cs b/StgSharp.Script/Express/ExpAstNode/ExpBinaryOperatorNode.cs
index fdb39a41..a713a449 100644
--- a/StgSharp.Script/Express/ExpAstNode/ExpBinaryOperatorNode.cs
+++ b/StgSharp.Script/Express/ExpAstNode/ExpBinaryOperatorNode.cs
@@ -61,6 +61,8 @@ namespace StgSharp.Script.Express
public override ExpSyntaxNode Right => _right;
+ public string Operator { get; private set; }
+
public static ExpBinaryOperatorNode Add(
Token source,
ExpSyntaxNode left,
@@ -93,6 +95,7 @@ namespace StgSharp.Script.Express
{
_returnType = ExpInstantiableElement.Void,
_nodeFlag = ExpNodeFlag.Operator_Binary | left._nodeFlag,
+ Operator = "=",
CodeConvertTemplate = "{0} = {1}",
};
}
@@ -111,11 +114,11 @@ namespace StgSharp.Script.Express
}
public static ExpBinaryOperatorNode CompareInstanceNotEqual(
- Token nsource,
+ Token source,
ExpSyntaxNode left,
ExpSyntaxNode right )
{
- return new ExpBinaryOperatorNode( nsource, left, right )
+ return new ExpBinaryOperatorNode( source, left, right )
{
_returnType = ExpressCompile.ExpBool,
_nodeFlag = ExpNodeFlag.BuiltinType_Boolean | ExpNodeFlag.Operator_Binary,
@@ -128,13 +131,13 @@ namespace StgSharp.Script.Express
ExpSyntaxNode left,
ExpSyntaxNode right )
{
- if( right is not ExpMetaRefNode metaref ) {
+ if( right is not ExpMetaRefNode metaRef ) {
throw new ExpInvalidTypeException(
"", right.EqualityTypeConvert.Name );
}
return new ExpBinaryOperatorNode( source, left, right )
{
- _returnType = metaref.SourceRef,
+ _returnType = metaRef.SourceRef,
_nodeFlag = ExpNodeFlag.Operator_Binary,
/*
* 0. instance to convert
diff --git a/StgSharp.Script/Express/ExpAstNode/ExpElementInitializingNode.cs b/StgSharp.Script/Express/ExpAstNode/ExpElementInitializingNode.cs
index 475bdd31..de80c358 100644
--- a/StgSharp.Script/Express/ExpAstNode/ExpElementInitializingNode.cs
+++ b/StgSharp.Script/Express/ExpAstNode/ExpElementInitializingNode.cs
@@ -65,6 +65,9 @@ namespace StgSharp.Script.Express
ExpMetaRefNode type,
ExpSyntaxNode init )
{
+ if( init is ExpTupleNode tupleNode ) {
+ init = tupleNode.Right;
+ }
ExpElementInitializingNode node = new ExpElementInitializingNode( source, type, init );
return node;
}
diff --git a/StgSharp.Script/Express/ExpAstNode/ExpFunctionCallingNode.cs b/StgSharp.Script/Express/ExpAstNode/ExpFunctionCallingNode.cs
index d81fd1fc..16ebc340 100644
--- a/StgSharp.Script/Express/ExpAstNode/ExpFunctionCallingNode.cs
+++ b/StgSharp.Script/Express/ExpAstNode/ExpFunctionCallingNode.cs
@@ -58,8 +58,7 @@ namespace StgSharp.Script.Express
public ExpFunctionSource FunctionCaller => _function;
- public override ExpInstantiableElement EqualityTypeConvert => throw new NotImplementedException(
- );
+ public override ExpInstantiableElement EqualityTypeConvert => _function.;
public override ExpSyntaxNode Left => Empty;
@@ -75,6 +74,9 @@ namespace StgSharp.Script.Express
ExpFunctionSource function,
ExpSyntaxNode param )
{
+ if( param is ExpTupleNode ) {
+ param = param.Right;
+ }
return new ExpFunctionCallingNode( source, function, param );
}