Int2 Blast_RunSearch(SeqLoc* query_seqloc, Blast_PsiCheckpointLoc * psi_checkpoint, const BlastSeqSrc* seq_src, SeqLoc* masking_locs, const SBlastOptions* options, BlastTabularFormatData* tf_data, BlastHSPResults **results, SeqLoc** filter_out, Blast_SummaryReturn* extra_returns) { Int2 status = 0; BLAST_SequenceBlk *query = NULL; BlastQueryInfo* query_info = NULL; double scale_factor = 1.0; BlastSeqLoc* lookup_segments = NULL; BlastScoreBlk* sbp = NULL; LookupTableWrap* lookup_wrap = NULL; BlastMaskLoc* mask_loc = NULL; BlastHSPStream* hsp_stream = NULL; const EBlastProgramType kProgram = options->program; const Boolean kRpsBlast = (kProgram == eBlastTypeRpsBlast || kProgram == eBlastTypeRpsTblastn); BlastRPSInfo* rps_info = NULL; Nlm_MemMapPtr rps_mmap = NULL; Nlm_MemMapPtr rps_pssm_mmap = NULL; const QuerySetUpOptions* query_options = options->query_options; const LookupTableOptions* lookup_options = options->lookup_options; const BlastScoringOptions* score_options = options->score_options; const BlastHitSavingOptions* hit_options = options->hit_options; SBlastOptions* rps_options = NULL; const Boolean kPhiBlast = Blast_ProgramIsPhiBlast(kProgram); const Uint1 kDeallocateMe = 253; Blast_Message *core_msg = NULL; if (!query_seqloc || !seq_src || !options || !extra_returns) return -1; if ((status = BLAST_ValidateOptions(kProgram, options->ext_options, score_options, lookup_options, options->word_options, hit_options, &core_msg)) != 0) { extra_returns->error = Blast_MessageToSBlastMessage(core_msg, NULL, NULL, options->believe_query); core_msg = Blast_MessageFree(core_msg); return status; } if (options->program == eBlastTypeBlastn) { SeqLoc* dust_mask = NULL; /* Dust mask locations */ Blast_FindDustSeqLoc(query_seqloc, options, &dust_mask); /* Combine dust mask with lower case mask The dust mask will be deallocated by the end of this function though as it's copied in BLAST_MainSetUp Not deallocating it will result in a memory leak if masking_locs was NULL at the start of this function */ if (dust_mask) { SeqLoc* dust_mask_var = dust_mask; while (dust_mask_var) { dust_mask_var->choice = kDeallocateMe; dust_mask_var = dust_mask_var->next; } ValNodeLink(&masking_locs, dust_mask); } } if (kRpsBlast) { if ((status = s_RPSExtraStructsSetUp(seq_src, options, &rps_options, &rps_info, &rps_mmap, &rps_pssm_mmap, &scale_factor, extra_returns))) return status; score_options = rps_options->score_options; hit_options = rps_options->hit_options; options = rps_options; /* This will not change the caller's pointer. */ } if ((status = BLAST_SetUpQuery(kProgram, query_seqloc, query_options, masking_locs, &query_info, &query))) { SBlastMessageWrite(&extra_returns->error, SEV_ERROR, "BLAST_SetUpQuery returned non-zero status\n", NULL, FALSE); return status; } status = BLAST_MainSetUp(kProgram, query_options, score_options, query, query_info, scale_factor, &lookup_segments, &mask_loc, &sbp, &core_msg, s_BlastFindMatrixPath); if (core_msg) { extra_returns->error = Blast_MessageToSBlastMessage(core_msg, query_seqloc, query_info, options->believe_query); core_msg = Blast_MessageFree(core_msg); } if (status) return status; if (psi_checkpoint) { core_msg = NULL; status = s_SetupScoreBlkPssmFromChkpt(sbp, query, psi_checkpoint, &core_msg); if (core_msg) { extra_returns->error = Blast_MessageToSBlastMessage(core_msg, query_seqloc, query_info, options->believe_query); core_msg = Blast_MessageFree(core_msg); } if (status) return status; } if (filter_out) { *filter_out = BlastMaskLocToSeqLoc(kProgram, mask_loc, query_seqloc); } /* Mask locations in BlastMaskLoc form are no longer needed. */ BlastMaskLocFree(mask_loc); if (masking_locs) { SeqLocPtr slp_var = masking_locs; SeqLocPtr last = NULL; while (slp_var) { if (slp_var->choice == kDeallocateMe) { if (last == NULL) { masking_locs = slp_var->next; slp_var->next = NULL; Blast_ValNodeMaskListFree(slp_var); slp_var = masking_locs; } else { last->next = slp_var->next; slp_var->next = NULL; Blast_ValNodeMaskListFree(slp_var); slp_var = last->next; } } else { last = slp_var; slp_var = slp_var->next; } } } status = LookupTableWrapInit(query, lookup_options, query_options, lookup_segments, sbp, &lookup_wrap, rps_info, &core_msg); if (core_msg) { extra_returns->error = Blast_MessageToSBlastMessage(core_msg, query_seqloc, query_info, options->believe_query); core_msg = Blast_MessageFree(core_msg); } if (status) return status; /* For PHI BLAST, save information about pattern occurrences in query in the BlastQueryInfo structure. */ if (kPhiBlast) { SPHIPatternSearchBlk* pattern_blk = (SPHIPatternSearchBlk*) lookup_wrap->lut; Blast_SetPHIPatternInfo(kProgram, pattern_blk, query, lookup_segments, query_info, &core_msg); if (core_msg) { extra_returns->error = Blast_MessageToSBlastMessage(core_msg, query_seqloc, query_info, options->believe_query); core_msg = Blast_MessageFree(core_msg); } } /* Only need for the setup of lookup table. */ lookup_segments = BlastSeqLocFree(lookup_segments); if ((status = s_BlastHSPStreamSetUp(query, query_info, seq_src, options, sbp, tf_data, &hsp_stream, extra_returns))) return status; if ((status = s_BlastThreadManager(query, query_info, seq_src, options, lookup_wrap, sbp, hsp_stream, rps_info, tf_data, results, extra_returns))) return status; lookup_wrap = LookupTableWrapFree(lookup_wrap); query = BlastSequenceBlkFree(query); query_info = BlastQueryInfoFree(query_info); BlastScoreBlkFree(sbp); if (kRpsBlast) s_RPSExtraStructsFree(rps_info, rps_mmap, rps_pssm_mmap, rps_options); return status; }
void Blast_PerrorEx(Blast_Message* *msg, Int2 error_code, const char* file_name, int lineno, int context) { Blast_Message* new_msg = (Blast_Message*) calloc(1, sizeof(Blast_Message)); ASSERT(msg); switch (error_code) { case BLASTERR_IDEALSTATPARAMCALC: new_msg->message = strdup("Failed to calculate ideal Karlin-Altschul " "parameters"); new_msg->severity = eBlastSevError; new_msg->context = context; break; case BLASTERR_REDOALIGNMENTCORE_NOTSUPPORTED: new_msg->message = strdup("Composition based statistics or " "Smith-Waterman not supported for your " "program type"); new_msg->severity = eBlastSevError; new_msg->context = context; break; case BLASTERR_INTERRUPTED: new_msg->message = strdup("BLAST search interrupted at user's request"); new_msg->severity = eBlastSevInfo; new_msg->context = context; break; case BLASTERR_NOVALIDKARLINALTSCHUL: new_msg->message = strdup("Warning: Could not calculate ungapped Karlin-Altschul " "parameters due to an invalid query sequence or its translation. " "Please verify the query sequence(s) and/or filtering options"); new_msg->severity = eBlastSevError; new_msg->context = context; break; /* Fatal errors */ case BLASTERR_MEMORY: /** @todo Ideally this message would be more informative (the error code * already conveys this information) so that this string can be * displayed to the end user via the CATCH_ALL macro. If this string is * ever changed, please update that macro accordingly (ideally this * error code would be caught and would lead to a CBlastSystemException * being thrown with the eOutOfMemory error code) */ new_msg->message = strdup("Out of memory"); new_msg->severity = eBlastSevFatal; new_msg->context = context; break; case BLASTERR_INVALIDPARAM: new_msg->message = strdup("Invalid argument to function"); new_msg->severity = eBlastSevFatal; new_msg->context = context; break; case BLASTERR_INVALIDQUERIES: new_msg->message = strdup("search cannot proceed due to errors in all " "contexts/frames of query sequences"); new_msg->severity = eBlastSevFatal; new_msg->context = context; break; case BLASTERR_SEQSRC: new_msg->message = strdup("search cannot proceed due to errors " "retrieving sequences from databases"); new_msg->severity = eBlastSevFatal; new_msg->context = context; break; /* No error, just free the structure */ case 0: new_msg = Blast_MessageFree(new_msg); break; /* Unknown error */ default: { char buf[512]; snprintf(buf, sizeof(buf) - 1, "Unknown error code %d", error_code); new_msg->message = strdup(buf); new_msg->severity = eBlastSevError; new_msg->context = context; } break; } if (file_name && lineno > 0) { new_msg->origin = SMessageOriginNew(file_name, (unsigned int) lineno); } if (*msg) { Blast_Message* var = *msg; while (var->next) var = var->next; var->next = new_msg; } else { *msg = new_msg; } return; }