OpenDreamProject / OpenDream

A project for running games made in the DM programming language
MIT License
206 stars 110 forks source link

In BYOND, type declaration compile order impacts static var initialization order #2041

Open ike709 opened 6 days ago

ike709 commented 6 days ago

This is the root cause of https://github.com/OpenDreamProject/OpenDream/issues/2040

The compile order of types impacts the order of their static var initialization:

Case 1:

var/global/datum/controller/global_vars/GLOB;

/datum/browser
    var/static/datum/asset/simple/namespaced/common/common_asset = get_asset_datum(/datum/asset/simple/namespaced/common)

/world/proc/Genesis()
    world.log << "Genesis"
    GLOB = new
    GLOB.InitGlobalasset_datums()

/datum/controller/global_vars/var/global/list/asset_datums; /datum/controller/global_vars/proc/InitGlobalasset_datums(){asset_datums = list();}
/proc/get_asset_datum(type)
    world.log << "get_asset_datum"
    var/datum/asset/loaded_asset = GLOB.asset_datums[type] || new type()
    return loaded_asset.ensure_ready()

/datum/asset/proc/ensure_ready()
    return src

/datum/asset/simple/namespaced/common

/proc/main()

/world/Error(e)
    world.log << e

/world/proc/_()
    var/static/_ = world.Genesis()

image

Case 2 (note the type declarations):

var/global/datum/controller/global_vars/GLOB;

/world

/datum/browser
    var/static/datum/asset/simple/namespaced/common/common_asset = get_asset_datum(/datum/asset/simple/namespaced/common)

/world/proc/Genesis()
    world.log << "Genesis"
    GLOB = new
    GLOB.InitGlobalasset_datums()

/datum/controller/global_vars/var/global/list/asset_datums; /datum/controller/global_vars/proc/InitGlobalasset_datums(){asset_datums = list();}
/proc/get_asset_datum(type)
    world.log << "get_asset_datum"
    var/datum/asset/loaded_asset = GLOB.asset_datums[type] || new type()
    return loaded_asset.ensure_ready()

/datum/asset/proc/ensure_ready()
    return src

/datum/asset/simple/namespaced/common

/proc/main()

/world/Error(e)
    world.log << e

/world/proc/_()
    var/static/_ = world.Genesis()

image

ike709 commented 6 days ago

Update: It's actually the type declaration order, not the New() order. Re-arranging New()s just happened to also adjust type declaration order.