1. network.rpc.use_xmlrpc and network.rpc.use_jsonrpc: change from
CMD2_VAR_BOOL_U (getter+setter both safe) to CMD2_VAR_BOOL_U_GET
(getter safe, setter trusted-only). Untrusted callers could
previously disable RPC transports entirely.
2. Remove broad catch(std::exception&) and catch(...) from xmlrpc_c.cc
that masked real defects and altered fault semantics.
3. Revert SCGI callback catch-all to re-throw instead of swallowing
exceptions with a generic error response.
Root cause: network.rpc.use_xmlrpc and network.rpc.use_jsonrpc were not
marked as untrusted-safe, but RpcManager::process() calls them before
dispatching to the protocol handler. When an untrusted request arrived,
call_command() threw untrusted_error for these gatekeepers, which escaped
the callback_interrupt_pollling callback and crashed rtorrent.
Fix: Mark network.rpc.use_xmlrpc/jsonrpc as safe (CMD2_VAR_BOOL_U).
Also harden exception safety:
- SCGI callback catch-all now sends a generic error response instead of
re-throwing, since the callback infrastructure may not support
exception propagation.
- xmlrpc_c.cc now has catch(std::exception&) and catch(...) safety nets
after the specific exception handlers.
Replace the v2 blacklist approach with a per-command flag system.
Commands must opt in to being available for untrusted connections
via flag_untrusted_safe (0x400), checked in call_command() which
catches all execution paths including nested commands.
Infrastructure changes:
- Add flag_untrusted_safe to CommandMap
- Add untrusted_error exception type for proper error codes
- Enforce trust check in both call_command() overloads
- Add catch blocks in xmlrpc_c, xmlrpc_tinyxml2, and jsonrpc handlers
- Port SCGI trust state management from v2 (thread_local, header parsing)
- Add _U macro variants in command_helpers.h for safe command registration
- Add CMD2_VAR_*_U and CMD2_VAR_*_U_GET variants for variables
- Close pipe fds on fork failure in ExecFile::execute
- Add exception-safe fclose in cmd_file_append via try/catch
- Add overflow guards before K/M/G bit shifts in parse_whole_value
- Fix %u format for int* in sscanf (change to %d)
- Fix typo "atter"→"after" in error message