Merge branch 'master' into bplane
Conflicts: extract/ExtSubtree.c utils/Depend Updated bplane branch from master branch.
This commit is contained in:
commit
bb1c9a6c0e
|
|
@ -1,5 +1,5 @@
|
|||
defs.mak
|
||||
Depend
|
||||
*/Depend
|
||||
config.cache
|
||||
config.log
|
||||
scripts/config.log
|
||||
|
|
|
|||
|
|
@ -345,6 +345,7 @@ calmaParseStructure(filename)
|
|||
}
|
||||
}
|
||||
cifReadCellDef = calmaFindCell(strname, &was_called);
|
||||
def->cd_flags &= ~CDDEREFERENCE;
|
||||
DBCellClearDef(cifReadCellDef);
|
||||
DBCellSetAvail(cifReadCellDef);
|
||||
HashSetValue(he, cifReadCellDef);
|
||||
|
|
@ -664,6 +665,10 @@ calmaElementSref(filename)
|
|||
TxPrintf("Cell definition %s does not exist!\n", sname);
|
||||
fseek(calmaInputFile, originalFilePos, SEEK_SET);
|
||||
def = calmaFindCell(sname, NULL);
|
||||
/* Cell flags set to "dereferenced" in case there is no */
|
||||
/* definition in the GDS file. If there is a definition */
|
||||
/* made after the instance, then the flag will be cleared. */
|
||||
def->cd_flags |= CDDEREFERENCE;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1455,7 +1455,8 @@ badTransform:
|
|||
pathOK = TRUE;
|
||||
}
|
||||
|
||||
if ((pathOK == FALSE) && strcmp(subCellDef->cd_file, pathptr))
|
||||
if ((pathOK == FALSE) && strcmp(subCellDef->cd_file, pathptr)
|
||||
&& (dereference == FALSE))
|
||||
{
|
||||
TxError("Duplicate cell in %s: Instance of cell %s is from "
|
||||
"path %s but cell was previously read from %s.\n",
|
||||
|
|
|
|||
|
|
@ -507,6 +507,11 @@ typedef struct celluse
|
|||
*/
|
||||
#define CU_SELECT_NET 0x02
|
||||
#define CU_SELECT_CHUNK 0x04
|
||||
/* CU_SUB_EXTRACTED is a temporary flag indicating that the substrate
|
||||
* of the use has been extracted and the extraction
|
||||
* does not need to be repeated for this use.
|
||||
*/
|
||||
#define CU_SUB_EXTRACTED 0x08
|
||||
|
||||
/* Character prefix used to denote a locked cell use in a .mag file */
|
||||
#define CULOCKCHAR '*'
|
||||
|
|
|
|||
|
|
@ -184,6 +184,7 @@ efBuildNode(def, isSubsnode, nodeName, nodeCap, x, y, layerName, av, ac)
|
|||
newnode->efnode_loc.r_xtop = newnode->efnode_loc.r_xbot + 1;
|
||||
newnode->efnode_loc.r_ytop = newnode->efnode_loc.r_ybot + 1;
|
||||
newnode->efnode_client = (ClientData) NULL;
|
||||
newnode->efnode_num = 1;
|
||||
if (layerName) newnode->efnode_type =
|
||||
efBuildAddStr(EFLayerNames, &EFLayerNumNames, MAXTYPES, layerName);
|
||||
else newnode->efnode_type = 0;
|
||||
|
|
@ -464,7 +465,7 @@ efBuildEquiv(def, nodeName1, nodeName2)
|
|||
{
|
||||
if (efWarn)
|
||||
efReadError("Merged nodes %s and %s\n", nodeName1, nodeName2);
|
||||
efNodeMerge(nn1->efnn_node, nn2->efnn_node);
|
||||
efNodeMerge(&nn1->efnn_node, &nn2->efnn_node);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
|
@ -1580,70 +1581,86 @@ efNodeAddName(node, he, hn)
|
|||
*/
|
||||
|
||||
void
|
||||
efNodeMerge(node1, node2)
|
||||
EFNode *node1, *node2; /* Hierarchical nodes */
|
||||
efNodeMerge(node1ptr, node2ptr)
|
||||
EFNode **node1ptr, **node2ptr; /* Pointers to hierarchical nodes */
|
||||
{
|
||||
EFNodeName *nn, *nnlast;
|
||||
EFAttr *ap;
|
||||
int n;
|
||||
EFNode *keeping, *removing;
|
||||
|
||||
/* Sanity check: ignore if same node */
|
||||
if (node1 == node2)
|
||||
if (*node1ptr == *node2ptr)
|
||||
return;
|
||||
|
||||
/* Keep the node with the greater number of entries, and merge */
|
||||
/* the node with fewer entries into it. */
|
||||
|
||||
if ((*node1ptr)->efnode_num >= (*node2ptr)->efnode_num)
|
||||
{
|
||||
keeping = *node1ptr;
|
||||
removing = *node2ptr;
|
||||
}
|
||||
else
|
||||
{
|
||||
keeping = *node2ptr;
|
||||
removing = *node1ptr;
|
||||
}
|
||||
|
||||
if (efWatchNodes)
|
||||
{
|
||||
if (HashLookOnly(&efWatchTable, (char *) node1->efnode_name->efnn_hier)
|
||||
|| (node2->efnode_name
|
||||
if (HashLookOnly(&efWatchTable, (char *) keeping->efnode_name->efnn_hier)
|
||||
|| (removing->efnode_name
|
||||
&& HashLookOnly(&efWatchTable,
|
||||
(char *) node2->efnode_name->efnn_hier)))
|
||||
(char *) removing->efnode_name->efnn_hier)))
|
||||
{
|
||||
printf("\ncombine: %s\n",
|
||||
EFHNToStr(node1->efnode_name->efnn_hier));
|
||||
EFHNToStr(keeping->efnode_name->efnn_hier));
|
||||
printf(" with %s\n\n",
|
||||
node2->efnode_name
|
||||
? EFHNToStr(node2->efnode_name->efnn_hier)
|
||||
removing->efnode_name
|
||||
? EFHNToStr(removing->efnode_name->efnn_hier)
|
||||
: "(unnamed)");
|
||||
}
|
||||
}
|
||||
|
||||
/* Sum capacitances, perimeters, areas */
|
||||
node1->efnode_cap += node2->efnode_cap;
|
||||
keeping->efnode_cap += removing->efnode_cap;
|
||||
for (n = 0; n < efNumResistClasses; n++)
|
||||
{
|
||||
node1->efnode_pa[n].pa_area += node2->efnode_pa[n].pa_area;
|
||||
node1->efnode_pa[n].pa_perim += node2->efnode_pa[n].pa_perim;
|
||||
keeping->efnode_pa[n].pa_area += removing->efnode_pa[n].pa_area;
|
||||
keeping->efnode_pa[n].pa_perim += removing->efnode_pa[n].pa_perim;
|
||||
}
|
||||
|
||||
/* Make all EFNodeNames point to node1 */
|
||||
if (node2->efnode_name)
|
||||
/* Make all EFNodeNames point to "keeping" */
|
||||
if (removing->efnode_name)
|
||||
{
|
||||
bool topport1, topport2;
|
||||
bool topportk, topportr;
|
||||
|
||||
for (nn = node2->efnode_name; nn; nn = nn->efnn_next)
|
||||
for (nn = removing->efnode_name; nn; nn = nn->efnn_next)
|
||||
{
|
||||
nnlast = nn;
|
||||
nn->efnn_node = node1;
|
||||
nn->efnn_node = keeping;
|
||||
}
|
||||
|
||||
topport1 = (node1->efnode_flags & EF_TOP_PORT) ? TRUE : FALSE;
|
||||
topport2 = (node2->efnode_flags & EF_TOP_PORT) ? TRUE : FALSE;
|
||||
topportk = (keeping->efnode_flags & EF_TOP_PORT) ? TRUE : FALSE;
|
||||
topportr = (removing->efnode_flags & EF_TOP_PORT) ? TRUE : FALSE;
|
||||
|
||||
/* Concatenate list of EFNodeNames, taking into account precedence */
|
||||
if (!topport1 && (topport2 || EFHNBest(node2->efnode_name->efnn_hier,
|
||||
node1->efnode_name->efnn_hier)))
|
||||
if ((!keeping->efnode_name) || (!topportk && (topportr
|
||||
|| EFHNBest(removing->efnode_name->efnn_hier,
|
||||
keeping->efnode_name->efnn_hier))))
|
||||
{
|
||||
/*
|
||||
* New official name is that of node2.
|
||||
* New official name is that of "removing".
|
||||
* The new list of names is:
|
||||
* node2-names, node1-names
|
||||
* removing-names, keeping-names
|
||||
*/
|
||||
nnlast->efnn_next = node1->efnode_name;
|
||||
node1->efnode_name = node2->efnode_name;
|
||||
nnlast->efnn_next = keeping->efnode_name;
|
||||
keeping->efnode_name = removing->efnode_name;
|
||||
|
||||
/*
|
||||
* Choose the new location only if node2's location is a valid one,
|
||||
* i.e, node2 wasn't created before it was mentioned. This is mainly
|
||||
* Choose the new location only if "removing"'s location is a valid one,
|
||||
* i.e, "removing" wasn't created before it was mentioned. This is mainly
|
||||
* to deal with new fets, resistors, and capacitors created by resistance
|
||||
* extraction, which appear with their full hierarchical names in the
|
||||
* .ext file for the root cell.
|
||||
|
|
@ -1658,18 +1675,10 @@ efNodeMerge(node1, node2)
|
|||
*
|
||||
* Tim, 6/14/04
|
||||
*/
|
||||
if (node2->efnode_type > 0)
|
||||
if (removing->efnode_type > 0)
|
||||
{
|
||||
node1->efnode_loc = node2->efnode_loc;
|
||||
node1->efnode_type = node2->efnode_type;
|
||||
|
||||
if (node2->efnode_loc.r_ybot < node1->efnode_loc.r_ybot
|
||||
|| (node2->efnode_loc.r_ybot == node1->efnode_loc.r_ybot
|
||||
&& node2->efnode_loc.r_xbot < node1->efnode_loc.r_xbot))
|
||||
{
|
||||
// node1->efnode_loc = node2->efnode_loc;
|
||||
// node1->efnode_type = node2->efnode_type;
|
||||
}
|
||||
keeping->efnode_loc = removing->efnode_loc;
|
||||
keeping->efnode_type = removing->efnode_type;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
|
@ -1677,52 +1686,59 @@ efNodeMerge(node1, node2)
|
|||
/*
|
||||
* Keep old official name.
|
||||
* The new list of names is:
|
||||
* node1-names[0], node2-names, node1-names[1-]
|
||||
* keeping-names[0], removing-names, keeping-names[1-]
|
||||
*/
|
||||
nnlast->efnn_next = node1->efnode_name->efnn_next;
|
||||
node1->efnode_name->efnn_next = node2->efnode_name;
|
||||
nnlast->efnn_next = keeping->efnode_name->efnn_next;
|
||||
keeping->efnode_name->efnn_next = removing->efnode_name;
|
||||
}
|
||||
}
|
||||
|
||||
/* Merge list counts */
|
||||
keeping->efnode_num += removing->efnode_num;
|
||||
|
||||
/* Merge attribute lists */
|
||||
if (ap = node2->efnode_attrs)
|
||||
if (ap = removing->efnode_attrs)
|
||||
{
|
||||
while (ap->efa_next)
|
||||
ap = ap->efa_next;
|
||||
ap->efa_next = node1->efnode_attrs;
|
||||
node1->efnode_attrs = ap;
|
||||
node2->efnode_attrs = (EFAttr *) NULL; /* Sanity */
|
||||
ap->efa_next = keeping->efnode_attrs;
|
||||
keeping->efnode_attrs = ap;
|
||||
removing->efnode_attrs = (EFAttr *) NULL; /* Sanity */
|
||||
}
|
||||
|
||||
/* Unlink node2 from list for def */
|
||||
node2->efnode_prev->efnhdr_next = node2->efnode_next;
|
||||
node2->efnode_next->efnhdr_prev = node2->efnode_prev;
|
||||
/* Unlink "removing" from list for def */
|
||||
removing->efnode_prev->efnhdr_next = removing->efnode_next;
|
||||
removing->efnode_next->efnhdr_prev = removing->efnode_prev;
|
||||
|
||||
/*
|
||||
* Only if both nodes were EF_DEVTERM do we keep EF_DEVTERM set
|
||||
* in the resultant node.
|
||||
*/
|
||||
if ((node2->efnode_flags & EF_DEVTERM) == 0)
|
||||
node1->efnode_flags &= ~EF_DEVTERM;
|
||||
if ((removing->efnode_flags & EF_DEVTERM) == 0)
|
||||
keeping->efnode_flags &= ~EF_DEVTERM;
|
||||
|
||||
/*
|
||||
* If node2 has the EF_PORT flag set, then copy the port
|
||||
* If "removing" has the EF_PORT flag set, then copy the port
|
||||
* record in the flags to node1.
|
||||
*/
|
||||
if (node2->efnode_flags & EF_PORT)
|
||||
node1->efnode_flags |= EF_PORT;
|
||||
if (node2->efnode_flags & EF_TOP_PORT)
|
||||
node1->efnode_flags |= EF_TOP_PORT;
|
||||
if (removing->efnode_flags & EF_PORT)
|
||||
keeping->efnode_flags |= EF_PORT;
|
||||
if (removing->efnode_flags & EF_TOP_PORT)
|
||||
keeping->efnode_flags |= EF_TOP_PORT;
|
||||
|
||||
/*
|
||||
* If node2 has the EF_SUBS_NODE flag set, then copy the port
|
||||
* record in the flags to node1.
|
||||
* If "removing" has the EF_SUBS_NODE flag set, then copy the port
|
||||
* record in the flags to "keeping".
|
||||
*/
|
||||
if (node2->efnode_flags & EF_SUBS_NODE)
|
||||
node1->efnode_flags |= EF_SUBS_NODE;
|
||||
if (removing->efnode_flags & EF_SUBS_NODE)
|
||||
keeping->efnode_flags |= EF_SUBS_NODE;
|
||||
|
||||
/* Get rid of node2 */
|
||||
freeMagic((char *) node2);
|
||||
/* Get rid of "removing" */
|
||||
freeMagic((char *) removing);
|
||||
|
||||
/* Make sure that the active node is always node1 */
|
||||
*node1ptr = keeping;
|
||||
*node2ptr = (EFNode *)NULL; /* Sanity check */
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -62,6 +62,11 @@ int efAddNodes(HierContext *, bool);
|
|||
int efAddConns(HierContext *, bool);
|
||||
int efAddOneConn(HierContext *, char *, char *, Connection *, bool);
|
||||
|
||||
/* Flags passed to efFlatNode() */
|
||||
|
||||
#define FLATNODE_STDCELL 0x01
|
||||
#define FLATNODE_DOWARN 0x02
|
||||
|
||||
|
||||
/*
|
||||
* ----------------------------------------------------------------------------
|
||||
|
|
@ -127,7 +132,10 @@ EFFlatBuild(name, flags)
|
|||
if (flags & EF_NOFLATSUBCKT)
|
||||
efFlatNodesStdCell(&efFlatContext);
|
||||
else
|
||||
efFlatNodes(&efFlatContext, FALSE, TRUE);
|
||||
{
|
||||
int flags = FLATNODE_DOWARN; /* No FLATNODE_STDCELL flag */
|
||||
efFlatNodes(&efFlatContext, (ClientData)flags);
|
||||
}
|
||||
efFlatKills(&efFlatContext);
|
||||
if (!(flags & EF_NONAMEMERGE))
|
||||
efFlatGlob();
|
||||
|
|
@ -166,6 +174,7 @@ EFFlatBuildOneLevel(def, flags)
|
|||
Use *use;
|
||||
int efFlatNodesDeviceless(); /* Forward declaration */
|
||||
int efFlatCapsDeviceless(); /* Forward declaration */
|
||||
int flatnodeflags;
|
||||
|
||||
efFlatRootDef = def;
|
||||
|
||||
|
|
@ -195,7 +204,8 @@ EFFlatBuildOneLevel(def, flags)
|
|||
efFlatRootUse.use_def = efFlatRootDef;
|
||||
|
||||
/* Record all nodes down the hierarchy from here */
|
||||
efFlatNodes(&efFlatContext, (ClientData)TRUE, (ClientData)FALSE);
|
||||
flatnodeflags = FLATNODE_STDCELL; /* No FLATDNODE_DOWARN flag */
|
||||
efFlatNodes(&efFlatContext, (ClientData)flatnodeflags);
|
||||
|
||||
/* Expand all subcells that contain connectivity information but */
|
||||
/* no active devices (including those in subcells). */
|
||||
|
|
@ -292,10 +302,16 @@ EFFlatDone()
|
|||
*/
|
||||
|
||||
int
|
||||
efFlatNodes(hc, stdcell, doWarn)
|
||||
efFlatNodes(hc, clientData)
|
||||
HierContext *hc;
|
||||
ClientData clientData;
|
||||
{
|
||||
(void) efHierSrUses(hc, efFlatNodes);
|
||||
int flags = (int)clientData;
|
||||
|
||||
bool stdcell = (flags & FLATNODE_STDCELL) ? TRUE : FALSE;
|
||||
bool doWarn = (flags & FLATNODE_DOWARN) ? TRUE : FALSE;
|
||||
|
||||
(void) efHierSrUses(hc, efFlatNodes, clientData);
|
||||
|
||||
/* Add all our own nodes to the table */
|
||||
efAddNodes(hc, stdcell);
|
||||
|
|
@ -466,6 +482,7 @@ efAddNodes(hc, stdcell)
|
|||
newnode->efnode_client = (ClientData) NULL;
|
||||
newnode->efnode_flags = node->efnode_flags;
|
||||
newnode->efnode_type = node->efnode_type;
|
||||
newnode->efnode_num = 1;
|
||||
if (!stdcell)
|
||||
bcopy((char *) node->efnode_pa, (char *) newnode->efnode_pa,
|
||||
efNumResistClasses * sizeof (EFPerimArea));
|
||||
|
|
@ -514,7 +531,7 @@ efAddNodes(hc, stdcell)
|
|||
if (hierName != nn->efnn_hier)
|
||||
EFHNFree(hierName, hc->hc_hierName, HN_CONCAT);
|
||||
if (oldname->efnn_node != newnode)
|
||||
efNodeMerge(oldname->efnn_node, newnode);
|
||||
efNodeMerge(&oldname->efnn_node, &newnode);
|
||||
newnode = oldname->efnn_node;
|
||||
continue;
|
||||
}
|
||||
|
|
@ -638,7 +655,7 @@ efAddOneConn(hc, name1, name2, conn, doWarn)
|
|||
return 0;
|
||||
newnode = ((EFNodeName *) HashGetValue(he2))->efnn_node;
|
||||
if (node != newnode)
|
||||
efNodeMerge(node, newnode);
|
||||
efNodeMerge(&node, &newnode);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
|
@ -744,7 +761,7 @@ efFlatGlob()
|
|||
{
|
||||
efFlatGlobError(nameGlob, nameFlat);
|
||||
}
|
||||
efNodeMerge(nodeFlat, nodeGlob);
|
||||
efNodeMerge(&nodeFlat, &nodeGlob);
|
||||
nameGlob->efnn_node = nodeFlat;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -212,6 +212,7 @@ typedef struct efnode
|
|||
|
||||
EFCapValue efnode_cap; /* Total capacitance to ground for this node */
|
||||
int efnode_type; /* Index into type table for node */
|
||||
int efnode_num; /* Number of items in efnode_hdr list */
|
||||
Rect efnode_loc; /* Location of a 1x1 rect contained in this
|
||||
* node. This information is provided in the
|
||||
* .ext file so it will be easy to map between
|
||||
|
|
|
|||
|
|
@ -91,6 +91,10 @@ extHierSubstrate(ha, use, x, y)
|
|||
/* define a substrate plane or substrate connections. */
|
||||
if (glob_subsnode == NULL) return;
|
||||
|
||||
/* If the substrate has already been extracted for this use */
|
||||
/* then there is no need to do it again. */
|
||||
if (use->cu_flags & CU_SUB_EXTRACTED) return;
|
||||
|
||||
def = (CellDef *)ha->ha_parentUse->cu_def;
|
||||
|
||||
/* Register the name of the parent's substrate */
|
||||
|
|
@ -107,7 +111,6 @@ extHierSubstrate(ha, use, x, y)
|
|||
/* Make sure substrate labels are represented */
|
||||
ExtLabelRegions(use->cu_def, ExtCurStyle->exts_nodeConn, &nodeList,
|
||||
&TiPlaneRect);
|
||||
|
||||
ExtResetTiles(use->cu_def, extUnInit);
|
||||
|
||||
name2 = extNodeName(temp_subsnode);
|
||||
|
|
|
|||
|
|
@ -94,6 +94,26 @@ void extSubtreeAdjustInit();
|
|||
void extSubtreeOutputCoupling();
|
||||
void extSubtreeHardSearch();
|
||||
|
||||
/*
|
||||
* ----------------------------------------------------------------------------
|
||||
*
|
||||
* extClearUseFlags --
|
||||
*
|
||||
* Callback function to clear the CU_SUB_EXTRACTED flag from each child
|
||||
* use of a CellDef.
|
||||
*
|
||||
* ----------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
int
|
||||
extClearUseFlags(use, clientData)
|
||||
CellUse *use;
|
||||
ClientData clientData;
|
||||
{
|
||||
use->cu_flags &= ~CU_SUB_EXTRACTED;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* ----------------------------------------------------------------------------
|
||||
|
|
@ -146,6 +166,7 @@ extSubtree(parentUse, reg, f)
|
|||
bool result;
|
||||
int cuts, totcuts;
|
||||
float pdone, plast;
|
||||
SearchContext scx;
|
||||
|
||||
if ((ExtOptions & (EXT_DOCOUPLING|EXT_DOADJUST))
|
||||
!= (EXT_DOCOUPLING|EXT_DOADJUST))
|
||||
|
|
@ -232,8 +253,8 @@ extSubtree(parentUse, reg, f)
|
|||
{
|
||||
/* Make sure substrate connections have been handled */
|
||||
/* even if there were no other interactions found. */
|
||||
SearchContext scx;
|
||||
|
||||
ha.ha_clipArea = r;
|
||||
scx.scx_trans = GeoIdentityTransform;
|
||||
scx.scx_area = r;
|
||||
scx.scx_use = ha.ha_parentUse;
|
||||
|
|
@ -292,6 +313,9 @@ done:
|
|||
/* Output connections and node adjustments */
|
||||
extOutputConns(&ha.ha_connHash, f);
|
||||
HashKill(&ha.ha_connHash);
|
||||
|
||||
/* Clear the CU_SUB_EXTRACTED flag from all children instances */
|
||||
DBCellEnum(def, extClearUseFlags, (ClientData)NULL);
|
||||
}
|
||||
|
||||
#ifdef exactinteractions
|
||||
|
|
@ -800,6 +824,8 @@ extSubtreeFunc(scx, ha)
|
|||
for (y = use->cu_ylo; y <= use->cu_yhi; y++)
|
||||
extHierSubstrate(ha, use, x, y);
|
||||
}
|
||||
/* Mark substrate as having been extracted for this use. */
|
||||
use->cu_flags |= CU_SUB_EXTRACTED;
|
||||
|
||||
/* Free the cumulative node list we extracted above */
|
||||
if (ha->ha_cumFlat.et_nodes)
|
||||
|
|
|
|||
|
|
@ -3,10 +3,15 @@ child.o: child.c ../utils/utils.h ../utils/magic.h ../utils/malloc.h
|
|||
dqueue.o: dqueue.c ../utils/magic.h ../utils/dqueue.h ../utils/malloc.h
|
||||
finddisp.o: finddisp.c ../utils/magic.h ../utils/utils.h
|
||||
flock.o: flock.c ../utils/magic.h ../utils/hash.h ../utils/geometry.h \
|
||||
<<<<<<< HEAD
|
||||
../tiles/tile.h ../database/database.h ../bplane/bplane.h \
|
||||
../bplane/bpOpaque.h ../utils/ihash.h ../bplane/bpEnum.h \
|
||||
../utils/utils.h ../utils/geofast.h ../bplane/bplaneInt.h \
|
||||
../windows/windows.h ../utils/malloc.h
|
||||
=======
|
||||
../tiles/tile.h ../database/database.h ../windows/windows.h \
|
||||
../utils/malloc.h
|
||||
>>>>>>> master
|
||||
flsbuf.o: flsbuf.c
|
||||
fraction.o: fraction.c ../utils/magic.h ../utils/geometry.h
|
||||
geometry.o: geometry.c ../utils/magic.h ../utils/geometry.h \
|
||||
|
|
|
|||
|
|
@ -220,14 +220,15 @@ hash(table, key)
|
|||
char *key;
|
||||
{
|
||||
unsigned *up;
|
||||
int i, j;
|
||||
unsigned long i;
|
||||
int j;
|
||||
|
||||
i = 0;
|
||||
switch (table->ht_ptrKeys)
|
||||
{
|
||||
/* Add up the characters as though this were a number */
|
||||
case HT_STRINGKEYS:
|
||||
while (*key != 0) i = (i*10) + (*key++ - '0');
|
||||
while (*key != 0) i = (*key++) + (i << 6) + (i << 16) - i;
|
||||
break;
|
||||
|
||||
/* Map the key into another 32-bit value if necessary */
|
||||
|
|
|
|||
Loading…
Reference in New Issue