Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Sniper bug improvement #246

Open
wants to merge 3 commits into
base: master
Choose a base branch
from

Conversation

ZantetsukenGT
Copy link

@ZantetsukenGT ZantetsukenGT commented Jul 12, 2022

When a player gets killed, and after the respawn_time passes, the player will briefly be streamed out and then streamed in to be respawned, and during that brief time if that player gets shot by any weapon, the library will set the issuerid to INVALID_PLAYER_ID, which later on will falsely trigger the sniper bug detection. This behavior can be quickly reproduced with SetRespawnTime(0) and respawning the player on the spot.

This PR is only relevant to servers with lag_compensation disabled.

This PR also added a new enum variant namely WC_SNIPER_BUG which can be used in OnInvalidWeaponDamage.

@ADRFranklin
Copy link
Collaborator

Why make a new enum item when you could just return WC_NO_DAMAGED or WC_NO_ISSUER. Returning the sniper bug enum value doesn't really offer any new information, that wouldn't already be understood with the existing enum values.

@ZantetsukenGT
Copy link
Author

That's debatible, I added the extra enum variant long time ago since it would be easier to use in OnInvalidWeaponDamage as no further checks are needed to know what triggered it and under what circumstance.

99% of the time this sniper bug check is triggered by the actual sniper bug, the other 1% of the time, by cj with his tec9 bug.

Though further checks are still needed to distinguish sniper bug from cj, I still consider a new enum variant as more ergonomic option to the library user.

I will change it back to WC_NO_ISSUER to keep compatibility with current implementations.

@ZantetsukenGT
Copy link
Author

I came out with a cleaner solution, applying the same logic from OnPlayerGiveDamage: reject damage when either player is streamed out.

Let me know your thoughts about this, imo this should've been the default behavior.

@NexiusTailer
Copy link
Contributor

NexiusTailer commented Jul 19, 2022

There shouldn't be returning 0
https://github.com/oscar-broman/samp-weapon-config/pull/246/files#diff-b22ee17f67f3abb181cf164d690011a5abe341533db8673200a945bf7b386ecaR3599

Because most of damage at least from grenade explosions and fire may be completely blocked when issuerid just died (but it doesn't mean that the damage should be dropped, for example, if a grenade or molotov cocktail detonated only after his death).

The current way with resetting issuerid to invalid id is the best solution to both prevent damage spoofing and keep a real damage apply in some specific cases like mentioned.

@ZantetsukenGT
Copy link
Author

An additional check can be added around the same line to allow all explosion or fire and reset issuerid to invalid id, but block the remaining weapons when they deal unstreamed damage.

It may not be the cleanest but it could work out and performance hit will be negligible at best and potentially faster since we are blocking earliler when this situation arises.

In any case, let me know your thoughts, should I continue this by adding the explosion and fire check or revert to what I initially had without the additional enum, which specifically targets the sniper bug.

@NexiusTailer
Copy link
Contributor

NexiusTailer commented Jul 20, 2022

Well you can also check for lag_compensation and do your logic (dropping the damage) if it's disabled if you said it's relevant only for non-lagcomp servers. Anyway most of people use lagcomp enabled and they won't need this for any weapon you'll try to check for.

Something like this I suppose:

// Will be applied on fire, explosion, vehicle and heliblades (carpark) damage
// Both players should see eachother, if playerid claims to keep issuerid valid
if ((!IsPlayerStreamedIn(playerid, issuerid) && !WC_IsPlayerPaused(issuerid)) || !IsPlayerStreamedIn(issuerid, playerid)) {
	if (s_LagCompMode) {
		// Probably fake or belated damage, so let's just reset issuerid
		issuerid = INVALID_PLAYER_ID;
	} else {
		// Also could be a sniper bug, reject the hit then
		AddRejectedHit(playerid, damagedid, HIT_UNSTREAMED, weaponid, damagedid);
		return 0;
	}
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants