You are viewing a potentially older version of this package. View all versions.
korCaptain-NullReferenceFix-1.0.6 icon

NullReferenceFix

Fixes several repeating NullReferenceException crashes/log-spam bugs: a vanilla Valheim ZNetScene.RemoveObjects bug, an AzuCraftyBoxes stale-container bug, and an EnemyHud mod-conflict bug (EpicMMOSystem vs. other HUD-patching mods).

Date uploaded 4 days ago
Version 1.0.6
Download link korCaptain-NullReferenceFix-1.0.6.zip
Downloads 484
Dependency string korCaptain-NullReferenceFix-1.0.6

This mod requires the following mods to function

denikson-BepInExPack_Valheim-5.4.2201 icon
denikson-BepInExPack_Valheim

BepInEx pack for Valheim. Preconfigured and includes unstripped Unity DLLs.

Preferred version: 5.4.2201

README

NullReferenceFix

A small collection of independent Harmony patches, each fixing one specific bug where a NullReferenceException repeats every single frame for the rest of your play session once triggered — spamming the log and wasting CPU. Every patch targets a different root cause and can trigger (or not) completely independently of the others.

한국어 설명 보기 | English Description


🇰🇷 한국어 (Korean)

개요

NullReferenceFix는 서로 독립적인 여러 개의 작은 Harmony 패치를 모아둔 모드입니다. 각 패치는 한 번 터지면 세션이 끝날 때까지 매 프레임 반복해서 터지는 NullReferenceException 버그를 하나씩 담당합니다. 패치마다 원인이 다르고, 서로 완전히 독립적으로 발동합니다 — 즉 설치된 다른 모드 구성에 따라 일부 패치는 평생 한 번도 발동하지 않을 수도 있습니다.

현재 3가지 버그를 고칩니다:

  1. 바닐라 발헤임 자체 버그 (ZNetScene.RemoveObjects)
  2. AzuCraftyBoxes 모드 버그 (제작함 근처 재료 확인)
  3. EnemyHud를 건드리는 모드 간 충돌 (EpicMMOSystem 등)

📦 필수 모드 (Dependencies)
모드 버전 필수 여부
BepInExPack_Valheim 5.4.2200+ 필수
AzuCraftyBoxes 아무 버전 선택 — 설치되어 있을 때만 해당 패치가 활성화됩니다
EpicMMOSystem 아무 버전 선택 — 설치되어 있지 않아도 다른 두 패치는 정상 작동합니다

이 모드는 어떤 조합으로 설치해도 안전합니다. 위 모드들이 없어도 해당 패치만 조용히 비활성화될 뿐, 나머지 패치는 그대로 작동합니다.


🐛 버그 1 — ZNetScene.RemoveObjects (바닐라 발헤임)

같은 프레임 안에서 어떤 ZNetView의 GameObject가 다른 경로로 먼저 파괴되면, 바닐라 ZNetScene.RemoveObjects가 그 오브젝트를 내부 추적 딕셔너리(m_instances)에서 제거하기도 전에 NullReferenceException을 던집니다. 이 예외 때문에 문제의 entry가 딕셔너리에서 끝내 제거되지 못하고 남아버리고, 그 결과 다음 프레임에도 똑같은 예외가 또 발생 — 이 과정이 세션이 끝날 때까지 매 프레임 무한 반복됩니다.

이건 특정 모드가 만든 버그가 아니라 발헤임 엔진 자체의 오래된 결함입니다. 모드를 하나도 설치하지 않아도 발생할 수 있으며, 몬스터 스폰/디스폰이 잦은 상황(전투, 대규모 소환 등)일수록 더 쉽게 걸립니다.

이 모드가 하는 일: ZNetScene.RemoveObjects에 Harmony Finalizer 패치를 추가해 해당 예외만 정확히 잡아내고, 이미 파괴된(fake-null) ZNetView entry를 m_instances에서 직접 제거합니다.


🐛 버그 2 — AzuCraftyBoxes 제작함 조건 확인

AzuCraftyBoxes는 근처에서 본 모든 제작함을 HashSet<Container>에 정적으로 계속 쌓아둡니다. 상자가 철거될 때는 Container.OnDestroyed 패치로 항목을 지우지만, 일부 파괴 경로(구역/청크 언로드 등)는 이 메서드를 거치지 않고 GameObject를 바로 파괴해버려서, 이미 죽은(fake-null) Container가 세트에 그대로 남습니다. 이후 제작 메뉴가 열려 있는 동안 매 프레임 실행되는 재료 확인 로직이 이 죽은 항목의 GetPrefabName()을 호출하면서 NullReferenceException이 반복 발생합니다 — 제작 메뉴를 닫기 전까지 계속됩니다.

이 모드가 하는 일: AzuCraftyBoxes가 설치되어 있을 때만 활성화되는 패치로, 해당 예외를 잡아내고 파괴된 Container 항목들을 세트에서 직접 제거합니다.


🐛 버그 3 — EnemyHud를 건드리는 모드 간 충돌 (EpicMMOSystem 등)

일부 팩션/마켓플레이스 계열 모드는 자체 EnemyHud.LateUpdate 패치 안에서 EnemyHud.ShowHud를 직접 강제로 재호출해 HUD를 즉시 새로고침하려 합니다. 그런데 이 재호출이 이미 로그아웃했거나 디스폰된 캐릭터를 대상으로 발생하면, 그 캐릭터의 HUD 항목(m_huds)이 아직 정리되지 않은 채 남아있을 수 있고, 이걸 전제로 동작하는 다른 모드의 ShowHud 패치(예: EpicMMOSystem의 PvP 플레이어 이름 색상 표시 패치 DataMonsters.MonsterColorTexts)가 죽은 참조를 건드리면서 NullReferenceException이 반복 발생합니다.

이 모드가 하는 일: EpicMMOSystem이나 특정 모드를 콕 집어 패치하지 않고, 발헤임 기본 EnemyHud.ShowHud에 Finalizer를 걸어서 어떤 모드의 postfix에서 터지든 잡아내고, 문제의 오래된 m_huds 항목과 남은 HUD GameObject를 직접 정리합니다. 그러면 다음 프레임에 정상적인 새 항목이 만들어집니다.


회피(무시)가 아니라 청소입니다. 세 패치 모두 예외 자체는 처음 한 번은 그대로 발생하고, 이 모드가 그걸 잡아낸 뒤 원인이 된 깨진 상태(딕셔너리/세트의 죽은 항목)를 실제로 지웁니다. 그래서 같은 entry로는 다시 터지지 않습니다 — 단순히 로그만 숨기고 깨진 상태를 계속 방치하는 방식이 아닙니다. 각 패치는 오직 대상 메서드(또는 없으면 아무 일도 하지 않는 선택적 대상)만 건드리며, 다른 모드의 코드를 수정하지는 않습니다.


📥 설치 방법
  1. 권장: r2modman/Thunderstore에서 자동 설치
  2. 수동: NullReferenceFix.dllBepInEx/plugins/ 폴더에 복사

이 버그들은 네트워크로 동기화되지 않는 로컬 상태 문제라서, 서버와 각 클라이언트가 각자 독립적으로 겪을 수 있습니다. 한쪽에만 설치하면 그쪽만 고쳐집니다 — 멀티플레이 환경이라면 서버 + 접속하는 모든 클라이언트에 설치하는 것을 권장합니다.


🏴󠁧󠁢󠁥󠁮󠁧󠁿 English

Overview

NullReferenceFix is a collection of independent, small Harmony patches. Each one fixes a specific bug where a NullReferenceException, once triggered, repeats every single frame for the rest of the session. Every patch has a different root cause and triggers (or doesn't) completely independently — depending on your mod list, some patches may never activate at all.

It currently fixes 3 bugs:

  1. A vanilla Valheim engine bug (ZNetScene.RemoveObjects)
  2. An AzuCraftyBoxes mod bug (nearby-container requirement check)
  3. A mod-conflict bug involving EnemyHud (EpicMMOSystem and similar mods)

📦 Required Mods (Dependencies)
Mod Version Required
BepInExPack_Valheim 5.4.2200+ Required
AzuCraftyBoxes any Optional — that patch only activates if it's installed
EpicMMOSystem any Optional — the other two patches work fine without it

Safe to install in any combination. If a mod above isn't installed, its corresponding patch just stays inactive; the rest still work normally.


🐛 Bug 1 — ZNetScene.RemoveObjects (vanilla Valheim)

If a ZNetView's GameObject is destroyed by something else in the same frame that vanilla ZNetScene.RemoveObjects tries to clean it up, the method throws a NullReferenceException before it can reach the line that removes the stale entry from its internal tracking dictionary (m_instances). Because that entry never gets removed, the exact same exception fires again on the very next frame — and every frame after that, for the rest of the session.

This is vanilla engine behavior, not something any particular mod causes. It can happen with zero mods installed; busier games (more monster spawns/despawns, heavy combat) simply hit the underlying race condition more often.

What this patch does: adds a Harmony Finalizer to ZNetScene.RemoveObjects that catches only that specific exception and removes the already-destroyed (stale) ZNetView entry from m_instances directly.


🐛 Bug 2 — AzuCraftyBoxes nearby-container check

AzuCraftyBoxes keeps a static HashSet<Container> of every crafting container it has ever seen nearby. Container.OnDestroyed is patched to remove an entry when a box is demolished, but some destroy paths (e.g. a zone/chunk unload) destroy the GameObject without going through that method, leaving a Unity-destroyed (fake-null) Container sitting in the set. The next recipe check that walks nearby containers calls GetPrefabName() on the dead entry and throws NullReferenceException — every frame the crafting menu stays open.

What this patch does: only activates when AzuCraftyBoxes is installed; catches that exception and removes the destroyed Container entries from the set directly.


🐛 Bug 3 — Mod conflicts touching EnemyHud (EpicMMOSystem, etc.)

Some factions/marketplace-style mods call EnemyHud.ShowHud directly from their own EnemyHud.LateUpdate patch to force an immediate HUD refresh. If that re-entrant call targets a Character that already logged out or despawned, its HUD entry (m_huds) can still be sitting around uncleaned, and another mod's ShowHud patch that assumes a live entry — e.g. EpicMMOSystem's PvP player name-color patch, DataMonsters.MonsterColorTexts — dereferences the dead reference and throws NullReferenceException repeatedly.

What this patch does: instead of targeting EpicMMOSystem or any specific mod, it patches vanilla EnemyHud.ShowHud itself with a Finalizer, so it catches the exception no matter which installed mod's postfix throws it, then clears the stale m_huds entry (and its leftover HUD GameObject) so the next call rebuilds a clean one.


Cleanup, not evasion. For all three patches, the exception itself still fires once — this mod catches that one occurrence and then actually deletes the broken state (the dead dictionary/set entry) that caused it. The same entry can't throw again. It's not just hiding the log while leaving the broken state in place. Each patch only touches its own target method (or, if that target isn't present, does nothing at all) — no other mod's code is modified.


📥 Installation
  1. Recommended: Install via r2modman/Thunderstore
  2. Manual: Copy NullReferenceFix.dll into BepInEx/plugins/

These bugs are local state, not something synced over the network — the server and each client can hit them independently. Installing on only one side only fixes that side. In multiplayer, install it on the server and every connected client to be safe.


🎮 My Other Mods / 함께 즐기면 더 좋은 모드

🌳 CaptainSkillTree

👹 MonsterModifiers

🎵 CaptainAudio


📝 Credits / 크레딧

  • Developer / 개발자: KorCaptain
  • Framework / 프레임워크: BepInEx, Harmony

💬 Support / 지원


📜 License / 라이선스

Developer - KorCaptain


Enjoy a quieter log file! / 조용해진 로그를 즐기세요!

CHANGELOG

Changelog

한국어 보기 | English Version


English

1.0.6

  • Found & cleaned up: a conflict between EpicMMOSystem (WackyMole.EpicMMOSystem) and factions/marketplace-style mods. EpicMMOSystem's DataMonsters.MonsterColorTexts patch (player PvP name coloring) was throwing a repeating NullReferenceException every frame when a separate factions/marketplace-style mod force-called EnemyHud.ShowHud directly from its own EnemyHud.LateUpdate patch, targeting a Character whose HUD entry should already have been torn down (logged out / despawned). Instead of targeting EpicMMOSystem or any specific mod, this patches vanilla EnemyHud.ShowHud itself with a Finalizer so it catches the exception no matter which installed mod's postfix throws it, and directly cleans up the stale m_huds entry (and its leftover HUD GameObject) so the next call rebuilds a clean one.

1.0.4 - 1.0.5

  • Found & cleaned up: a bug in AzuCraftyBoxes (Azumatt.AzuCraftyBoxes). AzuCraftyBoxes keeps a static HashSet<Container> of every crafting container it has ever seen nearby, but some destroy paths (e.g. a zone/chunk unload) destroy the GameObject without going through Container.OnDestroyed, leaving a Unity-destroyed (fake-null) Container sitting in the set. The recipe check that runs every frame while the crafting menu is open then dereferenced that dead entry, throwing NullReferenceException repeatedly. Added a patch (only active when AzuCraftyBoxes is installed) that catches the exception and directly removes the destroyed Container entries from the set.

1.0.3 (Hotfix)

  • Fixed: the plugin DLL was accidentally missing from the previous releases (1.0.1, 1.0.2), so the mod did not work at all. This release restores the DLL.

1.0.1

  • Found & cleaned up: a vanilla Valheim engine bug (initial release). If a ZNetView's GameObject is destroyed by something else in the same frame that vanilla ZNetScene.RemoveObjects tries to clean it up, the method throws a NullReferenceException before it can remove the stale entry from its internal tracking dictionary (m_instances) — so the same exception then repeats every frame for the rest of the session. Not caused by any specific mod; it's an engine-level defect. Added a Finalizer patch on ZNetScene.RemoveObjects that catches the exception and directly removes the already-destroyed (stale) ZNetView entry from m_instances.

🇰🇷 한국어 (Korean)

1.0.6

  • EpicMMOSystem(WackyMole.EpicMMOSystem) ↔ 팩션/마켓플레이스 계열 모드 충돌 발견 및 정리: EpicMMOSystem의 DataMonsters.MonsterColorTexts(플레이어 PvP 이름 색상 표시) 패치가, 팩션/마켓플레이스 계열의 다른 모드가 EnemyHud.LateUpdate 패치 안에서 EnemyHud.ShowHud를 직접 강제 재호출할 때 이미 정리됐어야 할(로그아웃/디스폰된) 캐릭터의 남은 HUD 항목을 참조하면서 매 프레임 NullReferenceException을 반복 발생시키던 문제를 발견했습니다. EpicMMOSystem이나 특정 모드를 콕 집어 패치하는 대신 발헤임 기본 EnemyHud.ShowHud에 Finalizer를 걸어, 어떤 모드의 postfix에서 터지든 잡아내고 원인이 된 오래된 m_huds 항목(과 남은 HUD GameObject)을 직접 정리해서 다음 프레임에 정상적으로 새로 만들어지도록 청소 처리했습니다.

1.0.4 - 1.0.5

  • AzuCraftyBoxes(Azumatt.AzuCraftyBoxes) 모드 문제 발견 및 정리: AzuCraftyBoxes가 근처에서 본 모든 제작함을 정적 HashSet<Container>에 계속 쌓아두는데, 구역/청크 언로드 등 일부 파괴 경로가 Container.OnDestroyed 정리 로직을 거치지 않고 GameObject를 바로 파괴해버려서 이미 죽은(fake-null) Container가 세트에 남아있는 것을 발견했습니다. 제작 메뉴가 열려 있는 동안 매 프레임 실행되는 재료 확인 로직이 이 죽은 항목을 건드리며 NullReferenceException을 반복 발생시켰습니다. AzuCraftyBoxes가 설치된 경우에만 활성화되는 패치를 추가해 해당 예외를 잡아내고, 파괴된 Container 항목들을 세트에서 직접 제거해 정리했습니다.

1.0.3 (긴급 패치 / Hotfix)

  • 이전 배포(1.0.1, 1.0.2)에서 실수로 플러그인 DLL이 패키지에서 누락되어 모드가 전혀 동작하지 않던 문제를 수정했습니다.

1.0.1

  • 바닐라 발헤임 엔진 문제 발견 및 정리 (최초 배포): 같은 프레임 안에서 어떤 ZNetView의 GameObject가 다른 경로로 먼저 파괴되면, 바닐라 ZNetScene.RemoveObjects가 그 오브젝트를 내부 추적 딕셔너리(m_instances)에서 제거하기도 전에 NullReferenceException을 던지고, 그 결과 문제의 entry가 끝내 제거되지 못한 채 남아 다음 프레임에도 똑같은 예외가 세션이 끝날 때까지 무한 반복되는 것을 발견했습니다. 특정 모드가 아닌 발헤임 엔진 자체의 결함입니다. ZNetScene.RemoveObjects에 Finalizer 패치를 추가해 해당 예외를 잡아내고, 이미 파괴된(fake-null) ZNetView entry를 m_instances에서 직접 제거해 정리했습니다.