1 puan yazan GN⁺ 2025-11-24 | 1 yorum | WhatsApp'ta paylaş
  • Half-Life 2'nin erken bir sahnesinde kapının açılmaması nedeniyle ilerlemenin durduğu garip bir hata keşfedildi
  • Nedeni, kapı açılırken içeride duran güvenlik görevlisinin ayak ucunun kapının hareket yoluyla çarpışması ve bunun kapının yeniden kapanıp kilitlenmesine yol açması
  • Aynı çarpışma orijinal kodda da vardı, ancak 2004 x87 kayan nokta hesaplamaları ile 2013 SSE hesaplamaları arasındaki hassasiyet farkı sonucu değiştirdi
  • x87 ortamında çok küçük bir dönüş ayağı hafifçe iterek çarpışmayı çözerken, SSE'de dönüş miktarı yetersiz kaldığı için kapı kapanıyor
  • Bu olay, kayan nokta hassasiyeti ve derleyici farklarının gerçek oyun davranışı üzerindeki etkisini gösteren temsilî bir örnek

Half-Life 2 VR port sürecinde bulunan hata

  • 2013'te Valve, Team Fortress 2'yi VR'a portlama deneyi yaparken, aynı motoru kullanan Half-Life 2 ve Portal 1 de VR'da çalışır hale geldi
    • Portal 1, bakış açısı bozulması nedeniyle VR'da oynanamayacak kadar baş döndürücüydü
    • Half-Life 2 ise nispeten iyi çalıştı; tekne sahneleri, kutu dizme ve manhack savaşları gibi bölümlerde VR'a özgü sürükleyicilik arttı
  • Test sırasında bir geliştirici oyunu baştan sona VR'da oynarken erken tren istasyonu sahnesinde ilerlemenin imkânsız hale geldiğini fark etti

Kapının açılmama nedeninin analizi

  • Normal senaryoda güvenlik görevlisi (aslında Barney) kapıyı çalıp “içeri gir” dedikten sonra, oyuncu odaya girince bir sonraki script'e geçiliyor
  • Ancak hata durumunda kapı takırtıyla kapanıp kilitleniyor, güvenlik görevlisi kapıyı göstermeye devam ediyor ve oyuncu içeride mahsur kalıyor
  • Orijinal Half-Life 2 kaynak kodu yeniden derlendiğinde de aynı sorun ortaya çıkınca, bu durum zamanda geriye giderek oluşmuş bir hata gibi göründü ve kafa karışıklığı yarattı

Temel neden: kayan nokta hesaplama yöntemindeki değişim

  • Half-Life 2, 2004'te çıktığında x87 matematik komut setini kullanıyordu ve 32·64·80 bit hassasiyetin karışık olduğu bir yapıdaydı
  • 2013 sonrası derlemelerde ise varsayılan olarak SSE komut seti kullanıldı; böylece hesaplama hassasiyeti açık biçimde 32 bit veya 64 bitle sınırlı hale geldi
  • Her iki ortamda da kapı ile güvenlik görevlisinin ayak ucu çarpışıyor, ancak fizik motorundaki çok küçük hesap farkları sonucu değiştiriyor
    • x87'de çarpışma sırasında güvenlik görevlisi çok hafif dönüyor, ayağı kapıdan kurtuluyor ve kapı açılıyor
    • SSE'de dönüş miktarı çok az daha düşük kaldığı için ayak hâlâ temas ediyor ve kapı yeniden kapanıp kilitleniyor

Düzeltme ve çözüm

  • Sorun anlaşıldıktan sonra, güvenlik görevlisinin konumu yaklaşık 1 mm geriye alınarak basitçe çözüldü
  • Hata ayıklama sürecinde eski araçların kullanımını yeniden öğrenmek gibi nedenlerle ciddi zaman harcandı
  • Bu örnek, hassasiyet farkları ve derleyici ayarı değişikliklerinin eski kodun davranışını değiştirebileceğini gösteriyor

Topluluk tepkisi

  • Geliştiriciler, “sorun her zaman kayan nokta hassasiyetidir” diyerek duruma katıldı
  • Bazıları Sonic 1·2·3 remake'lerinde çarpışma hesaplarının değiştiği örnekleri anarak benzerliğe dikkat çekti
  • “Kod aynı ama derleyici farklı” dersiyle birlikte, legacy kod bakımının zorluğunu hatırlatan bir vaka olarak değerlendirildi
  • Diğer geliştiriciler de Fallout 4 gibi oyunlarda NPC'lerin kapılardan geçmemesi için yapılan tasarımları bu tür sorunlarla ilişkilendirdi
  • Genel olarak bunun “en ilginç hata hikâyelerinden biri” olduğu yönünde çok sayıda yorum yapıldı

1 yorum

 
GN⁺ 2025-11-24
Hacker News görüşleri
  • Eskiden oyun geliştirdiğim dönemde, FPU hesaplama hatası yüzünden yalnızca belirli PC'lerde assertion failure yaşandığını hatırlıyorum
    Sebebi, el yazısı girişi yazılımının tüm süreçlere DLL enjekte edip FPU modunu varsayılan değere sıfırlamasıydı
    Sonunda FPU ayar kodunu başlatma aşamasından event loop'a taşıyarak üçüncü taraf DLL'lerin etkisinden kaçınmıştık

    • Harika bir iz sürmeydi. Global FPU durumu gerçekten çok fazla baş ağrısına yol açtı
  • Hedeflerimden biri de Valve'ı Nix kullanmaya ikna etmek
    Windows desteği ilerlediği için artık daha cazip görüneceğini düşünüyorum
    Böylece yalnızca kaynak kodu değil, o dönemin toolchain ve bağımlılıkları da tamamen yeniden üretilebilir hale gelir; bu tür hataların kök nedenini bulmak da çok daha kolaylaşır

  • Bu bana “DOOR STUCK” meme'ini hatırlattı
    İlgili video

  • “Half-Life 2 VR beta”nın gerçekten oynanabilir olup olmadığını merak ediyorum
    Eğer öyleyse neden haberim olmadı, değilse neden hâlâ olmadığını merak ediyorum
    Portal VR'ı da mutlaka denemek istiyorum. İnsanlar çok mide bulandırdığını söylüyor ama ben VR motion sickness'e bağışıklıyım, o yüzden denemeye değer

    • Betayı bilmiyorum ama şu anda oynayabileceğiniz harika bir HL2 VR conversion mod var
      Hatta uzun zaman sonra HL2'yi yeniden oynamamı sağlayacak kadar iyi yapılmış
    • Bir de Portal 2 VR modu var. Baştan sona oynadım ve şaşırtıcı derecede rahat bir deneyimdi
  • x87'den SSE'ye geçince bazı hesaplamaların bozulması oldukça yaygın
    TF2'de de aynı şey olmuştu; Linux build SSE kullandığı için mühimmat hesabı biraz farklıydı

    • Mühimmat hesabında float kullanılmış olmasına şaşırdım
    • Gözle görülür tek fark aslında engineer'ın metal değeriydi
      Küçük kutudan +40 ya da +41 geliyordu ve bu, sunucunun işletim sistemine göre değişiyordu
      Yeni bir sunucuya bağlanınca hangi OS olduğunu anlamaya çalışmak eğlenceliydi
  • Yalnızca x87'den SSE'ye geçmek bile oyunu bozuyorsa, x86→ARM dönüşümünün nasıl bu kadar iyi çalıştığı gerçekten şaşırtıcı

    • x87 FPU, gerçekten de tek tuhaf kayan nokta birimi
      80 bit register kullandığı için daha yüksek hassasiyet sağlıyor ama belleğe spill edildiğinde hassasiyet kaybetmesi gibi garip davranışlar sergiliyor
    • Hassasiyet farkları yüzünden sayılar çok küçük miktarlarda değişebiliyor ve bu da kapı çarpışması gibi sorunlara yol açabiliyor
      Eskiden bir yazılım synthesizer debug ederken benzer bir hassasiyet hatası yaşamıştım
      RC devresi simülasyonunda durumun değişmesi için değerin 0'a yeterince yaklaşması gerekiyordu ama bazı CPU'larda denormal değerler flush edilmediği için koşul sağlanmıyordu
      Sonunda eşiği kabaca 0.7 ve 0.01 gibi değerlere ayarlayınca tüm platformlarda sorunsuz çalıştı
  • Meta bir not olarak, bir Twitter clone yapacak olsam çok paragraflı blog yazıları paylaşanları anında banlayan bir özellik eklerdim

    • İlgili thread'i tek sayfada açan şu link paylaşıldı
    • Böyle bir paylaşım seçeneğinin olmaması, thread'lerin ortadan kalkacağı anlamına gelmez görüşü de vardı
    • Tersine, en az iki paragraf yazmayı zorunlu kılan ve LLM'in içeriği doğruladığı bir platform yapalım diyenler de oldu