samples/seccomp: Support programs with >256 instructions

Previously, the program size was incorrectly truncated to 8 bits,
resulting in broken labels in large programs. Also changes the jump
resolution loop to not rely on undefined behavior (making a pointer
point before the filter array).

Signed-off-by: Ricky Zhou <rickyz@chromium.org>
Signed-off-by: Kees Cook <keescook@chromium.org>
diff --git a/samples/seccomp/bpf-helper.c b/samples/seccomp/bpf-helper.c
index 05cb4d5..1ef0f4d 100644
--- a/samples/seccomp/bpf-helper.c
+++ b/samples/seccomp/bpf-helper.c
@@ -18,41 +18,41 @@
 int bpf_resolve_jumps(struct bpf_labels *labels,
 		      struct sock_filter *filter, size_t count)
 {
-	struct sock_filter *begin = filter;
-	__u8 insn = count - 1;
+	size_t i;
 
-	if (count < 1)
+	if (count < 1 || count > BPF_MAXINSNS)
 		return -1;
 	/*
 	* Walk it once, backwards, to build the label table and do fixups.
 	* Since backward jumps are disallowed by BPF, this is easy.
 	*/
-	filter += insn;
-	for (; filter >= begin; --insn, --filter) {
-		if (filter->code != (BPF_JMP+BPF_JA))
+	for (i = 0; i < count; ++i) {
+		size_t offset = count - i - 1;
+		struct sock_filter *instr = &filter[offset];
+		if (instr->code != (BPF_JMP+BPF_JA))
 			continue;
-		switch ((filter->jt<<8)|filter->jf) {
+		switch ((instr->jt<<8)|instr->jf) {
 		case (JUMP_JT<<8)|JUMP_JF:
-			if (labels->labels[filter->k].location == 0xffffffff) {
+			if (labels->labels[instr->k].location == 0xffffffff) {
 				fprintf(stderr, "Unresolved label: '%s'\n",
-					labels->labels[filter->k].label);
+					labels->labels[instr->k].label);
 				return 1;
 			}
-			filter->k = labels->labels[filter->k].location -
-				    (insn + 1);
-			filter->jt = 0;
-			filter->jf = 0;
+			instr->k = labels->labels[instr->k].location -
+				    (offset + 1);
+			instr->jt = 0;
+			instr->jf = 0;
 			continue;
 		case (LABEL_JT<<8)|LABEL_JF:
-			if (labels->labels[filter->k].location != 0xffffffff) {
+			if (labels->labels[instr->k].location != 0xffffffff) {
 				fprintf(stderr, "Duplicate label use: '%s'\n",
-					labels->labels[filter->k].label);
+					labels->labels[instr->k].label);
 				return 1;
 			}
-			labels->labels[filter->k].location = insn;
-			filter->k = 0; /* fall through */
-			filter->jt = 0;
-			filter->jf = 0;
+			labels->labels[instr->k].location = offset;
+			instr->k = 0; /* fall through */
+			instr->jt = 0;
+			instr->jf = 0;
 			continue;
 		}
 	}