You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
With the host code now separable, this adds the target that makes use of it.
cuopt_client holds the host-side problem representation (parsers, data_model_view,
mps_data_model, writers), the gRPC wire protocol (generated protos + mappers) and the
LP/MIP gRPC client. libcuopt and cuopt_grpc_server both link it, so there is one mapper
implementation rather than a client-side fork.
Built as an OBJECT library plus a SHARED library, mirroring cuopt_objs/cuopt.
cuopt_static embeds the objects directly rather than linking the shared library, because
the internal test binaries reach parser internals such as mps_phase_registry_t.
Three constraints are worth knowing, because each of them produced a bug during
development that only surfaced at runtime:
* The routing gRPC arm stays in libcuopt. Its mappers contain no raft/rmm/thrust, but they
call routing::solver_settings_t and routing::assignment_t accessors that live in CUDA
translation units -- so putting them in cuopt_client creates a cycle
(libcuopt -> cuopt_client -> libcuopt). ldd -r does not flag it, because both libraries
are always loaded together; it surfaces only when the call happens, as
"undefined symbol: routing::solver_settings_t::get_time_limit". Moving that arm down
needs its host-only accessors split out first, exactly as was done for LP/MIP.
* solver_settings.cpp deliberately does not use `template class`. That instantiates every
member, including the constructor, which builds a pdlp_solver_settings_t holding a
pdlp_warm_start_data_t by value -- whose ctor is CUDA-side. Members are instantiated
individually instead, and the constructor itself moved to solver_settings_gpu.cu, so the
client library references nothing it cannot resolve.
* cuopt_client uses default visibility, unlike cuopt_objs. libcuopt depends on roughly 214
of its symbols -- essentially the whole host-side API -- because this library was carved
out of the internals rather than designed as a curated CUOPT_EXPORT surface. Hiding them
makes libcuopt.so fail to load.
Also moves logger.cpp into the client sources: both the parsers and the gRPC code include
<utilities/logger.hpp>.
Result:
libcuopt_client.so NEEDED: libgrpc++, libprotobuf, libabseil, librapids_logger,
libc, libstdc++, libgomp, libdl
-- no libcudart, no rmm, no raft, no cudss
undefined cuopt symbols: 0
Note that raft/rmm headers are still needed at *build* time (the CPU headers transitively
include them), which costs nothing at runtime because the device getters throw. Separating
the headers is follow-up work, and is what a standalone client package would additionally
require.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Signed-off-by: Ramakrishna Prabhu <ramakrishnap@nvidia.com>
0 commit comments