All of lore.kernel.org
 help / color / mirror / Atom feed
From: kernel test robot <lkp@intel.com>
To: Alexei Starovoitov <ast@kernel.org>
Cc: oe-kbuild-all@lists.linux.dev, linux-kernel@vger.kernel.org
Subject: kernel/bpf/fixups.c:1021:44: sparse: sparse: cast truncates bits from constant value (ffffc00000000000 becomes 0)
Date: Tue, 22 Sep 2026 19:57:21 +0800	[thread overview]
Message-ID: <202609221901.Su9mYT2B-lkp@intel.com> (raw)

Hi Alexei,

FYI, the error/warning was bisected to this commit, please ignore it if it's irrelevant.

tree:   https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git master
head:   f0100363d8c374bd8e9ea7c9ba02744f0b802ca4
commit: 449f08fa59dda5da40317b6976604b877c4ecd63 bpf: Move fixup/post-processing logic from verifier.c into fixups.c
date:   5 months ago
config: arm64-randconfig-r1300-20260922 (https://download.01.org/0day-ci/archive/20260922/202609221901.Su9mYT2B-lkp@intel.com/config)
compiler: aarch64-linux-gcc (GCC) 8.5.0
sparse: v0.6.5-rc1
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20260922/202609221901.Su9mYT2B-lkp@intel.com/reproduce)

If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Fixes: 449f08fa59dd ("bpf: Move fixup/post-processing logic from verifier.c into fixups.c")
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202609221901.Su9mYT2B-lkp@intel.com/

sparse warnings: (new ones prefixed by >>)
   kernel/bpf/fixups.c:2202:38: sparse: sparse: subtraction of functions? Share your drugs
>> kernel/bpf/fixups.c:1021:44: sparse: sparse: cast truncates bits from constant value (ffffc00000000000 becomes 0)

vim +1021 kernel/bpf/fixups.c

   975	
   976	int bpf_jit_subprogs(struct bpf_verifier_env *env)
   977	{
   978		struct bpf_prog *prog = env->prog, **func, *tmp;
   979		int i, j, subprog_start, subprog_end = 0, len, subprog;
   980		struct bpf_map *map_ptr;
   981		struct bpf_insn *insn;
   982		void *old_bpf_func;
   983		int err, num_exentries;
   984		int old_len, subprog_start_adjustment = 0;
   985	
   986		if (env->subprog_cnt <= 1)
   987			return 0;
   988	
   989		for (i = 0, insn = prog->insnsi; i < prog->len; i++, insn++) {
   990			if (!bpf_pseudo_func(insn) && !bpf_pseudo_call(insn))
   991				continue;
   992	
   993			/* Upon error here we cannot fall back to interpreter but
   994			 * need a hard reject of the program. Thus -EFAULT is
   995			 * propagated in any case.
   996			 */
   997			subprog = bpf_find_subprog(env, i + insn->imm + 1);
   998			if (verifier_bug_if(subprog < 0, env, "No program to jit at insn %d",
   999					    i + insn->imm + 1))
  1000				return -EFAULT;
  1001			/* temporarily remember subprog id inside insn instead of
  1002			 * aux_data, since next loop will split up all insns into funcs
  1003			 */
  1004			insn->off = subprog;
  1005			/* remember original imm in case JIT fails and fallback
  1006			 * to interpreter will be needed
  1007			 */
  1008			env->insn_aux_data[i].call_imm = insn->imm;
  1009			/* point imm to __bpf_call_base+1 from JITs point of view */
  1010			insn->imm = 1;
  1011			if (bpf_pseudo_func(insn)) {
  1012	#if defined(MODULES_VADDR)
  1013				u64 addr = MODULES_VADDR;
  1014	#else
  1015				u64 addr = VMALLOC_START;
  1016	#endif
  1017				/* jit (e.g. x86_64) may emit fewer instructions
  1018				 * if it learns a u32 imm is the same as a u64 imm.
  1019				 * Set close enough to possible prog address.
  1020				 */
> 1021				insn[0].imm = (u32)addr;
  1022				insn[1].imm = addr >> 32;
  1023			}
  1024		}
  1025	
  1026		err = bpf_prog_alloc_jited_linfo(prog);
  1027		if (err)
  1028			goto out_undo_insn;
  1029	
  1030		err = -ENOMEM;
  1031		func = kzalloc_objs(prog, env->subprog_cnt);
  1032		if (!func)
  1033			goto out_undo_insn;
  1034	
  1035		for (i = 0; i < env->subprog_cnt; i++) {
  1036			subprog_start = subprog_end;
  1037			subprog_end = env->subprog_info[i + 1].start;
  1038	
  1039			len = subprog_end - subprog_start;
  1040			/* bpf_prog_run() doesn't call subprogs directly,
  1041			 * hence main prog stats include the runtime of subprogs.
  1042			 * subprogs don't have IDs and not reachable via prog_get_next_id
  1043			 * func[i]->stats will never be accessed and stays NULL
  1044			 */
  1045			func[i] = bpf_prog_alloc_no_stats(bpf_prog_size(len), GFP_USER);
  1046			if (!func[i])
  1047				goto out_free;
  1048			memcpy(func[i]->insnsi, &prog->insnsi[subprog_start],
  1049			       len * sizeof(struct bpf_insn));
  1050			func[i]->type = prog->type;
  1051			func[i]->len = len;
  1052			if (bpf_prog_calc_tag(func[i]))
  1053				goto out_free;
  1054			func[i]->is_func = 1;
  1055			func[i]->sleepable = prog->sleepable;
  1056			func[i]->aux->func_idx = i;
  1057			/* Below members will be freed only at prog->aux */
  1058			func[i]->aux->btf = prog->aux->btf;
  1059			func[i]->aux->subprog_start = subprog_start + subprog_start_adjustment;
  1060			func[i]->aux->func_info = prog->aux->func_info;
  1061			func[i]->aux->func_info_cnt = prog->aux->func_info_cnt;
  1062			func[i]->aux->poke_tab = prog->aux->poke_tab;
  1063			func[i]->aux->size_poke_tab = prog->aux->size_poke_tab;
  1064			func[i]->aux->main_prog_aux = prog->aux;
  1065	
  1066			for (j = 0; j < prog->aux->size_poke_tab; j++) {
  1067				struct bpf_jit_poke_descriptor *poke;
  1068	
  1069				poke = &prog->aux->poke_tab[j];
  1070				if (poke->insn_idx < subprog_end &&
  1071				    poke->insn_idx >= subprog_start)
  1072					poke->aux = func[i]->aux;
  1073			}
  1074	
  1075			func[i]->aux->name[0] = 'F';
  1076			func[i]->aux->stack_depth = env->subprog_info[i].stack_depth;
  1077			if (env->subprog_info[i].priv_stack_mode == PRIV_STACK_ADAPTIVE)
  1078				func[i]->aux->jits_use_priv_stack = true;
  1079	
  1080			func[i]->jit_requested = 1;
  1081			func[i]->blinding_requested = prog->blinding_requested;
  1082			func[i]->aux->kfunc_tab = prog->aux->kfunc_tab;
  1083			func[i]->aux->kfunc_btf_tab = prog->aux->kfunc_btf_tab;
  1084			func[i]->aux->linfo = prog->aux->linfo;
  1085			func[i]->aux->nr_linfo = prog->aux->nr_linfo;
  1086			func[i]->aux->jited_linfo = prog->aux->jited_linfo;
  1087			func[i]->aux->linfo_idx = env->subprog_info[i].linfo_idx;
  1088			func[i]->aux->arena = prog->aux->arena;
  1089			func[i]->aux->used_maps = env->used_maps;
  1090			func[i]->aux->used_map_cnt = env->used_map_cnt;
  1091			num_exentries = 0;
  1092			insn = func[i]->insnsi;
  1093			for (j = 0; j < func[i]->len; j++, insn++) {
  1094				if (BPF_CLASS(insn->code) == BPF_LDX &&
  1095				    (BPF_MODE(insn->code) == BPF_PROBE_MEM ||
  1096				     BPF_MODE(insn->code) == BPF_PROBE_MEM32 ||
  1097				     BPF_MODE(insn->code) == BPF_PROBE_MEM32SX ||
  1098				     BPF_MODE(insn->code) == BPF_PROBE_MEMSX))
  1099					num_exentries++;
  1100				if ((BPF_CLASS(insn->code) == BPF_STX ||
  1101				     BPF_CLASS(insn->code) == BPF_ST) &&
  1102				     BPF_MODE(insn->code) == BPF_PROBE_MEM32)
  1103					num_exentries++;
  1104				if (BPF_CLASS(insn->code) == BPF_STX &&
  1105				     BPF_MODE(insn->code) == BPF_PROBE_ATOMIC)
  1106					num_exentries++;
  1107			}
  1108			func[i]->aux->num_exentries = num_exentries;
  1109			func[i]->aux->tail_call_reachable = env->subprog_info[i].tail_call_reachable;
  1110			func[i]->aux->exception_cb = env->subprog_info[i].is_exception_cb;
  1111			func[i]->aux->changes_pkt_data = env->subprog_info[i].changes_pkt_data;
  1112			func[i]->aux->might_sleep = env->subprog_info[i].might_sleep;
  1113			if (!i)
  1114				func[i]->aux->exception_boundary = env->seen_exception;
  1115	
  1116			/*
  1117			 * To properly pass the absolute subprog start to jit
  1118			 * all instruction adjustments should be accumulated
  1119			 */
  1120			old_len = func[i]->len;
  1121			func[i] = bpf_int_jit_compile(func[i]);
  1122			subprog_start_adjustment += func[i]->len - old_len;
  1123	
  1124			if (!func[i]->jited) {
  1125				err = -ENOTSUPP;
  1126				goto out_free;
  1127			}
  1128			cond_resched();
  1129		}
  1130	
  1131		/* at this point all bpf functions were successfully JITed
  1132		 * now populate all bpf_calls with correct addresses and
  1133		 * run last pass of JIT
  1134		 */
  1135		for (i = 0; i < env->subprog_cnt; i++) {
  1136			insn = func[i]->insnsi;
  1137			for (j = 0; j < func[i]->len; j++, insn++) {
  1138				if (bpf_pseudo_func(insn)) {
  1139					subprog = insn->off;
  1140					insn[0].imm = (u32)(long)func[subprog]->bpf_func;
  1141					insn[1].imm = ((u64)(long)func[subprog]->bpf_func) >> 32;
  1142					continue;
  1143				}
  1144				if (!bpf_pseudo_call(insn))
  1145					continue;
  1146				subprog = insn->off;
  1147				insn->imm = BPF_CALL_IMM(func[subprog]->bpf_func);
  1148			}
  1149	
  1150			/* we use the aux data to keep a list of the start addresses
  1151			 * of the JITed images for each function in the program
  1152			 *
  1153			 * for some architectures, such as powerpc64, the imm field
  1154			 * might not be large enough to hold the offset of the start
  1155			 * address of the callee's JITed image from __bpf_call_base
  1156			 *
  1157			 * in such cases, we can lookup the start address of a callee
  1158			 * by using its subprog id, available from the off field of
  1159			 * the call instruction, as an index for this list
  1160			 */
  1161			func[i]->aux->func = func;
  1162			func[i]->aux->func_cnt = env->subprog_cnt - env->hidden_subprog_cnt;
  1163			func[i]->aux->real_func_cnt = env->subprog_cnt;
  1164		}
  1165		for (i = 0; i < env->subprog_cnt; i++) {
  1166			old_bpf_func = func[i]->bpf_func;
  1167			tmp = bpf_int_jit_compile(func[i]);
  1168			if (tmp != func[i] || func[i]->bpf_func != old_bpf_func) {
  1169				verbose(env, "JIT doesn't support bpf-to-bpf calls\n");
  1170				err = -ENOTSUPP;
  1171				goto out_free;
  1172			}
  1173			cond_resched();
  1174		}
  1175	
  1176		/*
  1177		 * Cleanup func[i]->aux fields which aren't required
  1178		 * or can become invalid in future
  1179		 */
  1180		for (i = 0; i < env->subprog_cnt; i++) {
  1181			func[i]->aux->used_maps = NULL;
  1182			func[i]->aux->used_map_cnt = 0;
  1183		}
  1184	
  1185		/* finally lock prog and jit images for all functions and
  1186		 * populate kallsysm. Begin at the first subprogram, since
  1187		 * bpf_prog_load will add the kallsyms for the main program.
  1188		 */
  1189		for (i = 1; i < env->subprog_cnt; i++) {
  1190			err = bpf_prog_lock_ro(func[i]);
  1191			if (err)
  1192				goto out_free;
  1193		}
  1194	
  1195		for (i = 1; i < env->subprog_cnt; i++)
  1196			bpf_prog_kallsyms_add(func[i]);
  1197	
  1198		/* Last step: make now unused interpreter insns from main
  1199		 * prog consistent for later dump requests, so they can
  1200		 * later look the same as if they were interpreted only.
  1201		 */
  1202		for (i = 0, insn = prog->insnsi; i < prog->len; i++, insn++) {
  1203			if (bpf_pseudo_func(insn)) {
  1204				insn[0].imm = env->insn_aux_data[i].call_imm;
  1205				insn[1].imm = insn->off;
  1206				insn->off = 0;
  1207				continue;
  1208			}
  1209			if (!bpf_pseudo_call(insn))
  1210				continue;
  1211			insn->off = env->insn_aux_data[i].call_imm;
  1212			subprog = bpf_find_subprog(env, i + insn->off + 1);
  1213			insn->imm = subprog;
  1214		}
  1215	
  1216		prog->jited = 1;
  1217		prog->bpf_func = func[0]->bpf_func;
  1218		prog->jited_len = func[0]->jited_len;
  1219		prog->aux->extable = func[0]->aux->extable;
  1220		prog->aux->num_exentries = func[0]->aux->num_exentries;
  1221		prog->aux->func = func;
  1222		prog->aux->func_cnt = env->subprog_cnt - env->hidden_subprog_cnt;
  1223		prog->aux->real_func_cnt = env->subprog_cnt;
  1224		prog->aux->bpf_exception_cb = (void *)func[env->exception_callback_subprog]->bpf_func;
  1225		prog->aux->exception_boundary = func[0]->aux->exception_boundary;
  1226		bpf_prog_jit_attempt_done(prog);
  1227		return 0;
  1228	out_free:
  1229		/* We failed JIT'ing, so at this point we need to unregister poke
  1230		 * descriptors from subprogs, so that kernel is not attempting to
  1231		 * patch it anymore as we're freeing the subprog JIT memory.
  1232		 */
  1233		for (i = 0; i < prog->aux->size_poke_tab; i++) {
  1234			map_ptr = prog->aux->poke_tab[i].tail_call.map;
  1235			map_ptr->ops->map_poke_untrack(map_ptr, prog->aux);
  1236		}
  1237		/* At this point we're guaranteed that poke descriptors are not
  1238		 * live anymore. We can just unlink its descriptor table as it's
  1239		 * released with the main prog.
  1240		 */
  1241		for (i = 0; i < env->subprog_cnt; i++) {
  1242			if (!func[i])
  1243				continue;
  1244			func[i]->aux->poke_tab = NULL;
  1245			bpf_jit_free(func[i]);
  1246		}
  1247		kfree(func);
  1248	out_undo_insn:
  1249		/* cleanup main prog to be interpreted */
  1250		prog->jit_requested = 0;
  1251		prog->blinding_requested = 0;
  1252		for (i = 0, insn = prog->insnsi; i < prog->len; i++, insn++) {
  1253			if (!bpf_pseudo_call(insn))
  1254				continue;
  1255			insn->off = 0;
  1256			insn->imm = env->insn_aux_data[i].call_imm;
  1257		}
  1258		bpf_prog_jit_attempt_done(prog);
  1259		return err;
  1260	}
  1261	

--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki

                 reply	other threads:[~2026-09-22 11:58 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=202609221901.Su9mYT2B-lkp@intel.com \
    --to=lkp@intel.com \
    --cc=ast@kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=oe-kbuild-all@lists.linux.dev \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.