diff options
author | Lauri Aarnio <Lauri.Aarnio@iki.fi> | 2008-10-23 17:27:55 +0300 |
---|---|---|
committer | Lauri Leukkunen <lle@rahina.org> | 2008-10-23 19:18:01 +0300 |
commit | 0a44f98a97a22eb57ac34dea67623a2188038eda (patch) | |
tree | 23530e1eb51f5dab742443018eb14220c5b259d5 /lua_scripts | |
parent | b779e037736239d3b8005506b898456c66c11a2a (diff) |
Added path reversing logic; getcwd() etc now return backward-mapped results - i.e. getcwd(), realpath(), get_current_dir_name_gate() and getwd() now return the place where SB2 pretends to be, not the real path anymore - reverse mapping rules are created automatically when the session is created. However, there are still some situations where reverse mapping is disabled (see lua_scripts/create_reverse_rules.lua for details) - This also fixes a nasty bug with "mkdir -p" (which created directories to wrong locations in certain situations. "mkdir" witout "-p" was OK) - sb2-show: added new command "realcwd" - "devel" mapping mode: some paths were classified as virtual (virtual_path is a new attribute for rules: It disables reversing of that rule) - "simple" mapping mode: ~/.scratchbox2, .../share/scratchbox2 and /usr/bin/sb2-show were added to mapping rules - luaif.c: sb.decolonize_path() was disabled (It isn't anymore used from our Lua scripts, but I didn't
Diffstat (limited to 'lua_scripts')
-rw-r--r-- | lua_scripts/create_reverse_rules.lua | 255 | ||||
-rw-r--r-- | lua_scripts/mapping.lua | 65 | ||||
-rw-r--r-- | lua_scripts/pathmaps/devel/00_default.lua | 9 | ||||
-rw-r--r-- | lua_scripts/pathmaps/simple/00_default.lua | 9 |
4 files changed, 332 insertions, 6 deletions
diff --git a/lua_scripts/create_reverse_rules.lua b/lua_scripts/create_reverse_rules.lua new file mode 100644 index 0000000..ad9f758 --- /dev/null +++ b/lua_scripts/create_reverse_rules.lua @@ -0,0 +1,255 @@ +-- Copyright (c) 2008 Nokia Corporation. +-- Author: Lauri T. Aarnio +-- +-- Licensed under MIT license + +-- This script is executed once after a new SB2 session has been created, +-- to create reversing rules for path mapping (see utils/sb2). +-- This is still simple, and may not work in all cases: This script +-- will shut down if problems are detected (then path reversing won't be +-- available and SB2 works just as it did before this feature was implemented) +-- +-- FIXME: +-- 1. Rules with conditional actions are not reversed correctly. Basically, +-- this script just gives up and marks the destinations with "use_orig_path". +-- This should be fixed, even if it is not a problem with our current +-- "official" mapping modes. +-- +-- 2. Reverse rules won't be created if the forward rules use "func_name" +-- conditions. It might be possible to fix that, but "func_names" certainly +-- complicate sorting of the generated reversing rules. +-- +-- 3. Rule chains with "next_chain" set to something else than 'nil' +-- are not currently supported. + +allow_reversing = true -- default = create reverse rules. + +-- Order of reverse rules is not necessarily the same as order of forward rules +function test_rev_rule_position(output_rules, d_path) + local n + for n=1,table.maxn(output_rules) do + local rule = output_rules[n] + if (rule.prefix and (rule.prefix ~= "") and + (isprefix(rule.prefix, d_path))) then + return n + end + -- "path" rules: (exact match) + if (rule.path == d_path) then + return n + end + end + return nil +end + +function reverse_one_rule(output_rules, rule, n) + local new_rule = {} + new_rule.comments = {} + + if rule.name then + new_rule.name = string.format( + "Rev: %s (%d)", rule.name, n) + else + new_rule.name = string.format( + "Rev: Rule %d", n) + end + + local forward_path + if (rule.prefix) then + forward_path = rule.prefix + elseif (rule.path) then + forward_path = rule.path + else + forward_path = nil + new_rule.error = string.format( + "--ERROR: Rule '%s' does not contain 'prefix' or 'path'", + new_rule.name) + end + + if (rule.func_name ~= nil) then + allow_reversing = false + end + + local d_path + if (rule.use_orig_path) then + new_rule.use_orig_path = true + d_path = forward_path + elseif (rule.actions) then + -- FIXME: To be implemented. See the "TODO" list at top. + new_rule.use_orig_path = true + d_path = forward_path + elseif (rule.map_to) then + d_path = rule.map_to .. forward_path + new_rule.replace_by = forward_path + elseif (rule.replace_by) then + d_path = rule.replace_by + new_rule.replace_by = forward_path + else + new_rule.error = string.format( + "--ERROR: Rule '%s' does not contain any actions", + new_rule.name) + end + + local idx + if (rule.prefix) then + new_rule.prefix = d_path + new_rule.orig_prefix = rule.prefix + idx = test_rev_rule_position(output_rules, d_path..":") + elseif (rule.path) then + new_rule.path = d_path + new_rule.orig_path = rule.path + idx = test_rev_rule_position(output_rules, d_path) + end + + if (idx ~= nil) then + -- a conflict, must reorganize + table.insert(new_rule.comments, string.format( + "--NOTE: '%s' conflicts with '%s', reorganized", + new_rule.name, output_rules[idx].name)) + + local x_path = nil + if (output_rules[idx].prefix) then + x_path = output_rules[idx].prefix + elseif (output_rules[idx].path) then + x_path = output_rules[idx].path + end + + table.insert(output_rules, idx, new_rule) + + if x_path then + local idx2 + idx2 = test_rev_rule_position(output_rules, x_path) + + if idx2 ~= idx+1 then + table.insert(new_rule.comments, string.format( + "--NOTE: '%s' DOUBLE CONFLICT with '%s'", + new_rule.name, output_rules[idx].name)) + end + end + + else + -- no conflicts + table.insert(output_rules, new_rule) + end +end + +function reverse_rules(input_rules) + local output_rules = {} + local n + for n=1,table.maxn(input_rules) do + local rule = input_rules[n] + + if rule.virtual_path then + -- don't reverse virtual paths + print("-- virtual_path set, not reversing", n) + else + reverse_one_rule(output_rules, rule, n) + end + + end + return(output_rules) +end + +function print_rules(rules) + local n + for n=1,table.maxn(rules) do + local rule = rules[n] + + print(string.format("\t{name=\"%s\",", rule.name)) + + local k + for k=1,table.maxn(rule.comments) do + print(rule.comments[k]) + end + + if (rule.orig_prefix) then + print("\t -- orig_prefix", rule.orig_prefix) + end + if (rule.orig_path) then + print("\t -- orig_path", rule.orig_path) + end + + if (rule.prefix) then + print("\t prefix=\""..rule.prefix.."\",") + end + if (rule.path) then + print("\t path=\""..rule.path.."\",") + end + + if (rule.use_orig_path) then + print("\t use_orig_path=true,") + end + -- FIXME: To be implemented. See the "TODO" list at top. + -- elseif (rule.actions) then + -- print("\t -- FIXME: handle 'actions'") + -- print(string.format( + -- "\t %s=\"%s\",\n\t use_orig_path=true},", + -- sel, fwd_target)) + if (rule.map_to) then + print("\t map_to=\""..rule.map_to.."\",") + end + if (rule.replace_by) then + print("\t replace_by=\""..rule.replace_by.."\",") + end + if (rule.error) then + print("\t -- ",rule.error) + allow_reversing = false + end + print("\t},") + end +end + +function process_chains(chains_table) + local n + + for n=1,table.maxn(chains_table) do + if chains_table[n].noentry then + print("-- ========== ",n) + print("-- noentry") + else + print(string.format("-- ======= Chain %d =======",n)) + print(string.format("reverse_chain_%d = {",n)) + + if chains_table[n].next_chain then + -- FIXME: Handle next_chain!!! + print(" -- NOTE: next_chain is not nil,") + print(" -- can't create reversing rules") + allow_reversing = false + else + print(" next_chain=nil,") + end + + if chains_table[n].binary then + print(string.format(" binary=\"%s\",", + chains_table[n].binary,"\n")) + else + print(" binary=nil,") + end + + local rev_rules = reverse_rules(chains_table[n].rules) + if (allow_reversing) then + print(" rules={") + print_rules(rev_rules) + print(" }") + end + print("}") + end + end + + if (allow_reversing) then + print("reverse_chains = {") + for n=1,table.maxn(chains_table) do + if chains_table[n].noentry then + print(string.format(" -- %d = noentry",n)) + else + print(string.format(" reverse_chain_%d,",n)) + end + end + print("}") + else + print("-- Failed to create reverse rules.") + print("reverse_chains = nil") + end +end + +process_chains(active_mode_mapping_rule_chains) + diff --git a/lua_scripts/mapping.lua b/lua_scripts/mapping.lua index f42aee9..1e4adde 100644 --- a/lua_scripts/mapping.lua +++ b/lua_scripts/mapping.lua @@ -133,6 +133,21 @@ active_mode_exec_policy_chains = {} load_and_check_rules() +-- load reverse mapping rules, if those have been created +-- (the file does not exist during the very first round here) +reverse_chains = nil +if (sb.path_exists(session_dir .. "/rev_rules.lua")) then + sb.log("debug", "Loading reverse rules") + do_file(session_dir .. "/rev_rules.lua") +end +if (debug_messages_enabled) then + if reverse_chains ~= nil then + sb.log("debug", "Loaded reverse rules") + else + sb.log("debug", "No reverse rules") + end +end + function sbox_execute_replace_rule(path, replacement, rule) local ret = nil @@ -283,11 +298,20 @@ function find_rule(chain, func, full_path) or string.match(func, wrk.rules[i].func_name))) then -- "prefix" rules: -- compare prefix (only if a non-zero prefix) + local rulename + if (debug_messages_enabled) then + rulename = wrk.rules[i].name + if rulename == nil then + rulename = string.format("#%d",i) + end + end if (wrk.rules[i].prefix and (wrk.rules[i].prefix ~= "") and (isprefix(wrk.rules[i].prefix, full_path))) then if (debug_messages_enabled) then - sb.log("noise", string.format("selected prefix rule %d (%s)", i, wrk.rules[i].prefix)) + sb.log("noise", string.format( + "selected prefix rule '%s' (%s)", + rulename, wrk.rules[i].prefix)) end min_path_len = string.len(wrk.rules[i].prefix) return wrk.rules[i], min_path_len @@ -295,7 +319,9 @@ function find_rule(chain, func, full_path) -- "path" rules: (exact match) if (wrk.rules[i].path == full_path) then if (debug_messages_enabled) then - sb.log("noise", string.format("selected path rule %d (%s)", i, wrk.rules[i].path)) + sb.log("noise", string.format( + "selected path rule '%s' (%s)", + rulename, wrk.rules[i].path)) end min_path_len = string.len(wrk.rules[i].path) return wrk.rules[i], min_path_len @@ -427,3 +453,38 @@ function sb_find_exec_policy(binaryname, mapped_file) return 0, nil end +-- sbox_reverse_path is called from libsb2.so +-- returns "orig_path" +function sbox_reverse_path(binary_name, func_name, full_path) + -- loop through the chains, first match is used + local min_path_len = 0 + local rule = nil + local chain = nil + + if (reverse_chains ~= nil) then + chain = find_chain(reverse_chains, binary_name) + end + if (chain == nil) then + -- reverse mapping is an optional feature, + -- so it isn't really an error if the rule + -- can't be found. + sb.log("info", string.format("Unable to find REVERSE chain for: %s(%s)", + func_name, full_path)) + + return nil + end + + rule, min_path_len = find_rule(chain, func_name, full_path) + if (not rule) then + -- not even a default rule found + sb.log("info", string.format("Unable to find REVERSE rule for: %s(%s)", func_name, full_path)) + return nil + end + + local rule2, exec_policy2, orig_path, ro2 + rule2, exec_policy2, orig_path, ro2 = sbox_translate_path(rule, + binary_name, func_name, full_path) + + return orig_path +end + diff --git a/lua_scripts/pathmaps/devel/00_default.lua b/lua_scripts/pathmaps/devel/00_default.lua index b38a451..a0febd5 100644 --- a/lua_scripts/pathmaps/devel/00_default.lua +++ b/lua_scripts/pathmaps/devel/00_default.lua @@ -337,28 +337,29 @@ simple_chain = { -- 98. Scratchbox 1 emulation rules -- (some packages have hard-coded paths to the SB1 enviroment; -- replace those by the correct locations in our environment) + -- (these are marked "virtual"; these won't be reversed) -- "libtool" for arm {prefix = "/scratchbox/compilers/cs2005q3.2-glibc2.5-arm/arch_tools/share/libtool", replace_by = sb2_share_dir .. "/libtool", log_level = "warning", - readonly = true}, + readonly = true, virtual_path = true}, -- "libtool" for i386 {prefix = "/scratchbox/compilers/cs2005q3.2-glibc-i386/arch_tools/share", replace_by = tools .. "/usr/share", log_level = "warning", - readonly = true}, + readonly = true, virtual_path = true}, {prefix = "/scratchbox/tools/bin", replace_by = tools .. "/usr/bin", log_level = "warning", - readonly = true}, + readonly = true, virtual_path = true}, {prefix = "/scratchbox/tools/autotools/automake-1.7/share/automake-1.7", replace_by = tools .. "/usr/share/automake-1.7", log_level = "warning", - readonly = true}, + readonly = true, virtual_path = true}, -- otherwise, don't map /scratchbox, some people still -- keep their projects there. diff --git a/lua_scripts/pathmaps/simple/00_default.lua b/lua_scripts/pathmaps/simple/00_default.lua index 44311c0..d1534ff 100644 --- a/lua_scripts/pathmaps/simple/00_default.lua +++ b/lua_scripts/pathmaps/simple/00_default.lua @@ -30,6 +30,15 @@ simple_chain = { replace_by = sbox_dir.."/share/scratchbox2/scripts", readonly = true}, + {prefix = sbox_user_home_dir .. "/.scratchbox2", + use_orig_path = true}, + + {prefix = sbox_dir .. "/share/scratchbox2", + use_orig_path = true}, + + {path = "/usr/bin/sb2-show", + use_orig_path = true, readonly = true}, + -- ----------------------------------------------- -- 99. Other rules. {prefix = "/lib", map_to = target_root}, |