PROC scroll(bool down) { int i; if (count <= 0) count = dofscroll; strput(CURoff); if (down) { curr = min(bufmax-1, nextline(TRUE, curr, count)); i = min(bufmax-1, nextline(TRUE, pend, count)); if (i > pend) scrollforward(i); } else { curr = bseekeol(max(0,nextline(FALSE, curr, count))); i = bseekeol(max(0,nextline(FALSE, ptop, count))); if (i < ptop) if (canUPSCROLL) scrollback(i); else { ptop = i; setend(); redisplay(TRUE); } } strput(CURon); setpos(skipws(curr)); /* initialize new position - first nonwhite */ yp = setY(curr); mvcur(yp, xp); /* go there */ }
PROC refresh(int y,int x,int start,int endd, bool rest) { int sp; #if ST /* turn the cursor off */ asm(" clr.l -(sp) "); asm(" move.w #21,-(sp) "); asm(" trap #14 "); asm(" addq.l #6,sp "); #endif sp = start; while (sp <= endd) { writeline(y, x, sp); sp = 1+fseekeol(sp); y++; x = 0; } if (rest && sp >= bufmax) while (y<LINES-1) { /* fill screen with ~ */ mvcur(y, 0); printch('~'); strput(CE); y++; } #if ST /* turn the cursor back on */ asm(" clr.w -(sp) "); asm(" move.w #1,-(sp) "); asm(" move.w #21,-(sp) "); asm(" trap #14 "); asm(" addq.l #6,sp "); #endif }
PROC writeline(int y,int x,int start) { int endd,oxp; unsigned int size; char buf[MAXCOLS+1]; unsigned int bi = 0; endd = fseekeol(start); if (start==0 || core[start-1] == EOL) mvcur(y, 0); else mvcur(y, x); oxp = curpos.x; while (start < endd && curpos.x < COLS) { size = format(&buf[bi],core[start++]); bi += size; curpos.x += size; } if (list) { buf[bi++] = '$'; curpos.x++; } size = min(bi,COLS-oxp); if (size > 0) { zwrite(buf, size); } if (curpos.x < COLS) strput(CE); }
PROC println(void) { strput("\n\r"); curpos.x = 0; curpos.y = min(curpos.y+1, LINES-1); }
PROC mvcur(int y, int x) { static char gt[30]; if (y == -1) y = curpos.y; else curpos.y = y; if (y >= LINES) y = LINES-1; if (x == -1) x = curpos.x; else curpos.x = x; if (x >= COLS) x = COLS-1; #if ZTERM zgoto(x,y); #endif #if ANSI { register char *p = gt; /* make a ansi gotoXY string */ *p++ = 033; *p++ = '['; numtoa(p,1+y); p += strlen(p); *p++ = ';'; numtoa(p,1+x); p += strlen(p); *p++ = 'H'; WRITE_TEXT(1, gt, (p-gt)); } #endif #if VT52 CM[2] = y+32; CM[3] = x+32; strput(CM); #endif #if TERMCAP tgoto(gt,y,x); strput(gt); #endif }
PROC scrollforward(int curr) { do { writeline(LINES-1, 0, pend+1); strput("\n"); pend = fseekeol(pend+1); ptop = fseekeol(ptop)+1; } while (pend < curr); }
PROC scrollback(int curr) { mvcur(0,0); /* move to the top line */ do { ptop = bseekeol(ptop-1); strput(UpS); writeline(0, 0, ptop); } while (ptop > curr); setend(); }
PROC clrprompt(void) { mvcur(LINES-1,0); strput(CE); }
static void add_import_table(void) { IMAGE_IMPORT_DESCRIPTOR ds[2], *d; char *dllname = "kernel32.dll"; struct { char *name; uint32 thunk; } *f, fs[] = { { "GetProcAddress", 0 }, { "LoadLibraryExA", 0 }, { 0, 0 } }; uint32 size = 0; memset(ds, 0, sizeof(ds)); size += sizeof(ds); ds[0].Name = size; size += strlen(dllname) + 1; for(f=fs; f->name; f++) { f->thunk = size; size += sizeof(uint16) + strlen(f->name) + 1; } ds[0].FirstThunk = size; for(f=fs; f->name; f++) size += sizeof(fs[0].thunk); IMAGE_SECTION_HEADER *isect; isect = new_section(".idata", size, 0); isect->Characteristics = IMAGE_SCN_CNT_INITIALIZED_DATA| IMAGE_SCN_MEM_READ|IMAGE_SCN_MEM_WRITE; uint32 va = isect->VirtualAddress; oh.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress = va; oh.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].Size = isect->VirtualSize; ds[0].Name += va; ds[0].FirstThunk += va; for(f=fs; f->name; f++) f->thunk += va; vlong off = seek(cout, 0, 1); seek(cout, 0, 2); for(d=ds; ; d++) { lputl(d->OriginalFirstThunk); lputl(d->TimeDateStamp); lputl(d->ForwarderChain); lputl(d->Name); lputl(d->FirstThunk); if(!d->Name) break; } strput(dllname); for(f=fs; f->name; f++) { wputl(0); strput(f->name); } for(f=fs; f->name; f++) lputl(f->thunk); strnput("", isect->SizeOfRawData - size); cflush(); seek(cout, off, 0); }
static void addimports(IMAGE_SECTION_HEADER *datsect) { IMAGE_SECTION_HEADER *isect; uvlong n, oftbase, ftbase; vlong startoff, endoff; Imp *m; Dll *d; LSym* dynamic; startoff = cpos(); dynamic = linklookup(ctxt, ".windynamic", 0); // skip import descriptor table (will write it later) n = 0; for(d = dr; d != nil; d = d->next) n++; cseek(startoff + sizeof(IMAGE_IMPORT_DESCRIPTOR) * (n + 1)); // write dll names for(d = dr; d != nil; d = d->next) { d->nameoff = cpos() - startoff; strput(d->name); } // write function names for(d = dr; d != nil; d = d->next) { for(m = d->ms; m != nil; m = m->next) { m->off = nextsectoff + cpos() - startoff; wputl(0); // hint strput(m->s->extname); } } // write OriginalFirstThunks oftbase = cpos() - startoff; n = cpos(); for(d = dr; d != nil; d = d->next) { d->thunkoff = cpos() - n; for(m = d->ms; m != nil; m = m->next) put(m->off); put(0); } // add pe section and pad it at the end n = cpos() - startoff; isect = addpesection(".idata", n, n); isect->Characteristics = IMAGE_SCN_CNT_INITIALIZED_DATA| IMAGE_SCN_MEM_READ|IMAGE_SCN_MEM_WRITE; chksectoff(isect, startoff); strnput("", isect->SizeOfRawData - n); endoff = cpos(); // write FirstThunks (allocated in .data section) ftbase = dynamic->value - datsect->VirtualAddress - PEBASE; cseek(datsect->PointerToRawData + ftbase); for(d = dr; d != nil; d = d->next) { for(m = d->ms; m != nil; m = m->next) put(m->off); put(0); } // finally write import descriptor table cseek(startoff); for(d = dr; d != nil; d = d->next) { lputl(isect->VirtualAddress + oftbase + d->thunkoff); lputl(0); lputl(0); lputl(isect->VirtualAddress + d->nameoff); lputl(datsect->VirtualAddress + ftbase + d->thunkoff); } lputl(0); //end lputl(0); lputl(0); lputl(0); lputl(0); // update data directory dd[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress = isect->VirtualAddress; dd[IMAGE_DIRECTORY_ENTRY_IMPORT].Size = isect->VirtualSize; dd[IMAGE_DIRECTORY_ENTRY_IAT].VirtualAddress = dynamic->value - PEBASE; dd[IMAGE_DIRECTORY_ENTRY_IAT].Size = dynamic->size; cseek(endoff); }