SymImpl.cpp

00001 /*          
00002  *             Copyright (C) 2005 Maarten Keijzer
00003  *
00004  *          This program is free software; you can redistribute it and/or modify
00005  *          it under the terms of version 2 of the GNU General Public License as 
00006  *          published by the Free Software Foundation. 
00007  *
00008  *          This program is distributed in the hope that it will be useful,
00009  *          but WITHOUT ANY WARRANTY; without even the implied warranty of
00010  *          MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00011  *          GNU General Public License for more details.
00012  *
00013  *          You should have received a copy of the GNU General Public License
00014  *          along with this program; if not, write to the Free Software
00015  *          Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00016  */
00017 #include "Sym.h"
00018 
00019 using namespace std;
00020 namespace detail {
00021     
00022 class SymArgsImpl {
00023     public:
00024     std::vector<Sym> owned_args;
00025 };
00026 
00027 size_t SymArgs::len() const { 
00028     return vec().size(); 
00029 }
00030 
00031 SymArgs::SymArgs() : pimpl( new SymArgsImpl ) {
00032     args_ptr = &pimpl->owned_args;
00033 }
00034 
00035 SymArgs::SymArgs(const std::vector<Sym>& v) : pimpl(0) {
00036     args_ptr = &v;
00037 }
00038 
00039 SymArgs::~SymArgs() { 
00040     delete pimpl; 
00041 }
00042 
00043 SymArgs::SymArgs(const SymArgs& args) : pimpl(0), args_ptr(args.args_ptr) {
00044     if (args.pimpl && args.args_ptr == &args.pimpl->owned_args) {
00045         pimpl = new SymArgsImpl(*args.pimpl);
00046         args_ptr = &pimpl->owned_args; 
00047     } 
00048 }
00049 
00050 const SymArgs& SymArgs::operator=(const SymArgs& args) {
00051     if (args.pimpl && args.args_ptr == &args.pimpl->owned_args) {
00052         pimpl = new SymArgsImpl(*args.pimpl);
00053         args_ptr = &pimpl->owned_args;
00054     } else {
00055         args_ptr = args.args_ptr;
00056     }
00057 
00058     return *this;
00059 }
00060 
00061 void SymArgs::fixate() const {
00062     assert(pimpl == 0);
00063     pimpl = new SymArgsImpl;
00064     pimpl->owned_args = *args_ptr;
00065     args_ptr = &pimpl->owned_args;
00066 }
00067 
00068 // For Tackett's hashcode
00069 #define PRIMET 21523
00070 #define HASHMOD 277218551
00071 
00072 const int nprimes = 4;
00073 const unsigned long primes[] = {3221225473ul, 201326611ul, 1610612741ul, 805306457ul};
00074     
00075 int SymKey::calc_hash() const {
00076     unsigned long hash = unsigned(token);
00077     hash *= PRIMET;
00078     
00079     const std::vector<Sym>& v = args.vec();
00080     for (unsigned i = 0; i < v.size(); ++i) {
00081         hash += ( (v[i].address() >> 3) * primes[i%nprimes]) % HASHMOD;
00082     }
00083 
00084     return hash;// % HASHMOD;
00085 }
00086 
00087 bool SymKey::operator==(const SymKey& other) const {
00088     if (token != other.token) return false;
00089     return args.vec() == other.args.vec();
00090 }
00091 
00092 /* Just to store this info somewhere:
00093  * 
00094  * Address Based Hash Function Implementation
00095  * uint32 address_hash(char* addr)
00096  * {
00097  *   register uint32 key;
00098  *     key = (uint32) addr;
00099  *       return (key >> 3) * 2654435761;
00100  *  }
00101  */     
00102 
00103 SymValue::SymValue() : refcount(0), size(0), depth(0), uniqueNodeStats(0)  {}
00104 
00105 SymValue::~SymValue() { delete uniqueNodeStats; }
00106 
00107 
00108 
00109 } // namespace detail

Generated on Thu Oct 19 05:06:42 2006 for EO by  doxygen 1.3.9.1