c++ oo syntax behind the scenes behavior

Started by
21 comments, last by King Mir 10 years ago



Quote
non virtual method calls require no vmt lookup, correct?
Yes. And if the class itself has zero virtual functions, then it won't have any Virtual Method Table.

I think you're confusing a pointer to the vtable and the vtable itself. An object will store a pointer to the vtable not the full table. The vtables themselves are generally stored in a read only data segment.

Yep, already edited my post. I should remember to hold off on posting in the morning until after breakfast. laugh.png

all this seems to imply that all method calls require dereferencing the object's vmt pointer to get the jump address of the actual method to use. i thought non-virtual methods had their jump addresses stored in the objects, to avoid the derferencing overhead.

so all method calls become: gosub vmt_ptr->method->address ?

IE gosub to the address of <method> stored in the vmt pointed to by vmt_ptr ?

for non-virtual, I thought it was more like: gosub instance.method_address[method]

and a stand alone function, by comparison is simply: gosub method_address, correct?

Norm Barrows

Rockland Software Productions

"Building PC games since 1989"

rocklandsoftware.net

PLAY CAVEMAN NOW!

http://rocklandsoftware.net/beta.php

Advertisement


for non-virtual, I thought it was more like: gosub instance.method_address[method]

and a stand alone function, by comparison is simply: gosub method_address, correct?

A non-virtual member function and a stand-alone function are pretty much the same thing. The method address is known after linking. The only real difference is the implicit "this" argument.

fascinating! i thought local declarations did a new in the background and a dispose on return, using the heap.[/quote] Things only go on the heap if they are explicitly allocated, either directly or indirectly. If the object you create on the stack uses allocation with new, then that data would go on the heap. The pointer to that data would be on the stack. If the object you created was on the heap then both the pointer and the other data would both go on the heap. Its basically recursive. Say you created an object on the heap and called a member function. If that member function has local variables then they would be pushed onto the stack even though the object itself was allocated on the heap. This is due to the way the compiler treats executable code.

would object1 go on the stack when main was called? or is main a special case and it goes in the data segment?
main is exactly like any other function except it is called by the operating system rather than your program.

object1 (its member var storage space) would go in the data segment?
That would go in the data segment. While I said that main is a special case, it's slightly more complicated than I implied. main is actually called indirectly by the operating system in most environments. The operating system will generally call a function implemented in the run-time library. You can read a little about it here. That link mentions that the run-time library will initialize global variables before main is called. If the operating system called main directly then none of the constructors for the global variables would be called, among other things.

C++: A Dialog | C++0x Features: Part1 (lambdas, auto, static_assert) , Part 2 (rvalue references) , Part 3 (decltype) | Write Games | Fix Your Timestep!


A non-virtual member function and a stand-alone function are pretty much the same thing. The method address is known after linking.

ok, so the vmt addresses replace the non-virtual method calls at link time, correct?

i _thought_ they were the same thing....

Norm Barrows

Rockland Software Productions

"Building PC games since 1989"

rocklandsoftware.net

PLAY CAVEMAN NOW!

http://rocklandsoftware.net/beta.php


Things only go on the heap if they are explicitly allocated, either directly or indirectly.

i was under the impression that all were allocated on the heap, except global instances, which were allocated in the data segment at load time.

thanks for clarifying that. (lending a machete to my intellectual thicket).

and locally declared instances, being allocated on the heap, are automatically de-allocated when they go out of scope. and they don't use the heap so no possibility of memory leak. just the usual cross your i's and dot your t's stuff with malloc and free under different names (new and dispose) - correct?

Norm Barrows

Rockland Software Productions

"Building PC games since 1989"

rocklandsoftware.net

PLAY CAVEMAN NOW!

http://rocklandsoftware.net/beta.php

would object1 go on the stack when main was called? or is main a special case and it goes in the data segment?
main is exactly like any other function except it is called by the operating system rather than your program.

Almost. You cannot legally call main from your program in c++. This design was because the compiler may wish to insert additional setup code at the beginning of main.


class MyClass; //Declare a class. Nothing created yet.

int main()
{
    MyClass *instance = new MyClass; //An instance created on the heap.

    MyClass instance; //An instance created on the stack.
}

If declared on the stack, the class is constructed when the code calls that function and the function reaches that line of code. Whether or not they are allocated before the function is called I *think* might be up to the compiler.

The above has to do with variables created inside functions.

If a variable is global, or if a variable is a static member-variable of a class (which is just a global variable in the class's namespace), then you can't count on the order or timing of when they are constructed. The only thing you can depend on is that they'll be constructed before int main() enters... but other than that, the order is compiler-specific.

This is one of the reasons why programmers avoid global variables in C++. I've dealt with, in my own code, far too many bugs caused by global variables.

Global variables are a convenience, but they end up hurting more than they help. Global constants are usually fine though.


If a variable is global, or if a variable is a static member-variable of a class (which is just a global variable in the class's namespace), then you can't count on the order or timing of when they are constructed. The only thing you can depend on is that they'll be constructed before int main() enters... but other than that, the order is compiler-specific.

right, startup code constructor hell. you can't rely on other globals being valid during your custom constructor. i hear about this a fair amount. i would think an explicit init() would take care of it. bad form?

Norm Barrows

Rockland Software Productions

"Building PC games since 1989"

rocklandsoftware.net

PLAY CAVEMAN NOW!

http://rocklandsoftware.net/beta.php

If a variable is global, or if a variable is a static member-variable of a class (which is just a global variable in the class's namespace), then you can't count on the order or timing of when they are constructed. The only thing you can depend on is that they'll be constructed before int main() enters... but other than that, the order is compiler-specific.


right, startup code constructor hell. you can't rely on other globals being valid during your custom constructor. i hear about this a fair amount. i would think an explicit init() would take care of it. bad form?
Very bad.

I once had the misfortune of working on a port that severely abused global variables.

It took so long to run the pre-main initialization that we could not pass certification as-is. We had to hack in to the runtime and display the splash screen. Rather than the normal sleep while a splash was running, it spent those seconds initializing variables and doing other pre-main work.

IIRC it took something like five seconds between execution start and the beginning of main.

Just don't start down that road. It is a horrible thing.

except global instances, which were allocated in the data segment at load time.

It depends on the compiler you use, but generally yes, a global object will exist in the data segment, specifically in the bss section if it is a basic datatype or a structure containing basic datatypes. This isn't written in stone, though, and it's possible for it to also be allocated on the heap, or even on the stack.

"I would try to find halo source code by bungie best fps engine ever created, u see why call of duty loses speed due to its detail." -- GettingNifty

This topic is closed to new replies.

Advertisement