| 569 | } |
| 570 | |
| 571 | int osql_clean_sqlclntstate(struct sqlclntstate *clnt) |
| 572 | { |
| 573 | osqlstate_t *osql = &clnt->osql; |
| 574 | int rc = 0; |
| 575 | int bdberr = 0; |
| 576 | enum ctrl_sqleng state = clnt->ctrl_sqlengine; |
| 577 | |
| 578 | /* |
| 579 | * Warn of any invalid engine state. Do it before srs_tran_destroy() as |
| 580 | * clnt->sql will be pointing at free memory after that. |
| 581 | */ |
| 582 | if (state != SQLENG_NORMAL_PROCESS /* most common case */ |
| 583 | && state != SQLENG_STRT_STATE /* empty transactions */ |
| 584 | && state != SQLENG_FNSH_ABORTED_STATE /* aborted transactions */) { |
| 585 | logmsg(LOGMSG_ERROR, "%p ctrl engine has wrong state %d %llx %p\n", clnt, state, clnt->osql.rqid, |
| 586 | (void *)pthread_self()); |
| 587 | if (clnt->sql) |
| 588 | logmsg(LOGMSG_ERROR, "%p sql is \"%s\"\n", clnt, clnt->sql); |
| 589 | } |
| 590 | |
| 591 | /* TODO: once Dr. Hipp fixes the plan, this should be moved |
| 592 | to sqlite3BtreeCloseCursor */ |
| 593 | clearClientSideRow(clnt); |
| 594 | |
| 595 | fdb_clear_sqlclntstate(clnt); |
| 596 | |
| 597 | if (osql->tablename) |
| 598 | free(osql->tablename); |
| 599 | if (!osql_shadtbl_empty(clnt)) |
| 600 | osql_shadtbl_close(clnt); |
| 601 | if (osql->history) |
| 602 | srs_tran_destroy(clnt); |
| 603 | if (clnt->saved_errstr) { |
| 604 | free(clnt->saved_errstr); |
| 605 | clnt->saved_errstr = NULL; |
| 606 | } |
| 607 | |
| 608 | if (clnt->dbtran.shadow_tran) { |
| 609 | /* for some reason the clnt contains an unfinished |
| 610 | shadow transaction, that could have allocated structures |
| 611 | and temp tables |
| 612 | Abort here to avoid leaking them */ |
| 613 | logmsg(LOGMSG_ERROR, "shadow_tran not cleared, aborting\n"); |
| 614 | rc = trans_abort_shadow((void **)&clnt->dbtran.shadow_tran, &bdberr); |
| 615 | if (rc != 0) { |
| 616 | logmsg(LOGMSG_ERROR, "%s:%d: abort shadow failed rc=%d bdberr=%d\n", |
| 617 | __FILE__, __LINE__, rc, bdberr); |
| 618 | } |
| 619 | } |
| 620 | |
| 621 | if (osql_chkboard_sqlsession_exists(clnt->osql.rqid, clnt->osql.uuid)) { |
| 622 | uuidstr_t us; |
| 623 | logmsg(LOGMSG_ERROR, "%p [%llx %s] in USE! %p\n", clnt, clnt->osql.rqid, comdb2uuidstr(clnt->osql.uuid, us), |
| 624 | (void *)pthread_self()); |
| 625 | /* XXX temporary debug code. */ |
| 626 | if (gbl_abort_on_clear_inuse_rqid) |
| 627 | abort(); |
| 628 | } |
no test coverage detected