Sign in to follow this  

Unnecessary null check of static_cast

This topic is 3249 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

There are lots of static_cast's from base class pointer to derived class pointer in my code and that's probably unevitable without rewriting major portion of code. (I'm using static polymorphism) Well everything is fine except null check of the static_cast. It seems to be causing certain degree of overhead. The problem is I know the pointer can never be null but have no way to tell compiler. So is there any way to perform static_cast without null check? I wrote this function but it's too crappy even for me :D
template<typename T, typename U> inline T unsafe_cast(U p)
{
    return reinterpret_cast<T>(
        reinterpret_cast<char*>(p)
        + reinterpret_cast<ptrdiff_t>(static_cast<T>((U)1))
        - 1
    );
}


... 
struct A { int x; };
struct B { int y; };
struct C : A, B {};

int main()
{
    B* p;
    C* volatile q = unsafe_cast<C*>(p);
}


Thanks in advance

Share this post


Link to post
Share on other sites
Quote:
Original post by muse1987
So is there any way to perform static_cast without null check? I wrote this function but it's too crappy even for me :D
Static-cast references instead of pointers?

Share this post


Link to post
Share on other sites
I tried it but didn't make any difference. (in VC9 SP1. No idea about other compilers)

I think the standard defines null reference as "undefined behavior" so that's part of Microsoft-specific behavior?

edit: This is the code I used to test

struct A { int x; };
struct B { int y; };
struct C : A, B {};


int main()
{
B* p;
C& q = static_cast<C&>(*p);
printf("%p", &q);
}


Share this post


Link to post
Share on other sites
You appear to be casting an uninitialized pointer?

If I'm not wrong, for static cast to work the pointer should actually point to an instance of the type you are casting it to.

dynamic_cast differs from static_cast in that it returns 0, if the cast wouldn't be valid.

Share this post


Link to post
Share on other sites
Quote:
Original post by visitor
You appear to be casting an uninitialized pointer?

If I'm not wrong, for static cast to work the pointer should actually point to an instance of the type you are casting it to.

dynamic_cast differs from static_cast in that it returns 0, if the cast wouldn't be valid.


Well, yes. If I initialize the pointer with address of local variable or any constant expression then the compiler definitely optimizes it. But I'm trying to optimize it when the compiler cannot make any assumption about it, like parameter of virtual function. (only I know the pointer cannot be NULL)

Share this post


Link to post
Share on other sites
// compile-time type check
// result is not assigned so it will be omitted in compiled code
static_cast<T>((U)1);
return
reinterpret_cast<T>(
reinterpret_cast<char*>(p)
+ reinterpret_cast<ptrdiff_t>( (T)((U)1) )
- 1
);


And hopefully, this is done in release build. Since entire part after (p) is a constant and evaluated during compilation.

Share this post


Link to post
Share on other sites
Quote:
Original post by Extrarius
In MSVC, you can use the '__assume' keyword to help the optimizer with assumptions. For example: __assume(ptr != NULL)


Yeees! That's exactly what I was looking for. Thanks very much. :)

Share this post


Link to post
Share on other sites

This topic is 3249 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this