misc: Tweak NullReferenceException fixes

This commit is contained in:
KeatonTheBot 2025-10-30 08:59:45 -05:00
parent e3ee28605d
commit a6c0eabf49
23 changed files with 143 additions and 128 deletions

View file

@ -327,16 +327,13 @@ namespace Ryujinx.Common.Collections
{
Root = newNode;
}
else if (parent != null && start.CompareTo(parent.Start) < 0)
else if (start.CompareTo(parent!.Start) < 0)
{
parent.Left = newNode;
}
else
{
if (parent != null)
{
parent.Right = newNode;
}
parent.Right = newNode;
}
PropagateIncrease(newNode);

View file

@ -278,16 +278,13 @@ namespace Ryujinx.Common.Collections
{
Root = newNode;
}
else if (parent != null && key.CompareTo(parent.Key) < 0)
else if (key.CompareTo(parent.Key) < 0)
{
parent.Left = newNode;
}
else
{
if (parent != null)
{
parent.Right = newNode;
}
parent.Right = newNode;
}
Count++;
return newNode;

View file

@ -388,12 +388,7 @@ namespace Ryujinx.Cpu.Jit.HostTracked
_treeLock.ExitReadLock();
}
if (_firstPagePa != null)
{
return (_backingMemory, _firstPagePa.Value);
}
return (null, 0);
return _firstPagePa != null ? (_backingMemory, _firstPagePa.Value) : (null, 0);
}
public PrivateRange GetPrivateAllocation(ulong va)

View file

@ -391,7 +391,7 @@ namespace Ryujinx.Graphics.Gpu.Memory
// Range list must be consistent for this operation
if (_migrationTarget != null)
{
_migrationTarget!.WaitForAndFlushRanges(address, size);
_migrationTarget.WaitForAndFlushRanges(address, size);
return;
}

View file

@ -210,7 +210,7 @@ namespace Ryujinx.Graphics.OpenGL.Effects.Smaa
var dispatchY = BitUtils.DivRoundUp(view.Height, IPostProcessingEffect.LocalGroupSize);
int previousProgram = GL.GetInteger(GetPName.CurrentProgram);
GL.BindImageTexture(0, edgeOutput.Handle, 0, false, 0, TextureAccess.ReadWrite, SizedInternalFormat.Rgba8);
GL.BindImageTexture(0, edgeOutput!.Handle, 0, false, 0, TextureAccess.ReadWrite, SizedInternalFormat.Rgba8);
GL.UseProgram(_edgeShaderPrograms[Quality]);
view.Bind(0);
GL.Uniform1(_inputUniform, 0);
@ -219,7 +219,7 @@ namespace Ryujinx.Graphics.OpenGL.Effects.Smaa
GL.DispatchCompute(dispatchX, dispatchY, 1);
GL.MemoryBarrier(MemoryBarrierFlags.ShaderImageAccessBarrierBit);
GL.BindImageTexture(0, blendOutput.Handle, 0, false, 0, TextureAccess.ReadWrite, SizedInternalFormat.Rgba8);
GL.BindImageTexture(0, blendOutput!.Handle, 0, false, 0, TextureAccess.ReadWrite, SizedInternalFormat.Rgba8);
GL.UseProgram(_blendShaderPrograms[Quality]);
edgeOutput.Bind(0);
areaTexture?.Bind(1);
@ -232,7 +232,7 @@ namespace Ryujinx.Graphics.OpenGL.Effects.Smaa
GL.DispatchCompute(dispatchX, dispatchY, 1);
GL.MemoryBarrier(MemoryBarrierFlags.ShaderImageAccessBarrierBit);
GL.BindImageTexture(0, textureView.Handle, 0, false, 0, TextureAccess.ReadWrite, SizedInternalFormat.Rgba8);
GL.BindImageTexture(0, textureView!.Handle, 0, false, 0, TextureAccess.ReadWrite, SizedInternalFormat.Rgba8);
GL.UseProgram(_neighbourShaderPrograms[Quality]);
view.Bind(0);
blendOutput.Bind(1);

View file

@ -63,12 +63,9 @@ namespace Ryujinx.Graphics.Shader.IntermediateRepresentation
{
INode lastOp = GetLastOp();
if (lastOp is Operation operation && IsControlFlowInst(operation.Inst))
if (lastOp is Operation operation && IsControlFlowInst(operation.Inst) && Operations.Last != null)
{
if (Operations.Last != null)
{
Operations.AddBefore(Operations.Last, node);
}
Operations.AddBefore(Operations.Last, node);
}
else
{

View file

@ -1693,7 +1693,7 @@ namespace Ryujinx.Graphics.Vulkan
var pipeline = pbp == PipelineBindPoint.Compute
? _newState.CreateComputePipeline(Gd, Device, _program, PipelineCache)
: _newState.CreateGraphicsPipeline(Gd, Device, _program, PipelineCache, _renderPass.Get(Cbs).Value);
: _newState.CreateGraphicsPipeline(Gd, Device, _program, PipelineCache, _renderPass!.Get(Cbs).Value);
if (pipeline == null)
{

View file

@ -134,7 +134,7 @@ namespace Ryujinx.Graphics.Vulkan
// Register this render pass with all render target views.
if (fb != null)
if (hasFramebuffer)
{
var textures = fb.GetAttachmentViews();

View file

@ -19,38 +19,51 @@ namespace Ryujinx.HLE.Generators
generator.EnterScope($"partial class IUserInterface");
generator.EnterScope($"public IpcService? GetServiceInstance(Type type, ServiceCtx context, object? parameter = null)");
foreach (var className in syntaxReceiver.Types)
if (syntaxReceiver != null)
{
if (className.Modifiers.Any(SyntaxKind.AbstractKeyword) || className.Modifiers.Any(SyntaxKind.PrivateKeyword) || !className.AttributeLists.Any(x => x.Attributes.Any(y => y.ToString().StartsWith("Service"))))
continue;
var name = GetFullName(className, context).Replace("global::", "");
if (!name.StartsWith("Ryujinx.HLE.HOS.Services"))
continue;
var constructors = className.ChildNodes().Where(x => x.IsKind(SyntaxKind.ConstructorDeclaration)).Select(y => y as ConstructorDeclarationSyntax);
if (!constructors.Any(x => x != null && x.ParameterList.Parameters.Count >= 1))
continue;
if (constructors.FirstOrDefault(x => x != null && x.ParameterList.Parameters.Count >= 1).ParameterList.Parameters[0].Type.ToString() == "ServiceCtx")
foreach (var className in syntaxReceiver.Types)
{
generator.EnterScope($"if (type == typeof({GetFullName(className, context)}))");
if (constructors.Any(x => x != null && x.ParameterList.Parameters.Count == 2))
if (className.Modifiers.Any(SyntaxKind.AbstractKeyword) ||
className.Modifiers.Any(SyntaxKind.PrivateKeyword) ||
!className.AttributeLists.Any(x => x.Attributes.Any(y => y.ToString().StartsWith("Service"))))
continue;
var name = GetFullName(className, context).Replace("global::", "");
if (!name.StartsWith("Ryujinx.HLE.HOS.Services"))
continue;
var constructors = className.ChildNodes().Where(x => x.IsKind(SyntaxKind.ConstructorDeclaration))
.Select(y => y as ConstructorDeclarationSyntax);
if (!constructors.Any(x => x?.ParameterList.Parameters.Count >= 1))
continue;
if (constructors.FirstOrDefault(x => x?.ParameterList.Parameters.Count >= 1)
.ParameterList.Parameters[0].Type.ToString() == "ServiceCtx")
{
var type = constructors.FirstOrDefault(x => x != null && x.ParameterList.Parameters.Count == 2).ParameterList.Parameters[1].Type;
var model = context.Compilation.GetSemanticModel(type.SyntaxTree);
var typeSymbol = model.GetSymbolInfo(type).Symbol as INamedTypeSymbol;
var fullName = typeSymbol?.ToString();
generator.EnterScope("if (parameter != null)");
generator.AppendLine($"return new {GetFullName(className, context)}(context, ({fullName})parameter);");
generator.EnterScope($"if (type == typeof({GetFullName(className, context)}))");
if (constructors.Any(x => x?.ParameterList.Parameters.Count == 2))
{
var type = constructors
.FirstOrDefault(x => x?.ParameterList.Parameters.Count == 2).ParameterList
.Parameters[1].Type;
if (type?.SyntaxTree != null)
{
var model = context.Compilation.GetSemanticModel(type.SyntaxTree);
var typeSymbol = model.GetSymbolInfo(type).Symbol as INamedTypeSymbol;
var fullName = typeSymbol?.ToString();
generator.EnterScope("if (parameter != null)");
generator.AppendLine($"return new {GetFullName(className, context)}(context, ({fullName})parameter);");
}
generator.LeaveScope();
}
if (constructors.Any(x => x != null && x.ParameterList.Parameters.Count == 1))
{
generator.AppendLine($"return new {GetFullName(className, context)}(context);");
}
generator.LeaveScope();
}
if (constructors.Any(x => x != null && x.ParameterList.Parameters.Count == 1))
{
generator.AppendLine($"return new {GetFullName(className, context)}(context);");
}
generator.LeaveScope();
}
}

View file

@ -60,12 +60,9 @@ namespace Ryujinx.HLE.HOS.Kernel.Ipc
KernelContext.CriticalSection.Enter();
if (list.Count != 0)
if (list.Count != 0 && list.First != null)
{
if (list.First != null)
{
session = list.First.Value;
}
session = list.First.Value;
list.RemoveFirst();
}

View file

@ -32,13 +32,10 @@ namespace Ryujinx.HLE.HOS.Kernel.Memory
public ref T GetRef<T>(ulong offset) where T : unmanaged
{
if (_pageList.Nodes.Count == 1)
if (_pageList.Nodes.Count == 1 && _pageList.Nodes.First != null)
{
if (_pageList.Nodes.First != null)
{
ulong address = _pageList.Nodes.First.Value.Address - DramMemoryMap.DramBase;
return ref _context.Memory.GetRef<T>(address + offset);
}
ulong address = _pageList.Nodes.First.Value.Address - DramMemoryMap.DramBase;
return ref _context.Memory.GetRef<T>(address + offset);
}
throw new NotImplementedException("Non-contiguous shared memory is not yet supported.");

View file

@ -164,8 +164,11 @@ namespace Ryujinx.HLE.HOS.Services.Nv
Logger.Debug?.Print(LogClass.ServiceNv, $"Deallocation resulted in new free range from 0x{expandedStart:X} to 0x{expandedEnd:X}.");
_tree.Add(expandedStart, expandedEnd);
LinkedListNode<ulong> nodePtr = _list.AddAfter(node, expandedStart);
_dictionary[expandedStart] = nodePtr;
if (node != null)
{
LinkedListNode<ulong> nodePtr = _list.AddAfter(node, expandedStart);
_dictionary[expandedStart] = nodePtr;
}
}
}
}
@ -196,11 +199,14 @@ namespace Ryujinx.HLE.HOS.Services.Nv
if (address < AddressSpaceSize)
{
bool reachedEndOfAddresses = false;
ulong targetAddress;
ulong targetAddress = 0;
if (start == DefaultStart)
{
Logger.Debug?.Print(LogClass.ServiceNv, $"Target address set to start of the last available range: 0x{_list.Last.Value:X}.");
targetAddress = _list.Last.Value;
if (_list.Last != null)
{
Logger.Debug?.Print(LogClass.ServiceNv, $"Target address set to start of the last available range: 0x{_list.Last.Value:X}.");
targetAddress = _list.Last.Value;
}
}
else
{

View file

@ -97,8 +97,8 @@ namespace Ryujinx.HLE.HOS.Services.Sm
IpcService service = GetServiceInstance(type, context, serviceAttribute.Parameter);
service.TrySetServer(_commonServer);
service.Server.AddSessionObj(session.ServerSession, service);
service?.TrySetServer(_commonServer);
service?.Server.AddSessionObj(session.ServerSession, service);
}
else
{

View file

@ -61,7 +61,7 @@ namespace Ryujinx.Horizon.Generators.Hipc
{
HipcSyntaxReceiver syntaxReceiver = (HipcSyntaxReceiver)context.SyntaxReceiver;
if (syntaxReceiver?.CommandInterfaces != null)
if (syntaxReceiver != null)
{
foreach (var commandInterface in syntaxReceiver.CommandInterfaces)
{
@ -98,7 +98,8 @@ namespace Ryujinx.Horizon.Generators.Hipc
generator.LeaveScope();
generator.LeaveScope();
context.AddSource($"{GetNamespaceName(commandInterface.ClassDeclarationSyntax)}.{className}.g.cs", generator.ToString());
context.AddSource($"{GetNamespaceName(commandInterface.ClassDeclarationSyntax)}.{className}.g.cs",
generator.ToString());
}
}
}
@ -244,7 +245,7 @@ namespace Ryujinx.Horizon.Generators.Hipc
"ReadOnlySpan<byte> inRawData, " +
"ref Span<CmifOutHeader> outHeader)");
bool returnsResult = method.ReturnType != null && GetCanonicalTypeName(compilation, method.ReturnType) == TypeResult;
bool returnsResult = GetCanonicalTypeName(compilation, method.ReturnType) == TypeResult;
if (returnsResult || buffersCount != 0 || inObjectsCount != 0)
{
@ -567,16 +568,11 @@ namespace Ryujinx.Horizon.Generators.Hipc
if (symbol != null)
{
foreach (var attribute in symbol.GetAttributes())
{
if (attribute.AttributeClass?.ToDisplayString() == attributeName)
{
foreach (var kv in attribute.NamedArguments.Where(kv => kv.Key == argName))
{
return kv.Value.ToCSharpString();
}
}
}
return (from attribute in symbol.GetAttributes()
where attribute.AttributeClass?.ToDisplayString() == attributeName
from kv in attribute.NamedArguments
where kv.Key == argName
select kv.Value.ToCSharpString()).FirstOrDefault();
}
return null;
@ -717,11 +713,16 @@ namespace Ryujinx.Horizon.Generators.Hipc
private static bool IsObject(Compilation compilation, ParameterSyntax parameter)
{
SyntaxNode syntaxNode = parameter.Type;
TypeInfo typeInfo = compilation.GetSemanticModel(syntaxNode!.SyntaxTree).GetTypeInfo(syntaxNode);
if (syntaxNode != null)
{
TypeInfo typeInfo = compilation.GetSemanticModel(syntaxNode.SyntaxTree).GetTypeInfo(syntaxNode);
return typeInfo.Type != null &&
(typeInfo.Type.ToDisplayString() == TypeIServiceObject ||
typeInfo.Type.AllInterfaces.Any(x => x.ToDisplayString() == TypeIServiceObject));
return typeInfo.Type != null &&
(typeInfo.Type.ToDisplayString() == TypeIServiceObject ||
typeInfo.Type.AllInterfaces.Any(x => x.ToDisplayString() == TypeIServiceObject));
}
return false;
}
private static bool IsProcessId(Compilation compilation, ParameterSyntax parameter)

View file

@ -164,7 +164,9 @@ namespace Ryujinx.Horizon.Kernel.Generators
where attributeArg.Expression.Kind() == SyntaxKind.NumericLiteralExpression
select (LiteralExpressionSyntax)attributeArg.Expression
into numericLiteral
select new SyscallIdAndName((int)numericLiteral.Token.Value, method.Identifier.Text));
let tokenValue = numericLiteral.Token.Value
where tokenValue != null
select new SyscallIdAndName((int)tokenValue, method.Identifier.Text));
}
}
}

View file

@ -88,7 +88,8 @@ namespace Ryujinx.Ava.UI.Models
private void UpdateBackground()
{
var currentApplication = Avalonia.Application.Current;
currentApplication!.Styles.TryGetResource("ControlFillColorSecondary", currentApplication.ActualThemeVariant, out object color);
object color = null;
currentApplication?.Styles.TryGetResource("ControlFillColorSecondary", currentApplication.ActualThemeVariant, out color);
if (color is not null)
{

View file

@ -525,16 +525,16 @@ namespace Ryujinx.Ava.UI.ViewModels.Input
{
ProfilesList.Clear();
string basePath = GetProfileBasePath() ?? string.Empty;
string basePath = GetProfileBasePath();
if (!Directory.Exists(basePath))
{
Directory.CreateDirectory(basePath);
Directory.CreateDirectory(basePath ?? string.Empty);
}
ProfilesList.Add((LocaleManager.Instance[LocaleKeys.ControllerSettingsProfileDefault]));
foreach (string profile in Directory.GetFiles(basePath, "*.json", SearchOption.AllDirectories))
foreach (string profile in Directory.GetFiles(basePath ?? string.Empty, "*.json", SearchOption.AllDirectories))
{
ProfilesList.Add(Path.GetFileNameWithoutExtension(profile));
}

View file

@ -1555,11 +1555,11 @@ namespace Ryujinx.Ava.UI.ViewModels
private void Update_StatusBar(object sender, StatusUpdatedEventArgs args)
{
if (ShowMenuAndStatusBar && !ShowLoadProgress)
if (ShowMenuAndStatusBar && !ShowLoadProgress && Application.Current != null)
{
Dispatcher.UIThread.InvokeAsync(() =>
{
Application.Current!.Styles.TryGetResource(args.VSyncMode,
Application.Current.Styles.TryGetResource(args.VSyncMode,
Application.Current.ActualThemeVariant,
out object color);

View file

@ -9,6 +9,7 @@ using Ryujinx.Ava.UI.ViewModels.Input;
using Ryujinx.Common.Configuration.Hid.Controller;
using Ryujinx.Input;
using Ryujinx.Input.Assigner;
using System;
using StickInputId = Ryujinx.Common.Configuration.Hid.Controller.StickInputId;
namespace Ryujinx.Ava.UI.Views.Input
@ -68,14 +69,12 @@ namespace Ryujinx.Ava.UI.Views.Input
if (_changeSlider != -1.0f && _changeSlider != (float)check.Value)
{
if (DataContext is ControllerInputViewModel viewModel)
{
viewModel.ParentModel.IsModified = true;
}
var viewModel = (DataContext as ControllerInputViewModel);
if (viewModel != null)
{
viewModel.ParentModel.IsModified = true;
}
_changeSlider = (float)check.Value;
_changeSlider = (float)check.Value;
}
}
}
@ -119,7 +118,10 @@ namespace Ryujinx.Ava.UI.Views.Input
PointerPressed += MouseClick;
var viewModel = (DataContext as ControllerInputViewModel);
if (DataContext is not ControllerInputViewModel viewModel)
{
return;
}
IKeyboard keyboard = (IKeyboard)viewModel.ParentModel.AvaloniaKeyboardDriver.GetGamepad("0"); // Open Avalonia keyboard for cancel operations.
IButtonAssigner assigner = CreateButtonAssigner(isStick);
@ -234,13 +236,14 @@ namespace Ryujinx.Ava.UI.Views.Input
private IButtonAssigner CreateButtonAssigner(bool forStick)
{
IButtonAssigner assigner;
if (DataContext is not ControllerInputViewModel controllerInputViewModel)
{
return null;
}
var controllerInputViewModel = DataContext as ControllerInputViewModel;
assigner = new GamepadButtonAssigner(
controllerInputViewModel?.ParentModel.SelectedGamepad,
(controllerInputViewModel.ParentModel.Config as StandardControllerInputConfig).TriggerThreshold,
IButtonAssigner assigner = new GamepadButtonAssigner(
controllerInputViewModel.ParentModel.SelectedGamepad,
((StandardControllerInputConfig)controllerInputViewModel.ParentModel.Config).TriggerThreshold,
forStick);
return assigner;

View file

@ -36,7 +36,7 @@ namespace Ryujinx.Ava.UI.Views.Settings
{
base.OnPointerReleased(e);
if (!_currentAssigner?.ToggledButton?.IsPointerOver ?? false)
if (!_currentAssigner?.ToggledButton.IsPointerOver ?? false)
{
_currentAssigner.Cancel();
}

View file

@ -63,25 +63,27 @@ namespace Ryujinx.Ava.UI.Views.User
private async void Import_OnClick(object sender, RoutedEventArgs e)
{
var window = this.GetVisualRoot() as Window;
var result = await window?.StorageProvider.OpenFilePickerAsync(new FilePickerOpenOptions
if (this.GetVisualRoot() is Window window)
{
AllowMultiple = false,
FileTypeFilter = new List<FilePickerFileType>
var result = await window.StorageProvider.OpenFilePickerAsync(new FilePickerOpenOptions
{
new(LocaleManager.Instance[LocaleKeys.AllSupportedFormats])
AllowMultiple = false,
FileTypeFilter = new List<FilePickerFileType>
{
Patterns = ["*.jpg", "*.jpeg", "*.png", "*.bmp"],
AppleUniformTypeIdentifiers = ["public.jpeg", "public.png", "com.microsoft.bmp"],
MimeTypes = ["image/jpeg", "image/png", "image/bmp"],
new(LocaleManager.Instance[LocaleKeys.AllSupportedFormats])
{
Patterns = ["*.jpg", "*.jpeg", "*.png", "*.bmp"],
AppleUniformTypeIdentifiers = ["public.jpeg", "public.png", "com.microsoft.bmp"],
MimeTypes = ["image/jpeg", "image/png", "image/bmp"],
},
},
},
});
});
if (result.Count > 0)
{
_profile.Image = ProcessProfileImage(File.ReadAllBytes(result[0].Path.LocalPath));
_parent.GoBack();
if (result.Count > 0)
{
_profile.Image = ProcessProfileImage(File.ReadAllBytes(result[0].Path.LocalPath));
_parent.GoBack();
}
}
}

View file

@ -42,7 +42,10 @@ namespace Ryujinx.Ava.UI.Views.User
if (arg.NavigationMode == NavigationMode.Back)
{
((ContentDialog)_parent.Parent).Title = LocaleManager.Instance[LocaleKeys.UserProfileWindowTitle];
if (_parent.Parent != null)
{
((ContentDialog)_parent.Parent).Title = LocaleManager.Instance[LocaleKeys.UserProfileWindowTitle];
}
}
DataContext = ViewModel;

View file

@ -516,12 +516,16 @@ namespace Ryujinx.Ava.UI.Windows
ApplicationLibrary.ApplicationCountUpdated += ApplicationLibrary_ApplicationCountUpdated;
_appLibraryAppsSubscription?.Dispose();
_appLibraryAppsSubscription = ApplicationLibrary.Applications
if (SynchronizationContext.Current != null)
{
_appLibraryAppsSubscription = ApplicationLibrary.Applications
.Connect()
.ObserveOn(SynchronizationContext.Current)
.Bind(ViewModel.Applications)
.OnItemAdded(UpdateApplicationWithLdnData)
.Subscribe();
}
ApplicationLibrary.LdnGameDataReceived += ApplicationLibrary_LdnGameDataReceived;
ConfigurationState.Instance.Multiplayer.Mode.Event += (sender, evt) =>
@ -581,7 +585,7 @@ namespace Ryujinx.Ava.UI.Windows
var volumeSplitButton = sender as ToggleSplitButton;
if (ViewModel.IsGameRunning)
{
if (volumeSplitButton is not { IsChecked: true })
if (volumeSplitButton is { IsChecked: false })
{
ViewModel.AppHost.Device.SetVolume(ViewModel.VolumeBeforeMute);
}