diff --git a/Libraries/Opc.Ua.Gds.Client.Common/GlobalDiscoveryServerClient.cs b/Libraries/Opc.Ua.Gds.Client.Common/GlobalDiscoveryServerClient.cs
index 2841c8f5a..c1ef8089b 100644
--- a/Libraries/Opc.Ua.Gds.Client.Common/GlobalDiscoveryServerClient.cs
+++ b/Libraries/Opc.Ua.Gds.Client.Common/GlobalDiscoveryServerClient.cs
@@ -68,6 +68,11 @@ public GlobalDiscoveryServerClient(
AdminCredentials = adminUserIdentity;
}
+ ///
+ /// 1MB default max trust list size
+ ///
+ private const int kDefaultMaxTrustListSize = 1 * 1024 * 1024;
+
///
/// Gets the application.
///
@@ -1442,7 +1447,8 @@ public TrustListDataType ReadTrustList(NodeId trustListId)
///
/// Reads the trust list.
///
- public async Task ReadTrustListAsync(NodeId trustListId, CancellationToken ct = default)
+ ///
+ public async Task ReadTrustListAsync(NodeId trustListId, long maxTrustListSize = 0, CancellationToken ct = default)
{
ISession session = await ConnectIfNeededAsync(ct).ConfigureAwait(false);
@@ -1456,6 +1462,14 @@ public async Task ReadTrustListAsync(NodeId trustListId, Canc
using var ostrm = new MemoryStream();
try
{
+ // Use a reasonable maximum size limit for trust lists
+ if (maxTrustListSize == 0)
+ {
+ maxTrustListSize = kDefaultMaxTrustListSize;
+ }
+
+ long totalBytesRead = 0;
+
while (true)
{
const int length = 4096;
@@ -1468,6 +1482,17 @@ public async Task ReadTrustListAsync(NodeId trustListId, Canc
length).ConfigureAwait(false);
byte[] bytes = (byte[])outputArguments[0];
+
+ // Validate total size before writing
+ totalBytesRead += bytes.Length;
+ if (totalBytesRead > maxTrustListSize)
+ {
+ throw ServiceResultException.Create(
+ StatusCodes.BadEncodingLimitsExceeded,
+ "Trust list size exceeds maximum allowed size of {0} bytes",
+ maxTrustListSize);
+ }
+
ostrm.Write(bytes, 0, bytes.Length);
if (length != bytes.Length)
diff --git a/Libraries/Opc.Ua.Gds.Client.Common/ServerPushConfigurationClient.cs b/Libraries/Opc.Ua.Gds.Client.Common/ServerPushConfigurationClient.cs
index e2927da54..d70c73a52 100644
--- a/Libraries/Opc.Ua.Gds.Client.Common/ServerPushConfigurationClient.cs
+++ b/Libraries/Opc.Ua.Gds.Client.Common/ServerPushConfigurationClient.cs
@@ -64,6 +64,11 @@ public ServerPushConfigurationClient(
};
}
+ ///
+ /// 1MB default max trust list size
+ ///
+ private const int kDefaultMaxTrustListSize = 1 * 1024 * 1024;
+
public NodeId DefaultApplicationGroup { get; private set; }
public NodeId DefaultHttpsGroup { get; private set; }
public NodeId DefaultUserTokenGroup { get; private set; }
@@ -462,8 +467,10 @@ public TrustListDataType ReadTrustList(TrustListMasks masks = TrustListMasks.All
///
/// Reads the trust list.
///
+ ///
public async Task ReadTrustListAsync(
TrustListMasks masks = TrustListMasks.All,
+ long maxTrustListSize = 0,
CancellationToken ct = default)
{
ISession session = await ConnectIfNeededAsync(ct).ConfigureAwait(false);
@@ -489,6 +496,14 @@ public async Task ReadTrustListAsync(
using var ostrm = new MemoryStream();
try
{
+ // Use a reasonable maximum size limit for trust lists
+ if (maxTrustListSize == 0)
+ {
+ maxTrustListSize = kDefaultMaxTrustListSize;
+ }
+
+ long totalBytesRead = 0;
+
while (true)
{
const int length = 256;
@@ -510,6 +525,17 @@ public async Task ReadTrustListAsync(
.ConfigureAwait(false);
byte[] bytes = (byte[])outputArguments[0];
+
+ // Validate total size before reading
+ totalBytesRead += bytes.Length;
+ if (totalBytesRead > maxTrustListSize)
+ {
+ throw ServiceResultException.Create(
+ StatusCodes.BadEncodingLimitsExceeded,
+ "Trust list size exceeds maximum allowed size of {0} bytes",
+ maxTrustListSize);
+ }
+
ostrm.Write(bytes, 0, bytes.Length);
if (length != bytes.Length)
@@ -581,7 +607,8 @@ public bool UpdateTrustList(TrustListDataType trustList)
///
/// Updates the trust list.
///
- public async Task UpdateTrustListAsync(TrustListDataType trustList, CancellationToken ct = default)
+ ///
+ public async Task UpdateTrustListAsync(TrustListDataType trustList, long maxTrustListSize = 0, CancellationToken ct = default)
{
ISession session = await ConnectIfNeededAsync(ct).ConfigureAwait(false);
IUserIdentity oldUser = await ElevatePermissionsAsync(session, ct).ConfigureAwait(false);
@@ -595,6 +622,22 @@ public async Task UpdateTrustListAsync(TrustListDataType trustList, Cancel
}
strm.Position = 0;
+ // Use a reasonable maximum size limit for trust lists
+ if (maxTrustListSize == 0)
+ {
+ maxTrustListSize = kDefaultMaxTrustListSize;
+ }
+
+ // Validate trust list size before attempting to write
+ if (strm.Length > maxTrustListSize)
+ {
+ throw ServiceResultException.Create(
+ StatusCodes.BadEncodingLimitsExceeded,
+ "Trust list size {0} exceeds maximum allowed size of {1} bytes",
+ strm.Length,
+ maxTrustListSize);
+ }
+
System.Collections.Generic.IList