Esempio n. 1
0
int
main(
  int           argc,
  char **       argv)
{
  if ( MPI_SUCCESS != MPI_Init( & argc , & argv ) ) {
    std::cerr << "MPI_Init FAILED" << std::endl ;
    abort();
  }

  {
    std::string test_names;

    for (int i = 0; i < argc; ++i) {
      if (std::string(argv[i]) == "-test") {
        if (i + 1 < argc)
          test_names = argv[i + 1];
        else 
          std::cout << "Running all tests" << std::endl;
      }
    }
      
    CppUnit::TextUi::TestRunner runner;
    CppUnit::TestFactoryRegistry & registry = CppUnit::TestFactoryRegistry::getRegistry();
    runner.addTest( registry.makeTest() );
    runner.run(test_names);
  }

  MPI_Finalize();

  return 0;
}
Esempio n. 2
0
 bool crypto_ops::check_signature(const Hash &prefix_hash, const PublicKey &pub, const Signature &sig) {
   ge_p2 tmp2;
   ge_p3 tmp3;
   EllipticCurveScalar c;
   s_comm buf;
   assert(check_key(pub));
   buf.h = prefix_hash;
   buf.key = reinterpret_cast<const EllipticCurvePoint&>(pub);
   if (ge_frombytes_vartime(&tmp3, reinterpret_cast<const unsigned char*>(&pub)) != 0) {
     abort();
   }
   if (sc_check(reinterpret_cast<const unsigned char*>(&sig)) != 0 || sc_check(reinterpret_cast<const unsigned char*>(&sig) + 32) != 0) {
     return false;
   }
   ge_double_scalarmult_base_vartime(&tmp2, reinterpret_cast<const unsigned char*>(&sig), &tmp3, reinterpret_cast<const unsigned char*>(&sig) + 32);
   ge_tobytes(reinterpret_cast<unsigned char*>(&buf.comm), &tmp2);
   hash_to_scalar(&buf, sizeof(s_comm), c);
   sc_sub(reinterpret_cast<unsigned char*>(&c), reinterpret_cast<unsigned char*>(&c), reinterpret_cast<const unsigned char*>(&sig));
   return sc_isnonzero(reinterpret_cast<unsigned char*>(&c)) == 0;
 }
Esempio n. 3
0
 bool crypto_ops::check_signature(const hash &prefix_hash, const public_key &pub, const signature &sig) {
   ge_p2 tmp2;
   ge_p3 tmp3;
   ec_scalar c;
   s_comm buf;
   assert(check_key(pub));
   buf.h = prefix_hash;
   buf.key = pub;
   if (ge_frombytes_vartime(&tmp3, &pub) != 0) {
     abort();
   }
   if (sc_check(&sig.c) != 0 || sc_check(&sig.r) != 0) {
     return false;
   }
   ge_double_scalarmult_base_vartime(&tmp2, &sig.c, &tmp3, &sig.r); //tmp2 = cP + rG
   ge_tobytes(&buf.comm, &tmp2);
   hash_to_scalar(&buf, sizeof(s_comm), c);
   sc_sub(&c, &c, &sig.c);
   return sc_isnonzero(&c) == 0;
 }
Esempio n. 4
0
  bool crypto_ops::check_ring_signature(const Hash &prefix_hash, const KeyImage &image,
    const PublicKey *const *pubs, size_t pubs_count,
    const Signature *sig) {
    size_t i;
    ge_p3 image_unp;
    ge_dsmp image_pre;
    EllipticCurveScalar sum, h;
    rs_comm *const buf = reinterpret_cast<rs_comm *>(alloca(rs_comm_size(pubs_count)));
#if !defined(NDEBUG)
    for (i = 0; i < pubs_count; i++) {
      assert(check_key(*pubs[i]));
    }
#endif
    if (ge_frombytes_vartime(&image_unp, reinterpret_cast<const unsigned char*>(&image)) != 0) {
      return false;
    }
    ge_dsm_precomp(image_pre, &image_unp);
    sc_0(reinterpret_cast<unsigned char*>(&sum));
    buf->h = prefix_hash;
    for (i = 0; i < pubs_count; i++) {
      ge_p2 tmp2;
      ge_p3 tmp3;
      if (sc_check(reinterpret_cast<const unsigned char*>(&sig[i])) != 0 || sc_check(reinterpret_cast<const unsigned char*>(&sig[i]) + 32) != 0) {
        return false;
      }
      if (ge_frombytes_vartime(&tmp3, reinterpret_cast<const unsigned char*>(&*pubs[i])) != 0) {
        abort();
      }
      ge_double_scalarmult_base_vartime(&tmp2, reinterpret_cast<const unsigned char*>(&sig[i]), &tmp3, reinterpret_cast<const unsigned char*>(&sig[i]) + 32);
      ge_tobytes(reinterpret_cast<unsigned char*>(&buf->ab[i].a), &tmp2);
      hash_to_ec(*pubs[i], tmp3);
      ge_double_scalarmult_precomp_vartime(&tmp2, reinterpret_cast<const unsigned char*>(&sig[i]) + 32, &tmp3, reinterpret_cast<const unsigned char*>(&sig[i]), image_pre);
      ge_tobytes(reinterpret_cast<unsigned char*>(&buf->ab[i].b), &tmp2);
      sc_add(reinterpret_cast<unsigned char*>(&sum), reinterpret_cast<unsigned char*>(&sum), reinterpret_cast<const unsigned char*>(&sig[i]));
    }
    hash_to_scalar(buf, rs_comm_size(pubs_count), h);
    sc_sub(reinterpret_cast<unsigned char*>(&h), reinterpret_cast<unsigned char*>(&h), reinterpret_cast<unsigned char*>(&sum));
    return sc_isnonzero(reinterpret_cast<unsigned char*>(&h)) == 0;
  }
Esempio n. 5
0
  bool crypto_ops::check_ring_signature(const hash &prefix_hash, const key_image &image,
    const public_key *const *pubs, size_t pubs_count,
    const signature *sig) {
    size_t i;
    ge_p3 image_unp;
    ge_dsmp image_pre;
    ec_scalar sum, h;
    rs_comm *const buf = reinterpret_cast<rs_comm *>(alloca(rs_comm_size(pubs_count)));
#if !defined(NDEBUG)
    for (i = 0; i < pubs_count; i++) {
      assert(check_key(*pubs[i]));
    }
#endif
    if (ge_frombytes_vartime(&image_unp, &image) != 0) {
      return false;
    }
    ge_dsm_precomp(image_pre, &image_unp);
    sc_0(&sum);
    buf->h = prefix_hash;
    for (i = 0; i < pubs_count; i++) {
      ge_p2 tmp2;
      ge_p3 tmp3;
      if (sc_check(&sig[i].c) != 0 || sc_check(&sig[i].r) != 0) {
        return false;
      }
      if (ge_frombytes_vartime(&tmp3, &*pubs[i]) != 0) {
        abort();
      }
      ge_double_scalarmult_base_vartime(&tmp2, &sig[i].c, &tmp3, &sig[i].r);
      ge_tobytes(&buf->ab[i].a, &tmp2);
      hash_to_ec(*pubs[i], tmp3);
      ge_double_scalarmult_precomp_vartime(&tmp2, &sig[i].r, &tmp3, &sig[i].c, image_pre);
      ge_tobytes(&buf->ab[i].b, &tmp2);
      sc_add(&sum, &sum, &sig[i].c);
    }
    hash_to_scalar(buf, rs_comm_size(pubs_count), h);
    sc_sub(&h, &h, &sum);
    return sc_isnonzero(&h) == 0;
  }
Esempio n. 6
0
int main( int argc, char **argv ){
    // initialize the logger
    cpplog::FileLogger log( "log.txt"  );

    po::options_description desc("Allowed Options");

    desc.add_options()
        ("help,h", "produce this message")
        ("target,t", po::value< string >(), "extant graph file")
        ("ratio,r", po::value< double >()->default_value(1.0), "ratio of creation to deletion cost")
        ("beta,b", po::value< double >()->default_value(60.0), "scale factor for cost classes")
        ("undir,u", po::value< bool >()->zero_tokens() , "graph is undirected")
        ("output,o", po::value< string >()->default_value("edgeProbs.txt"), "output file containing edge probabilities")
        ("numOpt,k", po::value< size_t>()->default_value(10), "number of near-optimal score classes to use")
        ("timePenalty,p", po::value< double >()->default_value(0.0), "amount to penalize flips between nodes whose time intervals don't overlap'")
        ("old,x", po::value< bool >()->zero_tokens(), "run using \"old\" algorithm")
        ("lazy,l", po::value< bool >()->zero_tokens(), "run using the \"lazy\" algorithm")
        ("dupHist,d", po::value< vector<string> >(), "duplication history input file(s) [ either 1 or 2 newick format trees ]")
        ;

    try {
        ArgParser ap( desc );
        ap.parse_args( argc, argv );

        vector<string> treeNames = ap["dupHist"].as< vector<string> >();
        if ( treeNames.size() > 2 ) {
            cerr << "only 1 or 2 duplication histories can be provided; you provided "+treeNames.size() << "\n";
            abort();
        } else {
            for ( const auto& tn : treeNames ) { cerr << "Input tree : " << tn << "\n"; }
        }
        string graphName = ap["target"].as<string>();
        string outputName = ap["output"].as<string>();

        double penalty = ap["timePenalty"].as<double>();
        double creationCost = ap["ratio"].as<double>();
        double deletionCost = 1.0;

        bool undirected = ap.isPresent("undir");
        bool directed = !undirected;
        size_t k = ap["numOpt"].as<size_t>();

        LOG_INFO(log) << "Input graph is " << (undirected  ? "Undirected" : "Directed") << "\n";
        try {

            TreePtrT tree ( Utils::Trees::readNewickTree(treeNames[0]) );

            if ( treeNames.size() > 1 ) {
                auto tree2 = Utils::Trees::readNewickTree(treeNames[1]).release();
                auto node = new bpp::Node("#preroot#");
                auto r1 = tree->getRootNode();
                auto r2 = tree2->getRootNode();

                // relationship with tree 1
                node->addSon(0, tree->getRootNode());
                // relationship with tree 2
                node->addSon(1, tree2->getRootNode());

                // root the tree at our new node
                tree->setRootNode(node);
                LOG_INFO(log) << "rerooted\n";
                // relabel all of the nodes
                tree->resetNodesId();
                LOG_INFO(log) << "relabeled\n";

                auto rootId = tree->getRootId();
                // set the name of the root
                tree->setNodeName( rootId, "#preroot#");
                tree->setVoidBranchLengths(0.0);
            }

            // put the node names on all the nodes
            Utils::Trees::labelTree(tree);


            TreeInfo tinfo("TreeInfo");
            auto rId = tree->getRootId();

            vector<FlipKey> keyList;
            if ( treeNames.size() > 1 ) {

                auto r1 = tree->getSonsId(rId)[0];
                auto r2 = tree->getSonsId(rId)[1];

                keyList.push_back( FlipKey(r1,r2,true,true) );
            }

            tinfo.extantInterval[ rId ] = make_tuple( -std::numeric_limits<double>::infinity(), 0.0 );
            Utils::Trees::prepareTree( tree, tinfo, rId );
            /*
            auto nodes = vector<int>(tree->getNodesId());
            std::sort( nodes.begin(), nodes.end(),
                [&]( const int& n1, const int& n2 ) -> bool {
                    return tree->getNodeName(n1) < tree->getNodeName(n2);
                }
            );
            for ( auto n : nodes ) {
                cerr << tree->getNodeName(n) << ",";
                for ( auto sn : tinfo.leaves[n] ) {
                    cerr << " " << tree->getNodeName(sn);
                }
                cerr << ",";
                for ( auto en : tinfo.enets[n] ) {
                    cerr << " " << en;
                }
                cerr << "\n";
            }
            exit(0);
            */
            // print out the existence intervals for all of the nodes
            /*
            for ( auto nid : tree->getNodesId() ){
                auto nodeName = Utils::Trees::getName(tree,nid);
                cout << "Node [" << nodeName << "] : existance interval = [" <<
                    get<0>(tinfo.extantInterval[nid]) << ", " << get<1>(tinfo.extantInterval[nid]) << "] \n";
            }
            */

            unordered_map<string, int> leafIDMap;
            for( auto nid : tree->getLeavesId() ) { leafIDMap[ Utils::Trees::getName(tree,nid) ] = nid; }

            auto isAdjList = [&](){
                auto spos = graphName.find_last_of(".");
                auto suffix(graphName.substr( spos ));
                return suffix == ".adj";
            }();

            variant< directedGraphT, undirectedGraphT > G;
            if ( undirected ) {
                G = undirectedGraphT();
                auto& UG = get<undirectedGraphT>(G);
                //Add all leaf nodes to the graph
                for ( auto nameId : leafIDMap ) {
                    if ( nameId.first.find("LOST") == nameId.first.npos  ) {
                        auto u = add_vertex(UG);
                        UG[u].name = nameId.first;
                        UG[u].idx = nameId.second;
                    }
                }


                if ( isAdjList ) {
                    GraphUtils::readFromAdjacencyList( graphName, leafIDMap, UG );
                } else {
                    GraphUtils::readFromMultilineAdjacencyList(graphName, leafIDMap, UG );
                }

            } else {
                G = directedGraphT();
                auto& DG = get<directedGraphT>(G);
                // Add all leaf nodes to the graph
                for ( auto nameId : leafIDMap ) {
                    if ( nameId.first.find("LOST") == nameId.first.npos  ) {
                        auto u = add_vertex(DG);
                        DG[u].name = nameId.first;
                        DG[u].idx = nameId.second;
                    }
                }

                GraphUtils::readFromMultilineAdjacencyList(graphName, leafIDMap, DG);
            }

            //typedef graph_traits < graphT >::vertex_descriptor vertexDescT;
            //typedef graph_traits < graphT >::edge_descriptor
            //edgeDescT;

            auto H = MultiOpt::buildSolutionSpaceGraph( tree, tinfo, creationCost, deletionCost, penalty, directed );

            vector<size_t> order; order.reserve( H->order() );
            MultiOpt::topologicalOrder( H, order );

            MultiOpt::slnDictT slnDict;
            //slnDict.set_empty_key( std::numeric_limits<size_t>::max() );
            if ( undirected ) {
                MultiOpt::leafCostDict( H, tree, get<undirectedGraphT>(G), directed, creationCost, deletionCost, slnDict);
            } else {
                MultiOpt::leafCostDict( H, tree, get<directedGraphT>(G), directed, creationCost, deletionCost, slnDict);
            }


            auto rootKey = FlipKey( tree->getRootId(), tree->getRootId(), false, false );
            auto rootInd = H->index(rootKey);

            // Count the # of opt slns.
            MultiOpt::countDictT countDict;
            countDict.set_empty_key(-1);
            auto beta =  ap["beta"].as<double>();

            if (ap.isPresent("lazy")) {
                // lazy
                auto derivs = MultiOpt::initKBest( H, order, slnDict );
                std::vector<size_t> edges = MultiOpt::viterbiPass(H, derivs, order);

                auto vstr = [&]( const FlipKey& vert ) -> string {
                    auto uname = tree->getNodeName(vert.u());
                    auto vname = tree->getNodeName(vert.v());
                    if (uname > vname) {
                        auto tmp = vname;
                        vname = uname;
                        uname = tmp;
                    }
                    auto fstr = vert.f() ? "true" : "false";
                    auto rstr = vert.r() ? "true" : "false";
                    return uname+"\t"+vname+"\t"+fstr+"\t"+rstr;
                };

                vector<size_t> q;
                q.push_back(rootInd);
                while ( q.size() > 0 ) {
                    auto vit = q.back();
                    auto eid = edges[vit];
                    auto e = H->edge(eid);
                    auto isInternal = H->incident(vit).size() > 0;
                    q.pop_back();
                    cerr << "satisfying " << vstr(H->vertex(vit)) << " using [ ";
                    for ( auto tid : e.tail() ) {
                        cerr << vstr( H->vertex(tid) ) << ", ";
                        if (isInternal) { q.push_back(tid);}
                    }
                    cerr << "]\n";
                }

                exit(0);
                MultiOpt::lazyKthBest( H, rootInd, k, k, derivs );
                MultiOpt::computePosteriors(H, tree, order, derivs, outputName, keyList, beta);
            } else {
                if ( ap.isPresent("old") ) {
                    LOG_INFO(log) << "Old algo\n";
                    MultiOpt::viterbiCount(H, tree, tinfo, penalty, order, slnDict, countDict, k, outputName, keyList, beta);
                } else {
                    LOG_INFO(log) << "New algo\n";
                    // eager
                    MultiOpt::viterbiCountNew<CostClass<EdgeDerivInfoEager>>(H, tree, tinfo, penalty, order, slnDict, countDict, k, outputName, keyList, beta);
                }
            }

        } catch (const Exception &e) {
            LOG_ERROR(log) << "Error when reading tree : " << e.what() << endl;
        }
    } catch(exception& e) {
        LOG_ERROR(log) << "Caught Exception: [" << e.what() << "]\n";
        abort();
    }

    return 0;
}
Esempio n. 7
0
  void crypto_ops::generate_ring_signature(const Hash &prefix_hash, const KeyImage &image,
    const PublicKey *const *pubs, size_t pubs_count,
    const SecretKey &sec, size_t sec_index,
    Signature *sig) {
    lock_guard<mutex> lock(random_lock);
    size_t i;
    ge_p3 image_unp;
    ge_dsmp image_pre;
    EllipticCurveScalar sum, k, h;
    rs_comm *const buf = reinterpret_cast<rs_comm *>(alloca(rs_comm_size(pubs_count)));
    assert(sec_index < pubs_count);
#if !defined(NDEBUG)
    {
      ge_p3 t;
      PublicKey t2;
      KeyImage t3;
      assert(sc_check(reinterpret_cast<const unsigned char*>(&sec)) == 0);
      ge_scalarmult_base(&t, reinterpret_cast<const unsigned char*>(&sec));
      ge_p3_tobytes(reinterpret_cast<unsigned char*>(&t2), &t);
      assert(*pubs[sec_index] == t2);
      generate_key_image(*pubs[sec_index], sec, t3);
      assert(image == t3);
      for (i = 0; i < pubs_count; i++) {
        assert(check_key(*pubs[i]));
      }
    }
#endif
    if (ge_frombytes_vartime(&image_unp, reinterpret_cast<const unsigned char*>(&image)) != 0) {
      abort();
    }
    ge_dsm_precomp(image_pre, &image_unp);
    sc_0(reinterpret_cast<unsigned char*>(&sum));
    buf->h = prefix_hash;
    for (i = 0; i < pubs_count; i++) {
      ge_p2 tmp2;
      ge_p3 tmp3;
      if (i == sec_index) {
        random_scalar(k);
        ge_scalarmult_base(&tmp3, reinterpret_cast<unsigned char*>(&k));
        ge_p3_tobytes(reinterpret_cast<unsigned char*>(&buf->ab[i].a), &tmp3);
        hash_to_ec(*pubs[i], tmp3);
        ge_scalarmult(&tmp2, reinterpret_cast<unsigned char*>(&k), &tmp3);
        ge_tobytes(reinterpret_cast<unsigned char*>(&buf->ab[i].b), &tmp2);
      } else {
        random_scalar(reinterpret_cast<EllipticCurveScalar&>(sig[i]));
        random_scalar(*reinterpret_cast<EllipticCurveScalar*>(reinterpret_cast<unsigned char*>(&sig[i]) + 32));
        if (ge_frombytes_vartime(&tmp3, reinterpret_cast<const unsigned char*>(&*pubs[i])) != 0) {
          abort();
        }
        ge_double_scalarmult_base_vartime(&tmp2, reinterpret_cast<unsigned char*>(&sig[i]), &tmp3, reinterpret_cast<unsigned char*>(&sig[i]) + 32);
        ge_tobytes(reinterpret_cast<unsigned char*>(&buf->ab[i].a), &tmp2);
        hash_to_ec(*pubs[i], tmp3);
        ge_double_scalarmult_precomp_vartime(&tmp2, reinterpret_cast<unsigned char*>(&sig[i]) + 32, &tmp3, reinterpret_cast<unsigned char*>(&sig[i]), image_pre);
        ge_tobytes(reinterpret_cast<unsigned char*>(&buf->ab[i].b), &tmp2);
        sc_add(reinterpret_cast<unsigned char*>(&sum), reinterpret_cast<unsigned char*>(&sum), reinterpret_cast<unsigned char*>(&sig[i]));
      }
    }
    hash_to_scalar(buf, rs_comm_size(pubs_count), h);
    sc_sub(reinterpret_cast<unsigned char*>(&sig[sec_index]), reinterpret_cast<unsigned char*>(&h), reinterpret_cast<unsigned char*>(&sum));
    sc_mulsub(reinterpret_cast<unsigned char*>(&sig[sec_index]) + 32, reinterpret_cast<unsigned char*>(&sig[sec_index]), reinterpret_cast<const unsigned char*>(&sec), reinterpret_cast<unsigned char*>(&k));
  }
Esempio n. 8
0
  void crypto_ops::generate_ring_signature(const hash &prefix_hash, const key_image &image,
    const public_key *const *pubs, size_t pubs_count,
    const secret_key &sec, size_t sec_index,
    signature *sig) {
    lock_guard<mutex> lock(random_lock);
    size_t i;
    ge_p3 image_unp;
    ge_dsmp image_pre;
    ec_scalar sum, k, h;
    rs_comm *const buf = reinterpret_cast<rs_comm *>(alloca(rs_comm_size(pubs_count)));
    assert(sec_index < pubs_count);
#if !defined(NDEBUG)
    {
      ge_p3 t;
      public_key t2;
      key_image t3;
      assert(sc_check(&sec) == 0);
      ge_scalarmult_base(&t, &sec);
      ge_p3_tobytes(&t2, &t);
      assert(*pubs[sec_index] == t2);
      generate_key_image(*pubs[sec_index], sec, t3);
      assert(image == t3);
      for (i = 0; i < pubs_count; i++) {
        assert(check_key(*pubs[i]));
      }
    }
#endif
    if (ge_frombytes_vartime(&image_unp, &image) != 0) {
      abort();
    }
    ge_dsm_precomp(image_pre, &image_unp);
    sc_0(&sum);
    buf->h = prefix_hash;
    for (i = 0; i < pubs_count; i++) {
      ge_p2 tmp2;
      ge_p3 tmp3;
      if (i == sec_index) {
        random_scalar(k);
        ge_scalarmult_base(&tmp3, &k);
        ge_p3_tobytes(&buf->ab[i].a, &tmp3);
        hash_to_ec(*pubs[i], tmp3);
        ge_scalarmult(&tmp2, &k, &tmp3);
        ge_tobytes(&buf->ab[i].b, &tmp2);
      } else {
        random_scalar(sig[i].c);
        random_scalar(sig[i].r);
        if (ge_frombytes_vartime(&tmp3, &*pubs[i]) != 0) {
          abort();
        }
        ge_double_scalarmult_base_vartime(&tmp2, &sig[i].c, &tmp3, &sig[i].r);
        ge_tobytes(&buf->ab[i].a, &tmp2);
        hash_to_ec(*pubs[i], tmp3);
        ge_double_scalarmult_precomp_vartime(&tmp2, &sig[i].r, &tmp3, &sig[i].c, image_pre);
        ge_tobytes(&buf->ab[i].b, &tmp2);
        sc_add(&sum, &sum, &sig[i].c);
      }
    }
    hash_to_scalar(buf, rs_comm_size(pubs_count), h);
    sc_sub(&sig[sec_index].c, &h, &sum);
    sc_mulsub(&sig[sec_index].r, &sig[sec_index].c, &sec, &k);
  }
Esempio n. 9
0
int main(int argc, char* argv[]) {

    using std::exception;

    // The options to choose the method (parsimony | probabilistic)
    po::options_description cmd("commands");
    cmd.add_options()
    ("command", po::value< string >(), "command to use; one of {gensig, align}");

    // The help option
    po::options_description help("Help Options");
    help.add_options()
    ("help,h", po::value<bool>()->zero_tokens(), "display help for a specific method");

    // The general options are relevant to either method
    po::options_description general("Genearal Options");
    general.add_options()
    ("numProcessors,p", po::value< uint32_t >(), "number of processors to use in parallel");
    ;

    // Those options only relevant to the parsimony method
    po::options_description align("Alignment Options");
    align.add_options()
    ("localSearch,l", po::value< uint32_t >()->default_value(10), "number of iterations of local search to use")
    ("alpha,a", po::value< double >()->default_value(1.0), "alpha() parameter (trade-off between sequence & topology")
    ("beta,b", po::value< double >()->default_value(2.0), "beta parameter (BLAST e-value cutoff)")
    ("unconstrained,r", po::value< double >()->default_value(10), "percentage of local swaps which should be allowed to be unconstrained")
    ("g1,u", po::value< string >(), "first input graph")
    ("g2,v", po::value< string >(), "second input graph")
    ("s1,s", po::value< string >(), "first input signature file")
    ("s2,t", po::value< string >(), "second input signature file")
    ("blast,b", po::value< string >(), "pairwise BLAST scores")
    ("output,o", po::value< string >(), "output alignemnt file")
    ("config,c", po::value< string >(), "configuration file")
    ;

    po::positional_options_description pos;
    pos.add("command", 1);

    // The options description to parse all of the options
    po::options_description all("Allowed options");
    all.add(help).add(cmd).add(general).add(align);

    try {
    	po::variables_map vm;
    	po::store(po::command_line_parser(argc, argv).positional(pos).options(all).run(), vm);

    	if ( vm.count("help") ){
    		std::cout << "GHOST\n";
    		std::cout << all << std::endl;
    		std::exit(1);
    	}
    	/*
    	if ( vm.count("cfg") ) {
    		std::cerr << "have detected configuration file\n";
    		string cfgFile = vm["cfg"].as<string>();
    		std::cerr << "cfgFile : [" << cfgFile << "]\n";
    		po::store(po::parse_config_file<char>(cfgFile.c_str(), programOptions, true), vm);
    	}
    	po::notify(vm);
     	*/

        string logFilePath(".");
        g2LogWorker logger(argv[0], logFilePath);
        g2::initializeLogging(&logger);

        // For any combination of cmd line arguments that won't actually run the program
        // print the appropriate message and exit
        //printHelpUsage(ap, general, prob, parsimony);
        auto command = vm["command"].as<std::string>();
        std::cerr << "command is : " << command << "\n";
        if (command == "align") {
        	globalAlignmentDriver(argc, argv, vm);
        }

        // boost::property_tree::ptree pt;
        // boost::property_tree::ini_parser::read_ini("config.ini", pt);
        // std::cout << pt.get<std::string>("Section1.Value1") << std::endl;
        // std::cout << pt.get<std::string>("Section1.Value2") << std::endl;


    } catch (exception &e) {
        LOG(FATAL) << "Caught Exception: [" << e.what() << "]\n";
        abort();
    }

    return 0;


}