diff --git a/.github/workflows/ci-extension.yml b/.github/workflows/ci-extension.yml
index e3fdd58..f90a6e9 100644
--- a/.github/workflows/ci-extension.yml
+++ b/.github/workflows/ci-extension.yml
@@ -35,40 +35,41 @@ jobs:
# We currently only support tf2 - however when we support more sdks
# we will have to deal with the special case of our custom tf2 + AM's sdks
SDKS: '["tf2"]'
- MMSOURCE_VERSION: '1.10'
- SOURCEMOD_VERSION: '1.11'
+ MMSOURCE_VERSION: '1.12-dev'
+ SOURCEMOD_VERSION: '35ac74c7a7243e17a3aa2338b116eaa8a0a9ccdc'
CACHE_PATH: ${{ github.workspace }}/cache
steps:
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
name: Repository checkout
with:
fetch-depth: 0
+ submodules: true
path: CBaseNPC
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
name: Sourcemod checkout
with:
repository: alliedmodders/sourcemod
- ref: ${{ env.SOURCEMOD_VERSION }}-dev
+ ref: ${{ env.SOURCEMOD_VERSION }}
submodules: true
path: cache/sourcemod
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
name: Metamod-Source checkout
with:
repository: alliedmodders/metamod-source
- ref: ${{ env.MMSOURCE_VERSION }}-dev
+ ref: ${{ env.MMSOURCE_VERSION }}
path: cache/metamod
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
name: AMBuild checkout
with:
repository: alliedmodders/ambuild
ref: master
path: cache/ambuild
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
name: Custom TF2 SDK checkout
with:
repository: TF2-DMB/hl2sdk-tf2
@@ -121,7 +122,7 @@ jobs:
run: |
mkdir build
cd build
- python ../configure.py --extension-only --enable-auto-versioning --enable-optimize --sdks=${{ join(fromJSON(env.SDKS)) }} --mms-path=${{ env.CACHE_PATH }}/metamod --hl2sdk-root=${{ env.CACHE_PATH }} --sm-path=${{ env.CACHE_PATH }}/sourcemod
+ python ../configure.py --extension-only --enable-auto-versioning --enable-optimize --targets x86,x86_64 --sdks=${{ join(fromJSON(env.SDKS)) }} --mms-path=${{ env.CACHE_PATH }}/metamod --hl2sdk-root=${{ env.CACHE_PATH }} --sm-path=${{ env.CACHE_PATH }}/sourcemod
ambuild
- name: Upload artifact
diff --git a/.github/workflows/ci-scripting.yml b/.github/workflows/ci-scripting.yml
index 5b50a83..d70aea2 100644
--- a/.github/workflows/ci-scripting.yml
+++ b/.github/workflows/ci-scripting.yml
@@ -28,7 +28,10 @@ jobs:
runs-on: ubuntu-latest
steps:
- - uses: actions/checkout@v3
+ - uses: actions/checkout@v4
+ with:
+ fetch-depth: 0
+ submodules: true
- uses: actions/setup-python@v3
name: Setup Python 3.8
diff --git a/.gitmodules b/.gitmodules
new file mode 100644
index 0000000..84ea369
--- /dev/null
+++ b/.gitmodules
@@ -0,0 +1,6 @@
+[submodule "hl2sdk-manifests"]
+ path = hl2sdk-manifests
+ url = git@github.com:alliedmodders/hl2sdk-manifests.git
+[submodule "third_party\\safetyhook"]
+ path = third_party\\safetyhook
+ url = https://github.com/alliedmodders/safetyhook.git
diff --git a/AMBuildScript b/AMBuildScript
index b942aad..0942047 100644
--- a/AMBuildScript
+++ b/AMBuildScript
@@ -1,61 +1,6 @@
# vim: set sts=2 ts=8 sw=2 tw=99 et ft=python:
import os, sys, shutil
-# Simple extensions do not need to modify this file.
-
-class SDK(object):
- def __init__(self, sdk, ext, aDef, name, platform, dir):
- self.folder = 'hl2sdk-' + dir
- self.envvar = sdk
- self.ext = ext
- self.code = aDef
- self.define = name
- self.platform = platform
- self.name = dir
- self.path = None # Actual path
- self.platformSpec = platform
-
- # By default, nothing supports x64.
- if type(platform) is list:
- self.platformSpec = {p: ['x86'] for p in platform}
- else:
- self.platformSpec = platform
-
- def shouldBuild(self, targets):
- for cxx in targets:
- if cxx.target.platform in self.platformSpec:
- if cxx.target.arch in self.platformSpec[cxx.target.platform]:
- return True
- return False
-
-WinOnly = ['windows']
-WinLinux = ['windows', 'linux']
-WinLinuxMac = ['windows', 'linux', 'mac']
-
-PossibleSDKs = {
-# 'episode1': SDK('HL2SDK', '1.ep1', '1', 'EPISODEONE', WinLinux, 'episode1'),
-# 'ep2': SDK('HL2SDKOB', '2.ep2', '3', 'ORANGEBOX', WinLinux, 'orangebox'),
-# 'css': SDK('HL2SDKCSS', '2.css', '6', 'CSS', WinLinuxMac, 'css'),
-# 'hl2dm': SDK('HL2SDKHL2DM', '2.hl2dm', '7', 'HL2DM', WinLinuxMac, 'hl2dm'),
-# 'dods': SDK('HL2SDKDODS', '2.dods', '8', 'DODS', WinLinuxMac, 'dods'),
-# 'sdk2013': SDK('HL2SDK2013', '2.sdk2013', '9', 'SDK2013', WinLinuxMac, 'sdk2013'),
- 'tf2': SDK('HL2SDKTF2', '2.tf2', '11', 'TF2', WinLinuxMac, 'tf2')
-# 'l4d': SDK('HL2SDKL4D', '2.l4d', '12', 'LEFT4DEAD', WinLinuxMac, 'l4d'),
-# 'nucleardawn': SDK('HL2SDKND', '2.nd', '13', 'NUCLEARDAWN', WinLinuxMac, 'nucleardawn'),
-# 'l4d2': SDK('HL2SDKL4D2', '2.l4d2', '15', 'LEFT4DEAD2', WinLinuxMac, 'l4d2'),
-# 'darkm': SDK('HL2SDK-DARKM', '2.darkm', '2', 'DARKMESSIAH', WinOnly, 'darkm'),
-# 'swarm': SDK('HL2SDK-SWARM', '2.swarm', '16', 'ALIENSWARM', WinOnly, 'swarm'),
-# 'bgt': SDK('HL2SDK-BGT', '2.bgt', '4', 'BLOODYGOODTIME', WinOnly, 'bgt'),
-# 'eye': SDK('HL2SDK-EYE', '2.eye', '5', 'EYE', WinOnly, 'eye'),
-# 'csgo': SDK('HL2SDKCSGO', '2.csgo', '20', 'CSGO', WinLinuxMac, 'csgo'),
-# 'dota': SDK('HL2SDKDOTA', '2.dota', '21', 'DOTA', [], 'dota'),
-# 'portal2': SDK('HL2SDKPORTAL2', '2.portal2', '17', 'PORTAL2', [], 'portal2'),
-# 'blade': SDK('HL2SDKBLADE', '2.blade', '18', 'BLADE', WinLinux, 'blade'),
-# 'insurgency': SDK('HL2SDKINSURGENCY', '2.insurgency', '19', 'INSURGENCY', WinLinuxMac, 'insurgency'),
-# 'contagion': SDK('HL2SDKCONTAGION', '2.contagion', '14', 'CONTAGION', WinOnly, 'contagion'),
-# 'bms': SDK('HL2SDKBMS', '2.bms', '10', 'BMS', WinLinux, 'bms'),
-}
-
def ResolveEnvPath(env, folder=None):
if env in os.environ:
path = os.environ[env]
@@ -86,9 +31,13 @@ def SetArchFlags(compiler):
if compiler.target.arch == 'x86_64':
compiler.defines += ['WIN64']
+SdkHelpers = builder.Eval('hl2sdk-manifests/SdkHelpers.ambuild', { 'Project': 'cbasenpc' })
+
class ExtensionConfig(object):
def __init__(self):
self.sdks = {}
+ self.sdk_manifests = []
+ self.sdk_targets = []
self.binaries = []
self.extensions = []
self.generated_headers = None
@@ -99,6 +48,7 @@ class ExtensionConfig(object):
self.smapi_path = None
self.all_targets = []
self.target_archs = set()
+ self.libsafetyhook = {}
if self.build_extension():
if builder.options.targets:
@@ -147,35 +97,46 @@ class ExtensionConfig(object):
import re
with open(os.path.join(builder.sourcePath, 'product.version'), 'r') as fp:
productContents = fp.read()
- m = re.match('(\d+)\.(\d+)\.(\d+).*', productContents)
+ m = re.match(r'(\d+)\.(\d+)\.(\d+).*', productContents)
if m == None:
self.productVersion = '1.0.0'
else:
major, minor, release = m.groups()
self.productVersion = '{0}.{1}.{2}'.format(major, minor, release)
+ def findSdkPath(self, sdk_name):
+ dir_name = 'hl2sdk-{}'.format(sdk_name)
+ if builder.options.hl2sdk_root:
+ sdk_path = os.path.join(builder.options.hl2sdk_root, dir_name)
+ if os.path.exists(sdk_path):
+ return sdk_path
+ return ResolveEnvPath('HL2SDK{}'.format(sdk_name.upper()), dir_name)
+
+ def shouldIncludeSdk(self, sdk):
+ return not sdk.get('source2', False)
+
def detectSDKs(self):
- sdk_list = builder.options.sdks.split(',')
- use_all = sdk_list[0] == 'all'
- use_present = sdk_list[0] == 'present'
-
- for sdk_name in PossibleSDKs:
- sdk = PossibleSDKs[sdk_name]
- if sdk.shouldBuild(self.all_targets):
- if builder.options.hl2sdk_root:
- sdk_path = os.path.join(builder.options.hl2sdk_root, sdk.folder)
- else:
- sdk_path = ResolveEnvPath(sdk.envvar, sdk.folder)
- if sdk_path is None or not os.path.isdir(sdk_path):
- if use_all or sdk_name in sdk_list:
- raise Exception('Could not find a valid path for {0}'.format(sdk.envvar))
- continue
- if use_all or use_present or sdk_name in sdk_list:
- sdk.path = Normalize(sdk_path)
- self.sdks[sdk_name] = sdk
-
- if len(self.sdks) < 1:
- raise Exception('At least one SDK must be available.')
+ sdk_list = [s for s in builder.options.sdks.split(',') if s]
+ SdkHelpers.sdk_filter = self.shouldIncludeSdk
+ SdkHelpers.find_sdk_path = self.findSdkPath
+ SdkHelpers.findSdks(builder, self.all_targets, sdk_list)
+
+ self.sdks = SdkHelpers.sdks
+ self.sdk_manifests = SdkHelpers.sdk_manifests
+ self.sdk_targets = SdkHelpers.sdk_targets
+
+ for target in self.sdk_targets:
+ if target.sdk['name'] != 'tf2':
+ continue
+ # Our custom tf2 hl2sdk already has those defines
+ rm_defines = [
+ 'stricmp=strcasecmp', '_stricmp=strcasecmp',
+ '_snprintf=snprintf', '_vsnprintf=vsnprintf,'
+ ]
+ cxx = target.cxx
+ for rm_define in rm_defines:
+ if rm_define in cxx.defines:
+ cxx.defines.remove(rm_define)
if builder.options.sm_path:
self.sm_root = builder.options.sm_path
@@ -283,10 +244,6 @@ class ExtensionConfig(object):
def configure_gcc(self, cxx):
cxx.defines += [
- 'stricmp=strcasecmp',
- '_stricmp=strcasecmp',
- '_snprintf=snprintf',
- '_vsnprintf=vsnprintf',
'typeof=__typeof__',
'HAVE_STDINT_H',
'GNUC',
@@ -300,7 +257,6 @@ class ExtensionConfig(object):
'-Wno-switch',
'-Wno-array-bounds',
'-msse',
- '-m32',
'-fvisibility=hidden',
]
cxx.cxxflags += [
@@ -311,10 +267,9 @@ class ExtensionConfig(object):
'-fvisibility-inlines-hidden',
'-fpermissive'
]
- cxx.linkflags += ['-m32']
- have_gcc = cxx.vendor == 'gcc'
- have_clang = cxx.vendor == 'clang'
+ have_gcc = cxx.family == 'gcc'
+ have_clang = cxx.family == 'clang'
if cxx.version >= 'clang-3.9' or cxx.version == 'clang-3.4' or cxx.version > 'apple-clang-6.0':
cxx.cxxflags += ['-Wno-expansion-to-defined']
if cxx.version == 'clang-3.9' or cxx.version == 'apple-clang-8.0':
@@ -350,6 +305,9 @@ class ExtensionConfig(object):
if builder.options.opt == '1':
cxx.cflags += ['-O3']
+ # Don't omit the frame pointer.
+ cxx.cflags += ['-fno-omit-frame-pointer']
+
def configure_msvc(self, cxx):
if builder.options.debug == '1':
cxx.cflags += ['/MTd']
@@ -371,7 +329,6 @@ class ExtensionConfig(object):
'/std:c++17'
]
cxx.linkflags += [
- '/MACHINE:X86',
'kernel32.lib',
'user32.lib',
'gdi32.lib',
@@ -387,7 +344,7 @@ class ExtensionConfig(object):
]
if builder.options.opt == '1':
- cxx.cflags += ['/Ox', '/Zo', '-O3']
+ cxx.cflags += ['/Ox', '/Zo']
cxx.linkflags += ['/OPT:ICF', '/OPT:REF']
if builder.options.debug == '1':
@@ -398,7 +355,7 @@ class ExtensionConfig(object):
cxx.cflags += ['/Oy-']
def configure_linux(self, cxx):
- cxx.defines += ['_LINUX', 'POSIX']
+ cxx.defines += ['LINUX', '_LINUX', 'POSIX', '_FILE_OFFSET_BITS=64']
cxx.linkflags += ['-Wl,--exclude-libs,ALL', '-lm']
if cxx.vendor == 'gcc':
cxx.linkflags += ['-static-libgcc']
@@ -441,135 +398,10 @@ class ExtensionConfig(object):
os.path.join(self.mms_root, 'core', 'sourcehook'),
]
- defines = ['RAD_TELEMETRY_DISABLED']
- defines += ['SE_' + PossibleSDKs[i].define + '=' + PossibleSDKs[i].code for i in PossibleSDKs]
- compiler.defines += defines
-
- paths = [
- ['public'],
- ['public', 'engine'],
- ['public', 'mathlib'],
- ['public', 'vstdlib'],
- ['public', 'tier0'],
- ['public', 'tier1']
- ]
- if sdk.name == 'episode1' or sdk.name == 'darkm':
- paths.append(['public', 'dlls'])
- paths.append(['game_shared'])
- else:
- paths.append(['public', 'game', 'server'])
- paths.append(['public', 'toolframework'])
- paths.append(['game', 'shared'])
- paths.append(['common'])
-
- compiler.defines += ['SOURCE_ENGINE=' + sdk.code]
-
- if sdk.name in ['tf2', 'sdk2013', 'bms'] and compiler.like('gcc'):
- # The 2013 SDK already has these in public/tier0/basetypes.h
- compiler.defines.remove('stricmp=strcasecmp')
- compiler.defines.remove('_stricmp=strcasecmp')
- compiler.defines.remove('_snprintf=snprintf')
- compiler.defines.remove('_vsnprintf=vsnprintf')
-
- if compiler.like('msvc'):
- compiler.defines += ['COMPILER_MSVC']
- if compiler.target.arch == 'x86':
- compiler.defines += ['COMPILER_MSVC32']
- elif compiler.target.arch == 'x86_64':
- compiler.defines += ['COMPILER_MSVC64']
- compiler.linkflags += ['legacy_stdio_definitions.lib']
- else:
- compiler.defines += ['COMPILER_GCC']
-
- if compiler.target.arch == 'x86_64':
- compiler.defines += ['X64BITS', 'PLATFORM_64BITS']
-
- # For everything after Swarm, this needs to be defined for entity networking
- # to work properly with sendprop value changes.
- if sdk.name in ['blade', 'insurgency', 'doi', 'csgo']:
- compiler.defines += ['NETWORK_VARS_ENABLED']
-
- if sdk.name in ['css', 'hl2dm', 'dods', 'sdk2013', 'bms', 'tf2', 'l4d', 'nucleardawn', 'l4d2']:
- if compiler.target.platform in ['linux', 'mac']:
- compiler.defines += ['NO_HOOK_MALLOC', 'NO_MALLOC_OVERRIDE']
-
- if compiler.target.platform == 'linux':
- if sdk.name in ['csgo', 'blade']:
- compiler.linkflags.remove('-static-libstdc++')
- compiler.defines += ['_GLIBCXX_USE_CXX11_ABI=0']
-
- for path in paths:
- compiler.cxxincludes += [os.path.join(sdk.path, *path)]
-
- if compiler.target.platform == 'linux':
- if sdk.name == 'episode1':
- lib_folder = os.path.join(sdk.path, 'linux_sdk')
- elif sdk.name in ['sdk2013', 'bms']:
- lib_folder = os.path.join(sdk.path, 'lib', 'public', 'linux32')
- elif compiler.target.arch == 'x86_64':
- lib_folder = os.path.join(sdk.path, 'lib', 'linux64')
- else:
- lib_folder = os.path.join(sdk.path, 'lib', 'linux')
- elif compiler.target.platform == 'mac':
- if sdk.name in ['sdk2013', 'bms']:
- lib_folder = os.path.join(sdk.path, 'lib', 'public', 'osx32')
- elif compiler.target.arch == 'x86_64':
- lib_folder = os.path.join(sdk.path, 'lib', 'osx64')
- else:
- lib_folder = os.path.join(sdk.path, 'lib', 'mac')
-
- if compiler.target.platform in ['linux', 'mac']:
- if sdk.name in ['sdk2013', 'bms'] or compiler.target.arch == 'x86_64':
- compiler.postlink += [
- os.path.join(lib_folder, 'tier1.a'),
- os.path.join(lib_folder, 'mathlib.a')
- ]
- else:
- compiler.postlink += [
- os.path.join(lib_folder, 'tier1_i486.a'),
- os.path.join(lib_folder, 'mathlib_i486.a')
- ]
-
- if sdk.name in ['blade', 'insurgency', 'doi', 'csgo']:
- if compiler.target.arch == 'x86_64':
- compiler.postlink += [os.path.join(lib_folder, 'interfaces.a')]
- else:
- compiler.postlink += [os.path.join(lib_folder, 'interfaces_i486.a')]
-
- dynamic_libs = []
- if compiler.target.platform == 'linux':
- if sdk.name in ['css', 'hl2dm', 'dods', 'tf2', 'sdk2013', 'bms', 'nucleardawn', 'l4d2', 'insurgency', 'doi']:
- dynamic_libs = ['libtier0_srv.so', 'libvstdlib_srv.so']
- elif compiler.target.arch == 'x86_64' and sdk.name in ['csgo', 'mock']:
- dynamic_libs = ['libtier0_client.so', 'libvstdlib_client.so']
- elif sdk.name in ['l4d', 'blade', 'insurgency', 'doi', 'csgo']:
- dynamic_libs = ['libtier0.so', 'libvstdlib.so']
- else:
- dynamic_libs = ['tier0_i486.so', 'vstdlib_i486.so']
- elif compiler.target.platform == 'mac':
- compiler.linkflags.append('-liconv')
- dynamic_libs = ['libtier0.dylib', 'libvstdlib.dylib']
- elif compiler.target.platform == 'windows':
- libs = ['tier0', 'tier1', 'vstdlib', 'mathlib']
- if sdk.name in ['swarm', 'blade', 'insurgency', 'doi', 'csgo']:
- libs.append('interfaces')
- for lib in libs:
- if compiler.target.arch == 'x86':
- lib_path = os.path.join(sdk.path, 'lib', 'public', lib) + '.lib'
- elif compiler.target.arch == 'x86_64':
- lib_path = os.path.join(sdk.path, 'lib', 'public', 'win64', lib) + '.lib'
- compiler.linkflags.append(lib_path)
-
- for library in dynamic_libs:
- source_path = os.path.join(lib_folder, library)
- output_path = os.path.join(binary.localFolder, library)
-
- # Ensure the output path exists.
- context.AddFolder(binary.localFolder)
- output = context.AddSymlink(source_path, output_path)
-
- compiler.weaklinkdeps += [output]
- compiler.linkflags[0:0] = [library]
+ for other_sdk in self.sdk_manifests:
+ compiler.defines += ['SE_{}={}'.format(other_sdk['define'], other_sdk['code'])]
+
+ SdkHelpers.configureCxx(context, binary, sdk)
return binary
@@ -592,6 +424,28 @@ class ExtensionConfig(object):
binary.compiler.sourcedeps += Extension.generated_headers
return binary
+ def AddCDetour(self, binary):
+ binary.sources += [ os.path.join(self.sm_root, 'public', 'CDetour', 'detours.cpp') ]
+ binary.compiler.cxxincludes += [ os.path.join(builder.sourcePath, 'third_party', 'safetyhook', 'include') ]
+
+ for task in self.libsafetyhook:
+ if task.target.arch == binary.compiler.target.arch:
+ binary.compiler.linkflags += [task.binary]
+ return
+ raise Exception('No suitable build of safetyhook was found.')
+
+ def LibraryBuilder(self, compiler, name):
+ binary = compiler.Library(name)
+ self.AddVersioning(binary)
+ if binary.compiler.like('msvc'):
+ binary.compiler.linkflags += ['/SUBSYSTEM:WINDOWS']
+ return binary
+
+ def Library(self, context, compiler, name):
+ compiler = compiler.clone()
+ SetArchFlags(compiler)
+ return self.LibraryBuilder(compiler, name)
+
def HL2Library(self, context, compiler, name, sdk):
binary = self.Library(context, compiler, name)
self.ConfigureForExtension(context, binary.compiler)
@@ -599,13 +453,13 @@ class ExtensionConfig(object):
def HL2Config(self, project, context, compiler, name, sdk):
binary = project.Configure(compiler, name,
- '{0} - {1} {2}'.format(self.tag, sdk.name, compiler.target.arch))
+ '{0} - {1} {2}'.format(self.tag, sdk['name'], compiler.target.arch))
self.AddVersioning(binary)
return self.ConfigureForHL2(context, binary, sdk)
def HL2ExtConfig(self, project, context, compiler, name, sdk):
binary = project.Configure(compiler, name,
- '{0} - {1} {2}'.format(self.tag, sdk.name, compiler.target.arch))
+ '{0} - {1} {2}'.format(self.tag, sdk['name'], compiler.target.arch))
self.AddVersioning(binary)
self.ConfigureForHL2(context, binary, sdk)
self.ConfigureForExtension(context, binary.compiler)
@@ -617,6 +471,16 @@ if Extension.build_extension():
Extension.detectSDKs()
Extension.configure()
+class SafetyHookShim(object):
+ def __init__(self):
+ self.all_targets = {}
+ self.libsafetyhook = {}
+
+SafetyHook = SafetyHookShim()
+SafetyHook.all_targets = Extension.all_targets
+builder.Build(os.path.join('third_party/safetyhook/AMBuilder'), {'SafetyHook': SafetyHook })
+Extension.libsafetyhook = SafetyHook.libsafetyhook
+
if Extension.use_auto_versioning():
Extension.generated_headers = builder.Build(
'tools/Versioning',
@@ -635,4 +499,4 @@ if Extension.build_extension():
BuildScripts += ['PackageScript']
-builder.Build(BuildScripts, {'Extension': Extension})
+builder.Build(BuildScripts, {'Extension': Extension})
\ No newline at end of file
diff --git a/PackageScript b/PackageScript
index c192d46..680199c 100644
--- a/PackageScript
+++ b/PackageScript
@@ -9,6 +9,7 @@ builder.SetBuildFolder('package')
# Add any folders you need to this list
folder_list = [
'addons/sourcemod/extensions',
+ 'addons/sourcemod/extensions/x64',
'addons/sourcemod/scripting/include',
'addons/sourcemod/scripting/include/cbasenpc',
'addons/sourcemod/scripting/include/cbasenpc/tf',
@@ -39,7 +40,10 @@ def CopyDirContent(src, dest):
builder.AddCopy(item.path, dest_entry)
# Copy binaries.
for cxx_task in Extension.extensions:
- builder.AddCopy(cxx_task.binary, folder_map['addons/sourcemod/extensions'])
+ if cxx_task.target.arch == 'x86_64':
+ builder.AddCopy(cxx_task.binary, folder_map['addons/sourcemod/extensions/x64'])
+ else:
+ builder.AddCopy(cxx_task.binary, folder_map['addons/sourcemod/extensions'])
for smx_file in Extension.smx_files:
smx_entry = Extension.smx_files[smx_file]
builder.AddCopy(smx_entry, folder_map['addons/sourcemod/plugins/disabled'])
diff --git a/extension/AMBuilder b/extension/AMBuilder
index 25039d7..30bafde 100644
--- a/extension/AMBuilder
+++ b/extension/AMBuilder
@@ -12,8 +12,6 @@ project.sources = [
'pluginentityfactory.cpp',
'toolsnav_mesh.cpp',
'toolsnextbot.cpp',
- 'CDetour/detours.cpp',
- 'asm/asm.c',
'helpers.cpp',
'sourcesdk/NextBot/Path/NextBotPath.cpp',
'sourcesdk/NextBot/Path/NextBotPathFollow.cpp',
@@ -30,6 +28,7 @@ project.sources = [
'sourcesdk/nav_mesh.cpp',
'sourcesdk/entityfactorydictionary.cpp',
'sourcesdk/customfactory.cpp',
+ 'sourcesdk/studio.cpp',
'sourcesdk/baseentity.cpp',
'sourcesdk/baseentityoutput.cpp',
'sourcesdk/baseanimating.cpp',
@@ -69,29 +68,29 @@ project.sources = [
'natives/nextbotplayer.cpp',
'natives/tf/nav.cpp',
'natives/tf/nav/area.cpp',
- 'smsdk_ext.cpp'
+ os.path.join(Extension.sm_root, 'public/smsdk_ext.cpp')
]
for sdk_name in Extension.sdks:
sdk = Extension.sdks[sdk_name]
for cxx in builder.targets:
- if not cxx.target.arch in sdk.platformSpec[cxx.target.platform]:
+ if not cxx.target.arch in sdk['platforms'][cxx.target.platform]:
continue
-
- binary = Extension.HL2ExtConfig(project, builder, cxx, 'cbasenpc.ext.' + sdk.ext, sdk)
+ binary = Extension.HL2ExtConfig(project, builder, cxx, 'cbasenpc.ext.' + sdk['extension'], sdk)
+ Extension.AddCDetour(binary)
binary.compiler.cxxincludes += [
os.path.join(builder.currentSourcePath, 'sourcesdk'),
os.path.join(builder.currentSourcePath, 'sourcesdk/NextBot'),
os.path.join(builder.currentSourcePath, 'sourcesdk/NextBot/Path'),
os.path.join(builder.currentSourcePath, 'natives'),
os.path.join(builder.currentSourcePath, 'shared'),
- os.path.join(builder.currentSourcePath, ''),
- os.path.join(sdk.path, 'game', 'shared'),
- os.path.join(sdk.path, 'game', 'server')
+ os.path.join(builder.currentSourcePath),
+ os.path.join(sdk['path'], 'game', 'server')
]
+ binary.compiler.defines += ['RAD_TELEMETRY_DISABLED', 'HAVE_STRING_H']
if binary.compiler.behavior == 'gcc' or binary.compiler.behavior == 'clang':
binary.compiler.cxxflags += ['-Wno-invalid-offsetof']
binary.sources += ['linux/glibc_compat.cpp']
-Extension.extensions = builder.Add(project)
\ No newline at end of file
+Extension.extensions += builder.Add(project)
\ No newline at end of file
diff --git a/extension/CDetour/detourhelpers.h b/extension/CDetour/detourhelpers.h
deleted file mode 100644
index 954eb84..0000000
--- a/extension/CDetour/detourhelpers.h
+++ /dev/null
@@ -1,99 +0,0 @@
-/**
- * vim: set ts=4 :
- * =============================================================================
- * SourceMod
- * Copyright (C) 2004-2007 AlliedModders LLC. All rights reserved.
- * =============================================================================
- *
- * This program is free software; you can redistribute it and/or modify it under
- * the terms of the GNU General Public License, version 3.0, as published by the
- * Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
- * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
- * details.
- *
- * You should have received a copy of the GNU General Public License along with
- * this program. If not, see .
- *
- * As a special exception, AlliedModders LLC gives you permission to link the
- * code of this program (as well as its derivative works) to "Half-Life 2," the
- * "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software
- * by the Valve Corporation. You must obey the GNU General Public License in
- * all respects for all other code used. Additionally, AlliedModders LLC grants
- * this exception to all derivative works. AlliedModders LLC defines further
- * exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007),
- * or .
- *
- * Version: $Id: detourhelpers.h 248 2008-08-27 00:56:22Z pred $
- */
-
-#ifndef _INCLUDE_SOURCEMOD_DETOURHELPERS_H_
-#define _INCLUDE_SOURCEMOD_DETOURHELPERS_H_
-
-#if defined PLATFORM_LINUX
-#include
-#define PAGE_SIZE 4096
-#define ALIGN(ar) ((long)ar & ~(PAGE_SIZE-1))
-#define PAGE_EXECUTE_READWRITE PROT_READ|PROT_WRITE|PROT_EXEC
-#endif
-
-struct patch_t
-{
- patch_t()
- {
- patch[0] = 0;
- bytes = 0;
- }
- unsigned char patch[20];
- size_t bytes;
-};
-
-inline void ProtectMemory(void *addr, int length, int prot)
-{
-#if defined PLATFORM_LINUX
- void *addr2 = (void *)ALIGN(addr);
- mprotect(addr2, sysconf(_SC_PAGESIZE), prot);
-#elif defined PLATFORM_WINDOWS
- DWORD old_prot;
- VirtualProtect(addr, length, prot, &old_prot);
-#endif
-}
-
-inline void SetMemPatchable(void *address, size_t size)
-{
- ProtectMemory(address, (int)size, PAGE_EXECUTE_READWRITE);
-}
-
-inline void DoGatePatch(unsigned char *target, void *callback)
-{
- SetMemPatchable(target, 20);
-
- target[0] = 0xFF; /* JMP */
- target[1] = 0x25; /* MEM32 */
- *(void **)(&target[2]) = callback;
-}
-
-inline void ApplyPatch(void *address, int offset, const patch_t *patch, patch_t *restore)
-{
- ProtectMemory(address, 20, PAGE_EXECUTE_READWRITE);
-
- unsigned char *addr = (unsigned char *)address + offset;
- if (restore)
- {
- for (size_t i=0; ibytes; i++)
- {
- restore->patch[i] = addr[i];
- }
- restore->bytes = patch->bytes;
- }
-
- for (size_t i=0; ibytes; i++)
- {
- //g_pSM->LogMessage(myself, "Patching %02X with %02X..", addr[i], patch->patch[i]);
- addr[i] = patch->patch[i];
- }
-}
-
-#endif //_INCLUDE_SOURCEMOD_DETOURHELPERS_H_
diff --git a/extension/CDetour/detours.cpp b/extension/CDetour/detours.cpp
deleted file mode 100644
index b4f6cc6..0000000
--- a/extension/CDetour/detours.cpp
+++ /dev/null
@@ -1,192 +0,0 @@
-/**
-* vim: set ts=4 :
-* =============================================================================
-* SourceMod
-* Copyright (C) 2004-2008 AlliedModders LLC. All rights reserved.
-* =============================================================================
-*
-* This program is free software; you can redistribute it and/or modify it under
-* the terms of the GNU General Public License, version 3.0, as published by the
-* Free Software Foundation.
-*
-* This program is distributed in the hope that it will be useful, but WITHOUT
-* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
-* FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
-* details.
-*
-* You should have received a copy of the GNU General Public License along with
-* this program. If not, see .
-*
-* As a special exception, AlliedModders LLC gives you permission to link the
-* code of this program (as well as its derivative works) to "Half-Life 2," the
-* "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software
-* by the Valve Corporation. You must obey the GNU General Public License in
-* all respects for all other code used. Additionally, AlliedModders LLC grants
-* this exception to all derivative works. AlliedModders LLC defines further
-* exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007),
-* or .
-*
-* Version: $Id: detours.cpp 248 2008-08-27 00:56:22Z pred $
-*/
-
-#include "detours.h"
-#include
-
-ISourcePawnEngine *CDetourManager::spengine = NULL;
-IGameConfig *CDetourManager::gameconf = NULL;
-
-void CDetourManager::Init(ISourcePawnEngine *spengine, IGameConfig *gameconf)
-{
- CDetourManager::spengine = spengine;
- CDetourManager::gameconf = gameconf;
-}
-
-CDetour *CDetourManager::CreateDetour(void *callbackfunction, void **trampoline, const char *signame)
-{
- CDetour *detour = new CDetour(callbackfunction, trampoline, signame);
- if (detour)
- {
- if (!detour->Init(spengine, gameconf))
- {
- delete detour;
- return NULL;
- }
-
- return detour;
- }
-
- return NULL;
-}
-
-CDetour::CDetour(void *callbackfunction, void **trampoline, const char *signame)
-{
- enabled = false;
- detoured = false;
- detour_address = NULL;
- detour_trampoline = NULL;
- this->signame = signame;
- this->detour_callback = callbackfunction;
- spengine = NULL;
- gameconf = NULL;
- this->trampoline = trampoline;
-}
-
-bool CDetour::Init(ISourcePawnEngine *spengine, IGameConfig *gameconf)
-{
- this->spengine = spengine;
- this->gameconf = gameconf;
-
- if (!CreateDetour())
- {
- enabled = false;
- return enabled;
- }
-
- enabled = true;
-
- return enabled;
-}
-
-void CDetour::Destroy()
-{
- DeleteDetour();
- delete this;
-}
-
-bool CDetour::IsEnabled()
-{
- return enabled;
-}
-
-bool CDetour::CreateDetour()
-{
- if (!gameconf->GetMemSig(signame, &detour_address))
- {
- g_pSM->LogError(myself, "Could not locate %s - Disabling detour", signame);
- return false;
- }
-
- if (!detour_address)
- {
- g_pSM->LogError(myself, "Sigscan for %s failed - Disabling detour to prevent crashes", signame);
- return false;
- }
-
- detour_restore.bytes = copy_bytes((unsigned char *)detour_address, NULL, OP_JMP_SIZE+1);
-
- /* First, save restore bits */
- for (size_t i=0; iAllocatePageMemory(CodeSize);
- spengine->SetReadWrite(wr.outbase);
- wr.outptr = wr.outbase;
- detour_trampoline = wr.outbase;
- goto jit_rewind;
- }
-
- spengine->SetReadExecute(wr.outbase);
-
- *trampoline = detour_trampoline;
-
- return true;
-}
-
-void CDetour::DeleteDetour()
-{
- if (detoured)
- {
- DisableDetour();
- }
-
- if (detour_trampoline)
- {
- /* Free the allocated trampoline memory */
- spengine->FreePageMemory(detour_trampoline);
- detour_trampoline = NULL;
- }
-}
-
-void CDetour::EnableDetour()
-{
- if (!detoured)
- {
- DoGatePatch((unsigned char *)detour_address, &detour_callback);
- detoured = true;
- }
-}
-
-void CDetour::DisableDetour()
-{
- if (detoured)
- {
- /* Remove the patch */
- ApplyPatch(detour_address, 0, &detour_restore, NULL);
- detoured = false;
- }
-}
diff --git a/extension/CDetour/detours.h b/extension/CDetour/detours.h
deleted file mode 100644
index 1e81395..0000000
--- a/extension/CDetour/detours.h
+++ /dev/null
@@ -1,249 +0,0 @@
-/**
-* vim: set ts=4 :
-* =============================================================================
-* SourceMod
-* Copyright (C) 2004-2008 AlliedModders LLC. All rights reserved.
-* =============================================================================
-*
-* This program is free software; you can redistribute it and/or modify it under
-* the terms of the GNU General Public License, version 3.0, as published by the
-* Free Software Foundation.
-*
-* This program is distributed in the hope that it will be useful, but WITHOUT
-* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
-* FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
-* details.
-*
-* You should have received a copy of the GNU General Public License along with
-* this program. If not, see .
-*
-* As a special exception, AlliedModders LLC gives you permission to link the
-* code of this program (as well as its derivative works) to "Half-Life 2," the
-* "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software
-* by the Valve Corporation. You must obey the GNU General Public License in
-* all respects for all other code used. Additionally, AlliedModders LLC grants
-* this exception to all derivative works. AlliedModders LLC defines further
-* exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007),
-* or .
-*
-* Version: $Id: detours.h 257 2008-09-23 03:12:13Z pred $
-*/
-
-#ifndef _INCLUDE_SOURCEMOD_DETOURS_H_
-#define _INCLUDE_SOURCEMOD_DETOURS_H_
-
-#include "extension.h"
-#include
-#include
-#include "detourhelpers.h"
-
-/**
- * CDetours class for SourceMod Extensions by pRED*
- * detourhelpers.h entirely stolen from CSS:DM and were written by BAILOPAN (I assume).
- * asm.h/c from devmaster.net (thanks cybermind) edited by pRED* to handle gcc -fPIC thunks correctly
- * Concept by Nephyrin Zey (http://www.doublezen.net/) and Windows Detour Library (http://research.microsoft.com/sn/detours/)
- * Member function pointer ideas by Don Clugston (http://www.codeproject.com/cpp/FastDelegate.asp)
- */
-
-#define DETOUR_MEMBER_CALL(name) (this->*name##_Actual)
-#define DETOUR_STATIC_CALL(name) (name##_Actual)
-
-#define DETOUR_DECL_STATIC0(name, ret) \
-ret (*name##_Actual)(void) = NULL; \
-ret name(void)
-
-#define DETOUR_DECL_STATIC1(name, ret, p1type, p1name) \
-ret (*name##_Actual)(p1type) = NULL; \
-ret name(p1type p1name)
-
-#define DETOUR_DECL_STATIC2(name, ret, p1type, p1name, p2type, p2name) \
-ret (*name##_Actual)(p1type, p2type) = NULL; \
-ret name(p1type p1name, p2type p2name)
-
-#define DETOUR_DECL_STATIC4(name, ret, p1type, p1name, p2type, p2name, p3type, p3name, p4type, p4name) \
-ret (*name##_Actual)(p1type, p2type, p3type, p4type) = NULL; \
-ret name(p1type p1name, p2type p2name, p3type p3name, p4type p4name)
-
-#define DETOUR_DECL_STATIC5(name, ret, p1type, p1name, p2type, p2name, p3type, p3name, p4type, p4name, p5type, p5name) \
-ret (*name##_Actual)(p1type, p2type, p3type, p4type, p5type) = NULL; \
-ret name(p1type p1name, p2type p2name, p3type p3name, p4type p4name, p5type p5name)
-
-#define DETOUR_DECL_MEMBER0(name, ret) \
-class name##Class \
-{ \
-public: \
- ret name(); \
- static ret (name##Class::* name##_Actual)(void); \
-}; \
-ret (name##Class::* name##Class::name##_Actual)(void) = NULL; \
-ret name##Class::name()
-
-#define DETOUR_DECL_MEMBER1(name, ret, p1type, p1name) \
-class name##Class \
-{ \
-public: \
- ret name(p1type p1name); \
- static ret (name##Class::* name##_Actual)(p1type); \
-}; \
-ret (name##Class::* name##Class::name##_Actual)(p1type) = NULL; \
-ret name##Class::name(p1type p1name)
-
-#define DETOUR_DECL_MEMBER2(name, ret, p1type, p1name, p2type, p2name) \
-class name##Class \
-{ \
-public: \
- ret name(p1type p1name, p2type p2name); \
- static ret (name##Class::* name##_Actual)(p1type, p2type); \
-}; \
-ret (name##Class::* name##Class::name##_Actual)(p1type, p2type) = NULL; \
-ret name##Class::name(p1type p1name, p2type p2name)
-
-#define DETOUR_DECL_MEMBER3(name, ret, p1type, p1name, p2type, p2name, p3type, p3name) \
-class name##Class \
-{ \
-public: \
- ret name(p1type p1name, p2type p2name, p3type p3name); \
- static ret (name##Class::* name##_Actual)(p1type, p2type, p3type); \
-}; \
-ret (name##Class::* name##Class::name##_Actual)(p1type, p2type, p3type) = NULL; \
-ret name##Class::name(p1type p1name, p2type p2name, p3type p3name)
-
-#define DETOUR_DECL_MEMBER4(name, ret, p1type, p1name, p2type, p2name, p3type, p3name, p4type, p4name) \
-class name##Class \
-{ \
-public: \
- ret name(p1type p1name, p2type p2name, p3type p3name, p4type p4name); \
- static ret (name##Class::* name##_Actual)(p1type, p2type, p3type, p4type); \
-}; \
-ret (name##Class::* name##Class::name##_Actual)(p1type, p2type, p3type, p4type) = NULL; \
-ret name##Class::name(p1type p1name, p2type p2name, p3type p3name, p4type p4name)
-
-
-#define GET_MEMBER_CALLBACK(name) (void *)GetCodeAddress(&name##Class::name)
-#define GET_MEMBER_TRAMPOLINE(name) (void **)(&name##Class::name##_Actual)
-
-#define GET_STATIC_CALLBACK(name) (void *)&name
-#define GET_STATIC_TRAMPOLINE(name) (void **)&name##_Actual
-
-#define DETOUR_CREATE_MEMBER(name, gamedata) CDetourManager::CreateDetour(GET_MEMBER_CALLBACK(name), GET_MEMBER_TRAMPOLINE(name), gamedata);
-#define DETOUR_CREATE_STATIC(name, gamedata) CDetourManager::CreateDetour(GET_STATIC_CALLBACK(name), GET_STATIC_TRAMPOLINE(name), gamedata);
-
-
-class GenericClass {};
-typedef void (GenericClass::*VoidFunc)();
-
-inline void *GetCodeAddr(VoidFunc mfp)
-{
- return *(void **)&mfp;
-}
-
-/**
- * Converts a member function pointer to a void pointer.
- * This relies on the assumption that the code address lies at mfp+0
- * This is the case for both g++ and later MSVC versions on non virtual functions but may be different for other compilers
- * Based on research by Don Clugston : http://www.codeproject.com/cpp/FastDelegate.asp
- */
-#define GetCodeAddress(mfp) GetCodeAddr(reinterpret_cast(mfp))
-
-class CDetourManager;
-
-class CDetour
-{
-public:
-
- bool IsEnabled();
-
- /**
- * These would be somewhat self-explanatory I hope
- */
- void EnableDetour();
- void DisableDetour();
-
- void Destroy();
-
- friend class CDetourManager;
-
-protected:
- CDetour(void *callbackfunction, void **trampoline, const char *signame);
-
- bool Init(ISourcePawnEngine *spengine, IGameConfig *gameconf);
-private:
-
- /* These create/delete the allocated memory */
- bool CreateDetour();
- void DeleteDetour();
-
- bool enabled;
- bool detoured;
-
- patch_t detour_restore;
- /* Address of the detoured function */
- void *detour_address;
- /* Address of the allocated trampoline function */
- void *detour_trampoline;
- /* Address of the callback handler */
- void *detour_callback;
- /* The function pointer used to call our trampoline */
- void **trampoline;
-
- const char *signame;
- ISourcePawnEngine *spengine;
- IGameConfig *gameconf;
-};
-
-class CDetourManager
-{
-public:
-
- static void Init(ISourcePawnEngine *spengine, IGameConfig *gameconf);
-
- /**
- * Creates a new detour
- *
- * @param callbackfunction Void pointer to your detour callback function.
- * @param trampoline Address of the trampoline pointer
- * @param signame Section name containing a signature to fetch from the gamedata file.
- * @return A new CDetour pointer to control your detour.
- *
- * Example:
- *
- * CBaseServer::ConnectClient(netadr_s &, int, int, int, char const*, char const*, char const*, int)
- *
- * Define a new class with the required function and a member function pointer to the same type:
- *
- * class CBaseServerDetour
- * {
- * public:
- * bool ConnectClient(void *netaddr_s, int, int, int, char const*, char const*, char const*, int);
- * static bool (CBaseServerDetour::* ConnectClient_Actual)(void *netaddr_s, int, int, int, char const*, char const*, char const*, int);
- * }
- *
- * void *callbackfunc = GetCodeAddress(&CBaseServerDetour::ConnectClient);
- * void **trampoline = (void **)(&CBaseServerDetour::ConnectClient_Actual);
- *
- * Creation:
- * CDetourManager::CreateDetour(callbackfunc, trampoline, "ConnectClient");
- *
- * Usage:
- *
- * CBaseServerDetour::ConnectClient(void *netaddr_s, int, int, int, char const*, char const*, char const*, int)
- * {
- * //pre hook code
- * bool result = (this->*ConnectClient_Actual)(netaddr_s, rest of params);
- * //post hook code
- * return result;
- * }
- *
- * Note we changed the netadr_s reference into a void* to avoid needing to define the type
- */
- static CDetour *CreateDetour(void *callbackfunction, void **trampoline, const char *signame);
-
- friend class CBlocker;
- friend class CDetour;
-
-private:
- static ISourcePawnEngine *spengine;
- static IGameConfig *gameconf;
-};
-
-#endif // _INCLUDE_SOURCEMOD_DETOURS_H_
diff --git a/extension/asm/asm.c b/extension/asm/asm.c
deleted file mode 100644
index dc548a9..0000000
--- a/extension/asm/asm.c
+++ /dev/null
@@ -1,420 +0,0 @@
-#include "asm.h"
-
-#ifndef WIN32
-#define _GNU_SOURCE
-#include
-#include
-#include
-#include
-
-#define REG_EAX 0
-#define REG_ECX 1
-#define REG_EDX 2
-#define REG_EBX 3
-
-#define IA32_MOV_REG_IMM 0xB8 // encoding is +r
-#endif
-
-/**
-* Checks if a call to a fpic thunk has just been written into dest.
-* If found replaces it with a direct mov that sets the required register to the value of pc.
-*
-* @param dest Destination buffer where a call opcode + addr (5 bytes) has just been written.
-* @param pc The program counter value that needs to be set (usually the next address from the source).
-* @noreturn
-*/
-void check_thunks(unsigned char *dest, unsigned char *pc)
-{
-#ifndef WIN32
- /* Step write address back 4 to the start of the function address */
- unsigned char *writeaddr = dest - 4;
- unsigned char *calloffset = *(unsigned char **)writeaddr;
- unsigned char *calladdr = (unsigned char *)(dest + (unsigned int)calloffset);
-
- /* Lookup name of function being called */
- if ((*calladdr == 0x8B) && (*(calladdr+2) == 0x24) && (*(calladdr+3) == 0xC3))
- {
- //a thunk maybe?
- char movByte = IA32_MOV_REG_IMM;
-
- /* Calculate the correct mov opcode */
- switch (*(calladdr+1))
- {
- case 0x04:
- {
- movByte += REG_EAX;
- break;
- }
- case 0x1C:
- {
- movByte += REG_EBX;
- break;
- }
- case 0x0C:
- {
- movByte += REG_ECX;
- break;
- }
- case 0x14:
- {
- movByte += REG_EDX;
- break;
- }
- default:
- {
- printf("Unknown thunk: %c\n", *(calladdr+1));
-#ifndef NDEBUG
- abort();
-#endif
- break;
- }
- }
-
- /* Move our write address back one to where the call opcode was */
- writeaddr--;
-
-
- /* Write our mov */
- *writeaddr = movByte;
- writeaddr++;
-
- /* Write the value - The provided program counter value */
- *(void **)writeaddr = (void *)pc;
- writeaddr += 4;
- }
-#endif
-}
-
-//if dest is NULL, returns minimum number of bytes needed to be copied
-//if dest is not NULL, it will copy the bytes to dest as well as fix CALLs and JMPs
-//http://www.devmaster.net/forums/showthread.php?t=2311
-int copy_bytes(unsigned char *func, unsigned char* dest, int required_len) {
- int bytecount = 0;
-
- while(bytecount < required_len && *func != 0xCC)
- {
- // prefixes F0h, F2h, F3h, 66h, 67h, D8h-DFh, 2Eh, 36h, 3Eh, 26h, 64h and 65h
- int operandSize = 4;
- int FPU = 0;
- int twoByte = 0;
- unsigned char opcode = 0x90;
- unsigned char modRM = 0xFF;
- while(*func == 0xF0 ||
- *func == 0xF2 ||
- *func == 0xF3 ||
- (*func & 0xFC) == 0x64 ||
- (*func & 0xF8) == 0xD8 ||
- (*func & 0x7E) == 0x62)
- {
- if(*func == 0x66)
- {
- operandSize = 2;
- }
- else if((*func & 0xF8) == 0xD8)
- {
- FPU = *func;
- if (dest)
- *dest++ = *func++;
- else
- func++;
- bytecount++;
- break;
- }
-
- if (dest)
- *dest++ = *func++;
- else
- func++;
- bytecount++;
- }
-
- // two-byte opcode byte
- if(*func == 0x0F)
- {
- twoByte = 1;
- if (dest)
- *dest++ = *func++;
- else
- func++;
- bytecount++;
- }
-
- // opcode byte
- opcode = *func++;
- if (dest) *dest++ = opcode;
- bytecount++;
-
- // mod R/M byte
- modRM = 0xFF;
- if(FPU)
- {
- if((opcode & 0xC0) != 0xC0)
- {
- modRM = opcode;
- }
- }
- else if(!twoByte)
- {
- if((opcode & 0xC4) == 0x00 ||
- ((opcode & 0xF4) == 0x60 && ((opcode & 0x0A) == 0x02 || (opcode & 0x09) == 0x09)) ||
- (opcode & 0xF0) == 0x80 ||
- ((opcode & 0xF8) == 0xC0 && (opcode & 0x0E) != 0x02) ||
- (opcode & 0xFC) == 0xD0 ||
- (opcode & 0xF6) == 0xF6)
- {
- modRM = *func++;
- if (dest) *dest++ = modRM;
- bytecount++;
- }
- }
- else
- {
- if(((opcode & 0xF0) == 0x00 && (opcode & 0x0F) >= 0x04 && (opcode & 0x0D) != 0x0D) ||
- (opcode & 0xF0) == 0x30 ||
- opcode == 0x77 ||
- (opcode & 0xF0) == 0x80 ||
- ((opcode & 0xF0) == 0xA0 && (opcode & 0x07) <= 0x02) ||
- (opcode & 0xF8) == 0xC8)
- {
- // No mod R/M byte
- }
- else
- {
- modRM = *func++;
- if (dest) *dest++ = modRM;
- bytecount++;
- }
- }
-
- // SIB
- if((modRM & 0x07) == 0x04 &&
- (modRM & 0xC0) != 0xC0)
- {
- if (dest)
- *dest++ = *func++; //SIB
- else
- func++;
- bytecount++;
- }
-
- // mod R/M displacement
-
- // Dword displacement, no base
- if((modRM & 0xC5) == 0x05) {
- if (dest) {
- *(unsigned int*)dest = *(unsigned int*)func;
- dest += 4;
- }
- func += 4;
- bytecount += 4;
- }
-
- // Byte displacement
- if((modRM & 0xC0) == 0x40) {
- if (dest)
- *dest++ = *func++;
- else
- func++;
- bytecount++;
- }
-
- // Dword displacement
- if((modRM & 0xC0) == 0x80) {
- if (dest) {
- *(unsigned int*)dest = *(unsigned int*)func;
- dest += 4;
- }
- func += 4;
- bytecount += 4;
- }
-
- // immediate
- if(FPU)
- {
- // Can't have immediate operand
- }
- else if(!twoByte)
- {
- if((opcode & 0xC7) == 0x04 ||
- (opcode & 0xFE) == 0x6A || // PUSH/POP/IMUL
- (opcode & 0xF0) == 0x70 || // Jcc
- opcode == 0x80 ||
- opcode == 0x83 ||
- (opcode & 0xFD) == 0xA0 || // MOV
- opcode == 0xA8 || // TEST
- (opcode & 0xF8) == 0xB0 || // MOV
- (opcode & 0xFE) == 0xC0 || // RCL
- opcode == 0xC6 || // MOV
- opcode == 0xCD || // INT
- (opcode & 0xFE) == 0xD4 || // AAD/AAM
- (opcode & 0xF8) == 0xE0 || // LOOP/JCXZ
- opcode == 0xEB ||
- (opcode == 0xF6 && (modRM & 0x30) == 0x00)) // TEST
- {
- if (dest)
- *dest++ = *func++;
- else
- func++;
- bytecount++;
- }
- else if((opcode & 0xF7) == 0xC2) // RET
- {
- if (dest) {
- *(unsigned short*)dest = *(unsigned short*)func;
- dest += 2;
- }
- func += 2;
- bytecount += 2;
- }
- else if((opcode & 0xFC) == 0x80 ||
- (opcode & 0xC7) == 0x05 ||
- (opcode & 0xF8) == 0xB8 ||
- (opcode & 0xFE) == 0xE8 || // CALL/Jcc
- (opcode & 0xFE) == 0x68 ||
- (opcode & 0xFC) == 0xA0 ||
- (opcode & 0xEE) == 0xA8 ||
- opcode == 0xC7 ||
- (opcode == 0xF7 && (modRM & 0x30) == 0x00))
- {
- if (dest) {
- //Fix CALL/JMP offset
- if ((opcode & 0xFE) == 0xE8) {
- if (operandSize == 4)
- {
- *(long*)dest = ((func + *(long*)func) - dest);
-
- //pRED* edit. func is the current address of the call address, +4 is the next instruction, so the value of $pc
- check_thunks(dest+4, func+4);
- }
- else
- *(short*)dest = ((func + *(short*)func) - dest);
-
- } else {
- if (operandSize == 4)
- *(unsigned long*)dest = *(unsigned long*)func;
- else
- *(unsigned short*)dest = *(unsigned short*)func;
- }
- dest += operandSize;
- }
- func += operandSize;
- bytecount += operandSize;
-
- }
- }
- else
- {
- if(opcode == 0xBA || // BT
- opcode == 0x0F || // 3DNow!
- (opcode & 0xFC) == 0x70 || // PSLLW
- (opcode & 0xF7) == 0xA4 || // SHLD
- opcode == 0xC2 ||
- opcode == 0xC4 ||
- opcode == 0xC5 ||
- opcode == 0xC6)
- {
- if (dest)
- *dest++ = *func++;
- else
- func++;
- }
- else if((opcode & 0xF0) == 0x80) // Jcc -i
- {
- if (dest) {
- if (operandSize == 4)
- *(unsigned long*)dest = *(unsigned long*)func;
- else
- *(unsigned short*)dest = *(unsigned short*)func;
-
- dest += operandSize;
- }
- func += operandSize;
- bytecount += operandSize;
- }
- }
- }
-
- return bytecount;
-}
-
-//insert a specific JMP instruction at the given location
-void inject_jmp(void* src, void* dest) {
- *(unsigned char*)src = OP_JMP;
- *(long*)((unsigned char*)src+1) = (long)((unsigned char*)dest - ((unsigned char*)src + OP_JMP_SIZE));
-}
-
-//fill a given block with NOPs
-void fill_nop(void* src, unsigned int len) {
- unsigned char* src2 = (unsigned char*)src;
- while (len) {
- *src2++ = OP_NOP;
- --len;
- }
-}
-
-void* eval_jump(void* src) {
- unsigned char* addr = (unsigned char*)src;
-
- if (!addr) return 0;
-
- //import table jump
- if (addr[0] == OP_PREFIX && addr[1] == OP_JMP_SEG) {
- addr += 2;
- addr = *(unsigned char**)addr;
- //TODO: if addr points into the IAT
- return *(void**)addr;
- }
-
- //8bit offset
- else if (addr[0] == OP_JMP_BYTE) {
- addr = &addr[OP_JMP_BYTE_SIZE] + *(char*)&addr[1];
- //mangled 32bit jump?
- if (addr[0] == OP_JMP) {
- addr = addr + *(int*)&addr[1];
- }
- return addr;
- }
- /*
- //32bit offset
- else if (addr[0] == OP_JMP) {
- addr = &addr[OP_JMP_SIZE] + *(int*)&addr[1];
- }
- */
-
- return addr;
-}
-/*
-from ms detours package
-static bool detour_is_imported(PBYTE pbCode, PBYTE pbAddress)
-{
- MEMORY_BASIC_INFORMATION mbi;
- VirtualQuery((PVOID)pbCode, &mbi, sizeof(mbi));
- __try {
- PIMAGE_DOS_HEADER pDosHeader = (PIMAGE_DOS_HEADER)mbi.AllocationBase;
- if (pDosHeader->e_magic != IMAGE_DOS_SIGNATURE) {
- return false;
- }
-
- PIMAGE_NT_HEADERS pNtHeader = (PIMAGE_NT_HEADERS)((PBYTE)pDosHeader +
- pDosHeader->e_lfanew);
- if (pNtHeader->Signature != IMAGE_NT_SIGNATURE) {
- return false;
- }
-
- if (pbAddress >= ((PBYTE)pDosHeader +
- pNtHeader->OptionalHeader
- .DataDirectory[IMAGE_DIRECTORY_ENTRY_IAT].VirtualAddress) &&
- pbAddress < ((PBYTE)pDosHeader +
- pNtHeader->OptionalHeader
- .DataDirectory[IMAGE_DIRECTORY_ENTRY_IAT].VirtualAddress +
- pNtHeader->OptionalHeader
- .DataDirectory[IMAGE_DIRECTORY_ENTRY_IAT].Size)) {
- return true;
- }
- return false;
- }
- __except(EXCEPTION_EXECUTE_HANDLER) {
- return false;
- }
-}
-*/
diff --git a/extension/asm/asm.h b/extension/asm/asm.h
deleted file mode 100644
index 838e691..0000000
--- a/extension/asm/asm.h
+++ /dev/null
@@ -1,40 +0,0 @@
-#ifndef __ASM_H__
-#define __ASM_H__
-
-#define OP_JMP 0xE9
-#define OP_JMP_SIZE 5
-
-#define OP_NOP 0x90
-#define OP_NOP_SIZE 1
-
-#define OP_PREFIX 0xFF
-#define OP_JMP_SEG 0x25
-
-#define OP_JMP_BYTE 0xEB
-#define OP_JMP_BYTE_SIZE 2
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-void check_thunks(unsigned char *dest, unsigned char *pc);
-
-//if dest is NULL, returns minimum number of bytes needed to be copied
-//if dest is not NULL, it will copy the bytes to dest as well as fix CALLs and JMPs
-//http://www.devmaster.net/forums/showthread.php?t=2311
-int copy_bytes(unsigned char *func, unsigned char* dest, int required_len);
-
-//insert a specific JMP instruction at the given location
-void inject_jmp(void* src, void* dest);
-
-//fill a given block with NOPs
-void fill_nop(void* src, unsigned int len);
-
-//evaluate a JMP at the target
-void* eval_jump(void* src);
-
-#ifdef __cplusplus
-}
-#endif
-
-#endif //__ASM_H__
diff --git a/extension/cbasenpc_behavior.cpp b/extension/cbasenpc_behavior.cpp
index d2073ba..e409a34 100644
--- a/extension/cbasenpc_behavior.cpp
+++ b/extension/cbasenpc_behavior.cpp
@@ -2,6 +2,8 @@
#include "cbasenpc_behavior.h"
#include
+#define CBPUSHPTR(ptr) Handle_t hndl_##ptr = PtrToPawnAddress(ptr, nullptr); pCallback->PushCell(hndl_##ptr);
+#define CBRELPTR(ptr) ReleasePawnAddress(hndl_##ptr, nullptr);
#define CBPUSHCELL(cell) pCallback->PushCell((cell_t)(cell));
#define CBPUSHFLOAT(fl) pCallback->PushCell(sp_ftoc(fl));
#define CBPUSHENTITY(ent) CBPUSHCELL(gamehelpers->EntityToBCompatRef(ent))
@@ -19,12 +21,16 @@ ActionResult< INextBot > CBaseNPCPluginAction:: funcName (INextBot* me, ##__VA_A
ResetPluginActionResult(); \
IPluginFunction* pCallback = m_pFactory->GetCallback( CBaseNPCPluginActionFactory::CallbackType::typeName ); \
if (pCallback && pCallback->IsRunnable()) { \
- pCallback->PushCell(PtrToPawnAddress(this)); pCallback->PushCell(gamehelpers->EntityToBCompatRef(me->GetEntity()));
+ Handle_t hndlThis = PtrToPawnAddress((void*)this, nullptr); \
+ pCallback->PushCell(hndlThis); pCallback->PushCell(gamehelpers->EntityToBCompatRef(me->GetEntity()));
#define BEGINACTIONCALLBACK(funcName, ...) BEGINACTIONCALLBACKEX(funcName, funcName, ##__VA_ARGS__)
+#define EXECUTEACTIONCALLBACK() \
+ pCallback->Execute(nullptr);
+
#define ENDACTIONCALLBACK() \
- pCallback->Execute(nullptr); \
+ ReleasePawnAddress(hndlThis, nullptr); \
} \
m_bInActionCallback = false; \
return m_pluginActionResult; \
@@ -35,10 +41,16 @@ QueryResultType CBaseNPCPluginAction:: funcName ( const INextBot *me, ##__VA_ARG
cell_t result = ANSWER_UNDEFINED; \
IPluginFunction* pCallback = m_pFactory->GetQueryCallback( CBaseNPCPluginActionFactory::QueryCallbackType::funcName ); \
if (pCallback && pCallback->IsRunnable()) { \
- CBPUSHCELL(PtrToPawnAddress(this)); CBPUSHCELL(PtrToPawnAddress(me));
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr); \
+ Handle_t hndlMe = PtrToPawnAddress(me, nullptr); \
+ CBPUSHCELL(hndlThis); CBPUSHCELL(hndlMe);
+
+#define EXECUTEQUERYCALLBACK() \
+ pCallback->Execute(&result);
#define ENDQUERYCALLBACK() \
- pCallback->Execute(&result); \
+ ReleasePawnAddress(hndlThis, nullptr); \
+ ReleasePawnAddress(hndlMe, nullptr); \
} \
return (QueryResultType)result; \
}
@@ -49,19 +61,25 @@ EventDesiredResult< INextBot > CBaseNPCPluginAction:: funcName (INextBot* me, ##
ResetPluginEventResult(); \
IPluginFunction* pCallback = m_pFactory->GetEventCallback( CBaseNPCPluginActionFactory::EventResponderCallbackType::typeName ); \
if (pCallback && pCallback->IsRunnable()) { \
- pCallback->PushCell(PtrToPawnAddress(this)); \
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr); \
+ pCallback->PushCell(hndlThis); \
pCallback->PushCell(gamehelpers->EntityToBCompatRef(me->GetEntity()));
#define BEGINEVENTCALLBACK(funcName, ...) BEGINEVENTCALLBACKEX(funcName, funcName, ##__VA_ARGS__)
+#define EVENTPUSHPTR(cell) CBPUSHPTR(cell)
+#define EVENTRELPTR(cell) CBRELPTR(cell)
#define EVENTPUSHCELL(cell) CBPUSHCELL(cell)
#define EVENTPUSHFLOAT(fl) CBPUSHFLOAT(fl)
#define EVENTPUSHENTITY(ent) CBPUSHENTITY(ent)
#define EVENTPUSHSTRING(str) CBPUSHSTRING(str)
#define EVENTPUSHVECTOR(vec) CBPUSHVECTOR(vec)
+#define EXECUTEEVENTCALLBACK() \
+ pCallback->Execute(nullptr);
+
#define ENDEVENTCALLBACK() \
- pCallback->Execute(nullptr); \
+ ReleasePawnAddress(hndlThis, nullptr); \
} \
m_inEventCallback--; \
return m_pluginEventResult; \
@@ -185,28 +203,37 @@ void CBaseNPCPluginAction::PluginTryToSustain( EventResultPriorityType priority,
// Actions
BEGINACTIONCALLBACK(OnStart, Action< INextBot > *prevAction)
- CBPUSHCELL(PtrToPawnAddress(prevAction))
+ CBPUSHPTR(prevAction)
+ EXECUTEACTIONCALLBACK()
+ CBRELPTR(prevAction)
ENDACTIONCALLBACK()
BEGINACTIONCALLBACK(Update, float interval)
CBPUSHFLOAT(interval)
+ EXECUTEACTIONCALLBACK()
ENDACTIONCALLBACK()
BEGINACTIONCALLBACK(OnSuspend, Action< INextBot > *interruptingAction)
- CBPUSHCELL(PtrToPawnAddress(interruptingAction))
+ CBPUSHPTR(interruptingAction)
+ EXECUTEACTIONCALLBACK()
+ CBRELPTR(interruptingAction)
ENDACTIONCALLBACK()
BEGINACTIONCALLBACK(OnResume, Action< INextBot > *interruptingAction)
- CBPUSHCELL(PtrToPawnAddress(interruptingAction))
+ CBPUSHPTR(interruptingAction)
+ EXECUTEACTIONCALLBACK()
+ CBRELPTR(interruptingAction)
ENDACTIONCALLBACK()
void CBaseNPCPluginAction::OnEnd( INextBot * me, Action< INextBot > *nextAction ) {
IPluginFunction* pCallback = m_pFactory->GetCallback( CBaseNPCPluginActionFactory::CallbackType::OnEnd );
if (pCallback && pCallback->IsRunnable()) {
- CBPUSHCELL(PtrToPawnAddress(this))
+ CBPUSHPTR(this)
CBPUSHENTITY(me->GetEntity())
- CBPUSHCELL(PtrToPawnAddress(nextAction))
+ CBPUSHPTR(nextAction)
pCallback->Execute(nullptr);
+ CBRELPTR(this)
+ CBRELPTR(nextAction)
}
}
@@ -217,13 +244,14 @@ Action< INextBot >* CBaseNPCPluginAction::InitialContainedAction( INextBot * me
IPluginFunction* pCallback = m_pFactory->GetCallback( CBaseNPCPluginActionFactory::CallbackType::InitialContainedAction );
if (pCallback && pCallback->IsRunnable())
{
- CBPUSHCELL(PtrToPawnAddress(this))
+ CBPUSHPTR(this)
CBPUSHENTITY(me->GetEntity())
pCallback->Execute(&result);
+ CBRELPTR(this)
}
- return (Action< INextBot >*)PawnAddressToPtr(result);
+ return (Action< INextBot >*)PawnAddressToPtr(result, nullptr);
}
bool CBaseNPCPluginAction::IsAbleToBlockMovementOf( const INextBot *botInMotion ) const
@@ -233,10 +261,12 @@ bool CBaseNPCPluginAction::IsAbleToBlockMovementOf( const INextBot *botInMotion
IPluginFunction* pCallback = m_pFactory->GetCallback( CBaseNPCPluginActionFactory::CallbackType::IsAbleToBlockMovementOf );
if (pCallback && pCallback->IsRunnable())
{
- CBPUSHCELL(PtrToPawnAddress(this))
- CBPUSHCELL(PtrToPawnAddress(botInMotion))
+ CBPUSHPTR(this)
+ CBPUSHPTR(botInMotion)
pCallback->Execute(&result);
+ CBRELPTR(this)
+ CBRELPTR(botInMotion)
}
return !!result;
@@ -246,20 +276,26 @@ bool CBaseNPCPluginAction::IsAbleToBlockMovementOf( const INextBot *botInMotion
BEGINQUERYCALLBACK(ShouldPickUp, CBaseEntity *item )
CBPUSHENTITY(item);
+ EXECUTEQUERYCALLBACK()
ENDQUERYCALLBACK()
BEGINQUERYCALLBACK(ShouldHurry)
+ EXECUTEQUERYCALLBACK()
ENDQUERYCALLBACK()
BEGINQUERYCALLBACK(ShouldRetreat)
+ EXECUTEQUERYCALLBACK()
ENDQUERYCALLBACK()
BEGINQUERYCALLBACK(ShouldAttack, const CKnownEntity *them)
- CBPUSHCELL(PtrToPawnAddress(them))
+ CBPUSHPTR(them)
+ EXECUTEQUERYCALLBACK()
+ CBRELPTR(them)
ENDQUERYCALLBACK()
BEGINQUERYCALLBACK(IsHindrance, CBaseEntity* blocker)
CBPUSHENTITY(blocker == IS_ANY_HINDRANCE_POSSIBLE ? nullptr : blocker)
+ EXECUTEQUERYCALLBACK()
ENDQUERYCALLBACK()
Vector CBaseNPCPluginAction::SelectTargetPoint( const INextBot* me, const CBaseCombatCharacter* subject ) const
@@ -274,11 +310,13 @@ Vector CBaseNPCPluginAction::SelectTargetPoint( const INextBot* me, const CBaseC
buffer[1] = sp_ftoc(result[1]);
buffer[2] = sp_ftoc(result[2]);
- CBPUSHCELL(PtrToPawnAddress(this))
- CBPUSHCELL(PtrToPawnAddress(me))
+ CBPUSHPTR(this)
+ CBPUSHPTR(me)
CBPUSHENTITY((CBaseCombatCharacter*)subject)
pCallback->PushArray(buffer, 3, SM_PARAM_COPYBACK);
pCallback->Execute(nullptr);
+ CBRELPTR(this)
+ CBRELPTR(me)
result[0] = sp_ctof(buffer[0]);
result[1] = sp_ctof(buffer[1]);
@@ -290,6 +328,7 @@ Vector CBaseNPCPluginAction::SelectTargetPoint( const INextBot* me, const CBaseC
BEGINQUERYCALLBACK(IsPositionAllowed, const Vector &pos)
CBPUSHVECTOR(pos)
+ EXECUTEQUERYCALLBACK()
ENDQUERYCALLBACK()
const CKnownEntity * CBaseNPCPluginAction::SelectMoreDangerousThreat( const INextBot *me,
@@ -302,56 +341,73 @@ const CKnownEntity * CBaseNPCPluginAction::SelectMoreDangerousThreat( const INex
IPluginFunction* pCallback = m_pFactory->GetQueryCallback( CBaseNPCPluginActionFactory::QueryCallbackType::SelectMoreDangerousThreat );
if (pCallback && pCallback->IsRunnable())
{
- CBPUSHCELL(PtrToPawnAddress(this))
- CBPUSHCELL(PtrToPawnAddress(me))
+ CBPUSHPTR(this)
+ CBPUSHPTR(me)
CBPUSHENTITY((CBaseCombatCharacter*)subject)
- CBPUSHCELL(PtrToPawnAddress(threat1))
- CBPUSHCELL(PtrToPawnAddress(threat2))
+ CBPUSHPTR(threat1)
+ CBPUSHPTR(threat2)
pCallback->Execute(&result);
+ CBRELPTR(this)
+ CBRELPTR(me)
+ CBRELPTR(threat1)
+ CBRELPTR(threat2)
}
- return (const CKnownEntity*)PawnAddressToPtr(result);
+ return (const CKnownEntity*)PawnAddressToPtr(result, nullptr);
}
// Events
BEGINEVENTCALLBACK(OnLeaveGround, CBaseEntity* ground)
EVENTPUSHENTITY(ground)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnLandOnGround, CBaseEntity* ground)
EVENTPUSHENTITY(ground)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnContact, CBaseEntity* other, CGameTrace* traceResult)
EVENTPUSHENTITY(other)
- EVENTPUSHCELL(PtrToPawnAddress(traceResult))
+ EVENTPUSHPTR(traceResult)
+ EXECUTEEVENTCALLBACK()
+ EVENTRELPTR(traceResult)
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnMoveToSuccess, const Path *path)
- EVENTPUSHCELL(PtrToPawnAddress(path))
+ EVENTPUSHPTR(path)
+ EXECUTEEVENTCALLBACK()
+ EVENTRELPTR(path)
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnMoveToFailure, const Path *path, MoveToFailureType reason)
- EVENTPUSHCELL(PtrToPawnAddress(path))
+ EVENTPUSHPTR(path)
EVENTPUSHCELL(reason)
+ EXECUTEEVENTCALLBACK()
+ EVENTRELPTR(path)
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnStuck)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnUnStuck)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnPostureChanged)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnAnimationActivityComplete, int activity)
EVENTPUSHCELL(activity)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnAnimationActivityInterrupted, int activity)
EVENTPUSHCELL(activity)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnAnimationEvent, animevent_t *event)
@@ -361,9 +417,11 @@ BEGINEVENTCALLBACK(OnAnimationEvent, animevent_t *event)
EVENTPUSHFLOAT(event->eventtime)
EVENTPUSHCELL(event->type)
EVENTPUSHENTITY((CBaseAnimating*)event->pSource)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnIgnite)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnInjured, const CTakeDamageInfo &info)
@@ -375,6 +433,7 @@ BEGINEVENTCALLBACK(OnInjured, const CTakeDamageInfo &info)
EVENTPUSHVECTOR(info.GetDamageForce())
EVENTPUSHVECTOR(info.GetDamagePosition())
EVENTPUSHCELL(info.GetDamageCustom())
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnKilled, const CTakeDamageInfo &info)
@@ -386,6 +445,7 @@ BEGINEVENTCALLBACK(OnKilled, const CTakeDamageInfo &info)
EVENTPUSHVECTOR(info.GetDamageForce())
EVENTPUSHVECTOR(info.GetDamagePosition())
EVENTPUSHCELL(info.GetDamageCustom())
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnOtherKilled, CBaseCombatCharacter *victim, const CTakeDamageInfo &info)
@@ -398,14 +458,17 @@ BEGINEVENTCALLBACK(OnOtherKilled, CBaseCombatCharacter *victim, const CTakeDamag
EVENTPUSHVECTOR(info.GetDamageForce())
EVENTPUSHVECTOR(info.GetDamagePosition())
EVENTPUSHCELL(info.GetDamageCustom())
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnSight, CBaseEntity *subject)
EVENTPUSHENTITY(subject)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnLostSight, CBaseEntity *subject)
EVENTPUSHENTITY(subject)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnSound, CBaseEntity *source, const Vector &pos, KeyValues *keys)
@@ -426,95 +489,119 @@ BEGINEVENTCALLBACK(OnSound, CBaseEntity *source, const Vector &pos, KeyValues *k
// Deletes pStk
handlesys->FreeHandle(hndl, &sec);
-
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK_NOEXECUTE()
BEGINEVENTCALLBACK(OnSpokeConcept, CBaseCombatCharacter* who, AIConcept_t concept, AI_Response *response)
EVENTPUSHENTITY(who)
- EVENTPUSHCELL(concept)
- EVENTPUSHCELL(PtrToPawnAddress(response))
+ EVENTPUSHSTRING(concept)
+ EVENTPUSHPTR(response)
+ EXECUTEEVENTCALLBACK()
+ EVENTRELPTR(response)
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnWeaponFired, CBaseCombatCharacter* whoFired, CBaseEntity* weapon )
EVENTPUSHENTITY(whoFired)
EVENTPUSHENTITY(weapon)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnNavAreaChanged, CNavArea *newArea, CNavArea *oldArea)
- EVENTPUSHCELL(PtrToPawnAddress(newArea))
- EVENTPUSHCELL(PtrToPawnAddress(oldArea))
+ EVENTPUSHPTR(newArea)
+ EVENTPUSHPTR(oldArea)
+ EXECUTEEVENTCALLBACK()
+ EVENTRELPTR(newArea)
+ EVENTRELPTR(oldArea)
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnModelChanged)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnPickUp, CBaseEntity* item, CBaseCombatCharacter* giver)
EVENTPUSHENTITY(item)
EVENTPUSHENTITY(giver)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnDrop, CBaseEntity* item)
EVENTPUSHENTITY(item)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnActorEmoted, CBaseCombatCharacter* emoter, int emote)
EVENTPUSHENTITY(emoter)
EVENTPUSHCELL(emote)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnCommandAttack, CBaseEntity *victim)
EVENTPUSHENTITY(victim)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnCommandApproach, const Vector &pos, float range )
EVENTPUSHVECTOR(pos)
EVENTPUSHFLOAT(range)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACKEX(OnCommandApproach, OnCommandApproachEntity, CBaseEntity* goal)
EVENTPUSHENTITY(goal)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnCommandRetreat, CBaseEntity *threat, float range)
EVENTPUSHENTITY(threat)
EVENTPUSHFLOAT(range)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnCommandPause, float duration)
EVENTPUSHFLOAT(duration)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnCommandResume)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnCommandString, const char *command)
EVENTPUSHSTRING(command)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnShoved, CBaseEntity *pusher)
EVENTPUSHENTITY(pusher)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnBlinded, CBaseEntity *blinder)
EVENTPUSHENTITY(blinder)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnTerritoryContested, int territoryID)
EVENTPUSHCELL(territoryID)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnTerritoryCaptured, int territoryID)
EVENTPUSHCELL(territoryID)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnTerritoryLost, int territoryID)
EVENTPUSHCELL(territoryID)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnWin)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
BEGINEVENTCALLBACK(OnLose)
+ EXECUTEEVENTCALLBACK()
ENDEVENTCALLBACK()
CBaseNPCIntention::CBaseNPCIntention( INextBot * bot, CBaseNPCPluginActionFactory* initialActionFactory )
@@ -750,7 +837,9 @@ void CBaseNPCPluginActionFactory::OnCreateInitialAction(Action * pActi
IPluginFunction * pCallback = GetCallback( CreateInitialAction );
if (pCallback && pCallback->IsRunnable())
{
- pCallback->PushCell(PtrToPawnAddress(pAction));
+ Handle_t hndlAction = PtrToPawnAddress(pAction, nullptr);
+ pCallback->PushCell(hndlAction);
pCallback->Execute(nullptr);
+ ReleasePawnAddress(hndlAction, nullptr);
}
}
diff --git a/extension/cbasenpc_locomotion.cpp b/extension/cbasenpc_locomotion.cpp
index d06740b..7a30506 100644
--- a/extension/cbasenpc_locomotion.cpp
+++ b/extension/cbasenpc_locomotion.cpp
@@ -180,9 +180,13 @@ bool CBaseNPC_Locomotion::V_IsAbleToClimb()
{
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
@@ -211,9 +215,13 @@ bool CBaseNPC_Locomotion::V_IsClimbingUpToLedge()
{
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
@@ -285,12 +293,16 @@ bool CBaseNPC_Locomotion::V_ClimbUpToLedge(const Vector& vecGoal, const Vector&
cell_t entRef = gamehelpers->EntityToBCompatRef(const_cast(pEntity));
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->PushArray(goalArr, 3);
pCallback->PushArray(forwardArr, 3);
pCallback->PushCell(entRef);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
@@ -319,9 +331,13 @@ bool CBaseNPC_Locomotion::V_IsAbleToJumpAcrossGaps()
{
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
@@ -350,9 +366,13 @@ bool CBaseNPC_Locomotion::V_IsJumpingAcrossGap()
{
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
@@ -383,10 +403,14 @@ void CBaseNPC_Locomotion::V_JumpAcrossGap(const Vector& landingGoal, const Vecto
VectorToPawnVector(forwardArr, landingForward);
cell_t result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->PushArray(goalArr, 3);
pCallback->PushArray(forwardArr, 3);
pCallback->Execute(&result);
+
+ ReleasePawnAddress(hndlThis, nullptr);
}
else
{
@@ -418,11 +442,15 @@ bool CBaseNPC_Locomotion::V_IsEntityTraversable(CBaseEntity* pEntity, ILocomotio
cell_t entRef = gamehelpers->EntityToBCompatRef(pEntity);
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->PushCell(entRef);
pCallback->PushCell((cell_t)when);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
@@ -452,10 +480,14 @@ bool CBaseNPC_Locomotion::V_ShouldCollideWith(const CBaseEntity* pEntity)
cell_t entRef = gamehelpers->EntityToBCompatRef(const_cast(pEntity));
cell_t _result = 0;
- pCallback->PushCell((cell_t)this);
+ Handle_t hndlThis = PtrToPawnAddress(this, nullptr);
+
+ pCallback->PushCell(hndlThis);
pCallback->PushCell(entRef);
pCallback->Execute(&_result);
+ ReleasePawnAddress(hndlThis, nullptr);
+
result = !!_result;
}
else
diff --git a/extension/extension.cpp b/extension/extension.cpp
index a0cbf95..ab215df 100644
--- a/extension/extension.cpp
+++ b/extension/extension.cpp
@@ -16,6 +16,7 @@
class CTakeDamageInfoHack;
SH_DECL_MANUALEXTERN1_void(MEvent_Killed, CTakeDamageInfoHack &);
+SH_DECL_HOOK1_void(IServerGameDLL, GameFrame, SH_NOATTRIB, false, bool);
CGlobalVars* gpGlobals = nullptr;
IGameConfig* g_pGameConf = nullptr;
@@ -54,6 +55,8 @@ extern ConVar* nb_update_framelimit;
extern ConVar* nb_update_maxslide;
HandleType_t g_KeyValueType;
+HandleType_t g_MemoryPtr;
+std::unordered_set gHandlesToFree;
CBaseNPCExt g_CBaseNPCExt;
SMEXT_LINK(&g_CBaseNPCExt);
@@ -62,6 +65,19 @@ IForward *g_pForwardEventKilled = nullptr;
bool (ToolsTraceFilterSimple:: *ToolsTraceFilterSimple::func_ShouldHitEntity)(IHandleEntity *pHandleEntity, int contentsMask) = nullptr;
CUtlMap g_EntitiesHooks;
+void Hook_GameFrame(bool simulating) {
+ // This is only temporary help for plugin authors getting
+ // accustomed with the new handles
+ HandleSecurity security;
+ security.pIdentity = myself->GetIdentity();
+ security.pOwner = nullptr;
+
+ for (auto hndl : gHandlesToFree) {
+ handlesys->FreeHandle(hndl, &security);
+ }
+ gHandlesToFree.clear();
+}
+
bool CBaseNPCExt::SDK_OnLoad(char* error, size_t maxlength, bool late) {
char conf_error[255];
if (!gameconfs->LoadGameConfigFile("cbasenpc", &g_pGameConf, conf_error, sizeof(conf_error))) {
@@ -153,6 +169,8 @@ bool CBaseNPCExt::SDK_OnMetamodLoad(ISmmAPI *ismm, char *error, size_t maxlen, b
g_pSharedChangeInfo = engine->GetSharedEdictChangeInfo();
gpGlobals = ismm->GetCGlobals();
+
+ SH_ADD_HOOK(IServerGameDLL, GameFrame, gamedll, SH_STATIC(Hook_GameFrame), false);
return true;
}
@@ -167,7 +185,6 @@ void CBaseNPCExt::OnCoreMapStart(edict_t* edictlist, int edictCount, int clientM
void CBaseNPCExt::OnCoreMapEnd() {
g_pBaseNPCPluginActionFactories->OnCoreMapEnd();
g_pPluginEntityFactories->OnCoreMapEnd();
- CNavMesh::OnCoreMapEnd();
}
void CBaseNPCExt::OnEntityCreated(CBaseEntity* pEntity, const char* classname) {
@@ -212,6 +229,7 @@ void CBaseNPCExt::SDK_OnAllLoaded() {
SM_GET_LATE_IFACE(SDKHOOKS, g_pSDKHooks);
handlesys->FindHandleType("KeyValues", &g_KeyValueType);
+ handlesys->FindHandleType("MemoryPointer", &g_MemoryPtr);
// HACK: Get g_pCoreIdent from KeyValues QHandleType
// g_KeyValueType is an index of QHandleType array m_Types
@@ -280,6 +298,8 @@ void CBaseNPCExt::NotifyInterfaceDrop(SMInterface* interface) {
}
void CBaseNPCExt::SDK_OnUnload() {
+ SH_REMOVE_HOOK(IServerGameDLL, GameFrame, gamedll, SH_STATIC(Hook_GameFrame), false);
+
gameconfs->CloseGameConfigFile(g_pGameConf);
forwards->ReleaseForward(g_pForwardEventKilled);
diff --git a/extension/helpers.h b/extension/helpers.h
index bfed9d3..7c4d3e6 100644
--- a/extension/helpers.h
+++ b/extension/helpers.h
@@ -4,12 +4,14 @@
#pragma once
#include "smsdk_ext.h"
+#include "IMemoryPointer.h"
#include
#include
#include
#include
#include
#include
+#include
#define GETGAMEDATAOFFSET(name, var) \
if(!g_pGameConf->GetOffset(name, &var) || var == -1) { snprintf(error, maxlength, "FAILED TO GET GAMEDATA OFFSET FOR %s", name); return false; } \
@@ -148,20 +150,96 @@ inline void VectorToPawnVector(cell_t* angAddr, const QAngle* angle)
angAddr[2] = sp_ftoc(angle->z);
}
-inline cell_t PtrToPawnAddress(const void* ptr) {
-#ifdef PLATFORM_X64
- return g_pSM->ToPseudoAddress(ptr);
-#else
- return (cell_t)ptr;
-#endif
+class ForeignMemoryPointer : IMemoryPointer {
+public:
+ ForeignMemoryPointer(const void* ptr) : m_ptr(ptr) {}
+
+ virtual void Delete() override
+ {
+ delete this;
+ }
+
+ virtual cell_t GetSize() override
+ {
+ return 0;
+ }
+
+ virtual void* Get() override
+ {
+ return (void*)m_ptr;
+ }
+protected:
+ const void* m_ptr;
+};
+
+extern HandleType_t g_MemoryPtr;
+extern std::unordered_set gHandlesToFree;
+
+inline void ReleasePawnAddress(Handle_t hndl, IPluginContext* context)
+{
+ HandleSecurity security;
+ security.pIdentity = myself->GetIdentity();
+ // Enable when plugins should be in charge of the handles
+ /*if (context) {
+ security.pOwner = context->GetIdentity();
+ } else {
+ security.pOwner = nullptr;
+ }*/
+ security.pOwner = nullptr;
+
+ gHandlesToFree.erase(hndl);
+ handlesys->FreeHandle(hndl, &security);
}
-inline void* PawnAddressToPtr(cell_t addr) {
-#ifdef PLATFORM_X64
- return (void*)g_pSM->FromPseudoAddress(param);
-#else
- return (void*)addr;
-#endif
+inline Handle_t PtrToPawnAddress(const void* ptr, IPluginContext* context, bool keepAround = false) {
+ auto foreignPtr = new ForeignMemoryPointer(ptr);
+
+ // Enable when plugins should be in charge of the handles
+ /*IdentityToken_t* identity = nullptr;
+ if (context) {
+ identity = context->GetIdentity();
+ }*/
+ // Atm regardless of identity, the handle will be owned by no-one
+ Handle_t handle = handlesys->CreateHandle(g_MemoryPtr, foreignPtr, nullptr, myself->GetIdentity(), nullptr);
+ if (handle == BAD_HANDLE)
+ {
+ delete foreignPtr;
+ return BAD_HANDLE;
+ }
+
+ // Unless explicitly specified otherwise, handles will be automatically destroyed next server frame
+ if (!keepAround) {
+ gHandlesToFree.insert(handle);
+ }
+
+ return handle;
+}
+
+inline void* PawnAddressToPtr(cell_t cellHndl, IPluginContext* context) {
+ Handle_t hndl = (Handle_t)cellHndl;
+ if (hndl == BAD_HANDLE) {
+ return nullptr;
+ }
+
+ HandleError err = HandleError_None;
+ IMemoryPointer* ptr = nullptr;
+
+ HandleSecurity security;
+ security.pIdentity = myself->GetIdentity();
+ if (context) {
+ security.pOwner = context->GetIdentity();
+ } else {
+ security.pOwner = nullptr;
+ }
+
+ if ((err=handlesys->ReadHandle(hndl, g_MemoryPtr, &security, (void **)&ptr)) != HandleError_None || ptr == nullptr) {
+ if (context) {
+ context->ThrowNativeError("Could not read Handle %x (error %d)", hndl, err);
+ }
+ return nullptr;
+ }
+
+ return ptr->Get();
}
#if SOURCEPAWN_API_VERSION >= 0x0211
diff --git a/extension/idatamapcontainer.cpp b/extension/idatamapcontainer.cpp
index b0854b4..f72883c 100644
--- a/extension/idatamapcontainer.cpp
+++ b/extension/idatamapcontainer.cpp
@@ -188,7 +188,7 @@ void IDataMapContainer::EndDataDesc()
void IDataMapContainer::DefineField(const char* name, fieldtype_t fieldType, unsigned short count, short flags, const char* externalName, float fieldTolerance)
{
size_t padding = 0;
- int fieldOffset = GetAlignedOffset( GetDataDescOffset() + m_DataMapDescSizeInBytes, fieldType, &padding );
+ int fieldOffset = (int)GetAlignedOffset( GetDataDescOffset() + m_DataMapDescSizeInBytes, fieldType, &padding );
int fieldSizeInBytes = g_DataMapDescFieldSizes[fieldType] * count;
name = name ? strdup(name) : NULL;
@@ -772,10 +772,29 @@ void IEntityDataMapInputFuncDelegate::Alloc()
if (m_pInputFuncPtr)
return;
- uint32_t thisAddr = (uint32_t)this;
- uint32_t callFuncAddr = (uint32_t)(&IEntityDataMapInputFuncDelegate::HandleInput);
-
- uint8_t funcBytes[] = {
+ intp thisAddr = (intp)this;
+ intp callFuncAddr = (intp)(&IEntityDataMapInputFuncDelegate::HandleInput);
+
+ uint8_t funcBytes[] = {
+#ifdef PLATFORM_X64
+ // (IEntityDataMapInputFuncDelegate* pDelegate, CBaseEntity* pEntity, inputdata_t &data)
+ // this::(inputdata_t &)
+#ifdef WIN64
+ // RCX / XMM0L, RDX / XMM1L, R8 / XMM2L, and R9 / XMM3L
+ 0x49, 0x89, 0xD0, // mov R8, RDX
+ 0x48, 0x89, 0xCA, // mov RDX, RCX
+ 0x48, 0xB9, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // movabs rcx, thisAddr
+ 0x49, 0xB9, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // movabs r9, callFuncAddr
+ 0x41, 0xFF, 0xE1 // jmp r9
+#else
+ // RDI, RSI, RDX, RCX, R8, R9
+ 0x48, 0x89, 0xF2, // mov RDX, RSI - 3rd arg
+ 0x48, 0x89, 0xFE, // mov RSI, RDI
+ 0x48, 0xBF, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // movabs rdi, thisAddr
+ 0x49, 0xB9, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // movabs r9, callFuncAddr
+ 0x41, 0xFF, 0xE1 // jmp r9
+#endif
+#else
#ifdef WIN32
// MSVC __thiscall
0x55, // push ebp
@@ -813,6 +832,7 @@ void IEntityDataMapInputFuncDelegate::Alloc()
0x89, 0xEC, // mov esp, ebp
0x5D, // pop ebp
0xC3 // ret
+#endif
#endif
};
@@ -823,14 +843,23 @@ void IEntityDataMapInputFuncDelegate::Alloc()
{
g_InputFuncAlloc.SetRW(m_pInputFuncPtr);
+#ifdef PLATFORM_X64
+#ifdef WIN64
+ *((intp*)(&funcBytes[8])) = thisAddr;
+ *((intp*)(&funcBytes[18])) = callFuncAddr;
+#else
+ *((intp*)(&funcBytes[8])) = thisAddr;
+ *((intp*)(&funcBytes[18])) = callFuncAddr;
+#endif
+#else
#ifdef WIN32
- *((uint32_t*)(&funcBytes[11])) = thisAddr;
- *((uint32_t*)(&funcBytes[16])) = callFuncAddr;
+ *((intp*)(&funcBytes[11])) = thisAddr;
+ *((intp*)(&funcBytes[16])) = callFuncAddr;
#else
- *((uint32_t*)(&funcBytes[14])) = thisAddr;
- *((uint32_t*)(&funcBytes[19])) = callFuncAddr;
+ *((intp*)(&funcBytes[14])) = thisAddr;
+ *((intp*)(&funcBytes[19])) = callFuncAddr;
+#endif
#endif
-
memcpy(m_pInputFuncPtr, funcBytes, m_iInputFuncSize);
g_InputFuncAlloc.SetRE(m_pInputFuncPtr);
@@ -984,7 +1013,7 @@ void IEntityDataMapContainer::DefineInputFunc(const char* name, fieldtype_t fiel
m_pEntityInputFuncDelegates.AddToTail(pDelegate);
// this shuts up the compiler
- *(uint32_t*)(&(typeDesc.inputFunc)) = (uint32_t)pDelegate->m_pInputFuncPtr;
+ *(intp*)(&(typeDesc.inputFunc)) = (intp)pDelegate->m_pInputFuncPtr;
m_vecEntityDataTypeDescriptors.AddToTail(typeDesc);
}
@@ -992,7 +1021,7 @@ void IEntityDataMapContainer::DefineInputFunc(const char* name, fieldtype_t fiel
void IEntityDataMapContainer::DefineOutput(const char* name, const char* mapname)
{
size_t padding = 0;
- int fieldOffset = GetAlignedOffset( GetDataDescOffset() + m_DataMapDescSizeInBytes, sizeof(int*), &padding );
+ int fieldOffset = (int)GetAlignedOffset( GetDataDescOffset() + m_DataMapDescSizeInBytes, sizeof(int*), &padding );
int fieldSizeInBytes = sizeof(CBaseEntityOutput);
name = name ? strdup(name) : NULL;
diff --git a/extension/natives.cpp b/extension/natives.cpp
index 8c2078f..e27e784 100644
--- a/extension/natives.cpp
+++ b/extension/natives.cpp
@@ -118,14 +118,14 @@ void Event_Killed(CTakeDamageInfoHack &info)
RETURN_META(MRES_IGNORED);
}
-cell_t CBaseNPC_GetNextBotOfEntity(IPluginContext *pContext, const cell_t *params) {
+cell_t CBaseNPC_GetNextBotOfEntity(IPluginContext* pContext, const cell_t *params) {
CBaseEntity *pEntity;
ENTINDEX_TO_CBASEENTITY(params[1], pEntity);
- return PtrToPawnAddress(pEntity->MyNextBotPointer());
+ return PtrToPawnAddress(pEntity->MyNextBotPointer(), pContext);
}
-cell_t CBaseNPC_HookEventKilled(IPluginContext *pContext, const cell_t *params)
+cell_t CBaseNPC_HookEventKilled(IPluginContext* pContext, const cell_t *params)
{
CBaseEntity *pEntity;
ENTINDEX_TO_CBASEENTITY(params[1], pEntity);
@@ -139,22 +139,22 @@ cell_t CBaseNPC_HookEventKilled(IPluginContext *pContext, const cell_t *params)
return 1;
}
-cell_t Util_ConcatTransforms(IPluginContext* pContext, const cell_t* params) {
+cell_t Util_ConcatTransforms(IPluginContext* context, const cell_t* params) {
cell_t* inMat1;
cell_t* inMat2;
cell_t* outMat;
- pContext->LocalToPhysAddr(params[1], &inMat1);
- pContext->LocalToPhysAddr(params[2], &inMat2);
- pContext->LocalToPhysAddr(params[3], &outMat);
+ context->LocalToPhysAddr(params[1], &inMat1);
+ context->LocalToPhysAddr(params[2], &inMat2);
+ context->LocalToPhysAddr(params[3], &outMat);
matrix3x4_t in1;
matrix3x4_t in2;
matrix3x4_t out;
- PawnMatrixToMatrix(pContext, inMat1, in1);
- PawnMatrixToMatrix(pContext, inMat2, in2);
+ PawnMatrixToMatrix(context, inMat1, in1);
+ PawnMatrixToMatrix(context, inMat2, in2);
ConcatTransforms(in1, in2, out);
- MatrixToPawnMatrix(pContext, outMat, out);
+ MatrixToPawnMatrix(context, outMat, out);
return 0;
}
diff --git a/extension/natives/baseanimating.cpp b/extension/natives/baseanimating.cpp
index 9de0a1b..558ca1a 100644
--- a/extension/natives/baseanimating.cpp
+++ b/extension/natives/baseanimating.cpp
@@ -133,7 +133,7 @@ cell_t GetModelPtr(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->GetModelPtr());
+ return PtrToPawnAddress(entity->GetModelPtr(), context);
}
cell_t LookupPoseParameter(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/baseanimatingoverlay.cpp b/extension/natives/baseanimatingoverlay.cpp
index 61fba02..eedb180 100644
--- a/extension/natives/baseanimatingoverlay.cpp
+++ b/extension/natives/baseanimatingoverlay.cpp
@@ -6,7 +6,7 @@ namespace natives::baseanimatingoverlay {
namespace layer {
inline CAnimationLayer* Get(IPluginContext* context, const cell_t param) {
- CAnimationLayer* layer = (CAnimationLayer*)PawnAddressToPtr(param);
+ CAnimationLayer* layer = (CAnimationLayer*)PawnAddressToPtr(param, context);
if (!layer) {
context->ThrowNativeError("Layer is a null ptr!");
return nullptr;
@@ -697,7 +697,7 @@ cell_t GetAnimOverlay(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->GetAnimOverlay(params[2]));
+ return PtrToPawnAddress(entity->GetAnimOverlay(params[2]), context);
};
cell_t GetNumAnimOverlays(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/basecombatcharacter.cpp b/extension/natives/basecombatcharacter.cpp
index 0059999..2d676b7 100644
--- a/extension/natives/basecombatcharacter.cpp
+++ b/extension/natives/basecombatcharacter.cpp
@@ -34,7 +34,7 @@ cell_t GetLastKnownArea(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->GetLastKnownArea());
+ return PtrToPawnAddress(entity->GetLastKnownArea(), context);
};
void setup(std::vector& natives) {
diff --git a/extension/natives/baseentity.cpp b/extension/natives/baseentity.cpp
index c6f506e..f70d956 100644
--- a/extension/natives/baseentity.cpp
+++ b/extension/natives/baseentity.cpp
@@ -23,7 +23,7 @@ cell_t NetworkProp(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->NetworkProp());
+ return PtrToPawnAddress(entity->NetworkProp(), context);
}
cell_t CollisionProp(IPluginContext* context, const cell_t* params) {
@@ -32,7 +32,7 @@ cell_t CollisionProp(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->CollisionProp());
+ return PtrToPawnAddress(entity->CollisionProp(), context);
}
cell_t DispatchUpdateTransmitState(IPluginContext* context, const cell_t* params) {
@@ -300,7 +300,7 @@ cell_t NetworkStateChangedVar(IPluginContext* context, const cell_t* params) {
return 0;
}
- entity->NetworkStateChanged(PawnAddressToPtr(params[2]));
+ entity->NetworkStateChanged(PawnAddressToPtr(params[2], context));
return 0;
}
@@ -480,7 +480,7 @@ cell_t MyNextBotPointer(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->MyNextBotPointer());
+ return PtrToPawnAddress(entity->MyNextBotPointer(), context);
}
cell_t GetBaseAnimating(IPluginContext* context, const cell_t* params) {
@@ -516,7 +516,7 @@ cell_t TakeDamage(IPluginContext* context, const cell_t* params) {
return 0;
}
- CTakeDamageInfo* inputInfo = (CTakeDamageInfo*)PawnAddressToPtr(params[2]);
+ CTakeDamageInfo* inputInfo = (CTakeDamageInfo*)PawnAddressToPtr(params[2], context);
if (!inputInfo) {
context->ThrowNativeError("CTakeDamageInfo is a null ptr!");
return 0;
diff --git a/extension/natives/cbasenpc.cpp b/extension/natives/cbasenpc.cpp
index 34c836f..06587af 100644
--- a/extension/natives/cbasenpc.cpp
+++ b/extension/natives/cbasenpc.cpp
@@ -47,7 +47,7 @@ void setup(std::vector& natives) {
namespace locomotion {
inline CBaseNPC_Locomotion* Get(IPluginContext* context, const cell_t param) {
- CBaseNPC_Locomotion* mover = (CBaseNPC_Locomotion*)PawnAddressToPtr(param);
+ CBaseNPC_Locomotion* mover = (CBaseNPC_Locomotion*)PawnAddressToPtr(param, context);
if (!mover) {
context->ThrowNativeError("Invalid Locomotion %i", param);
return nullptr;
@@ -261,7 +261,7 @@ cell_t GetBot(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(npc->GetEntity()->MyNextBotPointer());
+ return PtrToPawnAddress(npc->GetEntity()->MyNextBotPointer(), context);
}
cell_t GetLocomotion(IPluginContext* context, const cell_t* params) {
@@ -270,7 +270,7 @@ cell_t GetLocomotion(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(npc->m_pMover);
+ return PtrToPawnAddress(npc->m_pMover, context);
}
cell_t GetBody(IPluginContext* context, const cell_t* params) {
@@ -279,7 +279,7 @@ cell_t GetBody(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(npc->m_pBody);
+ return PtrToPawnAddress(npc->m_pBody, context);
}
cell_t GetVision(IPluginContext* context, const cell_t* params) {
@@ -288,7 +288,7 @@ cell_t GetVision(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(npc->GetEntity()->MyNextBotPointer()->GetVisionInterface());
+ return PtrToPawnAddress(npc->GetEntity()->MyNextBotPointer()->GetVisionInterface(), context);
}
cell_t GetIntention(IPluginContext* context, const cell_t* params) {
@@ -297,7 +297,7 @@ cell_t GetIntention(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(npc->GetEntity()->MyNextBotPointer()->GetIntentionInterface());
+ return PtrToPawnAddress(npc->GetEntity()->MyNextBotPointer()->GetIntentionInterface(), context);
}
cell_t SetType(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/entityfactory.cpp b/extension/natives/entityfactory.cpp
index 5a27663..d50491e 100644
--- a/extension/natives/entityfactory.cpp
+++ b/extension/natives/entityfactory.cpp
@@ -254,9 +254,7 @@ cell_t AttachNextBot(IPluginContext* context, const cell_t* params) {
return 0;
}
- // TO-DO: 2.0.0
- bool old = ((params[0] < 2) || context->GetFunctionById(params[2]) == nullptr);
- factory->AttachNextBot((old) ? (IPluginFunction*)0x1 : context->GetFunctionById(params[2]));
+ factory->AttachNextBot(context->GetFunctionById(params[2]));
return 0;
}
diff --git a/extension/natives/nav.cpp b/extension/natives/nav.cpp
index d968adb..ff4b0ad 100644
--- a/extension/natives/nav.cpp
+++ b/extension/natives/nav.cpp
@@ -31,7 +31,7 @@ cell_t GetElement(IPluginContext* context, const cell_t* params) {
if (ID > collector->Count()) {
return 0;
}
- return PtrToPawnAddress(collector->Element(ID));
+ return PtrToPawnAddress(collector->Element(ID), context);
}
void setup(std::vector& natives) {
@@ -48,7 +48,11 @@ void setup(std::vector& natives) {
}
cell_t GetAddress(IPluginContext* context, const cell_t* params) {
- return PtrToPawnAddress(TheNavMesh);
+ static Handle_t hndlNavMesh = BAD_HANDLE;
+ if (hndlNavMesh == BAD_HANDLE) {
+ hndlNavMesh = PtrToPawnAddress(TheNavMesh, nullptr, true);
+ }
+ return hndlNavMesh;
}
cell_t IsLoaded(IPluginContext* context, const cell_t* params) {
@@ -72,7 +76,7 @@ cell_t GetNavArea(IPluginContext* context, const cell_t* params) {
context->LocalToPhysAddr(params[2], &vecAddr);
Vector vecPos;
PawnVectorToVector(vecAddr, vecPos);
- return PtrToPawnAddress(ToolsNavMesh->GetNavArea(vecPos, sp_ctof(params[3])));
+ return PtrToPawnAddress(ToolsNavMesh->GetNavArea(vecPos, sp_ctof(params[3])), context);
}
cell_t GetNavAreaEntity(IPluginContext* context, const cell_t* params) {
@@ -80,7 +84,7 @@ cell_t GetNavAreaEntity(IPluginContext* context, const cell_t* params) {
if (!ent) {
return context->ThrowNativeError("Invalid Entity index/reference %d", params[1]);
}
- return PtrToPawnAddress(ToolsNavMesh->GetNavArea(ent, params[3], sp_ctof(params[4])));
+ return PtrToPawnAddress(ToolsNavMesh->GetNavArea(ent, params[3], sp_ctof(params[4])), context);
}
cell_t GetNearestNavArea(IPluginContext* context, const cell_t* params) {
@@ -88,12 +92,12 @@ cell_t GetNearestNavArea(IPluginContext* context, const cell_t* params) {
context->LocalToPhysAddr(params[2], &vecAddr);
Vector vecPos;
PawnVectorToVector(vecAddr, vecPos);
- return PtrToPawnAddress(ToolsNavMesh->GetNearestNavArea(vecPos, params[3], sp_ctof(params[4]), params[5], params[6], params[7]));
+ return PtrToPawnAddress(ToolsNavMesh->GetNearestNavArea(vecPos, params[3], sp_ctof(params[4]), params[5], params[6], params[7]), context);
}
cell_t GetNavAreaByID(IPluginContext* context, const cell_t* params) {
unsigned int id = (unsigned int)params[2];
- return PtrToPawnAddress(ToolsNavMesh->GetNavAreaByID(id));
+ return PtrToPawnAddress(ToolsNavMesh->GetNavAreaByID(id), context);
}
class CCollectorAddToTail {
@@ -107,7 +111,7 @@ class CCollectorAddToTail {
cell_t CollectSurroundingAreas(IPluginContext* context, const cell_t* params) {
CUtlVector *pCollector = new CUtlVector;
- CollectSurroundingAreas( pCollector, (CNavArea*)PawnAddressToPtr(params[2]), sp_ctof(params[3]), sp_ctof(params[4]), sp_ctof(params[5]));
+ CollectSurroundingAreas( pCollector, (CNavArea*)PawnAddressToPtr(params[2], context), sp_ctof(params[3]), sp_ctof(params[4]), sp_ctof(params[5]));
return CREATEHANDLE(AreasCollector, pCollector);
}
@@ -145,8 +149,8 @@ cell_t CollectAreasInRadius(IPluginContext* context, const cell_t* params) {
}
cell_t CollectAreasAlongLine(IPluginContext* context, const cell_t* params) {
- CNavArea* startArea = (CNavArea*)PawnAddressToPtr(params[2]);
- CNavArea* endArea = (CNavArea*)PawnAddressToPtr(params[3]);
+ CNavArea* startArea = (CNavArea*)PawnAddressToPtr(params[2], context);
+ CNavArea* endArea = (CNavArea*)PawnAddressToPtr(params[3], context);
cell_t* reachedEndAddr;
context->LocalToPhysAddr(params[4], &reachedEndAddr);
@@ -166,13 +170,22 @@ class SMPathCost : public IPathCost
{
if (m_pFunc && m_pFunc->IsRunnable())
{
+ Handle_t hndlArea = PtrToPawnAddress(area, nullptr);
+ Handle_t hndlFromArea = PtrToPawnAddress(fromArea, nullptr);
+ Handle_t hndlLadder = PtrToPawnAddress(ladder, nullptr);
+
cell_t result = sp_ftoc(0.0);
- m_pFunc->PushCell(PtrToPawnAddress(area));
- m_pFunc->PushCell(PtrToPawnAddress(fromArea));
- m_pFunc->PushCell(PtrToPawnAddress(ladder));
+ m_pFunc->PushCell(hndlArea);
+ m_pFunc->PushCell(hndlFromArea);
+ m_pFunc->PushCell(hndlLadder);
m_pFunc->PushCell(gamehelpers->EntityToBCompatRef((CBaseEntity*)elevator));
m_pFunc->PushFloat(length);
m_pFunc->Execute(&result);
+
+ ReleasePawnAddress(hndlArea, nullptr);
+ ReleasePawnAddress(hndlFromArea, nullptr);
+ ReleasePawnAddress(hndlLadder, nullptr);
+
return sp_ctof(result);
}
else {
@@ -215,12 +228,12 @@ class SMPathCost : public IPathCost
};
cell_t BuildPath(IPluginContext* context, const cell_t* params) {
- CNavArea *startArea = (CNavArea *)PawnAddressToPtr(params[2]);
+ CNavArea *startArea = (CNavArea *)PawnAddressToPtr(params[2], context);
if (!startArea) {
return context->ThrowNativeError("Starting area is null!");
}
- CNavArea* goalArea = (CNavArea *)PawnAddressToPtr(params[3]);
+ CNavArea* goalArea = (CNavArea *)PawnAddressToPtr(params[3], context);
cell_t* goalPosAddr;
context->LocalToPhysAddr(params[4], &goalPosAddr);
Vector goalPos;
@@ -248,7 +261,7 @@ cell_t BuildPath(IPluginContext* context, const cell_t* params) {
ignoreNavBlockers);
if (closestAreaAddr) {
- *closestAreaAddr = PtrToPawnAddress(closestArea);
+ *closestAreaAddr = PtrToPawnAddress(closestArea, context);
}
return result;
diff --git a/extension/natives/nav/area.cpp b/extension/natives/nav/area.cpp
index 36fff52..0014ccd 100644
--- a/extension/natives/nav/area.cpp
+++ b/extension/natives/nav/area.cpp
@@ -19,7 +19,7 @@ inline cell_t Get(IPluginContext* context, const cell_t* params)
if (i < 0 || i >= TheHidingSpots.Count()) {
return context->ThrowNativeError("Index is out of bounds!");
}
- return PtrToPawnAddress(TheHidingSpots[i]);
+ return PtrToPawnAddress(TheHidingSpots[i], context);
}
void setup(std::vector& natives) {
@@ -38,7 +38,7 @@ void setup(std::vector& natives) {
}
inline HidingSpot* Get(IPluginContext* context, const cell_t param) {
- HidingSpot* spot = (HidingSpot*)PawnAddressToPtr(param);
+ HidingSpot* spot = (HidingSpot*)PawnAddressToPtr(param, context);
if (!spot) {
context->ThrowNativeError("Hiding spot ptr is null!");
return nullptr;
@@ -82,7 +82,7 @@ cell_t GetArea(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(spot->GetArea());
+ return PtrToPawnAddress(spot->GetArea(), context);
}
void setup(std::vector& natives) {
@@ -103,7 +103,7 @@ void setup(std::vector& natives) {
namespace ladder {
inline CNavLadder* Get(IPluginContext* context, const cell_t param) {
- CNavLadder* spot = (CNavLadder*)PawnAddressToPtr(param);
+ CNavLadder* spot = (CNavLadder*)PawnAddressToPtr(param, context);
if (!spot) {
context->ThrowNativeError("Nav ladder ptr is null!");
return nullptr;
@@ -146,7 +146,7 @@ inline cell_t Get(IPluginContext* context, const cell_t* params)
if (i < 0 || i >= TheNavAreas.Count()) {
return context->ThrowNativeError("Index is out of bounds!");
}
- return PtrToPawnAddress(TheNavAreas[i]);
+ return PtrToPawnAddress(TheNavAreas[i], context);
}
void setup(std::vector& natives) {
@@ -173,11 +173,11 @@ cell_t IsOpenListEmpty(IPluginContext* context, const cell_t* params) {
}
cell_t PopOpenList(IPluginContext* context, const cell_t* params) {
- return PtrToPawnAddress(CNavArea::PopOpenList());
+ return PtrToPawnAddress(CNavArea::PopOpenList(), context);
}
inline CNavArea* Get(IPluginContext* context, const cell_t param) {
- CNavArea* area = (CNavArea*)PawnAddressToPtr(param);
+ CNavArea* area = (CNavArea*)PawnAddressToPtr(param, context);
if (!area) {
context->ThrowNativeError("Nav area ptr is null!");
return nullptr;
@@ -219,7 +219,7 @@ cell_t SetParent(IPluginContext* context, const cell_t* params) {
return 0;
}
- area->SetParent((CNavArea*)PawnAddressToPtr(params[2]), (NavTraverseType)params[3]);
+ area->SetParent((CNavArea*)PawnAddressToPtr(params[2], context), (NavTraverseType)params[3]);
return 1;
}
@@ -229,7 +229,7 @@ cell_t GetParent(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(area->GetParent());
+ return PtrToPawnAddress(area->GetParent(), context);
}
cell_t GetParentHow(IPluginContext* context, const cell_t* params) {
@@ -304,7 +304,7 @@ cell_t ComputePortal(IPluginContext* context, const cell_t* params) {
return 0;
}
- CNavArea* other = (CNavArea*)PawnAddressToPtr(params[2]);
+ CNavArea* other = (CNavArea*)PawnAddressToPtr(params[2], context);
if (!other) {
return context->ThrowNativeError("Nav area is null !");
}
@@ -328,7 +328,7 @@ cell_t ComputeClosestPointInPortal(IPluginContext* context, const cell_t* params
return 0;
}
- CNavArea* other = (CNavArea*)PawnAddressToPtr(params[2]);
+ CNavArea* other = (CNavArea*)PawnAddressToPtr(params[2], context);
if (!other) {
return context->ThrowNativeError("Nav area is null !");
}
@@ -436,7 +436,7 @@ cell_t IsConnected(IPluginContext* context, const cell_t* params) {
return 0;
}
- return area->IsConnected((CNavArea*)PawnAddressToPtr(params[2]), (NavDirType)params[3]);
+ return area->IsConnected((CNavArea*)PawnAddressToPtr(params[2], context), (NavDirType)params[3]);
}
cell_t IsOverlappingPoint(IPluginContext* context, const cell_t* params) {
@@ -568,7 +568,7 @@ cell_t GetAdjacentArea(IPluginContext* context, const cell_t* params) {
if (dir < 0 || dir >= NUM_DIRECTIONS) {
return context->ThrowNativeError("Invalid direction %d", dir);
}
- return PtrToPawnAddress(area->GetAdjacentArea(dir, params[3]));
+ return PtrToPawnAddress(area->GetAdjacentArea(dir, params[3]), context);
}
cell_t GetAdjacentLength(IPluginContext* context, const cell_t* params) {
@@ -619,7 +619,7 @@ cell_t GetIncomingConnection(IPluginContext* context, const cell_t* params) {
if (i < 0 || i >= incoming->Count()) {
return 0;
}
- return PtrToPawnAddress(incoming->Element(i).area);
+ return PtrToPawnAddress(incoming->Element(i).area, context);
}
cell_t GetIncomingConnectionLength(IPluginContext* context, const cell_t* params) {
@@ -657,7 +657,7 @@ cell_t Contains(IPluginContext* context, const cell_t* params) {
return 0;
}
- return area->Contains((CNavArea*)PawnAddressToPtr(params[2]));
+ return area->Contains((CNavArea*)PawnAddressToPtr(params[2], context));
}
cell_t ContainsPoint(IPluginContext* context, const cell_t* params) {
@@ -769,7 +769,7 @@ cell_t GetHidingSpot(IPluginContext* context, const cell_t* params) {
if ((i < 0) || (i >= pSpots->Count())) {
return 0;
}
- return PtrToPawnAddress(pSpots->Element(i));
+ return PtrToPawnAddress(pSpots->Element(i), context);
}
cell_t IsOpen(IPluginContext* context, const cell_t* params) {
@@ -864,7 +864,7 @@ cell_t IsPotentiallyVisible(IPluginContext* context, const cell_t* params) {
return 0;
}
- CNavArea* viewedArea = (CNavArea*)PawnAddressToPtr(params[2]);
+ CNavArea* viewedArea = (CNavArea*)PawnAddressToPtr(params[2], context);
if (!viewedArea) {
return context->ThrowNativeError("Nav area is null !");
}
@@ -877,16 +877,16 @@ cell_t IsCompletelyVisible(IPluginContext* context, const cell_t* params) {
return 0;
}
- CNavArea* viewedArea = (CNavArea*)PawnAddressToPtr(params[2]);
+ CNavArea* viewedArea = (CNavArea*)PawnAddressToPtr(params[2], context);
if (!viewedArea) {
return context->ThrowNativeError("Nav area is null !");
}
return area->IsCompletelyVisible(viewedArea);
}
-cell_t native_GetHidingSpotByID(IPluginContext* pContext, const cell_t* params) {
+cell_t native_GetHidingSpotByID(IPluginContext* context, const cell_t* params) {
unsigned int id = params[1];
- return PtrToPawnAddress(GetHidingSpotByID(id));
+ return PtrToPawnAddress(GetHidingSpotByID(id), context);
}
void setup(std::vector& natives) {
diff --git a/extension/natives/nextbot.cpp b/extension/natives/nextbot.cpp
index 2c7b828..f49045a 100644
--- a/extension/natives/nextbot.cpp
+++ b/extension/natives/nextbot.cpp
@@ -15,7 +15,7 @@ namespace natives::nextbot {
template
inline T* Get(IPluginContext* context, const cell_t param) {
- T* bot = (T*)PawnAddressToPtr(param);
+ T* bot = (T*)PawnAddressToPtr(param, context);
if (!bot) {
context->ThrowNativeError("Bot is a null ptr!");
return nullptr;
@@ -79,7 +79,7 @@ cell_t GetLocomotionInterface(IPluginContext* context, const cell_t* params) {
if (!bot) {
return 0;
}
- return PtrToPawnAddress(bot->GetLocomotionInterface());
+ return PtrToPawnAddress(bot->GetLocomotionInterface(), context);
}
cell_t GetBodyInterface(IPluginContext* context, const cell_t* params) {
@@ -87,7 +87,7 @@ cell_t GetBodyInterface(IPluginContext* context, const cell_t* params) {
if (!bot) {
return 0;
}
- return PtrToPawnAddress(bot->GetBodyInterface());
+ return PtrToPawnAddress(bot->GetBodyInterface(), context);
}
cell_t GetIntentionInterface(IPluginContext* context, const cell_t* params) {
@@ -95,7 +95,7 @@ cell_t GetIntentionInterface(IPluginContext* context, const cell_t* params) {
if (!bot) {
return 0;
}
- return PtrToPawnAddress(bot->GetIntentionInterface());
+ return PtrToPawnAddress(bot->GetIntentionInterface(), context);
}
cell_t GetVisionInterface(IPluginContext* context, const cell_t* params) {
@@ -103,7 +103,7 @@ cell_t GetVisionInterface(IPluginContext* context, const cell_t* params) {
if (!bot) {
return 0;
}
- return PtrToPawnAddress(bot->GetVisionInterface());
+ return PtrToPawnAddress(bot->GetVisionInterface(), context);
}
cell_t SetPosition(IPluginContext* context, const cell_t* params) {
@@ -274,7 +274,7 @@ cell_t GetCurrentPath(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(bot->GetCurrentPath());
+ return PtrToPawnAddress(bot->GetCurrentPath(), context);
}
cell_t SetCurrentPath(IPluginContext* context, const cell_t* params) {
@@ -283,7 +283,7 @@ cell_t SetCurrentPath(IPluginContext* context, const cell_t* params) {
return 0;
}
- bot->SetCurrentPath((PathFollower*)PawnAddressToPtr(params[2]));
+ bot->SetCurrentPath((PathFollower*)PawnAddressToPtr(params[2], context));
return 0;
}
@@ -293,7 +293,7 @@ cell_t NotifyPathDestruction(IPluginContext* context, const cell_t* params) {
return 0;
}
- bot->NotifyPathDestruction((PathFollower*)PawnAddressToPtr(params[2]));
+ bot->NotifyPathDestruction((PathFollower*)PawnAddressToPtr(params[2], context));
return 0;
}
@@ -454,12 +454,12 @@ cell_t DisplayDebugText(IPluginContext* context, const cell_t* params) {
}
cell_t ToolsNextBot(IPluginContext* context, const cell_t* params) {
- CBaseCombatCharacter* entity = (CBaseCombatCharacter*)PawnAddressToPtr(params[1]);
+ CBaseCombatCharacter* entity = (CBaseCombatCharacter*)PawnAddressToPtr(params[1], context);
if (!entity) {
return context->ThrowNativeError("Invalid entity address %x", params[1]);
}
- return PtrToPawnAddress(new class ToolsNextBot(entity));
+ return PtrToPawnAddress(new class ToolsNextBot(entity), context);
}
void setup(std::vector& natives) {
diff --git a/extension/natives/nextbot/behavior.cpp b/extension/natives/nextbot/behavior.cpp
index 707dcc9..432239f 100644
--- a/extension/natives/nextbot/behavior.cpp
+++ b/extension/natives/nextbot/behavior.cpp
@@ -83,7 +83,7 @@ cell_t Create(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(factory->Create());
+ return PtrToPawnAddress(factory->Create(), context);
}
cell_t BeginDataMapDesc(IPluginContext* context, const cell_t* params) {
@@ -171,7 +171,7 @@ void setup(std::vector& natives) {
}
inline CBaseNPCPluginAction* Get(IPluginContext* context, const cell_t param) {
- CBaseNPCPluginAction* action = (CBaseNPCPluginAction*)PawnAddressToPtr(param);
+ CBaseNPCPluginAction* action = (CBaseNPCPluginAction*)PawnAddressToPtr(param, context);
if (!action) {
context->ThrowNativeError("CBaseNPCPluginAction ptr is null!");
return nullptr;
@@ -301,7 +301,7 @@ cell_t GetParent(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(action->GetParentAction());
+ return PtrToPawnAddress(action->GetParentAction(), context);
}
cell_t GetActiveChild(IPluginContext* context, const cell_t* params) {
@@ -310,7 +310,7 @@ cell_t GetActiveChild(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(action->GetActiveChildAction());
+ return PtrToPawnAddress(action->GetActiveChildAction(), context);
}
cell_t GetActionBuriedUnderMe(IPluginContext* context, const cell_t* params) {
@@ -319,7 +319,7 @@ cell_t GetActionBuriedUnderMe(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(action->GetActionBuriedUnderMe());
+ return PtrToPawnAddress(action->GetActionBuriedUnderMe(), context);
}
cell_t GetActionCoveringMe(IPluginContext* context, const cell_t* params) {
@@ -328,7 +328,7 @@ cell_t GetActionCoveringMe(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(action->GetActionCoveringMe());
+ return PtrToPawnAddress(action->GetActionCoveringMe(), context);
}
cell_t GetIsSuspended(IPluginContext* context, const cell_t* params) {
@@ -531,7 +531,7 @@ cell_t ChangeTo(IPluginContext* context, const cell_t* params) {
char* reason = nullptr;
context->LocalToStringNULL( params[3], &reason );
- action->PluginChangeTo( (CBaseNPCPluginAction*)PawnAddressToPtr(params[2]), reason );
+ action->PluginChangeTo( (CBaseNPCPluginAction*)PawnAddressToPtr(params[2], context), reason );
return 0;
}
@@ -547,7 +547,7 @@ cell_t SuspendFor(IPluginContext* context, const cell_t* params) {
char* reason = nullptr;
context->LocalToStringNULL( params[3], &reason );
- action->PluginSuspendFor( (CBaseNPCPluginAction*)PawnAddressToPtr(params[2]), reason );
+ action->PluginSuspendFor( (CBaseNPCPluginAction*)PawnAddressToPtr(params[2], context), reason );
return 0;
}
@@ -591,7 +591,7 @@ cell_t TryChangeTo(IPluginContext* context, const cell_t* params) {
return context->ThrowNativeError( "Cannot use TryChangeTo() outside of event callback" );
}
- CBaseNPCPluginAction* otherAction = (CBaseNPCPluginAction*)PawnAddressToPtr(params[2]);
+ CBaseNPCPluginAction* otherAction = (CBaseNPCPluginAction*)PawnAddressToPtr(params[2], context);
if (!otherAction) {
return context->ThrowNativeError("action is NULL");
}
@@ -613,7 +613,7 @@ cell_t TrySuspendFor(IPluginContext* context, const cell_t* params) {
return context->ThrowNativeError( "Cannot use TrySuspendFor() outside of event callback" );
}
- CBaseNPCPluginAction* otherAction = (CBaseNPCPluginAction*)PawnAddressToPtr(params[2]);
+ CBaseNPCPluginAction* otherAction = (CBaseNPCPluginAction*)PawnAddressToPtr(params[2], context);
if (!otherAction) {
return context->ThrowNativeError("action is NULL");
}
diff --git a/extension/natives/nextbot/body.cpp b/extension/natives/nextbot/body.cpp
index 284da73..00e9d19 100644
--- a/extension/natives/nextbot/body.cpp
+++ b/extension/natives/nextbot/body.cpp
@@ -5,7 +5,7 @@
namespace natives::nextbot::body {
inline IBody* Get(IPluginContext* context, const cell_t param) {
- IBody* body = (IBody*)PawnAddressToPtr(param);
+ IBody* body = (IBody*)PawnAddressToPtr(param, context);
if (!body) {
context->ThrowNativeError("Body ptr is null!");
return nullptr;
diff --git a/extension/natives/nextbot/component.cpp b/extension/natives/nextbot/component.cpp
index 36493f6..0eb0feb 100644
--- a/extension/natives/nextbot/component.cpp
+++ b/extension/natives/nextbot/component.cpp
@@ -3,7 +3,7 @@
namespace natives::nextbot::component {
inline INextBotComponent* Get(IPluginContext* context, const cell_t param) {
- INextBotComponent* component = (INextBotComponent*)PawnAddressToPtr(param);
+ INextBotComponent* component = (INextBotComponent*)PawnAddressToPtr(param, context);
if (!component) {
context->ThrowNativeError("Component is a null ptr!");
return nullptr;
@@ -48,7 +48,7 @@ cell_t GetBot(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(component->GetBot());
+ return PtrToPawnAddress(component->GetBot(), context);
}
void setup(std::vector& natives) {
diff --git a/extension/natives/nextbot/eventresponder.cpp b/extension/natives/nextbot/eventresponder.cpp
index c1bd644..4bb4878 100644
--- a/extension/natives/nextbot/eventresponder.cpp
+++ b/extension/natives/nextbot/eventresponder.cpp
@@ -6,7 +6,7 @@
namespace natives::nextbot::eventresponder {
inline INextBotEventResponder* Get(IPluginContext* context, const cell_t param) {
- INextBotEventResponder* responder = (INextBotEventResponder*)PawnAddressToPtr(param);
+ INextBotEventResponder* responder = (INextBotEventResponder*)PawnAddressToPtr(param, context);
if (!responder) {
context->ThrowNativeError("Event responder ptr is null!");
return nullptr;
@@ -20,7 +20,7 @@ cell_t FirstContainedResponder(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(responder->FirstContainedResponder());
+ return PtrToPawnAddress(responder->FirstContainedResponder(), context);
}
cell_t NextContainedResponder(IPluginContext* context, const cell_t* params) {
@@ -33,7 +33,7 @@ cell_t NextContainedResponder(IPluginContext* context, const cell_t* params) {
if (!responder2) {
return 0;
}
- return PtrToPawnAddress(responder->NextContainedResponder(responder2));
+ return PtrToPawnAddress(responder->NextContainedResponder(responder2), context);
}
cell_t OnLeaveGround(IPluginContext* context, const cell_t* params) {
@@ -74,7 +74,7 @@ cell_t OnMoveToSuccess(IPluginContext* context, const cell_t* params) {
return 0;
}
- Path* path = (Path*)PawnAddressToPtr(params[2]);
+ Path* path = (Path*)PawnAddressToPtr(params[2], context);
if (!path) {
return context->ThrowNativeError("Path is null!");
}
@@ -89,7 +89,7 @@ cell_t OnMoveToFailure(IPluginContext* context, const cell_t* params) {
return 0;
}
- Path* path = (Path*)PawnAddressToPtr(params[2]);
+ Path* path = (Path*)PawnAddressToPtr(params[2], context);
if (!path) {
return context->ThrowNativeError("Path is null!");
}
@@ -231,7 +231,7 @@ cell_t OnNavAreaChanged(IPluginContext* context, const cell_t* params) {
return 0;
}
- responder->OnNavAreaChanged((CNavArea*)PawnAddressToPtr(params[2]), (CNavArea*)PawnAddressToPtr(params[3]));
+ responder->OnNavAreaChanged((CNavArea*)PawnAddressToPtr(params[2], context), (CNavArea*)PawnAddressToPtr(params[3], context));
return 0;
}
diff --git a/extension/natives/nextbot/intention.cpp b/extension/natives/nextbot/intention.cpp
index 989c6d6..45ddd15 100644
--- a/extension/natives/nextbot/intention.cpp
+++ b/extension/natives/nextbot/intention.cpp
@@ -6,7 +6,7 @@
namespace natives::nextbot::intention {
inline IIntention* Get(IPluginContext* context, const cell_t param) {
- IIntention* intention = (IIntention*)PawnAddressToPtr(param);
+ IIntention* intention = (IIntention*)PawnAddressToPtr(param, context);
if (!intention) {
context->ThrowNativeError("Intention ptr is null!");
return nullptr;
@@ -67,7 +67,7 @@ cell_t ShouldAttack(IPluginContext* context, const cell_t* params) {
return 0;
}
- CKnownEntity* them = reinterpret_cast< CKnownEntity* >( PawnAddressToPtr(params[2]) );
+ CKnownEntity* them = reinterpret_cast< CKnownEntity* >( PawnAddressToPtr(params[2], context) );
if (!them) {
return context->ThrowNativeError("them entity is a null ptr!");
}
@@ -171,12 +171,12 @@ cell_t SelectMoreDangerousThreat(IPluginContext* context, const cell_t* params)
return context->ThrowNativeError( "Subject entity is not a CBaseCombatCharacter.");
}
- CKnownEntity* threat1 = reinterpret_cast< CKnownEntity* >( PawnAddressToPtr(params[3]) );
+ CKnownEntity* threat1 = reinterpret_cast< CKnownEntity* >( PawnAddressToPtr(params[3], context) );
if (!threat1) {
return context->ThrowNativeError("threat1 entity cannot be a null ptr!");
}
- CKnownEntity* threat2 = reinterpret_cast< CKnownEntity* >( PawnAddressToPtr(params[4]) );
+ CKnownEntity* threat2 = reinterpret_cast< CKnownEntity* >( PawnAddressToPtr(params[4], context) );
if (!threat2) {
return context->ThrowNativeError("threat2 entity cannot be a null ptr!");
}
@@ -186,7 +186,7 @@ cell_t SelectMoreDangerousThreat(IPluginContext* context, const cell_t* params)
return context->ThrowNativeError("GetBot returned null!");
}
- return PtrToPawnAddress(intention->SelectMoreDangerousThreat(me, subject, threat1, threat2));
+ return PtrToPawnAddress(intention->SelectMoreDangerousThreat(me, subject, threat1, threat2), context);
}
void setup(std::vector& natives) {
diff --git a/extension/natives/nextbot/knownentity.cpp b/extension/natives/nextbot/knownentity.cpp
index 4ae8598..dab6a7e 100644
--- a/extension/natives/nextbot/knownentity.cpp
+++ b/extension/natives/nextbot/knownentity.cpp
@@ -5,7 +5,7 @@
namespace natives::nextbot::knownentity {
inline CKnownEntity* Get(IPluginContext* context, const cell_t param) {
- CKnownEntity* entity = (CKnownEntity*)PawnAddressToPtr(param);
+ CKnownEntity* entity = (CKnownEntity*)PawnAddressToPtr(param, context);
if (!entity) {
context->ThrowNativeError("Known entity ptr is null!");
return nullptr;
@@ -81,7 +81,7 @@ cell_t GetLastKnownArea(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(entity->GetLastKnownArea());
+ return PtrToPawnAddress(entity->GetLastKnownArea(), context);
}
cell_t GetTimeSinceLastKnown(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/nextbot/locomotion.cpp b/extension/natives/nextbot/locomotion.cpp
index f389a97..be11536 100644
--- a/extension/natives/nextbot/locomotion.cpp
+++ b/extension/natives/nextbot/locomotion.cpp
@@ -6,7 +6,7 @@
namespace natives::nextbot::locomotion {
inline ILocomotion* Get(IPluginContext* context, const cell_t param) {
- ILocomotion* mover = (ILocomotion*)PawnAddressToPtr(param);
+ ILocomotion* mover = (ILocomotion*)PawnAddressToPtr(param, context);
if (!mover) {
context->ThrowNativeError("Locomotion ptr is null!");
return nullptr;
@@ -263,7 +263,7 @@ cell_t ClimbLadder(IPluginContext* context, const cell_t* params) {
return 0;
}
- mover->ClimbLadder((CNavLadder*)PawnAddressToPtr(params[2]), (CNavArea*)PawnAddressToPtr(params[3]));
+ mover->ClimbLadder((CNavLadder*)PawnAddressToPtr(params[2], context), (CNavArea*)PawnAddressToPtr(params[3], context));
return 0;
}
@@ -273,7 +273,7 @@ cell_t DescendLadder(IPluginContext* context, const cell_t* params) {
return 0;
}
- mover->DescendLadder((CNavLadder*)PawnAddressToPtr(params[2]), (CNavArea*)PawnAddressToPtr(params[3]));
+ mover->DescendLadder((CNavLadder*)PawnAddressToPtr(params[2], context), (CNavArea*)PawnAddressToPtr(params[3], context));
return 0;
}
@@ -480,7 +480,7 @@ cell_t IsAreaTraversable(IPluginContext* context, const cell_t* params) {
return 0;
}
- return (mover->IsAreaTraversable((CNavArea *)PawnAddressToPtr(params[2])) == true) ? 1 : 0;
+ return (mover->IsAreaTraversable((CNavArea *)PawnAddressToPtr(params[2], context)) == true) ? 1 : 0;
}
cell_t GetTraversableSlopeLimit(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/nextbot/locomotion/ground.cpp b/extension/natives/nextbot/locomotion/ground.cpp
index 07e9198..1818ae4 100644
--- a/extension/natives/nextbot/locomotion/ground.cpp
+++ b/extension/natives/nextbot/locomotion/ground.cpp
@@ -5,7 +5,7 @@
namespace natives::nextbot::locomotion::ground {
inline NextBotGroundLocomotion* Get(IPluginContext* context, const cell_t param) {
- NextBotGroundLocomotion* mover = (NextBotGroundLocomotion*)PawnAddressToPtr(param);
+ NextBotGroundLocomotion* mover = (NextBotGroundLocomotion*)PawnAddressToPtr(param, context);
if (!mover) {
context->ThrowNativeError("NextBotGroundLocomotion ptr is null!");
return nullptr;
diff --git a/extension/natives/nextbot/path.cpp b/extension/natives/nextbot/path.cpp
index 0d3d3d6..865aa90 100644
--- a/extension/natives/nextbot/path.cpp
+++ b/extension/natives/nextbot/path.cpp
@@ -44,13 +44,24 @@ float SMPathFollowerCost::operator()(CNavArea* area, CNavArea* fromArea, const C
}
cell_t cost = sp_ftoc(0.0);
- m_pFunc->PushCell(PtrToPawnAddress(m_bot));
- m_pFunc->PushCell(PtrToPawnAddress(area));
- m_pFunc->PushCell(PtrToPawnAddress(fromArea));
- m_pFunc->PushCell(PtrToPawnAddress(ladder));
+
+ Handle_t hndlBot = PtrToPawnAddress(m_bot, nullptr);
+ Handle_t hndlArea = PtrToPawnAddress(area, nullptr);
+ Handle_t hndlfromArea = PtrToPawnAddress(fromArea, nullptr);
+ Handle_t hndlladder = PtrToPawnAddress(ladder, nullptr);
+
+ m_pFunc->PushCell(hndlBot);
+ m_pFunc->PushCell(hndlArea);
+ m_pFunc->PushCell(hndlfromArea);
+ m_pFunc->PushCell(hndlladder);
m_pFunc->PushCell(gamehelpers->EntityToBCompatRef((CBaseEntity *)elevator));
m_pFunc->PushFloat(length);
m_pFunc->Execute(&cost);
+
+ ReleasePawnAddress(hndlBot, nullptr);
+ ReleasePawnAddress(hndlArea, nullptr);
+ ReleasePawnAddress(hndlfromArea, nullptr);
+ ReleasePawnAddress(hndlladder, nullptr);
return sp_ctof(cost);
}
@@ -58,7 +69,7 @@ float SMPathFollowerCost::operator()(CNavArea* area, CNavArea* fromArea, const C
template
inline T* Get(IPluginContext* context, const cell_t param) {
- T* bot = (T*)PawnAddressToPtr(param);
+ T* bot = (T*)PawnAddressToPtr(param, context);
if (!bot) {
context->ThrowNativeError("Object is a null ptr!");
return nullptr;
@@ -74,7 +85,7 @@ cell_t GetArea(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(seg->area);
+ return PtrToPawnAddress(seg->area, context);
}
cell_t GetHow(IPluginContext* context, const cell_t* params) {
@@ -104,7 +115,7 @@ cell_t GetLadder(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(seg->ladder);
+ return PtrToPawnAddress(seg->ladder, context);
}
cell_t GetType(IPluginContext* context, const cell_t* params) {
@@ -246,7 +257,7 @@ cell_t GetSegmentPrior(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(cursor->segmentPrior);
+ return PtrToPawnAddress(cursor->segmentPrior, context);
}
void setup(std::vector& natives) {
@@ -276,7 +287,7 @@ cell_t PathCtor(IPluginContext* context, const cell_t* params) {
path->pTraceFilterIgnoreActors = pTraceFilter;
path->pTraceFilterOnlyActors = pTraceFilter2;
- return PtrToPawnAddress(path);
+ return PtrToPawnAddress(path, context);
}
cell_t GetLength(IPluginContext* context, const cell_t* params) {
@@ -297,7 +308,7 @@ cell_t GetPosition(IPluginContext* context, const cell_t* params) {
float dist = sp_ctof(params[2]);
cell_t* addr;
context->LocalToPhysAddr(params[3], &addr);
- Path::Segment* segment = (Path::Segment*)PawnAddressToPtr(params[4]);
+ Path::Segment* segment = (Path::Segment*)PawnAddressToPtr(params[4], context);
Vector pos = path->GetPosition(dist, segment);
VectorToPawnVector(addr, pos);
@@ -310,8 +321,8 @@ cell_t Copy(IPluginContext* context, const cell_t* params) {
return 0;
}
- INextBot* bot = (INextBot*)PawnAddressToPtr(params[2]);
- Path* path2 = (Path*)PawnAddressToPtr(params[3]);
+ INextBot* bot = (INextBot*)PawnAddressToPtr(params[2], context);
+ Path* path2 = (Path*)PawnAddressToPtr(params[3], context);
path->Copy(bot, *path2);
return 0;
@@ -329,7 +340,7 @@ cell_t GetClosestPosition(IPluginContext* context, const cell_t* params) {
PawnVectorToVector(nearAddr, vecNear);
cell_t* posAddr;
context->LocalToPhysAddr(params[3], &posAddr);
- Path::Segment* segment = (Path::Segment*)PawnAddressToPtr(params[4]);
+ Path::Segment* segment = (Path::Segment*)PawnAddressToPtr(params[4], context);
float alongLimit = sp_ctof(params[5]);
Vector pos = path->GetClosestPosition(vecNear, segment, alongLimit);
@@ -379,7 +390,7 @@ cell_t GetCurrentGoal(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(path->GetCurrentGoal());
+ return PtrToPawnAddress(path->GetCurrentGoal(), context);
}
cell_t GetAge(IPluginContext* context, const cell_t* params) {
@@ -450,7 +461,7 @@ cell_t GetCursorData(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(&path->GetCursorData());
+ return PtrToPawnAddress(&path->GetCursorData(), context);
}
cell_t IsValid(IPluginContext* context, const cell_t* params) {
@@ -478,7 +489,7 @@ cell_t Draw(IPluginContext* context, const cell_t* params) {
return 0;
}
- Path::Segment* segment = (Path::Segment*)PawnAddressToPtr(params[2]);
+ Path::Segment* segment = (Path::Segment*)PawnAddressToPtr(params[2], context);
path->Draw(segment);
return 0;
}
@@ -499,7 +510,7 @@ cell_t FirstSegment(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(path->FirstSegment());
+ return PtrToPawnAddress(path->FirstSegment(), context);
}
cell_t NextSegment(IPluginContext* context, const cell_t* params) {
@@ -513,7 +524,7 @@ cell_t NextSegment(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(path->NextSegment(segment));
+ return PtrToPawnAddress(path->NextSegment(segment), context);
}
cell_t PriorSegment(IPluginContext* context, const cell_t* params) {
@@ -527,7 +538,7 @@ cell_t PriorSegment(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(path->PriorSegment(segment));
+ return PtrToPawnAddress(path->PriorSegment(segment), context);
}
cell_t LastSegment(IPluginContext* context, const cell_t* params) {
@@ -536,7 +547,7 @@ cell_t LastSegment(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(path->LastSegment());
+ return PtrToPawnAddress(path->LastSegment(), context);
}
cell_t ComputeToPos(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/nextbot/path/chase.cpp b/extension/natives/nextbot/path/chase.cpp
index ad4e5e1..eee592f 100644
--- a/extension/natives/nextbot/path/chase.cpp
+++ b/extension/natives/nextbot/path/chase.cpp
@@ -6,7 +6,7 @@ namespace natives::nextbot::path::chase {
template
inline T* Get(IPluginContext* context, const cell_t param) {
- T* bot = (T*)PawnAddressToPtr(param);
+ T* bot = (T*)PawnAddressToPtr(param, context);
if (!bot) {
context->ThrowNativeError("Object is a null ptr!");
return nullptr;
@@ -26,7 +26,7 @@ cell_t ChasePathCtor(IPluginContext* context, const cell_t* params) {
path->pTraceFilterIgnoreActors = pTraceFilter;
path->pTraceFilterOnlyActors = pTraceFilter2;
- return PtrToPawnAddress(path);
+ return PtrToPawnAddress(path, context);
}
cell_t Update(IPluginContext* context, const cell_t* params) {
@@ -144,7 +144,7 @@ cell_t DirectChasePathCtor(IPluginContext* context, const cell_t* params) {
path->pTraceFilterIgnoreActors = pTraceFilter;
path->pTraceFilterOnlyActors = pTraceFilter2;
- return PtrToPawnAddress(path);
+ return PtrToPawnAddress(path, context);
}
void setup(std::vector& natives) {
diff --git a/extension/natives/nextbot/path/follower.cpp b/extension/natives/nextbot/path/follower.cpp
index 817599a..4e2b57b 100644
--- a/extension/natives/nextbot/path/follower.cpp
+++ b/extension/natives/nextbot/path/follower.cpp
@@ -7,7 +7,7 @@ namespace natives::nextbot::path::follower {
template
inline T* Get(IPluginContext* context, const cell_t param) {
- T* bot = (T*)PawnAddressToPtr(param);
+ T* bot = (T*)PawnAddressToPtr(param, context);
if (!bot) {
context->ThrowNativeError("Object is a null ptr!");
return nullptr;
@@ -26,7 +26,7 @@ cell_t PathFollowerCtor(IPluginContext* context, const cell_t* params) {
path->pTraceFilterIgnoreActors = pTraceFilter;
path->pTraceFilterOnlyActors = pTraceFilter2;
- return PtrToPawnAddress(path);
+ return PtrToPawnAddress(path, context);
}
cell_t Update(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/nextbot/vision.cpp b/extension/natives/nextbot/vision.cpp
index 4919df3..5e841bc 100644
--- a/extension/natives/nextbot/vision.cpp
+++ b/extension/natives/nextbot/vision.cpp
@@ -6,7 +6,7 @@
namespace natives::nextbot::vision {
inline IVision* Get(IPluginContext* context, const cell_t param) {
- IVision* vision = (IVision*)PawnAddressToPtr(param);
+ IVision* vision = (IVision*)PawnAddressToPtr(param, context);
if (!vision) {
context->ThrowNativeError("Vision ptr is null!");
return nullptr;
@@ -20,7 +20,7 @@ cell_t GetPrimaryKnownThreat(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(vision->GetPrimaryKnownThreat((params[2]) ? true : false));
+ return PtrToPawnAddress(vision->GetPrimaryKnownThreat((params[2]) ? true : false), context);
}
cell_t GetTimeSinceVisible(IPluginContext* context, const cell_t* params) {
@@ -38,7 +38,7 @@ cell_t GetClosestKnown(IPluginContext* context, const cell_t* params) {
return 0;
}
- return PtrToPawnAddress(vision->GetClosestKnown(params[2]));
+ return PtrToPawnAddress(vision->GetClosestKnown(params[2]), context);
}
cell_t GetKnownCount(IPluginContext* context, const cell_t* params) {
@@ -60,7 +60,7 @@ cell_t GetKnown(IPluginContext* context, const cell_t* params) {
if (!entity) {
return context->ThrowNativeError("Invalid Entity Reference/Index %i", params[2]);
}
- return PtrToPawnAddress(vision->GetKnown(entity));
+ return PtrToPawnAddress(vision->GetKnown(entity), context);
}
cell_t AddKnownEntity(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/nextbotplayer.cpp b/extension/natives/nextbotplayer.cpp
index 40e9195..64105e1 100644
--- a/extension/natives/nextbotplayer.cpp
+++ b/extension/natives/nextbotplayer.cpp
@@ -7,7 +7,7 @@ namespace natives::nextbotplayer {
template
inline T* Get(IPluginContext* context, const cell_t param) {
- T* bot = (T*)PawnAddressToPtr(param);
+ T* bot = (T*)PawnAddressToPtr(param, context);
if (!bot) {
context->ThrowNativeError("Botplayer is a null ptr!");
return nullptr;
@@ -16,12 +16,12 @@ inline T* Get(IPluginContext* context, const cell_t param) {
}
cell_t ToolsNextBotPlayer(IPluginContext* context, const cell_t* params) {
- CBaseCombatCharacter* entity = (CBaseCombatCharacter*)PawnAddressToPtr(params[1]);
+ CBaseCombatCharacter* entity = (CBaseCombatCharacter*)PawnAddressToPtr(params[1], context);
if (!entity) {
return context->ThrowNativeError("Invalid entity address %x", params[1]);
}
- return PtrToPawnAddress(new class ToolsNextBotPlayer(entity));
+ return PtrToPawnAddress(new class ToolsNextBotPlayer(entity), context);
}
cell_t SetIsDormantWhenDead(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/takedamageinfo.cpp b/extension/natives/takedamageinfo.cpp
index b4615d4..2d920d5 100644
--- a/extension/natives/takedamageinfo.cpp
+++ b/extension/natives/takedamageinfo.cpp
@@ -18,7 +18,7 @@ namespace natives::takedamageinfo {
CTakeDamageInfo g_GlobalDamageInfo;
inline CTakeDamageInfo* Get(IPluginContext* context, const cell_t param) {
- CTakeDamageInfo* info = (CTakeDamageInfo*)PawnAddressToPtr(param);
+ CTakeDamageInfo* info = (CTakeDamageInfo*)PawnAddressToPtr(param, context);
if (!info) {
context->ThrowNativeError("CTakeDamageInfo is a null ptr!");
return nullptr;
@@ -27,11 +27,15 @@ inline CTakeDamageInfo* Get(IPluginContext* context, const cell_t param) {
}
cell_t CTakeDamageInfo_Ctor(IPluginContext* context, const cell_t* params) {
- return PtrToPawnAddress(PawnAddressToPtr(params[1]));
+ return PtrToPawnAddress(PawnAddressToPtr(params[1], context), context);
}
cell_t GetGlobalDamageInfo(IPluginContext* context, const cell_t* params) {
- return PtrToPawnAddress(&g_GlobalDamageInfo);
+ static Handle_t globalDmg = BAD_HANDLE;
+ if (globalDmg == BAD_HANDLE) {
+ globalDmg = PtrToPawnAddress(&g_GlobalDamageInfo, nullptr, true);
+ }
+ return globalDmg;
}
cell_t Init(IPluginContext* context, const cell_t* params) {
diff --git a/extension/natives/tf/nav/area.cpp b/extension/natives/tf/nav/area.cpp
index b06b1fe..ca05452 100644
--- a/extension/natives/tf/nav/area.cpp
+++ b/extension/natives/tf/nav/area.cpp
@@ -5,7 +5,7 @@
namespace natives::tf::nav::area {
inline CTFNavArea* Get(IPluginContext* context, const cell_t param) {
- CTFNavArea* area = (CTFNavArea*)PawnAddressToPtr(param);
+ CTFNavArea* area = (CTFNavArea*)PawnAddressToPtr(param, context);
if (!area) {
context->ThrowNativeError("TFNav area ptr is null!");
return nullptr;
diff --git a/extension/pluginentityfactory.cpp b/extension/pluginentityfactory.cpp
index caad1df..12b411c 100644
--- a/extension/pluginentityfactory.cpp
+++ b/extension/pluginentityfactory.cpp
@@ -117,7 +117,7 @@ PluginFactoryEntityRecord_t* CPluginEntityFactories::FindRecord(CBaseEntity* pEn
return nullptr;
}
- cell_t key = (cell_t)pEntity;
+ intp key = (intp)pEntity;
if (m_Records.find(key) == m_Records.end())
{
if (create)
@@ -140,7 +140,7 @@ void CPluginEntityFactories::RemoveRecord(CBaseEntity* pEntity)
return;
}
- cell_t key = (cell_t)pEntity;
+ intp key = (intp)pEntity;
m_Records.erase(key);
}
@@ -981,20 +981,20 @@ IServerNetworkable* CPluginEntityFactory::RecursiveCreate(const char* classname,
if (nextBotFactory && pEnt->MyCombatCharacterPointer() && !pEnt->MyNextBotPointer())
{
INextBot* createdBot = nullptr;
- if (nextBotFactory != (IPluginFunction*)0x1)
+ if (nextBotFactory->IsRunnable())
{
- if (nextBotFactory->IsRunnable())
- {
- nextBotFactory->PushCell(PtrToPawnAddress(pEnt));
- cell_t address = 0;
- nextBotFactory->Execute(&address);
- createdBot = (INextBot*)PawnAddressToPtr(address);
+ Handle_t hndlEnt = PtrToPawnAddress(pEnt, nullptr);
+
+ nextBotFactory->PushCell(hndlEnt);
+ Handle_t hndlBot = BAD_HANDLE;
+ nextBotFactory->Execute((cell_t*)&hndlBot);
+
+ ReleasePawnAddress(hndlEnt, nullptr);
+
+ if (hndlBot != BAD_HANDLE) {
+ createdBot = (INextBot*)PawnAddressToPtr(hndlBot, nullptr);
}
}
- else
- {
- createdBot = new ToolsNextBot(pEnt->MyCombatCharacterPointer());
- }
pEntityRecord->m_pNextBot = createdBot;
}
diff --git a/extension/pluginentityfactory.h b/extension/pluginentityfactory.h
index 33d8562..80ae25b 100644
--- a/extension/pluginentityfactory.h
+++ b/extension/pluginentityfactory.h
@@ -119,7 +119,7 @@ class CPluginEntityFactories : public IPluginsListener,
size_t m_BaseClassSizes[ FACTORYBASECLASS_MAX ];
CUtlVector< CPluginEntityFactory* > m_Factories;
- std::map> m_Records;
+ std::map> m_Records;
std::map m_gameFactories;
std::map m_pluginFactories;
std::vector m_hookIds;
diff --git a/extension/smsdk_ext.cpp b/extension/smsdk_ext.cpp
deleted file mode 100644
index 496ec6a..0000000
--- a/extension/smsdk_ext.cpp
+++ /dev/null
@@ -1,475 +0,0 @@
-/**
- * vim: set ts=4 sw=4 tw=99 noet:
- * =============================================================================
- * SourceMod Base Extension Code
- * Copyright (C) 2004-2008 AlliedModders LLC. All rights reserved.
- * =============================================================================
- *
- * This program is free software; you can redistribute it and/or modify it under
- * the terms of the GNU General Public License, version 3.0, as published by the
- * Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
- * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
- * details.
- *
- * You should have received a copy of the GNU General Public License along with
- * this program. If not, see .
- *
- * As a special exception, AlliedModders LLC gives you permission to link the
- * code of this program (as well as its derivative works) to "Half-Life 2," the
- * "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software
- * by the Valve Corporation. You must obey the GNU General Public License in
- * all respects for all other code used. Additionally, AlliedModders LLC grants
- * this exception to all derivative works. AlliedModders LLC defines further
- * exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007),
- * or .
- *
- * Version: $Id$
- */
-
-#include
-#include
-#include "smsdk_ext.h"
-#include "am-string.h"
-
-/**
- * @file smsdk_ext.cpp
- * @brief Contains wrappers for making Extensions easier to write.
- */
-
-IExtension *myself = NULL; /**< Ourself */
-IShareSys *g_pShareSys = NULL; /**< Share system */
-IShareSys *sharesys = NULL; /**< Share system */
-ISourceMod *g_pSM = NULL; /**< SourceMod helpers */
-ISourceMod *smutils = NULL; /**< SourceMod helpers */
-
-#if defined SMEXT_ENABLE_FORWARDSYS
-IForwardManager *g_pForwards = NULL; /**< Forward system */
-IForwardManager *forwards = NULL; /**< Forward system */
-#endif
-#if defined SMEXT_ENABLE_HANDLESYS
-IHandleSys *g_pHandleSys = NULL; /**< Handle system */
-IHandleSys *handlesys = NULL; /**< Handle system */
-#endif
-#if defined SMEXT_ENABLE_PLAYERHELPERS
-IPlayerManager *playerhelpers = NULL; /**< Player helpers */
-#endif //SMEXT_ENABLE_PLAYERHELPERS
-#if defined SMEXT_ENABLE_DBMANAGER
-IDBManager *dbi = NULL; /**< DB Manager */
-#endif //SMEXT_ENABLE_DBMANAGER
-#if defined SMEXT_ENABLE_GAMECONF
-IGameConfigManager *gameconfs = NULL; /**< Game config manager */
-#endif //SMEXT_ENABLE_DBMANAGER
-#if defined SMEXT_ENABLE_MEMUTILS
-IMemoryUtils *memutils = NULL;
-#endif //SMEXT_ENABLE_DBMANAGER
-#if defined SMEXT_ENABLE_GAMEHELPERS
-IGameHelpers *gamehelpers = NULL;
-#endif
-#if defined SMEXT_ENABLE_TIMERSYS
-ITimerSystem *timersys = NULL;
-#endif
-#if defined SMEXT_ENABLE_ADTFACTORY
-IADTFactory *adtfactory = NULL;
-#endif
-#if defined SMEXT_ENABLE_THREADER
-IThreader *threader = NULL;
-#endif
-#if defined SMEXT_ENABLE_LIBSYS
-ILibrarySys *libsys = NULL;
-#endif
-#if defined SMEXT_ENABLE_PLUGINSYS
-SourceMod::IPluginManager *plsys;
-#endif
-#if defined SMEXT_ENABLE_MENUS
-IMenuManager *menus = NULL;
-#endif
-#if defined SMEXT_ENABLE_ADMINSYS
-IAdminSystem *adminsys = NULL;
-#endif
-#if defined SMEXT_ENABLE_TEXTPARSERS
-ITextParsers *textparsers = NULL;
-#endif
-#if defined SMEXT_ENABLE_USERMSGS
-IUserMessages *usermsgs = NULL;
-#endif
-#if defined SMEXT_ENABLE_TRANSLATOR
-ITranslator *translator = NULL;
-#endif
-#if defined SMEXT_ENABLE_ROOTCONSOLEMENU
-IRootConsole *rootconsole = NULL;
-#endif
-
-/** Exports the main interface */
-PLATFORM_EXTERN_C IExtensionInterface *GetSMExtAPI()
-{
- return g_pExtensionIface;
-}
-
-SDKExtension::SDKExtension()
-{
-#if defined SMEXT_CONF_METAMOD
- m_SourceMMLoaded = false;
- m_WeAreUnloaded = false;
- m_WeGotPauseChange = false;
-#endif
-}
-
-bool SDKExtension::OnExtensionLoad(IExtension *me, IShareSys *sys, char *error, size_t maxlength, bool late)
-{
- g_pShareSys = sharesys = sys;
- myself = me;
-
-#if defined SMEXT_CONF_METAMOD
- m_WeAreUnloaded = true;
-
- if (!m_SourceMMLoaded)
- {
- if (error)
- {
- ke::SafeStrcpy(error, maxlength, "Metamod attach failed");
- }
- return false;
- }
-#endif
- SM_GET_IFACE(SOURCEMOD, g_pSM);
- smutils = g_pSM;
-#if defined SMEXT_ENABLE_HANDLESYS
- SM_GET_IFACE(HANDLESYSTEM, g_pHandleSys);
- handlesys = g_pHandleSys;
-#endif
-#if defined SMEXT_ENABLE_FORWARDSYS
- SM_GET_IFACE(FORWARDMANAGER, g_pForwards);
- forwards = g_pForwards;
-#endif
-#if defined SMEXT_ENABLE_PLAYERHELPERS
- SM_GET_IFACE(PLAYERMANAGER, playerhelpers);
-#endif
-#if defined SMEXT_ENABLE_DBMANAGER
- SM_GET_IFACE(DBI, dbi);
-#endif
-#if defined SMEXT_ENABLE_GAMECONF
- SM_GET_IFACE(GAMECONFIG, gameconfs);
-#endif
-#if defined SMEXT_ENABLE_MEMUTILS
- SM_GET_IFACE(MEMORYUTILS, memutils);
-#endif
-#if defined SMEXT_ENABLE_GAMEHELPERS
- SM_GET_IFACE(GAMEHELPERS, gamehelpers);
-#endif
-#if defined SMEXT_ENABLE_TIMERSYS
- SM_GET_IFACE(TIMERSYS, timersys);
-#endif
-#if defined SMEXT_ENABLE_ADTFACTORY
- SM_GET_IFACE(ADTFACTORY, adtfactory);
-#endif
-#if defined SMEXT_ENABLE_THREADER
- SM_GET_IFACE(THREADER, threader);
-#endif
-#if defined SMEXT_ENABLE_LIBSYS
- SM_GET_IFACE(LIBRARYSYS, libsys);
-#endif
-#if defined SMEXT_ENABLE_PLUGINSYS
- SM_GET_IFACE(PLUGINSYSTEM, plsys);
-#endif
-#if defined SMEXT_ENABLE_MENUS
- SM_GET_IFACE(MENUMANAGER, menus);
-#endif
-#if defined SMEXT_ENABLE_ADMINSYS
- SM_GET_IFACE(ADMINSYS, adminsys);
-#endif
-#if defined SMEXT_ENABLE_TEXTPARSERS
- SM_GET_IFACE(TEXTPARSERS, textparsers);
-#endif
-#if defined SMEXT_ENABLE_USERMSGS
- SM_GET_IFACE(USERMSGS, usermsgs);
-#endif
-#if defined SMEXT_ENABLE_TRANSLATOR
- SM_GET_IFACE(TRANSLATOR, translator);
-#endif
-#if defined SMEXT_ENABLE_ROOTCONSOLEMENU
- SM_GET_IFACE(ROOTCONSOLE, rootconsole);
-#endif
-
- if (SDK_OnLoad(error, maxlength, late))
- {
-#if defined SMEXT_CONF_METAMOD
- m_WeAreUnloaded = true;
-#endif
- return true;
- }
-
- return false;
-}
-
-bool SDKExtension::IsMetamodExtension()
-{
-#if defined SMEXT_CONF_METAMOD
- return true;
-#else
- return false;
-#endif
-}
-
-void SDKExtension::OnExtensionPauseChange(bool state)
-{
-#if defined SMEXT_CONF_METAMOD
- m_WeGotPauseChange = true;
-#endif
- SDK_OnPauseChange(state);
-}
-
-void SDKExtension::OnExtensionsAllLoaded()
-{
- SDK_OnAllLoaded();
-}
-
-void SDKExtension::OnExtensionUnload()
-{
-#if defined SMEXT_CONF_METAMOD
- m_WeAreUnloaded = true;
-#endif
- SDK_OnUnload();
-}
-
-void SDKExtension::OnDependenciesDropped()
-{
- SDK_OnDependenciesDropped();
-}
-
-const char *SDKExtension::GetExtensionAuthor()
-{
- return SMEXT_CONF_AUTHOR;
-}
-
-const char *SDKExtension::GetExtensionDateString()
-{
- return SMEXT_CONF_DATESTRING;
-}
-
-const char *SDKExtension::GetExtensionDescription()
-{
- return SMEXT_CONF_DESCRIPTION;
-}
-
-const char *SDKExtension::GetExtensionVerString()
-{
- return SMEXT_CONF_VERSION;
-}
-
-const char *SDKExtension::GetExtensionName()
-{
- return SMEXT_CONF_NAME;
-}
-
-const char *SDKExtension::GetExtensionTag()
-{
- return SMEXT_CONF_LOGTAG;
-}
-
-const char *SDKExtension::GetExtensionURL()
-{
- return SMEXT_CONF_URL;
-}
-
-bool SDKExtension::SDK_OnLoad(char *error, size_t maxlength, bool late)
-{
- return true;
-}
-
-void SDKExtension::SDK_OnUnload()
-{
-}
-
-void SDKExtension::SDK_OnPauseChange(bool paused)
-{
-}
-
-void SDKExtension::SDK_OnAllLoaded()
-{
-}
-
-void SDKExtension::SDK_OnDependenciesDropped()
-{
-}
-
-#if defined SMEXT_CONF_METAMOD
-
-PluginId g_PLID = 0; /**< Metamod plugin ID */
-ISmmPlugin *g_PLAPI = NULL; /**< Metamod plugin API */
-SourceHook::ISourceHook *g_SHPtr = NULL; /**< SourceHook pointer */
-ISmmAPI *g_SMAPI = NULL; /**< SourceMM API pointer */
-
-#ifndef META_NO_HL2SDK
-IVEngineServer *engine = NULL; /**< IVEngineServer pointer */
-IServerGameDLL *gamedll = NULL; /**< IServerGameDLL pointer */
-#endif
-
-/** Exposes the extension to Metamod */
-SMM_API void *PL_EXPOSURE(const char *name, int *code)
-{
-#if defined METAMOD_PLAPI_VERSION
- if (name && !strcmp(name, METAMOD_PLAPI_NAME))
-#else
- if (name && !strcmp(name, PLAPI_NAME))
-#endif
- {
- if (code)
- {
- *code = META_IFACE_OK;
- }
- return static_cast(g_pExtensionIface);
- }
-
- if (code)
- {
- *code = META_IFACE_FAILED;
- }
-
- return NULL;
-}
-
-bool SDKExtension::Load(PluginId id, ISmmAPI *ismm, char *error, size_t maxlen, bool late)
-{
- PLUGIN_SAVEVARS();
-
-#ifndef META_NO_HL2SDK
-#if !defined METAMOD_PLAPI_VERSION
- GET_V_IFACE_ANY(serverFactory, gamedll, IServerGameDLL, INTERFACEVERSION_SERVERGAMEDLL);
- GET_V_IFACE_CURRENT(engineFactory, engine, IVEngineServer, INTERFACEVERSION_VENGINESERVER);
-#else
- GET_V_IFACE_ANY(GetServerFactory, gamedll, IServerGameDLL, INTERFACEVERSION_SERVERGAMEDLL);
-#if SOURCE_ENGINE == SE_CSS || SOURCE_ENGINE == SE_DODS || SOURCE_ENGINE == SE_HL2DM || SOURCE_ENGINE == SE_SDK2013
- // Shim to avoid hooking shims
- engine = (IVEngineServer *) ismm->GetEngineFactory()("VEngineServer023", nullptr);
- if (!engine)
- {
- engine = (IVEngineServer *) ismm->GetEngineFactory()("VEngineServer022", nullptr);
- if (!engine)
- {
- engine = (IVEngineServer *) ismm->GetEngineFactory()("VEngineServer021", nullptr);
- if (!engine)
- {
- if (error && maxlen)
- {
- ismm->Format(error, maxlen, "Could not find interface: VEngineServer023 or VEngineServer022");
- }
- return false;
- }
- }
- }
-#else
- GET_V_IFACE_CURRENT(GetEngineFactory, engine, IVEngineServer, INTERFACEVERSION_VENGINESERVER);
-#endif // TF2 / CSS / DODS / HL2DM / SDK2013
-#endif // !METAMOD_PLAPI_VERSION
-#endif //META_NO_HL2SDK
-
- m_SourceMMLoaded = true;
-
- return SDK_OnMetamodLoad(ismm, error, maxlen, late);
-}
-
-bool SDKExtension::Unload(char *error, size_t maxlen)
-{
- if (!m_WeAreUnloaded)
- {
- if (error)
- {
- ke::SafeStrcpy(error, maxlen, "This extension must be unloaded by SourceMod.");
- }
- return false;
- }
-
- return SDK_OnMetamodUnload(error, maxlen);
-}
-
-bool SDKExtension::Pause(char *error, size_t maxlen)
-{
- if (!m_WeGotPauseChange)
- {
- if (error)
- {
- ke::SafeStrcpy(error, maxlen, "This extension must be paused by SourceMod.");
- }
- return false;
- }
-
- m_WeGotPauseChange = false;
-
- return SDK_OnMetamodPauseChange(true, error, maxlen);
-}
-
-bool SDKExtension::Unpause(char *error, size_t maxlen)
-{
- if (!m_WeGotPauseChange)
- {
- if (error)
- {
- ke::SafeStrcpy(error, maxlen, "This extension must be unpaused by SourceMod.");
- }
- return false;
- }
-
- m_WeGotPauseChange = false;
-
- return SDK_OnMetamodPauseChange(false, error, maxlen);
-}
-
-const char *SDKExtension::GetAuthor()
-{
- return GetExtensionAuthor();
-}
-
-const char *SDKExtension::GetDate()
-{
- return GetExtensionDateString();
-}
-
-const char *SDKExtension::GetDescription()
-{
- return GetExtensionDescription();
-}
-
-const char *SDKExtension::GetLicense()
-{
- return SMEXT_CONF_LICENSE;
-}
-
-const char *SDKExtension::GetLogTag()
-{
- return GetExtensionTag();
-}
-
-const char *SDKExtension::GetName()
-{
- return GetExtensionName();
-}
-
-const char *SDKExtension::GetURL()
-{
- return GetExtensionURL();
-}
-
-const char *SDKExtension::GetVersion()
-{
- return GetExtensionVerString();
-}
-
-bool SDKExtension::SDK_OnMetamodLoad(ISmmAPI *ismm, char *error, size_t maxlength, bool late)
-{
- return true;
-}
-
-bool SDKExtension::SDK_OnMetamodUnload(char *error, size_t maxlength)
-{
- return true;
-}
-
-bool SDKExtension::SDK_OnMetamodPauseChange(bool paused, char *error, size_t maxlength)
-{
- return true;
-}
-
-#endif
\ No newline at end of file
diff --git a/extension/sourcesdk/NextBot/NextBotComponentInterface.cpp b/extension/sourcesdk/NextBot/NextBotComponentInterface.cpp
index 58cba6f..5790c04 100644
--- a/extension/sourcesdk/NextBot/NextBotComponentInterface.cpp
+++ b/extension/sourcesdk/NextBot/NextBotComponentInterface.cpp
@@ -23,7 +23,7 @@ bool INextBotComponent::Init(SourceMod::IGameConfig* config, char* error, size_t
INextBotComponent::INextBotComponent(INextBot *bot)
{
#if SOURCE_ENGINE == SE_TF2
- m_scriptInstance = 0;
+ m_scriptInstance = nullptr;
#endif
m_curInterval = TICK_INTERVAL;
diff --git a/extension/sourcesdk/NextBot/NextBotComponentInterface.h b/extension/sourcesdk/NextBot/NextBotComponentInterface.h
index 7f6962e..b1fc989 100644
--- a/extension/sourcesdk/NextBot/NextBotComponentInterface.h
+++ b/extension/sourcesdk/NextBot/NextBotComponentInterface.h
@@ -4,6 +4,10 @@
#include "helpers.h"
#include "NextBotEventResponderInterface.h"
+#if SOURCE_ENGINE == SE_TF2
+FORWARD_DECLARE_HANDLE(HSCRIPT);
+#endif
+
class INextBot;
class Path;
class CGameTrace;
@@ -61,7 +65,7 @@ class INextBotComponent : public INextBotEventResponder
INextBotComponent *m_nextComponent;
#if SOURCE_ENGINE == SE_TF2
- std::int32_t m_scriptInstance;
+ HSCRIPT m_scriptInstance;
#endif
public:
diff --git a/extension/sourcesdk/baseanimating.cpp b/extension/sourcesdk/baseanimating.cpp
index a8a0e0b..fd66358 100644
--- a/extension/sourcesdk/baseanimating.cpp
+++ b/extension/sourcesdk/baseanimating.cpp
@@ -1,4 +1,5 @@
#include "sourcesdk/baseanimating.h"
+#include
#include
#include
#include
@@ -8,13 +9,13 @@
FCall fStudio_LookupSequence;
FCall fStudio_FindAttachment;
FCall fStudio_SelectWeightedSequence;
+FCall fStudio_Duration;
int CBaseAnimating::offset_HandleAnimEvent = 0;
VCall CBaseAnimating::vStudioFrameAdvance;
VCall CBaseAnimating::vDispatchAnimEvents;
VCall< bool, int, matrix3x4_t& > CBaseAnimating::vGetAttachment;
-MCall CBaseAnimating::mSequenceDuration;
MCall CBaseAnimating::mResetSequence;
MCall CBaseAnimating::mLookupPoseParameter;
MCall CBaseAnimating::mGetPoseParameter;
@@ -25,6 +26,7 @@ DEFINEVAR(CBaseAnimating, m_pStudioHdr);
DEFINEVAR(CBaseAnimating, m_OnIgnite);
DEFINEVAR(CBaseAnimating, m_nSequence);
DEFINEVAR(CBaseAnimating, m_flModelScale);
+DEFINEVAR(CBaseAnimating, m_flPoseParameter);
bool CBaseAnimating::Init(SourceMod::IGameConfig* config, char* error, size_t maxlength)
{
@@ -33,8 +35,8 @@ bool CBaseAnimating::Init(SourceMod::IGameConfig* config, char* error, size_t ma
fStudio_LookupSequence.Init(config, "Studio_LookupSequence");
fStudio_FindAttachment.Init(config, "Studio_FindAttachment");
fStudio_SelectWeightedSequence.Init(config, "Studio_SelectWeightedSequence");
+ fStudio_Duration.Init(config, "Studio_Duration");
- mSequenceDuration.Init(config, "CBaseAnimating::SequenceDuration");
mResetSequence.Init(config, "CBaseAnimating::ResetSequence");
mLookupPoseParameter.Init(config, "CBaseAnimating::LookupPoseParameter");
mSetPoseParameter.Init(config, "CBaseAnimating::SetPoseParameter");
@@ -64,6 +66,7 @@ bool CBaseAnimating::Init(SourceMod::IGameConfig* config, char* error, size_t ma
OFFSETVAR_SEND(CBaseAnimating, m_flModelScale);
// m_pStudioHdr is in front of m_OnIgnite
VAR_OFFSET_SET(m_pStudioHdr, VAR_OFFSET(m_OnIgnite) + sizeof(COutputEvent));
+ OFFSETVAR_SEND(CBaseAnimating, m_flPoseParameter);
END_VAR;
void* aVal = nullptr;
@@ -74,6 +77,13 @@ bool CBaseAnimating::Init(SourceMod::IGameConfig* config, char* error, size_t ma
}
uint8_t* aGetAnimationEvent = reinterpret_cast(aVal);
+#ifdef PLATFORM_X64
+#ifdef WIN64
+#else
+ SourceHook::SetMemAccess(aGetAnimationEvent + 0xF2, sizeof(uint32_t), SH_MEM_READ | SH_MEM_WRITE | SH_MEM_EXEC);
+ *(uint32_t*)(aGetAnimationEvent + 0xF2) = 9999;
+#endif
+#else
#ifdef WIN32
SourceHook::SetMemAccess(aGetAnimationEvent + 0x83, sizeof(uint32_t), SH_MEM_READ | SH_MEM_WRITE | SH_MEM_EXEC);
*(uint32_t*)(aGetAnimationEvent + 0x83) = 9999;
@@ -82,6 +92,7 @@ bool CBaseAnimating::Init(SourceMod::IGameConfig* config, char* error, size_t ma
*(uint32_t*)(aGetAnimationEvent + 0x17E) = 9999;
SourceHook::SetMemAccess(aGetAnimationEvent + 0xB3, sizeof(uint32_t), SH_MEM_READ | SH_MEM_WRITE | SH_MEM_EXEC);
*(uint32_t*)(aGetAnimationEvent + 0xB3) = 9999;
+#endif
#endif
return true;
}
@@ -127,9 +138,24 @@ float CBaseAnimating::GetPoseParameter(const char* name)
return GetPoseParameter(LookupPoseParameter(name));
}
-float CBaseAnimating::SequenceDuration(CStudioHdr* studio, int sequence)
+float CBaseAnimating::SequenceDuration(CStudioHdr* pStudioHdr, int iSequence)
{
- return mSequenceDuration(this, studio, sequence);
+ if ( !pStudioHdr )
+ {
+ DevWarning( 2, "CBaseAnimating::SequenceDuration( %d ) NULL pstudiohdr on %s!\n", iSequence, GetClassname() );
+ return 0.1;
+ }
+ if ( !pStudioHdr->SequencesAvailable() )
+ {
+ return 0.1;
+ }
+ if (iSequence >= pStudioHdr->GetNumSeq() || iSequence < 0 )
+ {
+ DevWarning( 2, "CBaseAnimating::SequenceDuration( %d ) out of range\n", iSequence );
+ return 0.1;
+ }
+
+ return fStudio_Duration(pStudioHdr, iSequence, GetPoseParameterArray());
}
void CBaseAnimating::ResetSequence(int sequence)
@@ -138,7 +164,7 @@ void CBaseAnimating::ResetSequence(int sequence)
}
bool CBaseAnimating::GetAttachment(const char *szName, Vector &absOrigin, QAngle &absAngles)
-{
+{
return GetAttachment(LookupAttachment(szName), absOrigin, absAngles);
}
diff --git a/extension/sourcesdk/baseanimating.h b/extension/sourcesdk/baseanimating.h
index 3b327bc..ca0c15e 100644
--- a/extension/sourcesdk/baseanimating.h
+++ b/extension/sourcesdk/baseanimating.h
@@ -34,6 +34,8 @@ class CBaseAnimating : public CBaseEntity
float GetPoseParameter(const char* name);
+ const float* GetPoseParameterArray() { return m_flPoseParameter(); }
+
static int offset_HandleAnimEvent;
static VCall vStudioFrameAdvance;
@@ -42,7 +44,6 @@ class CBaseAnimating : public CBaseEntity
static VCall vDispatchAnimEvents;
void DispatchAnimEvents(CBaseAnimating*);
- static MCall mSequenceDuration;
float SequenceDuration(CStudioHdr*, int);
static MCall mResetSequence;
@@ -67,6 +68,7 @@ class CBaseAnimating : public CBaseEntity
DECLAREVAR(CStudioHdr*, m_pStudioHdr);
DECLAREVAR(int, m_nSequence);
DECLAREVAR(float, m_flModelScale);
+ DECLAREVAR(float, m_flPoseParameter);
};
inline float CBaseAnimating::GetModelScale() const
diff --git a/extension/sourcesdk/baseentity.cpp b/extension/sourcesdk/baseentity.cpp
index 8e538af..ca87fee 100644
--- a/extension/sourcesdk/baseentity.cpp
+++ b/extension/sourcesdk/baseentity.cpp
@@ -166,8 +166,12 @@ bool CBaseEntity::Init(SourceMod::IGameConfig* config, char* error, size_t maxle
snprintf(error, maxlength, "Couldn't find offset for g_TouchTrace ptr!");
return false;
}
-
+#ifdef PLATFORM_X64
+ int32_t relativeoffset = *reinterpret_cast(addr + offset);
+ g_pTouchTrace = *reinterpret_cast(addr + offset + sizeof(int32_t) + relativeoffset);
+#else
g_pTouchTrace = *reinterpret_cast(addr + offset);
+#endif
}
else
{
diff --git a/extension/sourcesdk/baseentityoutput.cpp b/extension/sourcesdk/baseentityoutput.cpp
index 499e8b5..4b5a053 100644
--- a/extension/sourcesdk/baseentityoutput.cpp
+++ b/extension/sourcesdk/baseentityoutput.cpp
@@ -27,7 +27,12 @@ bool CBaseEntityOutput::Init(SourceMod::IGameConfig* config, char* error, size_t
snprintf(error, maxlength, "Couldn't find offset for g_EntityListPool ptr!");
return false;
}
+#ifdef PLATFORM_X64
+ int32_t relativeoffset = *reinterpret_cast(addr + offset);
+ g_pEntityListPool = *reinterpret_cast(addr + offset + sizeof(int32_t) + relativeoffset);
+#else
g_pEntityListPool = *reinterpret_cast(addr + offset);
+#endif
#endif
}
else
diff --git a/extension/sourcesdk/nav_mesh.cpp b/extension/sourcesdk/nav_mesh.cpp
index 18e4de9..696a4b3 100644
--- a/extension/sourcesdk/nav_mesh.cpp
+++ b/extension/sourcesdk/nav_mesh.cpp
@@ -37,17 +37,24 @@ bool CNavMesh::Init(SourceMod::IGameConfig* config, char* error, size_t maxlengt
snprintf(error, maxlength, "Couldn't find offset for TheNavMesh ptr!");
return false;
}
-
- CNavMesh** pTheNavMesh = *reinterpret_cast(addr + offset);
- TheNavMesh = *pTheNavMesh;
+#ifdef PLATFORM_X64
+ int32_t relativeoffset = *reinterpret_cast(addr + offset);
+ TheNavMesh = **reinterpret_cast(addr + offset + sizeof(int32_t) + relativeoffset);
+#else
+ TheNavMesh = **reinterpret_cast(addr + offset);
+#endif
if (!config->GetOffset("TheNavAreas", &offset) || !offset)
{
snprintf(error, maxlength, "Couldn't find offset for TheNavAreas ptr!");
return false;
}
-
+#ifdef PLATFORM_X64
+ relativeoffset = *reinterpret_cast(addr + offset);
+ pTheNavAreas = reinterpret_cast(addr + offset + sizeof(int32_t) + relativeoffset);
+#else
pTheNavAreas = *reinterpret_cast(addr + offset);
+#endif
}
else
{
@@ -88,10 +95,6 @@ bool CNavMesh::Init(SourceMod::IGameConfig* config, char* error, size_t maxlengt
return true;
}
-void CNavMesh::OnCoreMapEnd()
-{
-}
-
void CNavMesh::SDK_OnUnload()
{
if (g_pNavMeshLoad != nullptr)
diff --git a/extension/sourcesdk/nav_mesh.h b/extension/sourcesdk/nav_mesh.h
index 0d73f17..2cd14f4 100644
--- a/extension/sourcesdk/nav_mesh.h
+++ b/extension/sourcesdk/nav_mesh.h
@@ -29,7 +29,6 @@ class CNavMesh
{
public:
static bool Init(SourceMod::IGameConfig* config, char* error, size_t maxlength);
- static void OnCoreMapEnd();
static void SDK_OnUnload();
bool IsLoaded( void ) const { return *(bool*)((uint8_t*)this + offset_m_isLoaded); }
diff --git a/extension/sourcesdk/studio.cpp b/extension/sourcesdk/studio.cpp
new file mode 100644
index 0000000..d0d0fd4
--- /dev/null
+++ b/extension/sourcesdk/studio.cpp
@@ -0,0 +1,21 @@
+#include
+
+bool CStudioHdr::SequencesAvailable() const
+{
+ if (m_pStudioHdr->numincludemodels == 0)
+ {
+ return true;
+ }
+
+ return m_pVModel != nullptr;
+}
+
+int CStudioHdr::GetNumSeq( void ) const
+{
+ if (m_pVModel == NULL)
+ {
+ return m_pStudioHdr->numlocalseq;
+ }
+
+ return m_pVModel->m_seq.Count();
+}
\ No newline at end of file
diff --git a/gamedata/cbasenpc.txt b/gamedata/cbasenpc.txt
index 0a48c3b..a1eb45b 100644
--- a/gamedata/cbasenpc.txt
+++ b/gamedata/cbasenpc.txt
@@ -7,239 +7,362 @@
// Locate CNavMesh::Load, first dword is TheNavMesh second is TheNavAreas
"TheNavMesh"
{
- "linux" "979"
"windows" "786"
+ "windows64" "569"
+ "linux" "979"
+ "linux64" "849"
}
"TheNavAreas"
{
- "linux" "1058"
"windows" "819"
+ "windows64" "839"
+ "linux" "1058"
+ "linux64" "1008"
}
// Locate CBaseEntity::PhysicsMarkEntitiesAsTouching, first dword is g_TouchTrace
"g_TouchTrace"
{
- "linux" "29"
"windows" "32"
+ "windows64" "56"
+ "linux" "29"
+ "linux64" "55"
}
"g_EntityListPool"
{
"windows" "17"
+ "windows64" "33"
}
"CNavMesh::m_isLoaded"
{
- "linux" "52"
"windows" "52"
+ "windows64" "72"
+ "linux" "52"
+ "linux64" "72"
}
"CBaseEntity::Spawn"
{
- "linux" "25"
"windows" "24"
+ "windows64" "24"
+ "linux" "25"
+ "linux64" "25"
}
"CBaseEntity::PostConstructor"
{
- "linux" "29"
"windows" "28"
+ "windows64" "28"
+ "linux" "29"
+ "linux64" "29"
}
"CBaseEntity::GetBaseAnimating"
{
- "linux" "53"
"windows" "52"
+ "windows64" "52"
+ "linux" "53"
+ "linux64" "53"
}
"CBaseEntity::IsAlive"
{
- "linux" "68"
"windows" "67"
+ "windows64" "67"
+ "linux" "68"
+ "linux64" "68"
}
"CBaseEntity::Event_Killed"
{
- "linux" "69"
"windows" "68"
+ "windows64" "68"
+ "linux" "69"
+ "linux64" "69"
}
"CBaseEntity::MyCombatCharacterPointer"
{
- "linux" "74"
"windows" "73"
+ "windows64" "73"
+ "linux" "74"
+ "linux64" "74"
}
"CBaseEntity::MyNextBotPointer"
{
- "linux" "75"
"windows" "74"
+ "windows64" "74"
+ "linux" "75"
+ "linux64" "75"
}
"CBaseEntity::Touch"
{
- "linux" "105"
"windows" "104"
+ "windows64" "104"
+ "linux" "105"
+ "linux64" "105"
}
"CBaseEntity::PhysicsSimulate"
{
- "linux" "110"
"windows" "109"
+ "windows64" "109"
+ "linux" "110"
+ "linux64" "110"
}
"CBaseEntity::UpdateOnRemove"
{
- "linux" "111"
"windows" "110"
+ "windows64" "110"
+ "linux" "111"
+ "linux64" "111"
}
"CBaseEntity::EyeAngles"
{
- "linux" "138"
"windows" "137"
+ "windows64" "137"
+ "linux" "138"
+ "linux64" "138"
}
"CBaseEntity::GetVectors"
{
- "linux" "143"
"windows" "142"
+ "windows64" "142"
+ "linux" "143"
+ "linux64" "143"
}
- "CBaseEntity::WorldSpaceCenter"
+ "CBaseEntity::WorldSpaceCenter"
{
- "linux" "156"
"windows" "155"
+ "windows64" "155"
+ "linux" "156"
+ "linux64" "156"
}
"CBaseAnimating::StudioFrameAdvance"
{
- "linux" "201"
"windows" "200"
+ "windows64" "200"
+ "linux" "201"
+ "linux64" "201"
}
"CBaseAnimating::DispatchAnimEvents"
{
- "linux" "213"
"windows" "212"
+ "windows64" "212"
+ "linux" "213"
+ "linux64" "213"
}
"CBaseAnimating::HandleAnimEvent"
{
- "linux" "214"
"windows" "213"
+ "windows64" "213"
+ "linux" "214"
+ "linux64" "214"
}
"CBaseAnimating::GetAttachment"
{
- "linux" "216"
"windows" "215"
+ "windows64" "215"
+ "linux" "216"
+ "linux64" "216"
}
"CBaseCombatCharacter::Weapon_Equip"
{
- "linux" "272"
"windows" "271"
+ "windows64" "271"
+ "linux" "272"
+ "linux64" "272"
}
"CBaseCombatCharacter::Weapon_Drop"
{
- "linux" "274"
"windows" "273"
+ "windows64" "273"
+ "linux" "274"
+ "linux64" "274"
}
"CBaseCombatCharacter::OnTakeDamage_Alive"
{
- "linux" "283"
"windows" "282"
+ "windows64" "282"
+ "linux" "283"
+ "linux64" "283"
}
"CBaseCombatCharacter::OnTakeDamage_Dying"
{
- "linux" "284"
"windows" "283"
+ "windows64" "283"
+ "linux" "284"
+ "linux64" "284"
}
"CBaseCombatCharacter::GetLastKnownArea"
{
- "linux" "323"
"windows" "322"
+ "windows64" "322"
+ "linux" "323"
+ "linux64" "323"
}
"CBaseCombatCharacter::OnNavAreaChanged"
{
- "linux" "327"
"windows" "326"
+ "windows64" "326"
+ "linux" "327"
+ "linux64" "327"
}
"CBaseCombatCharacter::UpdateLastKnownArea"
{
- "linux" "326"
"windows" "325"
+ "windows64" "325"
+ "linux" "326"
+ "linux64" "326"
}
"NextBotCombatCharacter::vtable_entries"
{
"windows" "338"
+ "windows64" "338"
"linux" "338"
+ "linux64" "338"
}
"NextBotGroundLocomotion::vtable_entries"
{
- "linux" "111"
"windows" "111"
+ "windows64" "111"
+ "linux" "111"
+ "linux64" "111"
}
}
"Signatures"
{
+ // Find string "Missing command string" which is used by nb_command
+ // nb_command calls TheNextBots()
"TheNextBots"
{
"library" "server"
"windows" "\xA1\x2A\x2A\x2A\x2A\x85\xC0\x75\x2A\x8B\x0D\x2A\x2A\x2A\x2A\xF6\xC1\x01"
+ "windows64" "\x48\x83\xEC\x28\x48\x8B\x05\x2A\x2A\x2A\x2A\x48\x85\xC0\x0F\x85\x2A\x2A\x2A\x2A\x8B\x05\x2A\x2A\x2A\x2A"
"linux" "@_Z11TheNextBotsv"
+ "linux64" "@_Z11TheNextBotsv"
}
+ // Find string "or_crit_vs_playercond"
"CTFGameRules::ApplyOnDamageModifyRules"
{
"library" "server"
"windows" "\x55\x8B\xEC\x81\xEC\xAC\x00\x00\x00\x56\x8B\x75\x0C"
+ "windows64" "\x48\x8B\xC4\x44\x88\x48\x2A\x4C\x89\x40\x2A\x48\x89\x48\x2A\x55\x53\x56\x57"
"linux" "@_ZN12CTFGameRules24ApplyOnDamageModifyRulesER15CTakeDamageInfoP11CBaseEntityb"
+ "linux64" "@_ZN12CTFGameRules24ApplyOnDamageModifyRulesER15CTakeDamageInfoP11CBaseEntityb"
}
+ // Find string "mult_dmgtaken"
"CTFGameRules::ApplyOnDamageAliveModifyRules"
{
"library" "server"
"windows" "\x55\x8B\xEC\x81\xEC\x2A\x00\x00\x00\x53\x8B\x5D\x0C\x89\x2A\x2A\x56"
+ "windows64" "\x48\x8B\xC4\x4C\x89\x40\x2A\x48\x89\x48\x2A\x55"
"linux" "@_ZN12CTFGameRules29ApplyOnDamageAliveModifyRulesERK15CTakeDamageInfoP11CBaseEntityRNS_20DamageModifyExtras_tE"
+ "linux64" "@_ZN12CTFGameRules29ApplyOnDamageAliveModifyRulesERK15CTakeDamageInfoP11CBaseEntityRNS_20DamageModifyExtras_tE"
}
// Find string "Invalid navigation file.\n"
"CNavMesh::Load"
{
"library" "server"
- "windows" "\x55\x8B\xEC\x81\xEC\x84\x01\x00\x00\x53\x56\x8B\x35\x2A\x2A\x2A\x2A"
+ "windows" "\x55\x8B\xEC\x81\xEC\x84\x01\x00\x00\x53\x56\x8B\x35\x2A\x2A\x2A\x2A"
+ "windows64" "\x48\x8B\xC4\x48\x89\x48\x2A\x55\x53\x57\x41\x55"
"linux" "@_ZN8CNavMesh4LoadEv"
+ "linux64" "@_ZN8CNavMesh4LoadEv"
}
+ // Go to first data xref of "Warning: NavArea #%d: Truncated hiding spot list to 255\n", this is CNavArea::Save
+ // Go to first data xref to reach CNavArea vtable
+ // Go to vfunc "CNavArea::ComputeLighting"
+ // Go to last call
"CNavMesh::GetGroundHeight"
{
"library" "server"
"windows" "\x53\x8B\xDC\x83\xEC\x08\x83\xE4\xF0\x83\xC4\x04\x55\x8B\x6B\x04\x89\x6C\x24\x04\x8B\xEC\x81\xEC\xFC\x00\x00\x00\x56\x6A\x00\x6A\x00\x6A\x00\x8D"
+ "windows64" "\x48\x8B\xC4\x48\x89\x58\x2A\x48\x89\x70\x2A\x48\x89\x78\x2A\x4C\x89\x70\x2A\x55\x48\x8D\xA8\x2A\x2A\x2A\x2A\x48\x81\xEC\xD0\x01\x00\x00\x0F\x29\x70\x2A\x48\x8D\x4D\x00"
"linux" "@_ZNK8CNavMesh15GetGroundHeightERK6VectorPfPS0_"
+ "linux64" "@_ZNK8CNavMesh15GetGroundHeightERK6VectorPfPS0_"
}
+ // Go to first data xref of string " Usage: test_dispatcheffect \n ", this is CC_Player_TestDispatchEffect
+ // Go to first call that takes 6 params, this is UTIL_TraceLine
+ // Go to first call, this is CTraceFilterSimple::CTraceFilterSimple
+ // Go to src of first LEA op, this is CTraceFilterSimple vtable
+ // Go to first vfunc, this is CTraceFilterSimple::ShouldHitEntity
"CTraceFilterSimple::ShouldHitEntity"
{
"library" "server"
"windows" "\x55\x8B\xEC\x53\x8B\x5D\x0C\x56\x8B\x75\x08\x57\x53\x56"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x6C\x24\x2A\x48\x89\x74\x24\x2A\x48\x89\x7C\x24\x2A\x41\x56\x48\x83\xEC\x20\x48\x8B\xE9\x41\x8B\xF8"
"linux" "@_ZN18CTraceFilterSimple15ShouldHitEntityEP13IHandleEntityi"
+ "linux64" "@_ZN18CTraceFilterSimple15ShouldHitEntityEP13IHandleEntityi"
}
+ // Go to first data xref of string "%s has changed its model while processing AnimEvents on sequence %d. Aborting dispatch.\n", this is CBaseAnimating::DispatchAnimEvents
+ // Go to call that takes 6 params, this is GetAnimationEvent
"__GetAnimationEvent__"
{
"library" "server"
"windows" "\x55\x8B\xEC\x53\x56\x8B\x75\x08\x85\xF6\x0F\x84\x2A\x2A\x2A\x2A\x8B\xCE\xE8\x2A\x2A\x2A\x2A"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x74\x24\x2A\x57\x48\x83\xEC\x30\x0F\x29\x74\x24\x2A\x0F\x28\xF3\x49\x8B\xF0"
"linux" "@_Z17GetAnimationEventP10CStudioHdriP11animevent_tffi"
+ "linux64" "@_Z17GetAnimationEventP10CStudioHdriP11animevent_tffi"
}
+ // Go to first data xref of string "Dynamic prop %s: no sequence named:%s\n", this is CDynamicProp::PropSetAnim
+ // Go to first call, this is CBaseAnimating::LookupSequence
+ // Go to last call, this is ::LookupSequence
"Studio_LookupSequence"
{
"library" "server"
"windows" "\x55\x8B\xEC\x56\x8B\x75\x08\x85\xF6\x75\x2A\x33\xC0\x5E\x5D\xC3\x8B\xCE\xE8\x2A\x2A\x2A\x2A\x84\xC0\x74\x2A\x53"
+ "windows64" "\x48\x89\x5C\x24\x2A\x55\x48\x83\xEC\x20\x48\x8B\xEA"
"linux" "@_Z14LookupSequenceP10CStudioHdrPKc"
+ "linux64" "@_Z14LookupSequenceP10CStudioHdrPKc"
}
+ // Go to data xref of string "No appropriate sequence for arrival activity %s (%d)\n", this is CAI_Navigator::GetArrivalSequence
+ // Go to fourth call, this is CBaseAnimating::SelectWeightedSequence
+ // Follow jmp op at end to func
"Studio_SelectWeightedSequence"
{
"library" "server"
"windows" "\x55\x8B\xEC\x56\x8B\x75\x08\x85\xF6\x75\x2A\x33\xC0\x5E\x5D\xC3\x8B\xCE\xE8\x2A\x2A\x2A\x2A\x84\xC0\x74\x2A\x8B\xCE"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x6C\x24\x2A\x56\x48\x83\xEC\x20\x41\x8B\xF0"
"linux" "@_Z22SelectWeightedSequenceP10CStudioHdrii"
+ "linux64" "@_Z22SelectWeightedSequenceP10CStudioHdrii"
}
// Find "placementOrigin" first subroutine call below it
"Studio_FindAttachment"
{
"library" "server"
"windows" "\x55\x8B\xEC\x53\x56\x57\x8B\x7D\x08\x85\xFF\x74\x2A\x8B\xCF"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x74\x24\x2A\x57\x48\x83\xEC\x20\x48\x8B\xF2\x48\x8B\xF9\x48\x85\xC9"
"linux" "@_Z21Studio_FindAttachmentPK10CStudioHdrPKc"
+ "linux64" "@_Z21Studio_FindAttachmentPK10CStudioHdrPKc"
+ }
+ // Look up data xrefs to string "CBaseAnimating::SequenceDuration( %d ) NULL pstudiohdr on %s!\n"
+ // Find call that takes 3 parameters
+ "Studio_Duration"
+ {
+ "library" "server"
+ "windows" "\x55\x8B\xEC\xFF\x75\x2A\x8B\x4D\x2A\xE8\x2A\x2A\x2A\x2A\xFF\x75"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x74\x24\x2A\x57\x48\x83\xEC\x20\x49\x8B\xD8\x8B\xFA"
+ "linux" "@_Z15Studio_DurationPK10CStudioHdriPKf"
+ "linux64" "@_Z15Studio_DurationPK10CStudioHdriPKf"
}
// Bytes sequence search "00 00 C0 00", go to the only subroutine that uses that number with 'and' & 'cmp'
"SimThink_EntityChanged"
{
"library" "server"
"windows" "\x55\x8B\xEC\x56\x57\x8B\x7D\x08\x8B\xF1\xF6\x87\x3C\x01\x00\x00\x01"
+ "windows64" "\x40\x53\x56\x48\x83\xEC\x28\xF6\x82\x2A\x2A\x2A\x2A\x01"
"linux" "@_Z22SimThink_EntityChangedP11CBaseEntity"
- }
- // Find ".?AVCRallyPoint@@" to get to CRallyPoint's type descriptor -> complete object locator -> vtable
- // goto xref to vtable to enter CRallyPoint's constructor
- // CBaseEntity constructor is second call that takes additional argument (bServerOnly set to 0)
+ "linux64" "@_Z22SimThink_EntityChangedP11CBaseEntity"
+ }
+ // Go to first data xref of "simple_bot"
+ // Go to src of other LEA op, this is the instance of CEntityFactory singleton
+ // Go to ptr, this is the vtable
+ // Go to first vptr, this is CEntityFactory::Create (CSimpleBot::CSimpleBot is inlined in this function)
+ // Go to second call, this is NextBotCombatCharacter::NextBotCombatCharacter
+ // Go to first call, this is CBaseCombatCharacter::CBaseCombatCharacter
+ // ... CBaseCombatCharacter::CBaseCombatCharacter
+ // ... CBaseFlex::CBaseFlex
+ // ... CBaseAnimating::CBaseAnimating (CBaseAnimatingOverlay doesn't have a ctor)
+ // ... CBaseEntity::CBaseEntity (first call, has two arguments, this and false)
"CBaseEntity::CBaseEntity"
{
"library" "server"
"windows" "\x55\x8B\xEC\x83\xEC\x14\x53\x56\x8B\xF1\x57\x8D\x2A\x2A\xC7\x06"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x6C\x24\x2A\x48\x89\x74\x24\x2A\x88\x54\x24\x2A"
"linux" "@_ZN11CBaseEntityC2Eb"
+ "linux64" "@_ZN11CBaseEntityC2Eb"
}
// Find "add 0x%p: %s-%s (%d-%d) [%d in play, %d max]\n" to find CBaseEntity::PhysicsMarkEntityAsTouched
// jump to the function calling this one, there can be only one and it's CBaseEntity::PhysicsMarkEntitiesAsTouching
@@ -247,96 +370,129 @@
{
"library" "server"
"windows" "\x55\x8B\xEC\x56\x8B\x75\x0C\x57\x8B\xF9\xB9\x2A\x2A\x2A\x2A\x56\xE8\x2A\x2A\x2A\x2A\xF3\x0F\x10\x46\x38\x8B\xCF\xF3\x0F\x11\x05\x2A\x2A\x2A\x2A\x8B\x46\x3C\xA3\x2A\x2A\x2A\x2A\x8B\x46\x40\xA3\x2A\x2A\x2A\x2A\x8B\x46\x44\xA3\x2A\x2A\x2A\x2A\x66\x8B\x46\x48\x66\xA3\x2A\x2A\x2A\x2A\x8B\x46\x4C\xA3\x2A\x2A\x2A\x2A\x8B\x46\x50\x8B\x75\x08\x56\xA3\x2A\x2A\x2A\x2A\xE8\x2A\x2A\x2A\x2A"
+ "windows64" "\x48\x85\xD2\x0F\x84\x2A\x2A\x2A\x2A\x48\x89\x5C\x24\x2A\x57\x48\x83\xEC\x20\x8B\x82\x2A\x2A\x2A\x2A\x48\x8B\xDA\x0B\x81\x2A\x2A\x2A\x2A"
"linux" "@_ZN11CBaseEntity29PhysicsMarkEntitiesAsTouchingEPS_R10CGameTrace"
+ "linux64" "@_ZN11CBaseEntity29PhysicsMarkEntitiesAsTouchingEPS_R10CGameTrace"
}
// Find "m_CalcAbsolutePositionMutex" to find CBaseEntity::CalcAbsolutePosition
"CBaseEntity::CalcAbsolutePosition"
{
"library" "server"
"windows" "\x55\x8B\xEC\x81\xEC\x80\x00\x00\x00\x56\x8B\xF1\x8B\x86\x3C\x01\x00\x00"
+ "windows64" "\x4C\x8B\xDC\x55\x53\x49\x8D\x6B\x2A\x48\x81\xEC\xE8\x00\x00\x00"
"linux" "@_ZN11CBaseEntity20CalcAbsolutePositionEv"
+ "linux64" "@_ZN11CBaseEntity20CalcAbsolutePositionEv"
}
+ // Go to first data xref of string "Bad SetLocalAngles(%f,%f,%f) on %s\n", this is CBaseEntity::SetLocalAngles
+ // Go to call being passed 2 params (this, and the literal 2 which is ANGLES_CHANGED)
"CBaseEntity::InvalidatePhysicsRecursive"
{
"library" "server"
"windows" "\x55\x8B\xEC\x53\x8B\x5D\x08\x56\x8B\xF3\x83\xE6\x04"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x74\x24\x2A\x57\x48\x83\xEC\x20\x8B\xF2\x48\x89\x6C\x24\x2A"
"linux" "@_ZN11CBaseEntity26InvalidatePhysicsRecursiveEi"
- }
- "CBaseEntity::SetGroundEntity"
- {
- "library" "server"
- "windows" ""
- "linux" "@_ZN11CBaseEntity15SetGroundEntityEPS_"
+ "linux64" "@_ZN11CBaseEntity26InvalidatePhysicsRecursiveEi"
}
// Find string "CBaseEntity::TakeDamage: with inputInfo.GetDamageForce() == vec3_origin\n"
"CBaseEntity::TakeDamage"
{
"library" "server"
"windows" "\x55\x8B\xEC\x81\xEC\x98\x00\x00\x00\x53\x8B\xD9"
+ "windows64" "\x40\x55\x53\x57\x48\x8D\x6C\x24\x2A\x48\x81\xEC\x00\x01\x00\x00\x48\x8B\xF9"
"linux" "@_ZN11CBaseEntity10TakeDamageERK15CTakeDamageInfo"
+ "linux64" "@_ZN11CBaseEntity10TakeDamageERK15CTakeDamageInfo"
}
// "g_EntityListPool"
"g_EntityListPool"
{
"library" "server"
"windows" "\x6A\x00\x68\x2A\x2A\x2A\x2A\x6A\x01\x68\x00\x02\x00\x00\x6A\x1C"
+ "windows64" "\x48\x83\xEC\x38\xBA\x30\x00\x00\x00"
"linux" "@g_EntityListPool"
+ "linux64" "@g_EntityListPool"
}
+ // Go to data xref of CMultiPlayerAnimState::SetupPoseParameters, this is CMultiPlayerAnimState vtable
+ // Go to CMultiPlayerAnimState::ComputePoseParam_MoveYaw vfunc
+ // Multiple call pairs of CBaseAnimating::SetPoseParameter
"CBaseAnimating::SetPoseParameter"
{
"library" "server"
"windows" "\x55\x8B\xEC\x8B\x45\x08\xD9\x45\x10"
+ "windows64" "\x48\x89\x5C\x24\x2A\x57\x48\x83\xEC\x30\x0F\x29\x74\x24\x2A\x0F\x28\xF3"
"linux" "@_ZN14CBaseAnimating16SetPoseParameterEP10CStudioHdrif"
+ "linux64" "@_ZN14CBaseAnimating16SetPoseParameterEP10CStudioHdrif"
}
+ // Go to CMultiPlayerAnimState vtable
+ // Go to CMultiPlayerAnimState::GetCurrentMaxGroundSpeed vfunc
+ // Multiple call pairs of CBaseAnimating::GetPoseParameter
"CBaseAnimating::GetPoseParameter"
{
"library" "server"
"windows" "\x55\x8B\xEC\x56\x8B\xF1\x57\x80\xBE\x69\x03\x00\x00\x00\x75\x2A\x83\xBE\x98\x04\x00\x00\x00\x75\x2A\xE8\x2A\x2A\x2A\x2A\x85\xC0\x74\x2A\x8B\xCE\xE8\x2A\x2A\x2A\x2A\x8B\xBE\x98\x04\x00\x00"
+ "windows64" "\x48\x89\x5C\x24\x2A\x48\x89\x74\x24\x2A\x57\x48\x83\xEC\x20\x80\xB9\x2A\x2A\x2A\x2A\x00\x48\x8B\xD9\x48\x63\xF2"
"linux" "@_ZN14CBaseAnimating16GetPoseParameterEi"
+ "linux64" "@_ZN14CBaseAnimating16GetPoseParameterEi"
}
+ // Go to data xref of string "move_scale", this is CMultiPlayerAnimState::SetupPoseParameters
+ // Multiple calls to CBaseAnimating::LookupPoseParameter with different pose param names
"CBaseAnimating::LookupPoseParameter"
{
"library" "server"
"windows" "\x55\x8B\xEC\x57\x8B\x7D\x08\x85\xFF\x75\x2A\x33\xC0\x5F\x5D\xC2\x08\x00"
+ "windows64" "\x48\x89\x74\x24\x2A\x57\x48\x83\xEC\x20\x49\x8B\xF0\x48\x8B\xFA\x48\x85\xD2\x74\x2A\x48\x8B\xCA"
"linux" "@_ZN14CBaseAnimating19LookupPoseParameterEP10CStudioHdrPKc"
+ "linux64" "@_ZN14CBaseAnimating19LookupPoseParameterEP10CStudioHdrPKc"
}
- "CBaseAnimating::SequenceDuration"
- {
- "library" "server"
- "windows" "\x55\x8B\xEC\x56\x8B\x75\x08\x57\x8B\xF9\x85\xF6\x75\x2A\x8B\x47\x5C"
- "linux" "@_ZN14CBaseAnimating16SequenceDurationEP10CStudioHdri"
- }
+ // Go to data xref of string "ResetSequence : %s: %s -> %s\n"
"CBaseAnimating::ResetSequence"
{
"library" "server"
"windows" "\x55\x8B\xEC\xA1\x2A\x2A\x2A\x2A\x53\x56\x57\x83\x78\x30\x00\x8B\xD9\x8B\x7D\x08"
+ "windows64" "\x41\x56\x48\x83\xEC\x20\x48\x8B\x05\x2A\x2A\x2A\x2A\x4C\x8B\xF1"
"linux" "@_ZN14CBaseAnimating13ResetSequenceEi"
+ "linux64" "@_ZN14CBaseAnimating13ResetSequenceEi"
}
+ // Go to CEntityFactory::Create
+ // There's a call that has one parameter of around ~0x178 bytes, this is operator.new and NextBotGroundLocomotion::NextBotGroundLocomotion is below it
"NextBotGroundLocomotion::NextBotGroundLocomotion"
{
"library" "server"
"windows" "\x55\x8B\xEC\x56\xFF\x75\x08\x8B\xF1\xE8\x2A\x2A\x2A\x2A\xC7\x06\x2A\x2A\x2A\x2A\x8B\xC6\xC7\x86\xB4\x00\x00\x00\xFF\xFF\xFF\xFF"
+ "windows64" "\x40\x53\x48\x83\xEC\x20\x48\x8B\xD9\xE8\x2A\x2A\x2A\x2A\x33\xC9\x48\x8D\x05\x2A\x2A\x2A\x2A\x48\x89\x03\x48\x8D\x05\x2A\x2A\x2A\x2A\x48\x89\x83\x2A\x2A\x2A\x2A\x48\x89\x83\x2A\x2A\x2A\x2A"
"linux" "@_ZN23NextBotGroundLocomotionC2EP8INextBot"
+ "linux64" "@_ZN23NextBotGroundLocomotionC2EP8INextBot"
}
+ // Go to CEntityFactory::Create
+ // Go to second call, this is NextBotCombatCharacter::NextBotCombatCharacter
"NextBotCombatCharacter::NextBotCombatCharacter"
{
"library" "server"
"windows" "\x56\x57\x8B\xF9\xE8\x2A\x2A\x2A\x2A\x8D\x8F\x74\x08\x00\x00"
+ "windows64" "\x48\x89\x5C\x24\x2A\x57\x48\x83\xEC\x20\x48\x8B\xF9\xE8\x2A\x2A\x2A\x2A\x48\x8D\x8F\x2A\x2A\x2A\x2A\xE8\x2A\x2A\x2A\x2A"
"linux" "@_ZN22NextBotCombatCharacterC2Ev"
+ "linux64" "@_ZN22NextBotCombatCharacterC2Ev"
}
}
"Addresses"
- {
+ {
"GetAnimationEvent"
{
"windows"
{
"signature" "__GetAnimationEvent__"
}
+ "windows64"
+ {
+ "signature" "__GetAnimationEvent__"
+ }
"linux"
{
"signature" "__GetAnimationEvent__"
}
+ "linux64"
+ {
+ "signature" "__GetAnimationEvent__"
+ }
}
}
}
diff --git a/hl2sdk-manifests b/hl2sdk-manifests
new file mode 160000
index 0000000..a57b309
--- /dev/null
+++ b/hl2sdk-manifests
@@ -0,0 +1 @@
+Subproject commit a57b3095a6fc31a98b13e2d73ebb668dac4f1300
diff --git a/product.version b/product.version
index 1cac385..359a5b9 100644
--- a/product.version
+++ b/product.version
@@ -1 +1 @@
-1.11.0
+2.0.0
\ No newline at end of file
diff --git a/scripting/include/cbasenpc/baseanimating.inc b/scripting/include/cbasenpc/baseanimating.inc
index bbb3cfb..3cfca00 100644
--- a/scripting/include/cbasenpc/baseanimating.inc
+++ b/scripting/include/cbasenpc/baseanimating.inc
@@ -132,7 +132,7 @@ methodmap CBaseAnimating < CBaseEntity
* @return Memory address of CStudioHdr.
* @error Invalid entity.
*/
- public native Address GetModelPtr();
+ public native MemoryPointer GetModelPtr();
/**
* Retrieves the parameter index of a named pose parameter.
diff --git a/scripting/include/cbasenpc/baseanimatingoverlay.inc b/scripting/include/cbasenpc/baseanimatingoverlay.inc
index d7de063..1846a31 100644
--- a/scripting/include/cbasenpc/baseanimatingoverlay.inc
+++ b/scripting/include/cbasenpc/baseanimatingoverlay.inc
@@ -13,93 +13,7 @@
#define MAX_OVERLAYS 15
-#pragma deprecated Use CAnimationLayer instead
-enum //CAnimationLayer
-{
- m_fFlags = 0, //0x0000
- m_bSequenceFinished = 4, //0x0004
- m_bLooping = 6, //0x0006
- m_nSequence = 8, //0x0008
- m_flCycle = 12, //0x000C
- m_flPrevCycle = 16, //0x0010
- m_flWeight = 20, //0x0014
- m_flPlaybackRate = 24, //0x0018
- m_flBlendIn = 28, //0x001C
- m_flBlendOut = 32, //0x0020
- m_flKillRate = 36, //0x0024
- m_flKillDelay = 40, //0x0028
- m_flLayerAnimtime = 44, //0x002C
- m_flLayerFadeOuttime = 48, //0x0030
- m_nActivity = 52, //0x0034
- m_nPriority = 56, //0x0038
- m_nOrder = 60, //0x003C
- m_flLastEventCheck = 64, //0x0040
- m_flLastEventAccess = 68, //0x0044
- m_pOwnerEntity = 72, //0x0048
-
- CAnimationLayer_Size = 76 //0x004C
-}; //Size=0x004C
-
-methodmap CAnimationOverlay
-{
- #pragma deprecated Use CAnimationLayer instead
- public CAnimationOverlay(Address address)
- {
- return view_as(address);
- }
-
- property Address Address
- {
- public get()
- {
- return view_as(this);
- }
- }
-
- property bool isNull
- {
- public get()
- {
- return this.Address == Address_Null;
- }
- }
-
- public any Get(int iOffset)
- {
- return LoadFromAddress(this.Address + view_as(iOffset), NumberType_Int32);
- }
-
- public void Set(int iOffset, any iValue)
- {
- StoreToAddress(this.Address + view_as(iOffset), iValue, NumberType_Int32);
- }
-
- #pragma deprecated Use CAnimationLayer.IsActive() instead
- public bool IsActive() { return ((this.Get(m_fFlags) & ANIM_LAYER_ACTIVE) != 0); }
- #pragma deprecated Use CAnimationLayer.IsAutokill() instead
- public bool IsAutokill() { return ((this.Get(m_fFlags) & ANIM_LAYER_AUTOKILL) != 0); }
- #pragma deprecated Use CAnimationLayer.IsKillMe() instead
- public bool IsKillMe() { return ((this.Get(m_fFlags) & ANIM_LAYER_KILLME) != 0); }
- #pragma deprecated Use CAnimationLayer.IsDying() instead
- public bool IsDying() { return ((this.Get(m_fFlags) & ANIM_LAYER_DYING) != 0); }
- #pragma deprecated Use CAnimationLayer.NoEvents() instead
- public bool NoEvents() { return ((this.Get(m_fFlags) & ANIM_LAYER_NOEVENTS) != 0); }
- #pragma deprecated Use CAnimationLayer.KillMe() instead
- public void KillMe() { this.Set(m_fFlags, this.Get(m_fFlags) | ANIM_LAYER_KILLME); }
- #pragma deprecated Use CAnimationLayer.AutoKill() instead
- public void AutoKill() { this.Set(m_fFlags, this.Get(m_fFlags) | ANIM_LAYER_AUTOKILL); }
- #pragma deprecated Use CAnimationLayer.Dying() instead
- public void Dying() { this.Set(m_fFlags, this.Get(m_fFlags) | ANIM_LAYER_DYING); }
- #pragma deprecated Use CAnimationLayer.Dead() instead
- public void Dead() { this.Set(m_fFlags, this.Get(m_fFlags) & ~ANIM_LAYER_DYING); }
- #pragma deprecated Use CAnimationLayer.IsAlive() instead
- public bool IsAlive() { int iFlags = this.Get(m_fFlags); return (((iFlags & ANIM_LAYER_ACTIVE) != 0) || ((iFlags & ANIM_LAYER_KILLME) == 0)); }
-
- #pragma deprecated Use CAnimationLayer.m_nSequence instead
- public int GetLayerSequence() { return (this.Get(m_nSequence)); }
-};
-
-methodmap CAnimationLayer < CAnimationOverlay
+methodmap CAnimationLayer < MemoryPointer
{
property int m_fFlags
{
diff --git a/scripting/include/cbasenpc/baseentity.inc b/scripting/include/cbasenpc/baseentity.inc
index 26d5f86..852ac90 100644
--- a/scripting/include/cbasenpc/baseentity.inc
+++ b/scripting/include/cbasenpc/baseentity.inc
@@ -44,7 +44,7 @@ methodmap CBaseEntity
* @return Memory address of CServerNetworkProperty.
* @error Invalid entity.
*/
- public native Address NetworkProp();
+ public native MemoryPointer NetworkProp();
/**
* Obtains the entity's CCollisionProperty.
@@ -52,7 +52,7 @@ methodmap CBaseEntity
* @return Memory address of CCollisionProperty.
* @error Invalid entity.
*/
- public native Address CollisionProp();
+ public native MemoryPointer CollisionProp();
/**
* Informs the server that the network properties of this entity changed.
@@ -69,7 +69,7 @@ methodmap CBaseEntity
* @param varAddr Entity networked property address.
* @error Invalid entity.
*/
- public native void NetworkStateChangedVar(Address varAddr);
+ public native void NetworkStateChangedVar(MemoryPointer varAddr);
/**
* Gets the entity simulation time.
diff --git a/scripting/include/cbasenpc/entityfactory.inc b/scripting/include/cbasenpc/entityfactory.inc
index ab9d0ee..4d355ce 100644
--- a/scripting/include/cbasenpc/entityfactory.inc
+++ b/scripting/include/cbasenpc/entityfactory.inc
@@ -60,7 +60,7 @@ typeset CEntityFactoryOnRemoveCallback
typeset CEntityFactoryNextBot
{
- function INextBot (Address link);
+ function INextBot (MemoryPointer link);
};
methodmap CEntityFactory < Handle
@@ -241,7 +241,7 @@ methodmap CEntityFactory < Handle
*
* @error Invalid handle.
*/
- public native void AttachNextBot(CEntityFactoryNextBot factory = INVALID_FUNCTION);
+ public native void AttachNextBot(CEntityFactoryNextBot factory);
// Datamap
diff --git a/scripting/include/cbasenpc/nav.inc b/scripting/include/cbasenpc/nav.inc
index c15d3a2..81be7c9 100644
--- a/scripting/include/cbasenpc/nav.inc
+++ b/scripting/include/cbasenpc/nav.inc
@@ -180,8 +180,9 @@ methodmap CNavMesh
{
/**
* Pointer to TheNavMesh.
+ * You don't have to free the handle.
*/
- property Address Address
+ property MemoryPointer Address
{
public native get();
}
@@ -330,7 +331,7 @@ methodmap CNavMesh
bool ignoreNavBlockers = false);
};
-methodmap CNavLadder
+methodmap CNavLadder < MemoryPointer
{
/**
* The length of the ladder.
@@ -472,7 +473,7 @@ native HidingSpot GetHidingSpotByID(int id);
/**
* A rectangular region defining a walkable area in the environment.
*/
-methodmap CNavArea
+methodmap CNavArea < MemoryPointer
{
/**
* Updates the blocked status of the area.
diff --git a/scripting/include/cbasenpc/nextbot.inc b/scripting/include/cbasenpc/nextbot.inc
index 2f2be98..a6bc6d2 100644
--- a/scripting/include/cbasenpc/nextbot.inc
+++ b/scripting/include/cbasenpc/nextbot.inc
@@ -19,7 +19,7 @@ enum NextBotDebugType
DEBUG_ERRORS = (1 << 8),
};
-methodmap INextBotEventResponder
+methodmap INextBotEventResponder < MemoryPointer
{
public native INextBotEventResponder FirstContainedResponder();
public native INextBotEventResponder NextContainedResponder(INextBotEventResponder prev);
@@ -410,10 +410,10 @@ methodmap ToolsNextBot < INextBot
* @param entity Entity address
* @return The created NextBot interface
*/
- public native ToolsNextBot(Address entity);
+ public native ToolsNextBot(MemoryPointer entity);
}
-stock INextBot ToolsNextBot_Factory(Address entity)
+stock INextBot ToolsNextBot_Factory(MemoryPointer entity)
{
return ToolsNextBot(entity);
}
@@ -429,7 +429,7 @@ methodmap ToolsNextBotPlayer < ToolsNextBot
* @param entity Entity address
* @return The created NextBot interface
*/
- public native ToolsNextBotPlayer(Address entity);
+ public native ToolsNextBotPlayer(MemoryPointer entity);
/*
* Defines whether or not the nextbot interface should update when
@@ -442,7 +442,7 @@ methodmap ToolsNextBotPlayer < ToolsNextBot
}
}
-stock INextBot ToolsNextBotPlayer_Factory(Address entity)
+stock INextBot ToolsNextBotPlayer_Factory(MemoryPointer entity)
{
return ToolsNextBotPlayer(entity);
}
diff --git a/scripting/include/cbasenpc/nextbot/behavior.inc b/scripting/include/cbasenpc/nextbot/behavior.inc
index cae4034..db6a33c 100644
--- a/scripting/include/cbasenpc/nextbot/behavior.inc
+++ b/scripting/include/cbasenpc/nextbot/behavior.inc
@@ -76,10 +76,10 @@ typeset ActionEventResponderCallback
// OnContact
// result is a CGameTrace* structure
- function int (NextBotAction action, int actor, int other, Address result);
- function int (NextBotAction action, CBaseCombatCharacter actor, CBaseEntity other, Address result);
- function void (NextBotAction action, int actor, int other, Address result);
- function void (NextBotAction action, CBaseCombatCharacter actor, CBaseEntity other, Address result);
+ function int (NextBotAction action, int actor, int other, MemoryPointer result);
+ function int (NextBotAction action, CBaseCombatCharacter actor, CBaseEntity other, MemoryPointer result);
+ function void (NextBotAction action, int actor, int other, MemoryPointer result);
+ function void (NextBotAction action, CBaseCombatCharacter actor, CBaseEntity other, MemoryPointer result);
// OnMoveToSuccess
function int (NextBotAction action, int actor, Path path);
@@ -203,11 +203,11 @@ typeset ActionEventResponderCallback
// OnSpokeConcept
// response is AI_Response*
- function int (NextBotAction action, int actor, int who, const char[] concept, Address response);
- function int (NextBotAction action, CBaseCombatCharacter actor, CBaseCombatCharacter who, const char[] concept, Address response);
+ function int (NextBotAction action, int actor, int who, const char[] concept, MemoryPointer response);
+ function int (NextBotAction action, CBaseCombatCharacter actor, CBaseCombatCharacter who, const char[] concept, MemoryPointer response);
- function void (NextBotAction action, int actor, int who, const char[] concept, Address response);
- function void (NextBotAction action, CBaseCombatCharacter actor, CBaseCombatCharacter who, const char[] concept, Address response);
+ function void (NextBotAction action, int actor, int who, const char[] concept, MemoryPointer response);
+ function void (NextBotAction action, CBaseCombatCharacter actor, CBaseCombatCharacter who, const char[] concept, MemoryPointer response);
// OnWeaponFired
function int (NextBotAction action, int actor, int whoFired, int weapon);
diff --git a/scripting/include/cbasenpc/nextbot/knownentity.inc b/scripting/include/cbasenpc/nextbot/knownentity.inc
index 19711d9..5ccee0f 100644
--- a/scripting/include/cbasenpc/nextbot/knownentity.inc
+++ b/scripting/include/cbasenpc/nextbot/knownentity.inc
@@ -9,7 +9,7 @@
* Note: Do not attempt to save pointers of this class as location of the data
* can (and will!) change.
*/
-methodmap CKnownEntity
+methodmap CKnownEntity < MemoryPointer
{
/**
* Invalidates this entry. This will mark the entry for deletion.
diff --git a/scripting/include/cbasenpc/nextbot/path.inc b/scripting/include/cbasenpc/nextbot/path.inc
index abcea32..2ec2360 100644
--- a/scripting/include/cbasenpc/nextbot/path.inc
+++ b/scripting/include/cbasenpc/nextbot/path.inc
@@ -49,7 +49,7 @@ typeset PathFollowerCostFunctor
/**
* A segment of a Path.
*/
-methodmap Segment
+methodmap Segment < MemoryPointer
{
/**
* The CNavArea that this segment traverses.
@@ -200,7 +200,7 @@ methodmap Segment
/**
* A structure that stores data about the current progress on the Path.
*/
-methodmap CursorData
+methodmap CursorData < MemoryPointer
{
/**
* The current position along the path.
@@ -261,7 +261,7 @@ typeset PathComputeCallback
function void (Path path, bool success, any data);
};
-methodmap Path
+methodmap Path < MemoryPointer
{
/**
* A Path that is used by NextBots to navigate the world.
diff --git a/scripting/include/cbasenpc/takedamageinfo.inc b/scripting/include/cbasenpc/takedamageinfo.inc
index 2e53d64..9697ae9 100644
--- a/scripting/include/cbasenpc/takedamageinfo.inc
+++ b/scripting/include/cbasenpc/takedamageinfo.inc
@@ -10,14 +10,14 @@ enum TakeDamageInfo_CritType
TakeDamageInfo_CritType_Full
};
-methodmap CTakeDamageInfo
+methodmap CTakeDamageInfo < MemoryPointer
{
/**
- * Retrieves the CTakeDamageInfo class from the given address ptr.
+ * Retrieves the CTakeDamageInfo class from the given ptr.
*
* @return The CTakeDamageInfo.
*/
- public native CTakeDamageInfo(Address ptr);
+ public native CTakeDamageInfo(MemoryPointer ptr);
/**
* Initializes the CTakeDamageInfo's values.
@@ -393,6 +393,6 @@ methodmap CTakeDamageInfo
* initialize the values of the object first using CTakeDamageInfo.Init()
* before modifying and using it in a function call.
*
- * @return Address to the global CTakeDamageInfo object.
+ * @return Handle to the global CTakeDamageInfo object. You don't have to free this handle.
*/
native CTakeDamageInfo GetGlobalDamageInfo();
\ No newline at end of file
diff --git a/third_party/safetyhook b/third_party/safetyhook
new file mode 160000
index 0000000..4c93319
--- /dev/null
+++ b/third_party/safetyhook
@@ -0,0 +1 @@
+Subproject commit 4c933195789e9a0551a49c929dc3a2dd1e8fb97f