<commit_before>/// HEADER
#include <csapex/param/bitset_parameter.h>

/// SYSTEM
#include <yaml-cpp/yaml.h>
#include <boost/any.hpp>

using namespace csapex;
using namespace param;

BitSetParameter::BitSetParameter()
    : ParameterImplementation("noname", ParameterDescription())
{
}

BitSetParameter::BitSetParameter(const std::string &name, const ParameterDescription& description)
    : ParameterImplementation(name, description),
      value_(0)
{
}

BitSetParameter::~BitSetParameter()
{

}

bool BitSetParameter::accepts(const std::type_info& type) const
{
    return type == typeid(int) || type == typeid(std::pair<std::string, bool>);
}

void BitSetParameter::setByName(const std::string &name)
{
    for(std::map<std::string, int>::iterator it = set_.begin(); it != set_.end(); ++it) {
        if(it->first == name) {
            value_ = it->second;
            triggerChange();
            return;
        }
    }

    throw std::runtime_error(std::string("no such parameter: ") + name);
}

void BitSetParameter::setBitSet(const std::map<std::string, int> &set)
{
    set_ = set;
    scope_changed(this);
}

std::map<std::string, int> BitSetParameter::getBitSet() const
{
    return set_;
}

void BitSetParameter::clear()
{
    value_ = 0;
    triggerChange();
}

void BitSetParameter::setBits(const std::vector<std::string> &elements, bool silent)
{
    bool change = false;

    for(std::map<std::string, int>::iterator set_it = set_.begin(); set_it != set_.end(); ++set_it) {
        bool found = false;
        const std::string& e = set_it->first;
        for(std::vector<std::string>::const_iterator e_it = elements.begin(); e_it != elements.end(); ++e_it) {
            if(e == *e_it) {
                found = true;
                break;
            }
        }
        if(found) {
            if(!isSet(e)) {
                setBit(e, true);
                change = true;
            }
        } else {
            if(isSet(e)) {
                clearBit(e, true);
                change = true;
            }
        }
    }

    if(change && !silent) {
        triggerChange();
    }
}

void BitSetParameter::setBitTo(const std::string &element, bool set, bool silent)
{
    for(std::map<std::string, int>::iterator it = set_.begin(); it != set_.end(); ++it) {
        if(it->first == element) {
            if(set) {
                value_ |= it->second;
            } else {
                value_ &= ~(it->second);
            }

            if(!silent) {
                triggerChange();
            }
            return;
        }
    }
}

void BitSetParameter::setBit(const std::string &element, bool silent)
{
    setBitTo(element, true, silent);
}

void BitSetParameter::clearBit(const std::string &element, bool silent)
{
    setBitTo(element, false, silent);
}

bool BitSetParameter::isSet(const std::string &element) const
{
    for(std::map<std::string, int>::const_iterator it = set_.begin(); it != set_.end(); ++it) {
        if(it->first == element) {
            int target = it->second;

            return (value_ & target) == target;
        }
    }
    return false;
}

int BitSetParameter::noParameters() const
{
    return set_.size();
}

std::string BitSetParameter::getName(int idx) const
{
    std::map<std::string, int>::const_iterator i = set_.begin();
    std::advance(i, idx);
    return i->first;
}

std::string BitSetParameter::getName() const
{
    throw std::runtime_error("cannot get the name for parameter '" + name() + "'");
}

const std::type_info& BitSetParameter::type() const
{
    return typeid(int);
}

std::string BitSetParameter::toStringImpl() const
{
    return std::string("[bitset: ") +  "]";
}

void BitSetParameter::get_unsafe(boost::any& out) const
{
    out = value_;
}

bool BitSetParameter::set_unsafe(const boost::any &v)
{
    if(v.type() == typeid(int)) {
        int val = boost::any_cast<int>(v);
        if(val != value_) {
            value_ = val;
            return true;
        }
    } else if(v.type() == typeid(std::pair<std::string, bool>)) {
        auto pair = boost::any_cast<std::pair<std::string, bool>>(v);
        setBitTo(pair.first, pair.second);
        return true;
    }

    return false;
}

void BitSetParameter::doSetValueFrom(const Parameter &other)
{
    const BitSetParameter* range = dynamic_cast<const BitSetParameter*>(&other);
    if(range) {
        if(value_ != range->value_) {
            value_ = range->value_;
            triggerChange();
        }
    } else {
        throw std::runtime_error("bad setFrom, invalid types");
    }
}

void BitSetParameter::doClone(const Parameter &other)
{
    const BitSetParameter* range = dynamic_cast<const BitSetParameter*>(&other);
    if(range) {
        value_ = range->value_;
        set_ = range->set_;
        def_ = range->def_;
    } else {
        throw std::runtime_error("bad clone, invalid types");
    }
}

void BitSetParameter::doSerialize(YAML::Node& n) const
{
    n["int"] = boost::any_cast<int> (value_);
}

void BitSetParameter::doDeserialize(const YAML::Node& n)
{
    if(n["int"].IsDefined()) {
        value_ = n["int"].as<int>();
    }
}
<commit_msg>param: save values for bitset parameter<commit_after>/// HEADER
#include <csapex/param/bitset_parameter.h>

/// SYSTEM
#include <yaml-cpp/yaml.h>
#include <boost/any.hpp>

using namespace csapex;
using namespace param;

BitSetParameter::BitSetParameter()
    : ParameterImplementation("noname", ParameterDescription())
{
}

BitSetParameter::BitSetParameter(const std::string &name, const ParameterDescription& description)
    : ParameterImplementation(name, description),
      value_(0)
{
}

BitSetParameter::~BitSetParameter()
{

}

bool BitSetParameter::accepts(const std::type_info& type) const
{
    return type == typeid(int) || type == typeid(std::pair<std::string, bool>);
}

void BitSetParameter::setByName(const std::string &name)
{
    for(std::map<std::string, int>::iterator it = set_.begin(); it != set_.end(); ++it) {
        if(it->first == name) {
            value_ = it->second;
            triggerChange();
            return;
        }
    }

    throw std::runtime_error(std::string("no such parameter: ") + name);
}

void BitSetParameter::setBitSet(const std::map<std::string, int> &set)
{
    set_ = set;
    scope_changed(this);
}

std::map<std::string, int> BitSetParameter::getBitSet() const
{
    return set_;
}

void BitSetParameter::clear()
{
    value_ = 0;
    triggerChange();
}

void BitSetParameter::setBits(const std::vector<std::string> &elements, bool silent)
{
    bool change = false;

    for(std::map<std::string, int>::iterator set_it = set_.begin(); set_it != set_.end(); ++set_it) {
        bool found = false;
        const std::string& e = set_it->first;
        for(std::vector<std::string>::const_iterator e_it = elements.begin(); e_it != elements.end(); ++e_it) {
            if(e == *e_it) {
                found = true;
                break;
            }
        }
        if(found) {
            if(!isSet(e)) {
                setBit(e, true);
                change = true;
            }
        } else {
            if(isSet(e)) {
                clearBit(e, true);
                change = true;
            }
        }
    }

    if(change && !silent) {
        triggerChange();
    }
}

void BitSetParameter::setBitTo(const std::string &element, bool set, bool silent)
{
    for(std::map<std::string, int>::iterator it = set_.begin(); it != set_.end(); ++it) {
        if(it->first == element) {
            if(set) {
                value_ |= it->second;
            } else {
                value_ &= ~(it->second);
            }

            if(!silent) {
                triggerChange();
            }
            return;
        }
    }
}

void BitSetParameter::setBit(const std::string &element, bool silent)
{
    setBitTo(element, true, silent);
}

void BitSetParameter::clearBit(const std::string &element, bool silent)
{
    setBitTo(element, false, silent);
}

bool BitSetParameter::isSet(const std::string &element) const
{
    for(std::map<std::string, int>::const_iterator it = set_.begin(); it != set_.end(); ++it) {
        if(it->first == element) {
            int target = it->second;

            return (value_ & target) == target;
        }
    }
    return false;
}

int BitSetParameter::noParameters() const
{
    return set_.size();
}

std::string BitSetParameter::getName(int idx) const
{
    std::map<std::string, int>::const_iterator i = set_.begin();
    std::advance(i, idx);
    return i->first;
}

std::string BitSetParameter::getName() const
{
    throw std::runtime_error("cannot get the name for parameter '" + name() + "'");
}

const std::type_info& BitSetParameter::type() const
{
    return typeid(int);
}

std::string BitSetParameter::toStringImpl() const
{
    return std::string("[bitset: ") +  "]";
}

void BitSetParameter::get_unsafe(boost::any& out) const
{
    out = value_;
}

bool BitSetParameter::set_unsafe(const boost::any &v)
{
    if(v.type() == typeid(int)) {
        int val = boost::any_cast<int>(v);
        if(val != value_) {
            value_ = val;
            return true;
        }
    } else if(v.type() == typeid(std::pair<std::string, bool>)) {
        auto pair = boost::any_cast<std::pair<std::string, bool>>(v);
        setBitTo(pair.first, pair.second);
        return true;
    }

    return false;
}

void BitSetParameter::doSetValueFrom(const Parameter &other)
{
    const BitSetParameter* range = dynamic_cast<const BitSetParameter*>(&other);
    if(range) {
        if(value_ != range->value_) {
            value_ = range->value_;
            triggerChange();
        }
    } else {
        throw std::runtime_error("bad setFrom, invalid types");
    }
}

void BitSetParameter::doClone(const Parameter &other)
{
    const BitSetParameter* range = dynamic_cast<const BitSetParameter*>(&other);
    if(range) {
        value_ = range->value_;
        set_ = range->set_;
        def_ = range->def_;
    } else {
        throw std::runtime_error("bad clone, invalid types");
    }
}

void BitSetParameter::doSerialize(YAML::Node& n) const
{
    n["int"] = boost::any_cast<int> (value_);
    n["values"] = set_;
}

void BitSetParameter::doDeserialize(const YAML::Node& n)
{
    if(n["int"].IsDefined()) {
        value_ = n["int"].as<int>();
    }

    if (n["values"].IsDefined()) {
        set_ = n["values"].as<std::map<std::string, int>>();
        int full_mask = 0;
        for (auto& entry : set_)
            full_mask |= entry.second;

        value_ &= full_mask;
    }
}
<|endoftext|>


<commit_before>#include <stdio.h>
#include <node.h>
#include <v8.h>
#include <string>
#include "Types.h"
#include "JuliaExecEnv.h"

using namespace std;
using namespace v8;

static JuliaExecEnv *J = 0;

void returnNull(const FunctionCallbackInfo<Value> &args,Isolate *I)
{
   args.GetReturnValue().SetNull();
}

void returnString(const FunctionCallbackInfo<Value> &args,Isolate *I,const string &s)
{
   args.GetReturnValue().Set(String::NewFromUtf8(I,s.c_str()));
}

void callback(const FunctionCallbackInfo<Value>& args,Isolate *I,const Local<Function> &cb,int argc,Local<Value> *argv)
{
  cb->Call(I->GetCurrentContext()->Global(),argc,argv);
}

void buildArgs(Isolate *I,const std::shared_ptr<std::vector<std::shared_ptr<nj::Value>>> &res,int argc,Local<Value> *argv)
{
   int index = 0;

   for(std::shared_ptr<nj::Value> value: *res)
   {
      if(value.get())
      {
         switch(value->getTypeId())
         {
            case nj::null_type:
               argv[index++] = Null(I);
            break;
            case nj::boolean_type:
               argv[index++] = Boolean::New(I,value->toBoolean());
            break;
            case nj::int_type:
               argv[index++] = Number::New(I,value->toInt());
            break;
            case nj::float_type:
               argv[index++] = Number::New(I,value->toFloat());
            break;
            case nj::string_type:
               argv[index++] = String::NewFromUtf8(I,value->toString().c_str());
            break;
         }
      }
   }
}

void doEval(const FunctionCallbackInfo<Value> &args)
{
   Isolate *I = Isolate::GetCurrent();
   HandleScope scope(I);
   int numArgs = args.Length();

   if(numArgs < 2 || !J)
   {
      returnNull(args,I);
      return;
   }

   Local<String> arg0 = args[0]->ToString();
   String::Utf8Value text(arg0);
   Local<Function> cb = Local<Function>::Cast(args[1]);
   JMain *engine;

   if(text.length() > 0 && (engine = J->getEngine()))
   {
      engine->evalQueuePut(*text);
printf("enqueud a query %s\n",*text);
      std::shared_ptr<std::vector<std::shared_ptr<nj::Value>>> res = engine->resultQueueGet();

printf("Dequeued a Result\n");

      if(res.get())
      {
         int argc = res->size();
         Local<Value> *argv = new Local<Value>[argc];
         buildArgs(I,res,argc,argv);
         callback(args,I,cb,argc,argv);
      }
   }
   else
   {
      const unsigned argc = 1;
      Local<Value> argv[argc] = { String::NewFromUtf8(I,"") };
      callback(args,I,cb,argc,argv);
   }
}

void doStart(const FunctionCallbackInfo<Value> &args)
{
   Isolate *I = Isolate::GetCurrent();
   HandleScope scope(I);
   int numArgs = args.Length();

   if(numArgs == 0)
   {
      returnString(args,I,"");
      return;
   }

   Local<String> arg0 = args[0]->ToString();
   String::Utf8Value plainText_av(arg0);

   if(plainText_av.length() > 0)
   {
      if(!J) J = new JuliaExecEnv(*plainText_av);

      returnString(args,I,"Julia Started");
   }
   else returnString(args,I,"");
}

void init(Handle<Object> exports)
{
  NODE_SET_METHOD(exports,"start",doStart);
  NODE_SET_METHOD(exports,"eval",doEval);
}

NODE_MODULE(nj,init)
<commit_msg>Yet more debugging<commit_after>#include <stdio.h>
#include <node.h>
#include <v8.h>
#include <string>
#include "Types.h"
#include "JuliaExecEnv.h"

using namespace std;
using namespace v8;

static JuliaExecEnv *J = 0;

void returnNull(const FunctionCallbackInfo<Value> &args,Isolate *I)
{
   args.GetReturnValue().SetNull();
}

void returnString(const FunctionCallbackInfo<Value> &args,Isolate *I,const string &s)
{
   args.GetReturnValue().Set(String::NewFromUtf8(I,s.c_str()));
}

void callback(const FunctionCallbackInfo<Value>& args,Isolate *I,const Local<Function> &cb,int argc,Local<Value> *argv)
{
  cb->Call(I->GetCurrentContext()->Global(),argc,argv);
}

void buildArgs(Isolate *I,const std::shared_ptr<std::vector<std::shared_ptr<nj::Value>>> &res,int argc,Local<Value> *argv)
{
   int index = 0;
printf("In build args\n");
   for(std::shared_ptr<nj::Value> value: *res)
   {
printf("building arg %d\n",index);
      if(value.get())
      {
         switch(value->getTypeId())
         {
            case nj::null_type:
printf("arg is null\n");
               argv[index++] = Null(I);
            break;
            case nj::boolean_type:
printf("arg is %d\n",value->toBoolean());
               argv[index++] = Boolean::New(I,value->toBoolean());
            break;
            case nj::int_type:
printf("arg is %lld\n",value->toInt());
               argv[index++] = Number::New(I,value->toInt());
            break;
            case nj::float_type:
printf("arg is %f\n",value->toFloat());
               argv[index++] = Number::New(I,value->toFloat());
            break;
            case nj::string_type:
printf("arg is %s\n",value->toString().c_str());
               argv[index++] = String::NewFromUtf8(I,value->toString().c_str());
            break;
         }
      }
   }
}

void doEval(const FunctionCallbackInfo<Value> &args)
{
   Isolate *I = Isolate::GetCurrent();
   HandleScope scope(I);
   int numArgs = args.Length();

   if(numArgs < 2 || !J)
   {
      returnNull(args,I);
      return;
   }

   Local<String> arg0 = args[0]->ToString();
   String::Utf8Value text(arg0);
   Local<Function> cb = Local<Function>::Cast(args[1]);
   JMain *engine;

   if(text.length() > 0 && (engine = J->getEngine()))
   {
      engine->evalQueuePut(*text);
printf("enqueud a query %s\n",*text);
      std::shared_ptr<std::vector<std::shared_ptr<nj::Value>>> res = engine->resultQueueGet();

printf("Dequeued a Result\n");

      if(res.get())
      {
         int argc = res->size();
         Local<Value> *argv = new Local<Value>[argc];
         buildArgs(I,res,argc,argv);
         callback(args,I,cb,argc,argv);
      }
   }
   else
   {
      const unsigned argc = 1;
      Local<Value> argv[argc] = { String::NewFromUtf8(I,"") };
      callback(args,I,cb,argc,argv);
   }
}

void doStart(const FunctionCallbackInfo<Value> &args)
{
   Isolate *I = Isolate::GetCurrent();
   HandleScope scope(I);
   int numArgs = args.Length();

   if(numArgs == 0)
   {
      returnString(args,I,"");
      return;
   }

   Local<String> arg0 = args[0]->ToString();
   String::Utf8Value plainText_av(arg0);

   if(plainText_av.length() > 0)
   {
      if(!J) J = new JuliaExecEnv(*plainText_av);

      returnString(args,I,"Julia Started");
   }
   else returnString(args,I,"");
}

void init(Handle<Object> exports)
{
  NODE_SET_METHOD(exports,"start",doStart);
  NODE_SET_METHOD(exports,"eval",doEval);
}

NODE_MODULE(nj,init)
<|endoftext|>


<commit_before>#include <stddef.h>
#include <stdlib.h>
#include <new>
#include <string>
#include <locale>
#include <stdio.h>
#include <iostream>
#include "novoht.h"

NoVoHT::NoVoHT(){
   kvpairs = new kvpair*[1000];
   size = 1000;
   numEl = 0;
   magicNumber = 1000;
   resizeNum = -1;
   resizing=false;
   map_lock=false;
   write_lock=false;
   resizing = false;
   oldpairs = NULL;
}

/*
NoVoHT::NoVoHT(int s){
   kvpairs = new kvpair*[s];
   size = s;
   numEl=0;
   file = NULL;
}

NoVoHT::NoVoHT(char * f){
   kvpairs = new kvpair*[1000];
   size = 1000;
   numEl=0;
   file = f;
   readFile();
}
*/
NoVoHT::NoVoHT(string f,int s, int m){
   kvpairs = new kvpair*[s];
   for (int x = 0;x<s;x++){
      kvpairs[x] = NULL;
   }
   resizing=false;
   map_lock=false;
   write_lock=false;
   magicNumber = m;
   nRem = 0;
   resizeNum = 0;
   size = s;
   numEl=0;
   filename=f;
   dbfile = fopen(f.c_str(), "r+");
   if (!dbfile) dbfile = fopen(f.c_str(), "w+");
   readFile();
   oldpairs = NULL;
}
NoVoHT::NoVoHT(string f,int s, int m, float r){
   kvpairs = new kvpair*[s];
   for (int x = 0;x<s;x++){
      kvpairs[x] = NULL;
   }
   resizing=false;
   map_lock=false;
   write_lock=false;
   magicNumber = m;
   nRem = 0;
   resizeNum = r;
   size = s;
   numEl=0;
   filename=f;
   dbfile = fopen(f.c_str(), "r+");
   if (!dbfile) dbfile = fopen(f.c_str(), "w+");
   readFile();
   oldpairs = NULL;
}
/*
NoVoHT::NoVoHT(char * f, NoVoHT *map){
   kvpairs = new kvpair*[1000];
   size = 1000;
   numEl=0;
   file = f;
   readFile();
}*/
NoVoHT::~NoVoHT(){
   if (dbfile){
      writeFile();
      fclose(dbfile);
   }
   for (int i = 0; i < size; i++){
      fsu(kvpairs[i]);
   }
   delete [] kvpairs;
}

//0 success, -1 no insert, -2 no write
int NoVoHT::put(string k, string v){
   //while(resizing || map_lock){ /* Wait till done */}
   //while(map_lock){ }
   map_lock=true;
   if (numEl >= size*resizeNum) {
      if (resizeNum !=0){
         resize(size*2);
      }
   }
   int slot;
   slot = hash(k)%size;
   kvpair *cur = kvpairs[slot];
   kvpair *add = new kvpair;
   add->key = k;
   add->val = v;
   add->next = NULL;
   if (cur == NULL){
      kvpairs[slot] = add;
      numEl++;
      map_lock=false;
      return write(add);
   }
   while (cur->next != NULL){
      if (k.compare(cur->key) == 0) {delete add; map_lock=false; return -1;}
      cur = cur->next;
   }
   if (k.compare(cur->key) == 0) {delete add; map_lock=false; return -1;}
   cur->next = add;
   numEl++;
   map_lock=false;
   return write(add);
}

string* NoVoHT::get(string k){
   while(resizing){ /* Wait till done */}
   int loc = hash(k)%size;
   kvpair *cur = kvpairs[loc];
   while (cur != NULL && !k.empty()){
      if (k.compare(cur->key) == 0) return &(cur->val);
      cur = cur->next;
   }
   return NULL;
}

//return 0 for success, -1 fail to remove, -2+ write failure
int NoVoHT::remove(string k){
   while(map_lock){ /* Wait till done */}
   int ret =0;
   int loc = hash(k)%size;
   kvpair *cur = kvpairs[loc];
   if (cur == NULL) return ret-1;       //not found
   if (k.compare(cur->key) ==0) {
      fpos_t toRem = kvpairs[loc]->pos;
      kvpairs[loc] = cur->next;
      numEl--;
      ret+=mark(toRem);
      delete cur;
      nRem++;
      if (nRem == magicNumber) ret+=writeFile(); //write and save write success
      return ret;
   }
   while(cur != NULL){
      if (cur->next == NULL) return ret-1;
      else if (k.compare(cur->next->key)==0){
         kvpair *r = cur->next;
         cur->next = r->next;
         ret+=mark(r->pos);              //mark and sace status code
         delete r;
         numEl--;
         nRem++;
         if (nRem == magicNumber) ret+=writeFile();              //mark and sace status code
         return ret;
      }
      cur = cur->next;
   }
   return ret-1;        //not found
}

//return 0 if success -2 if failed
//write hashmap to file
int NoVoHT::writeFile(){
   while (write_lock){}
   write_lock=true;
   int ret =0;
   if (!dbfile)return (filename.compare("") == 0 ? 0 : -2);
   rewind(dbfile);
   for (int i=0; i<size;i++){
      kvpair *cur = kvpairs[i];
      while (cur != NULL){
         if(!cur->key.empty() && !cur->val.empty()){
                fgetpos(dbfile, &(cur->pos));
                fprintf(dbfile, "%s\t%s\t", cur->key.c_str(), cur->val.c_str());
         }
         cur = cur->next;
      }
   }
   truncate(filename.c_str(), (off_t)SEEK_CUR-SEEK_SET-1);
   write_lock=false;
   return ret;
}

//success 0 fail -2
//resize the hashmap's base size
void NoVoHT::resize(int ns){
   resizing = true;
   int olds = size;
   size = ns;
   oldpairs = kvpairs;
   kvpairs = new kvpair*[ns];
   for (int z=0; z<ns; z++) { kvpairs[z] = NULL;}
   numEl = 0;
   for (int i=0; i<olds;i++){
      kvpair *cur = oldpairs[i];
      while (cur != NULL){
         int pos = hash(cur->key)%size;
         kvpair * tmp = kvpairs[pos];
         kvpairs[pos] = cur;
         cur = cur->next;
         kvpairs[pos]->next = tmp;
      }
   }
   delete [] oldpairs;
   resizing = false;
}

//success 0 fail -2
//write kvpair to file
int NoVoHT::write(kvpair * p){
   while (write_lock){}
   write_lock=true;
   if (!dbfile)return (filename.compare("") == 0 ? 0 : -2);
   fseek(dbfile, 0, SEEK_END);
   fgetpos(dbfile, &(p->pos));
   fprintf(dbfile, "%s\t%s\t", p->key.c_str(), p->val.c_str());
   write_lock=false;
   return 0;
}

//success 0 fail -2
//mark line in file for deletion
int NoVoHT::mark(fpos_t position){
   while(write_lock){}
   write_lock=true;
   if (!dbfile)return (filename.compare("") == 0 ? 0 : -2);
   fsetpos(dbfile, &position);
   fputc((int) '~', dbfile);
   write_lock=false;
   return 0;
}
char *readTabString(FILE *file, char *buffer){
   int n =0;
   char t;
   while((t=fgetc(file)) != EOF){
      if (t == '\t') {
         buffer[n] = '\0';
         return buffer;
      }
      buffer[n] = t;
      n++;
   }
   buffer[n] = '\0';
   return (n == 0 ? NULL : buffer);
}

void NoVoHT::readFile(){
   if(!dbfile) return;
   char s[300];
   char v[300];
   while(readTabString(dbfile, s) != NULL){
      string key(s);
      if (readTabString(dbfile, v) == NULL) break;
      string val(v);
      if (key[0] != '~'){
         put(key,val);
      }
   }
   writeFile();
}

unsigned long long hash(string k){ //FNV hash
#if SIZE_OF_LONG_LONG_INT==8
#define FNV_PRIME 14695981039346656037
#define FNV_OFFSET 1099511628211
#else //SIZE_OF_LONG_LONG_INT == 4
#define FNV_PRIME 16777619
#define FNV_OFFSET 2166136261
#endif
   unsigned long long x = FNV_PRIME;
   for (unsigned int y=0;y<k.length();y++){
      x = x ^ (k[y]);
      x = x * FNV_OFFSET;
   }
   return (x);
}

void fsu(kvpair* p){
   if(p != NULL){
      fsu(p->next);
      delete p;
   }
}
<commit_msg>	modified:   novoht.cxx<commit_after>#include <stddef.h>
#include <stdlib.h>
#include <new>
#include <string>
#include <locale>
#include <stdio.h>
#include <iostream>
#include "novoht.h"

NoVoHT::NoVoHT(){
   kvpairs = new kvpair*[1000];
   size = 1000;
   numEl = 0;
   magicNumber = 1000;
   resizeNum = -1;
   resizing=false;
   map_lock=false;
   write_lock=false;
   resizing = false;
   oldpairs = NULL;
}

/*
NoVoHT::NoVoHT(int s){
   kvpairs = new kvpair*[s];
   size = s;
   numEl=0;
   file = NULL;
}

NoVoHT::NoVoHT(char * f){
   kvpairs = new kvpair*[1000];
   size = 1000;
   numEl=0;
   file = f;
   readFile();
}
*/
NoVoHT::NoVoHT(string f,int s, int m){
   kvpairs = new kvpair*[s];
   for (int x = 0;x<s;x++){
      kvpairs[x] = NULL;
   }
   resizing=false;
   map_lock=false;
   write_lock=false;
   magicNumber = m;
   nRem = 0;
   resizeNum = 0;
   size = s;
   numEl=0;
   filename=f;
   dbfile = fopen(f.c_str(), "r+");
   if (!dbfile) dbfile = fopen(f.c_str(), "w+");
   readFile();
   oldpairs = NULL;
}
NoVoHT::NoVoHT(string f,int s, int m, float r){
   kvpairs = new kvpair*[s];
   for (int x = 0;x<s;x++){
      kvpairs[x] = NULL;
   }
   resizing=false;
   map_lock=false;
   write_lock=false;
   magicNumber = m;
   nRem = 0;
   resizeNum = r;
   size = s;
   numEl=0;
   filename=f;
   dbfile = fopen(f.c_str(), "r+");
   if (!dbfile) dbfile = fopen(f.c_str(), "w+");
   readFile();
   oldpairs = NULL;
}
/*
NoVoHT::NoVoHT(char * f, NoVoHT *map){
   kvpairs = new kvpair*[1000];
   size = 1000;
   numEl=0;
   file = f;
   readFile();
}*/
NoVoHT::~NoVoHT(){
   if (dbfile){
      writeFile();
      fclose(dbfile);
   }
   for (int i = 0; i < size; i++){
      fsu(kvpairs[i]);
   }
   delete [] kvpairs;
}

//0 success, -1 no insert, -2 no write
int NoVoHT::put(string k, string v){
   //while(resizing || map_lock){ /* Wait till done */}
   //while(map_lock){ }
   map_lock=true;
   if (numEl >= size*resizeNum) {
      if (resizeNum !=0){
         resize(size*2);
      }
   }
   int slot;
   slot = hash(k)%size;
   kvpair *cur = kvpairs[slot];
   kvpair *add = new kvpair;
   add->key = k;
   add->val = v;
   add->next = NULL;
   if (cur == NULL){
      kvpairs[slot] = add;
      numEl++;
      map_lock=false;
      return write(add);
   }
   while (cur->next != NULL){
      if (k.compare(cur->key) == 0) {delete add; map_lock=false; return -1;}
      cur = cur->next;
   }
   if (k.compare(cur->key) == 0) {delete add; map_lock=false; return -1;}
   cur->next = add;
   numEl++;
   map_lock=false;
   return write(add);
}

string* NoVoHT::get(string k){
   while(map_lock){ /* Wait till done */}
   int loc = hash(k)%size;
   kvpair *cur = kvpairs[loc];
   while (cur != NULL && !k.empty()){
      if (k.compare(cur->key) == 0) return &(cur->val);
      cur = cur->next;
   }
   return NULL;
}

//return 0 for success, -1 fail to remove, -2+ write failure
int NoVoHT::remove(string k){
   while(map_lock){ /* Wait till done */}
   int ret =0;
   int loc = hash(k)%size;
   kvpair *cur = kvpairs[loc];
   if (cur == NULL) return ret-1;       //not found
   if (k.compare(cur->key) ==0) {
      fpos_t toRem = kvpairs[loc]->pos;
      kvpairs[loc] = cur->next;
      numEl--;
      ret+=mark(toRem);
      delete cur;
      nRem++;
      if (nRem == magicNumber) ret+=writeFile(); //write and save write success
      return ret;
   }
   while(cur != NULL){
      if (cur->next == NULL) return ret-1;
      else if (k.compare(cur->next->key)==0){
         kvpair *r = cur->next;
         cur->next = r->next;
         ret+=mark(r->pos);              //mark and sace status code
         delete r;
         numEl--;
         nRem++;
         if (nRem == magicNumber) ret+=writeFile();              //mark and sace status code
         return ret;
      }
      cur = cur->next;
   }
   return ret-1;        //not found
}

//return 0 if success -2 if failed
//write hashmap to file
int NoVoHT::writeFile(){
   while (write_lock){}
   write_lock=true;
   int ret =0;
   if (!dbfile)return (filename.compare("") == 0 ? 0 : -2);
   rewind(dbfile);
   for (int i=0; i<size;i++){
      kvpair *cur = kvpairs[i];
      while (cur != NULL){
         if(!cur->key.empty() && !cur->val.empty()){
                fgetpos(dbfile, &(cur->pos));
                fprintf(dbfile, "%s\t%s\t", cur->key.c_str(), cur->val.c_str());
         }
         cur = cur->next;
      }
   }
   truncate(filename.c_str(), (off_t)SEEK_CUR-SEEK_SET-1);
   write_lock=false;
   return ret;
}

//success 0 fail -2
//resize the hashmap's base size
void NoVoHT::resize(int ns){
   resizing = true;
   int olds = size;
   size = ns;
   oldpairs = kvpairs;
   kvpairs = new kvpair*[ns];
   for (int z=0; z<ns; z++) { kvpairs[z] = NULL;}
   numEl = 0;
   for (int i=0; i<olds;i++){
      kvpair *cur = oldpairs[i];
      while (cur != NULL){
         int pos = hash(cur->key)%size;
         kvpair * tmp = kvpairs[pos];
         kvpairs[pos] = cur;
         cur = cur->next;
         kvpairs[pos]->next = tmp;
      }
   }
   delete [] oldpairs;
   resizing = false;
}

//success 0 fail -2
//write kvpair to file
int NoVoHT::write(kvpair * p){
   while (write_lock){}
   write_lock=true;
   if (!dbfile)return (filename.compare("") == 0 ? 0 : -2);
   fseek(dbfile, 0, SEEK_END);
   fgetpos(dbfile, &(p->pos));
   fprintf(dbfile, "%s\t%s\t", p->key.c_str(), p->val.c_str());
   write_lock=false;
   return 0;
}

//success 0 fail -2
//mark line in file for deletion
int NoVoHT::mark(fpos_t position){
   while(write_lock){}
   write_lock=true;
   if (!dbfile)return (filename.compare("") == 0 ? 0 : -2);
   fsetpos(dbfile, &position);
   fputc((int) '~', dbfile);
   write_lock=false;
   return 0;
}
char *readTabString(FILE *file, char *buffer){
   int n =0;
   char t;
   while((t=fgetc(file)) != EOF){
      if (t == '\t') {
         buffer[n] = '\0';
         return buffer;
      }
      buffer[n] = t;
      n++;
   }
   buffer[n] = '\0';
   return (n == 0 ? NULL : buffer);
}

void NoVoHT::readFile(){
   if(!dbfile) return;
   char s[300];
   char v[300];
   while(readTabString(dbfile, s) != NULL){
      string key(s);
      if (readTabString(dbfile, v) == NULL) break;
      string val(v);
      if (key[0] != '~'){
         put(key,val);
      }
   }
   writeFile();
}

unsigned long long hash(string k){ //FNV hash
#if SIZE_OF_LONG_LONG_INT==8
#define FNV_PRIME 14695981039346656037
#define FNV_OFFSET 1099511628211
#else //SIZE_OF_LONG_LONG_INT == 4
#define FNV_PRIME 16777619
#define FNV_OFFSET 2166136261
#endif
   unsigned long long x = FNV_PRIME;
   for (unsigned int y=0;y<k.length();y++){
      x = x ^ (k[y]);
      x = x * FNV_OFFSET;
   }
   return (x);
}

void fsu(kvpair* p){
   if(p != NULL){
      fsu(p->next);
      delete p;
   }
}
<|endoftext|>


<commit_before>/*
* System Call getentropy(2)
* (C) 2017 Alexander Bluhm (genua GmbH)
*
* Botan is released under the Simplified BSD License (see license.txt)
*/

#include <botan/internal/getentropy.h>

#if defined(BOTAN_TARGET_OS_IS_OPENBSD) || defined(BOTAN_TARGET_OS_IS_FREEBSD) || defined(BOTAN_TARGET_OS_IS_SOLARIS)
   #include <unistd.h>
#else
   #include <sys/random.h>
#endif

namespace Botan {

/**
* Gather 256 bytes entropy from getentropy(2).  Note that maximum
* buffer size is limited to 256 bytes.  On OpenBSD this does neither
* block nor fail.
*/
size_t Getentropy::poll(RandomNumberGenerator& rng)
   {
   secure_vector<uint8_t> buf(256);

   if(::getentropy(buf.data(), buf.size()) == 0)
      {
      rng.add_entropy(buf.data(), buf.size());
      return buf.size() * 8;
      }

   return 0;
   }
}
<commit_msg>Fix compilation issue on older mac (< 10.12)<commit_after>/*
* System Call getentropy(2)
* (C) 2017 Alexander Bluhm (genua GmbH)
*
* Botan is released under the Simplified BSD License (see license.txt)
*/

#include <botan/internal/getentropy.h>

#if defined(BOTAN_TARGET_OS_IS_OPENBSD) || defined(BOTAN_TARGET_OS_IS_FREEBSD) || defined(BOTAN_TARGET_OS_IS_SOLARIS)
   #include <unistd.h>
#else
   #if defined(BOTAN_TARGET_OS_HAS_POSIX1)
      // Allows successful compilation on macOS older than 10.12: Provides a missing typedef for `u_int`.
      #include <sys/types.h>
   #endif
   #include <sys/random.h>
#endif

namespace Botan {

/**
* Gather 256 bytes entropy from getentropy(2).  Note that maximum
* buffer size is limited to 256 bytes.  On OpenBSD this does neither
* block nor fail.
*/
size_t Getentropy::poll(RandomNumberGenerator& rng)
   {
   secure_vector<uint8_t> buf(256);

   if(::getentropy(buf.data(), buf.size()) == 0)
      {
      rng.add_entropy(buf.data(), buf.size());
      return buf.size() * 8;
      }

   return 0;
   }
}
<|endoftext|>


<commit_before>#include "visualizer/GeomDataBuffer.h"
#include "visualizer/shader.h"
#include "visualizer/atengl.h"

namespace aten {
	void GeomVertexBuffer::init(
		uint32_t stride,
		uint32_t vtxNum,
		uint32_t offset,
		const void* data)
	{
		// Fix vertex structure
		//  float4 pos
		//  float3 nml
		//  float3 uv

		static const VertexAttrib attribs[] = {
			VertexAttrib(GL_FLOAT, 3, sizeof(GLfloat), 0),
			VertexAttrib(GL_FLOAT, 3, sizeof(GLfloat), 16),
			VertexAttrib(GL_FLOAT, 2, sizeof(GLfloat), 28),
		};

		init(
			stride,
			vtxNum,
			offset,
			attribs,
			AT_COUNTOF(attribs),
			data);
	}

	void GeomVertexBuffer::init(
		uint32_t stride,
		uint32_t vtxNum,
		uint32_t offset,
		const VertexAttrib* attribs,
		uint32_t attribNum,
		const void* data)
	{
		AT_ASSERT(m_vbo == 0);
		AT_ASSERT(m_vao == 0);

		CALL_GL_API(::glGenBuffers(1, &m_vbo));

		auto size = stride * vtxNum;

		m_vtxStride = stride;
		m_vtxNum = vtxNum;
		m_vtxOffset = offset;

		m_initVtxNum = vtxNum;

		CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

		CALL_GL_API(::glBufferData(
			GL_ARRAY_BUFFER,
			size,
			data,
			GL_STATIC_DRAW));

		// VAO
		{
			CALL_GL_API(::glGenVertexArrays(1, &m_vao));

			CALL_GL_API(::glBindVertexArray(m_vao));
			CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

			auto offsetByte = offset * m_vtxStride;

			for (uint32_t i = 0; i < attribNum; i++) {
				CALL_GL_API(::glEnableVertexAttribArray(i));

				CALL_GL_API(::glVertexAttribPointer(
					i,
					attribs[i].num,
					attribs[i].type,
					GL_FALSE,
					m_vtxStride,
					(void*)(offset + attribs[i].offset)));
			}
		}
	}

	void GeomVertexBuffer::initNoVAO(
		uint32_t stride,
		uint32_t vtxNum,
		uint32_t offset,
		const void* data)
	{
		AT_ASSERT(m_vbo == 0);

		CALL_GL_API(::glGenBuffers(1, &m_vbo));

		auto size = stride * vtxNum;

		m_vtxStride = stride;
		m_vtxNum = vtxNum;
		m_vtxOffset = offset;

		m_initVtxNum = vtxNum;

		CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

		CALL_GL_API(::glBufferData(
			GL_ARRAY_BUFFER,
			size,
			data,
			GL_STATIC_DRAW));
	}

	void GeomVertexBuffer::createVAOByAttribName(
		const shader* shd,
		const VertexAttrib* attribs,
		uint32_t attribNum)
	{
		AT_ASSERT(m_vbo > 0);
		AT_ASSERT(m_vao == 0);

		CALL_GL_API(::glGenVertexArrays(1, &m_vao));

		CALL_GL_API(::glBindVertexArray(m_vao));
		CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

		auto offsetByte = m_vtxOffset * m_vtxStride;

		auto program = shd->getProgramHandle();

		for (uint32_t i = 0; i < attribNum; i++) {
#if 0
			CALL_GL_API(::glEnableVertexAttribArray(i));

			CALL_GL_API(::glVertexAttribPointer(
				i,
				attribs[i].num,
				attribs[i].type,
				GL_FALSE,
				m_vtxStride,
				(void*)(m_vtxOffset + attribs[i].offset)));
#else
			if (attribs[i].name) {
				GLint loc = -1;
				CALL_GL_API(loc = ::glGetAttribLocation(program, attribs[i].name));

				if (loc >= 0) {
					CALL_GL_API(::glEnableVertexAttribArray(loc));

					CALL_GL_API(::glVertexAttribPointer(
						loc,
						attribs[i].num,
						attribs[i].type,
						attribs[i].needNormalize ? GL_TRUE : GL_FALSE,
						m_vtxStride,
						(void*)(m_vtxOffset + attribs[i].offset)));
				}
			}
#endif

		}
	}

	void GeomVertexBuffer::update(
		uint32_t vtxNum,
		const void* data)
	{
		AT_ASSERT(m_vbo > 0);
		AT_ASSERT(vtxNum <= m_initVtxNum);

		auto size = m_vtxStride * vtxNum;

		m_vtxNum = vtxNum;

		CALL_GL_API(::glNamedBufferSubData(
			m_vbo,
			(GLintptr)0,
			size,
			data));
	}

	static GLenum prims[] = {
		GL_TRIANGLES,
		GL_LINES,
	};

	inline uint32_t computeVtxNum(Primitive mode, uint32_t primNum)
	{
		uint32_t vtxNum = 0;

		switch (mode)
		{
		case Primitive::Triangles:
			vtxNum = primNum * 3;
			break;
		case Primitive::Lines:
			vtxNum = primNum * 2;
			break;
		}

		return vtxNum;
	}

	void GeomVertexBuffer::draw(
		Primitive mode,
		uint32_t idxOffset,
		uint32_t primNum)
	{
		AT_ASSERT(m_vao > 0);

		CALL_GL_API(::glBindVertexArray(m_vao));

		auto vtxNum = computeVtxNum(mode, primNum);

		CALL_GL_API(::glDrawArrays(prims[mode], idxOffset, vtxNum));
	}

	void GeomVertexBuffer::clear()
	{
		CALL_GL_API(::glDeleteBuffers(1, &m_vbo));
		CALL_GL_API(::glDeleteVertexArrays(1, &m_vao));

		m_vbo = 0;
		m_vao = 0;
	}

	//////////////////////////////////////////////////////////

	GeomIndexBuffer::~GeomIndexBuffer()
	{
		if (m_ibo > 0) {
			CALL_GL_API(::glDeleteBuffers(1, &m_ibo));
		}
	}

	void GeomIndexBuffer::init(
		uint32_t idxNum,
		const void* data)
	{
		CALL_GL_API(::glGenBuffers(1, &m_ibo));

		auto size = sizeof(GLuint) * idxNum;

		m_idxNum = idxNum;

		m_initIdxNum = idxNum;

		CALL_GL_API(::glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ibo));

		CALL_GL_API(::glBufferData(
			GL_ELEMENT_ARRAY_BUFFER,
			size,
			data,
			GL_STATIC_DRAW));
	}

	void GeomIndexBuffer::update(
		uint32_t idxNum,
		const void* data)
	{
		AT_ASSERT(m_ibo > 0);
		AT_ASSERT(idxNum <= m_initIdxNum);

		auto size = sizeof(GLuint) * idxNum;

		m_idxNum = idxNum;

		if (size > 0) {
			CALL_GL_API(::glNamedBufferSubData(
				m_ibo,
				(GLintptr)0,
				size,
				data));
		}
	}

	void GeomIndexBuffer::lock(void** dst)
	{
		void* tmp = nullptr;

		auto lockSize = sizeof(GLuint) * m_idxNum;

		CALL_GL_API(tmp = ::glMapNamedBufferRange(
			m_ibo,
			0,
			lockSize,
			GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT | GL_MAP_INVALIDATE_BUFFER_BIT));

		*dst = tmp;

		m_isLockedIBO = true;
	}

	void GeomIndexBuffer::unlock()
	{
		if (m_isLockedIBO) {
			CALL_GL_API(::glUnmapNamedBuffer(m_ibo));
		}

		m_isLockedIBO = false;
	}

	void GeomIndexBuffer::draw(
		GeomVertexBuffer& vb,
		Primitive mode,
		uint32_t idxOffset,
		uint32_t primNum)
	{
		AT_ASSERT(m_ibo > 0);
		AT_ASSERT(vb.m_vao > 0);

		CALL_GL_API(::glBindVertexArray(vb.m_vao));
		CALL_GL_API(::glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ibo));

		auto offsetByte = idxOffset * sizeof(GLuint);

		auto idxNum = computeVtxNum(mode, primNum);

		CALL_GL_API(::glDrawElements(
			prims[mode],
			idxNum,
			GL_UNSIGNED_INT,
			(const GLvoid*)offsetByte));
	}
}
<commit_msg>Add check if gl resource is valid.<commit_after>#include "visualizer/GeomDataBuffer.h"
#include "visualizer/shader.h"
#include "visualizer/atengl.h"

namespace aten {
	void GeomVertexBuffer::init(
		uint32_t stride,
		uint32_t vtxNum,
		uint32_t offset,
		const void* data)
	{
		// Fix vertex structure
		//  float4 pos
		//  float3 nml
		//  float3 uv

		static const VertexAttrib attribs[] = {
			VertexAttrib(GL_FLOAT, 3, sizeof(GLfloat), 0),
			VertexAttrib(GL_FLOAT, 3, sizeof(GLfloat), 16),
			VertexAttrib(GL_FLOAT, 2, sizeof(GLfloat), 28),
		};

		init(
			stride,
			vtxNum,
			offset,
			attribs,
			AT_COUNTOF(attribs),
			data);
	}

	void GeomVertexBuffer::init(
		uint32_t stride,
		uint32_t vtxNum,
		uint32_t offset,
		const VertexAttrib* attribs,
		uint32_t attribNum,
		const void* data)
	{
		AT_ASSERT(m_vbo == 0);
		AT_ASSERT(m_vao == 0);

		CALL_GL_API(::glGenBuffers(1, &m_vbo));

		auto size = stride * vtxNum;

		m_vtxStride = stride;
		m_vtxNum = vtxNum;
		m_vtxOffset = offset;

		m_initVtxNum = vtxNum;

		CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

		CALL_GL_API(::glBufferData(
			GL_ARRAY_BUFFER,
			size,
			data,
			GL_STATIC_DRAW));

		// VAO
		{
			CALL_GL_API(::glGenVertexArrays(1, &m_vao));

			CALL_GL_API(::glBindVertexArray(m_vao));
			CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

			auto offsetByte = offset * m_vtxStride;

			for (uint32_t i = 0; i < attribNum; i++) {
				CALL_GL_API(::glEnableVertexAttribArray(i));

				CALL_GL_API(::glVertexAttribPointer(
					i,
					attribs[i].num,
					attribs[i].type,
					GL_FALSE,
					m_vtxStride,
					(void*)(offset + attribs[i].offset)));
			}
		}
	}

	void GeomVertexBuffer::initNoVAO(
		uint32_t stride,
		uint32_t vtxNum,
		uint32_t offset,
		const void* data)
	{
		AT_ASSERT(m_vbo == 0);

		CALL_GL_API(::glGenBuffers(1, &m_vbo));

		auto size = stride * vtxNum;

		m_vtxStride = stride;
		m_vtxNum = vtxNum;
		m_vtxOffset = offset;

		m_initVtxNum = vtxNum;

		CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

		CALL_GL_API(::glBufferData(
			GL_ARRAY_BUFFER,
			size,
			data,
			GL_STATIC_DRAW));
	}

	void GeomVertexBuffer::createVAOByAttribName(
		const shader* shd,
		const VertexAttrib* attribs,
		uint32_t attribNum)
	{
		AT_ASSERT(m_vbo > 0);
		AT_ASSERT(m_vao == 0);

		CALL_GL_API(::glGenVertexArrays(1, &m_vao));

		CALL_GL_API(::glBindVertexArray(m_vao));
		CALL_GL_API(::glBindBuffer(GL_ARRAY_BUFFER, m_vbo));

		auto offsetByte = m_vtxOffset * m_vtxStride;

		auto program = shd->getProgramHandle();

		for (uint32_t i = 0; i < attribNum; i++) {
#if 0
			CALL_GL_API(::glEnableVertexAttribArray(i));

			CALL_GL_API(::glVertexAttribPointer(
				i,
				attribs[i].num,
				attribs[i].type,
				GL_FALSE,
				m_vtxStride,
				(void*)(m_vtxOffset + attribs[i].offset)));
#else
			if (attribs[i].name) {
				GLint loc = -1;
				CALL_GL_API(loc = ::glGetAttribLocation(program, attribs[i].name));

				if (loc >= 0) {
					CALL_GL_API(::glEnableVertexAttribArray(loc));

					CALL_GL_API(::glVertexAttribPointer(
						loc,
						attribs[i].num,
						attribs[i].type,
						attribs[i].needNormalize ? GL_TRUE : GL_FALSE,
						m_vtxStride,
						(void*)(m_vtxOffset + attribs[i].offset)));
				}
			}
#endif

		}
	}

	void GeomVertexBuffer::update(
		uint32_t vtxNum,
		const void* data)
	{
		AT_ASSERT(m_vbo > 0);
		AT_ASSERT(vtxNum <= m_initVtxNum);

		auto size = m_vtxStride * vtxNum;

		m_vtxNum = vtxNum;

		CALL_GL_API(::glNamedBufferSubData(
			m_vbo,
			(GLintptr)0,
			size,
			data));
	}

	static GLenum prims[] = {
		GL_TRIANGLES,
		GL_LINES,
	};

	inline uint32_t computeVtxNum(Primitive mode, uint32_t primNum)
	{
		uint32_t vtxNum = 0;

		switch (mode)
		{
		case Primitive::Triangles:
			vtxNum = primNum * 3;
			break;
		case Primitive::Lines:
			vtxNum = primNum * 2;
			break;
		}

		return vtxNum;
	}

	void GeomVertexBuffer::draw(
		Primitive mode,
		uint32_t idxOffset,
		uint32_t primNum)
	{
		AT_ASSERT(m_vao > 0);

		CALL_GL_API(::glBindVertexArray(m_vao));

		auto vtxNum = computeVtxNum(mode, primNum);

		CALL_GL_API(::glDrawArrays(prims[mode], idxOffset, vtxNum));
	}

	void GeomVertexBuffer::clear()
	{
		if (m_vbo > 0) {
			CALL_GL_API(::glDeleteBuffers(1, &m_vbo));
		}
		if (m_vao > 0) {
			CALL_GL_API(::glDeleteVertexArrays(1, &m_vao));
		}

		m_vbo = 0;
		m_vao = 0;
	}

	//////////////////////////////////////////////////////////

	GeomIndexBuffer::~GeomIndexBuffer()
	{
		if (m_ibo > 0) {
			CALL_GL_API(::glDeleteBuffers(1, &m_ibo));
		}
	}

	void GeomIndexBuffer::init(
		uint32_t idxNum,
		const void* data)
	{
		CALL_GL_API(::glGenBuffers(1, &m_ibo));

		auto size = sizeof(GLuint) * idxNum;

		m_idxNum = idxNum;

		m_initIdxNum = idxNum;

		CALL_GL_API(::glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ibo));

		CALL_GL_API(::glBufferData(
			GL_ELEMENT_ARRAY_BUFFER,
			size,
			data,
			GL_STATIC_DRAW));
	}

	void GeomIndexBuffer::update(
		uint32_t idxNum,
		const void* data)
	{
		AT_ASSERT(m_ibo > 0);
		AT_ASSERT(idxNum <= m_initIdxNum);

		auto size = sizeof(GLuint) * idxNum;

		m_idxNum = idxNum;

		if (size > 0) {
			CALL_GL_API(::glNamedBufferSubData(
				m_ibo,
				(GLintptr)0,
				size,
				data));
		}
	}

	void GeomIndexBuffer::lock(void** dst)
	{
		void* tmp = nullptr;

		auto lockSize = sizeof(GLuint) * m_idxNum;

		CALL_GL_API(tmp = ::glMapNamedBufferRange(
			m_ibo,
			0,
			lockSize,
			GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT | GL_MAP_INVALIDATE_BUFFER_BIT));

		*dst = tmp;

		m_isLockedIBO = true;
	}

	void GeomIndexBuffer::unlock()
	{
		if (m_isLockedIBO) {
			CALL_GL_API(::glUnmapNamedBuffer(m_ibo));
		}

		m_isLockedIBO = false;
	}

	void GeomIndexBuffer::draw(
		GeomVertexBuffer& vb,
		Primitive mode,
		uint32_t idxOffset,
		uint32_t primNum)
	{
		AT_ASSERT(m_ibo > 0);
		AT_ASSERT(vb.m_vao > 0);

		CALL_GL_API(::glBindVertexArray(vb.m_vao));
		CALL_GL_API(::glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ibo));

		auto offsetByte = idxOffset * sizeof(GLuint);

		auto idxNum = computeVtxNum(mode, primNum);

		CALL_GL_API(::glDrawElements(
			prims[mode],
			idxNum,
			GL_UNSIGNED_INT,
			(const GLvoid*)offsetByte));
	}
}
<|endoftext|>


<commit_before>/**************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** Commercial Usage
**
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
**
** GNU Lesser General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file.  Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** If you are unsure which license is appropriate for your use, please
** contact the sales department at http://qt.nokia.com/contact.
**
**************************************************************************/

#include "buildablehelperlibrary.h"

#include <QtCore/QFileInfo>
#include <QtCore/QCoreApplication>
#include <QtCore/QHash>
#include <QtCore/QProcess>
#include <QtCore/QDir>
#include <QtCore/QDateTime>

#include <utils/environment.h>
#include <utils/synchronousprocess.h>

#include <QtGui/QDesktopServices>
#include <QDebug>

namespace Utils {

QString BuildableHelperLibrary::findSystemQt(const Utils::Environment &env)
{
    QStringList paths = env.path();
    foreach (const QString &path, paths) {
        foreach (const QString &possibleCommand, possibleQMakeCommands()) {
            const QFileInfo qmake(path + QLatin1Char('/') + possibleCommand);
            if (qmake.exists()) {
                if (!qtVersionForQMake(qmake.absoluteFilePath()).isNull()) {
                    return qmake.absoluteFilePath();
                }
            }
        }
    }
    return QString();
}

QString BuildableHelperLibrary::qtInstallDataDir(const QString &qmakePath)
{
    QProcess proc;
    proc.start(qmakePath, QStringList() << QLatin1String("-query") << QLatin1String("QT_INSTALL_DATA"));
    if (proc.waitForFinished())
        return QString(proc.readAll().trimmed());
    return QString();
}

QString BuildableHelperLibrary::qtVersionForQMake(const QString &qmakePath)
{
    if (qmakePath.isEmpty())
        return QString();

    QProcess qmake;
    qmake.start(qmakePath, QStringList(QLatin1String("--version")));
    if (!qmake.waitForStarted()) {
        qWarning("Cannot start '%s': %s", qPrintable(qmakePath), qPrintable(qmake.errorString()));
        return QString();
    }
    if (!qmake.waitForFinished())      {
        Utils::SynchronousProcess::stopProcess(qmake);
        qWarning("Timeout running '%s'.", qPrintable(qmakePath));
        return QString();
    }
    if (qmake.exitStatus() != QProcess::NormalExit) {
        qWarning("'%s' crashed.", qPrintable(qmakePath));
        return QString();
    }
    const QString output = QString::fromLocal8Bit(qmake.readAllStandardOutput());
    static QRegExp regexp(QLatin1String("(QMake version|QMake version:)[\\s]*([\\d.]*)"),
                          Qt::CaseInsensitive);
    regexp.indexIn(output);
    if (regexp.cap(2).startsWith(QLatin1String("2."))) {
        static QRegExp regexp2(QLatin1String("Using Qt version[\\s]*([\\d\\.]*)"),
                               Qt::CaseInsensitive);
        regexp2.indexIn(output);
        const QString version = regexp2.cap(1);
        return version;
    }
    return QString();
}

bool BuildableHelperLibrary::checkMinimumQtVersion(const QString &qtVersionString, int majorVersion, int minorVersion, int patchVersion)
{
    int major = -1;
    int minor = -1;
    int patch = -1;

    // check format
    static QRegExp qtVersionRegex(QLatin1String("^\\d+\\.\\d+\\.\\d+$"));
    if (!qtVersionRegex.exactMatch(qtVersionString))
        return false;

    QStringList parts = qtVersionString.split(QLatin1Char('.'));
    major = parts.at(0).toInt();
    minor = parts.at(1).toInt();
    patch = parts.at(2).toInt();

    if (major == majorVersion) {
        if (minor == minorVersion) {
            if (patch >= patchVersion)
                return true;
        } else if (minor > minorVersion)
            return true;
    }

    return false;
}

QStringList BuildableHelperLibrary::possibleQMakeCommands()
{
    // On windows no one has renamed qmake, right?
#ifdef Q_OS_WIN
    return QStringList(QLatin1String("qmake.exe"));
#else
    // On unix some distributions renamed qmake to avoid clashes
    QStringList result;
    result << QLatin1String("qmake-qt4") << QLatin1String("qmake4") << QLatin1String("qmake");
    return result;
#endif
}

// Copy helper source files to a target directory, replacing older files.
bool BuildableHelperLibrary::copyFiles(const QString &sourcePath,
                                     const QStringList &files,
                                     const QString &targetDirectory,
                                     QString *errorMessage)
{
    if (!QDir().mkpath(targetDirectory)) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary", "The target directory %1 could not be created.").arg(targetDirectory);
        return false;
    }
    foreach (const QString &file, files) {
        const QString source = sourcePath + file;
        const QString dest = targetDirectory + file;
        const QFileInfo destInfo(dest);
        if (destInfo.exists()) {
            if (destInfo.lastModified() >= QFileInfo(source).lastModified())
                continue;
            if (!QFile::remove(dest)) {
                *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary", "The existing file %1 could not be removed.").arg(destInfo.absoluteFilePath());
                return false;
            }
        }
        if (!QFile::copy(source, dest)) {
            *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary", "The file %1 could not be copied to %2.").arg(source, dest);
            return false;
        }
    }
    return true;
}

// Helper: Run a build process with merged stdout/stderr
static inline bool runBuildProcessI(QProcess &proc,
                                    const QString &binary,
                                    const QStringList &args,
                                    int timeoutMS,
                                    bool ignoreNonNullExitCode,
                                    QString *output, QString *errorMessage)
{
    proc.start(binary, args);
    if (!proc.waitForStarted()) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                    "Cannot start process: %1").
                                                    arg(proc.errorString());
        return false;
    }
    // Read stdout/err and check for timeouts
    QByteArray stdOut;
    QByteArray stdErr;
    if (!SynchronousProcess::readDataFromProcess(proc, timeoutMS, &stdOut, &stdErr, false)) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                    "Timeout after %1s.").
                                                    arg(timeoutMS / 1000);
        SynchronousProcess::stopProcess(proc);
        return false;
    }
    if (proc.exitStatus() != QProcess::NormalExit) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                    "The process crashed.");
        return false;
    }
    const QString stdOutS = QString::fromLocal8Bit(stdOut);
    if (!ignoreNonNullExitCode && proc.exitCode() != 0) {
            *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                        "The process returned exit code %1:\n%2").
                                                         arg(proc.exitCode()).arg(stdOutS);
        return false;
    }
    output->append(stdOutS);
    return true;
}

// Run a build process with merged stdout/stderr and qWarn about errors.
static bool runBuildProcess(QProcess &proc,
                            const QString &binary,
                            const QStringList &args,
                            int timeoutMS,
                            bool ignoreNonNullExitCode,
                            QString *output, QString *errorMessage)
{
    const bool rc = runBuildProcessI(proc, binary, args, timeoutMS, ignoreNonNullExitCode, output, errorMessage);
    if (!rc) {
        // Fail - reformat error.
        QString cmd = binary;
        if (!args.isEmpty()) {
            cmd += QLatin1Char(' ');
            cmd += args.join(QString(QLatin1Char(' ')));
        }
        *errorMessage =
                QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                            "Error running '%1' in %2: %3").
                                            arg(cmd, proc.workingDirectory(), *errorMessage);
        qWarning("%s", qPrintable(*errorMessage));
    }
    return rc;
}

bool BuildableHelperLibrary::buildHelper(const QString &helperName, const QString &proFilename,
                                         const QString &directory, const QString &makeCommand,
                                         const QString &qmakeCommand, const QString &mkspec,
                                         const Utils::Environment &env, const QString &targetMode,
                                         QString *output, QString *errorMessage)
{
    const QChar newline = QLatin1Char('\n');
    // Setup process
    QProcess proc;
    proc.setEnvironment(env.toStringList());
    proc.setWorkingDirectory(directory);
    proc.setProcessChannelMode(QProcess::MergedChannels);

    output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                          "Building helper library '%1' in %2\n").arg(helperName, directory));
    output->append(newline);

    const QString makeFullPath = env.searchInPath(makeCommand);
    if (QFileInfo(directory + QLatin1String("/Makefile")).exists()) {
        if (makeFullPath.isEmpty()) {
            *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary",
                                                       "%1 not found in PATH\n").arg(makeCommand);
            return false;
        }
        const QString cleanTarget = QLatin1String("distclean");
        output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                   "Running %1 %2...\n").arg(makeFullPath, cleanTarget));
        if (!runBuildProcess(proc, makeFullPath, QStringList(cleanTarget), 30000, true, output, errorMessage))
            return false;
    }
    output->append(newline);
    output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary", "Running %1 ...\n").arg(qmakeCommand));

    QStringList qMakeArgs;
    if (!targetMode.isEmpty())
        qMakeArgs << targetMode;
    if (!mkspec.isEmpty())
        qMakeArgs << QLatin1String("-spec") << mkspec;
    qMakeArgs << proFilename;
    if (!runBuildProcess(proc, qmakeCommand, qMakeArgs, 30000, false, output, errorMessage))
        return false;
    output->append(newline);
    if (makeFullPath.isEmpty()) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary", "%1 not found in PATH\n").arg(makeCommand);
        return false;
    }
    output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary", "Running %1 ...\n").arg(makeFullPath));
    if (!runBuildProcess(proc, makeFullPath, QStringList(), 120000, false, output, errorMessage))
        return false;
    return true;
}

bool BuildableHelperLibrary::getHelperFileInfoFor(const QStringList &validBinaryFilenames,
                                                  const QString &directory, QFileInfo* info)
{
    if (!info)
        return false;

    foreach(const QString &binaryFilename, validBinaryFilenames) {
        info->setFile(directory + binaryFilename);
        if (info->exists())
            return true;
    }

    return false;
}

QString BuildableHelperLibrary::byInstallDataHelper(const QString &mainFilename,
                                                    const QStringList &installDirectories,
                                                    const QStringList &validBinaryFilenames)
{
    QDateTime sourcesModified = QFileInfo(mainFilename).lastModified();
    // We pretend that the lastmodified of gdbmacros.cpp is 5 minutes before what the file system says
    // Because afer a installation from the package the modified dates of gdbmacros.cpp
    // and the actual library are close to each other, but not deterministic in one direction
    sourcesModified = sourcesModified.addSecs(-300);

    // look for the newest helper library in the different locations
    QString newestHelper;
    QDateTime newestHelperModified = sourcesModified; // prevent using one that's older than the sources
    QFileInfo fileInfo;
    foreach(const QString &installDirectory, installDirectories) {
        if (getHelperFileInfoFor(validBinaryFilenames, installDirectory, &fileInfo)) {
            if (fileInfo.lastModified() > newestHelperModified) {
                newestHelper = fileInfo.filePath();
                newestHelperModified = fileInfo.lastModified();
            }
        }
    }
    return newestHelper;
}

} // namespace Utils
<commit_msg>Make sure we do not get "//" in the QMake path<commit_after>/**************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** Commercial Usage
**
** Licensees holding valid Qt Commercial licenses may use this file in
** accordance with the Qt Commercial License Agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Nokia.
**
** GNU Lesser General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file.  Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** If you are unsure which license is appropriate for your use, please
** contact the sales department at http://qt.nokia.com/contact.
**
**************************************************************************/

#include "buildablehelperlibrary.h"

#include <QtCore/QFileInfo>
#include <QtCore/QCoreApplication>
#include <QtCore/QHash>
#include <QtCore/QProcess>
#include <QtCore/QDir>
#include <QtCore/QDateTime>

#include <utils/environment.h>
#include <utils/synchronousprocess.h>

#include <QtGui/QDesktopServices>
#include <QDebug>

namespace Utils {

QString BuildableHelperLibrary::findSystemQt(const Utils::Environment &env)
{
    QStringList paths = env.path();
    foreach (const QString &path, paths) {
        QString prefix = path;
        if (!prefix.endsWith(QLatin1Char('/')))
            prefix.append(QLatin1Char('/'));
        foreach (const QString &possibleCommand, possibleQMakeCommands()) {
            const QFileInfo qmake(prefix + possibleCommand);
            if (qmake.exists()) {
                if (!qtVersionForQMake(qmake.absoluteFilePath()).isNull()) {
                    return qmake.absoluteFilePath();
                }
            }
        }
    }
    return QString();
}

QString BuildableHelperLibrary::qtInstallDataDir(const QString &qmakePath)
{
    QProcess proc;
    proc.start(qmakePath, QStringList() << QLatin1String("-query") << QLatin1String("QT_INSTALL_DATA"));
    if (proc.waitForFinished())
        return QString(proc.readAll().trimmed());
    return QString();
}

QString BuildableHelperLibrary::qtVersionForQMake(const QString &qmakePath)
{
    if (qmakePath.isEmpty())
        return QString();

    QProcess qmake;
    qmake.start(qmakePath, QStringList(QLatin1String("--version")));
    if (!qmake.waitForStarted()) {
        qWarning("Cannot start '%s': %s", qPrintable(qmakePath), qPrintable(qmake.errorString()));
        return QString();
    }
    if (!qmake.waitForFinished())      {
        Utils::SynchronousProcess::stopProcess(qmake);
        qWarning("Timeout running '%s'.", qPrintable(qmakePath));
        return QString();
    }
    if (qmake.exitStatus() != QProcess::NormalExit) {
        qWarning("'%s' crashed.", qPrintable(qmakePath));
        return QString();
    }
    const QString output = QString::fromLocal8Bit(qmake.readAllStandardOutput());
    static QRegExp regexp(QLatin1String("(QMake version|QMake version:)[\\s]*([\\d.]*)"),
                          Qt::CaseInsensitive);
    regexp.indexIn(output);
    if (regexp.cap(2).startsWith(QLatin1String("2."))) {
        static QRegExp regexp2(QLatin1String("Using Qt version[\\s]*([\\d\\.]*)"),
                               Qt::CaseInsensitive);
        regexp2.indexIn(output);
        const QString version = regexp2.cap(1);
        return version;
    }
    return QString();
}

bool BuildableHelperLibrary::checkMinimumQtVersion(const QString &qtVersionString, int majorVersion, int minorVersion, int patchVersion)
{
    int major = -1;
    int minor = -1;
    int patch = -1;

    // check format
    static QRegExp qtVersionRegex(QLatin1String("^\\d+\\.\\d+\\.\\d+$"));
    if (!qtVersionRegex.exactMatch(qtVersionString))
        return false;

    QStringList parts = qtVersionString.split(QLatin1Char('.'));
    major = parts.at(0).toInt();
    minor = parts.at(1).toInt();
    patch = parts.at(2).toInt();

    if (major == majorVersion) {
        if (minor == minorVersion) {
            if (patch >= patchVersion)
                return true;
        } else if (minor > minorVersion)
            return true;
    }

    return false;
}

QStringList BuildableHelperLibrary::possibleQMakeCommands()
{
    // On windows no one has renamed qmake, right?
#ifdef Q_OS_WIN
    return QStringList(QLatin1String("qmake.exe"));
#else
    // On unix some distributions renamed qmake to avoid clashes
    QStringList result;
    result << QLatin1String("qmake-qt4") << QLatin1String("qmake4") << QLatin1String("qmake");
    return result;
#endif
}

// Copy helper source files to a target directory, replacing older files.
bool BuildableHelperLibrary::copyFiles(const QString &sourcePath,
                                     const QStringList &files,
                                     const QString &targetDirectory,
                                     QString *errorMessage)
{
    if (!QDir().mkpath(targetDirectory)) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary", "The target directory %1 could not be created.").arg(targetDirectory);
        return false;
    }
    foreach (const QString &file, files) {
        const QString source = sourcePath + file;
        const QString dest = targetDirectory + file;
        const QFileInfo destInfo(dest);
        if (destInfo.exists()) {
            if (destInfo.lastModified() >= QFileInfo(source).lastModified())
                continue;
            if (!QFile::remove(dest)) {
                *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary", "The existing file %1 could not be removed.").arg(destInfo.absoluteFilePath());
                return false;
            }
        }
        if (!QFile::copy(source, dest)) {
            *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary", "The file %1 could not be copied to %2.").arg(source, dest);
            return false;
        }
    }
    return true;
}

// Helper: Run a build process with merged stdout/stderr
static inline bool runBuildProcessI(QProcess &proc,
                                    const QString &binary,
                                    const QStringList &args,
                                    int timeoutMS,
                                    bool ignoreNonNullExitCode,
                                    QString *output, QString *errorMessage)
{
    proc.start(binary, args);
    if (!proc.waitForStarted()) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                    "Cannot start process: %1").
                                                    arg(proc.errorString());
        return false;
    }
    // Read stdout/err and check for timeouts
    QByteArray stdOut;
    QByteArray stdErr;
    if (!SynchronousProcess::readDataFromProcess(proc, timeoutMS, &stdOut, &stdErr, false)) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                    "Timeout after %1s.").
                                                    arg(timeoutMS / 1000);
        SynchronousProcess::stopProcess(proc);
        return false;
    }
    if (proc.exitStatus() != QProcess::NormalExit) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                    "The process crashed.");
        return false;
    }
    const QString stdOutS = QString::fromLocal8Bit(stdOut);
    if (!ignoreNonNullExitCode && proc.exitCode() != 0) {
            *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                        "The process returned exit code %1:\n%2").
                                                         arg(proc.exitCode()).arg(stdOutS);
        return false;
    }
    output->append(stdOutS);
    return true;
}

// Run a build process with merged stdout/stderr and qWarn about errors.
static bool runBuildProcess(QProcess &proc,
                            const QString &binary,
                            const QStringList &args,
                            int timeoutMS,
                            bool ignoreNonNullExitCode,
                            QString *output, QString *errorMessage)
{
    const bool rc = runBuildProcessI(proc, binary, args, timeoutMS, ignoreNonNullExitCode, output, errorMessage);
    if (!rc) {
        // Fail - reformat error.
        QString cmd = binary;
        if (!args.isEmpty()) {
            cmd += QLatin1Char(' ');
            cmd += args.join(QString(QLatin1Char(' ')));
        }
        *errorMessage =
                QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                            "Error running '%1' in %2: %3").
                                            arg(cmd, proc.workingDirectory(), *errorMessage);
        qWarning("%s", qPrintable(*errorMessage));
    }
    return rc;
}

bool BuildableHelperLibrary::buildHelper(const QString &helperName, const QString &proFilename,
                                         const QString &directory, const QString &makeCommand,
                                         const QString &qmakeCommand, const QString &mkspec,
                                         const Utils::Environment &env, const QString &targetMode,
                                         QString *output, QString *errorMessage)
{
    const QChar newline = QLatin1Char('\n');
    // Setup process
    QProcess proc;
    proc.setEnvironment(env.toStringList());
    proc.setWorkingDirectory(directory);
    proc.setProcessChannelMode(QProcess::MergedChannels);

    output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                          "Building helper library '%1' in %2\n").arg(helperName, directory));
    output->append(newline);

    const QString makeFullPath = env.searchInPath(makeCommand);
    if (QFileInfo(directory + QLatin1String("/Makefile")).exists()) {
        if (makeFullPath.isEmpty()) {
            *errorMessage = QCoreApplication::translate("ProjectExplorer::DebuggingHelperLibrary",
                                                       "%1 not found in PATH\n").arg(makeCommand);
            return false;
        }
        const QString cleanTarget = QLatin1String("distclean");
        output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary",
                                                   "Running %1 %2...\n").arg(makeFullPath, cleanTarget));
        if (!runBuildProcess(proc, makeFullPath, QStringList(cleanTarget), 30000, true, output, errorMessage))
            return false;
    }
    output->append(newline);
    output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary", "Running %1 ...\n").arg(qmakeCommand));

    QStringList qMakeArgs;
    if (!targetMode.isEmpty())
        qMakeArgs << targetMode;
    if (!mkspec.isEmpty())
        qMakeArgs << QLatin1String("-spec") << mkspec;
    qMakeArgs << proFilename;
    if (!runBuildProcess(proc, qmakeCommand, qMakeArgs, 30000, false, output, errorMessage))
        return false;
    output->append(newline);
    if (makeFullPath.isEmpty()) {
        *errorMessage = QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary", "%1 not found in PATH\n").arg(makeCommand);
        return false;
    }
    output->append(QCoreApplication::translate("ProjectExplorer::BuildableHelperLibrary", "Running %1 ...\n").arg(makeFullPath));
    if (!runBuildProcess(proc, makeFullPath, QStringList(), 120000, false, output, errorMessage))
        return false;
    return true;
}

bool BuildableHelperLibrary::getHelperFileInfoFor(const QStringList &validBinaryFilenames,
                                                  const QString &directory, QFileInfo* info)
{
    if (!info)
        return false;

    foreach(const QString &binaryFilename, validBinaryFilenames) {
        info->setFile(directory + binaryFilename);
        if (info->exists())
            return true;
    }

    return false;
}

QString BuildableHelperLibrary::byInstallDataHelper(const QString &mainFilename,
                                                    const QStringList &installDirectories,
                                                    const QStringList &validBinaryFilenames)
{
    QDateTime sourcesModified = QFileInfo(mainFilename).lastModified();
    // We pretend that the lastmodified of gdbmacros.cpp is 5 minutes before what the file system says
    // Because afer a installation from the package the modified dates of gdbmacros.cpp
    // and the actual library are close to each other, but not deterministic in one direction
    sourcesModified = sourcesModified.addSecs(-300);

    // look for the newest helper library in the different locations
    QString newestHelper;
    QDateTime newestHelperModified = sourcesModified; // prevent using one that's older than the sources
    QFileInfo fileInfo;
    foreach(const QString &installDirectory, installDirectories) {
        if (getHelperFileInfoFor(validBinaryFilenames, installDirectory, &fileInfo)) {
            if (fileInfo.lastModified() > newestHelperModified) {
                newestHelper = fileInfo.filePath();
                newestHelperModified = fileInfo.lastModified();
            }
        }
    }
    return newestHelper;
}

} // namespace Utils
<|endoftext|>


<commit_before>//
// Created by Caleb on 11/15/16.
//

#include "lineFollowing.h"
#include "line_simplification.h"
#include "line_utilities.h"

void compress_lines(vector<Vec2f> &condensed, const vector<Vec2f> &tmp_list) {

  Vec2f new_point;
  float angle_sum = 0;
  float rho_sum = 0;
  for (int j = 0; j < (int) tmp_list.size(); ++j) {
    angle_sum += tmp_list[j][0];
    rho_sum += tmp_list[j][1];
  }
  angle_sum /= tmp_list.size();
  rho_sum /= tmp_list.size();

  new_point[0] = angle_sum;
  new_point[1] = rho_sum;

  condensed.push_back(new_point);
}

vector<Vec2f> condense_lines(vector<Vec2f> lines, bool keep_going) {
  bool debug = false;
  vector<Vec2f> condensed;
  vector<Vec2f> tmp_list;
  double diff;
  bool flipped;

  if (debug) {
    printf("\n================== Before Anything ===================\n");
    for (int i = 0; i < lines.size(); ++i) {
      printf("(%5.1f, %5.1f) ", rad2deg(lines[i][keep_going ? 1 : 0]), lines[i][keep_going ? 0 : 1]);
    }
    printf("\n");
  }

  if (keep_going) {
    for (int i = 0; i < (int) lines.size(); i++) {
      //put in order of theta, rho
      swap(lines[i][0], lines[i][1]);

      if (debug) {
        printf("Took line from (%5.1f, %5.1f) to ", rad2deg(lines[i][0]), lines[i][1]);

        //      lines[i] = normalize_point(lines[i]);
        printf("normalized (%5.1f, %5.1f) to ", rad2deg(lines[i][0]), lines[i][1]);
        flipped = false;
      }
      if (lines[i][0] >= deg2rad(90)) {
        if (debug) {
          flipped = true;
        }
        lines[i] = flip_line(lines[i]);
      }
      if (debug) {
        printf("oriented (%5.1f, %5.1f) ", rad2deg(lines[i][0]), lines[i][1]);
        if (flipped) { printf("And I flipped"); }
        printf("\n");
      }
    }
    // return lines;
  }

  if (debug) {
    printf("\n================== Before Sorting ===================\n");
    for (int i = 0; i < lines.size(); ++i) {
      printf("(%5.1f, %5.1f) ", rad2deg(lines[i][0]), lines[i][1]);
    }
    printf("\n");
  }

  //Order from least to greatest theta
  sort(lines.begin(), lines.end(),
       [](const Vec2f &a, const Vec2f &b) {
         return a[0] < b[0];
       });

  if (debug) {
    printf("\n================== After Pre-Processing ===================\n");
    for (int i = 0; i < lines.size(); ++i) {
      printf("(%5.1f, %5.1f) ", rad2deg(lines[i][0]), lines[i][1]);
    }
    printf("\n");
  }

  while (!lines.empty()) {
    Vec2f to_manipulate = lines.front();
    lines.erase(lines.begin());

    if (tmp_list.empty()) {
      tmp_list.push_back(to_manipulate);
      continue;
    } else {
      diff = abs(to_manipulate[0] - tmp_list.front()[0]);
      if (diff > deg2rad(180)) {
        diff = deg2rad(360) - diff;
      }
      if (diff < deg2rad(degree_tolerance)) {
        //The angles are similar
        if (abs(to_manipulate[1] - tmp_list.front()[1]) < distance_tolerance) {
          //the distances are similar
          tmp_list.push_back(to_manipulate);
          continue;
        } else {
          if (debug) {
            printf("The angles %6.1f and %6.1f are close enough\n", rad2deg(to_manipulate[0]), rad2deg(tmp_list.front()[0]));
            printf("distance of %4.1f and %4.1f is too much\n", to_manipulate[1], tmp_list.front()[1]);
          }
        }
      } else {
        if (debug) {
          printf("The angles %6.1f and %6.1f are too much\n", rad2deg(to_manipulate[0]), rad2deg(tmp_list.front()[0]));
        }
        //Need to clear out the tmp_list
        compress_lines(condensed, tmp_list);

        tmp_list.clear();
        tmp_list.push_back(to_manipulate);

      }
    }
  }
  if (!tmp_list.empty()) {
    compress_lines(condensed, tmp_list);
  }
  if (condensed.size() >= 2) {
    condensed.back() = flip_line(condensed.back());

    if (keep_going) {
      if (debug) {
        printf("Second loop\n");
      }
      condensed = condense_lines(condensed, false);
    }
  }
  return condensed;
}<commit_msg>things. idk<commit_after>//
// Created by Caleb on 11/15/16.
//

#include "lineFollowing.h"
#include "line_simplification.h"
#include "line_utilities.h"

void compress_lines(vector<Vec2f> &condensed, const vector<Vec2f> &tmp_list) {

  Vec2f new_point;
  float angle_sum = 0;
  float rho_sum = 0;
  for (int j = 0; j < (int) tmp_list.size(); ++j) {
    angle_sum += tmp_list[j][0];
    rho_sum += tmp_list[j][1];
  }
  angle_sum /= tmp_list.size();
  rho_sum /= tmp_list.size();

  new_point[0] = angle_sum;
  new_point[1] = rho_sum;

  condensed.push_back(new_point);
}

vector<Vec2f> condense_lines(vector<Vec2f> lines, bool keep_going) {
  bool debug = false;
  vector<Vec2f> condensed;
  vector<Vec2f> tmp_list;
  double diff;
  bool flipped;

  if (debug) {
    printf("\n================== Before Anything ===================\n");
    for (int i = 0; i < lines.size(); ++i) {
      printf("(%5.1f, %5.1f) ", rad2deg(lines[i][keep_going ? 1 : 0]), lines[i][keep_going ? 0 : 1]);
    }
    printf("\n");
  }

  if (keep_going) {
    for (int i = 0; i < (int) lines.size(); i++) {
      //put in order of theta, rho

      if (debug) {
        printf("Took line from (%5.1f, %5.1f) to ", rad2deg(lines[i][0]), lines[i][1]);

        //      lines[i] = normalize_point(lines[i]);
        printf("normalized (%5.1f, %5.1f) to ", rad2deg(lines[i][0]), lines[i][1]);
        flipped = false;
      }
      if (lines[i][0] >= deg2rad(90)) {
        if (debug) {
          flipped = true;
        }
        lines[i] = flip_line(lines[i]);
      }
      if (debug) {
        printf("oriented (%5.1f, %5.1f) ", rad2deg(lines[i][0]), lines[i][1]);
        if (flipped) { printf("And I flipped"); }
        printf("\n");
      }
    }
    // return lines;
  }

  if (debug) {
    printf("\n================== Before Sorting ===================\n");
    for (int i = 0; i < lines.size(); ++i) {
      printf("(%5.1f, %5.1f) ", rad2deg(lines[i][0]), lines[i][1]);
    }
    printf("\n");
  }

  //Order from least to greatest theta
  sort(lines.begin(), lines.end(),
       [](const Vec2f &a, const Vec2f &b) {
         return a[0] < b[0];
       });

  if (debug) {
    printf("\n================== After Pre-Processing ===================\n");
    for (int i = 0; i < lines.size(); ++i) {
      printf("(%5.1f, %5.1f) ", rad2deg(lines[i][0]), lines[i][1]);
    }
    printf("\n");
  }

  while (!lines.empty()) {
    Vec2f to_manipulate = lines.front();
    lines.erase(lines.begin());

    if (tmp_list.empty()) {
      tmp_list.push_back(to_manipulate);
      continue;
    } else {
      diff = abs(to_manipulate[0] - tmp_list.front()[0]);
      if (diff > deg2rad(180)) {
        diff = deg2rad(360) - diff;
      }
      if (diff < deg2rad(degree_tolerance)) {
        //The angles are similar
        if (abs(to_manipulate[1] - tmp_list.front()[1]) < distance_tolerance) {
          //the distances are similar
          tmp_list.push_back(to_manipulate);
          continue;
        } else {
          if (debug) {
            printf("The angles %6.1f and %6.1f are close enough\n", rad2deg(to_manipulate[0]), rad2deg(tmp_list.front()[0]));
            printf("distance of %4.1f and %4.1f is too much\n", to_manipulate[1], tmp_list.front()[1]);
          }
        }
      } else {
        if (debug) {
          printf("The angles %6.1f and %6.1f are too much\n", rad2deg(to_manipulate[0]), rad2deg(tmp_list.front()[0]));
        }
        //Need to clear out the tmp_list
        compress_lines(condensed, tmp_list);

        tmp_list.clear();
        tmp_list.push_back(to_manipulate);

      }
    }
  }
  if (!tmp_list.empty()) {
    compress_lines(condensed, tmp_list);
  }
  if (condensed.size() >= 2) {
    condensed.back() = flip_line(condensed.back());

    if (keep_going) {
      if (debug) {
        printf("Second loop\n");
      }
      condensed = condense_lines(condensed, false);
    }
  }
  return condensed;
}<|endoftext|>


<commit_before>#if !defined(B9_BYTECODES_HPP_)
#define B9_BYTECODES_HPP_

#include <cstdint>
#include <ostream>

namespace b9 {

// bits may be an argument to the opcode
using RawByteCode = std::uint8_t;

enum class ByteCode : RawByteCode {
  // Generic ByteCodes

  // A special uninterpreted ByteCode placed the end of a
  // ByteCode array.
  END_SECTION = 0x0,

  // Drop the top element of the stack
  DROP = 0x1,
  // Duplicate the top element on the stack
  DUPLICATE = 0x2,
  // Return from a function
  FUNCTION_RETURN = 0x3,
  // Call a Base9 function
  FUNCTION_CALL = 0x4,
  // Call a native C function
  PRIMITIVE_CALL = 0x5,
  // Jump unconditionally by the offset
  JMP = 0x6,
  // Push from a local variable
  PUSH_FROM_VAR = 0x7,
  // Push into a local variable
  POP_INTO_VAR = 0x8,

  // Integer bytecodes

  // Push a constant
  INT_PUSH_CONSTANT = 0x9,
  // Subtract two integers
  INT_SUB = 0xa,
  // Add two integers
  INT_ADD = 0xb,
  // Jump if two integers are equal
  INT_JMP_EQ = 0xc,
  // Jump if two integer are not equal
  INT_JMP_NEQ = 0xd,
  // Jump if the first integer is greater than the second
  INT_JMP_GT = 0xe,
  // Jump if the first integer is greater than or equal to the second
  INT_JMP_GE = 0xf,
  // Jump if the first integer is less than to the second
  INT_JMP_LT = 0x10,
  // Jump if the first integer is less than or equal to the second
  INT_JMP_LE = 0x11,

  // String ByteCodes

  // Push a string from this module's constant pool
  STR_PUSH_CONSTANT = 0x12,
  // Jump if two strings are equal
  STR_JMP_EQ = 0x13,
  // Jump if two integer are not equal
  STR_JMP_NEQ = 0x14,
};

inline const char *toString(ByteCode bc) {
  switch (bc) {
    case ByteCode::DROP:
      return "ByteCode::DROP";
    case ByteCode::DUPLICATE:
      return "ByteCode::DUPLICATE";
    case ByteCode::FUNCTION_RETURN:
      return "ByteCode::FUNCTION_RETURN";
    case ByteCode::FUNCTION_CALL:
      return "ByteCode::FUNCTION_CALL";
    case ByteCode::PRIMITIVE_CALL:
      return "ByteCode::PRIMITIVE_CALL";
    case ByteCode::JMP:
      return "ByteCode::JMP";
    case ByteCode::PUSH_FROM_VAR:
      return "ByteCode::PUSH_FROM_VAR";
    case ByteCode::POP_INTO_VAR:
      return "ByteCode::POP_INTO_VAR";
    case ByteCode::INT_PUSH_CONSTANT:
      return "ByteCode::INT_PUSH_CONSTANT";
    case ByteCode::INT_SUB:
      return "ByteCode::INT_SUB";
    case ByteCode::INT_ADD:
      return "ByteCode::INT_ADD";
    case ByteCode::INT_JMP_EQ:
      return "ByteCode::INT_JMP_EQ";
    case ByteCode::INT_JMP_NEQ:
      return "ByteCode::INT_JMP_NEQ";
    case ByteCode::INT_JMP_GT:
      return "ByteCode::INT_JMP_GT";
    case ByteCode::INT_JMP_GE:
      return "ByteCode::INT_JMP_GE";
    case ByteCode::INT_JMP_LT:
      return "ByteCode::INT_JMP_LT";
    case ByteCode::INT_JMP_LE:
      return "ByteCode::INT_JMP_LE";
    case ByteCode::STR_PUSH_CONSTANT:
      return "ByteCode::STR_PUSH_CONSTANT";
    case ByteCode::STR_JMP_EQ:
      return "ByteCode::STR_JMP_EQ";
    case ByteCode::STR_JMP_NEQ:
      return "ByteCode::STR_JMP_NEQ";
    default:
      return "UNKNOWN_BYTECODE";
  }
}

inline std::ostream &operator<<(std::ostream &out, ByteCode bc) {
  return out << toString(bc);
}

}  // namespace b9

#endif  // B9_BYTECODES_HPP_
<commit_msg>Print the END_SECTION ByteCode correctly<commit_after>#if !defined(B9_BYTECODES_HPP_)
#define B9_BYTECODES_HPP_

#include <cstdint>
#include <ostream>

namespace b9 {

// bits may be an argument to the opcode
using RawByteCode = std::uint8_t;

enum class ByteCode : RawByteCode {
  // Generic ByteCodes

  // A special uninterpreted ByteCode placed the end of a
  // ByteCode array.
  END_SECTION = 0x0,

  // Drop the top element of the stack
  DROP = 0x1,
  // Duplicate the top element on the stack
  DUPLICATE = 0x2,
  // Return from a function
  FUNCTION_RETURN = 0x3,
  // Call a Base9 function
  FUNCTION_CALL = 0x4,
  // Call a native C function
  PRIMITIVE_CALL = 0x5,
  // Jump unconditionally by the offset
  JMP = 0x6,
  // Push from a local variable
  PUSH_FROM_VAR = 0x7,
  // Push into a local variable
  POP_INTO_VAR = 0x8,

  // Integer bytecodes

  // Push a constant
  INT_PUSH_CONSTANT = 0x9,
  // Subtract two integers
  INT_SUB = 0xa,
  // Add two integers
  INT_ADD = 0xb,
  // Jump if two integers are equal
  INT_JMP_EQ = 0xc,
  // Jump if two integer are not equal
  INT_JMP_NEQ = 0xd,
  // Jump if the first integer is greater than the second
  INT_JMP_GT = 0xe,
  // Jump if the first integer is greater than or equal to the second
  INT_JMP_GE = 0xf,
  // Jump if the first integer is less than to the second
  INT_JMP_LT = 0x10,
  // Jump if the first integer is less than or equal to the second
  INT_JMP_LE = 0x11,

  // String ByteCodes

  // Push a string from this module's constant pool
  STR_PUSH_CONSTANT = 0x12,
  // Jump if two strings are equal
  STR_JMP_EQ = 0x13,
  // Jump if two integer are not equal
  STR_JMP_NEQ = 0x14,
};

inline const char *toString(ByteCode bc) {
  switch (bc) {
    case ByteCode::END_SECTION:
      return "ByteCode::END_SECTION";
    case ByteCode::DROP:
      return "ByteCode::DROP";
    case ByteCode::DUPLICATE:
      return "ByteCode::DUPLICATE";
    case ByteCode::FUNCTION_RETURN:
      return "ByteCode::FUNCTION_RETURN";
    case ByteCode::FUNCTION_CALL:
      return "ByteCode::FUNCTION_CALL";
    case ByteCode::PRIMITIVE_CALL:
      return "ByteCode::PRIMITIVE_CALL";
    case ByteCode::JMP:
      return "ByteCode::JMP";
    case ByteCode::PUSH_FROM_VAR:
      return "ByteCode::PUSH_FROM_VAR";
    case ByteCode::POP_INTO_VAR:
      return "ByteCode::POP_INTO_VAR";
    case ByteCode::INT_PUSH_CONSTANT:
      return "ByteCode::INT_PUSH_CONSTANT";
    case ByteCode::INT_SUB:
      return "ByteCode::INT_SUB";
    case ByteCode::INT_ADD:
      return "ByteCode::INT_ADD";
    case ByteCode::INT_JMP_EQ:
      return "ByteCode::INT_JMP_EQ";
    case ByteCode::INT_JMP_NEQ:
      return "ByteCode::INT_JMP_NEQ";
    case ByteCode::INT_JMP_GT:
      return "ByteCode::INT_JMP_GT";
    case ByteCode::INT_JMP_GE:
      return "ByteCode::INT_JMP_GE";
    case ByteCode::INT_JMP_LT:
      return "ByteCode::INT_JMP_LT";
    case ByteCode::INT_JMP_LE:
      return "ByteCode::INT_JMP_LE";
    case ByteCode::STR_PUSH_CONSTANT:
      return "ByteCode::STR_PUSH_CONSTANT";
    case ByteCode::STR_JMP_EQ:
      return "ByteCode::STR_JMP_EQ";
    case ByteCode::STR_JMP_NEQ:
      return "ByteCode::STR_JMP_NEQ";
    default:
      return "UNKNOWN_BYTECODE";
  }
}

inline std::ostream &operator<<(std::ostream &out, ByteCode bc) {
  return out << toString(bc);
}

}  // namespace b9

#endif  // B9_BYTECODES_HPP_
<|endoftext|>


<commit_before><commit_msg>Initialize StatsTable::Private members.<commit_after><|endoftext|>