From 8857365c1c5c147f70facceb77bfc9d4fa169af8 Mon Sep 17 00:00:00 2001 From: PsiOmega Date: Sun, 30 Nov 2014 14:41:32 +0100 Subject: [PATCH] Fixes exploit that lets AIs use machinery even after cameras are disabled. --- code/game/dna/dna_modifier.dm | 1 + code/game/machinery/Sleeper.dm | 2 +- code/game/machinery/cryo.dm | 1 + code/game/machinery/cryopod.dm | 1 + code/game/machinery/machinery.dm | 78 +++++++++++++++------- code/modules/mob/living/silicon/ai/ai.dm | 1 + code/modules/mob/living/silicon/ai/life.dm | 2 + 7 files changed, 62 insertions(+), 24 deletions(-) diff --git a/code/game/dna/dna_modifier.dm b/code/game/dna/dna_modifier.dm index 01ef334ce7d..322e65202f9 100644 --- a/code/game/dna/dna_modifier.dm +++ b/code/game/dna/dna_modifier.dm @@ -46,6 +46,7 @@ use_power = 1 idle_power_usage = 50 active_power_usage = 300 + interact_offline = 1 var/locked = 0 var/mob/living/carbon/occupant = null var/obj/item/weapon/reagent_containers/glass/beaker = null diff --git a/code/game/machinery/Sleeper.dm b/code/game/machinery/Sleeper.dm index f5474c927d0..9e52c28133a 100644 --- a/code/game/machinery/Sleeper.dm +++ b/code/game/machinery/Sleeper.dm @@ -13,7 +13,7 @@ use_power = 1 idle_power_usage = 40 - + interact_offline = 1 /obj/machinery/sleep_console/process() if(stat & (NOPOWER|BROKEN)) diff --git a/code/game/machinery/cryo.dm b/code/game/machinery/cryo.dm index 3974ebdd503..32543822b99 100644 --- a/code/game/machinery/cryo.dm +++ b/code/game/machinery/cryo.dm @@ -7,6 +7,7 @@ density = 1 anchored = 1.0 layer = 2.8 + interact_offline = 1 var/on = 0 use_power = 1 diff --git a/code/game/machinery/cryopod.dm b/code/game/machinery/cryopod.dm index d9c40ce64e6..c2a6d996a1e 100644 --- a/code/game/machinery/cryopod.dm +++ b/code/game/machinery/cryopod.dm @@ -15,6 +15,7 @@ icon = 'icons/obj/Cryogenic2.dmi' icon_state = "cellconsole" circuit = "/obj/item/weapon/circuitboard/cryopodcontrol" + interact_offline = 1 var/mode = null //Used for logging people entering cryosleep and important items they are carrying. diff --git a/code/game/machinery/machinery.dm b/code/game/machinery/machinery.dm index fab5bbea6e0..74799aa672c 100644 --- a/code/game/machinery/machinery.dm +++ b/code/game/machinery/machinery.dm @@ -109,6 +109,7 @@ Class Procs: var/list/component_parts = list() //list of all the parts used to build it, if made from certain kinds of frames. var/uid var/manual = 0 + var/interact_offline = 0 // Can the machine be interacted with while de-powered. var/global/gl_uid = 1 /obj/machinery/drain_power(var/drain_check) @@ -197,35 +198,66 @@ Class Procs: /obj/machinery/proc/inoperable(var/additional_flags = 0) return (stat & (NOPOWER|BROKEN|additional_flags)) + /obj/machinery/Topic(href, href_list, var/nowindow = 0, var/checkrange = 1) if(..()) return 1 - if(inoperable()) + if(!can_be_used_by(usr, be_close = checkrange)) return 1 - if(usr.restrained() || usr.lying || usr.stat) - return 1 - if ( ! (istype(usr, /mob/living/carbon/human) || \ - istype(usr, /mob/living/silicon) || \ - istype(usr, /mob/living/carbon/monkey)) ) - usr << "\red You don't have the dexterity to do this!" - return 1 - - var/norange = 0 - if(istype(usr, /mob/living/carbon/human)) - var/mob/living/carbon/human/H = usr - if(istype(H.l_hand, /obj/item/tk_grab)) - norange = 1 - else if(istype(H.r_hand, /obj/item/tk_grab)) - norange = 1 - - if(checkrange && !norange) - if ((!in_range(src, usr) || !istype(src.loc, /turf)) && !istype(usr, /mob/living/silicon)) - return 1 - - src.add_fingerprint(usr) - + add_fingerprint(usr) return 0 +/obj/machinery/proc/can_be_used_by(mob/user, be_close = 1) + if(!interact_offline && stat & (NOPOWER|BROKEN)) + return 0 + if(!user.canUseTopic(src, be_close)) + return 0 + return 1 + +//////////////////////////////////////////////////////////////////////////////////////////// + +/mob/proc/canUseTopic(atom/movable/M, be_close = 1) + return + +/mob/dead/observer/canUseTopic(atom/movable/M, be_close = 1) + if(check_rights(R_ADMIN, 0)) + return + +/mob/living/canUseTopic(atom/movable/M, be_close = 1, no_dextery = 0) + if(no_dextery) + src << "You don't have the dexterity to do this!" + return 0 + return be_close && !in_range(M, src) + +/mob/living/carbon/human/canUseTopic(atom/movable/M, be_close = 1) + if(restrained() || lying || stat || stunned || weakened) + return + if(be_close && !in_range(M, src)) + if(TK in mutations) + var/mob/living/carbon/human/H = M + if(istype(H.l_hand, /obj/item/tk_grab) || istype(H.r_hand, /obj/item/tk_grab)) + return 1 + return + if(!isturf(M.loc) && M.loc != src) + return + return 1 + +/mob/living/silicon/ai/canUseTopic(atom/movable/M) + if(stat) + return + //stop AIs from leaving windows open and using then after they lose vision + //apc_override is needed here because AIs use their own APC when powerless + if(cameranet && !cameranet.checkTurfVis(get_turf(M)) && !apc_override) + return + return 1 + +/mob/living/silicon/robot/canUseTopic(atom/movable/M) + if(stat || lockcharge || stunned || weakened) + return + return 1 + +//////////////////////////////////////////////////////////////////////////////////////////// + /obj/machinery/attack_ai(mob/user as mob) if(isrobot(user)) // For some reason attack_robot doesn't work diff --git a/code/modules/mob/living/silicon/ai/ai.dm b/code/modules/mob/living/silicon/ai/ai.dm index 16d42b07dec..e1fa6caa6c0 100644 --- a/code/modules/mob/living/silicon/ai/ai.dm +++ b/code/modules/mob/living/silicon/ai/ai.dm @@ -72,6 +72,7 @@ var/list/ai_verbs_default = list( var/mob/living/silicon/ai/parent = null + var/apc_override = 0 //hack for letting the AI use its APC even when visionless var/camera_light_on = 0 //Defines if the AI toggled the light on the camera it's looking through. var/datum/trackable/track = null var/last_announcement = "" diff --git a/code/modules/mob/living/silicon/ai/life.dm b/code/modules/mob/living/silicon/ai/life.dm index 5047f87d0d3..cf11f2d2118 100644 --- a/code/modules/mob/living/silicon/ai/life.dm +++ b/code/modules/mob/living/silicon/ai/life.dm @@ -166,7 +166,9 @@ src << "Receiving control information from APC." sleep(2) //bring up APC dialog + apc_override = 1 theAPC.attack_ai(src) + apc_override = 0 src:aiRestorePowerRoutine = 3 src << "Here are your current laws:" src.show_laws()