pull out the notifier object.

This commit is contained in:
starfrost013
2025-03-20 00:01:59 +00:00
parent c70a61e544
commit a5b864c59c
10 changed files with 124 additions and 30 deletions

Binary file not shown.

View File

@@ -845,6 +845,8 @@ extern const device_config_t nv3_config[];
#define NV3_CRTC_REGISTER_RMA_MODE_MAX 0x0F
/*
STRUCTURES FOR THE GPU START HERE
OBJECT CLASS & RENDERING RELATED STUFF IS IN VID_NV3_CLASSES.H
@@ -906,6 +908,7 @@ typedef struct nv3_pfb_s
//
// DMA & Notifier Engine
// All singing all dancing all happy happy bullshit to send dma transfers literally anywhere in your computer
//
// Not a notification status, because it's a 16-bit enum
@@ -914,6 +917,21 @@ typedef struct nv3_pfb_s
#define NV3_NOTIFICATION_STATUS_IN_PROGRESS 0xFF
#define NV3_NOTIFICATION_STATUS_ERROR 0x100
#define NV3_NOTIFICATION_INFO_ADJUST 0 // Wut
#define NV3_NOTIFICATION_PT_PRESENT 16 // Determines if the pagetable exists.
#define NV3_NOTIFICATION_TARGET 24 // Determines where this notification goes
#define NV3_NOTIFICATION_TARGET_NVM 0 // VRAM target for DMA
#define NV3_NOTIFICATION_TARGET_CART 1 // "Cartridge" target for dma, only mentioned in a few places, !!! NV2 LEFTOVER !!!
#define NV3_NOTIFICATION_TARGET_PCI 2 // Send the data to the host system over PCI
#define NV3_NOTIFICATION_TARGET_AGP 3 // Send the data to the host system over AGP
#define NV3_NOTIFICATION_PAGE_IS_PRESENT 0 // Determines if the page really exists
#define NV3_NOTIFICATION_PAGE_ACCESS 1 // Determines the page access type
#define NV3_NOTIFICATION_PAGE_ACCESS_READ 0x0 // If this is set, the page is read only
#define NV3_NOTIFICATION_PAGE_ACCESS_READ_WRITE 0x1 // If this is set, the page is read/write
#define NV3_NOTIFICATION_PAGE_FRAME_ADDRESS 12 // The pageframe to use
// Core notification structure
typedef struct nv3_notification_s
{
@@ -1170,6 +1188,7 @@ typedef struct nv3_pgraph_s
// CLIP
nv3_pgraph_clip_misc_settings_t clip_misc_settings;
nv3_notifier_t notifier;
bool notify_pending; // Determines if a notification is pending.
nv3_position_16_bigy_t clip0_min;
nv3_position_16_bigy_t clip0_max;
nv3_position_16_bigy_t clip1_min;
@@ -1550,7 +1569,7 @@ void nv3_class_018_method(uint32_t name, uint32_t method_id, nv3_ramin_co
void nv3_class_01c_method(uint32_t name, uint32_t method_id, nv3_ramin_context_t context, nv3_grobj_t grobj);
// Notification Engine
void nv3_notify_if_needed(nv3_grobj_t grobj);
void nv3_notify_if_needed(uint32_t name, uint32_t method_id, nv3_ramin_context_t context,nv3_grobj_t grobj);
// NV3 PFIFO
void nv3_pfifo_init();
@@ -1595,4 +1614,4 @@ void nv3_ptimer_tick(double real_time);
void nv3_pvideo_init();
// NV3 PMEDIA (Mediaport)
void nv3_pmedia_init();
void nv3_pmedia_init();

View File

@@ -1,19 +1,19 @@
/*
* 86Box A hypervisor and IBM PC system emulator that specializes in
* running old operating systems and software designed for IBM
* PC systems and compatibles from 1981 through fairly recent
* system designs based on the PCI bus.
*
* This file is part of the 86Box distribution.
*
* NV3: Methods for class 0x17 (Direct3D 5.0 accelerated triangle with zeta buffer)
*
*
*
* Authors: Connor Hyde, <mario64crashed@gmail.com> I need a better email address ;^)
*
* Copyright 2024-2025 Connor Hyde
*/
* 86Box A hypervisor and IBM PC system emulator that specializes in
* running old operating systems and software designed for IBM
* PC systems and compatibles from 1981 through fairly recent
* system designs based on the PCI bus.
*
* This file is part of the 86Box distribution.
*
* NV3: Methods for class 0x17 (Direct3D 5.0 accelerated triangle with zeta buffer)
*
*
*
* Authors: Connor Hyde, <mario64crashed@gmail.com> I need a better email address ;^)
*
* Copyright 2024-2025 Connor Hyde
*/
#include <stdlib.h>
#include <stdint.h>

View File

@@ -64,4 +64,4 @@ const char* nv3_class_names[] =
"NV3 INVALID class 0x1D",
"NV3 INVALID class 0x1E",
"NV3 INVALID class 0x1F",
};
};

View File

@@ -21,6 +21,7 @@
#include <stdio.h>
#include <86box/86box.h>
#include <86box/device.h>
#include <86box/dma.h>
#include <86box/mem.h>
#include <86box/pci.h>
#include <86box/rom.h>
@@ -39,7 +40,78 @@ void nv3_generic_method(uint32_t name, uint32_t method_id, nv3_ramin_context_t c
}
}
void nv3_notify_if_needed(nv3_grobj_t grobj)
/* Sees if any notification is required after an object method is executed. If so, executes it... */
void nv3_notify_if_needed(uint32_t name, uint32_t method_id, nv3_ramin_context_t context, nv3_grobj_t grobj)
{
if (nv3->pgraph.notify_pending)
{
nv_log("Called nv3_notify_if_needed with nv3->pgraph.notify_pending already set. name=0x%08x, method=0x%04x, grobj=0x%08x 0x%08x 0x%08x 0x%08x\n");
nv_log("IF THIS IS A DEBUG BUILD, YOU SHOULD SEE A CONTEXT BELOW");
nv3_debug_ramin_print_context_info(name, context);
nv3_pgraph_interrupt_invalid(NV3_PGRAPH_INTR_1_DOUBLE_NOTIFY);
// disable
nv3->pgraph.notify_pending = false;
return;
}
// set up the NvNotification structure
nv3_notification_t notify = {0};
notify.nanoseconds = nv3->ptimer.time;
notify.status = NV3_NOTIFICATION_STATUS_DONE_OK; // it should be fine to just signal that it's ok
}
// this is completely speculative and i have no idea
notify.info32 = grobj.grobj_0;
// notify object base=grobj_1 >> 12
uint32_t notify_obj_base = grobj.grobj_1 >> 12;
uint32_t notify_obj_info = nv3_ramin_read32(notify_obj_base, nv3);
uint32_t notify_obj_limit = nv3_ramin_read32(notify_obj_base + 0x04, nv3);
uint32_t notify_obj_page = nv3_ramin_read32(notify_obj_base + 0x08, nv3);
/* extract some important information*/
uint32_t info_adjust = notify_obj_info & 0xFFF;
bool info_pt_present = (notify_obj_info >> NV3_NOTIFICATION_PT_PRESENT) & 0x01;
uint8_t info_notification_target = (notify_obj_info >> NV3_NOTIFICATION_TARGET) & 0x03;
/* paging information */
bool page_is_present = notify_obj_page & 0x01;
bool page_is_readwrite = (notify_obj_page >> NV3_NOTIFICATION_PAGE_ACCESS);
uint32_t frame_value = (notify_obj_page >> NV3_NOTIFICATION_PAGE_FRAME_ADDRESS) & 0xFFFFF;
// This code is temporary and will probably be moved somewhere else
// Print torns of debug info
#ifdef DEBUG
nv_log("******* WARNING: IF THIS OPERATION FUCKS UP, RANDOM MEMORY WILL BE CORRUPTED, YOUR ENTIRE SYSTEM MAY BE HOSED *******\n");
nv_log("Notification Information:\n");
nv_log("Adjust Value: 0x%08x\n", info_adjust);
(info_pt_present) ? nv_log("Pagetable Present: True\n") : nv_log("Pagetable Present: False\n");
switch (info_notification_target)
{
case NV3_NOTIFICATION_TARGET_NVM:
nv_log("Notification Target: VRAM\n");
break;
case NV3_NOTIFICATION_TARGET_CART:
nv_log("VERY BAD WARNING: Notification detected with Notification Target: Cartridge. THIS SHOULD NEVER HAPPEN!!!!!\n");
break;
case NV3_NOTIFICATION_TARGET_PCI:
(nv3->nvbase.bus_generation == nv_bus_pci) ? nv_log("Notification Target: PCI Bus\n") : nv_log("Notification Target: PCI Bus (On AGP card???)\n");
break;
case NV3_NOTIFICATION_TARGET_AGP:
(nv3->nvbase.bus_generation == nv_bus_agp_1x
|| nv3->nvbase.bus_generation == nv_bus_agp_2x) ? nv_log("Notification Target: AGP Bus\n") : nv_log("Notification Target: AGP Bus (On PCI card???)\n");
break;
}
nv_log("Limit: 0x%08x", notify_obj_limit);
(page_is_present) ? nv_log("Page is present\n") : nv_log("Page is not present\n");
(page_is_readwrite) ? nv_log("Page is read-write\n") : nv_log("Page is read-only\n");
nv_log("Pageframe Address: 0x%08x", frame_value);
#endif
// set up the dma transfer. we need to translate to a physical address.
}

View File

@@ -194,5 +194,4 @@ uint32_t nv3_prmcio_read(uint32_t address) { return 0; };
void nv3_prmcio_write(uint32_t address, uint32_t value) {};
uint32_t nv3_vram_read(uint32_t address) { return 0; };
void nv3_vram_write(uint32_t address, uint32_t value) {};
void nv3_vram_write(uint32_t address, uint32_t value) {};

View File

@@ -28,4 +28,9 @@
#include <86box/nv/vid_nv.h>
#include <86box/nv/vid_nv3.h>
/* Nvidia DMA Engine */
/* Nvidia DMA Engine */
void nv3_dma_translate_address()
{
}

View File

@@ -168,13 +168,12 @@ void nv3_pfb_config0_write(uint32_t val)
uint32_t new_pfb_htotal = (nv3->pfb.config_0 & 0x3F) << 5;
// i don't think 16:9 is supported
uint32_t new_pfb_vtotal = new_pfb_htotal * (4.0/3.0);
uint32_t new_pfb_vtotal = new_pfb_htotal * (4.0/3.0);
uint32_t new_bit_depth = (nv3->pfb.config_0 >> 8) & 0x03;
nv_log("Framebuffer Config Change\n");
nv_log("Horizontal Size=%d pixels\n", new_pfb_htotal);
nv_log("Vertical Size @ 4:3=%d pixels\n", new_pfb_vtotal);
if (new_bit_depth == NV3_PFB_CONFIG_0_DEPTH_8BPP)
nv_log("Bit Depth=8bpp\n");

View File

@@ -589,7 +589,7 @@ void nv3_pgraph_arbitrate_method(uint32_t param, uint16_t method, uint8_t channe
return;
}
nv3_notify_if_needed(grobj);
nv3_notify_if_needed(param, method, context, grobj);
}
/* Arbitrates graphics object submission to the right object types */

View File

@@ -498,10 +498,11 @@ bool nv3_ramin_find_object(uint32_t name, uint32_t cache_num, uint8_t channel, u
}
#ifndef RELEASE_BUILD
// Prints out some informaiton about the object
void nv3_debug_ramin_print_context_info(uint32_t name, nv3_ramin_context_t context)
{
#ifndef RELEASE_BUILD
nv_log("Found object:\n");
nv_log("Name: 0x%04x\n", name);
@@ -511,6 +512,5 @@ void nv3_debug_ramin_print_context_info(uint32_t name, nv3_ramin_context_t conte
context.class_id & 0x1F, nv3_class_names[context.class_id & 0x1F]);
nv_log("Render Engine %d (0=Software, also DMA? 1=Accelerated Renderer)\n", context.is_rendering);
nv_log("PRAMIN Offset 0x%08x\n", context.ramin_offset << 4);
#endif
}
#endif