A glue Lua state with the reference glue surface, events and ModelFFX (#963)
The first piece of running the stock GlueXML: benilla had no glue Lua state, and no reference data for its surface. In 1.12.1 the glue state holds the base set (`0x7039e0`) and seven registrars (`0x46abb0`): 119 functions, 105 of them glue-only, with 26 glue events (`0xb41e70`, `0x46a88f`). `RegisterEvent` matches names case-insensitively and drops an unknown one (`0x702140`). The glue builds the 13 base frame types plus `ModelFFX` (`0x46a4fe`), a Model with its own show and paint (`0x46fa00`); the in-game types come only at world entry (`0x495940`). `reference/` gains the glue event and surface tables, generated and checked against the shapes table. `UiScript::new_glue()` builds that state; a gate holds its globals to the table, with the 108 unbuilt names listed. Nothing in the app changes yet. Part of #856 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
985dabff44
commit
a9dd325bb7
@@ -4,10 +4,10 @@
|
||||
//! `loadfile`, `load`, `module`, `newproxy` and `debug` removed), the reference's `debugstack`,
|
||||
//! and a text-only `loadstring`.
|
||||
//! - [`install`]: the 1.12 bare globals (string, table and math aliases, the `debug*` family, the
|
||||
//! error-handler pair), `time` and `date`, the clock and zone getters ([`super::clock`],
|
||||
//! [`super::zone_text`]), and a `string.format` that accepts positional `%N$` specs as the 1.12
|
||||
//! client's does, rewriting them into a sequential format. Mixing positional and sequential
|
||||
//! specs raises, as in the reference, whose single argument cursor a positional spec desyncs.
|
||||
//! error-handler pair), `time` and `date`, and a `string.format` that accepts positional `%N$`
|
||||
//! specs as the 1.12 client's does, rewriting them into a sequential format. Mixing positional
|
||||
//! and sequential specs raises, as in the reference, whose single argument cursor a positional
|
||||
//! spec desyncs.
|
||||
|
||||
use mlua::{Lua, Value, Variadic};
|
||||
|
||||
@@ -101,9 +101,7 @@ pub(super) fn sandbox(lua: &Lua) -> mlua::Result<()> {
|
||||
pub(super) fn install(lua: &Lua) -> mlua::Result<()> {
|
||||
install_error_handler(lua)?;
|
||||
install_time(lua)?;
|
||||
// Before the Lua layer, whose `debugprofile*` pair keeps its own `GetTime`.
|
||||
super::clock::install(lua)?;
|
||||
super::zone_text::install(lua)?;
|
||||
install_profile(lua)?;
|
||||
lua.load(WOW_STDLIB)
|
||||
.set_name("=[benilla wow stdlib]")
|
||||
.set_mode(mlua::ChunkMode::Text)
|
||||
@@ -111,6 +109,32 @@ pub(super) fn install(lua: &Lua) -> mlua::Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// `debugprofilestart`/`debugprofilestop` (`0x702840`/`0x702860`), the two real `debug*` verbs (RDTSC
|
||||
/// via `0x4293d0`): start latches, stop answers the milliseconds since. Ours read the `GetTime()`
|
||||
/// clock ([`super::clock::now`]), the monotonic session seconds the tick advances, as benilla has
|
||||
/// no cycle counter; read in Rust, so an addon that replaces the `GetTime` global cannot bend it.
|
||||
fn install_profile(lua: &Lua) -> mlua::Result<()> {
|
||||
use std::sync::atomic::{AtomicU64, Ordering};
|
||||
let start = std::sync::Arc::new(AtomicU64::new(0f64.to_bits()));
|
||||
let g = lua.globals();
|
||||
let latch = start.clone();
|
||||
g.set(
|
||||
"debugprofilestart",
|
||||
lua.create_function(move |lua, ()| {
|
||||
latch.store(super::clock::now(lua).to_bits(), Ordering::Relaxed);
|
||||
Ok(())
|
||||
})?,
|
||||
)?;
|
||||
g.set(
|
||||
"debugprofilestop",
|
||||
lua.create_function(move |lua, ()| {
|
||||
let since = f64::from_bits(start.load(Ordering::Relaxed));
|
||||
Ok((super::clock::now(lua) - since) * 1000.0)
|
||||
})?,
|
||||
)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// The handler `seterrorhandler` holds, `None` until one is given.
|
||||
pub(super) fn error_handler(lua: &Lua) -> Option<mlua::Function> {
|
||||
lua.named_registry_value::<Option<mlua::Function>>(super::REG_ERRORHANDLER)
|
||||
@@ -223,13 +247,9 @@ ldexp = math.ldexp
|
||||
-- That is what lets `BasicControls.xml` stop guarding its `debuginfo()` call and transcribe
|
||||
-- `_ERRORMESSAGE` verbatim, which it now does.
|
||||
--
|
||||
-- `debugprofilestart`/`debugprofilestop` are the two that are REAL (RDTSC via `0x4293d0`): start
|
||||
-- latches, stop answers the elapsed milliseconds since it. Modelled on `GetTime`'s own clock —
|
||||
-- the same monotonic session seconds the tick advances — because benilla has no cycle counter and
|
||||
-- an addon uses these to time its own work, which milliseconds answer honestly. The clock is
|
||||
-- captured, so an addon that replaces the `GetTime` global cannot bend it.
|
||||
-- `debugprofilestart`/`debugprofilestop` are the two that are REAL; they are Rust
|
||||
-- (`install_profile`).
|
||||
do
|
||||
local GetTime = GetTime
|
||||
local function noop() end
|
||||
debuginfo = noop
|
||||
debugload = noop
|
||||
@@ -237,19 +257,12 @@ do
|
||||
debugdump = noop
|
||||
debugbreak = noop
|
||||
debugtimestamp = noop
|
||||
|
||||
local profileStart = 0
|
||||
function debugprofilestart() profileStart = GetTime() end
|
||||
function debugprofilestop() return (GetTime() - profileStart) * 1000 end
|
||||
end
|
||||
|
||||
-- ── _G accessors (getglobal/setglobal: _G[name] get/set) ───────────────────────────────
|
||||
function getglobal(name) return _G[name] end
|
||||
function setglobal(name, value) _G[name] = value end
|
||||
|
||||
-- ── GetLocale: benilla ships/reads enUS data only (the 5875 MPQs + Spell.dbc enUS column) ──────
|
||||
function GetLocale() return "enUS" end
|
||||
|
||||
-- ── NOT here: wipe / tostringall / strsplit / strjoin / strconcat / strtrim ────────────────────
|
||||
-- Six 2.0+ names benilla used to define. 1.12 has none of them (absent from
|
||||
-- `reference/1.12-globals.tsv`, from the stock chain, and from every registrar table), and the
|
||||
|
||||
Reference in New Issue
Block a user