Raised This Month: $12 Target: $400
 3% 

Orpheu: Using virtual functions


Post New Thread Reply   
 
Thread Tools Display Modes
Author Message
joaquimandrade
Veteran Member
Join Date: Dec 2008
Location: Portugal
Old 02-08-2010 , 02:44   Orpheu: Using virtual functions
Reply With Quote #1

This is a tutorial that tries to explain what virtual functions are and how to use them with orpheu.

Virtual functions are a concept present in programming used to typify a set of functions that despite being different share their intent.

For example, in Half-Life all entities can spawn, be killed, attack, despite doing it differently. Attack for a player can mean trigger a weapon, to a weapon it can mean fire a bullet, to a grenade it can mean explode. But they all can attack. That's what a virtual function is.

Even if you didn't know what a virtual function is, you already used them if you used hamsandwich. In fact, every function that hamsandwich exposes its a virtual function.

What orpheu brings new is that it is not restricted to a set of functions so you can use functions that you never could.

Inherent to virtual functions is the concept class.
A class is the representation of an object. For example, a players belongs to the C++ class CBasePlayer. Classes can be formed of other classes. For example, in Half-Life all objects that have an ID are entities. Some are items, some are weapons, some are players. But, all are entities:
  • All bots are players
  • All players are entities
  • All items are entities
  • All weapons are items
  • All grenades are weapons
Therefore:
  • All bots are entities
  • All grenade are entities
  • All weapons are entities

Classes have functions and properties.

For example:

A player can spawn and has a name.

When a function that belongs to a class (like Spawn that belongs to the class CBaseEntity (the class from which all other classes that represent entities are built upon)) is meant to represent a concept to be implemented differently accordingly to the class that is based on it, it is a virtual function.

This is the relationships tree for the class CBasePlayer taken from here

  • CBaseEntity
  • CBaseDelay
    • CBaseAnimating
      • CBaseToggle
        • CBaseMonster
          • CBasePlayer
This means that a player is a monster,a toggle, an animating,a delay, and an entity. Whatever that means. For this tutorial that means that for players you can use every virtual function present in each one of the classes in CBasePlayer's tree.

Another thing you have to note is that those functions were made in C++ and their arguments have types unlike in pawn (where everything is a cell or a group of cells).

For example, take a look to this C++ function header:

PHP Code:
UTIL_FindEntityByClassname(CBaseEntity *,char *) 
It can be read as:

Function name - UTIL_FindEntityByClassname
Function first argument type - CBaseEntity *
Function second argument type - char *

This function doesn't belong to any class.

This is how functions pertaining to a class are represented:

PHP Code:
 CBasePlayer::Killed(entvars_s *,int
It can be read as:

Function class - CBasePlayer
Function name - Killed
Function first argument type - entvars_s *
Function second argument type - int

To use these functions you don't really need to care with what each type means or how it works. What you need to care with is in identify them so you can produce a file that will teach orpheu how to convert them to pawn. That will be addressed latter.

So, why are virtual functions considered differently for our purposes?
By identifying a virtual function you can automatically identify all its implementations (By identifying CBaseEntity::Spawn you automatically identify CBasePlayer::Spawn, CBasePlayerWeapon::Spawn, etc) and identifying them is easy.

The technique (that I learned with hamsandwich) consists on the following:
each class contains a table (an array) where references to the virtual functions associated with it are kept. So, by providing an offset, we can address them.

Take a look at the file "configs/hamdata.ini"

You can see that in this portion of text:

Code:
    spawn 2
    precache 3
    keyvalue 5
    objectcaps 8
Spawn has the offset 2.
It means that a reference to the function Spawn is kept in the virtual table of all classes that implement the function Spawn in the index 2.
This index depends on the mod and on the operative system and in practice it means that you can use virtual functions as long as you know their index in the virtual table.

Now let's search for virtual functions that we can use with orpheu.

Another thing to note is that you need the library of the mod you are dealing with in its linux version. Like cs_i386.so.

First, download this software:
http://www.hex-rays.com/idapro/idadownfreeware.htm

Install it an open it.

[IMG]http://img208.**************/img208/8749/12820721.png[/IMG]

Select New

[IMG]http://img694.**************/img694/1284/37280226.png[/IMG]

ELF/COFF Dynamic Library

OK

Now it will process the library. Wait for it to finish. To know when it is done take a look at the bottommost left corner and wait for it to display "idle".

Now maximize and order by name the windows Names:

[IMG]http://img705.**************/img705/7720/60593861.png[/IMG]

Now, to see the virtual table of the class CBaseEntity go to:

[IMG]http://img9.**************/img9/4030/78923133.png[/IMG]

Open it:


[IMG]http://img697.**************/img697/6669/56470347.png[/IMG]
This list of names represent the virtual functions of the class CBaseEntity.

There is nothing interesting here so let's go to the virtual table of the class CBasePlayer. Go to the windows Names again and search for CBasePlayer::'vtbl' and open it:

[IMG]http://img199.**************/img199/1285/12974837.png[/IMG]

You will have now:

[IMG]http://img17.**************/img17/8241/65668435.png[/IMG]

So let's say we want to use the function OnTouchingWeapon.

First we have to know its index. Its index is its position on that list, starting on 0 and knowing that the first unnamed functions don't count on Windows:

[IMG]http://img200.**************/img200/9868/38486216.png[/IMG]


So, Spawn is 0 on Windows and 2 on Linux.

To get the index the index of OnTouchingWeapon you can count over the list or do this but, beware that that tutorial depends on a non free version of this software.

The index is 87 for windows and 89 for linux (+2).

Now, double click over OnTouchingWeapon:

[IMG]http://img32.**************/img32/3684/32048341.png[/IMG]

So we have the header:

CBasePlayer::OnTouchingWeapon(CWeaponBox *)

It can be read as

Function class - CBasePlayer
Function name - OnTouchingWeapon
Function first argument type - CWeaponBox *

So, we now have to build a file to make orpheu aware of the function.

Go to "configs/orpheu/virtualFunctions"

Now you have to create (if it doesn't exist) a folder called CBasePlayer. This is meant to enforce organization and it's mandatory.

Inside it create a file named OnTouchingWeapon. It should look like:
Code:
{
    "name" : "OnTouchingWeapon",
    "class" : "CBasePlayer",
    "library" : "mod",
    "arguments" : 
    [
        {
            "type" : "CWeaponBox *"
        }
    ],
    "indexes" : 
    [
        {
            "os" : "windows",
            "mod" : "cstrike",
            "value" : 87
        },
        {
            "os" : "linux",
            "mod" : "cstrike",
            "value" : 89
        }
    ]
}
To finish, you need something like this in a plugin:
PHP Code:

    
#include <amxmodx>
    #include <orpheu>
    
    
public plugin_init()
    {
        new 
OrpheuFunction:Player_OnTouchingWeapon OrpheuGetFunctionFromClass("player","OnTouchingWeapon","CBasePlayer")
        
OrpheuRegisterHook(Player_OnTouchingWeapon,"OnTouchingWeapon")
    }
    
    public 
OnTouchingWeapon(id,weaponboxID)
    {
        
    } 
__________________
joaquimandrade is offline
joaquimandrade
Veteran Member
Join Date: Dec 2008
Location: Portugal
Old 02-08-2010 , 02:45   Re: Orpheu: Using virtual functions
Reply With Quote #2

If you have any trouble while following the tutorial, I'm here.
__________________
joaquimandrade is offline
Arkshine
AMX Mod X Plugin Approver
Join Date: Oct 2005
Old 02-08-2010 , 03:15   Re: Orpheu: Using virtual functions
Reply With Quote #3

I thought you must use with InstallGameRules ? Now, no ?
__________________
Arkshine is offline
joaquimandrade
Veteran Member
Join Date: Dec 2008
Location: Portugal
Old 02-08-2010 , 03:22   Re: Orpheu: Using virtual functions
Reply With Quote #4

Quote:
Originally Posted by Arkshine View Post
I thought you must use with InstallGameRules ? Now, no ?

InstallGameRules was to retrieve the CHalfLifeMultiplay object to hook virtual functions of it.

Here we are talking about of virtual functions of entities.
__________________

Last edited by joaquimandrade; 02-08-2010 at 03:35.
joaquimandrade is offline
Arkshine
AMX Mod X Plugin Approver
Join Date: Oct 2005
Old 02-08-2010 , 03:34   Re: Orpheu: Using virtual functions
Reply With Quote #5

I just wake up and I was just confusing with another thing, now it's ok.
__________________
Arkshine is offline
Exolent[jNr]
Veteran Member
Join Date: Feb 2007
Location: Tennessee
Old 02-08-2010 , 12:46   Re: Orpheu: Using virtual functions
Reply With Quote #6

+love
__________________
No private work or selling mods.
Quote:
Originally Posted by xPaw View Post
I love you exolent!
Exolent[jNr] is offline
01101101
BANNED
Join Date: Nov 2009
Location: 9`su 09`n0n7e`r0f76a
Old 02-08-2010 , 14:51   Re: Orpheu: Using virtual functions
Reply With Quote #7

;wait;+love
01101101 is offline
stupok
Veteran Member
Join Date: Feb 2006
Old 02-09-2010 , 16:31   Re: Orpheu: Using virtual functions
Reply With Quote #8

This is very cool, Joaquim. If I write more plugins, then I will use orpheu and it will be awesome. +love
__________________
stupok is offline
Dr.G
Senior Member
Join Date: Nov 2008
Old 02-11-2010 , 12:51   Re: Orpheu: Using virtual functions
Reply With Quote #9

WOW this is amazing! HAIL joaquim andrade! Thank you so much!
__________________
Dr.G is offline
joaquimandrade
Veteran Member
Join Date: Dec 2008
Location: Portugal
Old 02-11-2010 , 13:00   Re: Orpheu: Using virtual functions
Reply With Quote #10

Thanks
__________________
joaquimandrade is offline
Reply


Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT -4. The time now is 08:50.


Powered by vBulletin®
Copyright ©2000 - 2024, vBulletin Solutions, Inc.
Theme made by Freecode