.. | .. |
---|
168 | 168 | "panic", |
---|
169 | 169 | "do_exit", |
---|
170 | 170 | "do_task_dead", |
---|
| 171 | + "make_task_dead", |
---|
171 | 172 | "__module_put_and_exit", |
---|
172 | 173 | "complete_and_exit", |
---|
173 | 174 | "__reiserfs_panic", |
---|
.. | .. |
---|
175 | 176 | "fortify_panic", |
---|
176 | 177 | "usercopy_abort", |
---|
177 | 178 | "machine_real_restart", |
---|
178 | | - "rewind_stack_do_exit", |
---|
| 179 | + "rewind_stack_and_make_dead", |
---|
179 | 180 | "kunit_try_catch_throw", |
---|
180 | 181 | "xen_start_kernel", |
---|
181 | 182 | "cpu_bringup_and_idle", |
---|
| 183 | + "stop_this_cpu", |
---|
182 | 184 | }; |
---|
183 | 185 | |
---|
184 | 186 | if (!func) |
---|
.. | .. |
---|
196 | 198 | return false; |
---|
197 | 199 | |
---|
198 | 200 | insn = find_insn(file, func->sec, func->offset); |
---|
199 | | - if (!insn->func) |
---|
| 201 | + if (!insn || !insn->func) |
---|
200 | 202 | return false; |
---|
201 | 203 | |
---|
202 | 204 | func_for_each_insn(file, func, insn) { |
---|
.. | .. |
---|
367 | 369 | |
---|
368 | 370 | if (!strcmp(sec->name, ".noinstr.text") || |
---|
369 | 371 | !strcmp(sec->name, ".entry.text") || |
---|
370 | | - !strncmp(sec->name, ".text.__x86.", 12)) |
---|
| 372 | + !strncmp(sec->name, ".text..__x86.", 13)) |
---|
371 | 373 | sec->noinstr = true; |
---|
372 | 374 | |
---|
373 | 375 | for (offset = 0; offset < sec->len; offset += insn->len) { |
---|
.. | .. |
---|
570 | 572 | if (strncmp(key_name, STATIC_CALL_TRAMP_PREFIX_STR, |
---|
571 | 573 | STATIC_CALL_TRAMP_PREFIX_LEN)) { |
---|
572 | 574 | WARN("static_call: trampoline name malformed: %s", key_name); |
---|
| 575 | + free(key_name); |
---|
573 | 576 | return -1; |
---|
574 | 577 | } |
---|
575 | 578 | tmp = key_name + STATIC_CALL_TRAMP_PREFIX_LEN - STATIC_CALL_KEY_PREFIX_LEN; |
---|
.. | .. |
---|
579 | 582 | if (!key_sym) { |
---|
580 | 583 | if (!module) { |
---|
581 | 584 | WARN("static_call: can't find static_call_key symbol: %s", tmp); |
---|
| 585 | + free(key_name); |
---|
582 | 586 | return -1; |
---|
583 | 587 | } |
---|
584 | 588 | |
---|
.. | .. |
---|
845 | 849 | "__tsan_read_write4", |
---|
846 | 850 | "__tsan_read_write8", |
---|
847 | 851 | "__tsan_read_write16", |
---|
| 852 | + "__tsan_volatile_read1", |
---|
| 853 | + "__tsan_volatile_read2", |
---|
| 854 | + "__tsan_volatile_read4", |
---|
| 855 | + "__tsan_volatile_read8", |
---|
| 856 | + "__tsan_volatile_read16", |
---|
| 857 | + "__tsan_volatile_write1", |
---|
| 858 | + "__tsan_volatile_write2", |
---|
| 859 | + "__tsan_volatile_write4", |
---|
| 860 | + "__tsan_volatile_write8", |
---|
| 861 | + "__tsan_volatile_write16", |
---|
848 | 862 | "__tsan_atomic8_load", |
---|
849 | 863 | "__tsan_atomic16_load", |
---|
850 | 864 | "__tsan_atomic32_load", |
---|
.. | .. |
---|
895 | 909 | "__tsan_atomic64_compare_exchange_val", |
---|
896 | 910 | "__tsan_atomic_thread_fence", |
---|
897 | 911 | "__tsan_atomic_signal_fence", |
---|
| 912 | + "__tsan_unaligned_read16", |
---|
| 913 | + "__tsan_unaligned_write16", |
---|
898 | 914 | /* KCOV */ |
---|
899 | 915 | "write_comp_data", |
---|
900 | 916 | "check_kcov_mode", |
---|
.. | .. |
---|
973 | 989 | return 0; |
---|
974 | 990 | } |
---|
975 | 991 | |
---|
| 992 | +/* |
---|
| 993 | + * Symbols that replace INSN_CALL_DYNAMIC, every (tail) call to such a symbol |
---|
| 994 | + * will be added to the .retpoline_sites section. |
---|
| 995 | + */ |
---|
976 | 996 | __weak bool arch_is_retpoline(struct symbol *sym) |
---|
977 | 997 | { |
---|
978 | 998 | return false; |
---|
979 | 999 | } |
---|
980 | 1000 | |
---|
| 1001 | +/* |
---|
| 1002 | + * Symbols that replace INSN_RETURN, every (tail) call to such a symbol |
---|
| 1003 | + * will be added to the .return_sites section. |
---|
| 1004 | + */ |
---|
981 | 1005 | __weak bool arch_is_rethunk(struct symbol *sym) |
---|
| 1006 | +{ |
---|
| 1007 | + return false; |
---|
| 1008 | +} |
---|
| 1009 | + |
---|
| 1010 | +/* |
---|
| 1011 | + * Symbols that are embedded inside other instructions, because sometimes crazy |
---|
| 1012 | + * code exists. These are mostly ignored for validation purposes. |
---|
| 1013 | + */ |
---|
| 1014 | +__weak bool arch_is_embedded_insn(struct symbol *sym) |
---|
982 | 1015 | { |
---|
983 | 1016 | return false; |
---|
984 | 1017 | } |
---|
.. | .. |
---|
1230 | 1263 | continue; |
---|
1231 | 1264 | |
---|
1232 | 1265 | /* |
---|
1233 | | - * This is a special case for zen_untrain_ret(). |
---|
| 1266 | + * This is a special case for retbleed_untrain_ret(). |
---|
1234 | 1267 | * It jumps to __x86_return_thunk(), but objtool |
---|
1235 | 1268 | * can't find the thunk's starting RET |
---|
1236 | 1269 | * instruction, because the RET is also in the |
---|
1237 | 1270 | * middle of another instruction. Objtool only |
---|
1238 | 1271 | * knows about the outer instruction. |
---|
1239 | 1272 | */ |
---|
1240 | | - if (sym && sym->return_thunk) { |
---|
| 1273 | + if (sym && sym->embedded_insn) { |
---|
1241 | 1274 | add_return_call(file, insn, false); |
---|
1242 | 1275 | continue; |
---|
1243 | 1276 | } |
---|
.. | .. |
---|
2039 | 2072 | if (arch_is_rethunk(func)) |
---|
2040 | 2073 | func->return_thunk = true; |
---|
2041 | 2074 | |
---|
| 2075 | + if (arch_is_embedded_insn(func)) |
---|
| 2076 | + func->embedded_insn = true; |
---|
| 2077 | + |
---|
2042 | 2078 | if (!strcmp(func->name, "__fentry__")) |
---|
2043 | 2079 | func->fentry = true; |
---|
2044 | 2080 | |
---|
.. | .. |
---|
2148 | 2184 | return 0; |
---|
2149 | 2185 | } |
---|
2150 | 2186 | |
---|
2151 | | -static bool is_fentry_call(struct instruction *insn) |
---|
| 2187 | +static bool is_special_call(struct instruction *insn) |
---|
2152 | 2188 | { |
---|
2153 | | - if (insn->type == INSN_CALL && |
---|
2154 | | - insn->call_dest && |
---|
2155 | | - insn->call_dest->fentry) |
---|
2156 | | - return true; |
---|
| 2189 | + if (insn->type == INSN_CALL) { |
---|
| 2190 | + struct symbol *dest = insn->call_dest; |
---|
| 2191 | + |
---|
| 2192 | + if (!dest) |
---|
| 2193 | + return false; |
---|
| 2194 | + |
---|
| 2195 | + if (dest->fentry) |
---|
| 2196 | + return true; |
---|
| 2197 | + } |
---|
2157 | 2198 | |
---|
2158 | 2199 | return false; |
---|
2159 | 2200 | } |
---|
.. | .. |
---|
3027 | 3068 | if (ret) |
---|
3028 | 3069 | return ret; |
---|
3029 | 3070 | |
---|
3030 | | - if (!no_fp && func && !is_fentry_call(insn) && |
---|
| 3071 | + if (!no_fp && func && !is_special_call(insn) && |
---|
3031 | 3072 | !has_valid_stack_frame(&state)) { |
---|
3032 | 3073 | WARN_FUNC("call without frame pointer save/setup", |
---|
3033 | 3074 | sec, insn->offset); |
---|