zero-cost singleton

考えてみるまに使ってみた方が速かろーと思って作ってみた。 singleton template は、まぁラクだけど Singleton::instance() を呼ぶたびに if が呼ばれるのがなんか、なんか…と貧乏症プログラマとしては思う、ということで一度目の呼出し時に自己書き換えして、二度目からの呼出しからは、ただの

    static T_* instance() {
        return instance_;
    }

になるように。

んでベンチ取ってみたら、なんか非最適化時は速くなってるんだけど、最適化時はほんの少ししか速くなってない。今度理由を考えます。

あと double checked なんとかにはあんまり興味が。

#include <sys/mman.h>

template <class T_>
class Singleton {
public:
    static T_* instance() {
        if (!instance_) {
            instance_ = new T_;
            unsigned char* p = (unsigned char*)instance;
            mprotect((void*)(((int)p) & ~4095 - 4096),
                     4096, PROT_READ | PROT_WRITE | PROT_EXEC);
            p += 7;
            p[0] = 0xa1;
            void** i = (void**)p+1;
            i[0] = instance_;
            p[5] = 0xc9;
            p[6] = 0xc3;
        }
        return instance_;
    }

protected:
    Singleton() {}
    // no virtual destructor, you will not delete Singleton*

private:
    static T_* instance_;
};

template<class T_>
T_* Singleton<T_>::instance_ = 0;

追記:

おおおそういえばもとはといえば、memoizeとか、そのへん→sayさんの記述でなんとなく頭の中に→ヨタ話として少し喋る→ヨタ話としてメール→言ってる間に作ろう、という経緯だったのですが、記憶喪失気味なので 2-hop の距離があると覚えてませんでした。

http://d.hatena.ne.jp/sa-y/20051215#1134649858

http://d.hatena.ne.jp/sa-y/20051219#1134971623

なにかあれば下記メールアドレスへ。
shinichiro.hamaji _at_ gmail.com
shinichiro.h