#include #include #include using namespace std; #include #include using namespace boost; #include "cseputils.h" #include "parsequery.h" #include "calpontselectexecutionplan.h" #include "simplecolumn.h" #include "simplefilter.h" #include "constantcolumn.h" #include "calpontsystemcatalog.h" #include "sessionmanager.h" using namespace execplan; #include "brmtypes.h" using namespace BRM; extern int qfeparse(); extern int qfedebug; struct yy_buffer_state; extern yy_buffer_state* qfe_scan_string(const char*); extern void qfe_delete_buffer(yy_buffer_state*); extern CalpontSelectExecutionPlan* ParserCSEP; extern boost::shared_ptr ParserCSC; namespace { mutex ParserMutex; } // namespace namespace qfe { extern string DefaultSchema; CalpontSelectExecutionPlan* parseQuery(const string& query, const uint32_t sid) { // We're going to make parsing the query single-threaded for now. This makes it a lot // easier to interface with the parser and doesn;t materially affect overall query // performance (I think) mutex::scoped_lock lk(ParserMutex); boost::shared_ptr csc = CalpontSystemCatalog::makeCalpontSystemCatalog(sid); CalpontSelectExecutionPlan* csep = 0; csep = new CalpontSelectExecutionPlan(); // we use an auto_ptr here with some trepidation. We only want auto delete on an execption. // If the parseing and plan build succeed, we want the ptr to stay around. boost::scoped_ptr<> // doesn't have an API to release ownership, so we use auto_ptr... auto_ptr scsep(csep); yy_buffer_state* ybs = 0; ybs = qfe_scan_string(query.c_str()); if (ybs != 0) { ParserCSEP = csep; ParserCSC = csc; if (qfeparse() != 0) throw runtime_error("syntax error"); qfe_delete_buffer(ybs); } else throw runtime_error("Internal parser memory error"); csep->data(query); SessionManager sm; TxnID txnID; txnID = sm.getTxnID(sid); if (!txnID.valid) { txnID.id = 0; txnID.valid = true; } QueryContext verID; verID = sm.verID(); csep->txnID(txnID.id); csep->verID(verID); csep->sessionID(sid); // cout << *csep << endl; scsep.release(); return csep; } } // namespace qfe