void findClosestServer(char **pDb, char **pOrg)
/* If db doesn't have a blat server, look for the closest db (or org) that has one,
 * as hgPcr does. */
{
char *db = *pDb, *org = *pOrg;
struct sqlConnection *conn = hConnectCentral();
char query[256];
safef(query, sizeof(query), "select db from blatServers where db = '%s'", db);
if (!sqlExists(conn, query))
    {
    safef(query, sizeof(query), "select blatServers.db from blatServers,dbDb "
	  "where blatServers.db = dbDb.name and dbDb.genome = '%s'", org);
    char *db = sqlQuickString(conn, query);
    if (db == NULL)
	{
	safef(query, sizeof(query), "select blatServers.db from blatServers,dbDb "
	      "where blatServers.db = dbDb.name order by dbDb.orderKey,dbDb.name desc");
	char *db = sqlQuickString(conn, query);
	if (db == NULL)
	    errAbort("central database tables blatServers and dbDb are disjoint/empty");
	else
	    {
	    *pDb = db;
	    *pOrg = hGenome(db);
	    }
	}
    else
	{
	*pDb = db;
	*pOrg = hGenome(db);
	}
    }
hDisconnectCentral(&conn);
}
Exemple #2
0
static struct serverTable *trackHubServerTable(char *db, boolean isTrans)
/* Find out if database is a track hub with a blat server */
{
char *host, *port;

if (!trackHubGetBlatParams(db, isTrans, &host, &port))
    return NULL;

struct serverTable *st;

AllocVar(st);

st->db = cloneString(db);
st->genome = cloneString(hGenome(db));
st->isTrans = isTrans;
st->host = host; 
st->port = port;
struct trackHubGenome *genome = trackHubGetGenome(db);
st->nibDir = cloneString(genome->twoBitPath);
char *ptr = strrchr(st->nibDir, '/');
// we only want the directory name
if (ptr != NULL)
    *ptr = 0;
return st;
}
Exemple #3
0
static char *getDbForGenome(char *genome, struct cart *cart)
/*
  Function to find the default database for the given Genome.
It looks in the cart first and then, if that database's Genome matches the
passed-in Genome, returns it. If the Genome does not match, it returns the default
database that does match that Genome.

param Genome - The Genome for which to find a database
param cart - The cart to use to first search for a suitable database name
return - The database matching this Genome type
*/
{

char *retDb = cartUsualString(cart, dbCgiName, NULL);

if ((retDb == NULL) || !hDbExists(retDb))
    {
    retDb = hDefaultDb();
    }

/* If genomes don't match, then get the default db for that genome */
if (differentWord(genome, hGenome(retDb)))
    {
    retDb = hDefaultDbForGenome(genome);
    }

return retDb;
}
Exemple #4
0
void printAllAssemblyListHtmlParm(char *db, struct dbDb *dbList,
                            char *dbCgi, bool allowInactive, char *javascript)
/* Prints to stdout the HTML to render a dropdown list containing the list
 * of assemblies for the current genome to choose from.  By default,
 * this includes only active assemblies with a database (with the
 * exception of the default assembly, which will be included even
 * if it isn't active).
 *  param db - The default assembly (the database name) to choose as selected.
 *             If NULL, no default selection.
 *  param allowInactive - if set, print all assemblies for this genome,
 *                        even if they're inactive or have no database
 */
{

char *assemblyList[128];
char *values[128];
int numAssemblies = 0;
struct dbDb *cur = NULL;
char *genome = hGenome(db);
char *selAssembly = NULL;

if (genome == NULL)
#ifdef LOWELAB
    genome = "Pyrococcus furiosus";
#else
    genome = "Human";
#endif
for (cur = dbList; cur != NULL; cur = cur->next)
    {
    /* Only for this genome */
    if (!sameWord(genome, cur->genome))
        continue;

    /* Save a pointer to the current assembly */
    if (sameWord(db, cur->name))
        selAssembly = cur->name;

    if (allowInactive ||
        ((cur->active || sameWord(cur->name, db))
                && (trackHubDatabase(db) || sqlDatabaseExists(cur->name))))
        {
        assemblyList[numAssemblies] = cur->description;
        values[numAssemblies] = cur->name;
        numAssemblies++;
	if (numAssemblies >= ArraySize(assemblyList))
	    internalErr();
        }

    }
cgiMakeDropListFull(dbCgi, assemblyList, values, numAssemblies,
                                selAssembly, javascript);
}
static void getAssemblyInfo(struct cartJson *cj, struct hash *paramHash)
/* Return useful things from dbDb (or track hub) and assembly description html (possibly NULL).
 * If db param is NULL, use db from cart. */
{
char *db = cartJsonOptionalParam(paramHash, "db");
if (db == NULL)
    db = cartString(cj->cart, "db");
jsonWriteString(cj->jw, "db", db);
jsonWriteString(cj->jw, "commonName", hGenome(db));
jsonWriteString(cj->jw, "scientificName", hScientificName(db));
jsonWriteString(cj->jw, "dbLabel", hFreezeDate(db));
//#*** TODO: move jsonStringEscape inside jsonWriteString
jsonWriteString(cj->jw, "assemblyDescription", jsonStringEscape(hAssemblyDescription(db)));
}
Exemple #6
0
static void writeFindPositionInfo(struct jsonWrite *jw, char *db, int taxId, char *hubUrl,
                                  char *position)
/* Write JSON for the info needed to populate the 'Find Position' section. */
{
char *genome = hGenome(db);
if (isEmpty(genome))
    {
    jsonWriteStringf(jw, "error", "No genome for db '%s'", db);
    }
else
    {
    jsonWriteString(jw, "db", db);
    jsonWriteNumber(jw, "taxId", taxId);
    jsonWriteString(jw, "genome", genome);
    struct slPair *dbOptions = NULL;
    char genomeLabel[PATH_LEN*4];
    if (isNotEmpty(hubUrl))
        {
        struct trackHub *hub = hubConnectGetHub(hubUrl);
        if (hub == NULL)
            {
            jsonWriteStringf(jw, "error", "Can't connect to hub at '%s'", hubUrl);
            return;
            }
        struct dbDb *dbDbList = trackHubGetDbDbs(hub->name);
        dbOptions = trackHubDbDbToValueLabel(dbDbList);
        safecpy(genomeLabel, sizeof(genomeLabel), hub->shortLabel);
        jsonWriteString(jw, "hubUrl", hubUrl);
        }
    else
        {
        dbOptions = hGetDbOptionsForGenome(genome);
        safecpy(genomeLabel, sizeof(genomeLabel), genome);
        }
    jsonWriteValueLabelList(jw, "dbOptions", dbOptions);
    jsonWriteString(jw, "genomeLabel", genomeLabel);
    jsonWriteString(jw, "position", position);
    char *suggestTrack = NULL;
    if (! trackHubDatabase(db))
        suggestTrack = assemblyGeneSuggestTrack(db);
    jsonWriteString(jw, "suggestTrack", suggestTrack);
    char *description = maybeGetDescriptionText(db);
    //#*** TODO: move jsonStringEscape inside jsonWriteString
    char *encoded = jsonStringEscape(description);
    jsonWriteString(jw, "description", encoded);
    listAssemblyHubs(jw);
    }
}
Exemple #7
0
void doMiddle(struct cart *theCart)
/* Write header and body of html page. */
{
char *userSeq;
char *db, *organism;
boolean clearUserSeq = cgiBoolean("Clear");

cart = theCart;
dnaUtilOpen();

orgChange = sameOk(cgiOptionalString("changeInfo"),"orgChange");
if (orgChange)
    {
    cgiVarSet("db", hDefaultDbForGenome(cgiOptionalString("org"))); 
    }
getDbAndGenome(cart, &db, &organism, oldVars);
char *oldDb = cloneString(db);
findClosestServer(&db, &organism);

/* Get sequence - from userSeq variable, or if 
 * that is empty from a file. */
if (clearUserSeq)
    {
    cartSetString(cart, "userSeq", "");
    cartSetString(cart, "seqFile", "");
    }
userSeq = cartUsualString(cart, "userSeq", "");
if (isEmpty(userSeq))
    {
    userSeq = cartOptionalString(cart, "seqFile");
    }
if (isEmpty(userSeq) || orgChange)
    {
    cartWebStart(theCart, db, "%s BLAT Search", trackHubSkipHubName(organism));
    if (differentString(oldDb, db))
	printf("<HR><P><EM><B>Note:</B> BLAT search is not available for %s %s; "
	       "defaulting to %s %s</EM></P><HR>\n",
	       hGenome(oldDb), hFreezeDate(oldDb), organism, hFreezeDate(db));
    askForSeq(organism,db);
    cartWebEnd();
    }
else 
    {
    blatSeq(skipLeadingSpaces(userSeq), organism);
    }
}
Exemple #8
0
void redoDbAndOrgIfNoServer(struct pcrServer *serverList, char **pDb, char **pOrg)
/* Check that database and organism are on our serverList.  If not, then update
 * them to first thing that is. */
{
    struct pcrServer *server, *orgServer = NULL;
    char *organism = *pOrg;
    char *db = *pDb;
    boolean gotDb = FALSE;

    /*  Find first server for our organism */
    for (server = serverList; server != NULL; server = server->next)
    {
        if (sameString(server->genome, organism))
        {
            orgServer = server;
            break;
        }
    }

    /* If no server, change our organism to the one of the first server in list. */
    if (orgServer == NULL)
    {
        orgServer = serverList;
        *pOrg = organism = orgServer->genome;
    }

    /* Search for our database. */
    for (server = serverList; server != NULL; server = server->next)
    {
        if (sameString(db, server->db))
        {
            gotDb = TRUE;
            break;
        }
    }

    /* If no server for db, change db. */
    if (!gotDb)
    {
        if (differentString(db, orgServer->db))
            printf("<HR><P><EM><B>Note:</B> In-Silico PCR is not available for %s %s; "
                   "defaulting to %s %s</EM></P><HR>\n",
                   hGenome(db), hFreezeDate(db), organism, hFreezeDate(orgServer->db));
        *pDb = db = orgServer->db;
    }
}
static void getCladeOrgDbPos(struct cartJson *cj, struct hash *paramHash)
/* Get cart's current clade, org, db, position and geneSuggest track. */
{
jsonWriteObjectStart(cj->jw, "cladeOrgDb");
printCladeOrgDbTree(cj->jw);
char *db = cartString(cj->cart, "db");
jsonWriteString(cj->jw, "db", db);
char *org = cartUsualString(cj->cart, "org", hGenome(db));
jsonWriteString(cj->jw, "org", org);
char *clade = cartUsualString(cj->cart, "clade", hClade(org));
jsonWriteString(cj->jw, "clade", clade);
jsonWriteObjectEnd(cj->jw);
char *position = cartOptionalString(cj->cart, "position");
if (isEmpty(position))
    position = hDefaultPos(db);
jsonWriteString(cj->jw, "position", position);
printGeneSuggestTrack(cj, db);
}
Exemple #10
0
static void printSomeGenomeListHtmlNamedMaybeCheck(char *customOrgCgiName,
	 char *db, struct dbDb *dbList, char *onChangeText, boolean doCheck)
/* Prints to stdout the HTML to render a dropdown list
 * containing a list of the possible genomes to choose from.
 * param db - a database whose genome will be the default genome.
 *                       If NULL, no default selection.
 * param onChangeText - Optional (can be NULL) text to pass in
 *                              any onChange javascript. */
{
char *orgList[1024];
int numGenomes = 0;
struct dbDb *cur = NULL;
struct hash *hash = hashNew(10); // 2^^10 entries = 1024
char *selGenome = hGenome(db);
char *values [1024];
char *cgiName;

for (cur = dbList; cur != NULL; cur = cur->next)
    {
    if (!hashFindVal(hash, cur->genome) &&
	(!doCheck || hDbExists(cur->name)))
        {
        hashAdd(hash, cur->genome, cur);
        orgList[numGenomes] = trackHubSkipHubName(cur->genome);
        values[numGenomes] = cur->genome;
        numGenomes++;
	if (numGenomes >= ArraySize(orgList))
	    internalErr();
        }
    }

cgiName = (customOrgCgiName != NULL) ? customOrgCgiName : orgCgiName;
cgiMakeDropListFull(cgiName, orgList, values, numGenomes,
                    selGenome, onChangeText);
hashFree(&hash);
}
Exemple #11
0
void getDbGenomeClade(struct cart *cart, char **retDb, char **retGenome,
		      char **retClade, struct hash *oldVars)
/* Examine CGI and cart variables to determine which db, genome, or clade
 *  has been selected, and then adjust as necessary so that all three are
 * consistent.  Detect changes and reset db-specific cart variables.
 * Save db, genome and clade in the cart so it will be consistent hereafter.
 * The order of preference here is as follows:
 * If we got a request that explicitly names the db, that takes
 * highest priority, and we synch the organism to that db.
 * If we get a cgi request for a specific organism then we use that
 * organism to choose the DB.  If just clade, go from there.

 * In the cart only, we use the same order of preference.
 * If someone requests an Genome we try to give them the same db as
 * was in their cart, unless the Genome doesn't match.
 */
{
boolean gotClade = hGotClade();
*retDb = cgiOptionalString(dbCgiName);
*retGenome = cgiOptionalString(orgCgiName);
*retClade = cgiOptionalString(cladeCgiName);
/* phoneHome business */
phoneHome();

/* Was the database passed in as a cgi param?
 * If so, it takes precedence and determines the genome. */
if (*retDb && hDbExists(*retDb))
    {
    *retGenome = hGenome(*retDb);
    }
/* If no db was passed in as a cgi param then was the organism (a.k.a. genome)
 * passed in as a cgi param?
 * If so, the we use the proper database for that genome. */
else if (*retGenome && !sameWord(*retGenome, "0"))
    {
    *retDb = getDbForGenome(*retGenome, cart);
    *retGenome = hGenome(*retDb);
    }
else if (*retClade && gotClade)
    {
    *retGenome = hDefaultGenomeForClade(*retClade);
    *retDb = getDbForGenome(*retGenome, cart);
    }
/* If no cgi params passed in then we need to inspect the session */
else
    {
    *retDb = cartOptionalString(cart, dbCgiName);
    *retGenome = cartOptionalString(cart, orgCgiName);
    *retClade = cartOptionalString(cart, cladeCgiName);
    /* If there was a db found in the session that determines everything. */
    if (*retDb && hDbExists(*retDb))
        {
        *retGenome = hGenome(*retDb);
        }
    else if (*retGenome && !sameWord(*retGenome, "0"))
	{
	*retDb = hDefaultDbForGenome(*retGenome);
	}
    else if (*retClade && gotClade)
	{
        *retGenome = hDefaultGenomeForClade(*retClade);
	*retDb = getDbForGenome(*retGenome, cart);
	}
    /* If no organism in the session then get the default db and organism. */
    else
	{
	*retDb = hDefaultDb();
	*retGenome = hGenome(*retDb);
        }
    }
*retDb = cloneString(*retDb);
*retGenome = cloneString(*retGenome);
*retClade = hClade(*retGenome);

/* Detect change of database and reset db-specific cart variables: */
if (oldVars)
    {
    char *oldDb = hashFindVal(oldVars, "db");
    char *oldOrg = hashFindVal(oldVars, "org");
    char *oldClade = hashFindVal(oldVars, "clade");
    if ((!IS_CART_VAR_EMPTY(oldDb)    && differentWord(oldDb, *retDb)) ||
        (!IS_CART_VAR_EMPTY(oldOrg)   && differentWord(oldOrg, *retGenome)) ||
        (!IS_CART_VAR_EMPTY(oldClade) && differentWord(oldClade, *retClade)))
	{
	/* Change position to default -- unless it was passed in via CGI: */
	if (cgiOptionalString("position") == NULL)
	    cartSetString(cart, "position", hDefaultPos(*retDb));
	/* hgNear search term -- unless it was passed in via CGI: */
	if (cgiOptionalString("near_search") == NULL)
	    cartRemove(cart, "near_search");
	/* hgBlat results (hgUserPsl track): */
	cartRemove(cart, "ss");
	/* hgTables correlate: */
	cartRemove(cart, "hgta_correlateTrack");
	cartRemove(cart, "hgta_correlateTable");
	cartRemove(cart, "hgta_correlateGroup");
	cartRemove(cart, "hgta_correlateOp");
	cartRemove(cart, "hgta_nextCorrelateTrack");
	cartRemove(cart, "hgta_nextCorrelateTable");
	cartRemove(cart, "hgta_nextCorrelateGroup");
	cartRemove(cart, "hgta_nextCorrelateOp");
	cartRemove(cart, "hgta_corrWinSize");
	cartRemove(cart, "hgta_corrMaxLimitCount");
	}
    }

/* Save db, genome (as org) and clade in cart. */
cartSetString(cart, "db", *retDb);
cartSetString(cart, "org", *retGenome);
if (gotClade)
    cartSetString(cart, "clade", *retClade);
}
Exemple #12
0
void showMainControlTable(struct sqlConnection *conn)
/* Put up table with main controls for main page. */
{
struct grp *selGroup;
boolean isWig = FALSE, isPositional = FALSE, isMaf = FALSE, isBedGr = FALSE,
        isChromGraphCt = FALSE, isPal = FALSE, isArray = FALSE, isBam = FALSE, isVcf = FALSE, isHalSnake = FALSE, isLongTabix = FALSE;
boolean gotClade = hGotClade();
struct hTableInfo *hti = NULL;

hPrintf("<TABLE BORDER=0>\n");

/* Print clade, genome and assembly line. */
    {
    if (gotClade)
        {
        hPrintf("<TR><TD><B>clade:</B>\n");
        printCladeListHtml(hGenome(database), onChangeClade());
        nbSpaces(3);
        hPrintf("<B>genome:</B>\n");
        printGenomeListForCladeHtml(database, onChangeOrg());
        }
    else
        {
        hPrintf("<TR><TD><B>genome:</B>\n");
        printGenomeListHtml(database, onChangeOrg());
        }
    nbSpaces(3);
    hPrintf("<B>assembly:</B>\n");
    printAssemblyListHtml(database, onChangeDb());
    hPrintf("</TD></TR>\n");
    }

/* Print group and track line. */
    {
    hPrintf("<TR><TD>");
    selGroup = showGroupField(hgtaGroup, onChangeGroupOrTrack(), conn, hAllowAllTables());
    nbSpaces(3);
    curTrack = showTrackField(selGroup, hgtaTrack, onChangeGroupOrTrack(), FALSE);
    nbSpaces(3);
    boolean hasCustomTracks = FALSE;
    struct trackDb *t;
    for (t = fullTrackList;  t != NULL;  t = t->next)
        {
        if (isCustomTrack(t->table))
            {
            hasCustomTracks = TRUE;
            break;
            }
        }
    hOnClickButton("document.customTrackForm.submit();return false;",
                   hasCustomTracks ? CT_MANAGE_BUTTON_LABEL : CT_ADD_BUTTON_LABEL);

    hPrintf(" ");
    if (hubConnectTableExists())
	hOnClickButton("document.trackHubForm.submit();return false;", "track hubs");

    hPrintf("</TD></TR>\n");
    }

/* Print table line. */
    {
    hPrintf("<TR><TD>");
    curTable = showTableField(curTrack, hgtaTable, TRUE);
    if (isHubTrack(curTable) || (strchr(curTable, '.') == NULL))  /* In same database */
        {
        hti = getHti(database, curTable, conn);
        isPositional = htiIsPositional(hti);
        }
    isLongTabix = isLongTabixTable( curTable);
    isBam = isBamTable( curTable);
    isVcf = isVcfTable(curTable, NULL);
    isWig = isWiggle(database, curTable);
    if (isBigWigTable(curTable))
        {
        isPositional = TRUE;
        isWig = TRUE;
        }
    isHalSnake = isHalTable( curTable);
    isMaf = isMafTable(database, curTrack, curTable);
    isBedGr = isBedGraph(curTable);
    isArray = isMicroarray(curTrack, curTable);
    struct trackDb *tdb = findTdbForTable(database, curTrack, curTable, ctLookupName);
    isPal = isPalCompatible(conn, tdb, curTable);
    nbSpaces(1);
    if (isCustomTrack(curTable))
        {
        isChromGraphCt = isChromGraph(tdb);
        }
    cgiMakeButton(hgtaDoSchema, "describe table schema");
    hPrintf("</TD></TR>\n");
    }

if (curTrack == NULL)
    {
    struct trackDb *tdb = hTrackDbForTrack(database, curTable);
    struct trackDb *cTdb = hCompositeTrackDbForSubtrack(database, tdb);
    if (cTdb)
        curTrack = cTdb;
    else
        curTrack = tdb;
    isMaf = isMafTable(database, curTrack, curTable);
    }

/* Region line */
{
char *regionType = cartUsualString(cart, hgtaRegionType, hgtaRegionTypeGenome);
char *range = cartUsualString(cart, hgtaRange, "");
if (isPositional)
    {
    boolean doEncode = FALSE; 

    if (!trackHubDatabase(database))
	doEncode = sqlTableExists(conn, "encodeRegions");

    hPrintf("<TR><TD><B>region:</B>\n");

    /* If regionType not allowed force it to "genome". */
    if ((sameString(regionType, hgtaRegionTypeUserRegions) &&
	 userRegionsFileName() == NULL) ||
	(sameString(regionType, hgtaRegionTypeEncode) && !doEncode))
	regionType = hgtaRegionTypeGenome;
    // Is "genome" is not allowed because of tdb 'tableBrowser noGenome'?
    boolean disableGenome = ((curTrack && cartTrackDbIsNoGenome(database, curTrack->table)) ||
                             (curTable && cartTrackDbIsNoGenome(database, curTable)));
    // If "genome" is selected but not allowed, force it to "range":
    if (sameString(regionType, hgtaRegionTypeGenome) && disableGenome)
        regionType = hgtaRegionTypeRange;
    jsTrackingVar("regionType", regionType);
    if (disableGenome)
        {
        makeRegionButtonExtraHtml(hgtaRegionTypeGenome, regionType, "DISABLED");
        hPrintf("&nbsp;<span"NO_GENOME_CLASS">genome (unavailable for selected track)</span>"
                "&nbsp;");
        }
    else
        {
        makeRegionButton(hgtaRegionTypeGenome, regionType);
        hPrintf("&nbsp;genome&nbsp;");
        }
    if (doEncode)
        {
	makeRegionButton(hgtaRegionTypeEncode, regionType);
	hPrintf("&nbsp;ENCODE Pilot regions&nbsp;");
	}
    makeRegionButton(hgtaRegionTypeRange, regionType);
    hPrintf("&nbsp;position&nbsp;");
    hPrintf("<INPUT TYPE=TEXT NAME=\"%s\" SIZE=26 VALUE=\"%s\" onFocus=\"%s\">\n",
    	hgtaRange, range, jsRadioUpdate(hgtaRegionType, "regionType", "range"));
    cgiMakeButton(hgtaDoLookupPosition, "lookup");
    hPrintf("&nbsp;");
    if (userRegionsFileName() != NULL)
	{
	makeRegionButton(hgtaRegionTypeUserRegions, regionType);
	hPrintf("&nbsp;defined regions&nbsp;");
	cgiMakeButton(hgtaDoSetUserRegions, "change");
	hPrintf("&nbsp;");
	cgiMakeButton(hgtaDoClearUserRegions, "clear");
	}
    else
	cgiMakeButton(hgtaDoSetUserRegions, "define regions");
    hPrintf("</TD></TR>\n");
    }
else
    {
    /* Need to put at least stubs of cgi variables in for JavaScript to work. */
    jsTrackingVar("regionType", regionType);
    cgiMakeHiddenVar(hgtaRange, range);
    cgiMakeHiddenVar(hgtaRegionType, regionType);
    }

/* Select identifiers line (if applicable). */
if (!isWig && getIdField(database, curTrack, curTable, hti) != NULL)
    {
    hPrintf("<TR><TD><B>identifiers (names/accessions):</B>\n");
    cgiMakeButton(hgtaDoPasteIdentifiers, "paste list");
    hPrintf(" ");
    cgiMakeButton(hgtaDoUploadIdentifiers, "upload list");
    if (identifierFileName() != NULL)
        {
	hPrintf("&nbsp;");
	cgiMakeButton(hgtaDoClearIdentifiers, "clear list");
	}
    hPrintf("</TD></TR>\n");
    }
}

/* microarray options */
/*   button for option page here (median/log-ratio, etc)  */

/* Filter line. */
{
hPrintf("<TR><TD><B>filter:</B>\n");
if (anyFilter())
    {
    cgiMakeButton(hgtaDoFilterPage, "edit");
    hPrintf(" ");
    cgiMakeButton(hgtaDoClearFilter, "clear");
    if (isWig || isBedGr)
	wigShowFilter(conn);
    }
else
    {
    cgiMakeButton(hgtaDoFilterPage, "create");
    }
hPrintf("</TD></TR>\n");
}

/* Composite track subtrack merge line. */
boolean canSubtrackMerge = (curTrack && tdbIsComposite(curTrack) && !isBam && !isVcf && !isLongTabix);
if (canSubtrackMerge)
    {
    hPrintf("<TR><TD><B>subtrack merge:</B>\n");
    if (anySubtrackMerge(database, curTable))
	{
	cgiMakeButton(hgtaDoSubtrackMergePage, "edit");
	hPrintf(" ");
	cgiMakeButton(hgtaDoClearSubtrackMerge, "clear");
	}
    else
	{
	cgiMakeButton(hgtaDoSubtrackMergePage, "create");
	}
    hPrintf("</TD></TR>\n");
    }

/* Intersection line. */
if (isPositional)
    {
    if (anyIntersection())
        {
	hPrintf("<TR><TD><B>intersection with %s:</B>\n",
		cartString(cart, hgtaIntersectTable));
	cgiMakeButton(hgtaDoIntersectPage, "edit");
	hPrintf(" ");
	cgiMakeButton(hgtaDoClearIntersect, "clear");
        hPrintf("</TD></TR>\n");
	}
    else if (canIntersect(database, curTable))
        {
	hPrintf("<TR><TD><B>intersection:</B>\n");
	cgiMakeButton(hgtaDoIntersectPage, "create");
        hPrintf("</TD></TR>\n");
	}
    }

/* Correlation line. */
struct trackDb *tdb = findTdbForTable(database, curTrack, curTable, ctLookupName);
if (correlateTrackTableOK(tdb, curTable))
    {
    char *table2 = cartUsualString(cart, hgtaCorrelateTable, "none");
    hPrintf("<TR><TD><B>correlation:</B>\n");
    if (differentWord(table2, "none") && strlen(table2) && ! isNoGenomeDisabled(database, table2))
        {
        struct grp *groupList = fullGroupList;
        struct grp *selGroup = findSelectedGroup(groupList, hgtaCorrelateGroup);
        struct trackDb *tdb2 = findSelectedTrack(fullTrackList, selGroup,hgtaCorrelateTrack);
        if (tdbIsComposite(tdb2))
            {
	    struct slRef *tdbRefList = trackDbListGetRefsToDescendantLeaves(tdb2->subtracks);
	    struct slRef *tdbRef;
	    for (tdbRef = tdbRefList; tdbRef != NULL; tdbRef = tdbRef->next)
                {
		struct trackDb *subTdb = tdbRef->val;
                if (sameString(table2, subTdb->table))
                    {
                    tdb2 = subTdb;
                    break;
                    }
                }
	    slFreeList(&tdbRefList);
            }
        cgiMakeButton(hgtaDoCorrelatePage, "calculate");
        cgiMakeButton(hgtaDoClearCorrelate, "clear");
        if (tdb2 && tdb2->shortLabel)
            hPrintf("&nbsp;(with:&nbsp;&nbsp;%s)", tdb2->shortLabel);

#ifdef NOT_YET
        /* debugging 	dbg	vvvvv	*/
        if (curTrack && curTrack->type)		/*	dbg	*/
            {
            hPrintf("<BR>&nbsp;(debug:&nbsp;'%s',&nbsp;'%s(%s)')",
                    curTrack->type, tdb2->type, table2);
            }
        /* debugging 	debug	^^^^^	*/
#endif

        }
    else
        cgiMakeButton(hgtaDoCorrelatePage, "create");

    hPrintf("</TD></TR>\n");
    }

/* Print output type line. */
showOutputTypeRow(isWig, isBedGr, isPositional, isMaf, isChromGraphCt, isPal, isArray, isHalSnake);

/* Print output destination line. */
    {
    char *compressType =
	cartUsualString(cart, hgtaCompressType, textOutCompressNone);
    char *fileName = cartUsualString(cart, hgtaOutFileName, "");
    hPrintf("<TR><TD>\n");
    hPrintf("<B>output file:</B>&nbsp;");
    cgiMakeTextVar(hgtaOutFileName, fileName, 29);
    hPrintf("&nbsp;(leave blank to keep output in browser)</TD></TR>\n");
    hPrintf("<TR><TD>\n");
    hPrintf("<B>file type returned:&nbsp;</B>");
    cgiMakeRadioButton(hgtaCompressType, textOutCompressNone,
	sameWord(textOutCompressNone, compressType));
    hPrintf("&nbsp;plain text&nbsp&nbsp");
    cgiMakeRadioButton(hgtaCompressType, textOutCompressGzip,
	sameWord(textOutCompressGzip, compressType));
    hPrintf("&nbsp;gzip compressed");
    hPrintf("</TD></TR>\n");
    }

hPrintf("</TABLE>\n");


/* Submit buttons. */
    {
    hPrintf("<BR>\n");
    if (isWig || isBam || isVcf || isLongTabix)
	{
	char *name;
	extern char *maxOutMenu[];
	char *maxOutput = maxOutMenu[0];

	if (isCustomTrack(curTable))
	    name=filterFieldVarName("ct", curTable, "_", filterMaxOutputVar);
	else
	    name=filterFieldVarName(database,curTable, "_",filterMaxOutputVar);

	maxOutput = cartUsualString(cart, name, maxOutMenu[0]);

	if (isWig)
	    hPrintf(
		"<I>Note: to return more than %s lines, change the filter setting"
		" (above). The entire data set may be available for download as"
		" a very large file that contains the original data values (not"
		" compressed into the wiggle format) -- see the Downloads page."
		"</I><BR>", maxOutput);
	else if (isBam || isVcf || isLongTabix)
	    hPrintf(
		"<I>Note: to return more than %s lines, change the filter setting"
		" (above). Please consider downloading the entire data from our Download pages."
		"</I><BR>", maxOutput);
	}
    else if (anySubtrackMerge(database, curTable) || anyIntersection())
	{
	hPrintf("<I>Note: The all fields and selected fields output formats "
		"are not available when a%s has been specified.</I><BR>",
		canSubtrackMerge ? " subtrack merge or intersection" : "n intersection");
	}
    cgiMakeButton(hgtaDoTopSubmit, "get output");
    hPrintf(" ");
    if (isPositional || isWig)
	{
	cgiMakeButton(hgtaDoSummaryStats, "summary/statistics");
	hPrintf(" ");
	}

#ifdef SOMETIMES
    hPrintf(" ");
    cgiMakeButton(hgtaDoTest, "test");
#endif /* SOMETIMES */
    }
hPrintf("<P>"
	"To reset <B>all</B> user cart settings (including custom tracks), \n"
	"<A HREF=\"/cgi-bin/cartReset?destination=%s\">click here</A>.\n",
	getScriptName());

}
char *uniProtFindPrimAccFromGene(char *gene, char *db)
/* Return primary accession given gene name.
 * NULL if not found. */
{
static struct sqlConnection *conn=NULL;
char *acc = NULL;
char query[256];
char *pdb = cloneString(UNIPROT_DB_NAME);
char *geneTable = "gene";

if (conn==NULL)
    {
    conn = sqlMayConnect(pdb);
    if (conn == NULL) return NULL;
    }
if (geneTable != NULL && sqlTableExists(conn,geneTable)) 
    {
//    safef(query, sizeof(query), "select acc from %s where val = '%s'", geneTable, gene);
    safef(query, sizeof(query), "select g.acc from %s g , accToTaxon a, taxon t where val = '%s' and g.acc = a.acc and id = a.taxon and binomial = '%s' ",geneTable, gene, hGenome(db));
    acc = sqlQuickString(conn, query);
    }
return(acc);
}