Exemple #1
0
static rc_t OpenFile(KFile const **kf, char const path[], char const base[])
{
    char fname[4096];
    rc_t rc = PathWithBasePath(fname, sizeof(fname), path, base);
    
    if (rc == 0) {
        KDirectory *dir;
        
        rc = KDirectoryNativeDir(&dir);
        if (rc == 0) {
            rc = KDirectoryOpenFileRead(dir, kf, fname);
            KDirectoryRelease(dir);
        }
    }
    return rc;
}
Exemple #2
0
rc_t CC KMain (int argc, char * argv[])
{
    Args * args;
    rc_t rc;
    unsigned n_aligned = 0;
    unsigned n_unalgnd = 0;
    char *aligned[256];
    char *unalgnd[256];
    char *name_buffer = NULL;
    unsigned next_name = 0;
    unsigned nbsz = 0;
    char const *value;
    char *dummy;
    const XMLLogger* xml_logger = NULL;
    
    memset(&G, 0, sizeof(G));
    
    G.mode = mode_Archive;
    G.maxSeqLen = TableWriterRefSeq_MAX_SEQ_LEN;
    G.schemaPath = SCHEMAFILE;
    G.omit_aligned_reads = true;
    G.omit_reference_reads = true;
    G.minMapQual = 0; /* accept all */
    G.tmpfs = "/tmp";
#if _ARCH_BITS == 32
    G.cache_size = ( size_t ) 1 << 30;
#else
    G.cache_size = ( size_t ) 10 << 30;
#endif
    G.maxErrCount = 1000;
    G.minMatchCount = 10;
    
    set_pid();

    rc = ArgsMakeAndHandle (&args, argc, argv, 2, Options,
                            sizeof Options / sizeof (OptDef), XMLLogger_Args, XMLLogger_ArgsQty);

    while (rc == 0) {
        uint32_t pcount;

        if( (rc = XMLLogger_Make(&xml_logger, NULL, args)) != 0 ) {
            break;
        }
        rc = ArgsOptionCount(args, option_only_verify, &pcount);
        if (rc)
            break;
        G.onlyVerifyReferences = (pcount > 0);
        
        rc = ArgsOptionCount(args, option_no_verify, &pcount);
        if (rc)
            break;
        G.noVerifyReferences = (pcount > 0);
        
        rc = ArgsOptionCount(args, option_use_qual, &pcount);
        if (rc)
            break;
        G.useQUAL = (pcount > 0);
        
        rc = ArgsOptionCount(args, option_ref_config, &pcount);
        if (rc)
            break;
        G.limit2config = (pcount > 0);
        
        rc = ArgsOptionCount(args, OPTION_REF_FILE, &pcount);
        if (rc)
            break;
        G.refFiles = calloc(pcount + 1, sizeof(*(G.refFiles)));
        if( !G.refFiles ) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcMemory, rcExhausted);
            break;
        }
        while(pcount-- > 0) {
            rc = ArgsOptionValue(args, OPTION_REF_FILE, pcount, &G.refFiles[pcount]);
            if (rc)
                break;
        }

        rc = ArgsOptionCount (args, OPTION_TMPFS, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_TMPFS, 0, &G.tmpfs);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_INPUT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_INPUT, 0, &G.inpath);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single input parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, option_ref_filter, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, option_ref_filter, 0, &G.refFilter);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_CONFIG, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_CONFIG, 0, &G.refXRefPath);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single input parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_OUTPUT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_OUTPUT, 0, &G.outpath);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single output parameter required\n"));
            MiniUsage (args);
            break;
        }
        else if (!G.onlyVerifyReferences) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcInsufficient);
            OUTMSG (("Output parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_MINMAPQ, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MINMAPQ, 0, &value);
            if (rc)
                break;
            G.minMapQual = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_QCOMP, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_QCOMP, 0, &G.QualQuantizer);
            if (rc)
                break;
        }
        
        rc = ArgsOptionCount (args, option_edit_aligned_qual, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, option_edit_aligned_qual, 0, &value);
            if (rc)
                break;
            G.alignedQualValue = strtoul(value, &dummy, 0);
            if (G.alignedQualValue == 0) {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                OUTMSG (("edit-aligned-qual: bad value\n"));
                MiniUsage (args);
                break;
            }
            G.editAlignedQual = true;
        }
        
        rc = ArgsOptionCount (args, OPTION_CACHE_SIZE, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_CACHE_SIZE, 0, &value);
            if (rc)
                break;
            G.cache_size = strtoul(value, &dummy, 0) * 1024UL * 1024UL;
            if (G.cache_size == 0) {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                OUTMSG (("cache-size: bad value\n"));
                MiniUsage (args);
                break;
            }
        }
        
        rc = ArgsOptionCount (args, OPTION_MAX_WARN_DUP_FLAG, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_WARN_DUP_FLAG, 0, &value);
            if (rc)
                break;
            G.maxWarnCount_DupConflict = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, option_unsorted, &pcount);
        if (rc)
            break;
        G.expectUnsorted = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_MAX_REC_COUNT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_REC_COUNT, 0, &value);
            if (rc)
                break;
            G.maxAlignCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_MAX_ERR_COUNT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_ERR_COUNT, 0, &value);
            if (rc)
                break;
            G.maxErrCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_MIN_MATCH, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MIN_MATCH, 0, &value);
            if (rc)
                break;
            G.minMatchCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_ACCEPT_DUP, &pcount);
        if (rc)
            break;
        G.acceptBadDups = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_ACCEPT_NOMATCH, &pcount);
        if (rc)
            break;
        G.acceptNoMatch = pcount > 0;
        
        rc = ArgsOptionCount (args, option_keep_mismatch_qual, &pcount);
        if (rc)
            break;
        G.keepMismatchQual = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_NO_CS, &pcount);
        if (rc)
            break;
        G.noColorSpace = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_NO_SECONDARY, &pcount);
        if (rc)
            break;
        G.noSecondary = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_TI, &pcount);
        if (rc)
            break;
        G.hasTI = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_ACCEPT_HARD_CLIP, &pcount);
        if (rc)
            break;
        G.acceptHardClip = pcount > 0;
        
        rc = ArgsOptionCount (args, OPTION_NOMATCH_LOG, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            KDirectory *dir;
            
            rc = ArgsOptionValue (args, OPTION_NOMATCH_LOG, 0, &value);
            if (rc) break;
            rc = KDirectoryNativeDir(&dir);
            if (rc) break;
            rc = KDirectoryCreateFile(dir, &G.noMatchLog, 0, 0664, kcmInit, value);
            KDirectoryRelease(dir);
            if (rc) break;
        }
        
        rc = ArgsOptionCount (args, OPTION_HEADER, &pcount);
        if (rc)
            break;
        if (pcount == 1) {
            rc = ArgsOptionValue (args, OPTION_HEADER, 0, &value);
            if (rc) break;
            rc = LoadHeader(&G.headerText, value, G.inpath);
            if (rc) break;
        }
        
        rc = ArgsParamCount (args, &pcount);
        if (rc) break;
        if (pcount == 0)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcInsufficient);
            MiniUsage (args);
            break;
        }
        else if (pcount > sizeof(aligned)/sizeof(aligned[0])) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            (void)PLOGERR(klogErr, (klogErr, rc, "$(count) input files is too many, $(max) is the limit",
                        "count=%u,max=%u", (unsigned)pcount, (unsigned)(sizeof(aligned)/sizeof(aligned[0]))));
            break;
        }
        else {
            unsigned need = G.inpath ? (strlen(G.inpath) + 1) * pcount : 0;
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsParamValue(args, i, &value);
                if (rc) break;
                need += strlen(value) + 1;
            }
            nbsz = need;
        }
        
        rc = ArgsOptionCount (args, OPTION_UNALIGNED, &pcount);
        if (rc)
            break;
        if (pcount > 0)
        {
            unsigned need = G.inpath ? (strlen(G.inpath) + 1) * pcount : 0;
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsOptionValue(args, OPTION_UNALIGNED, i, &value);
                if (rc) break;
                need += strlen(value) + 1;
            }
            if (rc) break;
            nbsz += need;
        }
        
        name_buffer = malloc(nbsz);
        if (name_buffer == NULL) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcMemory, rcExhausted);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_UNALIGNED, &pcount);
        if (rc == 0) {
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsOptionValue(args, OPTION_UNALIGNED, i, &value);
                if (rc) break;
                
                unalgnd[n_unalgnd++] = name_buffer + next_name;
                rc = PathWithBasePath(name_buffer + next_name, nbsz - next_name, value, G.inpath);
                if (rc) break;
                next_name += strlen(name_buffer + next_name) + 1;
            }
            if (rc) break;
        }
        else
            break;
        
        rc = ArgsParamCount (args, &pcount);
        if (rc == 0) {
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsParamValue(args, i, &value);
                if (rc) break;
                
                aligned[n_aligned++] = name_buffer + next_name;
                rc = PathWithBasePath(name_buffer + next_name, nbsz - next_name, value, G.inpath);
                if (rc) break;
                next_name += strlen(name_buffer + next_name) + 1;
            }
        }
        else
            break;
        
        rc = run(argv[0], n_aligned, (char const **)aligned, n_unalgnd, (char const **)unalgnd);
        break;
    }
    free(name_buffer);
    free((void *)G.headerText);
    free(G.refFiles);

    value = G.outpath ? strrchr(G.outpath, '/') : "/???";
    if( value == NULL ) {
        value = G.outpath;
    } else {
        value++;
    }
    if (rc) {
        (void)PLOGERR(klogErr, (klogErr, rc, "load failed",
                "severity=total,status=failure,accession=%s,errors=%u", value, G.errCount));
    } else {
        (void)PLOGMSG(klogInfo, (klogInfo, "loaded",
                "severity=total,status=success,accession=%s,errors=%u", value, G.errCount));
    }
    ArgsWhack(args);
    XMLLogger_Release(xml_logger);
    return rc;
}
rc_t CC KMain (int argc, char * argv[])
{
    Args * args;
    rc_t rc;
    char *files[256];
    int8_t defaultReadNumbers[256];
    char *name_buffer = NULL;
    size_t next_name = 0;
    size_t nbsz = 0;
    char const *value;
    char *dummy;
    const XMLLogger* xml_logger = NULL;
    enum FASTQQualityFormat qualityFormat;
    bool ignoreSpotGroups;
    
    memset(&G, 0, sizeof(G));
    
    G.mode = mode_Archive;
    G.maxSeqLen = TableWriterRefSeq_MAX_SEQ_LEN;
    G.schemaPath = SCHEMAFILE;
    G.omit_aligned_reads = true;
    G.omit_reference_reads = true;
    G.minMapQual = 0; /* accept all */
    G.tmpfs = "/tmp";
#if _ARCH_BITS == 32
    G.cache_size = ( size_t ) 1 << 30;
#else
    G.cache_size = ( size_t ) 10 << 30;
#endif
    G.maxErrCount = 1000;
    G.maxErrPct = 5;
    G.acceptNoMatch = true; 
    G.minMatchCount = 0; 
    G.QualQuantizer="0";
    
    set_pid();

    rc = ArgsMakeAndHandle (&args, argc, argv, 2, Options,
                            sizeof Options / sizeof (OptDef), XMLLogger_Args, XMLLogger_ArgsQty);

    while (rc == 0) {
        uint32_t pcount;

        if( (rc = XMLLogger_Make(&xml_logger, NULL, args)) != 0 ) {
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_TMPFS, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_TMPFS, 0, (const void **)&G.tmpfs);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_OUTPUT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_OUTPUT, 0, (const void **)&G.outpath);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single output parameter required\n"));
            MiniUsage (args);
            break;
        }
        else {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcInsufficient);
            OUTMSG (("Output parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_QCOMP, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_QCOMP, 0, (const void **)&G.QualQuantizer);
            if (rc)
                break;
        }
        
        rc = ArgsOptionCount (args, OPTION_CACHE_SIZE, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_CACHE_SIZE, 0, (const void **)&value);
            if (rc)
                break;
            G.cache_size = strtoul(value, &dummy, 0) * 1024UL * 1024UL;
            if (G.cache_size == 0  || G.cache_size == ULONG_MAX) {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                OUTMSG (("cache-size: bad value\n"));
                MiniUsage (args);
                break;
            }
        }
        
        G.expectUnsorted = true;
        
        rc = ArgsOptionCount (args, OPTION_MAX_REC_COUNT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_REC_COUNT, 0, (const void **)&value);
            if (rc)
                break;
            G.maxAlignCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_MAX_ERR_COUNT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_ERR_COUNT, 0, (const void **)&value);
            if (rc)
                break;
            G.maxErrCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_MAX_ERR_PCT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_ERR_PCT, 0, (const void **)&value);
            if (rc)
                break;
            G.maxErrPct = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_PLATFORM, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_PLATFORM, 0, (const void **)&value);
            if (rc)
                break;
            G.platform = PlatformToId(value);
            if (G.platform == SRA_PLATFORM_UNDEFINED)
            {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                (void)PLOGERR(klogErr, (klogErr, rc, "Invalid platform $(v)",
                            "v=%s", value));
                break;
            }
        }
        else
            G.platform = SRA_PLATFORM_UNDEFINED;

        rc = ArgsOptionCount (args, OPTION_QUALITY, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_QUALITY, 0, (const void **)&value);
            if (rc)
                break;
            if (strcmp(value, "PHRED_33") == 0)
                qualityFormat = FASTQphred33;
            else if (strcmp(value, "PHRED_64") == 0)
                qualityFormat = FASTQphred64;
            else if (strcmp(value, "LOGODDS") == 0)
                qualityFormat = FASTQlogodds;
            else
            {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                (void)PLOGERR(klogErr, (klogErr, rc, "Invalid quality encoding $(v)",
                            "v=%s", value));
                break;
            }
        }
        else
            qualityFormat = 0;
            
        rc = ArgsOptionCount (args, OPTION_IGNORE_ILLUMINA_TAGS, &pcount);
        if (rc)
            break;
        ignoreSpotGroups = pcount > 0;
        
        rc = ArgsParamCount (args, &pcount);
        if (rc) break;
        if (pcount == 0)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcInsufficient);
            MiniUsage (args);
            break;
        }
        else if (pcount > sizeof(files)/sizeof(files[0])) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            (void)PLOGERR(klogErr, (klogErr, rc, "$(count) input files is too many, $(max) is the limit",
                        "count=%u,max=%u", (unsigned)pcount, (unsigned)(sizeof(files)/sizeof(files[0]))));
            break;
        }
        else {
            size_t need = G.inpath ? (strlen(G.inpath) + 1) * pcount : 0;
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsParamValue(args, i, (const void **)&value);
                if (rc) break;
                need += strlen(value) + 1;
            }
            nbsz = need;
        }
        
        name_buffer = malloc(nbsz);
        if (name_buffer == NULL) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcMemory, rcExhausted);
            break;
        }
        
        rc = ArgsParamCount (args, &pcount);
        if (rc == 0) {
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsParamValue(args, i, (const void **)&value);
                if (rc) break;

                defaultReadNumbers[i] = 0;
                files[i] = name_buffer + next_name;
                rc = PathWithBasePath(name_buffer + next_name, nbsz - next_name, value, G.inpath);
                if (rc) break;
                next_name += strlen(name_buffer + next_name) + 1;
            }
        }
        else
            break;
        
        rc = run(argv[0], &G, pcount, (char const **)files, qualityFormat, defaultReadNumbers, ignoreSpotGroups);
        break;
    }
    free(name_buffer);

    value = G.outpath ? strrchr(G.outpath, '/') : "/???";
    if( value == NULL ) {
        value = G.outpath;
    } else {
        value++;
    }
    if (rc) {
        (void)PLOGERR(klogErr, (klogErr, rc, "load failed",
                "severity=total,status=failure,accession=%s,errors=%u", value, G.errCount));
    } else {
        (void)PLOGMSG(klogInfo, (klogInfo, "loaded",
                "severity=total,status=success,accession=%s,errors=%u", value, G.errCount));
    }
    ArgsWhack(args);
    XMLLogger_Release(xml_logger);
    return rc;
}
Exemple #4
0
static rc_t main_1(int argc, char *argv[], bool const continuing, unsigned const load)
{
    Args *args;
    rc_t rc;
    unsigned n_aligned = 0;
    unsigned n_unalgnd = 0;
    char *aligned[256];
    char *unalgnd[256];
    char *name_buffer = NULL;
    unsigned next_name = 0;
    unsigned nbsz = 0;
    char const *value;
    char *dummy;

    rc = ArgsMakeAndHandle (&args, argc, argv, 1, Options, sizeof(Options)/sizeof(Options[0]));
    while (rc == 0) {
        uint32_t pcount;

        rc = ArgsOptionCount(args, option_only_verify, &pcount);
        if (rc)
            break;
        G.onlyVerifyReferences |= (pcount > 0);
        
        rc = ArgsOptionCount(args, option_no_verify, &pcount);
        if (rc)
            break;
        G.noVerifyReferences |= (pcount > 0);
        
        rc = ArgsOptionCount(args, option_use_qual, &pcount);
        if (rc)
            break;
        G.useQUAL |= (pcount > 0);
        
        rc = ArgsOptionCount(args, option_ref_config, &pcount);
        if (rc)
            break;
        G.limit2config |= (pcount > 0);
        
        rc = ArgsOptionCount(args, OPTION_REF_FILE, &pcount);
        if (rc)
            break;
        if (pcount && G.refFiles) {
            int i;

            for (i = 0; G.refFiles[i]; ++i)
                free((void *)G.refFiles[i]);
            free((void *)G.refFiles);
        }
        G.refFiles = calloc(pcount + 1, sizeof(*(G.refFiles)));
        if (!G.refFiles) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcMemory, rcExhausted);
            break;
        }
        while(pcount-- > 0) {
            rc = getArgValue(args, OPTION_REF_FILE, pcount, &G.refFiles[pcount]);
            if (rc)
                break;
        }

        rc = ArgsOptionCount (args, OPTION_TMPFS, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = getArgValue(args, OPTION_TMPFS, 0, &G.tmpfs);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_INPUT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = getArgValue(args, OPTION_INPUT, 0, &G.inpath);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single input parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, option_ref_filter, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = getArgValue(args, option_ref_filter, 0, &G.refFilter);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_CONFIG, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = getArgValue(args, OPTION_CONFIG, 0, &G.refXRefPath);
            if (rc)
                break;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single input parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_OUTPUT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = getArgValue(args, OPTION_OUTPUT, 0, &G.outpath);
            if (rc)
                break;
            if (load == 0) {
                G.firstOut = strdup(G.outpath);
            }
            value = strrchr(G.outpath, '/');
            G.outname = value ? (value + 1) : G.outpath;
        }
        else if (pcount > 1)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            OUTMSG (("Single output parameter required\n"));
            MiniUsage (args);
            break;
        }
        else if (!G.onlyVerifyReferences) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcInsufficient);
            OUTMSG (("Output parameter required\n"));
            MiniUsage (args);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_MINMAPQ, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue(args, OPTION_MINMAPQ, 0, (const void **)&value);
            if (rc)
                break;
            G.minMapQual = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_QCOMP, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = getArgValue(args, OPTION_QCOMP, 0, &G.QualQuantizer);
            if (rc)
                break;
        }

        rc = ArgsOptionCount (args, option_edit_aligned_qual, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, option_edit_aligned_qual, 0, (const void **)&value);
            if (rc)
                break;
            G.alignedQualValue = strtoul(value, &dummy, 0);
            if (G.alignedQualValue == 0) {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                OUTMSG (("edit-aligned-qual: bad value\n"));
                MiniUsage (args);
                break;
            }
            G.editAlignedQual = true;
        }
        
        rc = ArgsOptionCount (args, OPTION_CACHE_SIZE, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_CACHE_SIZE, 0, (const void **)&value);
            if (rc)
                break;
            G.cache_size = strtoul(value, &dummy, 0) * 1024UL * 1024UL;
            if (G.cache_size == 0) {
                rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcIncorrect);
                OUTMSG (("cache-size: bad value\n"));
                MiniUsage (args);
                break;
            }
        }
        
        rc = ArgsOptionCount (args, OPTION_MAX_WARN_DUP_FLAG, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_WARN_DUP_FLAG, 0, (const void **)&value);
            if (rc)
                break;
            G.maxWarnCount_DupConflict = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, option_unsorted, &pcount);
        if (rc)
            break;
        G.expectUnsorted |= (pcount > 0);
        
        rc = ArgsOptionCount (args, option_sorted, &pcount);
        if (rc)
            break;
        G.requireSorted |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_MAX_REC_COUNT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_REC_COUNT, 0, (const void **)&value);
            if (rc)
                break;
            G.maxAlignCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_MAX_ERR_COUNT, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MAX_ERR_COUNT, 0, (const void **)&value);
            if (rc)
                break;
            G.maxErrCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_MIN_MATCH, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            rc = ArgsOptionValue (args, OPTION_MIN_MATCH, 0, (const void **)&value);
            if (rc)
                break;
            G.minMatchCount = strtoul(value, &dummy, 0);
        }
        
        rc = ArgsOptionCount (args, OPTION_ACCEPT_DUP, &pcount);
        if (rc)
            break;
        G.acceptBadDups |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_ACCEPT_NOMATCH, &pcount);
        if (rc)
            break;
        G.acceptNoMatch |= (pcount > 0);
        
        rc = ArgsOptionCount (args, option_keep_mismatch_qual, &pcount);
        if (rc)
            break;
        G.keepMismatchQual |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_NO_CS, &pcount);
        if (rc)
            break;
        G.noColorSpace |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_NO_SECONDARY, &pcount);
        if (rc)
            break;
        G.noSecondary |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_TI, &pcount);
        if (rc)
            break;
        G.hasTI |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_ACCEPT_HARD_CLIP, &pcount);
        if (rc)
            break;
        G.acceptHardClip |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_ALLOW_MULTI_MAP, &pcount);
        if (rc)
            break;
        G.allowMultiMapping |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_ALLOW_SECONDARY, &pcount);
        if (rc)
            break;
        G.assembleWithSecondary |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_DEFER_SECONDARY, &pcount);
        if (rc)
            break;
        G.deferSecondary |= (pcount > 0);
        
        rc = ArgsOptionCount (args, OPTION_NOMATCH_LOG, &pcount);
        if (rc)
            break;
        if (pcount == 1)
        {
            KDirectory *dir;
            
            rc = ArgsOptionValue (args, OPTION_NOMATCH_LOG, 0, (const void **)&value);
            if (rc) break;
            rc = KDirectoryNativeDir(&dir);
            if (rc) break;
            rc = KDirectoryCreateFile(dir, &G.noMatchLog, 0, 0664, kcmInit, "%s", value);
            KDirectoryRelease(dir);
            if (rc) break;
        }
        
        rc = ArgsOptionCount (args, OPTION_HEADER, &pcount);
        if (rc)
            break;
        if (pcount == 1) {
            rc = ArgsOptionValue (args, OPTION_HEADER, 0, (const void **)&value);
            if (rc) break;
            free((void *)G.headerText);
            rc = LoadHeader(&G.headerText, value, G.inpath);
            if (rc) break;
        }
        
        rc = ArgsParamCount (args, &pcount);
        if (rc) break;
        if (pcount == 0)
        {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcInsufficient);
            MiniUsage (args);
            break;
        }
        else if (pcount > sizeof(aligned)/sizeof(aligned[0])) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcParam, rcExcessive);
            (void)PLOGERR(klogErr, (klogErr, rc, "$(count) input files is too many, $(max) is the limit",
                        "count=%u,max=%u", (unsigned)pcount, (unsigned)(sizeof(aligned)/sizeof(aligned[0]))));
            break;
        }
        else {
            unsigned need = G.inpath ? (strlen(G.inpath) + 1) * pcount : 0;
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsParamValue(args, i, (const void **)&value);
                if (rc) break;
                need += strlen(value) + 1;
            }
            nbsz = need;
        }
        
        rc = ArgsOptionCount (args, OPTION_UNALIGNED, &pcount);
        if (rc)
            break;
        if (pcount > 0)
        {
            unsigned need = G.inpath ? (strlen(G.inpath) + 1) * pcount : 0;
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsOptionValue(args, OPTION_UNALIGNED, i, (const void **)&value);
                if (rc) break;
                need += strlen(value) + 1;
            }
            if (rc) break;
            nbsz += need;
        }
        
        name_buffer = malloc(nbsz);
        if (name_buffer == NULL) {
            rc = RC(rcApp, rcArgv, rcAccessing, rcMemory, rcExhausted);
            break;
        }
        
        rc = ArgsOptionCount (args, OPTION_UNALIGNED, &pcount);
        if (rc == 0) {
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsOptionValue(args, OPTION_UNALIGNED, i, (const void **)&value);
                if (rc) break;
                
                unalgnd[n_unalgnd++] = name_buffer + next_name;
                rc = PathWithBasePath(name_buffer + next_name, nbsz - next_name, value, G.inpath);
                if (rc) break;
                next_name += strlen(name_buffer + next_name) + 1;
            }
            if (rc) break;
        }
        else
            break;
        
        rc = ArgsParamCount (args, &pcount);
        if (rc == 0) {
            unsigned i;
            
            for (i = 0; i < pcount; ++i) {
                rc = ArgsParamValue(args, i, (const void **)&value);
                if (rc) break;
                
                aligned[n_aligned++] = name_buffer + next_name;
                rc = PathWithBasePath(name_buffer + next_name, nbsz - next_name, value, G.inpath);
                if (rc) break;
                next_name += strlen(name_buffer + next_name) + 1;
            }
        }
        else
            break;

        rc = run(argv[0], n_aligned, (char const **)aligned, n_unalgnd, (char const **)unalgnd, continuing);
        break;
    }
    free(name_buffer);

    if (rc) {
        (void)PLOGERR(klogErr, (klogErr, rc, "load failed",
                "severity=total,status=failure,accession=%s,errors=%u", G.outname, G.errCount));
    } else {
        (void)PLOGMSG(klogInfo, (klogInfo, "loaded",
                "severity=total,status=success,accession=%s,errors=%u", G.outname, G.errCount));
    }
    ArgsWhack(args);
    return rc;
}