Skip to content

Commit e3473d0

Browse files
committed
In JavaScript engine settings was added one new property - MaxStackSize (default 492 or 984 KB)
1 parent 2c39c15 commit e3473d0

File tree

9 files changed

+127
-31
lines changed

9 files changed

+127
-31
lines changed

src/MsieJavaScriptEngine/ActiveScript/ActiveScriptJsEngineBase.cs

Lines changed: 35 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -49,11 +49,6 @@ internal abstract partial class ActiveScriptJsEngineBase : InnerJsEngineBase
4949
/// </summary>
5050
private ActiveScriptException _lastException;
5151

52-
/// <summary>
53-
/// Instance of script dispatcher
54-
/// </summary>
55-
private static readonly ScriptDispatcher _dispatcher = new ScriptDispatcher();
56-
5752
/// <summary>
5853
/// Instance of process debug manager wrapper
5954
/// </summary>
@@ -104,6 +99,16 @@ internal abstract partial class ActiveScriptJsEngineBase : InnerJsEngineBase
10499
/// </summary>
105100
protected bool _interruptRequested;
106101

102+
/// <summary>
103+
/// Instance of script dispatcher
104+
/// </summary>
105+
private static ScriptDispatcher _dispatcher;
106+
107+
/// <summary>
108+
/// Synchronizer of script dispatcher initialization
109+
/// </summary>
110+
private static readonly object _dispatcherSynchronizer = new object();
111+
107112

108113
/// <summary>
109114
/// Constructs an instance of the Active Script engine
@@ -117,6 +122,8 @@ protected ActiveScriptJsEngineBase(JsEngineSettings settings, string clsid,
117122
ScriptLanguageVersion languageVersion, string lowerIeVersion, string errorCategoryNamePrefix)
118123
: base(settings)
119124
{
125+
InitScriptDispatcher(_settings.MaxStackSize);
126+
120127
_lowerIeVersion = lowerIeVersion;
121128
_errorCategoryNamePrefix = errorCategoryNamePrefix;
122129

@@ -173,6 +180,29 @@ protected ActiveScriptJsEngineBase(JsEngineSettings settings, string clsid,
173180
}
174181

175182

183+
/// <summary>
184+
/// Initializes a script dispatcher
185+
/// </summary>
186+
/// <param name="maxStackSize">The maximum stack size, in bytes, to be used by the thread,
187+
/// or 0 to use the default maximum stack size specified in the header for the executable.</param>
188+
private static void InitScriptDispatcher(int maxStackSize)
189+
{
190+
if (_dispatcher != null)
191+
{
192+
return;
193+
}
194+
195+
lock (_dispatcherSynchronizer)
196+
{
197+
if (_dispatcher != null)
198+
{
199+
return;
200+
}
201+
202+
_dispatcher = new ScriptDispatcher(maxStackSize);
203+
}
204+
}
205+
176206
/// <summary>
177207
/// Checks a support of the JS engine on the machine
178208
/// </summary>

src/MsieJavaScriptEngine/JsEngineSettings.cs

Lines changed: 53 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,32 @@
1-
namespace MsieJavaScriptEngine
1+
using System;
2+
3+
using MsieJavaScriptEngine.Resources;
4+
using MsieJavaScriptEngine.Utilities;
5+
6+
namespace MsieJavaScriptEngine
27
{
38
/// <summary>
49
/// JS engine settings
510
/// </summary>
611
public sealed class JsEngineSettings
712
{
13+
#if !NETSTANDARD1_3
14+
/// <summary>
15+
/// The stack size is sufficient to run the code of modern JavaScript libraries in 32-bit process
16+
/// </summary>
17+
const int STACK_SIZE_32 = 492 * 1024; // like 32-bit Node.js
18+
19+
/// <summary>
20+
/// The stack size is sufficient to run the code of modern JavaScript libraries in 64-bit process
21+
/// </summary>
22+
const int STACK_SIZE_64 = 984 * 1024; // like 64-bit Node.js
23+
24+
/// <summary>
25+
/// The maximum stack size in bytes
26+
/// </summary>
27+
private int _maxStackSize;
28+
29+
#endif
830
/// <summary>
931
/// Gets or sets a flag for whether to enable script debugging features
1032
/// </summary>
@@ -22,6 +44,33 @@ public JsEngineMode EngineMode
2244
get;
2345
set;
2446
}
47+
#if !NETSTANDARD1_3
48+
49+
/// <summary>
50+
/// Gets or sets a maximum stack size in bytes
51+
/// </summary>
52+
/// <remarks>
53+
/// <para>Set a <code>0</code> to use the default maximum stack size specified in the header
54+
/// for the executable.
55+
/// </para>
56+
/// </remarks>
57+
public int MaxStackSize
58+
{
59+
get { return _maxStackSize; }
60+
set
61+
{
62+
if (value < 0)
63+
{
64+
throw new ArgumentOutOfRangeException(
65+
nameof(value),
66+
CommonStrings.Engine_MaxStackSizeMustBeNonNegative
67+
);
68+
}
69+
70+
_maxStackSize = value;
71+
}
72+
}
73+
#endif
2574

2675
/// <summary>
2776
/// Gets or sets a flag for whether to use the ECMAScript 5 Polyfill
@@ -49,6 +98,9 @@ public JsEngineSettings()
4998
{
5099
EnableDebugging = false;
51100
EngineMode = JsEngineMode.Auto;
101+
#if !NETSTANDARD1_3
102+
MaxStackSize = Utils.Is64BitProcess() ? STACK_SIZE_64 : STACK_SIZE_32;
103+
#endif
52104
UseEcmaScript5Polyfill = false;
53105
UseJson2Library = false;
54106
}

src/MsieJavaScriptEngine/JsRt/ChakraJsRtJsEngineBase.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,11 @@ internal abstract class ChakraJsRtJsEngineBase : InnerJsEngineBase
4848
protected ChakraJsRtJsEngineBase(JsEngineSettings settings)
4949
: base(settings)
5050
{
51+
#if NETSTANDARD1_3
5152
_dispatcher = new ScriptDispatcher();
53+
#else
54+
_dispatcher = new ScriptDispatcher(settings.MaxStackSize);
55+
#endif
5256
#if NETSTANDARD
5357
_externalObjectFinalizeCallback = ExternalObjectFinalizeCallback;
5458
#endif

src/MsieJavaScriptEngine/MsieJavaScriptEngine.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@
2424
<RepositoryUrl>https://github.com/Taritsyn/MsieJavaScriptEngine</RepositoryUrl>
2525
<RepositoryType>git</RepositoryType>
2626
<PackageTags>JavaScript;ECMAScript;MSIE;IE;Edge;Chakra</PackageTags>
27-
<PackageReleaseNotes>Fixed a error, that occurred during the generation of error message.</PackageReleaseNotes>
27+
<PackageReleaseNotes>In JavaScript engine settings was added one new property - `MaxStackSize` (default `492` or `984` KB).</PackageReleaseNotes>
2828
<NeutralLanguage>en-US</NeutralLanguage>
2929
<PackageOutputPath>../../nuget</PackageOutputPath>
3030
<GeneratePackageOnBuild>true</GeneratePackageOnBuild>

src/MsieJavaScriptEngine/Resources/CommonStrings.Designer.cs

Lines changed: 8 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/MsieJavaScriptEngine/Resources/CommonStrings.resx

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -150,6 +150,9 @@
150150
<data name="Engine_JsEngineNotLoaded" xml:space="preserve">
151151
<value>Failed to create instance of the MsieJsEngine in {0} mode.</value>
152152
</data>
153+
<data name="Engine_MaxStackSizeMustBeNonNegative" xml:space="preserve">
154+
<value>Maximum stack size must be non-negative.</value>
155+
</data>
153156
<data name="ErrorDetails_CallStack" xml:space="preserve">
154157
<value>Call stack</value>
155158
</data>

src/MsieJavaScriptEngine/Resources/CommonStrings.ru-ru.resx

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -150,6 +150,9 @@
150150
<data name="Engine_JsEngineNotLoaded" xml:space="preserve">
151151
<value>Не удалось создать экземпляр MsieJsEngine в режиме {0}.</value>
152152
</data>
153+
<data name="Engine_MaxStackSizeMustBeNonNegative" xml:space="preserve">
154+
<value>Максимальный размер стека должен быть неотрицательным!</value>
155+
</data>
153156
<data name="ErrorDetails_CallStack" xml:space="preserve">
154157
<value>Стек вызовов</value>
155158
</data>

src/MsieJavaScriptEngine/ScriptDispatcher.cs

Lines changed: 18 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,35 +1,25 @@
11
using System;
22
using System.Collections.Generic;
3+
using System.Runtime.CompilerServices;
34
#if NET45 || NETSTANDARD
45
using System.Runtime.ExceptionServices;
56
#endif
6-
using System.Runtime.CompilerServices;
77
using System.Threading;
88

9+
#if NET40
910
using MsieJavaScriptEngine.Extensions;
11+
#endif
1012
using MsieJavaScriptEngine.Utilities;
1113

1214
namespace MsieJavaScriptEngine
1315
{
1416
/// <summary>
15-
/// Provides services for managing the queue of script tasks on the thread with increased stack size
17+
/// Provides services for managing the queue of script tasks on the thread with modified stack size
1618
/// </summary>
1719
internal sealed class ScriptDispatcher : IDisposable
1820
{
19-
#if !NETSTANDARD1_3
2021
/// <summary>
21-
/// The stack size is sufficient to run the code of modern JS libraries in 32-bit process
22-
/// </summary>
23-
const int STACK_SIZE_32 = 492 * 1024; // like 32-bit Node.js
24-
25-
/// <summary>
26-
/// The stack size is sufficient to run the code of modern JS libraries in 64-bit process
27-
/// </summary>
28-
const int STACK_SIZE_64 = 984 * 1024; // like 64-bit Node.js
29-
30-
#endif
31-
/// <summary>
32-
/// The thread with increased stack size
22+
/// The thread with modified stack size
3323
/// </summary>
3424
private Thread _thread;
3525

@@ -54,17 +44,22 @@ internal sealed class ScriptDispatcher : IDisposable
5444
private InterlockedStatedFlag _disposedFlag = new InterlockedStatedFlag();
5545

5646

47+
#if NETSTANDARD1_3
5748
/// <summary>
5849
/// Constructs an instance of script dispatcher
5950
/// </summary>
6051
public ScriptDispatcher()
6152
{
62-
#if NETSTANDARD1_3
6353
_thread = new Thread(StartThread)
6454
#else
65-
int sufficientStackSize = Utils.Is64BitProcess() ? STACK_SIZE_64 : STACK_SIZE_32;
66-
67-
_thread = new Thread(StartThread, sufficientStackSize)
55+
/// <summary>
56+
/// Constructs an instance of script dispatcher
57+
/// </summary>
58+
/// <param name="maxStackSize">The maximum stack size, in bytes, to be used by the thread,
59+
/// or 0 to use the default maximum stack size specified in the header for the executable.</param>
60+
public ScriptDispatcher(int maxStackSize)
61+
{
62+
_thread = new Thread(StartThread, maxStackSize)
6863
#endif
6964
{
7065
IsBackground = true
@@ -83,7 +78,7 @@ private void VerifyNotDisposed()
8378
}
8479

8580
/// <summary>
86-
/// Starts a thread with increased stack size.
81+
/// Starts a thread with modified stack size.
8782
/// Loops forever, processing script tasks from the queue.
8883
/// </summary>
8984
private void StartThread()
@@ -139,7 +134,7 @@ private void EnqueueTask(ScriptTask task)
139134
}
140135

141136
/// <summary>
142-
/// Runs a specified delegate on the thread with increased stack size,
137+
/// Runs a specified delegate on the thread with modified stack size,
143138
/// and returns its result as an <see cref="System.Object"/>.
144139
/// Blocks until the invocation of delegate is completed.
145140
/// </summary>
@@ -174,7 +169,7 @@ private object InnnerInvoke(Func<object> del)
174169
}
175170

176171
/// <summary>
177-
/// Runs a specified delegate on the thread with increased stack size,
172+
/// Runs a specified delegate on the thread with modified stack size,
178173
/// and returns its result as an <typeparamref name="T" />.
179174
/// Blocks until the invocation of delegate is completed.
180175
/// </summary>
@@ -195,7 +190,7 @@ public T Invoke<T>(Func<T> func)
195190
}
196191

197192
/// <summary>
198-
/// Runs a specified delegate on the thread with increased stack size.
193+
/// Runs a specified delegate on the thread with modified stack size.
199194
/// Blocks until the invocation of delegate is completed.
200195
/// </summary>
201196
/// <param name="action">Delegate to invocation</param>

src/MsieJavaScriptEngine/readme.txt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,8 @@
2121
=============
2222
RELEASE NOTES
2323
=============
24-
Fixed a error, that occurred during the generation of error message.
24+
In JavaScript engine settings was added one new property - `MaxStackSize`
25+
(default `492` or `984` KB).
2526

2627
============
2728
PROJECT SITE

0 commit comments

Comments
 (0)