1*8ccd4a63SDavid du Colombier #include <windows.h> 2*8ccd4a63SDavid du Colombier #include "u.h" 3*8ccd4a63SDavid du Colombier #include "lib.h" 4*8ccd4a63SDavid du Colombier #include "dat.h" 5*8ccd4a63SDavid du Colombier #include "fns.h" 6*8ccd4a63SDavid du Colombier #include <libsec.h> 7*8ccd4a63SDavid du Colombier 8*8ccd4a63SDavid du Colombier typedef struct Oproc Oproc; 9*8ccd4a63SDavid du Colombier struct Oproc { 10*8ccd4a63SDavid du Colombier int tid; 11*8ccd4a63SDavid du Colombier HANDLE *sema; 12*8ccd4a63SDavid du Colombier }; 13*8ccd4a63SDavid du Colombier 14*8ccd4a63SDavid du Colombier static int tlsx = TLS_OUT_OF_INDEXES; 15*8ccd4a63SDavid du Colombier 16*8ccd4a63SDavid du Colombier char *argv0; 17*8ccd4a63SDavid du Colombier 18*8ccd4a63SDavid du Colombier Proc* 19*8ccd4a63SDavid du Colombier _getproc(void) 20*8ccd4a63SDavid du Colombier { 21*8ccd4a63SDavid du Colombier if(tlsx == TLS_OUT_OF_INDEXES) 22*8ccd4a63SDavid du Colombier return nil; 23*8ccd4a63SDavid du Colombier return TlsGetValue(tlsx); 24*8ccd4a63SDavid du Colombier } 25*8ccd4a63SDavid du Colombier 26*8ccd4a63SDavid du Colombier void 27*8ccd4a63SDavid du Colombier _setproc(Proc *p) 28*8ccd4a63SDavid du Colombier { 29*8ccd4a63SDavid du Colombier if(tlsx == TLS_OUT_OF_INDEXES){ 30*8ccd4a63SDavid du Colombier tlsx = TlsAlloc(); 31*8ccd4a63SDavid du Colombier if(tlsx == TLS_OUT_OF_INDEXES) 32*8ccd4a63SDavid du Colombier panic("out of indexes"); 33*8ccd4a63SDavid du Colombier } 34*8ccd4a63SDavid du Colombier TlsSetValue(tlsx, p); 35*8ccd4a63SDavid du Colombier } 36*8ccd4a63SDavid du Colombier 37*8ccd4a63SDavid du Colombier void 38*8ccd4a63SDavid du Colombier oserror(void) 39*8ccd4a63SDavid du Colombier { 40*8ccd4a63SDavid du Colombier oserrstr(); 41*8ccd4a63SDavid du Colombier nexterror(); 42*8ccd4a63SDavid du Colombier } 43*8ccd4a63SDavid du Colombier 44*8ccd4a63SDavid du Colombier void 45*8ccd4a63SDavid du Colombier osinit(void) 46*8ccd4a63SDavid du Colombier { 47*8ccd4a63SDavid du Colombier Oproc *t; 48*8ccd4a63SDavid du Colombier static Proc firstprocCTstore; 49*8ccd4a63SDavid du Colombier 50*8ccd4a63SDavid du Colombier _setproc(&firstprocCTstore); 51*8ccd4a63SDavid du Colombier t = (Oproc*)firstprocCTstore.oproc; 52*8ccd4a63SDavid du Colombier assert(t != 0); 53*8ccd4a63SDavid du Colombier 54*8ccd4a63SDavid du Colombier t->tid = GetCurrentThreadId(); 55*8ccd4a63SDavid du Colombier t->sema = CreateSemaphore(0, 0, 1000, 0); 56*8ccd4a63SDavid du Colombier if(t->sema == 0) { 57*8ccd4a63SDavid du Colombier oserror(); 58*8ccd4a63SDavid du Colombier panic("could not create semaphore: %r"); 59*8ccd4a63SDavid du Colombier } 60*8ccd4a63SDavid du Colombier } 61*8ccd4a63SDavid du Colombier 62*8ccd4a63SDavid du Colombier void 63*8ccd4a63SDavid du Colombier osnewproc(Proc *p) 64*8ccd4a63SDavid du Colombier { 65*8ccd4a63SDavid du Colombier Oproc *op; 66*8ccd4a63SDavid du Colombier 67*8ccd4a63SDavid du Colombier op = (Oproc*)p->oproc; 68*8ccd4a63SDavid du Colombier op->sema = CreateSemaphore(0, 0, 1000, 0); 69*8ccd4a63SDavid du Colombier if (op->sema == 0) { 70*8ccd4a63SDavid du Colombier oserror(); 71*8ccd4a63SDavid du Colombier panic("could not create semaphore: %r"); 72*8ccd4a63SDavid du Colombier } 73*8ccd4a63SDavid du Colombier } 74*8ccd4a63SDavid du Colombier 75*8ccd4a63SDavid du Colombier void 76*8ccd4a63SDavid du Colombier osmsleep(int ms) 77*8ccd4a63SDavid du Colombier { 78*8ccd4a63SDavid du Colombier Sleep((DWORD) ms); 79*8ccd4a63SDavid du Colombier } 80*8ccd4a63SDavid du Colombier 81*8ccd4a63SDavid du Colombier void 82*8ccd4a63SDavid du Colombier osyield(void) 83*8ccd4a63SDavid du Colombier { 84*8ccd4a63SDavid du Colombier Sleep(0); 85*8ccd4a63SDavid du Colombier } 86*8ccd4a63SDavid du Colombier 87*8ccd4a63SDavid du Colombier static DWORD WINAPI tramp(LPVOID vp); 88*8ccd4a63SDavid du Colombier 89*8ccd4a63SDavid du Colombier void 90*8ccd4a63SDavid du Colombier osproc(Proc *p) 91*8ccd4a63SDavid du Colombier { 92*8ccd4a63SDavid du Colombier DWORD tid; 93*8ccd4a63SDavid du Colombier 94*8ccd4a63SDavid du Colombier if(CreateThread(0, 0, tramp, p, 0, &tid) == 0) { 95*8ccd4a63SDavid du Colombier oserror(); 96*8ccd4a63SDavid du Colombier panic("osproc: %r"); 97*8ccd4a63SDavid du Colombier } 98*8ccd4a63SDavid du Colombier 99*8ccd4a63SDavid du Colombier Sleep(0); 100*8ccd4a63SDavid du Colombier } 101*8ccd4a63SDavid du Colombier 102*8ccd4a63SDavid du Colombier static DWORD WINAPI 103*8ccd4a63SDavid du Colombier tramp(LPVOID vp) 104*8ccd4a63SDavid du Colombier { 105*8ccd4a63SDavid du Colombier Proc *p = (Proc *) vp; 106*8ccd4a63SDavid du Colombier Oproc *op = (Oproc*) p->oproc; 107*8ccd4a63SDavid du Colombier 108*8ccd4a63SDavid du Colombier _setproc(p); 109*8ccd4a63SDavid du Colombier op->tid = GetCurrentThreadId(); 110*8ccd4a63SDavid du Colombier op->sema = CreateSemaphore(0, 0, 1000, 0); 111*8ccd4a63SDavid du Colombier if(op->sema == 0) { 112*8ccd4a63SDavid du Colombier oserror(); 113*8ccd4a63SDavid du Colombier panic("could not create semaphore: %r"); 114*8ccd4a63SDavid du Colombier } 115*8ccd4a63SDavid du Colombier 116*8ccd4a63SDavid du Colombier (*p->fn)(p->arg); 117*8ccd4a63SDavid du Colombier ExitThread(0); 118*8ccd4a63SDavid du Colombier return 0; 119*8ccd4a63SDavid du Colombier } 120*8ccd4a63SDavid du Colombier 121*8ccd4a63SDavid du Colombier void 122*8ccd4a63SDavid du Colombier procsleep(void) 123*8ccd4a63SDavid du Colombier { 124*8ccd4a63SDavid du Colombier Proc *p; 125*8ccd4a63SDavid du Colombier Oproc *op; 126*8ccd4a63SDavid du Colombier 127*8ccd4a63SDavid du Colombier p = up; 128*8ccd4a63SDavid du Colombier op = (Oproc*)p->oproc; 129*8ccd4a63SDavid du Colombier WaitForSingleObject(op->sema, INFINITE);} 130*8ccd4a63SDavid du Colombier 131*8ccd4a63SDavid du Colombier void 132*8ccd4a63SDavid du Colombier procwakeup(Proc *p) 133*8ccd4a63SDavid du Colombier { 134*8ccd4a63SDavid du Colombier Oproc *op; 135*8ccd4a63SDavid du Colombier 136*8ccd4a63SDavid du Colombier op = (Oproc*)p->oproc; 137*8ccd4a63SDavid du Colombier ReleaseSemaphore(op->sema, 1, 0); 138*8ccd4a63SDavid du Colombier } 139*8ccd4a63SDavid du Colombier 140*8ccd4a63SDavid du Colombier void 141*8ccd4a63SDavid du Colombier random20(uchar *p) 142*8ccd4a63SDavid du Colombier { 143*8ccd4a63SDavid du Colombier LARGE_INTEGER ti; 144*8ccd4a63SDavid du Colombier int i, j; 145*8ccd4a63SDavid du Colombier FILETIME ft; 146*8ccd4a63SDavid du Colombier DigestState ds; 147*8ccd4a63SDavid du Colombier vlong tsc; 148*8ccd4a63SDavid du Colombier 149*8ccd4a63SDavid du Colombier GetSystemTimeAsFileTime(&ft); 150*8ccd4a63SDavid du Colombier memset(&ds, 0, sizeof ds); 151*8ccd4a63SDavid du Colombier sha1((uchar*)&ft, sizeof(ft), 0, &ds); 152*8ccd4a63SDavid du Colombier for(i=0; i<50; i++) { 153*8ccd4a63SDavid du Colombier for(j=0; j<10; j++) { 154*8ccd4a63SDavid du Colombier QueryPerformanceCounter(&ti); 155*8ccd4a63SDavid du Colombier sha1((uchar*)&ti, sizeof(ti), 0, &ds); 156*8ccd4a63SDavid du Colombier tsc = GetTickCount(); 157*8ccd4a63SDavid du Colombier sha1((uchar*)&tsc, sizeof(tsc), 0, &ds); 158*8ccd4a63SDavid du Colombier } 159*8ccd4a63SDavid du Colombier Sleep(10); 160*8ccd4a63SDavid du Colombier } 161*8ccd4a63SDavid du Colombier sha1(0, 0, p, &ds); 162*8ccd4a63SDavid du Colombier } 163*8ccd4a63SDavid du Colombier 164*8ccd4a63SDavid du Colombier void 165*8ccd4a63SDavid du Colombier randominit(void) 166*8ccd4a63SDavid du Colombier { 167*8ccd4a63SDavid du Colombier } 168*8ccd4a63SDavid du Colombier 169*8ccd4a63SDavid du Colombier ulong 170*8ccd4a63SDavid du Colombier randomread(void *v, ulong n) 171*8ccd4a63SDavid du Colombier { 172*8ccd4a63SDavid du Colombier int i; 173*8ccd4a63SDavid du Colombier uchar p[20]; 174*8ccd4a63SDavid du Colombier 175*8ccd4a63SDavid du Colombier for(i=0; i<n; i+=20){ 176*8ccd4a63SDavid du Colombier random20(p); 177*8ccd4a63SDavid du Colombier if(i+20 <= n) 178*8ccd4a63SDavid du Colombier memmove((char*)v+i, p, 20); 179*8ccd4a63SDavid du Colombier else 180*8ccd4a63SDavid du Colombier memmove((char*)v+i, p, n-i); 181*8ccd4a63SDavid du Colombier } 182*8ccd4a63SDavid du Colombier return n; 183*8ccd4a63SDavid du Colombier } 184*8ccd4a63SDavid du Colombier 185*8ccd4a63SDavid du Colombier long 186*8ccd4a63SDavid du Colombier seconds(void) 187*8ccd4a63SDavid du Colombier { 188*8ccd4a63SDavid du Colombier return time(0); 189*8ccd4a63SDavid du Colombier } 190*8ccd4a63SDavid du Colombier 191*8ccd4a63SDavid du Colombier ulong 192*8ccd4a63SDavid du Colombier ticks(void) 193*8ccd4a63SDavid du Colombier { 194*8ccd4a63SDavid du Colombier return GetTickCount(); 195*8ccd4a63SDavid du Colombier } 196*8ccd4a63SDavid du Colombier 197*8ccd4a63SDavid du Colombier #if 0 198*8ccd4a63SDavid du Colombier uvlong 199*8ccd4a63SDavid du Colombier fastticks(uvlong *v) 200*8ccd4a63SDavid du Colombier { 201*8ccd4a63SDavid du Colombier uvlong n; 202*8ccd4a63SDavid du Colombier 203*8ccd4a63SDavid du Colombier n = GetTickCount() * 1000 * 1000; 204*8ccd4a63SDavid du Colombier if(v) 205*8ccd4a63SDavid du Colombier *v = n; 206*8ccd4a63SDavid du Colombier return n; 207*8ccd4a63SDavid du Colombier } 208*8ccd4a63SDavid du Colombier #endif 209*8ccd4a63SDavid du Colombier 210*8ccd4a63SDavid du Colombier extern int main(int, char*[]); 211*8ccd4a63SDavid du Colombier 212*8ccd4a63SDavid du Colombier 213*8ccd4a63SDavid du Colombier int 214*8ccd4a63SDavid du Colombier wstrutflen(Rune *s) 215*8ccd4a63SDavid du Colombier { 216*8ccd4a63SDavid du Colombier int n; 217*8ccd4a63SDavid du Colombier 218*8ccd4a63SDavid du Colombier for(n=0; *s; n+=runelen(*s),s++) 219*8ccd4a63SDavid du Colombier ; 220*8ccd4a63SDavid du Colombier return n; 221*8ccd4a63SDavid du Colombier } 222*8ccd4a63SDavid du Colombier 223*8ccd4a63SDavid du Colombier int 224*8ccd4a63SDavid du Colombier wstrtoutf(char *s, Rune *t, int n) 225*8ccd4a63SDavid du Colombier { 226*8ccd4a63SDavid du Colombier int i; 227*8ccd4a63SDavid du Colombier char *s0; 228*8ccd4a63SDavid du Colombier 229*8ccd4a63SDavid du Colombier s0 = s; 230*8ccd4a63SDavid du Colombier if(n <= 0) 231*8ccd4a63SDavid du Colombier return wstrutflen(t)+1; 232*8ccd4a63SDavid du Colombier while(*t) { 233*8ccd4a63SDavid du Colombier if(n < UTFmax+1 && n < runelen(*t)+1) { 234*8ccd4a63SDavid du Colombier *s = 0; 235*8ccd4a63SDavid du Colombier return s-s0+wstrutflen(t)+1; 236*8ccd4a63SDavid du Colombier } 237*8ccd4a63SDavid du Colombier i = runetochar(s, t); 238*8ccd4a63SDavid du Colombier s += i; 239*8ccd4a63SDavid du Colombier n -= i; 240*8ccd4a63SDavid du Colombier t++; 241*8ccd4a63SDavid du Colombier } 242*8ccd4a63SDavid du Colombier *s = 0; 243*8ccd4a63SDavid du Colombier return s-s0; 244*8ccd4a63SDavid du Colombier } 245*8ccd4a63SDavid du Colombier 246*8ccd4a63SDavid du Colombier int 247*8ccd4a63SDavid du Colombier win_hasunicode(void) 248*8ccd4a63SDavid du Colombier { 249*8ccd4a63SDavid du Colombier OSVERSIONINFOA osinfo; 250*8ccd4a63SDavid du Colombier int r; 251*8ccd4a63SDavid du Colombier 252*8ccd4a63SDavid du Colombier osinfo.dwOSVersionInfoSize = sizeof(osinfo); 253*8ccd4a63SDavid du Colombier if(!GetVersionExA(&osinfo)) 254*8ccd4a63SDavid du Colombier panic("GetVersionEx failed"); 255*8ccd4a63SDavid du Colombier switch(osinfo.dwPlatformId) { 256*8ccd4a63SDavid du Colombier default: 257*8ccd4a63SDavid du Colombier panic("unknown PlatformId"); 258*8ccd4a63SDavid du Colombier case VER_PLATFORM_WIN32s: 259*8ccd4a63SDavid du Colombier panic("Win32s not supported"); 260*8ccd4a63SDavid du Colombier case VER_PLATFORM_WIN32_WINDOWS: 261*8ccd4a63SDavid du Colombier r = 0; 262*8ccd4a63SDavid du Colombier break; 263*8ccd4a63SDavid du Colombier case VER_PLATFORM_WIN32_NT: 264*8ccd4a63SDavid du Colombier r = 1; 265*8ccd4a63SDavid du Colombier break; 266*8ccd4a63SDavid du Colombier } 267*8ccd4a63SDavid du Colombier 268*8ccd4a63SDavid du Colombier return r; 269*8ccd4a63SDavid du Colombier } 270*8ccd4a63SDavid du Colombier 271*8ccd4a63SDavid du Colombier int 272*8ccd4a63SDavid du Colombier wstrlen(Rune *s) 273*8ccd4a63SDavid du Colombier { 274*8ccd4a63SDavid du Colombier int n; 275*8ccd4a63SDavid du Colombier 276*8ccd4a63SDavid du Colombier for(n=0; *s; s++,n++) 277*8ccd4a63SDavid du Colombier ; 278*8ccd4a63SDavid du Colombier return n; 279*8ccd4a63SDavid du Colombier } 280*8ccd4a63SDavid du Colombier static int args(char *argv[], int n, char *p); 281*8ccd4a63SDavid du Colombier 282*8ccd4a63SDavid du Colombier int APIENTRY 283*8ccd4a63SDavid du Colombier WinMain(HINSTANCE x, HINSTANCE y, LPSTR z, int w) 284*8ccd4a63SDavid du Colombier { 285*8ccd4a63SDavid du Colombier int argc, n; 286*8ccd4a63SDavid du Colombier char *arg, *p, **argv; 287*8ccd4a63SDavid du Colombier Rune *warg; 288*8ccd4a63SDavid du Colombier 289*8ccd4a63SDavid du Colombier if(0 && win_hasunicode()){ 290*8ccd4a63SDavid du Colombier warg = GetCommandLineW(); 291*8ccd4a63SDavid du Colombier n = (wstrlen(warg)+1)*UTFmax; 292*8ccd4a63SDavid du Colombier arg = malloc(n); 293*8ccd4a63SDavid du Colombier wstrtoutf(arg, warg, n); 294*8ccd4a63SDavid du Colombier }else 295*8ccd4a63SDavid du Colombier arg = GetCommandLineA(); 296*8ccd4a63SDavid du Colombier 297*8ccd4a63SDavid du Colombier /* conservative guess at the number of args */ 298*8ccd4a63SDavid du Colombier for(argc=4,p=arg; *p; p++) 299*8ccd4a63SDavid du Colombier if(*p == ' ' || *p == '\t') 300*8ccd4a63SDavid du Colombier argc++; 301*8ccd4a63SDavid du Colombier argv = malloc(argc*sizeof(char*)); 302*8ccd4a63SDavid du Colombier argc = args(argv, argc, arg); 303*8ccd4a63SDavid du Colombier 304*8ccd4a63SDavid du Colombier mymain(argc, argv); 305*8ccd4a63SDavid du Colombier ExitThread(0); 306*8ccd4a63SDavid du Colombier return 0; 307*8ccd4a63SDavid du Colombier } 308*8ccd4a63SDavid du Colombier 309*8ccd4a63SDavid du Colombier /* 310*8ccd4a63SDavid du Colombier * Break the command line into arguments 311*8ccd4a63SDavid du Colombier * The rules for this are not documented but appear to be the following 312*8ccd4a63SDavid du Colombier * according to the source for the microsoft C library. 313*8ccd4a63SDavid du Colombier * Words are seperated by space or tab 314*8ccd4a63SDavid du Colombier * Words containing a space or tab can be quoted using " 315*8ccd4a63SDavid du Colombier * 2N backslashes + " ==> N backslashes and end quote 316*8ccd4a63SDavid du Colombier * 2N+1 backslashes + " ==> N backslashes + literal " 317*8ccd4a63SDavid du Colombier * N backslashes not followed by " ==> N backslashes 318*8ccd4a63SDavid du Colombier */ 319*8ccd4a63SDavid du Colombier static int 320*8ccd4a63SDavid du Colombier args(char *argv[], int n, char *p) 321*8ccd4a63SDavid du Colombier { 322*8ccd4a63SDavid du Colombier char *p2; 323*8ccd4a63SDavid du Colombier int i, j, quote, nbs; 324*8ccd4a63SDavid du Colombier 325*8ccd4a63SDavid du Colombier for(i=0; *p && i<n-1; i++) { 326*8ccd4a63SDavid du Colombier while(*p == ' ' || *p == '\t') 327*8ccd4a63SDavid du Colombier p++; 328*8ccd4a63SDavid du Colombier quote = 0; 329*8ccd4a63SDavid du Colombier argv[i] = p2 = p; 330*8ccd4a63SDavid du Colombier for(;*p; p++) { 331*8ccd4a63SDavid du Colombier if(!quote && (*p == ' ' || *p == '\t')) 332*8ccd4a63SDavid du Colombier break; 333*8ccd4a63SDavid du Colombier for(nbs=0; *p == '\\'; p++,nbs++) 334*8ccd4a63SDavid du Colombier ; 335*8ccd4a63SDavid du Colombier if(*p == '"') { 336*8ccd4a63SDavid du Colombier for(j=0; j<(nbs>>1); j++) 337*8ccd4a63SDavid du Colombier *p2++ = '\\'; 338*8ccd4a63SDavid du Colombier if(nbs&1) 339*8ccd4a63SDavid du Colombier *p2++ = *p; 340*8ccd4a63SDavid du Colombier else 341*8ccd4a63SDavid du Colombier quote = !quote; 342*8ccd4a63SDavid du Colombier } else { 343*8ccd4a63SDavid du Colombier for(j=0; j<nbs; j++) 344*8ccd4a63SDavid du Colombier *p2++ = '\\'; 345*8ccd4a63SDavid du Colombier *p2++ = *p; 346*8ccd4a63SDavid du Colombier } 347*8ccd4a63SDavid du Colombier } 348*8ccd4a63SDavid du Colombier /* move p up one to avoid pointing to null at end of p2 */ 349*8ccd4a63SDavid du Colombier if(*p) 350*8ccd4a63SDavid du Colombier p++; 351*8ccd4a63SDavid du Colombier *p2 = 0; 352*8ccd4a63SDavid du Colombier } 353*8ccd4a63SDavid du Colombier argv[i] = 0; 354*8ccd4a63SDavid du Colombier 355*8ccd4a63SDavid du Colombier return i; 356*8ccd4a63SDavid du Colombier } 357*8ccd4a63SDavid du Colombier /* 358*8ccd4a63SDavid du Colombier * Windows socket error messages 359*8ccd4a63SDavid du Colombier * There must be a way to get these strings out of the library. 360*8ccd4a63SDavid du Colombier * This table is derived from the MSDN online help. 361*8ccd4a63SDavid du Colombier */ 362*8ccd4a63SDavid du Colombier static struct { 363*8ccd4a63SDavid du Colombier int e; 364*8ccd4a63SDavid du Colombier char *s; 365*8ccd4a63SDavid du Colombier } tab[] = { 366*8ccd4a63SDavid du Colombier { 10004, "interrupted function call" }, 367*8ccd4a63SDavid du Colombier { 10013, "permission denied" }, 368*8ccd4a63SDavid du Colombier { 10014, "bad address" }, 369*8ccd4a63SDavid du Colombier { 10022, "invalid argument" }, 370*8ccd4a63SDavid du Colombier { 10024, "too many open files" }, 371*8ccd4a63SDavid du Colombier { 10035, "resource temporarily unavailable" }, 372*8ccd4a63SDavid du Colombier { 10036, "operation now in progress" }, 373*8ccd4a63SDavid du Colombier { 10037, "operation already in progress" }, 374*8ccd4a63SDavid du Colombier { 10038, "socket operation on nonsocket" }, 375*8ccd4a63SDavid du Colombier { 10039, "destination address required" }, 376*8ccd4a63SDavid du Colombier { 10040, "message too long" }, 377*8ccd4a63SDavid du Colombier { 10041, "protocol wrong type for socket" }, 378*8ccd4a63SDavid du Colombier { 10042, "bad protocol option" }, 379*8ccd4a63SDavid du Colombier { 10043, "protocol not supported" }, 380*8ccd4a63SDavid du Colombier { 10044, "socket type not supported" }, 381*8ccd4a63SDavid du Colombier { 10045, "operation not supported" }, 382*8ccd4a63SDavid du Colombier { 10046, "protocol family not supported" }, 383*8ccd4a63SDavid du Colombier { 10047, "address family not supported by protocol family" }, 384*8ccd4a63SDavid du Colombier { 10048, "address already in use" }, 385*8ccd4a63SDavid du Colombier { 10049, "cannot assign requested address" }, 386*8ccd4a63SDavid du Colombier { 10050, "network is down" }, 387*8ccd4a63SDavid du Colombier { 10051, "network is unreachable" }, 388*8ccd4a63SDavid du Colombier { 10052, "network dropped connection on reset" }, 389*8ccd4a63SDavid du Colombier { 10053, "software caused connection abort" }, 390*8ccd4a63SDavid du Colombier { 10054, "connection reset by peer" }, 391*8ccd4a63SDavid du Colombier { 10055, "no buffer space available" }, 392*8ccd4a63SDavid du Colombier { 10056, "socket is already connected" }, 393*8ccd4a63SDavid du Colombier { 10057, "socket is not connected" }, 394*8ccd4a63SDavid du Colombier { 10058, "cannot send after socket shutdown" }, 395*8ccd4a63SDavid du Colombier { 10060, "connection timed out" }, 396*8ccd4a63SDavid du Colombier { 10061, "connection refused" }, 397*8ccd4a63SDavid du Colombier { 10064, "host is down" }, 398*8ccd4a63SDavid du Colombier { 10065, "no route to host" }, 399*8ccd4a63SDavid du Colombier { 10067, "too many processes" }, 400*8ccd4a63SDavid du Colombier { 10091, "network subsystem is unavailable" }, 401*8ccd4a63SDavid du Colombier { 10092, "winsock.dll version out of range" }, 402*8ccd4a63SDavid du Colombier { 10093, "wsastartup not called" }, 403*8ccd4a63SDavid du Colombier { 10101, "graceful shutdown in progress" }, 404*8ccd4a63SDavid du Colombier { 10109, "class type not found" }, 405*8ccd4a63SDavid du Colombier { 11001, "host name not found" }, 406*8ccd4a63SDavid du Colombier { 11002, "host not found (non-authoritative)" }, 407*8ccd4a63SDavid du Colombier { 11003, "nonrecoverable error" }, 408*8ccd4a63SDavid du Colombier { 11004, "valid name, but no data record of requested type" }, 409*8ccd4a63SDavid du Colombier }; 410*8ccd4a63SDavid du Colombier 411*8ccd4a63SDavid du Colombier void 412*8ccd4a63SDavid du Colombier osrerrstr(char *buf, uint nbuf) 413*8ccd4a63SDavid du Colombier { 414*8ccd4a63SDavid du Colombier char *p, *q; 415*8ccd4a63SDavid du Colombier int e, i, r; 416*8ccd4a63SDavid du Colombier 417*8ccd4a63SDavid du Colombier e = GetLastError(); 418*8ccd4a63SDavid du Colombier r = FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM, 419*8ccd4a63SDavid du Colombier 0, e, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), 420*8ccd4a63SDavid du Colombier buf, nbuf, 0); 421*8ccd4a63SDavid du Colombier if(r == 0){ 422*8ccd4a63SDavid du Colombier for(i=0; i<nelem(tab); i++) 423*8ccd4a63SDavid du Colombier if(tab[i].e == e){ 424*8ccd4a63SDavid du Colombier strecpy(buf, buf+nbuf, tab[i].s); 425*8ccd4a63SDavid du Colombier break; 426*8ccd4a63SDavid du Colombier } 427*8ccd4a63SDavid du Colombier if(i==nelem(tab)) 428*8ccd4a63SDavid du Colombier snprint(buf, nbuf, "windows error %d", e); 429*8ccd4a63SDavid du Colombier } 430*8ccd4a63SDavid du Colombier 431*8ccd4a63SDavid du Colombier for(p=q=buf; *p; p++) { 432*8ccd4a63SDavid du Colombier if(*p == '\r') 433*8ccd4a63SDavid du Colombier continue; 434*8ccd4a63SDavid du Colombier if(*p == '\n') 435*8ccd4a63SDavid du Colombier *q++ = ' '; 436*8ccd4a63SDavid du Colombier else 437*8ccd4a63SDavid du Colombier *q++ = *p; 438*8ccd4a63SDavid du Colombier } 439*8ccd4a63SDavid du Colombier *q = '\0'; 440*8ccd4a63SDavid du Colombier } 441*8ccd4a63SDavid du Colombier 442*8ccd4a63SDavid du Colombier void 443*8ccd4a63SDavid du Colombier oserrstr(void) 444*8ccd4a63SDavid du Colombier { 445*8ccd4a63SDavid du Colombier osrerrstr(up->errstr, ERRMAX); 446*8ccd4a63SDavid du Colombier } 447