diff --git a/.github/workflows/ci_suite.yml b/.github/workflows/ci_suite.yml
index 683f3909b447..0488055312f7 100644
--- a/.github/workflows/ci_suite.yml
+++ b/.github/workflows/ci_suite.yml
@@ -60,6 +60,34 @@ jobs:
with:
outputFile: output-annotations.txt
+
+ odlint:
+ name: Lint with OpenDream
+ runs-on: ubuntu-20.04
+ steps:
+ - uses: actions/checkout@v3
+ - name: Get OpenDream Version
+ run: |
+ source dependencies.sh
+ echo "OPENDREAM_VERSION=$OPENDREAM_VERSION" >> $GITHUB_ENV
+ - name: Restore OpenDream cache
+ uses: actions/cache@v3
+ id: cache-od
+ with:
+ path: ~/OpenDream
+ key: ${{ runner.os }}-opendream-${{ env.OPENDREAM_VERSION }}
+ - name: Download OpenDream
+ if: steps.cache-od.outputs.cache-hit != 'true'
+ run: |
+ bash tools/ci/download_od.sh
+ - name: Setup OpenDream
+ if: steps.cache-od.outputs.cache-hit != 'true'
+ run: |
+ bash tools/ci/setup_od.sh
+ - name: Run OpenDream
+ run: |
+ bash tools/ci/run_od.sh
+
compile_all_maps:
if: "!contains(github.event.head_commit.message, '[ci skip]')"
name: Compile Maps
diff --git a/.gitignore b/.gitignore
index 210efc84d75b..4d2b7e810de8 100644
--- a/.gitignore
+++ b/.gitignore
@@ -31,3 +31,6 @@ test_environment.txt
# byond-tracy backend, not shipped with the codebase so it shouldn't be maintained
prof.dll
libprof.so
+
+# OpenDream compatibility stuff
+colonialmarines.json
diff --git a/code/__DEFINES/bullet_traits.dm b/code/__DEFINES/bullet_traits.dm
index 0ca3bce2e602..40e250cd0dd2 100644
--- a/code/__DEFINES/bullet_traits.dm
+++ b/code/__DEFINES/bullet_traits.dm
@@ -3,7 +3,7 @@
// list of args if there are any args
/// An entry to a list for giving projectiles bullet traits
/// Must be placed inside of a list
-#define BULLET_TRAIT_ENTRY(trait, args...) trait = #args ? list(##args) : null
+#define BULLET_TRAIT_ENTRY(trait, args...) trait = list(##args)
/// An entry to a list for giving projectiles bullet traits with a unique ID
/// Must be placed inside of a list
#define BULLET_TRAIT_ENTRY_ID(id, trait, args...) id = list(trait, ##args)
diff --git a/code/__HELPERS/type2type.dm b/code/__HELPERS/type2type.dm
index 4e4a1b3ff31c..5d0d113b0c55 100644
--- a/code/__HELPERS/type2type.dm
+++ b/code/__HELPERS/type2type.dm
@@ -21,7 +21,7 @@
var/char = copytext(hex, i, i + 1)
switch(char)
if("0")
- //Apparently, switch works with empty statements, yay! If that doesn't work, blame me, though. -- Urist
+ pass()
if("9", "8", "7", "6", "5", "4", "3", "2", "1")
num += text2num(char) * 16 ** power
if("a", "A")
@@ -77,7 +77,6 @@
hex += "E"
if(15.0)
hex += "F"
- else
power--
while(length(hex) < placeholder)
hex = text("0[]", hex)
@@ -165,8 +164,6 @@
return 6
if("SOUTHWEST")
return 10
- else
- return
//Converts an angle (degrees) into an ss13 direction
/proc/angle2dir(degree)
diff --git a/code/__odlint.dm b/code/__odlint.dm
new file mode 100644
index 000000000000..f42517133746
--- /dev/null
+++ b/code/__odlint.dm
@@ -0,0 +1,11 @@
+// This file is included right at the start of the DME.
+// Its purpose is to enable multiple lints (pragmas) that are supported by OpenDream to better validate the codebase
+// These are essentially nitpicks the DM compiler should pick up on but doesnt
+
+#ifndef SPACEMAN_DMM
+#ifdef OPENDREAM
+// These are in their own file as you need to do it with an include as a hack to avoid
+// SpacemanDMM evaluating the #pragma lines, even if its outside a block it cares about
+#include "__pragmas.dm"
+#endif
+#endif
diff --git a/code/__pragmas.dm b/code/__pragmas.dm
new file mode 100644
index 000000000000..39c14e1bbc95
--- /dev/null
+++ b/code/__pragmas.dm
@@ -0,0 +1,27 @@
+//1000-1999
+#pragma FileAlreadyIncluded error
+#pragma MissingIncludedFile error
+#pragma MisplacedDirective error
+#pragma UndefineMissingDirective error
+#pragma DefinedMissingParen error
+#pragma ErrorDirective error
+#pragma WarningDirective error
+#pragma MiscapitalizedDirective error
+
+//2000-2999
+#pragma SoftReservedKeyword error
+#pragma DuplicateVariable error
+#pragma DuplicateProcDefinition error
+#pragma TooManyArguments error
+#pragma PointlessParentCall error
+#pragma PointlessBuiltinCall error
+#pragma SuspiciousMatrixCall error
+#pragma MalformedRange error
+#pragma InvalidRange error
+#pragma InvalidSetStatement error
+#pragma InvalidOverride error
+#pragma DanglingVarType error
+#pragma MissingInterpolatedExpression error
+
+//3000-3999
+#pragma EmptyBlock error
diff --git a/code/_byond_version_compat.dm b/code/_byond_version_compat.dm
index 719d85654b5f..26968f0f837c 100644
--- a/code/_byond_version_compat.dm
+++ b/code/_byond_version_compat.dm
@@ -3,7 +3,7 @@
//Update this whenever you need to take advantage of more recent byond features
#define MIN_COMPILER_VERSION 514
#define MIN_COMPILER_BUILD 1588
-#if (DM_VERSION < MIN_COMPILER_VERSION || DM_BUILD < MIN_COMPILER_BUILD) && !defined(SPACEMAN_DMM)
+#if (DM_VERSION < MIN_COMPILER_VERSION || DM_BUILD < MIN_COMPILER_BUILD) && !defined(SPACEMAN_DMM) && !defined(OPENDREAM)
//Don't forget to update this part
#error Your version of BYOND is too out-of-date to compile this project. Go to https://secure.byond.com/download and update.
#error You need version 514.1588 or higher
diff --git a/code/_compile_options.dm b/code/_compile_options.dm
index 0f81b0173ac1..20aa2081318c 100644
--- a/code/_compile_options.dm
+++ b/code/_compile_options.dm
@@ -30,7 +30,7 @@
#define CBT
#endif
-#if !defined(CBT) && !defined(SPACEMAN_DMM)
+#if !defined(CBT) && !defined(SPACEMAN_DMM) && !defined(OPENDREAM)
#warn Building with Dream Maker is no longer supported and will result in errors.
#warn In order to build, run BUILD.bat in the bin directory.
#warn Consider switching to VSCode editor instead, where you can press Ctrl+Shift+B to build.
diff --git a/code/controllers/subsystem/atoms.dm b/code/controllers/subsystem/atoms.dm
index 23da8cc8c9eb..3d544dca1390 100644
--- a/code/controllers/subsystem/atoms.dm
+++ b/code/controllers/subsystem/atoms.dm
@@ -131,7 +131,7 @@ SUBSYSTEM_DEF(atoms)
switch(result)
if (INITIALIZE_HINT_NORMAL)
- // pass
+ pass()
if(INITIALIZE_HINT_LATELOAD)
if(arguments[1]) //mapload
late_loaders += A
diff --git a/code/controllers/subsystem/vote.dm b/code/controllers/subsystem/vote.dm
index 3882228a5ab1..a56e10636a1e 100644
--- a/code/controllers/subsystem/vote.dm
+++ b/code/controllers/subsystem/vote.dm
@@ -273,7 +273,7 @@ SUBSYSTEM_DEF(vote)
question = "Gamemode vote"
randomize_entries = TRUE
for(var/mode_type in config.gamemode_cache)
- var/datum/game_mode/M = initial(mode_type)
+ var/datum/game_mode/M = mode_type
if(initial(M.config_tag))
var/vote_cycle_met = !initial(M.vote_cycle) || (text2num(SSperf_logging?.round?.id) % initial(M.vote_cycle) == 0)
if(initial(M.votable) && vote_cycle_met)
diff --git a/code/datums/_ndatabase/code/brsql_adapter.dm b/code/datums/_ndatabase/code/brsql_adapter.dm
index 345ddfe005f3..20b1768c5f79 100644
--- a/code/datums/_ndatabase/code/brsql_adapter.dm
+++ b/code/datums/_ndatabase/code/brsql_adapter.dm
@@ -101,8 +101,8 @@
SSdatabase.create_parametric_query(query_updatetable, qpars, CB)
/datum/db/adapter/brsql_adapter/insert_table(table_name, list/values, datum/callback/CB, sync = FALSE)
- if(!sync)
- set waitfor = 0
+ set waitfor = FALSE
+
var/length = values.len
var/list/qpars = list()
var/query_inserttable = getquery_insert_table(table_name, values, qpars)
diff --git a/code/datums/_ndatabase/code/native_adapter.dm b/code/datums/_ndatabase/code/native_adapter.dm
index a5e4d41fb6a0..1c23a6ceab8f 100644
--- a/code/datums/_ndatabase/code/native_adapter.dm
+++ b/code/datums/_ndatabase/code/native_adapter.dm
@@ -83,8 +83,7 @@
SSdatabase.create_query(query_gettable, CB)
/datum/db/adapter/native_adapter/update_table(table_name, list/values, datum/callback/CB, sync = FALSE)
- if(!sync)
- set waitfor = 0
+ set waitfor = FALSE
for(var/list/vals in values)
var/list/qpars = list()
diff --git a/code/game/machinery/OpTable.dm b/code/game/machinery/OpTable.dm
index 3c4104b6c283..c9092a750f73 100644
--- a/code/game/machinery/OpTable.dm
+++ b/code/game/machinery/OpTable.dm
@@ -59,8 +59,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
/obj/structure/machinery/optable/get_examine_text(mob/user)
. = ..()
diff --git a/code/game/machinery/air_alarm.dm b/code/game/machinery/air_alarm.dm
index 16512a944be1..e6fc0c8de76e 100644
--- a/code/game/machinery/air_alarm.dm
+++ b/code/game/machinery/air_alarm.dm
@@ -431,8 +431,6 @@
var/wireIndex = AAlarmWireColorToIndex[wireColor] //not used in this function
AAlarmwires |= wireFlag
switch(wireIndex)
- if(AALARM_WIRE_IDSCAN)
-
if(AALARM_WIRE_POWER)
shorted = 0
shock(usr, 50)
diff --git a/code/game/machinery/bots/mulebot.dm b/code/game/machinery/bots/mulebot.dm
index b70829c708ed..d82591994e7b 100644
--- a/code/game/machinery/bots/mulebot.dm
+++ b/code/game/machinery/bots/mulebot.dm
@@ -551,7 +551,7 @@
var/speed = ((wires & WIRE_MOTOR1) ? 1:0) + ((wires & WIRE_MOTOR2) ? 2:0)
switch(speed)
if(0)
- // do nothing
+ pass()
if(1)
process_bot()
spawn(2)
diff --git a/code/game/machinery/computer/computer.dm b/code/game/machinery/computer/computer.dm
index adce72f7d8b6..304b24a14f04 100644
--- a/code/game/machinery/computer/computer.dm
+++ b/code/game/machinery/computer/computer.dm
@@ -53,8 +53,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
/obj/structure/machinery/computer/bullet_act(obj/projectile/Proj)
if(exproof)
diff --git a/code/game/machinery/computer/medical.dm b/code/game/machinery/computer/medical.dm
index b68ca41d6f09..fe85599018ae 100644
--- a/code/game/machinery/computer/medical.dm
+++ b/code/game/machinery/computer/medical.dm
@@ -123,7 +123,6 @@
else
dat += "
[bdat]"
- else
else
dat += text("{Log In}", src)
show_browser(user, dat, "Medical Records", "med_rec")
@@ -365,8 +364,6 @@
for(var/datum/data/record/E in GLOB.data_core.medical)
if ((E.fields["ref"] == R.fields["ref"] || E.fields["id"] == R.fields["id"]))
M = E
- else
- //Foreach continue //goto(2540)
src.active1 = R
src.active2 = M
src.screen = 4
@@ -417,16 +414,12 @@
for(var/datum/data/record/R as anything in GLOB.data_core.medical)
if ((lowertext(R.fields["name"]) == t1 || t1 == lowertext(R.fields["id"])))
src.active2 = R
- else
- //Foreach continue //goto(3229)
if (!active2)
temp = "Could not locate record [t1]."
else
for(var/datum/data/record/E in GLOB.data_core.general)
if ((E.fields["name"] == src.active2.fields["name"] || E.fields["id"] == src.active2.fields["id"]))
src.active1 = E
- else
- //Foreach continue //goto(3334)
src.screen = 4
if (href_list["print_p"])
diff --git a/code/game/machinery/computer/pod.dm b/code/game/machinery/computer/pod.dm
index 3858230a089c..f6adaa8edd4e 100644
--- a/code/game/machinery/computer/pod.dm
+++ b/code/game/machinery/computer/pod.dm
@@ -20,7 +20,6 @@
for(var/obj/structure/machinery/mass_driver/M in machines)
if(M.id == id)
connected = M
- else
return
return
diff --git a/code/game/machinery/computer/robot.dm b/code/game/machinery/computer/robot.dm
index 12f4faedc979..c5a13e2c3e74 100644
--- a/code/game/machinery/computer/robot.dm
+++ b/code/game/machinery/computer/robot.dm
@@ -55,8 +55,7 @@
dat += " Locked Down |"
else
dat += " Operating Normally |"
- if (!R.canmove)
- else if(R.cell)
+ if(R.canmove && R.cell)
dat += " Battery Installed ([R.cell.charge]/[R.cell.maxcharge]) |"
else
dat += " No Cell Installed |"
diff --git a/code/game/machinery/computer/skills.dm b/code/game/machinery/computer/skills.dm
index f891d46bc36b..a20d344b53a9 100644
--- a/code/game/machinery/computer/skills.dm
+++ b/code/game/machinery/computer/skills.dm
@@ -43,16 +43,16 @@
var/dat
if (temp)
- dat = text("[]
Clear Screen", temp, src)
+ dat = "[temp]
Clear Screen"
else
- dat = text("Confirm Identity: []
", src, (scan ? text("[]", scan.name) : "----------"))
+ dat = "Confirm Identity: [scan ? scan.name : "----------"]
"
if (authenticated)
switch(screen)
if(1.0)
dat += {"
"}
- dat += text("Search Records
", src)
- dat += text("New Record
", src)
+ dat += "Search Records
"
+ dat += "New Record
"
dat += {"
@@ -70,20 +70,19 @@
if(!isnull(GLOB.data_core.general))
for(var/datum/data/record/R in sortRecord(GLOB.data_core.general, sortBy, order))
for(var/datum/data/record/E in GLOB.data_core.security)
- var/background
- dat += text("[] | ", background, src, R, R.fields["name"])
- dat += text("[] | ", R.fields["id"])
- dat += text("[] | ", R.fields["rank"])
+ dat += "
[R.fields["name"]] | "
+ dat += "[R.fields["id"]] | "
+ dat += "[R.fields["rank"]] | "
dat += "
"
- dat += text("Record Maintenance
", src)
- dat += text("{Log Out}",src)
+ dat += "Record Maintenance
"
+ dat += "{Log Out}"
if(2.0)
dat += "Records Maintenance
"
dat += "
Delete All Records
Back"
if(3.0)
dat += "Employment Record
"
if ((istype(active1, /datum/data/record) && GLOB.data_core.general.Find(active1)))
- dat += text(" \
+ dat += "")
+ |
"
else
dat += "General Record Lost!
"
- dat += text("\nDelete Record (ALL)
\nPrint Record
\nBack
", src, src, src)
+ dat += "\nDelete Record (ALL)
\nPrint Record
\nBack
"
if(4.0)
if(!Perp.len)
- dat += text("ERROR. String could not be located.
Back", src)
+ dat += "ERROR. String could not be located.
Back"
else
dat += {"
"}
- dat += text("Search Results for '[]': | ", tempname)
+ dat += "Search Results for '[tempname]': | "
dat += {"
@@ -121,17 +120,14 @@
if(istype(Perp[i+1],/datum/data/record/))
var/datum/data/record/E = Perp[i+1]
crimstat = E.fields["criminal"]
- var/background
- background = "'background-color:#00FF7F;'"
- dat += text("[] | ", background, src, R, R.fields["name"])
- dat += text("[] | ", R.fields["id"])
- dat += text("[] | ", R.fields["rank"])
- dat += text("[] |
", crimstat)
+ dat += "[R.fields["name"]] | "
+ dat += "[R.fields["id"]] | "
+ dat += "[R.fields["rank"]] | "
+ dat += "[crimstat] |
"
dat += "
"
- dat += text("
Return to index.", src)
- else
+ dat += "
Return to index."
else
- dat += text("{Log In}", src)
+ dat += "{Log In}"
show_browser(user, dat, "Employment Records", "secure_rec", "size=600x400")
onclose(user, "secure_rec")
return
@@ -342,7 +338,6 @@ What a mess.*/
if ((R.fields["name"] == active1.fields["name"] || R.fields["id"] == active1.fields["id"]))
GLOB.data_core.medical -= R
qdel(R)
- else
QDEL_NULL(active1)
else
temp = "This function does not appear to be working at the moment. Our apologies."
diff --git a/code/game/machinery/deployable.dm b/code/game/machinery/deployable.dm
index e6df92d258c0..99996bea8978 100644
--- a/code/game/machinery/deployable.dm
+++ b/code/game/machinery/deployable.dm
@@ -54,7 +54,6 @@
src.health -= W.force * 0.75
if("brute")
src.health -= W.force * 0.5
- else
if (src.health <= 0)
src.explode()
..()
diff --git a/code/game/machinery/medical_pod/bodyscanner.dm b/code/game/machinery/medical_pod/bodyscanner.dm
index 4756121e50ae..fdcd0ceb62e6 100644
--- a/code/game/machinery/medical_pod/bodyscanner.dm
+++ b/code/game/machinery/medical_pod/bodyscanner.dm
@@ -62,8 +62,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
#ifdef OBJECTS_PROXY_SPEECH
// Transfers speech to occupant
@@ -124,8 +122,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
/obj/structure/machinery/body_scanconsole/power_change()
..()
diff --git a/code/game/machinery/medical_pod/sleeper.dm b/code/game/machinery/medical_pod/sleeper.dm
index 805fedb29257..35d9a44863d2 100644
--- a/code/game/machinery/medical_pod/sleeper.dm
+++ b/code/game/machinery/medical_pod/sleeper.dm
@@ -385,7 +385,6 @@
t1 = "Unconscious"
if(2)
t1 = "*dead*"
- else
to_chat(user, "[]\t Health %: [] ([])", (occupant.health > 50 ? SPAN_NOTICE("") : SPAN_DANGER("")), occupant.health, t1)
to_chat(user, "[]\t -Core Temperature: []°C ([]°F)
", (occupant.bodytemperature > 50 ? "" : ""), occupant.bodytemperature-T0C, occupant.bodytemperature*1.8-459.67)
to_chat(user, "[]\t -Brute Damage %: []", (occupant.getBruteLoss() < 60 ? SPAN_NOTICE("") : SPAN_DANGER("")), occupant.getBruteLoss())
diff --git a/code/game/machinery/vending/vending.dm b/code/game/machinery/vending/vending.dm
index a74dd923cbe7..414ab4a562e1 100644
--- a/code/game/machinery/vending/vending.dm
+++ b/code/game/machinery/vending/vending.dm
@@ -398,28 +398,25 @@ GLOBAL_LIST_EMPTY_TYPED(total_vending_machines, /obj/structure/machinery/vending
/obj/structure/machinery/vending/proc/GetProductIndex(datum/data/vending_product/product)
var/list/plist
- switch(product.category)
- if(CAT_NORMAL)
- plist=product_records
- if(CAT_HIDDEN)
- plist=hidden_records
- if(CAT_COIN)
- plist=coin_records
- else
- warning("UNKNOWN CATEGORY [product.category] IN TYPE [product.product_path] INSIDE [type]!")
+ if(product.category == CAT_NORMAL)
+ plist = product_records
+ else if(product.category == CAT_HIDDEN)
+ plist = hidden_records
+ else if(product.category == CAT_COIN)
+ plist = coin_records
+ else
+ warning("UNKNOWN CATEGORY [product.category] IN TYPE [product.product_path] INSIDE [type]!")
return plist.Find(product)
/obj/structure/machinery/vending/proc/GetProductByID(pid, category)
- switch(category)
- if(CAT_NORMAL)
- return product_records[pid]
- if(CAT_HIDDEN)
- return hidden_records[pid]
- if(CAT_COIN)
- return coin_records[pid]
- else
- warning("UNKNOWN PRODUCT: PID: [pid], CAT: [category] INSIDE [type]!")
- return null
+ if(category == CAT_NORMAL)
+ return product_records[pid]
+ else if(category == CAT_HIDDEN)
+ return hidden_records[pid]
+ else if(category == CAT_COIN)
+ return coin_records[pid]
+ else
+ warning("UNKNOWN PRODUCT: PID: [pid], CAT: [category] INSIDE [type]!")
/obj/structure/machinery/vending/attack_hand(mob/user)
if(is_tipped_over)
diff --git a/code/game/objects/effects/glowshroom.dm b/code/game/objects/effects/glowshroom.dm
index bebe0ec8b27f..56c6ae45cda7 100644
--- a/code/game/objects/effects/glowshroom.dm
+++ b/code/game/objects/effects/glowshroom.dm
@@ -95,8 +95,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
/obj/effect/glowshroom/fire_act(exposed_temperature, exposed_volume)
if(exposed_temperature > 300)
diff --git a/code/game/objects/explosion_recursive.dm b/code/game/objects/explosion_recursive.dm
index 1f52901c21a6..82566c80302f 100644
--- a/code/game/objects/explosion_recursive.dm
+++ b/code/game/objects/explosion_recursive.dm
@@ -149,7 +149,7 @@ explosion resistance exactly as much as their health
switch(angle) //this reduces power when the explosion is going around corners
if (0)
- //no change
+ pass()
if (45)
if(spread_power >= 0)
spread_power *= 0.75
diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm
index 077c0a463aaa..94de69343c1e 100644
--- a/code/game/objects/items.dm
+++ b/code/game/objects/items.dm
@@ -268,7 +268,6 @@ cases. Override_icon_state should be a list.*/
size = "huge"
if(SIZE_MASSIVE)
size = "massive"
- else
. += "This is a [blood_color ? blood_color != "#030303" ? "bloody " : "oil-stained " : ""][icon2html(src, user)][src.name]. It is a [size] item."
if(desc)
. += desc
diff --git a/code/game/objects/items/reagent_containers/food/snacks.dm b/code/game/objects/items/reagent_containers/food/snacks.dm
index 06a4d785e677..179e2014f8cf 100644
--- a/code/game/objects/items/reagent_containers/food/snacks.dm
+++ b/code/game/objects/items/reagent_containers/food/snacks.dm
@@ -182,8 +182,7 @@
return 0
var/inaccurate = 0
- if(W.sharp == IS_SHARP_ITEM_ACCURATE)
- else if(W.sharp == IS_SHARP_ITEM_BIG)
+ if(W.sharp == IS_SHARP_ITEM_BIG)
inaccurate = 1
else
return 1
diff --git a/code/game/objects/items/stacks/nanopaste.dm b/code/game/objects/items/stacks/nanopaste.dm
index 32e9a030462e..754a36c6012a 100644
--- a/code/game/objects/items/stacks/nanopaste.dm
+++ b/code/game/objects/items/stacks/nanopaste.dm
@@ -40,7 +40,7 @@
H.pain.recalculate_pain()
H.updatehealth()
use(1)
- var/others_msg = "\The [user] applies some nanite paste at[user != M ? " \the [M]'s" : " \the"] [S.display_name] with \the [src]." // Needs to create vars for these messages because macro doesn't work otherwise
+ var/others_msg = "\The [user] applies some nanite paste at[user != M ? " \the [M]'s" : " the"] [S.display_name] with \the [src]." // Needs to create vars for these messages because macro doesn't work otherwise
var/user_msg = "You apply some nanite paste at [user == M ? "your" : "[M]'s"] [S.display_name]."
user.visible_message(SPAN_NOTICE("[others_msg]"),\
SPAN_NOTICE("[user_msg]"))
diff --git a/code/game/objects/items/storage/large_holster.dm b/code/game/objects/items/storage/large_holster.dm
index ef2bcfb7216a..b4a6c3a8c1af 100644
--- a/code/game/objects/items/storage/large_holster.dm
+++ b/code/game/objects/items/storage/large_holster.dm
@@ -326,7 +326,7 @@
/obj/item/storage/large_holster/fuelpack/get_examine_text(mob/user)
. = ..()
if(contents.len)
- . += "It is storing \a M240-T incinerator unit."
+ . += "It is storing a M240-T incinerator unit."
if (get_dist(user, src) <= 1)
if(fuel)
. += "The [fuel.caliber] currently contains: [round(fuel.get_ammo_percent())]% fuel."
diff --git a/code/game/objects/structures/barricade/barricade.dm b/code/game/objects/structures/barricade/barricade.dm
index 0ca2ccb1ddbc..5a72ec33ea2a 100644
--- a/code/game/objects/structures/barricade/barricade.dm
+++ b/code/game/objects/structures/barricade/barricade.dm
@@ -78,7 +78,7 @@
switch(dir)
if(SOUTH)
layer = ABOVE_MOB_LAYER
- else if(NORTH)
+ if(NORTH)
layer = initial(layer) - 0.01
else
layer = initial(layer)
diff --git a/code/game/objects/structures/barricade/handrail.dm b/code/game/objects/structures/barricade/handrail.dm
index ea10dc7256de..ae166dbbf985 100644
--- a/code/game/objects/structures/barricade/handrail.dm
+++ b/code/game/objects/structures/barricade/handrail.dm
@@ -24,7 +24,7 @@
switch(dir)
if(SOUTH)
layer = ABOVE_MOB_LAYER
- else if(NORTH)
+ if(NORTH)
layer = initial(layer) - 0.01
else
layer = initial(layer)
diff --git a/code/game/objects/structures/bookcase.dm b/code/game/objects/structures/bookcase.dm
index c71b2853ea07..becb0906e3c6 100644
--- a/code/game/objects/structures/bookcase.dm
+++ b/code/game/objects/structures/bookcase.dm
@@ -58,8 +58,6 @@
contents_explosion(severity)
deconstruct(FALSE)
return
- else
- return
/obj/structure/bookcase/update_icon()
if(contents.len < 5)
diff --git a/code/game/objects/structures/crates_lockers/closets/utility_closets.dm b/code/game/objects/structures/crates_lockers/closets/utility_closets.dm
index 7848aaba4897..b000fd5733a2 100644
--- a/code/game/objects/structures/crates_lockers/closets/utility_closets.dm
+++ b/code/game/objects/structures/crates_lockers/closets/utility_closets.dm
@@ -51,8 +51,6 @@
new /obj/item/clothing/mask/gas(src)
new /obj/item/clothing/mask/gas(src)
new /obj/item/storage/firstaid/o2(src)
- if ("nothing")
- // doot
// teehee - Ah, tg coders...
if ("delete")
diff --git a/code/game/objects/structures/crates_lockers/crates.dm b/code/game/objects/structures/crates_lockers/crates.dm
index 7c9faaf1a027..9f0417ccb372 100644
--- a/code/game/objects/structures/crates_lockers/crates.dm
+++ b/code/game/objects/structures/crates_lockers/crates.dm
@@ -130,8 +130,6 @@
contents_explosion(severity)
deconstruct(FALSE)
return
- else
- return
/obj/structure/closet/crate/alpha
name = "alpha squad crate"
diff --git a/code/game/objects/structures/lattice.dm b/code/game/objects/structures/lattice.dm
index 38201e052c50..d2b3d36b5920 100644
--- a/code/game/objects/structures/lattice.dm
+++ b/code/game/objects/structures/lattice.dm
@@ -43,8 +43,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
/obj/structure/lattice/attackby(obj/item/C as obj, mob/user as mob)
diff --git a/code/game/objects/structures/reagent_dispensers.dm b/code/game/objects/structures/reagent_dispensers.dm
index 7dc6d883a2d5..6471dfa21520 100644
--- a/code/game/objects/structures/reagent_dispensers.dm
+++ b/code/game/objects/structures/reagent_dispensers.dm
@@ -119,8 +119,6 @@
if(EXPLOSION_THRESHOLD_MEDIUM to INFINITY)
deconstruct(FALSE)
return
- else
- return
/obj/structure/reagent_dispensers/attack_hand()
if(!reagents || reagents.locked)
diff --git a/code/modules/admin/topic/topic.dm b/code/modules/admin/topic/topic.dm
index 31f99870fe43..bb13843bfc34 100644
--- a/code/modules/admin/topic/topic.dm
+++ b/code/modules/admin/topic/topic.dm
@@ -336,86 +336,6 @@
/////////////////////////////////////new ban stuff
- else if(href_list["jobban2"])
-// if(!check_rights(R_BAN)) return
- /*
- var/mob/M = locate(href_list["jobban2"])
- if(!ismob(M))
- to_chat(usr, "This can only be used on instances of type /mob")
- return
-
- if(!M.ckey) //sanity
- to_chat(usr, "This mob has no ckey")
- return
- if(!RoleAuthority)
- to_chat(usr, "The Role Authority is not set up!")
- return
-
- var/datum/entity/player/P = get_player_from_key(M.ckey)
-
- var/dat = ""
- var/body
- var/jobs = ""
-
- /***********************************WARNING!************************************
- The jobban stuff looks mangled and disgusting
- But it looks beautiful in-game
- -Nodrak
- ************************************WARNING!***********************************/
-//Regular jobs
- //Command (Blue)
- jobs += generate_job_ban_list(M, ROLES_CIC, "CIC", "ddddff")
- jobs += "
"
- // SUPPORT
- jobs += generate_job_ban_list(M, ROLES_AUXIL_SUPPORT, "Support", "ccccff")
- jobs += "
"
- // MPs
- jobs += generate_job_ban_list(M, ROLES_POLICE, "Police", "ffdddd")
- jobs += "
"
- //Engineering (Yellow)
- jobs += generate_job_ban_list(M, ROLES_ENGINEERING, "Engineering", "fff5cc")
- jobs += "
"
- //Cargo (Yellow) //Copy paste, yada, yada. Hopefully Snail can rework this in the future.
- jobs += generate_job_ban_list(M, ROLES_REQUISITION, "Requisition", "fff5cc")
- jobs += "
"
- //Medical (White)
- jobs += generate_job_ban_list(M, ROLES_MEDICAL, "Medical", "ffeef0")
- jobs += "
"
- //Marines
- jobs += generate_job_ban_list(M, ROLES_MARINES, "Marines", "ffeeee")
- jobs += "
"
- // MISC
- jobs += generate_job_ban_list(M, ROLES_MISC, "Misc", "aaee55")
- jobs += "
"
- // Xenos (Orange)
- jobs += generate_job_ban_list(M, ROLES_XENO, "Xenos", "a268b1")
- jobs += "
"
- //Extra (Orange)
- var/isbanned_dept = jobban_isbanned(M, "Syndicate", P)
- jobs += ""
- jobs += "Extras |
---|
"
-
- //ERT
- if(jobban_isbanned(M, "Emergency Response Team", P) || isbanned_dept)
- jobs += "Emergency Response Team | "
- else
- jobs += "Emergency Response Team | "
-
- //Survivor
- if(jobban_isbanned(M, "Survivor", P) || isbanned_dept)
- jobs += "Survivor | "
- else
- jobs += "Survivor | "
-
- if(jobban_isbanned(M, "Agent", P) || isbanned_dept)
- jobs += "Agent | "
- else
- jobs += "Agent | "
-
- body = "[jobs]"
- dat = "[body]"
- show_browser(usr, dat, "Job-Ban Panel: [M.name]", "jobban2", "size=800x490")
- return*/ // DEPRECATED
//JOBBAN'S INNARDS
else if(href_list["jobban3"])
if(!check_rights(R_MOD,0) && !check_rights(R_ADMIN)) return
diff --git a/code/modules/asset_cache/asset_list_items.dm b/code/modules/asset_cache/asset_list_items.dm
index d5d44a047947..d1e7f83dacb1 100644
--- a/code/modules/asset_cache/asset_list_items.dm
+++ b/code/modules/asset_cache/asset_list_items.dm
@@ -321,7 +321,7 @@
I = icon(icon_file, icon_state, SOUTH)
var/c = initial(item.color)
if (!isnull(c) && c != "#FFFFFF")
- I.Blend(initial(c), ICON_MULTIPLY)
+ I.Blend(c, ICON_MULTIPLY)
else
if (ispath(k, /obj/effect/essentials_set))
var/obj/effect/essentials_set/es_set = new k()
diff --git a/code/modules/client/preferences.dm b/code/modules/client/preferences.dm
index 554ba28e417f..7111e8ccdc42 100644
--- a/code/modules/client/preferences.dm
+++ b/code/modules/client/preferences.dm
@@ -1413,11 +1413,8 @@ var/const/MAX_SAVE_SLOTS = 10
var/all_ok = TRUE
for(var/i=1, i<=length(new_xeno_prefix), i++)
var/ascii_char = text2ascii(new_xeno_prefix,i)
- switch(ascii_char)
- // A .. Z
- if(65 to 90) //Uppercase Letters will work
- else
- all_ok = FALSE //everything else - won't
+ if(ascii_char < 65 || ascii_char > 90)
+ all_ok = FALSE //everything else - won't
if(all_ok)
xeno_prefix = new_xeno_prefix
else
diff --git a/code/modules/clothing/suits/armor.dm b/code/modules/clothing/suits/armor.dm
index d969587e32e5..cc7fee7724f4 100644
--- a/code/modules/clothing/suits/armor.dm
+++ b/code/modules/clothing/suits/armor.dm
@@ -423,7 +423,7 @@
return
var/obj/item/weapon/gun/W = usr.get_active_hand()
if (W.w_class > SIZE_MEDIUM)
- to_chat(usr, SPAN_DANGER("This gun won't fit in \the belt!"))
+ to_chat(usr, SPAN_DANGER("This gun won't fit in the belt!"))
return
holstered = usr.get_active_hand()
usr.drop_held_item()
diff --git a/code/modules/desert_dam/filtration/consoles.dm b/code/modules/desert_dam/filtration/consoles.dm
index 038b96eb4713..8c2814fafde7 100644
--- a/code/modules/desert_dam/filtration/consoles.dm
+++ b/code/modules/desert_dam/filtration/consoles.dm
@@ -35,8 +35,6 @@ var/global/river_activated = FALSE
if (prob(10))
get_broken()
return
- else
- return
/obj/structure/machinery/filtration/console/proc/get_broken()
if(damaged)
diff --git a/code/modules/flufftext/Chinese.dm b/code/modules/flufftext/Chinese.dm
index 36da1d307a5b..6b19dd61fcf5 100644
--- a/code/modules/flufftext/Chinese.dm
+++ b/code/modules/flufftext/Chinese.dm
@@ -62,12 +62,12 @@
//remove complex/simple -u- glide final_syllables
if(initial.initial_sound_flags & SIMPLE_U_ONLY)
for(var/datum/chinese_sound/final_syllable/final_syllable as anything in possible_final_syllables)
- if(initial(initial(final_syllable.vowel_class)) == VOWEL_CLASS_BACK_CLOSE)
+ if(initial(final_syllable.vowel_class) == VOWEL_CLASS_BACK_CLOSE)
possible_final_syllables -= final_syllable
possible_final_syllables += /datum/chinese_sound/final_syllable/u
else if(initial.initial_sound_flags & HALF_U)
for(var/datum/chinese_sound/final_syllable/final_syllable as anything in possible_final_syllables)
- if(initial(initial(final_syllable.vowel_class)) == VOWEL_CLASS_BACK_CLOSE && initial(final_syllable.final_syllable_sound_flags) & U_GROUP_FULL)
+ if(initial(final_syllable.vowel_class) == VOWEL_CLASS_BACK_CLOSE && initial(final_syllable.final_syllable_sound_flags) & U_GROUP_FULL)
possible_final_syllables -= final_syllable
//check for if the sound is alveolo-palatal or sibilant/retroflex - then remove or keep front close vowels accordingly
diff --git a/code/modules/mob/living/carbon/human/say.dm b/code/modules/mob/living/carbon/human/say.dm
index 4b86c827a069..069392f2c92e 100644
--- a/code/modules/mob/living/carbon/human/say.dm
+++ b/code/modules/mob/living/carbon/human/say.dm
@@ -132,7 +132,6 @@
for(var/message_mode in parsed["modes"])
var/list/obj/item/used_radios = list()
switch(message_mode)
- if(MESSAGE_MODE_LOCAL)
if(RADIO_MODE_WHISPER)
whisper_say(message, speaking, alt_name)
return
diff --git a/code/modules/projectiles/guns/flamer/flamer.dm b/code/modules/projectiles/guns/flamer/flamer.dm
index 13ccd03c3e82..1091df3391b6 100644
--- a/code/modules/projectiles/guns/flamer/flamer.dm
+++ b/code/modules/projectiles/guns/flamer/flamer.dm
@@ -737,8 +737,6 @@ GLOBAL_LIST_EMPTY(flamer_particles)
var/angle = 180 - abs( abs( direction_angle - spread_direction_angle ) - 180 ) // the angle difference between the spread direction and initial direction
switch(angle) //this reduces power when the explosion is going around corners
- if (0)
- //no change
if (45)
spread_power *= 0.75
else //turns out angles greater than 90 degrees almost never happen. This bit also prevents trying to spread backwards
diff --git a/code/modules/reagents/chemistry_reagents/drink.dm b/code/modules/reagents/chemistry_reagents/drink.dm
index 468243a0cc8d..3bd7336c32b6 100644
--- a/code/modules/reagents/chemistry_reagents/drink.dm
+++ b/code/modules/reagents/chemistry_reagents/drink.dm
@@ -85,13 +85,13 @@
/datum/reagent/drink/carrotjuice/on_mob_life(mob/living/M)
. = ..()
- if(!.) return
+ if(!.)
+ return
M.ReduceEyeBlur(1)
M.ReduceEyeBlind(1)
- if(!data) data = 1
+ if(!data)
+ data = 1
switch(data)
- if(1 to 20)
- //nothing
if(21 to INFINITY)
if(prob(data-10))
M.disabilities &= ~NEARSIGHTED
diff --git a/colonialmarines.dme b/colonialmarines.dme
index 63140be5e458..5aaa405c2b90 100644
--- a/colonialmarines.dme
+++ b/colonialmarines.dme
@@ -1,4 +1,4 @@
-s// DM Environment file for colonialmarines.dme.
+// DM Environment file for colonialmarines.dme.
// All manual changes should be made outside the BEGIN_ and END_ blocks.
// New source code should be placed in .dm files: choose File/New --> Code File.
// BEGIN_INTERNALS
@@ -11,6 +11,7 @@ s// DM Environment file for colonialmarines.dme.
#define DEBUG
// END_PREFERENCES
// BEGIN_INCLUDE
+#include "code\__odlint.dm"
#include "code\_byond_version_compat.dm"
#include "code\_compile_options.dm"
#include "code\_experiments.dm"
diff --git a/dependencies.sh b/dependencies.sh
index 2889751d36e6..f88c2f9b0a4b 100644
--- a/dependencies.sh
+++ b/dependencies.sh
@@ -19,3 +19,5 @@ export SPACEMAN_DMM_VERSION=suite-1.7.2
# Python version for mapmerge and other tools
export PYTHON_VERSION=3.7.9
+
+export OPENDREAM_VERSION=0.2.0
diff --git a/tools/ci/download_od.sh b/tools/ci/download_od.sh
new file mode 100644
index 000000000000..024f93f9289c
--- /dev/null
+++ b/tools/ci/download_od.sh
@@ -0,0 +1,11 @@
+#!/bin/bash
+set -eo pipefail
+
+if [ -z "${OPENDREAM_VERSION+x}" ]; then
+ source dependencies.sh
+fi
+
+git clone https://github.com/OpenDreamProject/OpenDream.git ~/OpenDream
+cd ~/OpenDream
+git checkout tags/v${OPENDREAM_VERSION}
+git submodule update --init --recursive
diff --git a/tools/ci/run_od.sh b/tools/ci/run_od.sh
new file mode 100644
index 000000000000..3eeac5907353
--- /dev/null
+++ b/tools/ci/run_od.sh
@@ -0,0 +1,4 @@
+#!/bin/bash
+set -eo pipefail
+
+dotnet ~/OpenDream/DMCompiler/bin/Release/net7.0/DMCompiler.dll --suppress-unimplemented colonialmarines.dme
diff --git a/tools/ci/setup_od.sh b/tools/ci/setup_od.sh
new file mode 100644
index 000000000000..6d2ec170687c
--- /dev/null
+++ b/tools/ci/setup_od.sh
@@ -0,0 +1,7 @@
+#!/bin/bash
+set -eo pipefail
+
+cd ~/OpenDream
+
+dotnet restore
+dotnet build -c Release
diff --git a/tools/ci/validate_dme.py b/tools/ci/validate_dme.py
index 33066f72e75e..55666480425d 100644
--- a/tools/ci/validate_dme.py
+++ b/tools/ci/validate_dme.py
@@ -17,6 +17,9 @@
# Included by BSQL/includes.dm
r'code/__HELPERS/BSQL/**/*.dm',
+
+ # Included as part of OD lints
+ r'code/__pragmas.dm'
]
lines = []