update Config

This commit is contained in:
Michael Davidsaver
2020-02-21 09:45:03 -08:00
parent 024185ef81
commit cfa18525cf
4 changed files with 85 additions and 45 deletions
+46 -30
View File
@@ -24,14 +24,14 @@ DEFINE_LOGGER(config, "pvxs.config");
namespace pvxs {
namespace {
void split_addr_into(const char* name, std::vector<std::string>& out, const char *inp)
void split_addr_into(const char* name, std::vector<std::string>& out, const char *inp, uint16_t defaultPort)
{
std::regex word("\\s*(\\S+)(.*)");
std::cmatch M;
while(*inp && std::regex_match(inp, M, word)) {
sockaddr_in addr = {};
if(aToIPAddr(M[1].str().c_str(), 0, &addr)) {
if(aToIPAddr(M[1].str().c_str(), defaultPort, &addr)) {
log_err_printf(config, "%s ignoring invalid '%s'\n", name, M[1].str().c_str());
continue;
}
@@ -123,28 +123,9 @@ namespace server {
Config Config::from_env()
{
Config ret;
ret.udp_port = 5076;
const char* name;
if(const char *env = pickenv(&name, {"EPICS_PVAS_INTF_ADDR_LIST"})) {
split_addr_into(name, ret.interfaces, env);
}
if(auto env = pickenv(&name, {"EPICS_PVAS_BEACON_ADDR_LIST", "EPICS_PVA_ADDR_LIST"})) {
split_addr_into(name, ret.beaconDestinations, env);
}
if(const char *env = pickenv(&name, {"EPICS_PVAS_AUTO_BEACON_ADDR_LIST", "EPICS_PVA_AUTO_ADDR_LIST"})) {
if(epicsStrCaseCmp(env, "YES")==0) {
ret.auto_beacon = true;
} else if(epicsStrCaseCmp(env, "NO")==0) {
ret.auto_beacon = false;
} else {
log_err_printf(serversetup, "%s invalid bool value (YES/NO)", name);
}
}
if(const char *env = pickenv(&name, {"EPICS_PVAS_SERVER_PORT", "EPICS_PVA_SERVER_PORT"})) {
try {
ret.tcp_port = lexical_cast<unsigned short>(env);
@@ -161,6 +142,37 @@ Config Config::from_env()
}
}
if(const char *env = pickenv(&name, {"EPICS_PVAS_INTF_ADDR_LIST"})) {
split_addr_into(name, ret.interfaces, env, ret.tcp_port);
}
if(auto env = pickenv(&name, {"EPICS_PVAS_BEACON_ADDR_LIST", "EPICS_PVA_ADDR_LIST"})) {
split_addr_into(name, ret.beaconDestinations, env, ret.udp_port);
}
if(const char *env = pickenv(&name, {"EPICS_PVAS_AUTO_BEACON_ADDR_LIST", "EPICS_PVA_AUTO_ADDR_LIST"})) {
if(epicsStrCaseCmp(env, "YES")==0) {
ret.auto_beacon = true;
} else if(epicsStrCaseCmp(env, "NO")==0) {
ret.auto_beacon = false;
} else {
log_err_printf(serversetup, "%s invalid bool value (YES/NO)", name);
}
}
return ret;
}
Config Config::localhost()
{
Config ret;
ret.udp_port = 0u;
ret.tcp_port = 0u;
ret.interfaces.emplace_back("127.0.0.1");
ret.auto_beacon = false;
ret.beaconDestinations.emplace_back("127.0.0.1");
return ret;
}
@@ -226,8 +238,20 @@ Config Config::from_env()
const char* name;
if(const char *env = pickenv(&name, {"EPICS_PVA_BROADCAST_PORT"})) {
try {
ret.udp_port = lexical_cast<unsigned short>(env);
}catch(std::exception& e) {
log_err_printf(serversetup, "%s invalid integer : %s", name, e.what());
}
}
if(ret.udp_port==0u) {
log_err_printf(serversetup, "ignoring EPICS_PVA_BROADCAST_PORT=%d", 0);
ret.udp_port = 5076;
}
if(const char *env = pickenv(&name, {"EPICS_PVA_ADDR_LIST"})) {
split_addr_into(name, ret.addressList, env);
split_addr_into(name, ret.addressList, env, ret.udp_port);
}
if(const char *env = pickenv(&name, {"EPICS_PVA_AUTO_ADDR_LIST"})) {
@@ -240,14 +264,6 @@ Config Config::from_env()
}
}
if(const char *env = pickenv(&name, {"EPICS_PVA_BROADCAST_PORT"})) {
try {
ret.udp_port = lexical_cast<unsigned short>(env);
}catch(std::exception& e) {
log_err_printf(serversetup, "%s invalid integer : %s", name, e.what());
}
}
return ret;
}
+1 -2
View File
@@ -216,8 +216,7 @@ struct PVXS_API Config {
//! Create a new client Context using the current configuration.
inline
Context build() const {
Context ret(*this);
return ret;
return Context(*this);
}
};
+24 -13
View File
@@ -22,6 +22,9 @@
#include <pvxs/data.h>
namespace pvxs {
namespace client {
struct Config;
}
namespace server {
struct SharedPV;
@@ -72,6 +75,10 @@ public:
//! effective config
const Config& config() const;
//! Create a client configuration which can communicate with this Server.
//! Suitable for use in self-contained unit-tests.
client::Config clientConfig() const;
//! Add a SharedPV to the builtin StaticSource
Server& addPV(const std::string& name, const SharedPV& pv);
//! Remove a SharedPV from the builtin StaticSource
@@ -115,31 +122,35 @@ struct PVXS_API Config {
//! Supplimented iif auto_beacon==true
std::vector<std::string> beaconDestinations;
//! TCP port to bind. Default is 5075. May be zero.
unsigned short tcp_port;
unsigned short tcp_port = 5075;
//! UDP port to bind. Default is 5076. May be zero, cf. Server::config() to find allocated port.
unsigned short udp_port;
unsigned short udp_port = 5076;
//! Whether to populate the beacon address list automatically. (recommended)
bool auto_beacon;
bool auto_beacon = true;
//! Server unique ID. Only meaningful in readback via Server::config()
std::array<uint8_t, 12> guid;
std::array<uint8_t, 12> guid{};
//! Default configuration using process environment
static Config from_env();
//! Empty config
Config() :tcp_port(5075), udp_port(5076), auto_beacon(true), guid{} {}
//! Configuration limited to the local loopback interface on a randomly choosen port.
//! Suitable for use in self-contained unit-tests.
static Config localhost();
//! Apply rules to translate current requested configuration
//! into one which can actually be loaded.
//! @post auto_beacon==false
//! @post !interfaces.empty()
/** Apply rules to translate current requested configuration
* into one which can actually be loaded based on current host network configuration.
*
* Explicit use of expand() is optional as the Context ctor expands any Config given.
* expand() is provided as a aid to help understand how Context::effective() is arrived at.
*
* @post autoAddrList==false
*/
void expand();
//! Short-hand for @code Server(std::move(*this)) @endcode.
//! Create a new Server using the current configuration.
inline Server build() const {
Server ret(*this);
return ret;
return Server(*this);
}
};
+14
View File
@@ -23,6 +23,7 @@
#include <epicsString.h>
#include <pvxs/server.h>
#include <pvxs/client.h>
#include <pvxs/log.h>
#include "evhelper.h"
#include "serverconn.h"
@@ -139,6 +140,19 @@ const Config& Server::config() const
return pvt->effective;
}
client::Config Server::clientConfig() const
{
if(!pvt)
throw std::logic_error("NULL Server");
client::Config ret;
ret.udp_port = pvt->effective.udp_port;
ret.addressList = pvt->effective.interfaces;
ret.autoAddrList = false;
return ret;
}
Server& Server::addPV(const std::string& name, const SharedPV& pv)
{
if(!pvt)