Fixes publishing

This commit is contained in:
Kamron Batman 2019-10-04 22:02:19 -07:00
parent 6119774dc9
commit 58be0d416c
No known key found for this signature in database
GPG key ID: 5C9DFD15804B6BB8
53 changed files with 981 additions and 1225 deletions

9
.gitignore vendored
View file

@ -6,13 +6,14 @@
/Distribution/Saves
/Distribution/System.IO.Pipelines.dll
/Distribution/rdrand.so
/Distribution/rdrand32.dll
/Distribution/rdrand64.dll
/Distribution/zlib32.dll
/Distribution/zlib64.dll
/Distribution/rdrand.dll
/Distribution/zlib.dll
/Projects/Scripts/obj
/Projects/Scripts/bin
/Projects/Server/obj
/Projects/Server/bin
*.log
*.user
/.idea
/.vs

View file

@ -101,7 +101,7 @@ namespace Server.Commands
break;
}
Type type = ScriptCompiler.FindTypeByName(name);
Type type = AssemblyHandler.FindTypeByName(name);
if (!IsEntity(type))
{
@ -241,7 +241,7 @@ namespace Server.Commands
try
{
if (IsEnum(type)) return Enum.Parse(type, value, true);
if (IsType(type)) return ScriptCompiler.FindTypeByName(value);
if (IsType(type)) return AssemblyHandler.FindTypeByName(value);
if (IsParsable(type)) return ParseParsable(type, value);
object obj = value;

View file

@ -1016,7 +1016,7 @@ namespace Server.Commands
int indexOf = line.IndexOf(' ');
list.m_Type = ScriptCompiler.FindTypeByName(line.Substring(0, indexOf++), true);
list.m_Type = AssemblyHandler.FindTypeByName(line.Substring(0, indexOf++), true);
if (list.m_Type == null)
throw new ArgumentException($"Type not found for header: '{line}'");

View file

@ -1014,7 +1014,7 @@ namespace Server.Commands
int indexOf = line.IndexOf(' ');
list.m_Type = ScriptCompiler.FindTypeByName(line.Substring(0, indexOf++), true);
list.m_Type = AssemblyHandler.FindTypeByName(line.Substring(0, indexOf++), true);
if (list.m_Type == null)
throw new ArgumentException($"Type not found for header: '{line}'");

View file

@ -667,7 +667,7 @@ namespace Server.Commands
List<Assembly> assemblies = new List<Assembly> { Core.Assembly };
foreach (Assembly asm in ScriptCompiler.Assemblies)
foreach (Assembly asm in AssemblyHandler.Assemblies)
assemblies.Add(asm);
Assembly[] asms = assemblies.ToArray();

View file

@ -144,8 +144,8 @@ namespace Server.Commands
AddTypes(Core.Assembly, types);
for (int i = 0; i < ScriptCompiler.Assemblies.Length; ++i)
AddTypes(ScriptCompiler.Assemblies[i], types);
for (int i = 0; i < AssemblyHandler.Assemblies.Length; ++i)
AddTypes(AssemblyHandler.Assemblies[i], types);
m_RootItems = Load(types, "Data/items.cfg");
m_RootMobiles = Load(types, "Data/mobiles.cfg");
@ -315,7 +315,7 @@ namespace Server.Commands
for (int i = 0; i < split.Length; ++i)
{
Type type = ScriptCompiler.FindTypeByName(split[i].Trim());
Type type = AssemblyHandler.FindTypeByName(split[i].Trim());
if (type == null)
Console.WriteLine("Match type not found ('{0}')", split[i].Trim());

View file

@ -444,7 +444,7 @@ namespace Server.Commands.Generic
{
if (e.Length >= 1)
{
Type t = ScriptCompiler.FindTypeByName(e.GetString(0));
Type t = AssemblyHandler.FindTypeByName(e.GetString(0));
if (t == null)
{
@ -1108,4 +1108,4 @@ namespace Server.Commands.Generic
LogFailure("No house was found.");
}
}
}
}

View file

@ -90,7 +90,7 @@ namespace Server.Commands.Generic
int index = 0;
Type objectType = ScriptCompiler.FindTypeByName(args[offset + index], true);
Type objectType = AssemblyHandler.FindTypeByName(args[offset + index], true);
if (objectType == null)
throw new Exception($"No type with that name ({args[offset + index]}) was found.");

View file

@ -290,7 +290,7 @@ namespace Server.Commands
int count = bin.ReadInt32();
for (int i = 0; i < count; ++i)
types.Add(ScriptCompiler.FindTypeByFullName(bin.ReadString()));
types.Add(AssemblyHandler.FindTypeByFullName(bin.ReadString()));
}
long total = 0;

View file

@ -418,7 +418,7 @@ namespace Server.Commands
else if (IsType(type))
try
{
toSet = ScriptCompiler.FindTypeByName(value);
toSet = AssemblyHandler.FindTypeByName(value);
if (toSet == null)
return "No type with that name was found.";

View file

@ -23,7 +23,7 @@ namespace Server.Engines.BulkOrders
string type = reader.ReadString();
if (type != null)
ItemType = ScriptCompiler.FindTypeByFullName(type);
ItemType = AssemblyHandler.FindTypeByFullName(type);
AmountCur = reader.ReadEncodedInt();
Number = reader.ReadEncodedInt();
@ -53,4 +53,4 @@ namespace Server.Engines.BulkOrders
writer.WriteEncodedInt(Graphic);
}
}
}
}

View file

@ -32,7 +32,7 @@ namespace Server.Engines.BulkOrders
string type = reader.ReadString();
if (type != null)
ItemType = ScriptCompiler.FindTypeByFullName(type);
ItemType = AssemblyHandler.FindTypeByFullName(type);
RequireExceptional = reader.ReadBool();
@ -97,4 +97,4 @@ namespace Server.Engines.BulkOrders
writer.WriteEncodedInt(Price);
}
}
}
}

View file

@ -104,7 +104,7 @@ namespace Server.Engines.BulkOrders
string type = reader.ReadString();
if ( type != null )
realType = ScriptCompiler.FindTypeByFullName( type );
realType = AssemblyHandler.FindTypeByFullName( type );
Details = new SmallBulkEntry( realType, reader.ReadInt(), reader.ReadInt() );
}

View file

@ -201,7 +201,7 @@ namespace Server.Engines.BulkOrders
string type = reader.ReadString();
if (type != null)
Type = ScriptCompiler.FindTypeByFullName(type);
Type = AssemblyHandler.FindTypeByFullName(type);
m_Number = reader.ReadInt();
Graphic = reader.ReadInt();

View file

@ -71,7 +71,7 @@ namespace Server.Engines.BulkOrders
if ( split.Length >= 2 )
{
Type type = ScriptCompiler.FindTypeByName( split[0] );
Type type = AssemblyHandler.FindTypeByName( split[0] );
int graphic = Utility.ToInt32( split[split.Length - 1] );
if ( type != null && graphic > 0 )

View file

@ -299,7 +299,7 @@ namespace Server.Engines.Doom
if (TypeName == null)
return;
Type type = ScriptCompiler.FindTypeByName(TypeName, true);
Type type = AssemblyHandler.FindTypeByName(TypeName, true);
if (type == null)
return;

View file

@ -49,12 +49,12 @@ namespace Server.Factions
m_Factions = new List<Faction>();
m_Towns = new List<Town>();
Assembly[] asms = ScriptCompiler.Assemblies;
Assembly[] asms = AssemblyHandler.Assemblies;
for (int i = 0; i < asms.Length; ++i)
{
Assembly asm = asms[i];
TypeCache tc = ScriptCompiler.GetTypeCache(asm);
TypeCache tc = AssemblyHandler.GetTypeCache(asm);
Type[] types = tc.Types;
for (int j = 0; j < types.Length; ++j)
@ -75,4 +75,4 @@ namespace Server.Factions
}
}
}
}
}

View file

@ -88,7 +88,7 @@ namespace Server.Engines.MLQuests.Items
string typeName = reader.ReadString();
if (typeName != null)
m_QuestType = ScriptCompiler.FindTypeByFullName(typeName, false);
m_QuestType = AssemblyHandler.FindTypeByFullName(typeName, false);
Message = TextDefinition.Deserialize(reader);
}
@ -186,7 +186,7 @@ namespace Server.Engines.MLQuests.Items
string typeName = reader.ReadString();
if (typeName != null)
m_TicketType = ScriptCompiler.FindTypeByFullName(typeName, false);
m_TicketType = AssemblyHandler.FindTypeByFullName(typeName, false);
Message = TextDefinition.Deserialize(reader);
}

View file

@ -47,7 +47,7 @@ namespace Server.Engines.MLQuests
string[] split = line.Split('\t');
Type type = ScriptCompiler.FindTypeByName(split[0]);
Type type = AssemblyHandler.FindTypeByName(split[0]);
if (type == null || !baseQuestType.IsAssignableFrom(type))
{
@ -76,7 +76,7 @@ namespace Server.Engines.MLQuests
for (int i = 1; i < split.Length; ++i)
{
Type questerType = ScriptCompiler.FindTypeByName(split[i]);
Type questerType = AssemblyHandler.FindTypeByName(split[i]);
if (questerType == null || !baseQuesterType.IsAssignableFrom(questerType))
{
@ -157,7 +157,7 @@ namespace Server.Engines.MLQuests
return;
}
Type index = ScriptCompiler.FindTypeByName(e.GetString(0));
Type index = AssemblyHandler.FindTypeByName(e.GetString(0));
if (index == null || !Quests.TryGetValue(index, out MLQuest quest))
{
@ -183,7 +183,7 @@ namespace Server.Engines.MLQuests
return;
}
Type index = ScriptCompiler.FindTypeByName(e.GetString(0));
Type index = AssemblyHandler.FindTypeByName(e.GetString(0));
if (index == null || !Quests.TryGetValue(index, out MLQuest quest))
{
@ -638,7 +638,7 @@ namespace Server.Engines.MLQuests
if (typeName == null)
return null; // not serialized
Type questType = ScriptCompiler.FindTypeByFullName(typeName);
Type questType = AssemblyHandler.FindTypeByFullName(typeName);
if (questType == null)
return null; // no longer a type

View file

@ -63,7 +63,7 @@ namespace Server.Engines.Quests
if (fullName == null)
return null;
return ScriptCompiler.FindTypeByFullName(fullName, false);
return AssemblyHandler.FindTypeByFullName(fullName, false);
}
}
}
@ -185,4 +185,4 @@ namespace Server.Engines.Quests
}
}
}
}
}

View file

@ -6,7 +6,7 @@ namespace Server.Mobiles
{
public static Type GetType(string name)
{
return ScriptCompiler.FindTypeByName(name);
return AssemblyHandler.FindTypeByName(name);
}
}
}
}

View file

@ -133,15 +133,15 @@ namespace Server.Gumps
List<Type> results = new List<Type>();
Type[] types;
Assembly[] asms = ScriptCompiler.Assemblies;
Assembly[] asms = AssemblyHandler.Assemblies;
for (int i = 0; i < asms.Length; ++i)
{
types = ScriptCompiler.GetTypeCache(asms[i]).Types;
types = AssemblyHandler.GetTypeCache(asms[i]).Types;
Match(match, types, results);
}
types = ScriptCompiler.GetTypeCache(Core.Assembly).Types;
types = AssemblyHandler.GetTypeCache(Core.Assembly).Types;
Match(match, types, results);
results.Sort(new TypeNameComparer());

View file

@ -20,7 +20,7 @@ namespace Server.Gumps
Parent = parent;
if (xml.MoveToAttribute("type"))
Type = ScriptCompiler.FindTypeByFullName(xml.Value, false);
Type = AssemblyHandler.FindTypeByFullName(xml.Value, false);
if (xml.MoveToAttribute("gfx"))
ItemID = XmlConvert.ToInt32(xml.Value);

View file

@ -33,7 +33,7 @@ namespace Server.Items
SaveFlag flags = (SaveFlag)reader.ReadEncodedInt();
if (GetSaveFlag(flags, SaveFlag.Type))
Type = ScriptCompiler.FindTypeByFullName(reader.ReadString(), false);
Type = AssemblyHandler.FindTypeByFullName(reader.ReadString(), false);
if (GetSaveFlag(flags, SaveFlag.Name))
Name = TextDefinition.Deserialize(reader);

View file

@ -1,13 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
https://go.microsoft.com/fwlink/?LinkID=208121.
-->
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<PublishProtocol>FileSystem</PublishProtocol>
<Configuration>Release</Configuration>
<Platform>Any CPU</Platform>
<TargetFramework>netcoreapp3.0</TargetFramework>
<PublishDir>../Assemblies</PublishDir>
</PropertyGroup>
</Project>

View file

@ -1,13 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
https://go.microsoft.com/fwlink/?LinkID=208121.
-->
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<PublishProtocol>FileSystem</PublishProtocol>
<Configuration>Release</Configuration>
<Platform>Any CPU</Platform>
<TargetFramework>netcoreapp3.0</TargetFramework>
<PublishDir>../Assemblies</PublishDir>
</PropertyGroup>
</Project>

View file

@ -3,16 +3,11 @@
<PropertyGroup>
<RootNamespace>Server</RootNamespace>
<TargetFramework>netcoreapp3.0</TargetFramework>
</PropertyGroup>
<PropertyGroup Condition=" '$(TargetFramework)' == 'netcoreapp3.0'">
<DefineConstants>NETCORE;NETSTANDARD</DefineConstants>
<AssemblyName>Scripts.CS</AssemblyName>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<Optimize>true</Optimize>
<OutputPath>..\..\Distribution\Assemblies\</OutputPath>
<OutDir>..\..\Distribution\Assemblies</OutDir>
<WarningsAsErrors />
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<PlatformTarget>x64</PlatformTarget>
@ -22,8 +17,7 @@
<DefineConstants>TRACE;DEBUG</DefineConstants>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<Optimize>false</Optimize>
<OutputPath>..\..\Distribution\Assemblies\</OutputPath>
<OutDir>..\..\Distribution\Assemblies</OutDir>
<PublishDir>..\..\Distribution\Assemblies</PublishDir>
<WarningsAsErrors />
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<PlatformTarget>x64</PlatformTarget>
@ -32,8 +26,7 @@
<Content Include="SpecialSystems\README.TXT" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Server\Server.csproj">
<Private>false</Private>
<ProjectReference Include="..\Server\Server.csproj" Private="false" PrivateAssets="All" IncludeAssets="None">
<IncludeInPackage>false</IncludeInPackage>
</ProjectReference>
</ItemGroup>

View file

@ -147,7 +147,7 @@ namespace Server.Spells
{
for (int i = 0; i < m_CircleNames.Length; ++i)
{
Type t = ScriptCompiler.FindTypeByFullName($"Server.Spells.{m_CircleNames[i]}.{name}");
Type t = AssemblyHandler.FindTypeByFullName($"Server.Spells.{m_CircleNames[i]}.{name}");
if (t?.IsSubclassOf(typeof(SpecialMove)) == false)
{

View file

@ -1,6 +1,6 @@
/***************************************************************************
* ScriptCompiler.cs
* -------------------
* AssemblyHandler.cs
* --------------------
* begin : May 1, 2002
* copyright : (C) The RunUO Software Team
* email : info@runuo.com
@ -21,63 +21,31 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Reflection;
using System.Linq;
#if NETCORE
using System.Reflection;
using System.Runtime.Loader;
#endif
namespace Server
{
public static class ScriptCompiler
public static class AssemblyHandler
{
private static Dictionary<Assembly, TypeCache> m_TypeCaches = new Dictionary<Assembly, TypeCache>();
private static TypeCache m_NullCache;
public static Assembly[] Assemblies { get; set; }
public static string ScriptsPath = EnsureDirectory("Assemblies");
public static string AssembliesPath = EnsureDirectory("Assemblies");
public static bool LoadScripts(string path = null)
{
string[] files = Directory.GetFiles(path ?? ScriptsPath, "*.dll");
List<Assembly> assemblies = new List<Assembly>();
AssemblyName[] names = Assembly.GetExecutingAssembly().GetReferencedAssemblies();
int loaded = 0;
for (int i = 0; i < files.Length; i++)
{
#if NETCORE
assemblies.Add(AssemblyLoadContext.Default.LoadFromAssemblyPath(files[i]));
loaded++;
#else
Assemblies[i] = Assembly.LoadFrom(files[i]);
#endif
}
Assemblies = assemblies.ToArray();
return loaded > 0;
}
public static void LoadScripts(string path = null) =>
Assemblies = Directory.GetFiles(path ?? AssembliesPath, "*.dll")
.Select(t => AssemblyLoadContext.Default.LoadFromAssemblyPath(t)).ToArray();
public static void Invoke(string method)
{
List<MethodInfo> invoke = new List<MethodInfo>();
for (int a = 0; a < Assemblies.Length; ++a)
{
Type[] types = Assemblies[a].GetTypes();
for (int i = 0; i < types.Length; ++i)
{
MethodInfo m = types[i].GetMethod(method, BindingFlags.Static | BindingFlags.Public);
if (m != null)
invoke.Add(m);
}
}
invoke.AddRange(Assemblies[a].GetTypes()
.Select(t => t.GetMethod(method, BindingFlags.Static | BindingFlags.Public)).Where(m => m != null));
invoke.Sort(new CallPriorityComparer());
@ -87,20 +55,15 @@ namespace Server
public static TypeCache GetTypeCache(Assembly asm)
{
if (asm == null)
{
return m_NullCache ?? (m_NullCache = new TypeCache(null));
}
if (!m_TypeCaches.TryGetValue(asm, out TypeCache c))
m_TypeCaches[asm] = c = new TypeCache(asm);
if (asm == null) return m_NullCache ??= new TypeCache(null);
return c;
if (m_TypeCaches.TryGetValue(asm, out TypeCache c))
return c;
return m_TypeCaches[asm] = new TypeCache(asm);
}
public static Type FindTypeByFullName(string fullName)
{
return FindTypeByFullName(fullName, true);
}
public static Type FindTypeByFullName(string fullName) => FindTypeByFullName(fullName, true);
public static Type FindTypeByFullName(string fullName, bool ignoreCase)
{
@ -112,10 +75,7 @@ namespace Server
return type ?? GetTypeCache(Core.Assembly).GetTypeByFullName(fullName, ignoreCase);
}
public static Type FindTypeByName(string name)
{
return FindTypeByName(name, true);
}
public static Type FindTypeByName(string name) => FindTypeByName(name, true);
public static Type FindTypeByName(string name, bool ignoreCase)
{
@ -142,7 +102,7 @@ namespace Server
{
public TypeCache(Assembly asm)
{
Types = asm == null ? Type.EmptyTypes : asm.GetTypes();
Types = asm?.GetTypes() ?? Type.EmptyTypes;
Names = new TypeTable(Types.Length);
FullNames = new TypeTable(Types.Length);
@ -173,15 +133,9 @@ namespace Server
public TypeTable FullNames{ get; }
public Type GetTypeByName(string name, bool ignoreCase)
{
return Names.Get(name, ignoreCase);
}
public Type GetTypeByName(string name, bool ignoreCase) => Names.Get(name, ignoreCase);
public Type GetTypeByFullName(string fullName, bool ignoreCase)
{
return FullNames.Get(fullName, ignoreCase);
}
public Type GetTypeByFullName(string fullName, bool ignoreCase) => FullNames.Get(fullName, ignoreCase);
}
public class TypeTable

View file

@ -20,7 +20,7 @@
using System.Collections.Generic;
namespace Server.Mobiles
namespace Server
{
public class BuyItemStateComparer : IComparer<BuyItemState>
{
@ -103,4 +103,4 @@ namespace Server.Mobiles
public string Description{ get; }
}
}
}

View file

@ -0,0 +1,298 @@
/***************************************************************************
* SpanWriter.cs
* -------------------
* begin : August 5, 2019
* copyright : (C) The ModernUO Team
* email : hi@modernuo.com
*
* $Id$
*
***************************************************************************/
/***************************************************************************
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
***************************************************************************/
using System;
using System.Text;
namespace Server.Buffers
{
/// <summary>
/// Provides functionality for writing primitive binary data.
/// </summary>
public ref struct SpanWriter
{
private int m_Position;
/// <summary>
/// Underlying Span.
/// </summary>
public Span<byte> RawSpan { get; }
/// <summary>
/// Underlying Span up to the bytes written.
/// </summary>
public Span<byte> Span => RawSpan.Slice(0, WrittenCount);
/// <summary>
/// Gets the total length of the span.
/// </summary>
public int Length => RawSpan.Length;
/// <summary>
/// Total bytes written to the span.
/// </summary>
public int WrittenCount { get; private set; }
/// <summary>
/// Current position in the the span.
/// </summary>
public int Position
{
get => m_Position;
set
{
m_Position = value;
if (value > WrittenCount)
WrittenCount = value;
}
}
/// <summary>
/// Instantiates a new SpanWriter instance.
/// </summary>
public SpanWriter(Span<byte> span)
{
RawSpan = span;
m_Position = 0;
WrittenCount = 0;
}
/// <summary>
/// Writes a 1-byte boolean value to the span.
/// </summary>
public unsafe void Write(bool value)
{
RawSpan[Position++] = *(byte*)&value;
}
/// <summary>
/// Writes a 1-byte unsigned integer value to the span.
/// </summary>
public void Write(byte value)
{
RawSpan[Position++] = value;
}
/// <summary>
/// Writes a 1-byte signed integer value to the span.
/// </summary>
public void Write(sbyte value)
{
RawSpan[Position++] = (byte)value;
}
/// <summary>
/// Writes a 2-byte signed integer value to the span.
/// </summary>
public void Write(short value)
{
Write((byte)(value >> 8));
Write((byte)value);
}
/// <summary>
/// Writes a 2-byte unsigned integer value to the span.
/// </summary>
public void Write(ushort value)
{
Write((byte)(value >> 8));
Write((byte)value);
}
/// <summary>
/// Writes a 4-byte signed integer value to the span.
/// </summary>
public void Write(int value)
{
Write((byte)(value >> 24));
Write((byte)(value >> 16));
Write((byte)(value >> 8));
Write((byte)value);
}
/// <summary>
/// Writes a 4-byte unsigned integer value to the span.
/// </summary>
public void Write(uint value)
{
Write((byte)(value >> 24));
Write((byte)(value >> 16));
Write((byte)(value >> 8));
Write((byte)value);
}
/// <summary>
/// Writes an 8-byte signed integer value to the span.
/// </summary>
public void Write(long value)
{
Write((byte)(value >> 56));
Write((byte)(value >> 48));
Write((byte)(value >> 40));
Write((byte)(value >> 32));
Write((byte)(value >> 24));
Write((byte)(value >> 16));
Write((byte)(value >> 8));
Write((byte)value);
}
/// <summary>
/// Writes an 8-byte unsigned integer value to the span.
/// </summary>
public void Write(ulong value)
{
Write((byte)(value >> 56));
Write((byte)(value >> 48));
Write((byte)(value >> 40));
Write((byte)(value >> 32));
Write((byte)(value >> 24));
Write((byte)(value >> 16));
Write((byte)(value >> 8));
Write((byte)value);
}
/// <summary>
/// Writes a sequence of bytes to the span.
/// </summary>
public void Write(ReadOnlySpan<byte> input)
{
int size = Math.Min(input.Length, Length - Position);
input.Slice(0, size).CopyTo(RawSpan.Slice(Position));
Position += size;
}
/// <summary>
/// Writes an ASCII-encoded string value to the span.
/// </summary>
public void WriteAscii(string value)
{
Position += Encoding.ASCII.GetBytes(value ?? "", RawSpan.Slice(Position));
}
/// <summary>
/// Writes a fixed-length ASCII-encoded string value to the span.
/// </summary>
public void WriteAsciiFixed(string value, int size, bool zero = false)
{
value ??= "";
int length = Math.Min(size, value.Length);
Encoding.ASCII.GetBytes(value.AsSpan(0, length), RawSpan.Slice(Position));
if (zero)
{
Position += length;
Fill(size - length);
}
else
Position += size;
}
/// <summary>
/// Writes a dynamic-length ASCII-encoded string value to the span, followed by a 1-byte null character.
/// </summary>
public void WriteAsciiNull(string value)
{
Position += Encoding.ASCII.GetBytes(value ?? "", RawSpan.Slice(Position));
Write((byte)0);
}
/// <summary>
/// Writes a dynamic-length ASCII-encoded string value to the span, followed by a 1-byte null character.
/// </summary>
public void WriteAsciiNull(string value, int size)
{
value ??= "";
size = Math.Min(size, value.Length);
Position += Encoding.ASCII.GetBytes(value.AsSpan(0, size), RawSpan.Slice(Position));
Write((byte)0);
}
/// <summary>
/// Writes a dynamic-length little-endian unicode string value to the span.
/// </summary>
public void WriteLittleUni(string value)
{
Position += Encoding.Unicode.GetBytes(value ?? "", RawSpan.Slice(Position));
}
/// <summary>
/// Writes a dynamic-length little-endian unicode string value to the span, followed by a 2-byte null character.
/// </summary>
public void WriteLittleUniNull(string value)
{
WriteLittleUni(value);
Write((ushort)0);
}
/// <summary>
/// Writes a dynamic-length big-endian unicode string value to the span.
/// </summary>
public void WriteBigUni(string value)
{
Position += Encoding.BigEndianUnicode.GetBytes(value ?? "", RawSpan.Slice(Position));
}
/// <summary>
/// Writes a dynamic-length big-endian unicode string value to the span, followed by a 2-byte null character.
/// </summary>
public void WriteBigUniNull(string value, bool zero = false)
{
WriteBigUni(value);
if (zero)
Fill(2);
else
Position += 2;
}
/// <summary>
/// Writes a dynamic-length utf-8 string value, followed by a 1-byte null character.
/// </summary>
public void WriteUTF8Null(string value)
{
Position += Encoding.UTF8.GetBytes(value ?? "", RawSpan.Slice(Position)) + 1;
}
/// <summary>
/// Copies the span to the destination.
/// </summary>
public void CopyTo(Span<byte> destination)
{
RawSpan.CopyTo(destination);
}
/// <summary>
/// Fills the buffer with zeroes up to count
/// </summary>
public void Fill(int count)
{
count = Math.Min(count, RawSpan.Length - Position);
RawSpan.Slice(Position, count).Clear();
Position += count;
}
}
}

View file

@ -0,0 +1,61 @@
namespace Server
{
public sealed class CityInfo
{
private Point3D m_Location;
public CityInfo(string city, string building, int description, int x, int y, int z, Map m)
{
City = city;
Building = building;
Description = description;
Location = new Point3D(x, y, z);
Map = m;
}
public CityInfo(string city, string building, int x, int y, int z, Map m) : this(city, building, 0, x, y, z, m)
{
}
public CityInfo(string city, string building, int description, int x, int y, int z) : this(city, building,
description, x, y, z, Map.Trammel)
{
}
public CityInfo(string city, string building, int x, int y, int z) : this(city, building, 0, x, y, z, Map.Trammel)
{
}
public string City { get; set; }
public string Building { get; set; }
public int Description { get; set; }
public int X
{
get => m_Location.X;
set => m_Location.X = value;
}
public int Y
{
get => m_Location.Y;
set => m_Location.Y = value;
}
public int Z
{
get => m_Location.Z;
set => m_Location.Z = value;
}
public Point3D Location
{
get => m_Location;
set => m_Location = value;
}
public Map Map { get; set; }
}
}

View file

@ -0,0 +1,51 @@
using System;
using System.Collections;
using System.Collections.Generic;
namespace Server.Collections
{
public class ArraySet<T> : IList<T>
{
private readonly List<T> m_List = new List<T>();
public T this[int index] { get => m_List[index]; set => m_List[index] = value; }
public int Count => m_List.Count;
public bool IsReadOnly => false;
public int Add(T item)
{
int indexOf = m_List.IndexOf(item);
if (indexOf >= 0) return indexOf;
m_List.Add(item);
return m_List.Count - 1;
}
public void Clear() => m_List.Clear();
public bool Contains(T item) => m_List.Contains(item);
public void CopyTo(T[] array) => m_List.CopyTo(array);
public void CopyTo(T[] array, int arrayIndex) => m_List.CopyTo(array, arrayIndex);
public void CopyTo(int index, T[] array, int arrayIndex, int count) => m_List.CopyTo(index, array, arrayIndex, count);
public IEnumerator<T> GetEnumerator() => m_List.GetEnumerator();
public int IndexOf(T item) => m_List.IndexOf(item);
public void Insert(int index, T item) => throw new NotImplementedException();
public bool Remove(T item) => throw new NotImplementedException();
public void RemoveAt(int index) => throw new NotImplementedException();
void ICollection<T>.Add(T item) => m_List.Add(item);
IEnumerator IEnumerable.GetEnumerator() => m_List.GetEnumerator();
}
}

View file

@ -22,7 +22,7 @@ using System;
using System.Collections.Generic;
using Server.Network;
namespace Server.Commands
namespace Server
{
public delegate void CommandEventHandler(CommandEventArgs e);

View file

@ -11,7 +11,7 @@ namespace Server
public static Configuration Instance => m_Configuration ??= ReadConfiguration();
public List<string> DataDirectories { get; } = new List<string>();
public List<string> DataDirectories { get; set; } = new List<string>();
private static string FilePath => Path.Join(Core.BaseDirectory, "modernuo.json");

View file

@ -23,7 +23,6 @@ using System.Collections.Generic;
using System.Net;
using System.Net.Sockets;
using Server.Accounting;
using Server.Commands;
using Server.Guilds;
using Server.Network;

View file

@ -442,19 +442,19 @@ namespace Server
RandomImpl.IsHardwareRNG ? "Hardware" : "Software");
// Load Assembly Scripts.CS.dll
ScriptCompiler.LoadScripts();
AssemblyHandler.LoadScripts();
ScriptCompiler.Invoke("Configure");
AssemblyHandler.Invoke("Configure");
Region.Load();
World.Load();
ScriptCompiler.Invoke("Initialize");
AssemblyHandler.Invoke("Initialize");
// Start accepting new connections
MessagePump = new MessagePump();
ScriptCompiler.Invoke("RegisterListeners");
AssemblyHandler.Invoke("RegisterListeners");
timerThread.Start();
@ -513,7 +513,7 @@ namespace Server
VerifySerialization(ca);
foreach (Assembly a in ScriptCompiler.Assemblies.Where(a => a != ca)) VerifySerialization(a);
foreach (Assembly a in AssemblyHandler.Assemblies.Where(a => a != ca)) VerifySerialization(a);
}
private static void VerifyType(Type t)

View file

@ -25,7 +25,6 @@ using System.IO;
using System.Text;
using System.Threading.Tasks;
using Server.Accounting;
using Server.Commands;
using Server.ContextMenus;
using Server.Guilds;
using Server.Gumps;

View file

@ -19,6 +19,7 @@
***************************************************************************/
using System;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
namespace Server.Network
@ -47,7 +48,7 @@ namespace Server.Network
// If our input exceeds this length, we may potentially overflow the buffer
private const int PossibleOverflow = (BufferSize * 8 - TerminalCodeLength) / MaximalCodeLength;
private static int[] _huffmanTable = {
private static readonly int[] _huffmanTable = {
0x2, 0x000, 0x5, 0x01F, 0x6, 0x022, 0x7, 0x034, 0x7, 0x075, 0x6, 0x028, 0x6, 0x03B, 0x7, 0x032,
0x8, 0x0E0, 0x8, 0x062, 0x7, 0x056, 0x8, 0x079, 0x9, 0x19D, 0x8, 0x097, 0x6, 0x02A, 0x7, 0x057,
0x8, 0x071, 0x8, 0x05B, 0x9, 0x1CC, 0x8, 0x0A7, 0x7, 0x025, 0x7, 0x04F, 0x8, 0x066, 0x8, 0x07D,
@ -88,23 +89,12 @@ namespace Server.Network
static Compression()
{
if (Core.Unix)
{
if (Core.Is64Bit)
Compressor = new CompressorUnix64();
Compressor = new UnixCompressor();
else
Compressor = new CompressorUnix32();
Compressor = new Compressor();
}
else if (Core.Is64Bit)
{
Compressor = new Compressor64();
}
else
{
Compressor = new Compressor32();
}
}
public static unsafe void Compress(byte[] input, int offset, int count, byte[] output, ref int length)
public static unsafe void Compress(ReadOnlySpan<byte> input, int offset, int count, Span<byte> output, out int length)
{
if (input == null) throw new ArgumentNullException(nameof(input));
@ -121,8 +111,6 @@ namespace Server.Network
fixed (int* pTable = _huffmanTable)
{
int* pEntry;
fixed (byte* pInputBuffer = input)
{
byte* pInput = pInputBuffer + offset, pInputEnd = pInput + count;
@ -131,6 +119,7 @@ namespace Server.Network
{
byte* pOutput = pOutputBuffer, pOutputEnd = pOutput + BufferSize;
int* pEntry;
while (pInput < pInputEnd)
{
pEntry = &pTable[*pInput++ << 1];
@ -192,183 +181,150 @@ namespace Server.Network
}
}
public static ZLibError Pack(byte[] dest, ref int destLength, byte[] source, int sourceLength)
public static int MaxPackSize(int sourceLength) => (int)Compressor.CompressBound((ulong)sourceLength);
public static unsafe ZLibError Pack(Span<byte> dest, ref int destLength, ReadOnlySpan<byte> source, int sourceLength)
{
return Compressor.Compress(dest, ref destLength, source, sourceLength);
ulong destLengthLong = (ulong)destLength;
fixed (byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
{
ZLibError e = Compressor.Compress(Unsafe.AsRef<int>(dPtr), ref destLengthLong, Unsafe.AsRef<int>(sPtr), (ulong)sourceLength);
destLength = (int)destLengthLong;
return e;
}
}
public static unsafe ZLibError Pack(Span<byte> dest, ref int destLength, ReadOnlySpan<byte> source, ZLibQuality quality)
{
ulong destLengthLong = (ulong)destLength;
fixed (byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
{
ZLibError e = Compressor.Compress(Unsafe.AsRef<int>(dPtr), ref destLengthLong, Unsafe.AsRef<int>(sPtr), (ulong)source.Length, quality);
destLength = (int)destLengthLong;
return e;
}
}
public static unsafe ZLibError Pack(Span<byte> dest, ref int destLength, ReadOnlySpan<byte> source, int sourceLength, ZLibQuality quality)
{
ulong destLengthLong = (ulong)destLength;
fixed (byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
{
ZLibError e = Compressor.Compress(Unsafe.AsRef<int>(dPtr), ref destLengthLong, Unsafe.AsRef<int>(sPtr), (ulong)sourceLength, quality);
destLength = (int)destLengthLong;
return e;
}
}
public static ZLibError Pack(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality)
public static unsafe ZLibError Unpack(Span<byte> dest, ref int destLength, ReadOnlySpan<byte> source, int sourceLength)
{
return Compressor.Compress(dest, ref destLength, source, sourceLength, quality);
ulong destLengthLong = (ulong)destLength;
fixed (byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
{
ZLibError e = Compressor.Decompress(Unsafe.AsRef<int>(dPtr), ref destLengthLong, Unsafe.AsRef<int>(sPtr), (ulong)sourceLength);
destLength = (int)destLengthLong;
return e;
}
}
public static ulong MaxPackSize(ulong sourceLength) => Compressor.CompressBound(sourceLength);
public static unsafe ZLibError Pack(Span<byte> dest, ref ulong destLength, ReadOnlySpan<byte> source, ulong sourceLength)
{
fixed(byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
return Compressor.Compress(Unsafe.AsRef<int>(dPtr), ref destLength, Unsafe.AsRef<int>(sPtr), sourceLength);
}
public static ZLibError Unpack(byte[] dest, ref int destLength, byte[] source, int sourceLength)
public static unsafe ZLibError Pack(Span<byte> dest, ref ulong destLength, ReadOnlySpan<byte> source, ZLibQuality quality)
{
return Compressor.Decompress(dest, ref destLength, source, sourceLength);
fixed(byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
return Compressor.Compress(Unsafe.AsRef<int>(dPtr), ref destLength, Unsafe.AsRef<int>(sPtr), (ulong)source.Length, quality);
}
public static unsafe ZLibError Pack(Span<byte> dest, ref ulong destLength, ReadOnlySpan<byte> source, ulong sourceLength, ZLibQuality quality)
{
fixed(byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
return Compressor.Compress(Unsafe.AsRef<int>(dPtr), ref destLength, Unsafe.AsRef<int>(sPtr), sourceLength, quality);
}
public static unsafe ZLibError Unpack(Span<byte> dest, ref ulong destLength, ReadOnlySpan<byte> source, ulong sourceLength)
{
fixed(byte* dPtr = &MemoryMarshal.GetReference(dest), sPtr = &MemoryMarshal.GetReference(source))
return Compressor.Decompress(Unsafe.AsRef<int>(dPtr), ref destLength, Unsafe.AsRef<int>(sPtr), sourceLength);
}
}
public interface ICompressor
{
string Version{ get; }
ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength);
ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality);
ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength);
string Version { get; }
ZLibError Compress(in int dest, ref ulong destLength, in int source, ulong sourceLength);
ZLibError Compress(in int dest, ref ulong destLength, in int source, ulong sourceLength, ZLibQuality quality);
ZLibError Decompress(in int dest, ref ulong destLength, in int source, ulong sourceLength);
ulong CompressBound(ulong sourceLength);
}
public sealed class Compressor32 : ICompressor
{
public string Version => SafeNativeMethods.zlibVersion();
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
public class Compressor : ICompressor
{
return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength);
}
public string Version => zlibVersion();
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality)
{
return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality);
}
public ZLibError Compress(in int dest, ref ulong destLength, in int source, ulong sourceLength) =>
compress(dest, ref destLength, source, sourceLength);
public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength);
}
public ZLibError Compress(in int dest, ref ulong destLength, in int source, ulong sourceLength,
ZLibQuality quality) => compress2(dest, ref destLength, source, sourceLength, quality);
internal class SafeNativeMethods
{
[DllImport("zlib32")]
internal static extern string zlibVersion();
public ZLibError Decompress(in int dest, ref ulong destLength, in int source, ulong sourceLength) =>
uncompress(dest, ref destLength, source, sourceLength);
[DllImport("zlib32")]
internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength);
public ulong CompressBound(ulong sourceLength) => compressBound(sourceLength);
[DllImport("zlib32")]
internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength,
[DllImport("zlib")]
private static extern string zlibVersion();
[DllImport("zlib")]
private static extern ZLibError compress(in int dest, ref ulong destLength, in int source, ulong sourceLength);
[DllImport("zlib")]
private static extern ZLibError compress2(in int dest, ref ulong destLength, in int source, ulong sourceLength,
ZLibQuality quality);
[DllImport("zlib32")]
internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen);
}
[DllImport("zlib")]
private static extern ZLibError uncompress(in int dest, ref ulong destLength, in int source, ulong sourceLength);
[DllImport("zlib")]
private static extern ulong compressBound(ulong sourceLen);
}
public sealed class Compressor64 : ICompressor
public class UnixCompressor : ICompressor
{
public string Version => SafeNativeMethods.zlibVersion();
public string Version => zlibVersion();
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength);
}
public ZLibError Compress(in int dest, ref ulong destLength, in int source, ulong sourceLength) =>
compress(dest, ref destLength, source, sourceLength);
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality)
{
return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality);
}
public ZLibError Compress(in int dest, ref ulong destLength, in int source, ulong sourceLength,
ZLibQuality quality) => compress2(dest, ref destLength, source, sourceLength, quality);
public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength);
}
public ZLibError Decompress(in int dest, ref ulong destLength, in int source, ulong sourceLength) =>
uncompress(dest, ref destLength, source, sourceLength);
internal class SafeNativeMethods
{
[DllImport("zlib64")]
internal static extern string zlibVersion();
public ulong CompressBound(ulong sourceLength) => compressBound(sourceLength);
[DllImport("zlib64")]
internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength);
[DllImport("libz")]
private static extern string zlibVersion();
[DllImport("zlib64")]
internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength,
[DllImport("libz")]
private static extern ZLibError compress(in int dest, ref ulong destLength, in int source, ulong sourceLength);
[DllImport("libz")]
private static extern ZLibError compress2(in int dest, ref ulong destLength, in int source, ulong sourceLength,
ZLibQuality quality);
[DllImport("zlib64")]
internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen);
}
}
public sealed class CompressorUnix32 : ICompressor
{
public string Version => SafeNativeMethods.zlibVersion();
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength);
}
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality)
{
return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality);
}
public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength);
}
internal class SafeNativeMethods
{
[DllImport("libz")]
internal static extern string zlibVersion();
[DllImport("libz")]
private static extern ZLibError uncompress(in int dest, ref ulong destLength, in int source, ulong sourceLength);
[DllImport("libz")]
internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength);
[DllImport("libz")]
internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength,
ZLibQuality quality);
[DllImport("libz")]
internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen);
}
}
public sealed class CompressorUnix64 : ICompressor
{
public string Version => SafeNativeMethods.zlibVersion();
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
ulong destLengthLong = (ulong)destLength;
ZLibError z = SafeNativeMethods.compress(dest, ref destLengthLong, source, sourceLength);
destLength = (int)destLengthLong;
return z;
}
public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality)
{
ulong destLengthLong = (ulong)destLength;
ZLibError z = SafeNativeMethods.compress2(dest, ref destLengthLong, source, sourceLength, quality);
destLength = (int)destLengthLong;
return z;
}
public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength)
{
ulong destLengthLong = (ulong)destLength;
ZLibError z = SafeNativeMethods.uncompress(dest, ref destLengthLong, source, sourceLength);
destLength = (int)destLengthLong;
return z;
}
internal class SafeNativeMethods
{
[DllImport("libz")]
internal static extern string zlibVersion();
[DllImport("libz")]
internal static extern ZLibError compress(byte[] dest, ref ulong destLength, byte[] source, int sourceLength);
[DllImport("libz")]
internal static extern ZLibError compress2(byte[] dest, ref ulong destLength, byte[] source, int sourceLength,
ZLibQuality quality);
[DllImport("libz")]
internal static extern ZLibError uncompress(byte[] dest, ref ulong destLen, byte[] source, int sourceLen);
}
private static extern ulong compressBound(ulong sourceLen);
}
public enum ZLibError
@ -379,9 +335,7 @@ namespace Server.Network
DataError = -3,
StreamError = -2,
FileError = -1,
Okay = 0,
StreamEnd = 1,
NeedDictionary = 2
}
@ -389,10 +343,8 @@ namespace Server.Network
public enum ZLibQuality
{
Default = -1,
None = 0,
Speed = 1,
Size = 9
}
}
}

View file

@ -1,273 +1,273 @@
/***************************************************************************
* Packet.cs
* -------------------
* begin : August 2, 2019
* copyright : (C) The RunUO Software Team
* email : info@runuo.com
*
* $Id$
*
***************************************************************************/
/***************************************************************************
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
***************************************************************************/
using Server.Diagnostics;
using System;
using System.Buffers;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Text;
namespace Server.Network
{
public abstract class Packet
{
private const int CompressorBufferSize = 0x10000;
private const int BufferSize = 4096;
private byte[] m_CompiledBuffer;
private int m_CompiledLength;
private int m_Length;
private State m_State;
protected PacketWriter m_Stream;
protected Packet(int packetID)
{
PacketID = packetID;
if (Core.Profiling)
{
PacketSendProfile prof = PacketSendProfile.Acquire(GetType());
prof.Increment();
}
}
protected Packet(int packetID, int length)
{
PacketID = packetID;
m_Length = length;
m_Stream = PacketWriter.CreateInstance(length); // new PacketWriter( length );
m_Stream.Write((byte)packetID);
if (Core.Profiling)
{
PacketSendProfile prof = PacketSendProfile.Acquire(GetType());
prof.Increment();
}
}
public int PacketID { get; }
public PacketWriter UnderlyingStream => m_Stream;
public void EnsureCapacity(int length)
{
m_Stream = PacketWriter.CreateInstance(length); // new PacketWriter( length );
m_Stream.Write((byte)PacketID);
m_Stream.Write((short)0);
}
public static Packet SetStatic(Packet p)
{
p.SetStatic();
return p;
}
public static Packet Acquire(Packet p)
{
p.Acquire();
return p;
}
public static void Release(ref Packet p)
{
p?.Release();
p = null;
}
public static void Release(Packet p)
{
p?.Release();
}
public void SetStatic()
{
m_State |= State.Static | State.Acquired;
}
public void Acquire()
{
m_State |= State.Acquired;
}
public void OnSend()
{
Core.Set(); // Is this still needed if this is done async?
if ((m_State & (State.Acquired | State.Static)) == 0)
Free();
}
private void Free()
{
if (m_CompiledBuffer == null)
return;
if ((m_State & State.Buffered) != 0)
ArrayPool<byte>.Shared.Return(m_CompiledBuffer);
m_State &= ~(State.Static | State.Acquired | State.Buffered);
m_CompiledBuffer = null;
}
public void Release()
{
if ((m_State & State.Acquired) != 0)
Free();
}
public byte[] Compile(bool compress, out int length)
{
lock (this)
{
if (m_CompiledBuffer == null)
{
if ((m_State & State.Accessed) == 0)
{
m_State |= State.Accessed;
}
else
{
if ((m_State & State.Warned) == 0)
{
m_State |= State.Warned;
try
{
using (StreamWriter op = new StreamWriter("net_opt.log", true))
{
op.WriteLine("Redundant compile for packet {0}, use Acquire() and Release()", GetType());
op.WriteLine(new StackTrace());
}
}
catch
{
// ignored
}
}
m_CompiledBuffer = new byte[0];
m_CompiledLength = 0;
length = m_CompiledLength;
return m_CompiledBuffer;
}
InternalCompile(compress);
}
length = m_CompiledLength;
return m_CompiledBuffer;
}
}
private void InternalCompile(bool compress)
{
if (m_Length == 0)
{
long streamLen = m_Stream.Length;
m_Stream.Seek(1, SeekOrigin.Begin);
m_Stream.Write((ushort)streamLen);
}
else if (m_Stream.Length != m_Length)
{
int diff = (int)m_Stream.Length - m_Length;
Console.WriteLine("Packet: 0x{0:X2}: Bad packet length! ({1}{2} bytes)", PacketID, diff >= 0 ? "+" : "",
diff);
}
MemoryStream ms = m_Stream.UnderlyingStream;
m_CompiledBuffer = ms.GetBuffer();
int length = (int)ms.Length;
if (compress)
{
byte[] buffer = ArrayPool<byte>.Shared.Rent(CompressorBufferSize);
Compression.Compress(m_CompiledBuffer, 0, length, buffer, ref length);
if (length <= 0)
{
Console.WriteLine("Warning: Compression buffer overflowed on packet 0x{0:X2} ('{1}') (length={2})",
PacketID, GetType().Name, length);
using (StreamWriter op = new StreamWriter("compression_overflow.log", true))
{
op.WriteLine("{0} Warning: Compression buffer overflowed on packet 0x{1:X2} ('{2}') (length={3})",
DateTime.UtcNow, PacketID, GetType().Name, length);
op.WriteLine(new StackTrace());
}
}
else
{
m_CompiledLength = length;
if ((m_State & State.Static) != 0)
{
m_CompiledBuffer = new byte[length];
Buffer.BlockCopy(buffer, 0, m_CompiledBuffer, 0, length);
ArrayPool<byte>.Shared.Return(buffer);
}
else
{
m_CompiledBuffer = buffer;
m_State |= State.Buffered;
}
}
}
else if (length > 0)
{
byte[] old = m_CompiledBuffer;
m_CompiledLength = length;
if ((m_State & State.Static) != 0)
m_CompiledBuffer = new byte[length];
else
{
m_CompiledBuffer = ArrayPool<byte>.Shared.Rent(length);
m_State |= State.Buffered;
}
Buffer.BlockCopy(old, 0, m_CompiledBuffer, 0, length);
}
PacketWriter.ReleaseInstance(m_Stream);
m_Stream = null;
}
[Flags]
private enum State
{
Inactive = 0x00,
Static = 0x01,
Acquired = 0x02,
Accessed = 0x04,
Buffered = 0x08,
Warned = 0x10
}
}
}
/***************************************************************************
* Packet.cs
* -------------------
* begin : August 2, 2019
* copyright : (C) The RunUO Software Team
* email : info@runuo.com
*
* $Id$
*
***************************************************************************/
/***************************************************************************
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
***************************************************************************/
using Server.Diagnostics;
using System;
using System.Buffers;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Text;
namespace Server.Network
{
public abstract class Packet
{
private const int CompressorBufferSize = 0x10000;
private const int BufferSize = 4096;
private byte[] m_CompiledBuffer;
private int m_CompiledLength;
private int m_Length;
private State m_State;
protected PacketWriter m_Stream;
protected Packet(int packetID)
{
PacketID = packetID;
if (Core.Profiling)
{
PacketSendProfile prof = PacketSendProfile.Acquire(GetType());
prof.Increment();
}
}
protected Packet(int packetID, int length)
{
PacketID = packetID;
m_Length = length;
m_Stream = PacketWriter.CreateInstance(length); // new PacketWriter( length );
m_Stream.Write((byte)packetID);
if (Core.Profiling)
{
PacketSendProfile prof = PacketSendProfile.Acquire(GetType());
prof.Increment();
}
}
public int PacketID { get; }
public PacketWriter UnderlyingStream => m_Stream;
public void EnsureCapacity(int length)
{
m_Stream = PacketWriter.CreateInstance(length); // new PacketWriter( length );
m_Stream.Write((byte)PacketID);
m_Stream.Write((short)0);
}
public static Packet SetStatic(Packet p)
{
p.SetStatic();
return p;
}
public static Packet Acquire(Packet p)
{
p.Acquire();
return p;
}
public static void Release(ref Packet p)
{
p?.Release();
p = null;
}
public static void Release(Packet p)
{
p?.Release();
}
public void SetStatic()
{
m_State |= State.Static | State.Acquired;
}
public void Acquire()
{
m_State |= State.Acquired;
}
public void OnSend()
{
Core.Set(); // Is this still needed if this is done async?
if ((m_State & (State.Acquired | State.Static)) == 0)
Free();
}
private void Free()
{
if (m_CompiledBuffer == null)
return;
if ((m_State & State.Buffered) != 0)
ArrayPool<byte>.Shared.Return(m_CompiledBuffer);
m_State &= ~(State.Static | State.Acquired | State.Buffered);
m_CompiledBuffer = null;
}
public void Release()
{
if ((m_State & State.Acquired) != 0)
Free();
}
public byte[] Compile(bool compress, out int length)
{
lock (this)
{
if (m_CompiledBuffer == null)
{
if ((m_State & State.Accessed) == 0)
{
m_State |= State.Accessed;
}
else
{
if ((m_State & State.Warned) == 0)
{
m_State |= State.Warned;
try
{
using (StreamWriter op = new StreamWriter("net_opt.log", true))
{
op.WriteLine("Redundant compile for packet {0}, use Acquire() and Release()", GetType());
op.WriteLine(new StackTrace());
}
}
catch
{
// ignored
}
}
m_CompiledBuffer = new byte[0];
m_CompiledLength = 0;
length = m_CompiledLength;
return m_CompiledBuffer;
}
InternalCompile(compress);
}
length = m_CompiledLength;
return m_CompiledBuffer;
}
}
private void InternalCompile(bool compress)
{
if (m_Length == 0)
{
long streamLen = m_Stream.Length;
m_Stream.Seek(1, SeekOrigin.Begin);
m_Stream.Write((ushort)streamLen);
}
else if (m_Stream.Length != m_Length)
{
int diff = (int)m_Stream.Length - m_Length;
Console.WriteLine("Packet: 0x{0:X2}: Bad packet length! ({1}{2} bytes)", PacketID, diff >= 0 ? "+" : "",
diff);
}
MemoryStream ms = m_Stream.UnderlyingStream;
m_CompiledBuffer = ms.GetBuffer();
int length = (int)ms.Length;
if (compress)
{
byte[] buffer = ArrayPool<byte>.Shared.Rent(CompressorBufferSize);
Compression.Compress(m_CompiledBuffer, 0, length, buffer, out length);
if (length <= 0)
{
Console.WriteLine("Warning: Compression buffer overflowed on packet 0x{0:X2} ('{1}') (length={2})",
PacketID, GetType().Name, length);
using (StreamWriter op = new StreamWriter("compression_overflow.log", true))
{
op.WriteLine("{0} Warning: Compression buffer overflowed on packet 0x{1:X2} ('{2}') (length={3})",
DateTime.UtcNow, PacketID, GetType().Name, length);
op.WriteLine(new StackTrace());
}
}
else
{
m_CompiledLength = length;
if ((m_State & State.Static) != 0)
{
m_CompiledBuffer = new byte[length];
Buffer.BlockCopy(buffer, 0, m_CompiledBuffer, 0, length);
ArrayPool<byte>.Shared.Return(buffer);
}
else
{
m_CompiledBuffer = buffer;
m_State |= State.Buffered;
}
}
}
else if (length > 0)
{
byte[] old = m_CompiledBuffer;
m_CompiledLength = length;
if ((m_State & State.Static) != 0)
m_CompiledBuffer = new byte[length];
else
{
m_CompiledBuffer = ArrayPool<byte>.Shared.Rent(length);
m_State |= State.Buffered;
}
Buffer.BlockCopy(old, 0, m_CompiledBuffer, 0, length);
}
PacketWriter.ReleaseInstance(m_Stream);
m_Stream = null;
}
[Flags]
private enum State
{
Inactive = 0x00,
Static = 0x01,
Acquired = 0x02,
Accessed = 0x04,
Buffered = 0x08,
Warned = 0x10
}
}
}

View file

@ -3781,65 +3781,6 @@ namespace Server.Network
}
}
public sealed class CityInfo
{
private Point3D m_Location;
public CityInfo(string city, string building, int description, int x, int y, int z, Map m)
{
City = city;
Building = building;
Description = description;
m_Location = new Point3D(x, y, z);
Map = m;
}
public CityInfo(string city, string building, int x, int y, int z, Map m) : this(city, building, 0, x, y, z, m)
{
}
public CityInfo(string city, string building, int description, int x, int y, int z) : this(city, building,
description, x, y, z, Map.Trammel)
{
}
public CityInfo(string city, string building, int x, int y, int z) : this(city, building, 0, x, y, z, Map.Trammel)
{
}
public string City{ get; set; }
public string Building{ get; set; }
public int Description{ get; set; }
public int X
{
get => m_Location.X;
set => m_Location.X = value;
}
public int Y
{
get => m_Location.Y;
set => m_Location.Y = value;
}
public int Z
{
get => m_Location.Z;
set => m_Location.Z = value;
}
public Point3D Location
{
get => m_Location;
set => m_Location = value;
}
public Map Map{ get; set; }
}
public sealed class CharacterListUpdate : Packet
{
public CharacterListUpdate(IAccount a) : base(0x86)

View file

@ -12,6 +12,7 @@ using System.IO;
using System.Runtime.InteropServices;
using System.Security.Cryptography;
using System.Threading;
using System.Threading.Tasks;
namespace Server
{
@ -26,46 +27,31 @@ namespace Server
{
if (Core.Unix && File.Exists("rdrand.so"))
_Random = new RDRandUnix();
else if (Core.Is64Bit && File.Exists("rdrand64.dll"))
_Random = new RDRand64();
else if (File.Exists("rdrand.dll"))
_Random = new RDRand32();
else
_Random = new CSPRandom();
_Random = new RDRand64();
if (_Random is IHardwareRNG rng && !rng.IsSupported()) _Random = new CSPRandom();
if (_Random == null || _Random is IHardwareRNG rng && !rng.IsSupported())
_Random = new CSPRandom();
}
public static bool IsHardwareRNG => _Random is IHardwareRNG;
public static Type Type => _Random.GetType();
public static int Next(int c)
{
return _Random.Next(c);
}
public static int Next(int c) => _Random.Next(c);
public static bool NextBool()
{
return _Random.NextBool();
}
public static bool NextBool() => _Random.NextBool();
public static void NextBytes(byte[] b)
{
_Random.NextBytes(b);
}
public static void NextBytes(Span<byte> b) => _Random.NextBytes(b);
public static double NextDouble()
{
return _Random.NextDouble();
}
public static double NextDouble() => _Random.NextDouble();
}
public interface IRandomImpl
{
int Next(int c);
bool NextBool();
void NextBytes(byte[] b);
void NextBytes(Span<byte> b);
double NextDouble();
}
@ -74,48 +60,54 @@ namespace Server
bool IsSupported();
}
public sealed class SimpleRandom : IRandomImpl
public abstract class BaseRandom : IRandomImpl
{
private Random m_Random = new Random();
internal abstract void GetBytes(Span<byte> b);
internal abstract void GetBytes(byte[] b, int offset, int count);
public int Next(int c)
public virtual void NextBytes(Span<byte> b) => GetBytes(b);
public virtual int Next(int c) => (int)(c * NextDouble());
public virtual bool NextBool() => (NextByte() & 1) == 1;
public virtual byte NextByte()
{
int r;
lock (m_Random)
byte[] b = new byte[1];
GetBytes(b, 0, 1);
return b[0];
}
public virtual unsafe double NextDouble()
{
byte[] b = new byte[8];
if (BitConverter.IsLittleEndian)
{
r = m_Random.Next(c);
b[7] = 0;
GetBytes(b, 0, 7);
}
else
{
b[0] = 0;
GetBytes(b, 1, 7);
}
return r;
}
public bool NextBool()
{
return NextDouble() >= .5;
}
public void NextBytes(byte[] b)
{
lock (m_Random)
ulong r;
fixed (byte* buf = b)
{
m_Random.NextBytes(b);
}
}
public double NextDouble()
{
double r;
lock (m_Random)
{
r = m_Random.NextDouble();
r = *(ulong*)&buf[0] >> 3;
}
return r;
}
}
/* double: 53 bits of significand precision
* ulong.MaxValue >> 11 = 9007199254740991
* 2^53 = 9007199254740992
*/
public sealed class CSPRandom : IRandomImpl
{
return (double)r / 9007199254740992;
}
}
public sealed class CSPRandom : BaseRandom
{
private static int BUFFER_SIZE = 0x4000;
private static int LARGE_REQUEST = 0x40;
private byte[] _Buffer = new byte[BUFFER_SIZE];
@ -132,63 +124,24 @@ namespace Server
public CSPRandom()
{
_CSP.GetBytes(_Working);
ThreadPool.QueueUserWorkItem(Fill);
Task.Run(Fill);
}
public int Next(int c)
{
return (int)(c * NextDouble());
}
public bool NextBool()
{
return (NextByte() & 1) == 1;
}
public void NextBytes(byte[] b)
public override void NextBytes(Span<byte> b)
{
int c = b.Length;
if (c >= LARGE_REQUEST)
{
lock (_CSP)
{
lock (_sync)
{
_CSP.GetBytes(b);
}
}
return;
}
_GetBytes(b);
}
public unsafe double NextDouble()
{
byte[] b = new byte[8];
if (BitConverter.IsLittleEndian)
{
b[7] = 0;
_GetBytes(b, 0, 7);
}
else
{
b[0] = 0;
_GetBytes(b, 1, 7);
}
ulong r = 0;
fixed (byte* buf = b)
{
r = *(ulong*)&buf[0] >> 3;
}
/* double: 53 bits of significand precision
* ulong.MaxValue >> 11 = 9007199254740991
* 2^53 = 9007199254740992
*/
return (double)r / 9007199254740992;
GetBytes(b);
}
private void CheckSwap(int c)
@ -205,474 +158,91 @@ namespace Server
_filled.Reset();
ThreadPool.QueueUserWorkItem(Fill);
Task.Run(Fill);
}
private void Fill(object o)
private void Fill()
{
lock (_CSP)
{
_CSP.GetBytes(_Buffer);
}
_CSP.GetBytes(_Buffer);
_filled.Set();
}
private void _GetBytes(byte[] b)
internal override void GetBytes(Span<byte> b)
{
int c = b.Length;
lock (_sync)
{
CheckSwap(c);
Buffer.BlockCopy(_Working, _Index, b, 0, c);
_Working.CopyTo(b);
_Index += c;
}
}
private void _GetBytes(byte[] b, int offset, int count)
internal override void GetBytes(byte[] b, int offset, int count)
{
lock (_sync)
{
CheckSwap(count);
Buffer.BlockCopy(_Working, _Index, b, offset, count);
_Index += count;
}
GetBytes(b.AsSpan(offset, count));
}
private byte NextByte()
public override byte NextByte()
{
lock (_sync)
{
CheckSwap(1);
return _Working[_Index++];
}
}
}
public sealed class RDRandUnix : IRandomImpl, IHardwareRNG
{
private static int BUFFER_SIZE = 0x10000;
private static int LARGE_REQUEST = 0x40;
private byte[] _Buffer = new byte[BUFFER_SIZE];
private ManualResetEvent _filled = new ManualResetEvent(false);
private int _Index;
private object _sync = new object();
private byte[] _Working = new byte[BUFFER_SIZE];
public RDRandUnix()
{
SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working);
ThreadPool.QueueUserWorkItem(Fill);
}
public bool IsSupported()
{
uint r = 0;
return SafeNativeMethods.rdrand_32(ref r, true) == RDRandError.Success;
}
public int Next(int c)
{
return (int)(c * NextDouble());
}
public bool NextBool()
{
return (NextByte() & 1) == 1;
}
public void NextBytes(byte[] b)
{
int c = b.Length;
if (c >= LARGE_REQUEST)
{
SafeNativeMethods.rdrand_get_bytes(c, b);
return;
}
_GetBytes(b);
}
public unsafe double NextDouble()
{
byte[] b = new byte[8];
if (BitConverter.IsLittleEndian)
{
b[7] = 0;
_GetBytes(b, 0, 7);
}
else
{
b[0] = 0;
_GetBytes(b, 1, 7);
}
ulong r = 0;
fixed (byte* buf = b)
{
r = *(ulong*)&buf[0] >> 3;
}
/* double: 53 bits of significand precision
* ulong.MaxValue >> 11 = 9007199254740991
* 2^53 = 9007199254740992
*/
return (double)r / 9007199254740992;
}
private void CheckSwap(int c)
{
if (_Index + c < BUFFER_SIZE)
return;
_filled.WaitOne();
byte[] b = _Working;
_Working = _Buffer;
_Buffer = b;
_Index = 0;
_filled.Reset();
ThreadPool.QueueUserWorkItem(Fill);
}
private void Fill(object o)
{
SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer);
_filled.Set();
}
private void _GetBytes(byte[] b)
{
int c = b.Length;
lock (_sync)
{
CheckSwap(c);
Buffer.BlockCopy(_Working, _Index, b, 0, c);
_Index += c;
}
}
private void _GetBytes(byte[] b, int offset, int count)
{
lock (_sync)
{
CheckSwap(count);
Buffer.BlockCopy(_Working, _Index, b, offset, count);
_Index += count;
}
}
private byte NextByte()
{
lock (_sync)
{
CheckSwap(1);
return _Working[_Index++];
}
}
internal class SafeNativeMethods
public sealed class RDRandUnix : BaseRandom, IHardwareRNG
{
[DllImport("rdrand.so")]
internal static extern RDRandError rdrand_32(ref uint rand, bool retry);
[DllImport("rdrand.so")]
internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer);
}
}
public sealed class RDRand32 : IRandomImpl, IHardwareRNG
{
private static int BUFFER_SIZE = 0x10000;
private static int LARGE_REQUEST = 0x40;
private byte[] _Buffer = new byte[BUFFER_SIZE];
private ManualResetEvent _filled = new ManualResetEvent(false);
private int _Index;
private object _sync = new object();
private byte[] _Working = new byte[BUFFER_SIZE];
public RDRand32()
{
SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working);
ThreadPool.QueueUserWorkItem(Fill);
}
internal static extern unsafe RDRandError rdrand_get_bytes(int n, byte* buffer);
public bool IsSupported()
{
uint r = 0;
return SafeNativeMethods.rdrand_32(ref r, true) == RDRandError.Success;
return rdrand_32(ref r, true) == RDRandError.Success;
}
public int Next(int c)
internal override unsafe void GetBytes(Span<byte> b)
{
return (int)(c * NextDouble());
fixed(byte* ptr = b)
rdrand_get_bytes(b.Length, ptr);
}
public bool NextBool()
internal override void GetBytes(byte[] b, int offset, int count)
{
return (NextByte() & 1) == 1;
}
public void NextBytes(byte[] b)
{
int c = b.Length;
if (c >= LARGE_REQUEST)
{
SafeNativeMethods.rdrand_get_bytes(c, b);
return;
}
_GetBytes(b);
}
public unsafe double NextDouble()
{
byte[] b = new byte[8];
if (BitConverter.IsLittleEndian)
{
b[7] = 0;
_GetBytes(b, 0, 7);
}
else
{
b[0] = 0;
_GetBytes(b, 1, 7);
}
ulong r = 0;
fixed (byte* buf = b)
{
r = *(ulong*)&buf[0] >> 3;
}
/* double: 53 bits of significand precision
* ulong.MaxValue >> 11 = 9007199254740991
* 2^53 = 9007199254740992
*/
return (double)r / 9007199254740992;
}
private void CheckSwap(int c)
{
if (_Index + c < BUFFER_SIZE)
return;
_filled.WaitOne();
byte[] b = _Working;
_Working = _Buffer;
_Buffer = b;
_Index = 0;
_filled.Reset();
ThreadPool.QueueUserWorkItem(Fill);
}
private void Fill(object o)
{
SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer);
_filled.Set();
}
private void _GetBytes(byte[] b)
{
int c = b.Length;
lock (_sync)
{
CheckSwap(c);
Buffer.BlockCopy(_Working, _Index, b, 0, c);
_Index += c;
GetBytes(b.AsSpan().Slice(offset, count));
}
}
private void _GetBytes(byte[] b, int offset, int count)
public sealed class RDRand64 : BaseRandom, IHardwareRNG
{
lock (_sync)
{
CheckSwap(count);
Buffer.BlockCopy(_Working, _Index, b, offset, count);
_Index += count;
}
}
[DllImport("rdrand")]
internal static extern RDRandError rdrand_64(ref ulong rand, bool retry);
private byte NextByte()
{
lock (_sync)
{
CheckSwap(1);
return _Working[_Index++];
}
}
internal class SafeNativeMethods
{
[DllImport("rdrand32")]
internal static extern RDRandError rdrand_32(ref uint rand, bool retry);
[DllImport("rdrand32")]
internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer);
}
}
public sealed class RDRand64 : IRandomImpl, IHardwareRNG
{
private static int BUFFER_SIZE = 0x10000;
private static int LARGE_REQUEST = 0x40;
private byte[] _Buffer = new byte[BUFFER_SIZE];
private ManualResetEvent _filled = new ManualResetEvent(false);
private int _Index;
private object _sync = new object();
private byte[] _Working = new byte[BUFFER_SIZE];
public RDRand64()
{
SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working);
ThreadPool.QueueUserWorkItem(Fill);
}
[DllImport("rdrand")]
internal static extern unsafe RDRandError rdrand_get_bytes(int n, byte* buffer);
public bool IsSupported()
{
ulong r = 0;
return SafeNativeMethods.rdrand_64(ref r, true) == RDRandError.Success;
return rdrand_64(ref r, true) == RDRandError.Success;
}
public int Next(int c)
internal override unsafe void GetBytes(Span<byte> b)
{
return (int)(c * NextDouble());
fixed (byte* ptr = b)
rdrand_get_bytes(b.Length, ptr);
}
public bool NextBool()
internal override void GetBytes(byte[] b, int offset, int count)
{
return (NextByte() & 1) == 1;
}
public void NextBytes(byte[] b)
{
int c = b.Length;
if (c >= LARGE_REQUEST)
{
SafeNativeMethods.rdrand_get_bytes(c, b);
return;
}
_GetBytes(b);
}
public unsafe double NextDouble()
{
byte[] b = new byte[8];
if (BitConverter.IsLittleEndian)
{
b[7] = 0;
_GetBytes(b, 0, 7);
}
else
{
b[0] = 0;
_GetBytes(b, 1, 7);
}
ulong r = 0;
fixed (byte* buf = b)
{
r = *(ulong*)&buf[0] >> 3;
}
/* double: 53 bits of significand precision
* ulong.MaxValue >> 11 = 9007199254740991
* 2^53 = 9007199254740992
*/
return (double)r / 9007199254740992;
}
private void CheckSwap(int c)
{
if (_Index + c < BUFFER_SIZE)
return;
_filled.WaitOne();
byte[] b = _Working;
_Working = _Buffer;
_Buffer = b;
_Index = 0;
_filled.Reset();
ThreadPool.QueueUserWorkItem(Fill);
}
private void Fill(object o)
{
SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer);
_filled.Set();
}
private void _GetBytes(byte[] b)
{
int c = b.Length;
lock (_sync)
{
CheckSwap(c);
Buffer.BlockCopy(_Working, _Index, b, 0, c);
_Index += c;
}
}
private void _GetBytes(byte[] b, int offset, int count)
{
lock (_sync)
{
CheckSwap(count);
Buffer.BlockCopy(_Working, _Index, b, offset, count);
_Index += count;
}
}
private byte NextByte()
{
lock (_sync)
{
CheckSwap(1);
return _Working[_Index++];
}
}
internal class SafeNativeMethods
{
[DllImport("rdrand64")]
internal static extern RDRandError rdrand_64(ref ulong rand, bool retry);
[DllImport("rdrand64")]
internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer);
GetBytes(b.AsSpan(offset, count));
}
}
@ -687,4 +257,4 @@ namespace Server
Success = 1
}
}
}

View file

@ -1072,7 +1072,7 @@ namespace Server
Type type;
try
{
type = ScriptCompiler.FindTypeByName(s, false);
type = AssemblyHandler.FindTypeByName(s, false);
}
catch
{

View file

@ -1,4 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<?xml version="1.0" encoding="utf-8"?>
<Project Sdk="Microsoft.NET.Sdk" ToolsVersion="Current">
<PropertyGroup>
<OutputType>Exe</OutputType>
@ -7,7 +7,7 @@
</StartupObject>
<AssemblyName>ModernUO</AssemblyName>
<Win32Resource />
<Version>3.0.0</Version>
<Version>0.0.1</Version>
<Authors>Kamron Batman</Authors>
<Company>ModernUO</Company>
<Product>ModernUO</Product>
@ -15,54 +15,43 @@
<TargetFramework>netcoreapp3.0</TargetFramework>
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
</PropertyGroup>
<PropertyGroup Condition=" '$(TargetFramework)' == 'netcoreapp3.0'">
<DefineConstants>NETCORE;NETSTANDARD</DefineConstants>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
<DefineConstants>TRACE;DEBUG</DefineConstants>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<Optimize>false</Optimize>
<OutputPath>..\..\Distribution\</OutputPath>
<OutDir>..\..\Distribution</OutDir>
<WarningsAsErrors />
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<PublishDir>..\..\Distribution</PublishDir>
<OutDir>..\..\Distribution</OutDir>
<OutputPath>..\..\Distribution</OutputPath>
<PlatformTarget>x64</PlatformTarget>
<LangVersion>8.0</LangVersion>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<OutputPath>..\..\Distribution\</OutputPath>
<OutDir>..\..\Distribution</OutDir>
<WarningsAsErrors />
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<PlatformTarget>x64</PlatformTarget>
<PublishDir>..\..\Distribution</PublishDir>
<OutDir>..\..\Distribution</OutDir>
<OutputPath>..\..\Distribution</OutputPath>
<LangVersion>8.0</LangVersion>
</PropertyGroup>
<ItemGroup>
<Content Include="Assemblies\rdrand.so">
<Content Include="Assemblies\zlib.dll" Condition="'$(RuntimeIdentifier)'=='win-x64'">
<Link>zlib.dll</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Assemblies\rdrand.dll" Condition="'$(RuntimeIdentifier)'=='win-x64'">
<Link>rdrand.dll</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Assemblies\rdrand.so" Condition="'$(RuntimeIdentifier)'=='osx-x64' OR '$(RuntimeIdentifier)'=='linux-x64'">
<Link>rdrand.so</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Assemblies\rdrand32.dll">
<Link>rdrand32.dll</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Assemblies\rdrand64.dll">
<Link>rdrand64.dll</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Assemblies\zlib32.dll">
<Link>zlib32.dll</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
<Content Include="Assemblies\zlib64.dll">
<Link>zlib64.dll</Link>
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</Content>
</ItemGroup>
<ItemGroup>
<Reference Include="System.IO.Pipelines">
<HintPath>Assemblies\System.IO.Pipelines.dll</HintPath>
<IncludeInPackage>false</IncludeInPackage>
</Reference>
<PackageReference Include="System.IO.Pipelines" Version="4.6.0" />
</ItemGroup>
</Project>

View file

@ -422,7 +422,7 @@ namespace Server
public void Force()
{
if (ScriptCompiler.Assemblies == null || ScriptCompiler.Assemblies.Length == 0)
if ((AssemblyHandler.Assemblies?.Length ?? 0) == 0)
throw new Exception();
}

View file

@ -124,7 +124,7 @@ namespace Server
{
string typeName = tdbReader.ReadString();
Type t = ScriptCompiler.FindTypeByFullName(typeName);
Type t = AssemblyHandler.FindTypeByFullName(typeName);
if (t == null)
{
@ -703,7 +703,7 @@ namespace Server
}
else
{
Mobiles[m.Serial] = m;
Mobiles.Add(m.Serial, m);
}
}
@ -723,7 +723,7 @@ namespace Server
}
else
{
Items[item.Serial] = item;
Items.Add(item.Serial, item);
}
}

View file

@ -1,24 +0,0 @@
<?xml version="1.0"?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7"/>
</startup>
<runtime>
<gcServer enabled="true"/>
</runtime>
<!--Linux users will need to uncomment and modify the following line:-->
<!--<dllmap dll="libz" target="/lib/x86_64-linux-gnu/libz.so.1" />-->
<appSettings>
<add key="aspnet:RoslynCompilerLocation" value="roslyn"/>
</appSettings>
<system.codedom>
<compilers>
<compiler language="c#;cs;csharp" extension=".cs"
type="Microsoft.CodeDom.Providers.DotNetCompilerPlatform.CSharpCodeProvider, Microsoft.CodeDom.Providers.DotNetCompilerPlatform, Version=2.0.1.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"
warningLevel="4" compilerOptions="/langversion:default /nowarn:1659;1699;1701"/>
<compiler language="vb;vbs;visualbasic;vbscript" extension=".vb"
type="Microsoft.CodeDom.Providers.DotNetCompilerPlatform.VBCodeProvider, Microsoft.CodeDom.Providers.DotNetCompilerPlatform, Version=2.0.1.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"
warningLevel="4" compilerOptions="/langversion:default /nowarn:41008 /define:_MYTYPE=\&quot;Web\&quot; /optionInfer+"/>
</compilers>
</system.codedom>
</configuration>

View file

@ -1,2 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<packages />