Skip to content

Commit ac4219a

Browse files
LATX, fix: Scope KZT compatibility fallback by library group
Compatibility checks previously disabled the process-wide KZT option when an application path contained a private guest library matching any wrapped SONAME. This also disabled unrelated library families, while wrapper-selection logs could still describe the configured groups rather than the execution-time result. Keep the configured mask as the requested state and prune incompatible families only from a separate effective mask. Derive the execution-time KZT predicate from the process-level 0/1/2 mode and the effective mask, then use it consistently for translation, bridge, signal, address-validation, relocation, and callback paths. Configuration, direct-exec, and Wine deferral continue to manage the process-level mode. Match private guest libraries at the .so boundary and confirm each candidate is an x86_64 ELF. Remove the undocumented GTK3/libXt name gate; retain the existing Chrome process gate as an explicit all-family rejection. Signed-off-by: Hanlu Li <heuleehanlu@gmail.com>
1 parent 913710f commit ac4219a

18 files changed

Lines changed: 206 additions & 58 deletions

File tree

accel/tcg/cpu-exec.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -195,7 +195,7 @@ cpu_tb_exec(CPUState *cpu, TranslationBlock *itb, int *tb_exit)
195195
if (qemu_loglevel_mask(CPU_LOG_EXEC)) {
196196
#ifdef CONFIG_LATX_KZT
197197
Dl_info dl_info;
198-
if (option_kzt && itb->pc > reserved_va &&
198+
if (latx_kzt_runtime_enabled() && itb->pc > reserved_va &&
199199
dladdr ((const void *)((onebridge_t *)itb->pc)->f, &dl_info)) {
200200
qemu_log_mask_and_addr(CPU_LOG_EXEC, itb->pc,
201201
"pid(%d) - tid(%" PRIuPTR ") Trace cpu%d: %p [ "
@@ -285,7 +285,7 @@ cpu_tb_exec(CPUState *cpu, TranslationBlock *itb, int *tb_exit)
285285
}
286286
lazypc = rettb->pc + rettb->lazypc[0];
287287
#if defined(CONFIG_LATX_KZT)
288-
if (option_kzt && lazypc >= reserved_va) {
288+
if (latx_kzt_runtime_enabled() && lazypc >= reserved_va) {
289289
uintptr_t alt_pc = (uintptr_t)getAlternate((void *)(uintptr_t)lazypc);
290290
if (alt_pc != (uintptr_t)lazypc) {
291291
lazypc = alt_pc;
@@ -853,7 +853,7 @@ TranslationBlock * kzt_tb_find_exp(
853853
static inline bool cpu_handle_exception(CPUState *cpu, int *ret)
854854
{
855855
#if defined(CONFIG_LATX_KZT)
856-
if (option_kzt) {
856+
if (latx_kzt_runtime_enabled()) {
857857
CPUArchState *env = cpu->env_ptr;
858858
if(env->eip == (uint64_t)&RunFunctionWithState){
859859
*ret = 0xCC;
@@ -945,7 +945,7 @@ static inline bool cpu_handle_interrupt(CPUState *cpu,
945945
TranslationBlock **last_tb)
946946
{
947947
#if defined(CONFIG_LATX_KZT)
948-
if (option_kzt) {
948+
if (latx_kzt_runtime_enabled()) {
949949
CPUArchState *env = cpu->env_ptr;
950950
if(env->eip == (uint64_t)&RunFunctionWithState){
951951
*last_tb = NULL;

accel/tcg/tb-flush.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,7 @@ void do_tb_flush(CPUState *cpu, run_on_cpu_data tb_flush_count)
106106
}
107107
#if defined(CONFIG_LATX_KZT)
108108
CPU_FOREACH(cpu) {
109+
/* The installer also checks the effective library-group mask. */
109110
if (cpu && option_kzt) {
110111
kzt_install_runtime_callbacks(cpu, &info1);
111112
}

accel/tcg/translate-all.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3817,7 +3817,7 @@ void *page_alloc_target_data(target_ulong address, size_t size)
38173817
bool page_check_range(target_ulong start, target_ulong len, int flags)
38183818
{
38193819
#if defined(CONFIG_LATX_KZT)
3820-
if (option_kzt && start > reserved_va) {
3820+
if (latx_kzt_runtime_enabled() && start > reserved_va) {
38213821
return true;
38223822
}
38233823
#endif

accel/tcg/user-exec.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1360,7 +1360,8 @@ int cpu_signal_handler(int host_signum, void *pinfo,
13601360
}
13611361
}
13621362
#if defined(CONFIG_LATX_KZT)
1363-
if (option_kzt && (int64_t)info->si_addr >= info1.start_data &&
1363+
if (latx_kzt_runtime_enabled() &&
1364+
(int64_t)info->si_addr >= info1.start_data &&
13641365
(int64_t)info->si_addr <= info1.end_data &&
13651366
info->si_signo == SIGSEGV) {
13661367
int ret = elf_data_interpret(info, uc);
@@ -1369,7 +1370,7 @@ int cpu_signal_handler(int host_signum, void *pinfo,
13691370
return 1;
13701371
}
13711372
}
1372-
if (option_kzt && info->si_signo == SIGSEGV) {
1373+
if (latx_kzt_runtime_enabled() && info->si_signo == SIGSEGV) {
13731374
for (int i = 0; i < sizeof(elf_native_func) / sizeof(int); i++) {
13741375
if (!find_stack_func_exist(elf_native_func[i], 4)) {
13751376
int ret = elf_data_interpret(info, uc);

include/exec/cpu_ldst.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@
5858
#define CPU_LDST_H
5959

6060
#if defined(CONFIG_LATX_KZT)
61-
extern int option_kzt;
61+
#include "kzt-runtime.h"
6262
#endif
6363
#if defined(CONFIG_USER_ONLY)
6464
/* sparc32plus has 64bit long but 32bit space address
@@ -93,7 +93,7 @@ static inline void *g2h(CPUState *cs, abi_ptr x)
9393
static inline bool guest_addr_valid_untagged(abi_ulong x)
9494
{
9595
#if defined(CONFIG_LATX_KZT)
96-
if (option_kzt) {
96+
if (latx_kzt_runtime_enabled()) {
9797
return true;
9898
} else
9999
#endif
@@ -103,7 +103,7 @@ static inline bool guest_addr_valid_untagged(abi_ulong x)
103103
static inline bool guest_range_valid_untagged(abi_ulong start, abi_ulong len)
104104
{
105105
#if defined(CONFIG_LATX_KZT)
106-
if (option_kzt) {
106+
if (latx_kzt_runtime_enabled()) {
107107
return true;
108108
} else
109109
#endif

linux-user/i386/cpu_loop.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -221,7 +221,7 @@ void cpu_loop(CPUX86State *env)
221221
cpu_exec_end(cs);
222222
process_queued_cpu_work(cs);
223223
#if defined(CONFIG_LATX_KZT)
224-
if(option_kzt && trapnr == 0xCC)
224+
if (latx_kzt_runtime_enabled() && trapnr == 0xCC)
225225
break;
226226
#endif
227227
switch(trapnr) {

linux-user/signal.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1308,7 +1308,8 @@ static void host_signal_handler(int host_signum, siginfo_t *info,
13081308
cpu_exit(thread_cpu);
13091309
#if defined(CONFIG_LATX_KZT)
13101310
#define SIGCANCEL __SIGRTMIN
1311-
if (host_signum == SIGCANCEL + 2 && option_kzt && pc > reserved_va) {
1311+
if (host_signum == SIGCANCEL + 2 && latx_kzt_runtime_enabled() &&
1312+
pc > reserved_va) {
13121313
#define BTSIZT 64
13131314
void * array[BTSIZT] = {0};
13141315
size_t size;

target/i386/latx/context/elfloader.c

Lines changed: 55 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -653,7 +653,22 @@ static int isChromeApp(elfheader_t* h, int con_score)
653653
return 0;
654654
}
655655

656-
int CheckEnableKZT(elfheader_t* h, char** target_argv, int target_argc)
656+
static bool kzt_soname_matches_filename(const char *soname,
657+
const char *filename)
658+
{
659+
const char *suffix = strstr(soname, ".so");
660+
size_t prefix_length;
661+
662+
if (!suffix) {
663+
return !strcmp(soname, filename);
664+
}
665+
prefix_length = suffix - soname + strlen(".so");
666+
return !strncmp(soname, filename, prefix_length) &&
667+
(filename[prefix_length] == '\0' ||
668+
filename[prefix_length] == '.');
669+
}
670+
671+
void CheckEnableKZT(elfheader_t *h, char **target_argv, int target_argc)
657672
{
658673
path_collection_t lib_path = {0,0,0};
659674
char *rpathref;
@@ -675,11 +690,6 @@ int CheckEnableKZT(elfheader_t* h, char** target_argv, int target_argc)
675690
}
676691
break;
677692
case DT_NEEDED:
678-
if (strstr(h->DynStrTab+h->delta+h->Dynamic[i].d_un.d_val, "libgtk-3.so")||//skip gtk
679-
strstr(h->DynStrTab+h->delta+h->Dynamic[i].d_un.d_val, "libXt.so")) {//skip mainexec needed libXt.so
680-
printf_log(LOG_INFO, "latx find libgtk or libXt, skip kzt\n");
681-
return 0;
682-
}
683693
++needlibcnt;
684694
break;
685695
}
@@ -696,11 +706,6 @@ int CheckEnableKZT(elfheader_t* h, char** target_argv, int target_argc)
696706
if (!kzt_library_is_enabled(wrappedlibs_name[i])) {
697707
continue;
698708
}
699-
char *p = box_strdup(wrappedlibs_name[i]);
700-
char *p2 = strchr(p, '.');
701-
if (++p2) {
702-
*p2 = '\0';
703-
}
704709
for (int j=0; j<lib_path.size; ++j) {
705710
DIR *dir = opendir(lib_path.paths[j]);
706711
if (dir == NULL) {
@@ -710,26 +715,56 @@ int CheckEnableKZT(elfheader_t* h, char** target_argv, int target_argc)
710715

711716
struct dirent *entry;
712717
while ((entry = readdir(dir)) != NULL) {
713-
if (entry->d_type == DT_REG) { // Check if it's a regular file
714-
if (!strncmp(entry->d_name, p, strlen(p))) {
715-
printf_log(LOG_INFO, "File starting with '%s' found: %s at %s\n", p, entry->d_name, lib_path.paths[j]);
716-
closedir(dir);
717-
FreeCollection(&lib_path);
718-
return 0;
719-
}
718+
char candidate[PATH_MAX];
719+
char reason[PATH_MAX + 96];
720+
KztLibraryGroup group;
721+
int candidate_length;
722+
723+
if (!kzt_soname_matches_filename(wrappedlibs_name[i],
724+
entry->d_name)) {
725+
continue;
720726
}
727+
candidate_length = snprintf(
728+
candidate, sizeof(candidate), "%s%s%s", lib_path.paths[j],
729+
lib_path.paths[j][strlen(lib_path.paths[j]) - 1] == '/'
730+
? "" : "/",
731+
entry->d_name);
732+
if (candidate_length < 0 ||
733+
(size_t)candidate_length >= sizeof(candidate)) {
734+
continue;
735+
}
736+
if (!FileExist(candidate, IS_FILE) ||
737+
!FileIsX64ELF(candidate)) {
738+
continue;
739+
}
740+
group = kzt_group_for_library(wrappedlibs_name[i]);
741+
snprintf(reason, sizeof(reason),
742+
"guest %s resolved from application path %s",
743+
entry->d_name, lib_path.paths[j]);
744+
kzt_group_disable(group, reason);
745+
break;
721746
}
722747
closedir(dir);
748+
if (!kzt_library_is_enabled(wrappedlibs_name[i])) {
749+
break;
750+
}
723751
}
724752
}
725753
FreeCollection(&lib_path);
726754
//disable kzt chrome app
727755
for(int i = 0; i < target_argc; i++) {
728756
if (!strcmp(target_argv[i], "--no-sandbox")) {
729-
return !isChromeApp(h, 5);
757+
if (isChromeApp(h, 5)) {
758+
kzt_groups_disable_all(
759+
"main executable matched the Chrome compatibility gate");
760+
}
761+
return;
730762
}
731763
}
732-
return !isChromeApp(h, 10);
764+
if (isChromeApp(h, 10)) {
765+
kzt_groups_disable_all(
766+
"main executable matched the Chrome compatibility gate");
767+
}
733768
}
734769

735770
const char* ElfName(elfheader_t* head)

target/i386/latx/context/kzt-groups.c

Lines changed: 60 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,8 @@ static const KztLibraryGroupEntry kzt_library_groups[] = {
3939
#undef GO
4040
#undef GOALIAS
4141

42-
static uint32_t enabled_groups = KZT_GROUP_STABLE;
42+
static uint32_t requested_groups = KZT_GROUP_STABLE;
43+
uint32_t kzt_effective_groups = KZT_GROUP_STABLE;
4344
static bool group_log_enabled;
4445
static char group_error[128];
4546
static bool library_decision_logged[ARRAY_SIZE(kzt_library_groups)];
@@ -268,7 +269,7 @@ static void kzt_groups_log_effective(const char *spec, uint32_t dependencies,
268269
if (pruned) {
269270
kzt_groups_log_mask("disabled dependent library groups", pruned);
270271
}
271-
kzt_groups_log_mask("enabled library groups", enabled_groups);
272+
kzt_groups_log_mask("enabled library groups", kzt_effective_groups);
272273
}
273274

274275
KztLibraryGroup kzt_group_for_library(const char *soname)
@@ -326,7 +327,8 @@ void kzt_groups_print_available(void)
326327

327328
void kzt_groups_reset(void)
328329
{
329-
enabled_groups = KZT_GROUP_STABLE;
330+
requested_groups = KZT_GROUP_STABLE;
331+
kzt_effective_groups = KZT_GROUP_STABLE;
330332
group_log_enabled = false;
331333
group_error[0] = '\0';
332334
memset(library_decision_logged, 0, sizeof(library_decision_logged));
@@ -349,7 +351,8 @@ bool kzt_groups_configure(const char *spec, bool log_enabled)
349351
memset(library_decision_logged, 0, sizeof(library_decision_logged));
350352
if (!kzt_parse_group_spec(spec, &mode, &selected, &added, &removed,
351353
&use_stable)) {
352-
enabled_groups = KZT_GROUP_NONE;
354+
requested_groups = KZT_GROUP_NONE;
355+
kzt_effective_groups = KZT_GROUP_NONE;
353356
group_log_enabled = log_enabled;
354357
return false;
355358
}
@@ -367,28 +370,75 @@ bool kzt_groups_configure(const char *spec, bool log_enabled)
367370
dependencies = groups & ~before_dependencies;
368371
groups &= ~removed;
369372
before_prune = groups;
370-
enabled_groups = kzt_prune_missing_dependencies(groups);
371-
pruned = before_prune & ~enabled_groups;
373+
requested_groups = kzt_prune_missing_dependencies(groups);
374+
kzt_effective_groups = requested_groups;
375+
pruned = before_prune & ~kzt_effective_groups;
372376
group_log_enabled = log_enabled;
373377
kzt_groups_log_effective(spec, dependencies, removed, pruned);
374378
return true;
375379
}
376380

377381
void kzt_groups_reject_configuration(const char *reason, bool log_enabled)
378382
{
379-
enabled_groups = KZT_GROUP_NONE;
383+
requested_groups = KZT_GROUP_NONE;
384+
kzt_effective_groups = KZT_GROUP_NONE;
380385
group_log_enabled = log_enabled;
381386
snprintf(group_error, sizeof(group_error), "%s", reason);
382387
}
383388

384-
uint32_t kzt_groups_enabled_mask(void)
389+
uint32_t kzt_groups_requested_mask(void)
385390
{
386-
return enabled_groups;
391+
return requested_groups;
392+
}
393+
394+
uint32_t kzt_groups_effective_mask(void)
395+
{
396+
return kzt_effective_groups;
397+
}
398+
399+
bool kzt_group_disable(KztLibraryGroup group, const char *reason)
400+
{
401+
uint32_t before_prune;
402+
uint32_t pruned;
403+
404+
if (group == KZT_GROUP_NONE || !(kzt_effective_groups & group)) {
405+
return false;
406+
}
407+
408+
kzt_effective_groups &= ~group;
409+
before_prune = kzt_effective_groups;
410+
kzt_effective_groups = kzt_prune_missing_dependencies(kzt_effective_groups);
411+
pruned = before_prune & ~kzt_effective_groups;
412+
413+
if (group_log_enabled) {
414+
fprintf(stderr, "KZT: disabled library group %s: %s\n",
415+
kzt_group_name(group),
416+
reason ? reason : "compatibility check failed");
417+
if (pruned) {
418+
kzt_groups_log_mask("disabled dependent library groups", pruned);
419+
}
420+
kzt_groups_log_mask("enabled library groups", kzt_effective_groups);
421+
}
422+
return true;
423+
}
424+
425+
void kzt_groups_disable_all(const char *reason)
426+
{
427+
if (kzt_effective_groups == KZT_GROUP_NONE) {
428+
return;
429+
}
430+
kzt_effective_groups = KZT_GROUP_NONE;
431+
if (group_log_enabled) {
432+
fprintf(stderr, "KZT: disabled all library groups: %s\n",
433+
reason ? reason : "compatibility check failed");
434+
kzt_groups_log_mask("enabled library groups", kzt_effective_groups);
435+
}
387436
}
388437

389438
bool kzt_group_is_enabled(KztLibraryGroup group)
390439
{
391-
return group != KZT_GROUP_NONE && (enabled_groups & group) == group;
440+
return group != KZT_GROUP_NONE &&
441+
(kzt_effective_groups & group) == group;
392442
}
393443

394444
bool kzt_library_is_enabled(const char *soname)

0 commit comments

Comments
 (0)