Skip to content

CUBRID Utilities Miscellany — commdb, gencat, generate_timezone, daemon, cubrid_version, pl Bootstrap Helper

The six utilities covered here all have their own main (or nearly so), but each is too small to support its own 30–50 KB analysis. They share three traits that justify co-documentation: each is purely a thin wrapper around a CUBRID library function or a small POSIX helper; none participates in the SA/CS dual-launcher pattern the bigger utilities use; and each maps to a single, narrow operational concern. This document covers all six at the granularity each deserves.

The six divide into three families:

FamilyTools
Runtime probes / helperscommdb, pl, daemon
Build-time generatorsgencat, generate_timezone
Triviacubrid_version

The runtime probes are tools operators may invoke directly or that other utilities fork. The build-time generators run during the CUBRID build and produce artifacts compiled into the engine or shipped alongside it. The single trivia tool is a no-op shell on top of PRODUCT_STRING.

Where these tools also exist as cubrid <verb> forms in the unified admin CLI (cubrid commdb, cubrid pl ping, cubrid --version), the cubrid binary’s dispatcher (see cubrid-cub-admin.md) routes to in-process equivalents instead of forking these standalone binaries — but the standalone binaries are still installed and usable for the legacy invocation shape.

File. src/executables/commdb.c (~1480 lines).

Purpose. Probe and command cub_master directly via its listening socket, without going through the unified cubrid binary. Predates the cubrid commdb form; both still ship.

Argv shape.

commdb [-P] [-O] [-S <db>] [-A] [-h <host>] [-c <db>]
[--server-shutdown=...] [--all-list] [--server-list] ...

The short flags (-P, -O, -S, -A, -h) are the legacy form; util_front.c’s us_Commdb_map translates them to long forms before execvp-ing here when the user invoked the modern cubrid commdb.

What it sends.

FlagMaster opcodeResult
-P (server-list)GET_SERVER_LISTPrint one line per registered cub_server
-O (all-list)GET_ALL_LISTPrint servers + brokers + pl
-S <db> (shutdown one)KILL_SLAVE_SERVERSend shutdown request to the named server
-A (shutdown all)KILL_ALL_HA_PROCESS then per-server KILL_SLAVE_SERVERShut down everything master knows about
-c <db> (server status)GET_SERVER_STATEPrint one server’s HA mode + ping

The opcode taxonomy and per-opcode handler set are documented in cubrid-master-process.md §“Request dispatch”.

Why it still exists. Two reasons. First, the modern cubrid commdb is implemented in util_service.c via process_master helpers that talk to master in-process — useful for normal admin scripts. The standalone commdb is a pure RPC client that doesn’t need cubrid.conf to be loadable or any of the family-dispatcher logic; it’s the right tool for emergency probes when cubrid itself can’t read its config. Second, the cub_master RPC interface predates the unified admin CLI by years; many operator scripts still call commdb directly.

Position hints.

SymbolPath
mainsrc/executables/commdb.c:1209

File. src/executables/pl.cpp (~720 lines).

Purpose. Lifecycle commands for the per-database cub_pl JVM process (the one that hosts JavaSP and PL/CSQL — see cubrid-pl-javasp.md §“Process topology”). Issued by cubrid pl ping/start/stop/restart/status <db>; can also be invoked directly.

Argv shape.

pl <command> <db_name>

where <command> is ping, start, stop, restart, or status.

What it does.

// pl.cpp::main (paraphrased)
os_set_signal_handler (SIGABRT/TERM/ILL/FPE/BUS/SEGV/SYS, pl_signal_handler);
er_init (NULL_DEVICE, ER_NEVER_EXIT); // suppress msgs for ping
pl_check_argument (argc, argv, command, db_name);
pl_check_database (db_name, pathname); // verify db exists
if (command != "ping")
er_init ("pl/<db>_pl.err", ER_NEVER_EXIT); // real error log
PL_SERVER_INFO pl_info = ...;
pl_get_server_info (db_name, pl_info); // read $CUBRID/var/pl_<db>.info
if (command == "ping") {
if (pl_info.pid == PL_PID_DISABLED ||
is_terminated_process (pl_info.pid)) {
printf ("NO_PROCESS");
exit (NO_ERROR);
}
/* try to connect to the cub_pl socket and exchange a ping packet */
}
/* ... start / stop / restart / status branches ... */

The per-database pl_<db>.info file (in $CUBRID/var/) is the rendezvous file cub_pl writes its PID and port into when it starts (see cubrid-pl-javasp.md §“Discovery and rendezvous”). This helper just reads that file and either acts on it directly (ping, status, stop) or forks cub_pl (start) / re-execs (restart).

Why it’s a separate binary. Because cub_pl lifecycle needs to work even when the database server (cub_server) isn’t running — the JVM is its own process and can be inspected/managed independently. Bundling this into util_service.c::process_pl as an in-process call would require cub_master to mediate; the standalone helper avoids that dependency.

Position hints.

SymbolPath
mainsrc/executables/pl.cpp:160

File. src/executables/daemon.c (~40 lines).

Purpose. A nearly-empty helper used by other binaries that need to detach themselves from a controlling terminal but don’t want to inline the daemonisation idiom. Called from inside specific scripts and one-shot binaries; not generally invoked by operators.

What it does. Standard double-fork: fork(), child does setsid(), child fork()s again so the grandchild has no controlling terminal, parent and intermediate child exit. Equivalent to start-stop-daemon --background on Debian, used when systemd / launchd isn’t available.

The implementation is small enough that other binaries duplicate the idiom inline (master.c::css_daemon_start is the canonical example; see cubrid-master-process.md); this standalone helper exists for the few build-time scripts and test harnesses that prefer to invoke it as an external tool.

File. src/executables/cubrid_version.c (~37 lines).

Purpose. Prints PRODUCT_STRING (the canonical CUBRID version banner like CUBRID 11.3.1.0001) and exits.

Argv shape. None; no flags. Ignores any args.

What it does.

int main (int argc, char *argv[]) {
printf ("%s\n", PRODUCT_STRING);
return EXIT_SUCCESS;
}

(Slightly more elaborate in the actual file — pulls in the release-info library and uses rel_release_string() so the output adapts to build-time release patches.)

Why it’s a separate binary. Convenience for shell scripts that need the version string but don’t want to parse cubrid --version’s longer output. Operators and CI pipelines call cubrid_version for fixed-format output suitable for grep/awk.

File. src/executables/gencat.c (~1130 lines).

Provenance. NetBSD gencat(1) (from src/usr.bin/gencat/gencat.c in NetBSD), imported essentially verbatim with copyright preserved. The CUBRID build ships its own copy because not every platform’s libc provides a gencat binary, and the on-disk format CUBRID uses (MSGCAT_CATALOG_* table reads from .cat binary files generated by this tool) must be byte-compatible with NetBSD’s interpretation.

What it compiles. A .msg source file (one per locale/component) into a binary .cat file:

$set 1
1 "First message"
2 "Second message with %s placeholders"
$set 2
1 "Another set"

Becomes a binary .cat file with set/message tables that the runtime catopen()/catgets() reads. CUBRID uses these for all user-facing text — see MSGCAT_CATALOG_CSQL / MSGCAT_CATALOG_UTILS / MSGCAT_CATALOG_LOCALE referenced throughout the codebase.

Build-time only. Operators don’t run this directly. The CMake build invokes gencat per locale to produce the .cat files installed under $CUBRID/locales/<locale>/.

Position hints.

SymbolPath
mainsrc/executables/gencat.c:205

generate_timezone — tzdata to C source compiler

Section titled “generate_timezone — tzdata to C source compiler”

File. src/executables/generate_timezone.cpp (62 lines).

Purpose. Build-time tool that consumes IANA tzdata and produces a C source file (timezones.c) compiled into the cubrid_timezones shared library. The runtime tz functions (tz_id_to_str, datetime offset arithmetic, etc.) read the generated tables; updating to a new IANA release means re-running this tool against new tzdata and rebuilding.

Argv shape.

generate_timezone <input_tzdata_path> <output_timezones.c_path>

What it does.

int main (int argc, char **argv) {
if (argc != 3) { usage (); return EXIT_FAILURE; }
const char *tzdata_input_path = argv[1];
const char *timezones_dot_c_output_path = argv[2];
char checksum_str[TZ_CHECKSUM_SIZE + 1] = {0};
if (timezone_compile_data (tzdata_input_path, TZ_GEN_TYPE_NEW, NULL,
timezones_dot_c_output_path,
checksum_str) != NO_ERROR) {
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}

A 62-line wrapper around timezone_compile_data (declared in tz_compile.h, implemented in src/base/). The actual parsing of IANA tzdata files lives there; this binary is just a CLI shell.

Build-time only. Operators don’t run this either. The CMake cubrid_timezones target invokes it during build.

The pair (this tool + cubrid gen_tz + cubrid dump_tz, which are runtime variants registered in ua_Utility_Map) lets operators generate per-database tz tables at runtime if they need locales the build-time set doesn’t include — see cubrid-timezone.md.

Position hints.

SymbolPath
mainsrc/executables/generate_timezone.cpp:38
  • All six predate the unified cubrid admin CLI. Each ships a standalone binary so legacy scripts continue to work. The modern equivalents inside cubrid (e.g., cubrid commdb, cubrid pl ping, cubrid --version) call into the same library functions or do the same RPC, but via the dispatcher in util_service.c rather than via fork/exec of these binaries.
  • gencat and generate_timezone are build-time only. Mentioning them as runtime utilities is a category error; they appear in src/executables/ because the CMake build treats them as binaries to compile, but they don’t ship as operator tools.
  • commdb -h <host> exists for cross-host probes but is rarely used because cub_master’s default port is firewalled off in production. Most operator workflows are local-only.
  • pl is conceptually a child of process_pl in util_service.c. Operators invoking cubrid pl <verb> reach process_pl first, which in turn forks pl (or, for some verbs, calls the same library functions in-process). The standalone binary is the canonical implementation; process_pl is the unified-CLI integration.
  • daemon.c is intentionally minimal. It’s not a user-facing tool; it’s a build artefact for scripts that want a forking helper without writing C themselves.
  • commdb vs. cubrid commdb deprecation. With process_master available in-process, the standalone binary is largely redundant. A documented deprecation timeline doesn’t exist; both are shipped because removing the standalone would break legacy ops scripts.
  • gencat upstream sync. The NetBSD source has evolved since the import; periodic re-sync would pick up bug fixes but risks breaking byte compatibility with already-shipped .cat files. The trade-off isn’t currently being made; the imported version is treated as frozen.
  • generate_timezone testability. The 62-line wrapper has no unit tests; the only validation is CMake building successfully. Bad tzdata produces a meaningful error from timezone_compile_data, which propagates as an EXIT_FAILURE, but the wrapper itself isn’t exercised in CI as a separate unit.
  • cubrid_version vs. cubrid --version. The two produce slightly different output formats (the standalone is PRODUCT_STRING exactly; cubrid --version adds a few decorative lines from the message catalog). Scripts that parse output should explicitly choose one and not switch.
  • src/executables/commdb.c — master-process RPC client
  • src/executables/pl.cppcub_pl JVM lifecycle helper
  • src/executables/daemon.c — fork/setsid wrapper
  • src/executables/gencat.c — NetBSD-imported POSIX message-catalog compiler
  • src/executables/generate_timezone.cpp — tzdata → C source build-time tool
  • src/executables/cubrid_version.c — version printer
  • src/executables/AGENTS.md — agent guide
  • Adjacent docs: cubrid-cub-admin.md (the unified admin CLI that supersedes most of these for modern invocations), cubrid-master-process.md (the daemon commdb talks to; documents the request opcode taxonomy this client sends), cubrid-pl-javasp.md (the JVM pl manages; documents the rendezvous file pl reads), cubrid-timezone.md (the runtime tz infrastructure consuming what generate_timezone produces at build time)