예제 #1
0
파일: mpx.c 프로젝트: ammubhave/bargud
static int mpx_insn_decode(struct insn *insn,
			   struct pt_regs *regs)
{
	unsigned char buf[MAX_INSN_SIZE];
	int x86_64 = !test_thread_flag(TIF_IA32);
	int not_copied;
	int nr_copied;

	not_copied = copy_from_user(buf, (void __user *)regs->ip, sizeof(buf));
	nr_copied = sizeof(buf) - not_copied;
	/*
	 * The decoder _should_ fail nicely if we pass it a short buffer.
	 * But, let's not depend on that implementation detail.  If we
	 * did not get anything, just error out now.
	 */
	if (!nr_copied)
		return -EFAULT;
	insn_init(insn, buf, nr_copied, x86_64);
	insn_get_length(insn);
	/*
	 * copy_from_user() tries to get as many bytes as we could see in
	 * the largest possible instruction.  If the instruction we are
	 * after is shorter than that _and_ we attempt to copy from
	 * something unreadable, we might get a short read.  This is OK
	 * as long as the read did not stop in the middle of the
	 * instruction.  Check to see if we got a partial instruction.
	 */
	if (nr_copied < insn->length)
		return -EFAULT;

	insn_get_opcode(insn);
	/*
	 * We only _really_ need to decode bndcl/bndcn/bndcu
	 * Error out on anything else.
	 */
	if (insn->opcode.bytes[0] != 0x0f)
		goto bad_opcode;
	if ((insn->opcode.bytes[1] != 0x1a) &&
	    (insn->opcode.bytes[1] != 0x1b))
		goto bad_opcode;

	return 0;
bad_opcode:
	return -EINVAL;
}
예제 #2
0
파일: uprobes.c 프로젝트: AllenWeb/linux
static int validate_insn_64bits(struct arch_uprobe *auprobe, struct insn *insn)
{
	insn_init(insn, auprobe->insn, true);

	/* Skip good instruction prefixes; reject "bad" ones. */
	insn_get_opcode(insn);
	if (is_prefix_bad(insn))
		return -ENOTSUPP;

	if (test_bit(OPCODE1(insn), (unsigned long *)good_insns_64))
		return 0;

	if (insn->opcode.nbytes == 2) {
		if (test_bit(OPCODE2(insn), (unsigned long *)good_2byte_insns))
			return 0;
	}
	return -ENOTSUPP;
}
예제 #3
0
int main(int argc, char **argv)
{
	struct insn insn;
	int insns = 0;
	int errors = 0;
	unsigned long i;
	unsigned char insn_buf[MAX_INSN_SIZE * 2];

	parse_args(argc, argv);

	/*                              */
	memset(insn_buf + MAX_INSN_SIZE, INSN_NOP, MAX_INSN_SIZE);

	for (i = 0; i < iter_end; i++) {
		if (generate_insn(insn_buf) <= 0)
			break;

		if (i < iter_start)	/*                                */
			continue;

		/*                       */
		insn_init(&insn, insn_buf, x86_64);
		insn_get_length(&insn);

		if (insn.next_byte <= insn.kaddr ||
		    insn.kaddr + MAX_INSN_SIZE < insn.next_byte) {
			/*                            */
			dump_stream(stderr, "Error: Found an access violation", i, insn_buf, &insn);
			errors++;
		} else if (verbose && !insn_complete(&insn))
			dump_stream(stdout, "Info: Found an undecodable input", i, insn_buf, &insn);
		else if (verbose >= 2)
			dump_insn(stdout, &insn);
		insns++;
	}

	fprintf(stdout, "%s: decoded and checked %d %s instructions with %d errors (seed:0x%x)\n", (errors) ? "Failure" : "Success", insns, (input_file) ? "given" : "random", errors, seed);

	return errors ? 1 : 0;
}
예제 #4
0
int main(int argc, char **argv)
{
	char line[BUFSIZE], sym[BUFSIZE] = "<unknown>";
	unsigned char insn_buf[16];
	struct insn insn;
	int insns = 0;
	int warnings = 0;

	parse_args(argc, argv);

	while (fgets(line, BUFSIZE, stdin)) {
		char copy[BUFSIZE], *s, *tab1, *tab2;
		int nb = 0;
		unsigned int b;

		if (line[0] == '<') {
			/* Symbol line */
			strcpy(sym, line);
			continue;
		}

		insns++;
		memset(insn_buf, 0, 16);
		strcpy(copy, line);
		tab1 = strchr(copy, '\t');
		if (!tab1)
			malformed_line(line, insns);
		s = tab1 + 1;
		s += strspn(s, " ");
		tab2 = strchr(s, '\t');
		if (!tab2)
			malformed_line(line, insns);
		*tab2 = '\0';	/* Characters beyond tab2 aren't examined */
		while (s < tab2) {
			if (sscanf(s, "%x", &b) == 1) {
				insn_buf[nb++] = (unsigned char) b;
				s += 3;
			} else
				break;
		}
		/* Decode an instruction */
		insn_init(&insn, insn_buf, sizeof(insn_buf), x86_64);
		insn_get_length(&insn);
		if (insn.length != nb) {
			warnings++;
			pr_warn("Found an x86 instruction decoder bug, "
				"please report this.\n", sym);
			pr_warn("%s", line);
			pr_warn("objdump says %d bytes, but insn_get_length() "
				"says %d\n", nb, insn.length);
			if (verbose)
				dump_insn(stderr, &insn);
		}
	}
	if (warnings)
		pr_warn("Decoded and checked %d instructions with %d "
			"failures\n", insns, warnings);
	else
		fprintf(stdout, "%s: success: Decoded and checked %d"
			" instructions\n", prog, insns);
	return 0;
}