static void WriteOS2Data( unsigned_32 stub_len, os2_exe_header *exe_head ) /************************************************************************/ /* copy code from extra memory to loadfile. */ { group_entry *group; unsigned group_num; unsigned long off; segment_record segrec; unsigned_32 seg_addr; unsigned long relocsize; DEBUG(( DBG_BASE, "Writing data" )); group_num = 0; for( group = Groups; group != NULL; group = group->next_group ) { if( group->totalsize == 0 ) continue; // DANGER DANGER DANGER <--!!! segrec.info = group->segflags; // write segment segrec.min = MAKE_EVEN( group->totalsize ); segrec.size = MAKE_EVEN( group->size ); if( segrec.size != 0 ) { off = NullAlign( 1 << FmtData.u.os2.segment_shift ); seg_addr = off >> FmtData.u.os2.segment_shift; if( seg_addr > 0xffff ) { LnkMsg( ERR+MSG_ALIGN_TOO_SMALL, NULL ); }; segrec.address = (unsigned_16)seg_addr; WriteGroupLoad( group ); NullAlign( 2 ); // segment must be even length relocsize = WriteOS2Relocs( group ); if( relocsize != 0 ) { segrec.info |= SEG_RELOC; } } else {
char *IdentifyObject( file_list *list, unsigned long *loc, unsigned long *size ) /******************************************************************************/ { ar_header *ar_hdr; char *name; unsigned long ar_loc; name = NULL; *size = 0; if( list->status & STAT_AR_LIB ) { ar_loc = MAKE_EVEN( *loc ); /* AR headers are word aligned. */ ar_hdr = CacheRead( list, ar_loc, sizeof( ar_header ) ); ar_loc += sizeof( ar_header ); name = GetARName( ar_hdr, list, &ar_loc ); *size = GetARValue( ar_hdr->size, AR_SIZE_LEN ); *loc = ar_loc; } if( !IsORL( list, *loc ) ) { if( IsOMF( list, *loc ) ) { ObjFormat |= FMT_OMF; name = GetOMFName( list, loc ); if( list->status & STAT_AR_LIB ) { *loc = ar_loc; /* Restore the location. */ } } } return( name ); }
static bool ReadARDict( file_list *list, unsigned long *loc, bool makedict ) /**************************************************************************/ { ar_header *ar_hdr; unsigned long size; int numdicts; numdicts = 0; if( makedict ) { if( list->u.dict == NULL ) { _ChkAlloc( list->u.dict, sizeof( dict_entry ) ); } } for( ;; ) { ar_hdr = CacheRead( list, *loc, sizeof( ar_header ) ); size = GetARValue( ar_hdr->size, AR_SIZE_LEN ); if( ar_hdr->name[0] == '/' && ar_hdr->name[1] == ' ' ) { ++numdicts; *loc += sizeof( ar_header ); if( makedict ) ReadARDictData( list, loc, size, numdicts ); *loc += MAKE_EVEN( size ); } else if( ar_hdr->name[0] == '/' && ar_hdr->name[1] == '/' ) { *loc += sizeof( ar_header ); ReadARStringTable( list, loc, size ); *loc += MAKE_EVEN( size ); } else { break; // found an actual object file } } if( makedict ) { if( numdicts == 0 ) { Locator( list->file->name, NULL, 0 ); LnkMsg( ERR+MSG_NO_DICT_FOUND, NULL ); _LnkFree( list->u.dict ); list->u.dict = NULL; return( FALSE ); } if( !(LinkFlags & CASE_FLAG) || numdicts == 1 ) { SortARDict( &list->u.dict->a ); } } return( TRUE ); }
void Graph::process_sink_orphan(node *i) { node *j; arc_forward *a0_for, *a0_for_first, *a0_for_last; arc_reverse *a0_rev, *a0_rev_first, *a0_rev_last; arc_forward *a0_min = NULL, *a; nodeptr *np; int d, d_min = INFINITE_D; /* trying to find a new parent */ a0_for_first = i -> first_out; if (IS_ODD(a0_for_first)) { a0_for_first = (arc_forward *) (((char *)a0_for_first) + 1); a0_for_last = (arc_forward *) ((a0_for_first ++) -> shift); } else a0_for_last = (i + 1) -> first_out; a0_rev_first = i -> first_in; if (IS_ODD(a0_rev_first)) { a0_rev_first = (arc_reverse *) (((char *)a0_rev_first) + 1); a0_rev_last = (arc_reverse *) ((a0_rev_first ++) -> sister); } else a0_rev_last = (i + 1) -> first_in; for (a0_for=a0_for_first; a0_for<a0_for_last; a0_for++) if (a0_for->r_cap) { j = NEIGHBOR_NODE(i, a0_for -> shift); if (j->is_sink && (a=j->parent)) { /* checking the origin of j */ d = 0; while ( 1 ) { if (j->TS == TIME) { d += j -> DIST; break; } a = j -> parent; d ++; if (a==TERMINAL) { j -> TS = TIME; j -> DIST = 1; break; } if (a==ORPHAN) { d = INFINITE_D; break; } if (IS_ODD(a)) j = NEIGHBOR_NODE_REV(j, MAKE_EVEN(a) -> shift); else j = NEIGHBOR_NODE(j, a -> shift); } if (d<INFINITE_D) /* j originates from the sink - done */ { if (d<d_min) { a0_min = a0_for; d_min = d; } /* set marks along the path */ for (j=NEIGHBOR_NODE(i, a0_for->shift); j->TS!=TIME; ) { j -> TS = TIME; j -> DIST = d --; a = j->parent; if (IS_ODD(a)) j = NEIGHBOR_NODE_REV(j, MAKE_EVEN(a) -> shift); else j = NEIGHBOR_NODE(j, a -> shift); } } } } for (a0_rev=a0_rev_first; a0_rev<a0_rev_last; a0_rev++) { a0_for = a0_rev -> sister; if (a0_for->r_rev_cap) { j = NEIGHBOR_NODE_REV(i, a0_for -> shift); if (j->is_sink && (a=j->parent)) { /* checking the origin of j */ d = 0; while ( 1 ) { if (j->TS == TIME) { d += j -> DIST; break; } a = j -> parent; d ++; if (a==TERMINAL) { j -> TS = TIME; j -> DIST = 1; break; } if (a==ORPHAN) { d = INFINITE_D; break; } if (IS_ODD(a)) j = NEIGHBOR_NODE_REV(j, MAKE_EVEN(a) -> shift); else j = NEIGHBOR_NODE(j, a -> shift); } if (d<INFINITE_D) /* j originates from the sink - done */ { if (d<d_min) { a0_min = MAKE_ODD(a0_for); d_min = d; } /* set marks along the path */ for (j=NEIGHBOR_NODE_REV(i,a0_for->shift); j->TS!=TIME; ) { j -> TS = TIME; j -> DIST = d --; a = j->parent; if (IS_ODD(a)) j = NEIGHBOR_NODE_REV(j, MAKE_EVEN(a) -> shift); else j = NEIGHBOR_NODE(j, a -> shift); } } } } } if (i->parent = a0_min) { i -> TS = TIME; i -> DIST = d_min + 1; } else { /* no parent is found */ i -> TS = 0; /* process neighbors */ for (a0_for=a0_for_first; a0_for<a0_for_last; a0_for++) { j = NEIGHBOR_NODE(i, a0_for -> shift); if (j->is_sink && (a=j->parent)) { if (a0_for->r_cap) set_active(j); if (a!=TERMINAL && a!=ORPHAN && IS_ODD(a) && NEIGHBOR_NODE_REV(j, MAKE_EVEN(a)->shift)==i) { /* add j to the adoption list */ j -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = j; if (orphan_last) orphan_last -> next = np; else orphan_first = np; orphan_last = np; np -> next = NULL; } } } for (a0_rev=a0_rev_first; a0_rev<a0_rev_last; a0_rev++) { a0_for = a0_rev -> sister; j = NEIGHBOR_NODE_REV(i, a0_for -> shift); if (j->is_sink && (a=j->parent)) { if (a0_for->r_rev_cap) set_active(j); if (a!=TERMINAL && a!=ORPHAN && !IS_ODD(a) && NEIGHBOR_NODE(j, a->shift)==i) { /* add j to the adoption list */ j -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = j; if (orphan_last) orphan_last -> next = np; else orphan_first = np; orphan_last = np; np -> next = NULL; } } } } }
void Graph::augment(node *s_start, node *t_start, captype *cap_middle, captype *rev_cap_middle) { node *i; arc_forward *a; captype bottleneck; nodeptr *np; /* 1. Finding bottleneck capacity */ /* 1a - the source tree */ bottleneck = *cap_middle; for (i=s_start; ; ) { a = i -> parent; if (a == TERMINAL) break; if (IS_ODD(a)) { a = MAKE_EVEN(a); if (bottleneck > a->r_cap) bottleneck = a -> r_cap; i = NEIGHBOR_NODE_REV(i, a -> shift); } else { if (bottleneck > a->r_rev_cap) bottleneck = a -> r_rev_cap; i = NEIGHBOR_NODE(i, a -> shift); } } if (bottleneck > i->tr_cap) bottleneck = i -> tr_cap; /* 1b - the sink tree */ for (i=t_start; ; ) { a = i -> parent; if (a == TERMINAL) break; if (IS_ODD(a)) { a = MAKE_EVEN(a); if (bottleneck > a->r_rev_cap) bottleneck = a -> r_rev_cap; i = NEIGHBOR_NODE_REV(i, a -> shift); } else { if (bottleneck > a->r_cap) bottleneck = a -> r_cap; i = NEIGHBOR_NODE(i, a -> shift); } } if (bottleneck > - i->tr_cap) bottleneck = - i -> tr_cap; /* 2. Augmenting */ /* 2a - the source tree */ *rev_cap_middle += bottleneck; *cap_middle -= bottleneck; for (i=s_start; ; ) { a = i -> parent; if (a == TERMINAL) break; if (IS_ODD(a)) { a = MAKE_EVEN(a); a -> r_rev_cap += bottleneck; a -> r_cap -= bottleneck; if (!a->r_cap) { /* add i to the adoption list */ i -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = i; np -> next = orphan_first; orphan_first = np; } i = NEIGHBOR_NODE_REV(i, a -> shift); } else { a -> r_cap += bottleneck; a -> r_rev_cap -= bottleneck; if (!a->r_rev_cap) { /* add i to the adoption list */ i -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = i; np -> next = orphan_first; orphan_first = np; } i = NEIGHBOR_NODE(i, a -> shift); } } i -> tr_cap -= bottleneck; if (!i->tr_cap) { /* add i to the adoption list */ i -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = i; np -> next = orphan_first; orphan_first = np; } /* 2b - the sink tree */ for (i=t_start; ; ) { a = i -> parent; if (a == TERMINAL) break; if (IS_ODD(a)) { a = MAKE_EVEN(a); a -> r_cap += bottleneck; a -> r_rev_cap -= bottleneck; if (!a->r_rev_cap) { /* add i to the adoption list */ i -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = i; np -> next = orphan_first; orphan_first = np; } i = NEIGHBOR_NODE_REV(i, a -> shift); } else { a -> r_rev_cap += bottleneck; a -> r_cap -= bottleneck; if (!a->r_cap) { /* add i to the adoption list */ i -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = i; np -> next = orphan_first; orphan_first = np; } i = NEIGHBOR_NODE(i, a -> shift); } } i -> tr_cap += bottleneck; if (!i->tr_cap) { /* add i to the adoption list */ i -> parent = ORPHAN; np = nodeptr_block -> New(); np -> ptr = i; np -> next = orphan_first; orphan_first = np; } flow += bottleneck; }