📄 dolist.c
字号:
len = 16; checksum = len; culong = 0; cdouble = 0; if (pat < patend) goto reparse; break; case '@': if (len > strend - strbeg) fatal("@ outside of string"); s = strbeg + len; break; case 'X': if (len > s - strbeg) fatal("X outside of string"); s -= len; break; case 'x': if (len > strend - s) fatal("x outside of string"); s += len; break; case 'A': case 'a': if (len > strend - s) len = strend - s; if (checksum) goto uchar_checksum; str = Str_new(35,len); str_nset(str,s,len); s += len; if (datumtype == 'A') { aptr = s; /* borrow register */ s = str->str_ptr + len - 1; while (s >= str->str_ptr && (!*s || isSPACE(*s))) s--; *++s = '\0'; str->str_cur = s - str->str_ptr; s = aptr; /* unborrow register */ } (void)astore(stack, ++sp, str_2mortal(str)); break; case 'B': case 'b': if (pat[-1] == '*' || len > (strend - s) * 8) len = (strend - s) * 8; str = Str_new(35, len + 1); str->str_cur = len; str->str_pok = 1; aptr = pat; /* borrow register */ pat = str->str_ptr; if (datumtype == 'b') { aint = len; for (len = 0; len < aint; len++) { if (len & 7) /*SUPPRESS 595*/ bits >>= 1; else bits = *s++; *pat++ = '0' + (bits & 1); } } else { aint = len; for (len = 0; len < aint; len++) { if (len & 7) bits <<= 1; else bits = *s++; *pat++ = '0' + ((bits & 128) != 0); } } *pat = '\0'; pat = aptr; /* unborrow register */ (void)astore(stack, ++sp, str_2mortal(str)); break; case 'H': case 'h': if (pat[-1] == '*' || len > (strend - s) * 2) len = (strend - s) * 2; str = Str_new(35, len + 1); str->str_cur = len; str->str_pok = 1; aptr = pat; /* borrow register */ pat = str->str_ptr; if (datumtype == 'h') { aint = len; for (len = 0; len < aint; len++) { if (len & 1) bits >>= 4; else bits = *s++; *pat++ = hexdigit[bits & 15]; } } else { aint = len; for (len = 0; len < aint; len++) { if (len & 1) bits <<= 4; else bits = *s++; *pat++ = hexdigit[(bits >> 4) & 15]; } } *pat = '\0'; pat = aptr; /* unborrow register */ (void)astore(stack, ++sp, str_2mortal(str)); break; case 'c': if (len > strend - s) len = strend - s; if (checksum) { while (len-- > 0) { aint = *s++; if (aint >= 128) /* fake up signed chars */ aint -= 256; culong += aint; } } else { while (len-- > 0) { aint = *s++; if (aint >= 128) /* fake up signed chars */ aint -= 256; str = Str_new(36,0); str_numset(str,(double)aint); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'C': if (len > strend - s) len = strend - s; if (checksum) { uchar_checksum: while (len-- > 0) { auint = *s++ & 255; culong += auint; } } else { while (len-- > 0) { auint = *s++ & 255; str = Str_new(37,0); str_numset(str,(double)auint); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 's': along = (strend - s) / sizeof(short); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s,&ashort,1,short); s += sizeof(short); culong += ashort; } } else { while (len-- > 0) { Copy(s,&ashort,1,short); s += sizeof(short); str = Str_new(38,0); str_numset(str,(double)ashort); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'v': case 'n': case 'S': along = (strend - s) / sizeof(unsigned short); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s,&aushort,1,unsigned short); s += sizeof(unsigned short);#ifdef HAS_NTOHS if (datumtype == 'n') aushort = ntohs(aushort);#endif#ifdef HAS_VTOHS if (datumtype == 'v') aushort = vtohs(aushort);#endif culong += aushort; } } else { while (len-- > 0) { Copy(s,&aushort,1,unsigned short); s += sizeof(unsigned short); str = Str_new(39,0);#ifdef HAS_NTOHS if (datumtype == 'n') aushort = ntohs(aushort);#endif#ifdef HAS_VTOHS if (datumtype == 'v') aushort = vtohs(aushort);#endif str_numset(str,(double)aushort); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'i': along = (strend - s) / sizeof(int); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s,&aint,1,int); s += sizeof(int); if (checksum > 32) cdouble += (double)aint; else culong += aint; } } else { while (len-- > 0) { Copy(s,&aint,1,int); s += sizeof(int); str = Str_new(40,0); str_numset(str,(double)aint); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'I': along = (strend - s) / sizeof(unsigned int); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s,&auint,1,unsigned int); s += sizeof(unsigned int); if (checksum > 32) cdouble += (double)auint; else culong += auint; } } else { while (len-- > 0) { Copy(s,&auint,1,unsigned int); s += sizeof(unsigned int); str = Str_new(41,0); str_numset(str,(double)auint); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'l': along = (strend - s) / sizeof(long); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s,&along,1,long); s += sizeof(long); if (checksum > 32) cdouble += (double)along; else culong += along; } } else { while (len-- > 0) { Copy(s,&along,1,long); s += sizeof(long); str = Str_new(42,0); str_numset(str,(double)along); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'V': case 'N': case 'L': along = (strend - s) / sizeof(unsigned long); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s,&aulong,1,unsigned long); s += sizeof(unsigned long);#ifdef HAS_NTOHL if (datumtype == 'N') aulong = ntohl(aulong);#endif#ifdef HAS_VTOHL if (datumtype == 'V') aulong = vtohl(aulong);#endif if (checksum > 32) cdouble += (double)aulong; else culong += aulong; } } else { while (len-- > 0) { Copy(s,&aulong,1,unsigned long); s += sizeof(unsigned long); str = Str_new(43,0);#ifdef HAS_NTOHL if (datumtype == 'N') aulong = ntohl(aulong);#endif#ifdef HAS_VTOHL if (datumtype == 'V') aulong = vtohl(aulong);#endif str_numset(str,(double)aulong); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'p': along = (strend - s) / sizeof(char*); if (len > along) len = along; while (len-- > 0) { if (sizeof(char*) > strend - s) break; else { Copy(s,&aptr,1,char*); s += sizeof(char*); } str = Str_new(44,0); if (aptr) str_set(str,aptr); (void)astore(stack, ++sp, str_2mortal(str)); } break;#ifdef QUAD case 'q': while (len-- > 0) { if (s + sizeof(quad) > strend) aquad = 0; else { Copy(s,&aquad,1,quad); s += sizeof(quad); } str = Str_new(42,0); str_numset(str,(double)aquad); (void)astore(stack, ++sp, str_2mortal(str)); } break; case 'Q': while (len-- > 0) { if (s + sizeof(unsigned quad) > strend) auquad = 0; else { Copy(s,&auquad,1,unsigned quad); s += sizeof(unsigned quad); } str = Str_new(43,0); str_numset(str,(double)auquad); (void)astore(stack, ++sp, str_2mortal(str)); } break;#endif /* float and double added gnb@melba.bby.oz.au 22/11/89 */ case 'f': case 'F': along = (strend - s) / sizeof(float); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s, &afloat,1, float); s += sizeof(float); cdouble += afloat; } } else { while (len-- > 0) { Copy(s, &afloat,1, float); s += sizeof(float); str = Str_new(47, 0); str_numset(str, (double)afloat); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'd': case 'D': along = (strend - s) / sizeof(double); if (len > along) len = along; if (checksum) { while (len-- > 0) { Copy(s, &adouble,1, double); s += sizeof(double); cdouble += adouble; } } else { while (len-- > 0) { Copy(s, &adouble,1, double); s += sizeof(double); str = Str_new(48, 0); str_numset(str, (double)adouble); (void)astore(stack, ++sp, str_2mortal(str)); } } break; case 'u': along = (strend - s) * 3 / 4; str = Str_new(42,along); while (s < strend && *s > ' ' && *s < 'a') { int a,b,c,d; char hunk[4]; hunk[3] = '\0'; len = (*s++ - ' ') & 077; while (len > 0) { if (s < strend && *s >= ' ') a = (*s++ - ' ') & 077; else a = 0; if (s < strend && *s >= ' ') b = (*s++ - ' ') & 077; else b = 0; if (s < strend && *s >= ' ') c = (*s++ - ' ') & 077; else c = 0; if (s < strend && *s >= ' ') d = (*s++ - ' ') & 077; else d = 0; hunk[0] = a << 2 | b >> 4; hunk[1] = b << 4 | c >> 2; hunk[2] = c << 6 | d; str_ncat(str,hunk, len > 3 ? 3 : len); len -= 3; } if (*s == '\n') s++; else if (s[1] == '\n') /* possible checksum byte */ s += 2; } (void)astore(stack, ++sp, str_2mortal(str)); break; } if (checksum) { str = Str_new(42,0); if (index("fFdD", datumtype) || (checksum > 32 && index("iIlLN", datumtype)) ) { double modf(); double trouble; adouble = 1.0; while (checksum >= 16) { checksum -= 16; adouble *= 65536.0; } while (checksum >= 4) { checksum -= 4; adouble *= 16.0; } while (checksum--) adouble *= 2.0; along = (1 << checksum) - 1; while (cdouble < 0.0) cdouble += adouble; cdouble = modf(cdouble / adouble, &trouble) * adouble; str_numset(str,cdouble); } else { if (checksum < 32) { along = (1 << checksum) - 1; culong &= (unsigned long)along; } str_numset(str,(double)culong); } (void)astore(stack, ++sp, str_2mortal(str)); checksum = 0; } } return sp;}intdo_slice(stab,str,numarray,lval,gimme,arglast)STAB *stab;STR *str;int numarray;int lval;int gimme;int *arglast;{ register STR **st = stack->ary_array; register int sp = arglast[1]; register int max = arglast[2]; register char *tmps; register int len; register int magic = 0; register ARRAY *ary; register HASH *hash; int oldarybase = arybase; if (numarray) { if (numarray == 2) { /* a slice of a LIST */ ary = stack; ary->ary_fill = arglast[3]; arybase -= max + 1; st[sp] = str; /* make stack size available */ str_numset(str,(double)(sp - 1)); } else ary = stab_array(stab); /* a slice of an array */ } else { if (lval) { if (stab == envstab) magic = 'E'; else if (stab == sigstab) magic = 'S';#ifdef SOME_DBM else if (stab_hash(stab)->tbl_dbm) magic = 'D';#endif /* SOME_DBM */ } hash = stab_hash(stab); /* a slice of an associative array */ } if (gimme == G_ARRAY) { if (numarray) { while (sp < max) { if (st[++sp]) { st[sp-1] = afetch(ary, ((int)str_gnum(st[sp])) - arybase, lval); } else st[sp-1] = &str_undef; } } else { while (sp < max) { if (st[++sp]) { tmps = str_get(st[sp]); len = st[sp]->str_cur; st[sp-1] = hfetch(hash,tmps,len, lval); if (magic) str_magic(st[sp-1],stab,magic,tmps,len); } else st[sp-1] = &str_undef; } } sp--; } else { if (sp == max) st[sp] = &str_undef; else if (numarray) { if (st[max]) st[sp] = afetch(ary, ((int)str_gnum(st[max])) - arybase, lval); else st[sp] = &str_undef; } else { if (st[max]) { tmps = str_get(st[max]); len = st[max]->str_cur; st[sp] = hfetch(hash,tmps,len, lval); if (magic) str_magic(st[sp],stab,magic,tmps,len); } else st[sp] = &str_undef; } } arybase = oldarybase; return sp;}intdo_splice(ary,gimme,arglast)register ARRAY *ary;int gimme;int *arglast;{ register STR **st = stack->ary_array; register int sp = arglast[1]; int max = arglast[2] + 1; register STR **src; register STR **dst; register int i; register int offset; register int length; int newlen; int after; int diff; STR **tmparyval; if (++sp < max) { offset = (int)str_gnum(st[sp]); if (offset < 0) offset += ary->ary_fill + 1; else offset -= arybase; if (++sp < max) { length = (int)str_gnum(st[sp++]); if (length < 0) length = 0; } else length = ary->ary_max + 1; /* close enough to infinity */ } else { offset = 0; length = ary->ary_max + 1; } if (offset < 0) { length += offset; offset = 0; if (length < 0) length = 0; } if (offset > ary->ary_fill + 1) offset = ary->ary_fill + 1; after = ary->ary_fill + 1 - (offset + length); if (after < 0) { /* not that much array */ length += after; /* offset+length now in array */ after = 0; if (!ary->ary_alloc) { afill(ary,0); afill(ary,-1); } } /* At this point, sp .. max-1 is our new LIST */ newlen = max - sp; diff = newlen - length; if (diff < 0) { /* shrinking the area */ if (newlen) { New(451, tmparyval, newlen, STR*); /* so remember insertion */ Copy(st+sp, tmparyval, newlen, STR*); } sp = arglast[0] + 1; if (gimme == G_ARRAY) { /* copy return vals to stack */ if (sp + length >= stack->ary_max) { astore(stack,sp + length, Nullstr);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -