📄 snap_interp.c
字号:
value_t *top3 = p->sp - 3; /* stack amount */ value_t *top4 = p->sp - 4; /* entry point */ int child_rb_arg; int st_amt; int ep; unsigned char child_ttl; __u32 dest; packet_t *pdup; DYNCHECK(top4 >= p->stack_min); DYNCHECK_TAG(*top1,ADDRV); GET_ADDR(dest,p->heap_min,*top1); DYNCHECK_TAG(*top2,INTV); child_rb_arg = GET_INT(*top2); DYNCHECK(child_rb_arg > 0); DYNCHECK(child_rb_arg <= p->rb); child_ttl = (unsigned char)child_rb_arg; DYNCHECK_TAG(*top3,INTV); st_amt = GET_INT(*top3); DYNCHECK_TAG(*top4,INTV); ep = GET_INT(*top4); DYNCHECK(ep >= 0); p->sp -= 4; pdup = pkt_dup(p);/* if (pdup == NULL) { *//* warn("%s:%d: failed on pdup\n",__FILE__,__LINE__); *//* return -1; *//* } *//* pdup->skb->nh.iph->daddr = dest; *//* pdup->skb->nh.iph->ttl = child_ttl; *//* pdup->hdr->entry_point = htons(ep); */ d_printf(10,"%s:%d: pc=%d: SEND [%d.%d.%d.%d] rb=%d ep=%d sa=%d\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest),child_ttl,ep,st_amt); DYNCHECK(child_ttl > 0); /* ok to do dyncheck here because packet will just get dropped anyway */ /* send the request. the last parameter distinguishes between SEND and DSEND */ if (snap_send_packet(p, (st_amt == -1) ? (p->sp - p->stack_min) : st_amt, dest, child_ttl, ep, GET_OP(*p->pc) == SEND ? 0 : 1)) { warn("%s:%d: SEND or DSEND snap_send_packet failed\n", __FILE__,__LINE__); return -1; } p->rb -= child_ttl; p->pc++; break; }#undef OLDSEND#ifdef OLDSEND case SEND: { value_t *top1 = p->sp - 1; /* dest addr */ value_t *top2 = p->sp - 2; /* RB to use */ value_t *top3 = p->sp - 3; /* stack amount */ value_t *top4 = p->sp - 4; /* entry point */ uint32 dest; int intrb; DYNCHECK(top4 >= p->stack_min); DYNCHECK_TAG(*top1,ADDRV); GET_ADDR(dest,p->heap_min,*top1); DYNCHECK_TAG(*top2,INTV); intrb = GET_INT(*top2); p->sp -= 3; /* pop; leave room for return value */ if (intrb > 0) { if (intrb <= p->rb) { uint32 dstcache; unsigned char rb = (unsigned char)intrb; unsigned char rb_cache; int ep,st_amt; DYNCHECK_TAG(*top3,INTV); st_amt = GET_INT(*top3); DYNCHECK_TAG(*top4,INTV); ep = GET_INT(*top4); dstcache = p->hdr->daddr; rb_cache = p->rb; iph->daddr = dest;/* iph->ttl = rb; *//* p->hdr->entry_point = htons(ep); */ p->sp--; d_printf(50,"%s:%d: SEND about to call snap_send_packet()\n", __FILE__,__LINE__); snap_send_packet(p, (st_amt == -1) ? (p->sp - p->stack_min) : st_amt, dest); d_printf(150,"%s:%d: back from snap_send_packet\n", __FILE__,__LINE__); print_anti_timer(1,"interp_packet"); p->sp++;/* iph->daddr = dstcache; *//* iph->ttl = (rb_cache - rb); */ d_printf(10,"%s:%d: pc=%d: SEND %u.%u.%u.%u rb=%d st=%d ep=%d\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest),rb,st_amt,ep); SET_TAG(*top4,INTV); SET_INT(*top4,0); done = 1; } /* not enough resource bound */ else { d_printf(10,"%s:%d: pc=%d: SEND %d.%d.%d.%d rb=%d st=%d ep=%d (NOT ENOUGH RB!!!)\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest),intrb,GET_INT(*top3),GET_INT(*top4)); SET_TAG(*top4,EXCV); SET_INT(*top4,E_NOT_ENOUGH_RB); } } /* non-positive resource bound */ else { d_printf(10,"%s:%d: pc=%d: SEND %d.%d.%d.%d rb=%d st=%d ep=%d (NON-POSITIVE RB!!!)\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest),intrb,GET_INT(*top3),GET_INT(*top4)); SET_TAG(*top4,EXCV); SET_INT(*top4,E_NON_POSITIVE_RB); } p->pc++; break; }#endif /* OLDSEND */ case HOP: { value_t *top1 = p->sp - 1; /* dest addr */ value_t *top2 = p->sp - 2; /* RB to use */ value_t *top3 = p->sp - 3; /* stack amount (-1 = whole stack) */ value_t *top4 = p->sp - 4; /* entry point */ uint32 dest; int rb; DYNCHECK(top4 >= p->stack_min); DYNCHECK_TAG(*top1,ADDRV); GET_ADDR(dest,p->heap_min,*top1); DYNCHECK_TAG(*top2,INTV); rb = GET_INT(*top2); p->sp -= 3; /* pop; leave room for return value */ if (rb > 0) { if (rb <= p->rb) { short rb_cache; int ep,st_amt; DYNCHECK_TAG(*top3,INTV); st_amt = GET_INT(*top3); DYNCHECK_TAG(*top4,INTV); ep = GET_INT(*top4); rb_cache = p->rb; p->hdr->entry_point = htons(ep); p->rb = rb; p->sp--; print_timer(1,"interp_packet"); snap_send_packet(p,st_amt,dest,rb,ep, 0); print_anti_timer(1,"interp_packet"); p->sp++; p->rb = rb_cache - rb; d_printf(10,"%s:%d: pc=%d: HOP %d.%d.%d.%d rb=%d st=%d ep=%d\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest), rb, st_amt, ep); SET_TAG(*top4,INTV); SET_INT(*top4,0); } /* not enough resource bound */ else { d_printf(10,"%s:%d: pc=%d: HOP %d.%d.%d.%d rb=%d st=%d ep=%d (NOT ENOUGH RB!!!)\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest), rb, GET_INT(*top3), GET_INT(*top4)); SET_TAG(*top4,EXCV); SET_INT(*top4,E_NOT_ENOUGH_RB); } } /* non-positive resource bound */ else { d_printf(10,"%s:%d: pc=%d: HOP %d.%d.%d.%d rb=%d st=%d ep=%d (NON-POSITIVE RB!!!)\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest), rb, GET_INT(*top3),GET_INT(*top4)); SET_TAG(*top4,EXCV); SET_INT(*top4,E_NON_POSITIVE_RB); } p->pc++; break; } case FORW: case DFORW: { int herep; print_timer(1,"interp_packet"); herep = ishere(p->hdr->daddr, p); print_anti_timer(1,"interp_packet"); if (herep) { d_printf(10,"%s:%d: pc=%d: FORW: at dest, falling thru\n", __FILE__,__LINE__,(p->pc - p->code_min)); } else { d_printf(10,"%s:%d: pc=%d: FORW: moving on\n", __FILE__,__LINE__,(p->pc - p->code_min)); DYNCHECK(p->rb > 0); /* OK to do dyncheck here because packet will just get dropped anyway */ print_timer(1,"interp_packet"); /* send the request. the last parameter distinguishes between FORW and DFORW */ if (snap_send_packet(p, p->sp - p->stack_min, p->hdr->daddr, p->rb, ntohs(p->hdr->entry_point), GET_OP(*p->pc) == FORW ? 0 : 1)) { warn("%s:%d: snap_send_packet failed\n", __FILE__,__LINE__); return -1; } print_anti_timer(1,"interp_packet"); p->rb = 0; done = 1; } p->pc++; break; } case FORWTO: case DFORWTO: { value_t *top = p->sp - 1; uint32_t dest; int herep; DYNCHECK(top >= p->stack_min); DYNCHECK_TAG(*top,ADDRV); GET_ADDR(dest,p->heap_min,*top); p->sp--; print_timer(1,"interp_packet"); herep = ishere(dest,p); print_anti_timer(1,"interp_packet"); if (!herep) { d_printf(10,"%s:%d: pc=%d: FORWTO [%u.%u.%u.%u]: moving on\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest)); print_timer(1,"interp_packet"); DYNCHECK(p->rb > 0); /* OK to do dyncheck here because packet will just get dropped anyway */ print_timer(1,"interp_packet"); /* send the request. the last parameter distinguishes between FORWTO and DFORWTO */ if (snap_send_packet(p, p->sp - p->stack_min, dest, p->rb, htons(p->hdr->entry_point), GET_OP(*p->pc) == FORWTO ? 0 : 1)) { warn("%s:%d: FORWTO snap_send_packet failed\n", __FILE__,__LINE__); return -1; } print_anti_timer(1,"interp_packet"); p->rb = 0; done = 1; } else { d_printf(10,"%s:%d: pc=%d: FORWTO [%u.%u.%u.%u]: at dest, falling thru\n", __FILE__,__LINE__,(p->pc - p->code_min), NIPQUAD(dest)); } p->pc++; break; } case STACKEMPTY : PUSHWJDB(INTV,"STACKEMPTY",(p->sp == p->stack_min ? 1 : 0),"%d",(p->sp == p->stack_min ? 1 : 0)); break; case STACKCOUNT : PUSHWJDB(INTV,"STACKCOUNT",(p->sp - p->stack_min),"%d",(p->sp - p->stack_min)); break; case DEMUX:{ value_t *top1 = p->sp - 1; value_t *top2 = p->sp - 2; int pnum = 0; char *s; int slen = 0; heap_obj *ho; DYNCHECK(top2 >= p->stack_min); DYNCHECK_TAG(*top1,INTV); pnum = GET_INT(*top1); DYNCHECK(pnum > 0); DYNCHECK_TAG(*top2,STRV); ho = (heap_obj *)(p->heap_min + GET_OFFS(*top2)); DYNCHECK_IN_HEAP(ho); s = (char *)&(ho->s); slen = ho->len; print_timer(1,"interp_packet"); d_printf(10,"%s:%d: pc=%d: DEMUX or DEMUXUDP [%d] bytes to port [%d]\n", __FILE__,__LINE__,(p->pc - p->code_min),slen, pnum); if (snap_demux_send(pnum,p,s,slen)) { warn("%s:%d: snap_demux_send failed\n", __FILE__,__LINE__); return -1; } print_anti_timer(1,"interp_packet"); p->sp -= 2; /* pop */ p->pc++; done = 1; /* exit after one demux */ return 0; /* return, avoid skb_free */ break; } case DEMUXI:{ value_t *top = p->sp - 1; int pnum = 0; char *s; int slen = 0; heap_obj *ho; DYNCHECK(top >= p->stack_min); GET_LIT(pnum,INTV,*p->pc); DYNCHECK(pnum > 0); DYNCHECK_TAG(*top,STRV); ho = (heap_obj *)(p->heap_min + GET_OFFS(*top)); DYNCHECK_IN_HEAP(ho); s = (char *)&(ho->s); slen = ho->len; print_timer(1,"interp_packet"); d_printf(10,"%s:%d: pc=%d: DEMUXI or DEMUXIUDP port %d : [%d] bytes\n", __FILE__,__LINE__,(p->pc - p->code_min),pnum,slen); if (snap_demux_send(pnum,p,s,slen)) { warn("%s:%d: snap_demux_send failed\n",__FILE__,__LINE__); return -1; } print_anti_timer(1,"interp_packet"); p->sp--; /* pop */ p->pc++; done = 1; /* exit after one demux */ return 0; /* return, avoid skb_free */ break; } case PRINT: { value_t *top = p->sp - 1; DYNCHECK(top >= p->stack_min); d_printf(10,"%s:%d: pc=%d: PRINT\n",__FILE__,__LINE__, (p->pc - p->code_min));#ifdef __KERNEL__ printk(KERN_WARNING "print: "); printk_value(p,top); printk("\n");#else fprintf(stderr,"snap_interp : print: "); fprintf_value(p,stderr,top); fprintf(stderr,"\n"); fflush(stderr);#endif p->pc++; break; }#ifdef CONFIG_IP_SNAP_SVCS#if 0 case SVCV: { int offs, retc; heap_obj *ho; char *s; ENSURE_HEAP_ROOM(p,iph); DYNCHECK(p->sp < p->stack_max); GET_LIT(offs,STRV,*p->pc); ho = (heap_obj *)(p->heap_min + offs); DYNCHECK_IN_HEAP(ho); s = (char *)&(ho->s); retc = lookup_value(p,s,p->sp); if (retc != 0) { /* not found */ d_printf(10,"%s:%d: pc=%d: SVCV \"%s\": (SERVICE NOT PRESENT!!!)\n", __FILE__,__LINE__, (p->pc - p->code_min),s); SET_TAG(*p->sp,EXCV); SET_INT(*p->sp,E_SERVICE_NOT_PRESENT); } else { d_printf(10,"%s:%d: pc=%d: SVCV \"%s\"\n",__FILE__,__LINE__, (p->pc - p->code_min),s); } p->sp++; p->pc++; break; }#endif case CALLS: { int offs; heap_obj *ho; char *s; ENSURE_HEAP_ROOM(p,iph); DYNCHECK(p->sp < p->stack_max); GET_LIT(offs,STRV,*p->pc); ho = (heap_obj *)(p->heap_min + offs); DYNCHECK_IN_HEAP(ho); s = (char *)&(ho->s); if (snap_svc_call_service(p,s)) { /* not found */ d_printf(10,"%s:%d: pc=%d: CALLS \"%s\": (SERVICE NOT PRESENT!!!)\n", __FILE__,__LINE__, (p->pc - p->code_min),s); SET_TAG(*p->sp,EXCV); SET_INT(*p->sp,E_SERVICE_NOT_PRESENT); p->sp++; } else { d_printf(10,"%s:%d: pc=%d: CALLS \"%s\"\n",__FILE__,__LINE__, (p->pc - p->code_min),s); } p->pc++; break; }#endif /* CONFIG_IP_SNAP_SVCS */ default: warn("%s: unknown opcode: 0x%x\n",__FILE__,GET_OP(*p->pc)); return -1; } } print_timer(1,"interp_packet"); d_printf(40,"%s:%d: packet exits normally\n",__FILE__,__LINE__); return 0;}#endif /* CONFIG_IP_SNAP */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -