Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
U
uniset2
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
1
Issues
1
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
UniSet project repositories
uniset2
Commits
9674dd51
Commit
9674dd51
authored
Jun 24, 2021
by
Pavel Vainerman
Committed by
Pavel Vainerman
Jun 30, 2021
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
make style
parent
1d66bfef
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
2215 additions
and
2215 deletions
+2215
-2215
MessageType.cc
src/Core/MessageType.cc
+254
-254
UInterface.cc
src/Core/UInterface.cc
+0
-0
UniSetActivator.cc
src/Core/UniSetActivator.cc
+383
-383
UniSetManager.cc
src/Core/UniSetManager.cc
+499
-499
UniSetObject.cc
src/Core/UniSetObject.cc
+1079
-1079
No files found.
src/Core/MessageType.cc
View file @
9674dd51
...
...
@@ -30,259 +30,259 @@
namespace
uniset
{
//--------------------------------------------------------------------------------------------
std
::
string
strTypeOfMessage
(
int
type
)
{
if
(
type
==
Message
::
SensorInfo
)
return
"SensorInfo"
;
if
(
type
==
Message
::
SysCommand
)
return
"SysCommand"
;
if
(
type
==
Message
::
Confirm
)
return
"Confirm"
;
if
(
type
==
Message
::
Timer
)
return
"Timer"
;
if
(
type
==
Message
::
TextMessage
)
return
"TextMessage"
;
if
(
type
==
Message
::
Unused
)
return
"Unused"
;
return
"Unkown"
;
}
std
::
ostream
&
operator
<<
(
std
::
ostream
&
os
,
const
Message
::
TypeOfMessage
&
t
)
{
return
os
<<
strTypeOfMessage
(
t
);
}
//--------------------------------------------------------------------------------------------
Message
::
Message
()
noexcept
:
type
(
Unused
),
priority
(
Medium
),
node
(
uniset
::
uniset_conf
()
?
uniset
::
uniset_conf
()
->
getLocalNode
()
:
DefaultObjectId
),
supplier
(
DefaultObjectId
),
consumer
(
DefaultObjectId
)
{
tm
=
uniset
::
now_to_timespec
();
}
//--------------------------------------------------------------------------------------------
VoidMessage
::
VoidMessage
(
const
TransportMessage
&
tm
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
assert
(
sizeof
(
VoidMessage
)
>=
sizeof
(
uniset
::
RawDataOfTransportMessage
));
memcpy
(
this
,
&
tm
.
data
,
sizeof
(
tm
.
data
));
consumer
=
tm
.
consumer
;
}
VoidMessage
::
VoidMessage
()
noexcept
{
assert
(
sizeof
(
VoidMessage
)
>=
sizeof
(
uniset
::
RawDataOfTransportMessage
));
}
//--------------------------------------------------------------------------------------------
SensorMessage
::
SensorMessage
()
noexcept
:
id
(
DefaultObjectId
),
value
(
0
),
undefined
(
false
),
sensor_type
(
UniversalIO
::
DI
),
threshold
(
false
),
tid
(
uniset
::
DefaultThresholdId
)
{
type
=
Message
::
SensorInfo
;
sm_tv
=
tm
;
// или инициализировать нулём ?
ci
.
minRaw
=
0
;
ci
.
maxRaw
=
0
;
ci
.
minCal
=
0
;
ci
.
maxCal
=
0
;
ci
.
precision
=
0
;
}
SensorMessage
::
SensorMessage
(
ObjectId
id
,
long
value
,
const
IOController_i
::
CalibrateInfo
&
ci
,
Priority
priority
,
UniversalIO
::
IOType
st
,
ObjectId
consumer
)
noexcept
:
id
(
id
),
value
(
value
),
undefined
(
false
),
sensor_type
(
st
),
ci
(
ci
),
threshold
(
false
),
tid
(
uniset
::
DefaultThresholdId
)
{
type
=
Message
::
SensorInfo
;
this
->
priority
=
priority
;
this
->
consumer
=
consumer
;
sm_tv
=
tm
;
}
SensorMessage
::
SensorMessage
(
int
dummy
)
noexcept
:
Message
(
1
),
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
ci
(
IOController_i
::
CalibrateInfo
())
{
type
=
Message
::
SensorInfo
;
}
SensorMessage
::
SensorMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
SensorInfo
);
}
//--------------------------------------------------------------------------------------------
SystemMessage
::
SystemMessage
()
noexcept
:
command
(
SystemMessage
::
Unknown
)
{
memset
(
data
,
0
,
sizeof
(
data
));
type
=
Message
::
SysCommand
;
}
SystemMessage
::
SystemMessage
(
Command
command
,
Priority
priority
,
ObjectId
consumer
)
noexcept
:
command
(
command
)
{
type
=
Message
::
SysCommand
;
this
->
priority
=
priority
;
this
->
consumer
=
consumer
;
memset
(
data
,
0
,
sizeof
(
data
));
}
SystemMessage
::
SystemMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
SysCommand
);
}
//--------------------------------------------------------------------------------------------
std
::
ostream
&
operator
<<
(
std
::
ostream
&
os
,
const
SystemMessage
::
Command
&
c
)
{
if
(
c
==
SystemMessage
::
Unknown
)
return
os
<<
"Unknown"
;
if
(
c
==
SystemMessage
::
StartUp
)
return
os
<<
"StartUp"
;
if
(
c
==
SystemMessage
::
FoldUp
)
return
os
<<
"FoldUp"
;
if
(
c
==
SystemMessage
::
Finish
)
return
os
<<
"Finish"
;
if
(
c
==
SystemMessage
::
WatchDog
)
return
os
<<
"WatchDog"
;
if
(
c
==
SystemMessage
::
ReConfiguration
)
return
os
<<
"ReConfiguration"
;
if
(
c
==
SystemMessage
::
NetworkInfo
)
return
os
<<
"NetworkInfo"
;
if
(
c
==
SystemMessage
::
LogRotate
)
return
os
<<
"LogRotate"
;
return
os
;
}
//--------------------------------------------------------------------------------------------
TimerMessage
::
TimerMessage
()
:
id
(
uniset
::
DefaultTimerId
)
{
type
=
Message
::
Timer
;
}
TimerMessage
::
TimerMessage
(
uniset
::
TimerId
id
,
Priority
prior
,
ObjectId
cons
)
:
id
(
id
)
{
type
=
Message
::
Timer
;
this
->
consumer
=
cons
;
}
TimerMessage
::
TimerMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
Timer
);
}
//--------------------------------------------------------------------------------------------
ConfirmMessage
::
ConfirmMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
Confirm
);
}
//--------------------------------------------------------------------------------------------
ConfirmMessage
::
ConfirmMessage
(
uniset
::
ObjectId
in_sensor_id
,
const
double
&
in_sensor_value
,
const
timespec
&
in_sensor_time
,
const
timespec
&
in_confirm_time
,
Priority
in_priority
)
noexcept
:
sensor_id
(
in_sensor_id
),
sensor_value
(
in_sensor_value
),
sensor_time
(
in_sensor_time
),
confirm_time
(
in_confirm_time
),
broadcast
(
false
),
forward
(
false
)
{
type
=
Message
::
Confirm
;
priority
=
in_priority
;
}
//--------------------------------------------------------------------------------------------
TextMessage
::
TextMessage
(
const
VoidMessage
*
vmsg
)
noexcept
:
VoidMessage
(
1
)
// dummy constructor
{
assert
(
vmsg
->
type
==
Message
::
TextMessage
);
auto
m
=
static_cast
<
const
TextMessage
*>
(
vmsg
);
if
(
m
)
{
type
=
m
->
type
;
priority
=
m
->
priority
;
node
=
m
->
node
;
tm
=
m
->
tm
;
consumer
=
m
->
consumer
;
supplier
=
m
->
supplier
;
mtype
=
m
->
mtype
;
txt
=
m
->
txt
;
}
}
//--------------------------------------------------------------------------------------------
TextMessage
::
TextMessage
()
noexcept
{
type
=
Message
::
TextMessage
;
}
TextMessage
::
TextMessage
(
const
char
*
msg
,
int
_mtype
,
const
uniset
::
Timespec
&
tm
,
const
::
uniset
::
ProducerInfo
&
pi
,
Priority
prior
,
ObjectId
cons
)
noexcept
{
type
=
Message
::
TextMessage
;
this
->
node
=
pi
.
node
;
this
->
supplier
=
pi
.
id
;
this
->
priority
=
prior
;
this
->
consumer
=
cons
;
this
->
tm
.
tv_sec
=
tm
.
sec
;
this
->
tm
.
tv_nsec
=
tm
.
nsec
;
this
->
txt
=
std
::
string
(
msg
);
this
->
mtype
=
_mtype
;
}
//--------------------------------------------------------------------------------------------
std
::
shared_ptr
<
VoidMessage
>
TextMessage
::
toLocalVoidMessage
()
const
{
uniset
::
ProducerInfo
pi
;
pi
.
id
=
supplier
;
pi
.
node
=
node
;
uniset
::
Timespec
ts
;
ts
.
sec
=
tm
.
tv_sec
;
ts
.
nsec
=
tm
.
tv_nsec
;
auto
tmsg
=
std
::
make_shared
<
TextMessage
>
(
txt
.
c_str
(),
mtype
,
ts
,
pi
,
priority
,
consumer
);
return
std
::
static_pointer_cast
<
VoidMessage
>
(
tmsg
);
}
//--------------------------------------------------------------------------------------------
//--------------------------------------------------------------------------------------------
std
::
string
strTypeOfMessage
(
int
type
)
{
if
(
type
==
Message
::
SensorInfo
)
return
"SensorInfo"
;
if
(
type
==
Message
::
SysCommand
)
return
"SysCommand"
;
if
(
type
==
Message
::
Confirm
)
return
"Confirm"
;
if
(
type
==
Message
::
Timer
)
return
"Timer"
;
if
(
type
==
Message
::
TextMessage
)
return
"TextMessage"
;
if
(
type
==
Message
::
Unused
)
return
"Unused"
;
return
"Unkown"
;
}
std
::
ostream
&
operator
<<
(
std
::
ostream
&
os
,
const
Message
::
TypeOfMessage
&
t
)
{
return
os
<<
strTypeOfMessage
(
t
);
}
//--------------------------------------------------------------------------------------------
Message
::
Message
()
noexcept
:
type
(
Unused
),
priority
(
Medium
),
node
(
uniset
::
uniset_conf
()
?
uniset
::
uniset_conf
()
->
getLocalNode
()
:
DefaultObjectId
),
supplier
(
DefaultObjectId
),
consumer
(
DefaultObjectId
)
{
tm
=
uniset
::
now_to_timespec
();
}
//--------------------------------------------------------------------------------------------
VoidMessage
::
VoidMessage
(
const
TransportMessage
&
tm
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
assert
(
sizeof
(
VoidMessage
)
>=
sizeof
(
uniset
::
RawDataOfTransportMessage
));
memcpy
(
this
,
&
tm
.
data
,
sizeof
(
tm
.
data
));
consumer
=
tm
.
consumer
;
}
VoidMessage
::
VoidMessage
()
noexcept
{
assert
(
sizeof
(
VoidMessage
)
>=
sizeof
(
uniset
::
RawDataOfTransportMessage
));
}
//--------------------------------------------------------------------------------------------
SensorMessage
::
SensorMessage
()
noexcept
:
id
(
DefaultObjectId
),
value
(
0
),
undefined
(
false
),
sensor_type
(
UniversalIO
::
DI
),
threshold
(
false
),
tid
(
uniset
::
DefaultThresholdId
)
{
type
=
Message
::
SensorInfo
;
sm_tv
=
tm
;
// или инициализировать нулём ?
ci
.
minRaw
=
0
;
ci
.
maxRaw
=
0
;
ci
.
minCal
=
0
;
ci
.
maxCal
=
0
;
ci
.
precision
=
0
;
}
SensorMessage
::
SensorMessage
(
ObjectId
id
,
long
value
,
const
IOController_i
::
CalibrateInfo
&
ci
,
Priority
priority
,
UniversalIO
::
IOType
st
,
ObjectId
consumer
)
noexcept
:
id
(
id
),
value
(
value
),
undefined
(
false
),
sensor_type
(
st
),
ci
(
ci
),
threshold
(
false
),
tid
(
uniset
::
DefaultThresholdId
)
{
type
=
Message
::
SensorInfo
;
this
->
priority
=
priority
;
this
->
consumer
=
consumer
;
sm_tv
=
tm
;
}
SensorMessage
::
SensorMessage
(
int
dummy
)
noexcept
:
Message
(
1
),
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
ci
(
IOController_i
::
CalibrateInfo
())
{
type
=
Message
::
SensorInfo
;
}
SensorMessage
::
SensorMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
SensorInfo
);
}
//--------------------------------------------------------------------------------------------
SystemMessage
::
SystemMessage
()
noexcept
:
command
(
SystemMessage
::
Unknown
)
{
memset
(
data
,
0
,
sizeof
(
data
));
type
=
Message
::
SysCommand
;
}
SystemMessage
::
SystemMessage
(
Command
command
,
Priority
priority
,
ObjectId
consumer
)
noexcept
:
command
(
command
)
{
type
=
Message
::
SysCommand
;
this
->
priority
=
priority
;
this
->
consumer
=
consumer
;
memset
(
data
,
0
,
sizeof
(
data
));
}
SystemMessage
::
SystemMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
SysCommand
);
}
//--------------------------------------------------------------------------------------------
std
::
ostream
&
operator
<<
(
std
::
ostream
&
os
,
const
SystemMessage
::
Command
&
c
)
{
if
(
c
==
SystemMessage
::
Unknown
)
return
os
<<
"Unknown"
;
if
(
c
==
SystemMessage
::
StartUp
)
return
os
<<
"StartUp"
;
if
(
c
==
SystemMessage
::
FoldUp
)
return
os
<<
"FoldUp"
;
if
(
c
==
SystemMessage
::
Finish
)
return
os
<<
"Finish"
;
if
(
c
==
SystemMessage
::
WatchDog
)
return
os
<<
"WatchDog"
;
if
(
c
==
SystemMessage
::
ReConfiguration
)
return
os
<<
"ReConfiguration"
;
if
(
c
==
SystemMessage
::
NetworkInfo
)
return
os
<<
"NetworkInfo"
;
if
(
c
==
SystemMessage
::
LogRotate
)
return
os
<<
"LogRotate"
;
return
os
;
}
//--------------------------------------------------------------------------------------------
TimerMessage
::
TimerMessage
()
:
id
(
uniset
::
DefaultTimerId
)
{
type
=
Message
::
Timer
;
}
TimerMessage
::
TimerMessage
(
uniset
::
TimerId
id
,
Priority
prior
,
ObjectId
cons
)
:
id
(
id
)
{
type
=
Message
::
Timer
;
this
->
consumer
=
cons
;
}
TimerMessage
::
TimerMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
Timer
);
}
//--------------------------------------------------------------------------------------------
ConfirmMessage
::
ConfirmMessage
(
const
VoidMessage
*
msg
)
noexcept
:
Message
(
1
)
// вызываем dummy-конструктор, который не инициализирует данные (оптимизация)
{
memcpy
(
this
,
msg
,
sizeof
(
*
this
));
assert
(
this
->
type
==
Message
::
Confirm
);
}
//--------------------------------------------------------------------------------------------
ConfirmMessage
::
ConfirmMessage
(
uniset
::
ObjectId
in_sensor_id
,
const
double
&
in_sensor_value
,
const
timespec
&
in_sensor_time
,
const
timespec
&
in_confirm_time
,
Priority
in_priority
)
noexcept
:
sensor_id
(
in_sensor_id
),
sensor_value
(
in_sensor_value
),
sensor_time
(
in_sensor_time
),
confirm_time
(
in_confirm_time
),
broadcast
(
false
),
forward
(
false
)
{
type
=
Message
::
Confirm
;
priority
=
in_priority
;
}
//--------------------------------------------------------------------------------------------
TextMessage
::
TextMessage
(
const
VoidMessage
*
vmsg
)
noexcept
:
VoidMessage
(
1
)
// dummy constructor
{
assert
(
vmsg
->
type
==
Message
::
TextMessage
);
auto
m
=
static_cast
<
const
TextMessage
*>
(
vmsg
);
if
(
m
)
{
type
=
m
->
type
;
priority
=
m
->
priority
;
node
=
m
->
node
;
tm
=
m
->
tm
;
consumer
=
m
->
consumer
;
supplier
=
m
->
supplier
;
mtype
=
m
->
mtype
;
txt
=
m
->
txt
;
}
}
//--------------------------------------------------------------------------------------------
TextMessage
::
TextMessage
()
noexcept
{
type
=
Message
::
TextMessage
;
}
TextMessage
::
TextMessage
(
const
char
*
msg
,
int
_mtype
,
const
uniset
::
Timespec
&
tm
,
const
::
uniset
::
ProducerInfo
&
pi
,
Priority
prior
,
ObjectId
cons
)
noexcept
{
type
=
Message
::
TextMessage
;
this
->
node
=
pi
.
node
;
this
->
supplier
=
pi
.
id
;
this
->
priority
=
prior
;
this
->
consumer
=
cons
;
this
->
tm
.
tv_sec
=
tm
.
sec
;
this
->
tm
.
tv_nsec
=
tm
.
nsec
;
this
->
txt
=
std
::
string
(
msg
);
this
->
mtype
=
_mtype
;
}
//--------------------------------------------------------------------------------------------
std
::
shared_ptr
<
VoidMessage
>
TextMessage
::
toLocalVoidMessage
()
const
{
uniset
::
ProducerInfo
pi
;
pi
.
id
=
supplier
;
pi
.
node
=
node
;
uniset
::
Timespec
ts
;
ts
.
sec
=
tm
.
tv_sec
;
ts
.
nsec
=
tm
.
tv_nsec
;
auto
tmsg
=
std
::
make_shared
<
TextMessage
>
(
txt
.
c_str
(),
mtype
,
ts
,
pi
,
priority
,
consumer
);
return
std
::
static_pointer_cast
<
VoidMessage
>
(
tmsg
);
}
//--------------------------------------------------------------------------------------------
}
// end of namespace uniset
//--------------------------------------------------------------------------------------------
src/Core/UInterface.cc
View file @
9674dd51
This source diff could not be displayed because it is too large. You can
view the blob
instead.
src/Core/UniSetActivator.cc
View file @
9674dd51
...
...
@@ -56,416 +56,416 @@ static const int TERMINATE_TIMEOUT_SEC = 15; // время, отведённо
// ------------------------------------------------------------------------------------------
struct
ORBThreadDeleter
{
void
operator
()(
OmniThreadCreator
<
UniSetActivator
>*
p
)
const
{
// не удаляем..
}
void
operator
()(
OmniThreadCreator
<
UniSetActivator
>*
p
)
const
{
// не удаляем..
}
};
// ---------------------------------------------------------------------------
namespace
uniset
{
UniSetActivatorPtr
UniSetActivator
::
inst
;
// ---------------------------------------------------------------------------
UniSetActivatorPtr
UniSetActivator
::
Instance
()
{
if
(
inst
==
nullptr
)
inst
=
shared_ptr
<
UniSetActivator
>
(
new
UniSetActivator
()
);
return
inst
;
}
// ---------------------------------------------------------------------------
UniSetActivator
::
UniSetActivator
()
:
UniSetManager
(
uniset
::
DefaultObjectId
)
{
UniSetActivator
::
init
();
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
init
()
{
if
(
getId
()
==
DefaultObjectId
)
myname
=
"UniSetActivator"
;
auto
conf
=
uniset_conf
();
UniSetActivatorPtr
UniSetActivator
::
inst
;
// ---------------------------------------------------------------------------
UniSetActivatorPtr
UniSetActivator
::
Instance
()
{
if
(
inst
==
nullptr
)
inst
=
shared_ptr
<
UniSetActivator
>
(
new
UniSetActivator
()
);
return
inst
;
}
// ---------------------------------------------------------------------------
UniSetActivator
::
UniSetActivator
()
:
UniSetManager
(
uniset
::
DefaultObjectId
)
{
UniSetActivator
::
init
();
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
init
()
{
if
(
getId
()
==
DefaultObjectId
)
myname
=
"UniSetActivator"
;
auto
conf
=
uniset_conf
();
#ifndef DISABLE_REST_API
if
(
findArgParam
(
"--activator-run-httpserver"
,
conf
->
getArgc
(),
conf
->
getArgv
())
!=
-
1
)
{
httpHost
=
conf
->
getArgParam
(
"--activator-httpserver-host"
,
"localhost"
);
ostringstream
s
;
s
<<
(
getId
()
==
DefaultObjectId
?
8080
:
getId
()
);
httpPort
=
conf
->
getArgInt
(
"--activator-httpserver-port"
,
s
.
str
());
ulog1
<<
myname
<<
"(init): http server parameters "
<<
httpHost
<<
":"
<<
httpPort
<<
endl
;
httpCORS_allow
=
conf
->
getArgParam
(
"--activator-httpserver-cors-allow"
,
"*"
);
}
if
(
findArgParam
(
"--activator-run-httpserver"
,
conf
->
getArgc
(),
conf
->
getArgv
())
!=
-
1
)
{
httpHost
=
conf
->
getArgParam
(
"--activator-httpserver-host"
,
"localhost"
);
ostringstream
s
;
s
<<
(
getId
()
==
DefaultObjectId
?
8080
:
getId
()
);
httpPort
=
conf
->
getArgInt
(
"--activator-httpserver-port"
,
s
.
str
());
ulog1
<<
myname
<<
"(init): http server parameters "
<<
httpHost
<<
":"
<<
httpPort
<<
endl
;
httpCORS_allow
=
conf
->
getArgParam
(
"--activator-httpserver-cors-allow"
,
"*"
);
}
#endif
orb
=
conf
->
getORB
();
CORBA
::
Object_var
obj
=
orb
->
resolve_initial_references
(
"RootPOA"
);
PortableServer
::
POA_var
root_poa
=
PortableServer
::
POA
::
_narrow
(
obj
);
pman
=
root_poa
->
the_POAManager
();
const
CORBA
::
PolicyList
pl
=
conf
->
getPolicy
();
poa
=
root_poa
->
create_POA
(
"my poa"
,
pman
,
pl
);
if
(
CORBA
::
is_nil
(
poa
)
)
{
ucrit
<<
myname
<<
"(init): init poa failed!!!"
<<
endl
;
std
::
terminate
();
}
}
// ------------------------------------------------------------------------------------------
UniSetActivator
::~
UniSetActivator
()
{
if
(
active
)
{
try
{
shutdown
();
}
catch
(...)
{
std
::
exception_ptr
p
=
std
::
current_exception
();
cerr
<<
(
p
?
p
.
__cxa_exception_type
()
->
name
()
:
"null"
)
<<
std
::
endl
;
}
}
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
run
(
bool
thread
,
bool
terminate_control
)
{
ulogsys
<<
myname
<<
"(run): создаю менеджер "
<<
endl
;
termControl
=
terminate_control
;
auto
aptr
=
std
::
static_pointer_cast
<
UniSetActivator
>
(
get_ptr
());
UniSetManager
::
initPOA
(
aptr
);
if
(
getId
()
==
uniset
::
DefaultObjectId
)
offThread
();
// отключение потока обработки сообщений, раз не задан ObjectId
UniSetManager
::
activate
();
// а там вызывается активация всех подчиненных объектов и менеджеров
active
=
true
;
ulogsys
<<
myname
<<
"(run): активизируем менеджер"
<<
endl
;
pman
->
activate
();
msleep
(
50
);
if
(
termControl
)
set_signals
(
true
);
orb
=
conf
->
getORB
();
CORBA
::
Object_var
obj
=
orb
->
resolve_initial_references
(
"RootPOA"
);
PortableServer
::
POA_var
root_poa
=
PortableServer
::
POA
::
_narrow
(
obj
);
pman
=
root_poa
->
the_POAManager
();
const
CORBA
::
PolicyList
pl
=
conf
->
getPolicy
();
poa
=
root_poa
->
create_POA
(
"my poa"
,
pman
,
pl
);
if
(
CORBA
::
is_nil
(
poa
)
)
{
ucrit
<<
myname
<<
"(init): init poa failed!!!"
<<
endl
;
std
::
terminate
();
}
}
// ------------------------------------------------------------------------------------------
UniSetActivator
::~
UniSetActivator
()
{
if
(
active
)
{
try
{
shutdown
();
}
catch
(...)
{
std
::
exception_ptr
p
=
std
::
current_exception
();
cerr
<<
(
p
?
p
.
__cxa_exception_type
()
->
name
()
:
"null"
)
<<
std
::
endl
;
}
}
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
run
(
bool
thread
,
bool
terminate_control
)
{
ulogsys
<<
myname
<<
"(run): создаю менеджер "
<<
endl
;
termControl
=
terminate_control
;
auto
aptr
=
std
::
static_pointer_cast
<
UniSetActivator
>
(
get_ptr
());
UniSetManager
::
initPOA
(
aptr
);
if
(
getId
()
==
uniset
::
DefaultObjectId
)
offThread
();
// отключение потока обработки сообщений, раз не задан ObjectId
UniSetManager
::
activate
();
// а там вызывается активация всех подчиненных объектов и менеджеров
active
=
true
;
ulogsys
<<
myname
<<
"(run): активизируем менеджер"
<<
endl
;
pman
->
activate
();
msleep
(
50
);
if
(
termControl
)
set_signals
(
true
);
#ifndef DISABLE_REST_API
if
(
!
httpHost
.
empty
()
)
{
try
{
auto
reg
=
dynamic_pointer_cast
<
UHttp
::
IHttpRequestRegistry
>
(
shared_from_this
());
httpserv
=
make_shared
<
UHttp
::
UHttpServer
>
(
reg
,
httpHost
,
httpPort
);
httpserv
->
setCORS_allow
(
httpCORS_allow
);
httpserv
->
start
();
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(run): init http server error: "
<<
ex
.
what
()
<<
endl
;
}
}
if
(
!
httpHost
.
empty
()
)
{
try
{
auto
reg
=
dynamic_pointer_cast
<
UHttp
::
IHttpRequestRegistry
>
(
shared_from_this
());
httpserv
=
make_shared
<
UHttp
::
UHttpServer
>
(
reg
,
httpHost
,
httpPort
);
httpserv
->
setCORS_allow
(
httpCORS_allow
);
httpserv
->
start
();
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(run): init http server error: "
<<
ex
.
what
()
<<
endl
;
}
}
#endif
if
(
thread
)
{
uinfo
<<
myname
<<
"(run): запускаемся с созданием отдельного потока... "
<<
endl
;
orbthr
=
std
::
shared_ptr
<
OmniThreadCreator
<
UniSetActivator
>>
(
new
OmniThreadCreator
<
UniSetActivator
>
(
aptr
,
&
UniSetActivator
::
mainWork
),
ORBThreadDeleter
());
orbthr
->
start
();
}
else
{
uinfo
<<
myname
<<
"(run): запускаемся без создания отдельного потока... "
<<
endl
;
mainWork
();
shutdown
();
}
}
// ------------------------------------------------------------------------------------------
/*!
* Функция останавливает работу orb и завершает поток, а также удаляет ссылку из репозитория.
* \note Объект становится недоступен другим процессам
*/
void
UniSetActivator
::
shutdown
()
{
if
(
!
active
)
return
;
active
=
false
;
if
(
termControl
)
{
set_signals
(
false
);
{
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
g_done
=
false
;
g_finish_guard_thread
=
make_shared
<
std
::
thread
>
(
on_finish_timeout
);
}
}
ulogsys
<<
myname
<<
"(shutdown): deactivate... "
<<
endl
;
deactivate
();
ulogsys
<<
myname
<<
"(shutdown): deactivate ok. "
<<
endl
;
ulogsys
<<
myname
<<
"(shutdown): discard request..."
<<
endl
;
pman
->
discard_requests
(
true
);
ulogsys
<<
myname
<<
"(shutdown): discard request ok."
<<
endl
;
if
(
thread
)
{
uinfo
<<
myname
<<
"(run): запускаемся с созданием отдельного потока... "
<<
endl
;
orbthr
=
std
::
shared_ptr
<
OmniThreadCreator
<
UniSetActivator
>>
(
new
OmniThreadCreator
<
UniSetActivator
>
(
aptr
,
&
UniSetActivator
::
mainWork
),
ORBThreadDeleter
());
orbthr
->
start
();
}
else
{
uinfo
<<
myname
<<
"(run): запускаемся без создания отдельного потока... "
<<
endl
;
mainWork
();
shutdown
();
}
}
// ------------------------------------------------------------------------------------------
/*!
* Функция останавливает работу orb и завершает поток, а также удаляет ссылку из репозитория.
* \note Объект становится недоступен другим процессам
*/
void
UniSetActivator
::
shutdown
()
{
if
(
!
active
)
return
;
active
=
false
;
if
(
termControl
)
{
set_signals
(
false
);
{
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
g_done
=
false
;
g_finish_guard_thread
=
make_shared
<
std
::
thread
>
(
on_finish_timeout
);
}
}
ulogsys
<<
myname
<<
"(shutdown): deactivate... "
<<
endl
;
deactivate
();
ulogsys
<<
myname
<<
"(shutdown): deactivate ok. "
<<
endl
;
ulogsys
<<
myname
<<
"(shutdown): discard request..."
<<
endl
;
pman
->
discard_requests
(
true
);
ulogsys
<<
myname
<<
"(shutdown): discard request ok."
<<
endl
;
#ifndef DISABLE_REST_API
if
(
httpserv
)
httpserv
->
stop
();
if
(
httpserv
)
httpserv
->
stop
();
#endif
ulogsys
<<
myname
<<
"(shutdown): pman deactivate... "
<<
endl
;
pman
->
deactivate
(
false
,
true
);
ulogsys
<<
myname
<<
"(shutdown): pman deactivate ok. "
<<
endl
;
try
{
ulogsys
<<
myname
<<
"(shutdown): shutdown orb... "
<<
endl
;
if
(
orb
)
orb
->
shutdown
(
true
);
ulogsys
<<
myname
<<
"(shutdown): shutdown ok."
<<
endl
;
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ucrit
<<
myname
<<
"(shutdown): : поймали omniORB::fatalException:"
<<
endl
;
ucrit
<<
myname
<<
"(shutdown): file: "
<<
fe
.
file
()
<<
endl
;
ucrit
<<
myname
<<
"(shutdown): line: "
<<
fe
.
line
()
<<
endl
;
ucrit
<<
myname
<<
"(shutdown): mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
catch
(
const
std
::
exception
&
ex
)
{
ucrit
<<
myname
<<
"(shutdown): "
<<
ex
.
what
()
<<
endl
;
}
{
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
g_done
=
true
;
}
g_doneevent
.
notify_all
();
if
(
g_finish_guard_thread
)
g_finish_guard_thread
->
join
();
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
join
()
{
if
(
g_done
)
return
;
ulogsys
<<
myname
<<
"(join): ..."
<<
endl
;
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
g_doneevent
.
wait
(
lk
,
[]()
{
return
(
g_done
==
true
);
}
);
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
terminate
()
{
ulogsys
<<
myname
<<
"(terminate): ..."
<<
endl
;
kill
(
getpid
(),
SIGTERM
);
}
// ------------------------------------------------------------------------------------------
static
void
activator_terminate
(
int
signo
)
{
auto
act
=
UniSetActivator
::
Instance
();
act
->
shutdown
();
ulogsys
<<
"******** activator_terminate finished **** "
<<
endl
;
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
on_finish_timeout
()
{
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
if
(
g_done
)
return
;
ulogsys
<<
"(FINISH GUARD THREAD): wait "
<<
TERMINATE_TIMEOUT_SEC
<<
" sec.."
<<
endl
<<
flush
;
g_doneevent
.
wait_for
(
lk
,
std
::
chrono
::
milliseconds
(
TERMINATE_TIMEOUT_SEC
*
1000
),
[]()
{
return
(
g_done
==
true
);
}
);
if
(
!
g_done
)
{
ulogsys
<<
"(FINISH GUARD THREAD): WAIT TIMEOUT "
<<
TERMINATE_TIMEOUT_SEC
<<
" sec..KILL *******"
<<
endl
<<
flush
;
set_signals
(
false
);
std
::
abort
();
return
;
}
ulogsys
<<
"(FINISH GUARD THREAD): [OK]..bye.."
<<
endl
;
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
set_signals
(
bool
ask
)
{
struct
sigaction
act
;
// = { { 0 } };
struct
sigaction
oact
;
// = { { 0 } };
memset
(
&
act
,
0
,
sizeof
(
act
));
memset
(
&
act
,
0
,
sizeof
(
oact
));
sigemptyset
(
&
act
.
sa_mask
);
sigemptyset
(
&
oact
.
sa_mask
);
// добавляем сигналы, которые будут игнорироваться
// при обработке сигнала
sigaddset
(
&
act
.
sa_mask
,
SIGINT
);
sigaddset
(
&
act
.
sa_mask
,
SIGTERM
);
sigaddset
(
&
act
.
sa_mask
,
SIGABRT
);
sigaddset
(
&
act
.
sa_mask
,
SIGQUIT
);
if
(
ask
)
act
.
sa_handler
=
activator_terminate
;
else
act
.
sa_handler
=
SIG_DFL
;
sigaction
(
SIGINT
,
&
act
,
&
oact
);
sigaction
(
SIGTERM
,
&
act
,
&
oact
);
sigaction
(
SIGABRT
,
&
act
,
&
oact
);
sigaction
(
SIGQUIT
,
&
act
,
&
oact
);
// SIGSEGV отдельно
sigemptyset
(
&
act
.
sa_mask
);
sigaddset
(
&
act
.
sa_mask
,
SIGSEGV
);
act
.
sa_flags
=
0
;
//
act.sa_flags |= SA_RESTART;
act
.
sa_flags
|=
SA_RESETHAND
;
ulogsys
<<
myname
<<
"(shutdown): pman deactivate... "
<<
endl
;
pman
->
deactivate
(
false
,
true
);
ulogsys
<<
myname
<<
"(shutdown): pman deactivate ok. "
<<
endl
;
try
{
ulogsys
<<
myname
<<
"(shutdown): shutdown orb... "
<<
endl
;
if
(
orb
)
orb
->
shutdown
(
true
);
ulogsys
<<
myname
<<
"(shutdown): shutdown ok."
<<
endl
;
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ucrit
<<
myname
<<
"(shutdown): : поймали omniORB::fatalException:"
<<
endl
;
ucrit
<<
myname
<<
"(shutdown): file: "
<<
fe
.
file
()
<<
endl
;
ucrit
<<
myname
<<
"(shutdown): line: "
<<
fe
.
line
()
<<
endl
;
ucrit
<<
myname
<<
"(shutdown): mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
catch
(
const
std
::
exception
&
ex
)
{
ucrit
<<
myname
<<
"(shutdown): "
<<
ex
.
what
()
<<
endl
;
}
{
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
g_done
=
true
;
}
g_doneevent
.
notify_all
();
if
(
g_finish_guard_thread
)
g_finish_guard_thread
->
join
();
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
join
()
{
if
(
g_done
)
return
;
ulogsys
<<
myname
<<
"(join): ..."
<<
endl
;
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
g_doneevent
.
wait
(
lk
,
[]()
{
return
(
g_done
==
true
);
}
);
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
terminate
()
{
ulogsys
<<
myname
<<
"(terminate): ..."
<<
endl
;
kill
(
getpid
(),
SIGTERM
);
}
// ------------------------------------------------------------------------------------------
static
void
activator_terminate
(
int
signo
)
{
auto
act
=
UniSetActivator
::
Instance
();
act
->
shutdown
();
ulogsys
<<
"******** activator_terminate finished **** "
<<
endl
;
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
on_finish_timeout
()
{
std
::
unique_lock
<
std
::
mutex
>
lk
(
g_donemutex
);
if
(
g_done
)
return
;
ulogsys
<<
"(FINISH GUARD THREAD): wait "
<<
TERMINATE_TIMEOUT_SEC
<<
" sec.."
<<
endl
<<
flush
;
g_doneevent
.
wait_for
(
lk
,
std
::
chrono
::
milliseconds
(
TERMINATE_TIMEOUT_SEC
*
1000
),
[]()
{
return
(
g_done
==
true
);
}
);
if
(
!
g_done
)
{
ulogsys
<<
"(FINISH GUARD THREAD): WAIT TIMEOUT "
<<
TERMINATE_TIMEOUT_SEC
<<
" sec..KILL *******"
<<
endl
<<
flush
;
set_signals
(
false
);
std
::
abort
();
return
;
}
ulogsys
<<
"(FINISH GUARD THREAD): [OK]..bye.."
<<
endl
;
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
set_signals
(
bool
ask
)
{
struct
sigaction
act
;
// = { { 0 } };
struct
sigaction
oact
;
// = { { 0 } };
memset
(
&
act
,
0
,
sizeof
(
act
));
memset
(
&
act
,
0
,
sizeof
(
oact
));
sigemptyset
(
&
act
.
sa_mask
);
sigemptyset
(
&
oact
.
sa_mask
);
// добавляем сигналы, которые будут игнорироваться
// при обработке сигнала
sigaddset
(
&
act
.
sa_mask
,
SIGINT
);
sigaddset
(
&
act
.
sa_mask
,
SIGTERM
);
sigaddset
(
&
act
.
sa_mask
,
SIGABRT
);
sigaddset
(
&
act
.
sa_mask
,
SIGQUIT
);
if
(
ask
)
act
.
sa_handler
=
activator_terminate
;
else
act
.
sa_handler
=
SIG_DFL
;
sigaction
(
SIGINT
,
&
act
,
&
oact
);
sigaction
(
SIGTERM
,
&
act
,
&
oact
);
sigaction
(
SIGABRT
,
&
act
,
&
oact
);
sigaction
(
SIGQUIT
,
&
act
,
&
oact
);
// SIGSEGV отдельно
sigemptyset
(
&
act
.
sa_mask
);
sigaddset
(
&
act
.
sa_mask
,
SIGSEGV
);
act
.
sa_flags
=
0
;
//
act.sa_flags |= SA_RESTART;
act
.
sa_flags
|=
SA_RESETHAND
;
#if 0
g_sigseg_stack.ss_sp = g_stack_body;
g_sigseg_stack.ss_flags = SS_ONSTACK;
g_sigseg_stack.ss_size = sizeof(g_stack_body);
assert(!sigaltstack(&g_sigseg_stack, nullptr));
act.sa_flags |= SA_ONSTACK;
g_sigseg_stack.ss_sp = g_stack_body;
g_sigseg_stack.ss_flags = SS_ONSTACK;
g_sigseg_stack.ss_size = sizeof(g_stack_body);
assert(!sigaltstack(&g_sigseg_stack, nullptr));
act.sa_flags |= SA_ONSTACK;
#endif
//
if(ask)
//
act.sa_handler = activator_terminate_with_calltrace;
//
else
//
act.sa_handler = SIG_DFL;
//
sigaction(SIGSEGV, &act, &oact);
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
mainWork
()
{
ulogsys
<<
myname
<<
"(work): запускаем orb на обработку запросов..."
<<
endl
;
try
{
omniORB
::
setMainThread
();
orb
->
run
();
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ucrit
<<
myname
<<
"(work): поймали CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
ucrit
<<
myname
<<
"(work): поймали CORBA::Exception."
<<
endl
;
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ucrit
<<
myname
<<
"(work): : поймали omniORB::fatalException:"
<<
endl
;
ucrit
<<
myname
<<
"(work): file: "
<<
fe
.
file
()
<<
endl
;
ucrit
<<
myname
<<
"(work): line: "
<<
fe
.
line
()
<<
endl
;
ucrit
<<
myname
<<
"(work): mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
catch
(
std
::
exception
&
ex
)
{
ucrit
<<
myname
<<
"(work): catch: "
<<
ex
.
what
()
<<
endl
;
}
ulogsys
<<
myname
<<
"(work): orb thread stopped!"
<<
endl
<<
flush
;
}
// ------------------------------------------------------------------------------------------
//
if(ask)
//
act.sa_handler = activator_terminate_with_calltrace;
//
else
//
act.sa_handler = SIG_DFL;
//
sigaction(SIGSEGV, &act, &oact);
}
// ------------------------------------------------------------------------------------------
void
UniSetActivator
::
mainWork
()
{
ulogsys
<<
myname
<<
"(work): запускаем orb на обработку запросов..."
<<
endl
;
try
{
omniORB
::
setMainThread
();
orb
->
run
();
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ucrit
<<
myname
<<
"(work): поймали CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
ucrit
<<
myname
<<
"(work): поймали CORBA::Exception."
<<
endl
;
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ucrit
<<
myname
<<
"(work): : поймали omniORB::fatalException:"
<<
endl
;
ucrit
<<
myname
<<
"(work): file: "
<<
fe
.
file
()
<<
endl
;
ucrit
<<
myname
<<
"(work): line: "
<<
fe
.
line
()
<<
endl
;
ucrit
<<
myname
<<
"(work): mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
catch
(
std
::
exception
&
ex
)
{
ucrit
<<
myname
<<
"(work): catch: "
<<
ex
.
what
()
<<
endl
;
}
ulogsys
<<
myname
<<
"(work): orb thread stopped!"
<<
endl
<<
flush
;
}
// ------------------------------------------------------------------------------------------
#ifndef DISABLE_REST_API
Poco
::
JSON
::
Object
::
Ptr
UniSetActivator
::
httpGetByName
(
const
string
&
name
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
if
(
name
==
myname
)
return
httpGet
(
p
);
auto
obj
=
deepFindObject
(
name
);
if
(
obj
)
return
obj
->
httpGet
(
p
);
ostringstream
err
;
err
<<
"Object '"
<<
name
<<
"' not found"
;
throw
uniset
::
NameNotFound
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Array
::
Ptr
UniSetActivator
::
httpGetObjectsList
(
const
Poco
::
URI
::
QueryParameters
&
p
)
{
Poco
::
JSON
::
Array
::
Ptr
jdata
=
new
Poco
::
JSON
::
Array
();
std
::
vector
<
std
::
shared_ptr
<
UniSetObject
>>
vec
;
vec
.
reserve
(
objectsCount
());
//! \todo Доделать обработку параметров beg,lim на случай большого количества объектов (и частичных запросов)
size_t
lim
=
1000
;
getAllObjectsList
(
vec
,
lim
);
for
(
const
auto
&
o
:
vec
)
jdata
->
add
(
o
->
getName
());
return
jdata
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetActivator
::
httpHelpByName
(
const
string
&
name
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
if
(
name
==
myname
)
return
httpHelp
(
p
);
auto
obj
=
deepFindObject
(
name
);
if
(
obj
)
return
obj
->
httpHelp
(
p
);
ostringstream
err
;
err
<<
"Object '"
<<
name
<<
"' not found"
;
throw
uniset
::
NameNotFound
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetActivator
::
httpRequestByName
(
const
string
&
name
,
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
if
(
name
==
myname
)
return
httpRequest
(
req
,
p
);
// а вдруг встретится объект с именем "conf" а мы перекрываем имя?!
// (пока считаем что такого не будет)
if
(
name
==
"configure"
)
return
request_configure
(
req
,
p
);
auto
obj
=
deepFindObject
(
name
);
if
(
obj
)
return
obj
->
httpRequest
(
req
,
p
);
ostringstream
err
;
err
<<
"Object '"
<<
name
<<
"' not found"
;
throw
uniset
::
NameNotFound
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetActivator
::
httpGetByName
(
const
string
&
name
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
if
(
name
==
myname
)
return
httpGet
(
p
);
auto
obj
=
deepFindObject
(
name
);
if
(
obj
)
return
obj
->
httpGet
(
p
);
ostringstream
err
;
err
<<
"Object '"
<<
name
<<
"' not found"
;
throw
uniset
::
NameNotFound
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Array
::
Ptr
UniSetActivator
::
httpGetObjectsList
(
const
Poco
::
URI
::
QueryParameters
&
p
)
{
Poco
::
JSON
::
Array
::
Ptr
jdata
=
new
Poco
::
JSON
::
Array
();
std
::
vector
<
std
::
shared_ptr
<
UniSetObject
>>
vec
;
vec
.
reserve
(
objectsCount
());
//! \todo Доделать обработку параметров beg,lim на случай большого количества объектов (и частичных запросов)
size_t
lim
=
1000
;
getAllObjectsList
(
vec
,
lim
);
for
(
const
auto
&
o
:
vec
)
jdata
->
add
(
o
->
getName
());
return
jdata
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetActivator
::
httpHelpByName
(
const
string
&
name
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
if
(
name
==
myname
)
return
httpHelp
(
p
);
auto
obj
=
deepFindObject
(
name
);
if
(
obj
)
return
obj
->
httpHelp
(
p
);
ostringstream
err
;
err
<<
"Object '"
<<
name
<<
"' not found"
;
throw
uniset
::
NameNotFound
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetActivator
::
httpRequestByName
(
const
string
&
name
,
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
if
(
name
==
myname
)
return
httpRequest
(
req
,
p
);
// а вдруг встретится объект с именем "conf" а мы перекрываем имя?!
// (пока считаем что такого не будет)
if
(
name
==
"configure"
)
return
request_configure
(
req
,
p
);
auto
obj
=
deepFindObject
(
name
);
if
(
obj
)
return
obj
->
httpRequest
(
req
,
p
);
ostringstream
err
;
err
<<
"Object '"
<<
name
<<
"' not found"
;
throw
uniset
::
NameNotFound
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
#endif // #ifndef DISABLE_REST_API
// ------------------------------------------------------------------------------------------
// ------------------------------------------------------------------------------------------
}
// end of namespace uniset
// ------------------------------------------------------------------------------------------
src/Core/UniSetManager.cc
View file @
9674dd51
...
...
@@ -39,202 +39,202 @@ using namespace std;
// объект-функция для посылки сообщения менеджеру
class
MPush
:
public
unary_function
<
const
std
::
shared_ptr
<
uniset
::
UniSetManager
>&
,
bool
>
{
public
:
explicit
MPush
(
const
uniset
::
TransportMessage
&
msg
)
:
msg
(
msg
)
{}
bool
operator
()(
const
std
::
shared_ptr
<
uniset
::
UniSetManager
>&
m
)
const
{
try
{
if
(
m
)
{
m
->
push
(
msg
);
m
->
broadcast
(
msg
);
}
return
true
;
}
catch
(...)
{}
return
false
;
}
private
:
const
uniset
::
TransportMessage
&
msg
;
public
:
explicit
MPush
(
const
uniset
::
TransportMessage
&
msg
)
:
msg
(
msg
)
{}
bool
operator
()(
const
std
::
shared_ptr
<
uniset
::
UniSetManager
>&
m
)
const
{
try
{
if
(
m
)
{
m
->
push
(
msg
);
m
->
broadcast
(
msg
);
}
return
true
;
}
catch
(...)
{}
return
false
;
}
private
:
const
uniset
::
TransportMessage
&
msg
;
};
// объект-функция для посылки сообщения объекту
class
OPush
:
public
unary_function
<
const
std
::
shared_ptr
<
uniset
::
UniSetObject
>&
,
bool
>
{
public
:
explicit
OPush
(
const
uniset
::
TransportMessage
&
msg
)
:
msg
(
msg
)
{}
bool
operator
()(
const
std
::
shared_ptr
<
uniset
::
UniSetObject
>&
o
)
const
{
try
{
if
(
o
)
{
o
->
push
(
msg
);
return
true
;
}
}
catch
(...)
{}
return
false
;
}
private
:
const
uniset
::
TransportMessage
&
msg
;
public
:
explicit
OPush
(
const
uniset
::
TransportMessage
&
msg
)
:
msg
(
msg
)
{}
bool
operator
()(
const
std
::
shared_ptr
<
uniset
::
UniSetObject
>&
o
)
const
{
try
{
if
(
o
)
{
o
->
push
(
msg
);
return
true
;
}
}
catch
(...)
{}
return
false
;
}
private
:
const
uniset
::
TransportMessage
&
msg
;
};
// ------------------------------------------------------------------------------------------
UniSetManager
::
UniSetManager
()
:
UniSetObject
(
uniset
::
DefaultObjectId
),
olistMutex
(
"UniSetManager_olistMutex"
),
mlistMutex
(
"UniSetManager_mlistMutex"
)
UniSetObject
(
uniset
::
DefaultObjectId
),
olistMutex
(
"UniSetManager_olistMutex"
),
mlistMutex
(
"UniSetManager_mlistMutex"
)
{
}
// ------------------------------------------------------------------------------------------
UniSetManager
::
UniSetManager
(
ObjectId
id
)
:
UniSetObject
(
id
)
UniSetObject
(
id
)
{
olistMutex
.
setName
(
myname
+
"_olistMutex"
);
mlistMutex
.
setName
(
myname
+
"_mlistMutex"
);
olistMutex
.
setName
(
myname
+
"_olistMutex"
);
mlistMutex
.
setName
(
myname
+
"_mlistMutex"
);
}
// ------------------------------------------------------------------------------------------
UniSetManager
::
UniSetManager
(
const
string
&
name
,
const
string
&
section
)
:
UniSetObject
(
name
,
section
)
UniSetObject
(
name
,
section
)
{
olistMutex
.
setName
(
myname
+
"_olistMutex"
);
mlistMutex
.
setName
(
myname
+
"_mlistMutex"
);
olistMutex
.
setName
(
myname
+
"_olistMutex"
);
mlistMutex
.
setName
(
myname
+
"_mlistMutex"
);
}
// ------------------------------------------------------------------------------------------
UniSetManager
::~
UniSetManager
()
{
olist
.
clear
();
mlist
.
clear
();
olist
.
clear
();
mlist
.
clear
();
}
// ------------------------------------------------------------------------------------------
std
::
shared_ptr
<
UniSetManager
>
UniSetManager
::
get_mptr
()
{
return
std
::
dynamic_pointer_cast
<
UniSetManager
>
(
get_ptr
());
return
std
::
dynamic_pointer_cast
<
UniSetManager
>
(
get_ptr
());
}
// ------------------------------------------------------------------------------------------
void
UniSetManager
::
initPOA
(
const
std
::
weak_ptr
<
UniSetManager
>&
rmngr
)
{
auto
m
=
rmngr
.
lock
();
if
(
!
m
)
{
ostringstream
err
;
err
<<
myname
<<
"(initPOA): failed weak_ptr !!"
;
ucrit
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
if
(
CORBA
::
is_nil
(
pman
)
)
this
->
pman
=
m
->
getPOAManager
();
PortableServer
::
POA_var
rpoa
=
m
->
getPOA
();
if
(
rpoa
!=
poa
)
poa
=
m
->
getPOA
();
if
(
CORBA
::
is_nil
(
poa
)
)
{
ostringstream
err
;
err
<<
myname
<<
"(initPOA): failed init poa "
;
ucrit
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// Инициализация самого менеджера и его подобъектов
UniSetObject
::
init
(
rmngr
);
objects
(
initial
);
managers
(
initial
);
auto
m
=
rmngr
.
lock
();
if
(
!
m
)
{
ostringstream
err
;
err
<<
myname
<<
"(initPOA): failed weak_ptr !!"
;
ucrit
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
if
(
CORBA
::
is_nil
(
pman
)
)
this
->
pman
=
m
->
getPOAManager
();
PortableServer
::
POA_var
rpoa
=
m
->
getPOA
();
if
(
rpoa
!=
poa
)
poa
=
m
->
getPOA
();
if
(
CORBA
::
is_nil
(
poa
)
)
{
ostringstream
err
;
err
<<
myname
<<
"(initPOA): failed init poa "
;
ucrit
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// Инициализация самого менеджера и его подобъектов
UniSetObject
::
init
(
rmngr
);
objects
(
initial
);
managers
(
initial
);
}
// ------------------------------------------------------------------------------------------
bool
UniSetManager
::
add
(
const
std
::
shared_ptr
<
UniSetObject
>&
obj
)
{
auto
m
=
std
::
dynamic_pointer_cast
<
UniSetManager
>
(
obj
);
auto
m
=
std
::
dynamic_pointer_cast
<
UniSetManager
>
(
obj
);
if
(
m
)
return
addManager
(
m
);
if
(
m
)
return
addManager
(
m
);
return
addObject
(
obj
);
return
addObject
(
obj
);
}
// ------------------------------------------------------------------------------------------
bool
UniSetManager
::
remove
(
const
std
::
shared_ptr
<
UniSetObject
>&
obj
)
{
auto
m
=
std
::
dynamic_pointer_cast
<
UniSetManager
>
(
obj
);
auto
m
=
std
::
dynamic_pointer_cast
<
UniSetManager
>
(
obj
);
if
(
m
)
return
removeManager
(
m
);
if
(
m
)
return
removeManager
(
m
);
return
removeObject
(
obj
);
return
removeObject
(
obj
);
}
// ------------------------------------------------------------------------------------------
bool
UniSetManager
::
addObject
(
const
std
::
shared_ptr
<
UniSetObject
>&
obj
)
{
{
//lock
uniset_rwmutex_wrlock
lock
(
olistMutex
);
auto
li
=
find
(
olist
.
begin
(),
olist
.
end
(),
obj
);
if
(
li
==
olist
.
end
()
)
{
uinfo
<<
myname
<<
"(activator): добавляем объект "
<<
obj
->
getName
()
<<
endl
;
olist
.
push_back
(
obj
);
}
}
// unlock
return
true
;
{
//lock
uniset_rwmutex_wrlock
lock
(
olistMutex
);
auto
li
=
find
(
olist
.
begin
(),
olist
.
end
(),
obj
);
if
(
li
==
olist
.
end
()
)
{
uinfo
<<
myname
<<
"(activator): добавляем объект "
<<
obj
->
getName
()
<<
endl
;
olist
.
push_back
(
obj
);
}
}
// unlock
return
true
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetManager
::
removeObject
(
const
std
::
shared_ptr
<
UniSetObject
>&
obj
)
{
{
//lock
uniset_rwmutex_wrlock
lock
(
olistMutex
);
auto
li
=
find
(
olist
.
begin
(),
olist
.
end
(),
obj
);
if
(
li
!=
olist
.
end
()
)
{
uinfo
<<
myname
<<
"(activator): удаляем объект "
<<
obj
->
getName
()
<<
endl
;
try
{
if
(
obj
)
obj
->
deactivate
();
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
uwarn
<<
myname
<<
"(removeObject): поймали CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(removeObject): CORBA::Exception"
<<
endl
;
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ucrit
<<
myname
<<
"(managers): Caught omniORB::fatalException:"
<<
endl
;
ucrit
<<
myname
<<
"(managers): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
catch
(
const
uniset
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(removeObject): "
<<
ex
<<
endl
;
}
catch
(...)
{}
olist
.
erase
(
li
);
}
}
// unlock
return
true
;
{
//lock
uniset_rwmutex_wrlock
lock
(
olistMutex
);
auto
li
=
find
(
olist
.
begin
(),
olist
.
end
(),
obj
);
if
(
li
!=
olist
.
end
()
)
{
uinfo
<<
myname
<<
"(activator): удаляем объект "
<<
obj
->
getName
()
<<
endl
;
try
{
if
(
obj
)
obj
->
deactivate
();
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
uwarn
<<
myname
<<
"(removeObject): поймали CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(removeObject): CORBA::Exception"
<<
endl
;
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ucrit
<<
myname
<<
"(managers): Caught omniORB::fatalException:"
<<
endl
;
ucrit
<<
myname
<<
"(managers): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
catch
(
const
uniset
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(removeObject): "
<<
ex
<<
endl
;
}
catch
(...)
{}
olist
.
erase
(
li
);
}
}
// unlock
return
true
;
}
// ------------------------------------------------------------------------------------------
...
...
@@ -243,97 +243,97 @@ bool UniSetManager::removeObject( const std::shared_ptr<UniSetObject>& obj )
*/
void
UniSetManager
::
managers
(
OManagerCommand
cmd
)
{
uinfo
<<
myname
<<
"(managers): mlist.size="
<<
mlist
.
size
()
<<
" cmd="
<<
cmd
<<
endl
;
{
//lock
uniset_rwmutex_rlock
lock
(
mlistMutex
);
for
(
const
auto
&
li
:
mlist
)
{
if
(
!
li
)
continue
;
try
{
switch
(
cmd
)
{
case
initial
:
li
->
initPOA
(
get_mptr
()
);
break
;
case
activ
:
li
->
activate
();
break
;
case
deactiv
:
li
->
deactivate
();
break
;
default
:
break
;
}
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): поймали CORBA::SystemException:"
<<
ex
.
NP_minorString
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): Caught CORBA::Exception. "
<<
ex
.
_name
()
<<
" ("
<<
li
->
getName
()
<<
")"
;
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): Caught omniORB::fatalException:"
<<
endl
<<
myname
<<
"(managers): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): "
<<
ex
<<
endl
<<
" Не смог зарегистрировать (разрегистрировать) объект -->"
<<
li
->
getName
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
}
}
// unlock
uinfo
<<
myname
<<
"(managers): mlist.size="
<<
mlist
.
size
()
<<
" cmd="
<<
cmd
<<
endl
;
{
//lock
uniset_rwmutex_rlock
lock
(
mlistMutex
);
for
(
const
auto
&
li
:
mlist
)
{
if
(
!
li
)
continue
;
try
{
switch
(
cmd
)
{
case
initial
:
li
->
initPOA
(
get_mptr
()
);
break
;
case
activ
:
li
->
activate
();
break
;
case
deactiv
:
li
->
deactivate
();
break
;
default
:
break
;
}
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): поймали CORBA::SystemException:"
<<
ex
.
NP_minorString
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): Caught CORBA::Exception. "
<<
ex
.
_name
()
<<
" ("
<<
li
->
getName
()
<<
")"
;
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): Caught omniORB::fatalException:"
<<
endl
<<
myname
<<
"(managers): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(managers): "
<<
ex
<<
endl
<<
" Не смог зарегистрировать (разрегистрировать) объект -->"
<<
li
->
getName
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
}
}
// unlock
}
// ------------------------------------------------------------------------------------------
/*!
...
...
@@ -341,97 +341,97 @@ void UniSetManager::managers( OManagerCommand cmd )
*/
void
UniSetManager
::
objects
(
OManagerCommand
cmd
)
{
uinfo
<<
myname
<<
"(objects): olist.size="
<<
olist
.
size
()
<<
" cmd="
<<
cmd
<<
endl
;
{
//lock
uniset_rwmutex_rlock
lock
(
olistMutex
);
for
(
const
auto
&
li
:
olist
)
{
if
(
!
li
)
continue
;
try
{
switch
(
cmd
)
{
case
initial
:
li
->
init
(
get_mptr
());
break
;
case
activ
:
li
->
activate
();
break
;
case
deactiv
:
li
->
deactivate
();
break
;
default
:
break
;
}
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): поймали CORBA::SystemException:"
<<
ex
.
NP_minorString
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): Caught CORBA::Exception. "
<<
ex
.
_name
()
<<
" ("
<<
li
->
getName
()
<<
")"
;
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): Caught omniORB::fatalException:"
<<
endl
;
err
<<
myname
<<
"(objects): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
()
<<
endl
;
ucrit
<<
err
.
str
();
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): "
<<
ex
<<
endl
;
err
<<
myname
<<
"(objects): не смог зарегистрировать (разрегистрировать) объект -->"
<<
li
->
getName
()
<<
endl
;
ucrit
<<
err
.
str
();
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
}
}
// unlock
uinfo
<<
myname
<<
"(objects): olist.size="
<<
olist
.
size
()
<<
" cmd="
<<
cmd
<<
endl
;
{
//lock
uniset_rwmutex_rlock
lock
(
olistMutex
);
for
(
const
auto
&
li
:
olist
)
{
if
(
!
li
)
continue
;
try
{
switch
(
cmd
)
{
case
initial
:
li
->
init
(
get_mptr
());
break
;
case
activ
:
li
->
activate
();
break
;
case
deactiv
:
li
->
deactivate
();
break
;
default
:
break
;
}
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): поймали CORBA::SystemException:"
<<
ex
.
NP_minorString
();
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): Caught CORBA::Exception. "
<<
ex
.
_name
()
<<
" ("
<<
li
->
getName
()
<<
")"
;
ucrit
<<
err
.
str
()
<<
endl
;
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
omniORB
::
fatalException
&
fe
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): Caught omniORB::fatalException:"
<<
endl
;
err
<<
myname
<<
"(objects): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
()
<<
endl
;
ucrit
<<
err
.
str
();
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ostringstream
err
;
err
<<
myname
<<
"(objects): "
<<
ex
<<
endl
;
err
<<
myname
<<
"(objects): не смог зарегистрировать (разрегистрировать) объект -->"
<<
li
->
getName
()
<<
endl
;
ucrit
<<
err
.
str
();
if
(
cmd
==
activ
)
{
cerr
<<
err
.
str
();
std
::
terminate
();
}
}
}
}
// unlock
}
// ------------------------------------------------------------------------------------------
/*!
...
...
@@ -440,11 +440,11 @@ void UniSetManager::objects(OManagerCommand cmd)
*/
bool
UniSetManager
::
activateObject
()
{
uinfo
<<
myname
<<
"(activateObjects): активизирую объекты"
<<
endl
;
UniSetObject
::
activateObject
();
managers
(
activ
);
objects
(
activ
);
return
true
;
uinfo
<<
myname
<<
"(activateObjects): активизирую объекты"
<<
endl
;
UniSetObject
::
activateObject
();
managers
(
activ
);
objects
(
activ
);
return
true
;
}
// ------------------------------------------------------------------------------------------
/*!
...
...
@@ -453,261 +453,261 @@ bool UniSetManager::activateObject()
*/
bool
UniSetManager
::
deactivateObject
()
{
uinfo
<<
myname
<<
"(deactivateObjects): деактивизирую объекты"
<<
endl
;
// именно в такой последовательности!
objects
(
deactiv
);
managers
(
deactiv
);
return
true
;
uinfo
<<
myname
<<
"(deactivateObjects): деактивизирую объекты"
<<
endl
;
// именно в такой последовательности!
objects
(
deactiv
);
managers
(
deactiv
);
return
true
;
}
// ------------------------------------------------------------------------------------------
const
std
::
shared_ptr
<
UniSetObject
>
UniSetManager
::
findObject
(
const
string
&
name
)
const
{
uniset_rwmutex_rlock
lock
(
olistMutex
);
uniset_rwmutex_rlock
lock
(
olistMutex
);
for
(
auto
&&
o
:
olist
)
{
if
(
o
->
getName
()
==
name
)
return
o
;
}
for
(
auto
&&
o
:
olist
)
{
if
(
o
->
getName
()
==
name
)
return
o
;
}
return
nullptr
;
return
nullptr
;
}
// ------------------------------------------------------------------------------------------
const
std
::
shared_ptr
<
UniSetManager
>
UniSetManager
::
findManager
(
const
string
&
name
)
const
{
uniset_rwmutex_rlock
lock
(
mlistMutex
);
uniset_rwmutex_rlock
lock
(
mlistMutex
);
for
(
auto
&&
m
:
mlist
)
{
if
(
m
->
getName
()
==
name
)
return
m
;
}
for
(
auto
&&
m
:
mlist
)
{
if
(
m
->
getName
()
==
name
)
return
m
;
}
return
nullptr
;
return
nullptr
;
}
// ------------------------------------------------------------------------------------------
const
std
::
shared_ptr
<
UniSetObject
>
UniSetManager
::
deepFindObject
(
const
string
&
name
)
const
{
{
auto
obj
=
findObject
(
name
);
{
auto
obj
=
findObject
(
name
);
if
(
obj
)
return
obj
;
}
if
(
obj
)
return
obj
;
}
auto
man
=
findManager
(
name
);
auto
man
=
findManager
(
name
);
if
(
man
)
{
auto
obj
=
dynamic_pointer_cast
<
UniSetObject
>
(
man
);
return
obj
;
}
if
(
man
)
{
auto
obj
=
dynamic_pointer_cast
<
UniSetObject
>
(
man
);
return
obj
;
}
// ищем в глубину у каждого менеджера
for
(
const
auto
&
m
:
mlist
)
{
auto
obj
=
m
->
deepFindObject
(
name
);
// ищем в глубину у каждого менеджера
for
(
const
auto
&
m
:
mlist
)
{
auto
obj
=
m
->
deepFindObject
(
name
);
if
(
obj
)
return
obj
;
}
if
(
obj
)
return
obj
;
}
return
nullptr
;
return
nullptr
;
}
// ------------------------------------------------------------------------------------------
void
UniSetManager
::
getAllObjectsList
(
std
::
vector
<
std
::
shared_ptr
<
UniSetObject
>
>&
vec
,
size_t
lim
)
{
// добавить себя
vec
.
push_back
(
get_ptr
());
// добавить подчинённые объекты
for
(
const
auto
&
o
:
olist
)
{
vec
.
push_back
(
o
);
if
(
lim
>
0
&&
vec
.
size
()
>=
lim
)
return
;
}
// добавить рекурсивно по менеджерам
for
(
const
auto
&
m
:
mlist
)
{
// вызываем рекурсивно
m
->
getAllObjectsList
(
vec
,
lim
);
}
// добавить себя
vec
.
push_back
(
get_ptr
());
// добавить подчинённые объекты
for
(
const
auto
&
o
:
olist
)
{
vec
.
push_back
(
o
);
if
(
lim
>
0
&&
vec
.
size
()
>=
lim
)
return
;
}
// добавить рекурсивно по менеджерам
for
(
const
auto
&
m
:
mlist
)
{
// вызываем рекурсивно
m
->
getAllObjectsList
(
vec
,
lim
);
}
}
// ------------------------------------------------------------------------------------------
void
UniSetManager
::
broadcast
(
const
TransportMessage
&
msg
)
{
// себя не забыть...
// push(msg);
// Всем объектам...
{
//lock
uniset_rwmutex_rlock
lock
(
olistMutex
);
for_each
(
olist
.
begin
(),
olist
.
end
(),
OPush
(
msg
));
// STL метод
}
// unlock
// Всем менеджерам....
{
//lock
uniset_rwmutex_rlock
lock
(
mlistMutex
);
for_each
(
mlist
.
begin
(),
mlist
.
end
(),
MPush
(
msg
));
// STL метод
}
// unlock
// себя не забыть...
// push(msg);
// Всем объектам...
{
//lock
uniset_rwmutex_rlock
lock
(
olistMutex
);
for_each
(
olist
.
begin
(),
olist
.
end
(),
OPush
(
msg
));
// STL метод
}
// unlock
// Всем менеджерам....
{
//lock
uniset_rwmutex_rlock
lock
(
mlistMutex
);
for_each
(
mlist
.
begin
(),
mlist
.
end
(),
MPush
(
msg
));
// STL метод
}
// unlock
}
// ------------------------------------------------------------------------------------------
bool
UniSetManager
::
addManager
(
const
std
::
shared_ptr
<
UniSetManager
>&
child
)
{
{
//lock
uniset_rwmutex_wrlock
lock
(
mlistMutex
);
// Проверка на совпадение
auto
it
=
find
(
mlist
.
begin
(),
mlist
.
end
(),
child
);
if
(
it
==
mlist
.
end
()
)
{
mlist
.
push_back
(
child
);
uinfo
<<
myname
<<
": добавляем менеджер "
<<
child
->
getName
()
<<
endl
;
}
else
uwarn
<<
myname
<<
": попытка повторного добавления объекта "
<<
child
->
getName
()
<<
endl
;
}
// unlock
return
true
;
{
//lock
uniset_rwmutex_wrlock
lock
(
mlistMutex
);
// Проверка на совпадение
auto
it
=
find
(
mlist
.
begin
(),
mlist
.
end
(),
child
);
if
(
it
==
mlist
.
end
()
)
{
mlist
.
push_back
(
child
);
uinfo
<<
myname
<<
": добавляем менеджер "
<<
child
->
getName
()
<<
endl
;
}
else
uwarn
<<
myname
<<
": попытка повторного добавления объекта "
<<
child
->
getName
()
<<
endl
;
}
// unlock
return
true
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetManager
::
removeManager
(
const
std
::
shared_ptr
<
UniSetManager
>&
child
)
{
{
//lock
uniset_rwmutex_wrlock
lock
(
mlistMutex
);
mlist
.
remove
(
child
);
}
// unlock
{
//lock
uniset_rwmutex_wrlock
lock
(
mlistMutex
);
mlist
.
remove
(
child
);
}
// unlock
return
true
;
return
true
;
}
// ------------------------------------------------------------------------------------------
int
UniSetManager
::
getObjectsInfo
(
const
std
::
shared_ptr
<
UniSetManager
>&
mngr
,
SimpleInfoSeq
*
seq
,
int
begin
,
const
long
uplimit
,
const
char
*
userparam
)
int
begin
,
const
long
uplimit
,
const
char
*
userparam
)
{
auto
ind
=
begin
;
// получаем у самого менеджера
SimpleInfo_var
msi
=
mngr
->
getInfo
(
userparam
);
(
*
seq
)[
ind
]
=
msi
;
ind
++
;
if
(
ind
>
uplimit
)
return
ind
;
for
(
const
auto
&
o
:
olist
)
{
try
{
SimpleInfo_var
si
=
o
->
getInfo
(
userparam
);
(
*
seq
)[
ind
]
=
si
;
ind
++
;
if
(
ind
>
uplimit
)
break
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(getObjectsInfo): CORBA::Exception"
<<
endl
;
}
catch
(...)
{
uwarn
<<
myname
<<
"(getObjectsInfo): не смог получить у объекта "
<<
uniset_conf
()
->
oind
->
getNameById
(
o
->
getId
()
)
<<
" информацию"
<<
endl
;
}
}
if
(
ind
>
uplimit
)
return
ind
;
// а далее у его менеджеров (рекурсивно)
for
(
const
auto
&
m
:
mlist
)
{
ind
=
getObjectsInfo
(
m
,
seq
,
ind
,
uplimit
,
userparam
);
if
(
ind
>
uplimit
)
break
;
}
return
ind
;
auto
ind
=
begin
;
// получаем у самого менеджера
SimpleInfo_var
msi
=
mngr
->
getInfo
(
userparam
);
(
*
seq
)[
ind
]
=
msi
;
ind
++
;
if
(
ind
>
uplimit
)
return
ind
;
for
(
const
auto
&
o
:
olist
)
{
try
{
SimpleInfo_var
si
=
o
->
getInfo
(
userparam
);
(
*
seq
)[
ind
]
=
si
;
ind
++
;
if
(
ind
>
uplimit
)
break
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(getObjectsInfo): CORBA::Exception"
<<
endl
;
}
catch
(...)
{
uwarn
<<
myname
<<
"(getObjectsInfo): не смог получить у объекта "
<<
uniset_conf
()
->
oind
->
getNameById
(
o
->
getId
()
)
<<
" информацию"
<<
endl
;
}
}
if
(
ind
>
uplimit
)
return
ind
;
// а далее у его менеджеров (рекурсивно)
for
(
const
auto
&
m
:
mlist
)
{
ind
=
getObjectsInfo
(
m
,
seq
,
ind
,
uplimit
,
userparam
);
if
(
ind
>
uplimit
)
break
;
}
return
ind
;
}
// ------------------------------------------------------------------------------------------
SimpleInfoSeq
*
UniSetManager
::
getObjectsInfo
(
CORBA
::
Long
maxlength
,
const
char
*
userparam
)
{
SimpleInfoSeq
*
res
=
new
SimpleInfoSeq
();
// ЗА ОСВОБОЖДЕНИЕ ПАМЯТИ ОТВЕЧАЕТ КЛИЕНТ!!!!!!
// поэтому ему лучше пользоваться при получении _var-классом
int
length
=
objectsCount
()
+
1
;
SimpleInfoSeq
*
res
=
new
SimpleInfoSeq
();
// ЗА ОСВОБОЖДЕНИЕ ПАМЯТИ ОТВЕЧАЕТ КЛИЕНТ!!!!!!
// поэтому ему лучше пользоваться при получении _var-классом
int
length
=
objectsCount
()
+
1
;
if
(
length
>=
maxlength
)
length
=
maxlength
;
if
(
length
>=
maxlength
)
length
=
maxlength
;
res
->
length
(
length
);
res
->
length
(
length
);
// используем рекурсивную функцию
int
ind
=
0
;
const
int
limit
=
length
;
// используем рекурсивную функцию
int
ind
=
0
;
const
int
limit
=
length
;
(
void
)
getObjectsInfo
(
get_mptr
(),
res
,
ind
,
limit
,
userparam
);
return
res
;
(
void
)
getObjectsInfo
(
get_mptr
(),
res
,
ind
,
limit
,
userparam
);
return
res
;
}
// ------------------------------------------------------------------------------------------
void
UniSetManager
::
apply_for_objects
(
OFunction
f
)
{
for
(
const
auto
&
o
:
olist
)
f
(
o
);
for
(
const
auto
&
o
:
olist
)
f
(
o
);
}
// ------------------------------------------------------------------------------------------
void
UniSetManager
::
apply_for_managers
(
UniSetManager
::
MFunction
f
)
{
for
(
const
auto
&
m
:
mlist
)
f
(
m
);
for
(
const
auto
&
m
:
mlist
)
f
(
m
);
}
// ------------------------------------------------------------------------------------------
size_t
UniSetManager
::
objectsCount
()
const
{
size_t
res
=
olist
.
size
()
+
mlist
.
size
();
size_t
res
=
olist
.
size
()
+
mlist
.
size
();
for
(
const
auto
&
i
:
mlist
)
res
+=
i
->
objectsCount
();
for
(
const
auto
&
i
:
mlist
)
res
+=
i
->
objectsCount
();
return
res
;
return
res
;
}
// ------------------------------------------------------------------------------------------
PortableServer
::
POA_ptr
UniSetManager
::
getPOA
()
{
return
PortableServer
::
POA
::
_duplicate
(
poa
);
return
PortableServer
::
POA
::
_duplicate
(
poa
);
}
// ------------------------------------------------------------------------------------------
PortableServer
::
POAManager_ptr
UniSetManager
::
getPOAManager
()
{
return
PortableServer
::
POAManager
::
_duplicate
(
pman
);
return
PortableServer
::
POAManager
::
_duplicate
(
pman
);
}
// ------------------------------------------------------------------------------------------
std
::
ostream
&
uniset
::
operator
<<
(
std
::
ostream
&
os
,
uniset
::
UniSetManager
::
OManagerCommand
&
cmd
)
{
// { deactiv, activ, initial, term };
if
(
cmd
==
uniset
::
UniSetManager
::
deactiv
)
return
os
<<
"deactivate"
;
// { deactiv, activ, initial, term };
if
(
cmd
==
uniset
::
UniSetManager
::
deactiv
)
return
os
<<
"deactivate"
;
if
(
cmd
==
uniset
::
UniSetManager
::
activ
)
return
os
<<
"activate"
;
if
(
cmd
==
uniset
::
UniSetManager
::
activ
)
return
os
<<
"activate"
;
if
(
cmd
==
uniset
::
UniSetManager
::
initial
)
return
os
<<
"init"
;
if
(
cmd
==
uniset
::
UniSetManager
::
initial
)
return
os
<<
"init"
;
return
os
<<
"unkwnown"
;
return
os
<<
"unkwnown"
;
}
src/Core/UniSetObject.cc
View file @
9674dd51
...
...
@@ -45,1090 +45,1090 @@ namespace uniset
{
#define CREATE_TIMER unisetstd::make_unique<PassiveCondTimer>();
// new PassiveSysTimer();
// ------------------------------------------------------------------------------------------
UniSetObject
::
UniSetObject
()
:
msgpid
(
0
),
regOK
(
false
),
active
(
0
),
threadcreate
(
false
),
myid
(
uniset
::
DefaultObjectId
),
oref
(
0
)
{
ui
=
make_shared
<
UInterface
>
(
uniset
::
DefaultObjectId
);
tmr
=
CREATE_TIMER
;
myname
=
"noname"
;
initObject
();
}
// ------------------------------------------------------------------------------------------
UniSetObject
::
UniSetObject
(
ObjectId
id
)
:
msgpid
(
0
),
regOK
(
false
),
active
(
0
),
threadcreate
(
true
),
myid
(
id
),
oref
(
0
)
{
ui
=
make_shared
<
UInterface
>
(
id
);
tmr
=
CREATE_TIMER
;
if
(
myid
!=
DefaultObjectId
)
setID
(
id
);
else
{
threadcreate
=
false
;
myname
=
"UnknownUniSetObject"
;
}
initObject
();
}
UniSetObject
::
UniSetObject
(
const
string
&
name
,
const
string
&
section
)
:
msgpid
(
0
),
regOK
(
false
),
active
(
0
),
threadcreate
(
true
),
myid
(
uniset
::
DefaultObjectId
),
oref
(
0
)
{
ui
=
make_shared
<
UInterface
>
(
uniset
::
DefaultObjectId
);
/*! \warning UniversalInterface не инициализируется идентификатором объекта */
tmr
=
CREATE_TIMER
;
myname
=
section
+
"/"
+
name
;
myid
=
ui
->
getIdByName
(
myname
);
setID
(
myid
);
initObject
();
}
// ------------------------------------------------------------------------------------------
UniSetObject
::~
UniSetObject
()
{
}
// ------------------------------------------------------------------------------------------
std
::
shared_ptr
<
UniSetObject
>
UniSetObject
::
get_ptr
()
{
return
shared_from_this
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
initObject
()
{
//
a_working = ATOMIC_VAR_INIT(0);
active
=
ATOMIC_VAR_INIT
(
0
);
refmutex
.
setName
(
myname
+
"_refmutex"
);
auto
conf
=
uniset_conf
();
if
(
!
conf
)
{
ostringstream
err
;
err
<<
myname
<<
"(initObject): Unknown configuration!!"
;
throw
SystemError
(
err
.
str
());
}
int
sz
=
conf
->
getArgPInt
(
"--uniset-object-size-message-queue"
,
conf
->
getField
(
"SizeOfMessageQueue"
),
1000
);
if
(
sz
>
0
)
setMaxSizeOfMessageQueue
(
sz
);
uinfo
<<
myname
<<
"(init): SizeOfMessageQueue="
<<
getMaxSizeOfMessageQueue
()
<<
endl
;
}
// ------------------------------------------------------------------------------------------
/*!
* \param om - указатель на менеджер, управляющий объектом
* \return Возвращает \a true если инициализация прошла успешно, и \a false если нет
*/
bool
UniSetObject
::
init
(
const
std
::
weak_ptr
<
UniSetManager
>&
om
)
{
uinfo
<<
myname
<<
": init..."
<<
endl
;
this
->
mymngr
=
om
;
uinfo
<<
myname
<<
": init ok..."
<<
endl
;
return
true
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setID
(
uniset
::
ObjectId
id
)
{
if
(
isActive
()
)
throw
ObjectNameAlready
(
"Set ID error: ObjectId is active.."
);
string
myfullname
=
ui
->
getNameById
(
id
);
myname
=
ORepHelpers
::
getShortName
(
myfullname
);
myid
=
id
;
ui
->
initBackId
(
myid
);
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setMaxSizeOfMessageQueue
(
size_t
s
)
{
mqueueMedium
.
setMaxSizeOfMessageQueue
(
s
);
mqueueLow
.
setMaxSizeOfMessageQueue
(
s
);
mqueueHi
.
setMaxSizeOfMessageQueue
(
s
);
}
// ------------------------------------------------------------------------------------------
size_t
UniSetObject
::
getMaxSizeOfMessageQueue
()
const
{
return
mqueueMedium
.
getMaxSizeOfMessageQueue
();
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
isActive
()
const
{
return
active
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setActive
(
bool
set
)
{
active
=
set
;
}
// ------------------------------------------------------------------------------------------
/*!
* \param vm - указатель на структуру, которая заполняется, если есть сообщение
* \return Возвращает указатель VoidMessagePtr если сообщение есть, и shared_ptr(nullptr) если нет
*/
VoidMessagePtr
UniSetObject
::
receiveMessage
()
{
if
(
!
mqueueHi
.
empty
()
)
return
mqueueHi
.
top
();
if
(
!
mqueueMedium
.
empty
()
)
return
mqueueMedium
.
top
();
return
mqueueLow
.
top
();
}
// ------------------------------------------------------------------------------------------
VoidMessagePtr
UniSetObject
::
waitMessage
(
timeout_t
timeMS
)
{
auto
m
=
receiveMessage
();
if
(
m
)
return
m
;
tmr
->
wait
(
timeMS
);
return
receiveMessage
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
registration
()
{
ulogrep
<<
myname
<<
": registration..."
<<
endl
;
if
(
myid
==
uniset
::
DefaultObjectId
)
{
ulogrep
<<
myname
<<
"(registration): Don`t registration. myid=DefaultObjectId
\n
"
;
return
;
}
auto
m
=
mymngr
.
lock
();
if
(
!
m
)
{
uwarn
<<
myname
<<
"(registration): unknown my manager"
<<
endl
;
string
err
(
myname
+
": unknown my manager"
);
throw
ORepFailed
(
err
);
}
{
uniset
::
uniset_rwmutex_rlock
lock
(
refmutex
);
if
(
!
oref
)
{
uwarn
<<
myname
<<
"(registration): oref is NULL!..."
<<
endl
;
return
;
}
}
auto
conf
=
uniset_conf
();
regOK
=
false
;
for
(
size_t
i
=
0
;
i
<
conf
->
getRepeatCount
();
i
++
)
{
try
{
ui
->
registered
(
myid
,
getRef
(),
true
);
regOK
=
true
;
break
;
}
catch
(
ObjectNameAlready
&
al
)
{
/*!
\warning По умолчанию объекты должны быть уникальны! Поэтому если идёт попытка повторной регистрации.
Мы чистим существующую ссылку и заменяем её на новую.
Это сделано для более надёжной работы, иначе может получится, что если объект перед завершением
не очистил за собой ссылку (не разрегистрировался), то больше он никогда не сможет вновь зарегистрироваться.
Т.к. \b надёжной функции проверки "жив" ли объект пока нет...
(так бы можно было проверить и если "не жив", то смело заменять ссылку на новую). Но существует обратная сторона:
если заменяемый объект "жив" и завершит свою работу, то он может почистить за собой ссылку и это тогда наш (новый)
объект станет недоступен другим, а знать об этом не будет!!!
*/
uwarn
<<
myname
<<
"(registration): replace object (ObjectNameAlready)"
<<
endl
;
unregistration
();
}
catch
(
const
uniset
::
ORepFailed
&
ex
)
{
uwarn
<<
myname
<<
"(registration): don`t registration in object reposotory "
<<
endl
;
}
catch
(
const
uniset
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(registration): "
<<
ex
<<
endl
;
}
msleep
(
conf
->
getRepeatTimeout
());
}
if
(
!
regOK
)
{
string
err
(
myname
+
"(registration): don`t registration in object reposotory"
);
ucrit
<<
err
<<
endl
;
throw
ORepFailed
(
err
);
}
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
unregistration
()
{
if
(
myid
<
0
)
// || !reg )
{
regOK
=
false
;
return
;
}
if
(
myid
==
uniset
::
DefaultObjectId
)
// -V547
{
uinfo
<<
myname
<<
"(unregister): myid=DefaultObjectId
\n
"
;
regOK
=
false
;
return
;
}
{
uniset
::
uniset_rwmutex_rlock
lock
(
refmutex
);
if
(
!
oref
)
{
uwarn
<<
myname
<<
"(unregister): oref NULL!"
<<
endl
;
regOK
=
false
;
return
;
}
}
try
{
uinfo
<<
myname
<<
": unregister "
<<
endl
;
ui
->
unregister
(
myid
);
uinfo
<<
myname
<<
": unregister ok. "
<<
endl
;
}
catch
(...)
{
std
::
exception_ptr
p
=
std
::
current_exception
();
uwarn
<<
myname
<<
": don`t registration in object repository"
<<
" err: "
<<
(
p
?
p
.
__cxa_exception_type
()
->
name
()
:
"unknown"
)
<<
endl
;
}
regOK
=
false
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
waitFinish
()
{
// поток завершаем в конце, после пользовательских deactivateObject()
if
(
!
thr
)
return
;
std
::
unique_lock
<
std
::
mutex
>
lk
(
m_working
);
// cv_working.wait_for(lk, std::chrono::milliseconds(workingTerminateTimeout), [&](){ return (a_working == false); } );
cv_working
.
wait
(
lk
,
[
=
]()
{
return
a_working
==
false
;
});
if
(
thr
->
isRunning
()
)
thr
->
join
();
}
// ------------------------------------------------------------------------------------------
CORBA
::
Boolean
UniSetObject
::
exist
()
{
return
true
;
}
// ------------------------------------------------------------------------------------------
ObjectId
UniSetObject
::
getId
()
{
return
myid
;
}
// ------------------------------------------------------------------------------------------
const
ObjectId
UniSetObject
::
getId
()
const
{
return
myid
;
}
// ------------------------------------------------------------------------------------------
string
UniSetObject
::
getName
()
const
{
return
myname
;
}
// ------------------------------------------------------------------------------------------
const
string
UniSetObject
::
getStrType
()
{
return
CORBA
::
string_dup
(
getType
());
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
termWaiting
()
{
if
(
tmr
)
tmr
->
terminate
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setThreadPriority
(
Poco
::
Thread
::
Priority
p
)
{
if
(
thr
)
thr
->
setPriority
(
p
);
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
push
(
const
TransportMessage
&
tm
)
{
auto
vm
=
make_shared
<
VoidMessage
>
(
tm
);
if
(
vm
->
priority
==
Message
::
Medium
)
mqueueMedium
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
High
)
mqueueHi
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
Low
)
mqueueLow
.
push
(
vm
);
else
// на всякий по умолчанию medium
mqueueMedium
.
push
(
vm
);
termWaiting
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
pushMessage
(
const
char
*
msg
,
::
CORBA
::
Long
mtype
,
const
::
uniset
::
Timespec
&
tm
,
const
::
uniset
::
ProducerInfo
&
pi
,
::
CORBA
::
Long
priority
,
::
CORBA
::
Long
consumer
)
{
uniset
::
TextMessage
tmsg
(
msg
,
mtype
,
tm
,
pi
,
(
uniset
::
Message
::
Priority
)
priority
,
consumer
);
auto
vm
=
tmsg
.
toLocalVoidMessage
();
if
(
vm
->
priority
==
Message
::
Medium
)
mqueueMedium
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
High
)
mqueueHi
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
Low
)
mqueueLow
.
push
(
vm
);
else
// на всякий по умолчанию medium
mqueueMedium
.
push
(
vm
);
termWaiting
();
}
// ------------------------------------------------------------------------------------------
// new PassiveSysTimer();
// ------------------------------------------------------------------------------------------
UniSetObject
::
UniSetObject
()
:
msgpid
(
0
),
regOK
(
false
),
active
(
0
),
threadcreate
(
false
),
myid
(
uniset
::
DefaultObjectId
),
oref
(
0
)
{
ui
=
make_shared
<
UInterface
>
(
uniset
::
DefaultObjectId
);
tmr
=
CREATE_TIMER
;
myname
=
"noname"
;
initObject
();
}
// ------------------------------------------------------------------------------------------
UniSetObject
::
UniSetObject
(
ObjectId
id
)
:
msgpid
(
0
),
regOK
(
false
),
active
(
0
),
threadcreate
(
true
),
myid
(
id
),
oref
(
0
)
{
ui
=
make_shared
<
UInterface
>
(
id
);
tmr
=
CREATE_TIMER
;
if
(
myid
!=
DefaultObjectId
)
setID
(
id
);
else
{
threadcreate
=
false
;
myname
=
"UnknownUniSetObject"
;
}
initObject
();
}
UniSetObject
::
UniSetObject
(
const
string
&
name
,
const
string
&
section
)
:
msgpid
(
0
),
regOK
(
false
),
active
(
0
),
threadcreate
(
true
),
myid
(
uniset
::
DefaultObjectId
),
oref
(
0
)
{
ui
=
make_shared
<
UInterface
>
(
uniset
::
DefaultObjectId
);
/*! \warning UniversalInterface не инициализируется идентификатором объекта */
tmr
=
CREATE_TIMER
;
myname
=
section
+
"/"
+
name
;
myid
=
ui
->
getIdByName
(
myname
);
setID
(
myid
);
initObject
();
}
// ------------------------------------------------------------------------------------------
UniSetObject
::~
UniSetObject
()
{
}
// ------------------------------------------------------------------------------------------
std
::
shared_ptr
<
UniSetObject
>
UniSetObject
::
get_ptr
()
{
return
shared_from_this
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
initObject
()
{
//
a_working = ATOMIC_VAR_INIT(0);
active
=
ATOMIC_VAR_INIT
(
0
);
refmutex
.
setName
(
myname
+
"_refmutex"
);
auto
conf
=
uniset_conf
();
if
(
!
conf
)
{
ostringstream
err
;
err
<<
myname
<<
"(initObject): Unknown configuration!!"
;
throw
SystemError
(
err
.
str
());
}
int
sz
=
conf
->
getArgPInt
(
"--uniset-object-size-message-queue"
,
conf
->
getField
(
"SizeOfMessageQueue"
),
1000
);
if
(
sz
>
0
)
setMaxSizeOfMessageQueue
(
sz
);
uinfo
<<
myname
<<
"(init): SizeOfMessageQueue="
<<
getMaxSizeOfMessageQueue
()
<<
endl
;
}
// ------------------------------------------------------------------------------------------
/*!
* \param om - указатель на менеджер, управляющий объектом
* \return Возвращает \a true если инициализация прошла успешно, и \a false если нет
*/
bool
UniSetObject
::
init
(
const
std
::
weak_ptr
<
UniSetManager
>&
om
)
{
uinfo
<<
myname
<<
": init..."
<<
endl
;
this
->
mymngr
=
om
;
uinfo
<<
myname
<<
": init ok..."
<<
endl
;
return
true
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setID
(
uniset
::
ObjectId
id
)
{
if
(
isActive
()
)
throw
ObjectNameAlready
(
"Set ID error: ObjectId is active.."
);
string
myfullname
=
ui
->
getNameById
(
id
);
myname
=
ORepHelpers
::
getShortName
(
myfullname
);
myid
=
id
;
ui
->
initBackId
(
myid
);
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setMaxSizeOfMessageQueue
(
size_t
s
)
{
mqueueMedium
.
setMaxSizeOfMessageQueue
(
s
);
mqueueLow
.
setMaxSizeOfMessageQueue
(
s
);
mqueueHi
.
setMaxSizeOfMessageQueue
(
s
);
}
// ------------------------------------------------------------------------------------------
size_t
UniSetObject
::
getMaxSizeOfMessageQueue
()
const
{
return
mqueueMedium
.
getMaxSizeOfMessageQueue
();
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
isActive
()
const
{
return
active
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setActive
(
bool
set
)
{
active
=
set
;
}
// ------------------------------------------------------------------------------------------
/*!
* \param vm - указатель на структуру, которая заполняется, если есть сообщение
* \return Возвращает указатель VoidMessagePtr если сообщение есть, и shared_ptr(nullptr) если нет
*/
VoidMessagePtr
UniSetObject
::
receiveMessage
()
{
if
(
!
mqueueHi
.
empty
()
)
return
mqueueHi
.
top
();
if
(
!
mqueueMedium
.
empty
()
)
return
mqueueMedium
.
top
();
return
mqueueLow
.
top
();
}
// ------------------------------------------------------------------------------------------
VoidMessagePtr
UniSetObject
::
waitMessage
(
timeout_t
timeMS
)
{
auto
m
=
receiveMessage
();
if
(
m
)
return
m
;
tmr
->
wait
(
timeMS
);
return
receiveMessage
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
registration
()
{
ulogrep
<<
myname
<<
": registration..."
<<
endl
;
if
(
myid
==
uniset
::
DefaultObjectId
)
{
ulogrep
<<
myname
<<
"(registration): Don`t registration. myid=DefaultObjectId
\n
"
;
return
;
}
auto
m
=
mymngr
.
lock
();
if
(
!
m
)
{
uwarn
<<
myname
<<
"(registration): unknown my manager"
<<
endl
;
string
err
(
myname
+
": unknown my manager"
);
throw
ORepFailed
(
err
);
}
{
uniset
::
uniset_rwmutex_rlock
lock
(
refmutex
);
if
(
!
oref
)
{
uwarn
<<
myname
<<
"(registration): oref is NULL!..."
<<
endl
;
return
;
}
}
auto
conf
=
uniset_conf
();
regOK
=
false
;
for
(
size_t
i
=
0
;
i
<
conf
->
getRepeatCount
();
i
++
)
{
try
{
ui
->
registered
(
myid
,
getRef
(),
true
);
regOK
=
true
;
break
;
}
catch
(
ObjectNameAlready
&
al
)
{
/*!
\warning По умолчанию объекты должны быть уникальны! Поэтому если идёт попытка повторной регистрации.
Мы чистим существующую ссылку и заменяем её на новую.
Это сделано для более надёжной работы, иначе может получится, что если объект перед завершением
не очистил за собой ссылку (не разрегистрировался), то больше он никогда не сможет вновь зарегистрироваться.
Т.к. \b надёжной функции проверки "жив" ли объект пока нет...
(так бы можно было проверить и если "не жив", то смело заменять ссылку на новую). Но существует обратная сторона:
если заменяемый объект "жив" и завершит свою работу, то он может почистить за собой ссылку и это тогда наш (новый)
объект станет недоступен другим, а знать об этом не будет!!!
*/
uwarn
<<
myname
<<
"(registration): replace object (ObjectNameAlready)"
<<
endl
;
unregistration
();
}
catch
(
const
uniset
::
ORepFailed
&
ex
)
{
uwarn
<<
myname
<<
"(registration): don`t registration in object reposotory "
<<
endl
;
}
catch
(
const
uniset
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(registration): "
<<
ex
<<
endl
;
}
msleep
(
conf
->
getRepeatTimeout
());
}
if
(
!
regOK
)
{
string
err
(
myname
+
"(registration): don`t registration in object reposotory"
);
ucrit
<<
err
<<
endl
;
throw
ORepFailed
(
err
);
}
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
unregistration
()
{
if
(
myid
<
0
)
// || !reg )
{
regOK
=
false
;
return
;
}
if
(
myid
==
uniset
::
DefaultObjectId
)
// -V547
{
uinfo
<<
myname
<<
"(unregister): myid=DefaultObjectId
\n
"
;
regOK
=
false
;
return
;
}
{
uniset
::
uniset_rwmutex_rlock
lock
(
refmutex
);
if
(
!
oref
)
{
uwarn
<<
myname
<<
"(unregister): oref NULL!"
<<
endl
;
regOK
=
false
;
return
;
}
}
try
{
uinfo
<<
myname
<<
": unregister "
<<
endl
;
ui
->
unregister
(
myid
);
uinfo
<<
myname
<<
": unregister ok. "
<<
endl
;
}
catch
(...)
{
std
::
exception_ptr
p
=
std
::
current_exception
();
uwarn
<<
myname
<<
": don`t registration in object repository"
<<
" err: "
<<
(
p
?
p
.
__cxa_exception_type
()
->
name
()
:
"unknown"
)
<<
endl
;
}
regOK
=
false
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
waitFinish
()
{
// поток завершаем в конце, после пользовательских deactivateObject()
if
(
!
thr
)
return
;
std
::
unique_lock
<
std
::
mutex
>
lk
(
m_working
);
// cv_working.wait_for(lk, std::chrono::milliseconds(workingTerminateTimeout), [&](){ return (a_working == false); } );
cv_working
.
wait
(
lk
,
[
=
]()
{
return
a_working
==
false
;
});
if
(
thr
->
isRunning
()
)
thr
->
join
();
}
// ------------------------------------------------------------------------------------------
CORBA
::
Boolean
UniSetObject
::
exist
()
{
return
true
;
}
// ------------------------------------------------------------------------------------------
ObjectId
UniSetObject
::
getId
()
{
return
myid
;
}
// ------------------------------------------------------------------------------------------
const
ObjectId
UniSetObject
::
getId
()
const
{
return
myid
;
}
// ------------------------------------------------------------------------------------------
string
UniSetObject
::
getName
()
const
{
return
myname
;
}
// ------------------------------------------------------------------------------------------
const
string
UniSetObject
::
getStrType
()
{
return
CORBA
::
string_dup
(
getType
());
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
termWaiting
()
{
if
(
tmr
)
tmr
->
terminate
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
setThreadPriority
(
Poco
::
Thread
::
Priority
p
)
{
if
(
thr
)
thr
->
setPriority
(
p
);
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
push
(
const
TransportMessage
&
tm
)
{
auto
vm
=
make_shared
<
VoidMessage
>
(
tm
);
if
(
vm
->
priority
==
Message
::
Medium
)
mqueueMedium
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
High
)
mqueueHi
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
Low
)
mqueueLow
.
push
(
vm
);
else
// на всякий по умолчанию medium
mqueueMedium
.
push
(
vm
);
termWaiting
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
pushMessage
(
const
char
*
msg
,
::
CORBA
::
Long
mtype
,
const
::
uniset
::
Timespec
&
tm
,
const
::
uniset
::
ProducerInfo
&
pi
,
::
CORBA
::
Long
priority
,
::
CORBA
::
Long
consumer
)
{
uniset
::
TextMessage
tmsg
(
msg
,
mtype
,
tm
,
pi
,
(
uniset
::
Message
::
Priority
)
priority
,
consumer
);
auto
vm
=
tmsg
.
toLocalVoidMessage
();
if
(
vm
->
priority
==
Message
::
Medium
)
mqueueMedium
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
High
)
mqueueHi
.
push
(
vm
);
else
if
(
vm
->
priority
==
Message
::
Low
)
mqueueLow
.
push
(
vm
);
else
// на всякий по умолчанию medium
mqueueMedium
.
push
(
vm
);
termWaiting
();
}
// ------------------------------------------------------------------------------------------
#ifndef DISABLE_REST_API
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
httpGet
(
const
Poco
::
URI
::
QueryParameters
&
p
)
{
Poco
::
JSON
::
Object
::
Ptr
jret
=
new
Poco
::
JSON
::
Object
();
httpGetMyInfo
(
jret
);
return
jret
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
httpHelp
(
const
Poco
::
URI
::
QueryParameters
&
p
)
{
uniset
::
json
::
help
::
object
myhelp
(
myname
);
{
uniset
::
json
::
help
::
item
cmd
(
"params/get"
,
"get value for parameter"
);
cmd
.
param
(
"param1,param2,..."
,
"paremeter names. Default: all"
);
myhelp
.
add
(
cmd
);
}
{
uniset
::
json
::
help
::
item
cmd
(
"params/set"
,
"set value for parameter"
);
cmd
.
param
(
"param1=val1,param2=val2,..."
,
"paremeters"
);
myhelp
.
add
(
cmd
);
}
return
myhelp
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
httpGetMyInfo
(
Poco
::
JSON
::
Object
::
Ptr
root
)
{
Poco
::
JSON
::
Object
::
Ptr
my
=
uniset
::
json
::
make_child
(
root
,
"object"
);
my
->
set
(
"name"
,
myname
);
my
->
set
(
"id"
,
getId
());
my
->
set
(
"msgCount"
,
countMessages
());
my
->
set
(
"lostMessages"
,
getCountOfLostMessages
());
my
->
set
(
"maxSizeOfMessageQueue"
,
getMaxSizeOfMessageQueue
());
my
->
set
(
"isActive"
,
isActive
());
my
->
set
(
"objectType"
,
getStrType
());
return
my
;
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /configure/xxxx
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_configure
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
params
)
{
if
(
req
==
"get"
)
return
request_configure_get
(
req
,
params
);
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown command.."
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /params/xxxx
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_params
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
params
)
{
if
(
req
==
"get"
)
return
request_params_get
(
req
,
params
);
if
(
req
==
"set"
)
return
request_params_set
(
req
,
params
);
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown command.."
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /configure/get?[ID|NAME]&props=testname,name] from configure.xml
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_configure_get
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
params
)
{
Poco
::
JSON
::
Object
::
Ptr
json
=
new
Poco
::
JSON
::
Object
();
Poco
::
JSON
::
Array
::
Ptr
jdata
=
uniset
::
json
::
make_child_array
(
json
,
"conf"
);
auto
my
=
httpGetMyInfo
(
json
);
if
(
params
.
empty
()
)
{
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown id or name..."
;
throw
uniset
::
SystemError
(
err
.
str
());
}
auto
idlist
=
uniset
::
explode_str
(
params
[
0
].
first
,
','
);
if
(
idlist
.
empty
()
)
{
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown id or name in '"
<<
params
[
0
].
first
<<
"'"
;
throw
uniset
::
SystemError
(
err
.
str
());
}
string
props
=
{
""
};
for
(
const
auto
&
p
:
params
)
{
if
(
p
.
first
==
"props"
)
{
props
=
p
.
second
;
break
;
}
}
for
(
const
auto
&
id
:
idlist
)
{
Poco
::
JSON
::
Object
::
Ptr
j
=
request_configure_by_name
(
id
,
props
);
if
(
j
)
jdata
->
add
(
j
);
}
return
json
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_configure_by_name
(
const
string
&
name
,
const
std
::
string
&
props
)
{
Poco
::
JSON
::
Object
::
Ptr
jdata
=
new
Poco
::
JSON
::
Object
();
auto
conf
=
uniset_conf
();
ObjectId
id
=
conf
->
getAnyID
(
name
);
if
(
id
==
DefaultObjectId
)
{
ostringstream
err
;
err
<<
name
<<
" not found.."
;
jdata
->
set
(
name
,
""
);
jdata
->
set
(
"error"
,
err
.
str
());
return
jdata
;
}
xmlNode
*
xmlnode
=
conf
->
getXMLObjectNode
(
id
);
if
(
!
xmlnode
)
{
ostringstream
err
;
err
<<
name
<<
" not found confnode.."
;
jdata
->
set
(
name
,
""
);
jdata
->
set
(
"error"
,
err
.
str
());
return
jdata
;
}
UniXML
::
iterator
it
(
xmlnode
);
jdata
->
set
(
"name"
,
it
.
getProp
(
"name"
));
jdata
->
set
(
"id"
,
it
.
getProp
(
"id"
));
if
(
!
props
.
empty
()
)
{
auto
lst
=
uniset
::
explode_str
(
props
,
','
);
for
(
const
auto
&
p
:
lst
)
jdata
->
set
(
p
,
it
.
getProp
(
p
));
}
else
{
auto
lst
=
it
.
getPropList
();
for
(
const
auto
&
p
:
lst
)
jdata
->
set
(
p
.
first
,
p
.
second
);
}
return
jdata
;
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /conf/set?prop1=val1&prop2=val2
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_params_set
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
ostringstream
err
;
err
<<
"(request_params): 'set' not realized yet"
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /conf/get?prop1&prop2&prop3
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_params_get
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
ostringstream
err
;
err
<<
"(request_params): 'get' not realized yet"
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
httpGet
(
const
Poco
::
URI
::
QueryParameters
&
p
)
{
Poco
::
JSON
::
Object
::
Ptr
jret
=
new
Poco
::
JSON
::
Object
();
httpGetMyInfo
(
jret
);
return
jret
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
httpHelp
(
const
Poco
::
URI
::
QueryParameters
&
p
)
{
uniset
::
json
::
help
::
object
myhelp
(
myname
);
{
uniset
::
json
::
help
::
item
cmd
(
"params/get"
,
"get value for parameter"
);
cmd
.
param
(
"param1,param2,..."
,
"paremeter names. Default: all"
);
myhelp
.
add
(
cmd
);
}
{
uniset
::
json
::
help
::
item
cmd
(
"params/set"
,
"set value for parameter"
);
cmd
.
param
(
"param1=val1,param2=val2,..."
,
"paremeters"
);
myhelp
.
add
(
cmd
);
}
return
myhelp
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
httpGetMyInfo
(
Poco
::
JSON
::
Object
::
Ptr
root
)
{
Poco
::
JSON
::
Object
::
Ptr
my
=
uniset
::
json
::
make_child
(
root
,
"object"
);
my
->
set
(
"name"
,
myname
);
my
->
set
(
"id"
,
getId
());
my
->
set
(
"msgCount"
,
countMessages
());
my
->
set
(
"lostMessages"
,
getCountOfLostMessages
());
my
->
set
(
"maxSizeOfMessageQueue"
,
getMaxSizeOfMessageQueue
());
my
->
set
(
"isActive"
,
isActive
());
my
->
set
(
"objectType"
,
getStrType
());
return
my
;
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /configure/xxxx
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_configure
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
params
)
{
if
(
req
==
"get"
)
return
request_configure_get
(
req
,
params
);
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown command.."
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /params/xxxx
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_params
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
params
)
{
if
(
req
==
"get"
)
return
request_params_get
(
req
,
params
);
if
(
req
==
"set"
)
return
request_params_set
(
req
,
params
);
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown command.."
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /configure/get?[ID|NAME]&props=testname,name] from configure.xml
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_configure_get
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
params
)
{
Poco
::
JSON
::
Object
::
Ptr
json
=
new
Poco
::
JSON
::
Object
();
Poco
::
JSON
::
Array
::
Ptr
jdata
=
uniset
::
json
::
make_child_array
(
json
,
"conf"
);
auto
my
=
httpGetMyInfo
(
json
);
if
(
params
.
empty
()
)
{
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown id or name..."
;
throw
uniset
::
SystemError
(
err
.
str
());
}
auto
idlist
=
uniset
::
explode_str
(
params
[
0
].
first
,
','
);
if
(
idlist
.
empty
()
)
{
ostringstream
err
;
err
<<
"(request_conf): BAD REQUEST: Unknown id or name in '"
<<
params
[
0
].
first
<<
"'"
;
throw
uniset
::
SystemError
(
err
.
str
());
}
string
props
=
{
""
};
for
(
const
auto
&
p
:
params
)
{
if
(
p
.
first
==
"props"
)
{
props
=
p
.
second
;
break
;
}
}
for
(
const
auto
&
id
:
idlist
)
{
Poco
::
JSON
::
Object
::
Ptr
j
=
request_configure_by_name
(
id
,
props
);
if
(
j
)
jdata
->
add
(
j
);
}
return
json
;
}
// ------------------------------------------------------------------------------------------
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_configure_by_name
(
const
string
&
name
,
const
std
::
string
&
props
)
{
Poco
::
JSON
::
Object
::
Ptr
jdata
=
new
Poco
::
JSON
::
Object
();
auto
conf
=
uniset_conf
();
ObjectId
id
=
conf
->
getAnyID
(
name
);
if
(
id
==
DefaultObjectId
)
{
ostringstream
err
;
err
<<
name
<<
" not found.."
;
jdata
->
set
(
name
,
""
);
jdata
->
set
(
"error"
,
err
.
str
());
return
jdata
;
}
xmlNode
*
xmlnode
=
conf
->
getXMLObjectNode
(
id
);
if
(
!
xmlnode
)
{
ostringstream
err
;
err
<<
name
<<
" not found confnode.."
;
jdata
->
set
(
name
,
""
);
jdata
->
set
(
"error"
,
err
.
str
());
return
jdata
;
}
UniXML
::
iterator
it
(
xmlnode
);
jdata
->
set
(
"name"
,
it
.
getProp
(
"name"
));
jdata
->
set
(
"id"
,
it
.
getProp
(
"id"
));
if
(
!
props
.
empty
()
)
{
auto
lst
=
uniset
::
explode_str
(
props
,
','
);
for
(
const
auto
&
p
:
lst
)
jdata
->
set
(
p
,
it
.
getProp
(
p
));
}
else
{
auto
lst
=
it
.
getPropList
();
for
(
const
auto
&
p
:
lst
)
jdata
->
set
(
p
.
first
,
p
.
second
);
}
return
jdata
;
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /conf/set?prop1=val1&prop2=val2
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_params_set
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
ostringstream
err
;
err
<<
"(request_params): 'set' not realized yet"
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
// обработка запроса вида: /conf/get?prop1&prop2&prop3
Poco
::
JSON
::
Object
::
Ptr
UniSetObject
::
request_params_get
(
const
std
::
string
&
req
,
const
Poco
::
URI
::
QueryParameters
&
p
)
{
ostringstream
err
;
err
<<
"(request_params): 'get' not realized yet"
;
throw
uniset
::
SystemError
(
err
.
str
());
}
// ------------------------------------------------------------------------------------------
#endif
// ------------------------------------------------------------------------------------------
ObjectPtr
UniSetObject
::
getRef
()
const
{
uniset
::
uniset_rwmutex_rlock
lock
(
refmutex
);
return
(
uniset
::
ObjectPtr
)
CORBA
::
Object
::
_duplicate
(
oref
);
}
// ------------------------------------------------------------------------------------------
size_t
UniSetObject
::
countMessages
()
{
return
(
mqueueMedium
.
size
()
+
mqueueLow
.
size
()
+
mqueueHi
.
size
());
}
// ------------------------------------------------------------------------------------------
size_t
UniSetObject
::
getCountOfLostMessages
()
const
{
return
(
mqueueMedium
.
getCountOfLostMessages
()
+
mqueueLow
.
getCountOfLostMessages
()
+
mqueueHi
.
getCountOfLostMessages
()
);
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
activateObject
()
{
return
true
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
deactivateObject
()
{
return
true
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
uterminate
()
{
//
setActive(false);
auto
act
=
UniSetActivator
::
Instance
();
act
->
terminate
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
thread
(
bool
create
)
{
threadcreate
=
create
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
offThread
()
{
threadcreate
=
false
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
onThread
()
{
threadcreate
=
true
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
deactivate
()
{
if
(
!
isActive
()
)
{
try
{
deactivateObject
();
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
.
what
()
<<
endl
;
}
return
true
;
}
setActive
(
false
);
// завершаем поток обработки сообщений
if
(
tmr
)
tmr
->
terminate
();
try
{
uinfo
<<
myname
<<
"(deactivate): ..."
<<
endl
;
auto
m
=
mymngr
.
lock
();
if
(
m
)
{
PortableServer
::
POA_var
poamngr
=
m
->
getPOA
();
if
(
!
PortableServer
::
POA_Helper
::
is_nil
(
poamngr
)
)
{
try
{
deactivateObject
();
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
.
what
()
<<
endl
;
}
unregistration
();
PortableServer
::
ObjectId_var
oid
=
poamngr
->
servant_to_id
(
static_cast
<
PortableServer
::
ServantBase
*>
(
this
));
poamngr
->
deactivate_object
(
oid
);
uinfo
<<
myname
<<
"(deactivate): finished..."
<<
endl
;
waitFinish
();
return
true
;
}
}
uwarn
<<
myname
<<
"(deactivate): manager already destroyed.."
<<
endl
;
}
catch
(
const
CORBA
::
TRANSIENT
&
)
{
uwarn
<<
myname
<<
"(deactivate): isExist: нет связи..."
<<
endl
;
}
catch
(
CORBA
::
SystemException
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
"поймали CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
"поймали CORBA::Exception."
<<
endl
;
}
catch
(
const
uniset
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
<<
endl
;
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
.
what
()
<<
endl
;
}
return
false
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
activate
()
{
uinfo
<<
myname
<<
": activate..."
<<
endl
;
auto
m
=
mymngr
.
lock
();
if
(
!
m
)
{
ostringstream
err
;
err
<<
myname
<<
"(activate): mymngr=NULL!!! activate failure..."
;
ucrit
<<
err
.
str
()
<<
endl
;
throw
SystemError
(
err
.
str
());
}
PortableServer
::
POA_var
poa
=
m
->
getPOA
();
if
(
poa
==
NULL
||
CORBA
::
is_nil
(
poa
)
)
{
string
err
(
myname
+
": не задан менеджер"
);
throw
ORepFailed
(
err
);
}
bool
actOK
=
false
;
auto
conf
=
uniset_conf
();
for
(
size_t
i
=
0
;
i
<
conf
->
getRepeatCount
();
i
++
)
{
try
{
if
(
conf
->
isTransientIOR
()
)
{
// activate witch generate id
poa
->
activate_object
(
static_cast
<
PortableServer
::
ServantBase
*>
(
this
));
actOK
=
true
;
break
;
}
else
{
// А если myid==uniset::DefaultObjectId
// то myname = noname. ВСЕГДА!
if
(
myid
==
uniset
::
DefaultObjectId
)
{
uwarn
<<
myname
<<
"(activate): Не задан ID!!! IGNORE ACTIVATE..."
<<
endl
;
// вызываем на случай если она переопределена в дочерних классах
// Например в UniSetManager, если здесь не вызвать, то не будут инициализированы подчинённые объекты.
// (см. UniSetManager::activateObject)
activateObject
();
return
false
;
}
// Always use the same object id.
PortableServer
::
ObjectId_var
oid
=
PortableServer
::
string_to_ObjectId
(
myname
.
c_str
());
// Activate object...
poa
->
activate_object_with_id
(
oid
,
this
);
actOK
=
true
;
break
;
}
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
if
(
string
(
ex
.
_name
())
!=
"ObjectAlreadyActive"
)
{
ostringstream
err
;
err
<<
myname
<<
"(activate): ACTIVATE ERROR: "
<<
ex
.
_name
();
ucrit
<<
myname
<<
"(activate): "
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
uwarn
<<
myname
<<
"(activate): IGNORE.. catch "
<<
ex
.
_name
()
<<
endl
;
}
msleep
(
conf
->
getRepeatTimeout
()
);
}
if
(
!
actOK
)
{
ostringstream
err
;
err
<<
myname
<<
"(activate): DON`T ACTIVATE.."
;
ucrit
<<
myname
<<
"(activate): "
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
{
uniset
::
uniset_rwmutex_wrlock
lock
(
refmutex
);
oref
=
poa
->
servant_to_reference
(
static_cast
<
PortableServer
::
ServantBase
*>
(
this
)
);
}
registration
();
// Запускаем поток обработки сообщений
setActive
(
true
);
if
(
myid
!=
uniset
::
DefaultObjectId
&&
threadcreate
)
{
thr
=
unisetstd
::
make_unique
<
ThreadCreator
<
UniSetObject
>
>
(
this
,
&
UniSetObject
::
work
);
//thr->setCancel(ost::Thread::cancelDeferred);
std
::
unique_lock
<
std
::
mutex
>
locker
(
m_working
);
a_working
=
true
;
thr
->
start
();
}
else
{
// выдаём предупреждение только если поток не отключён, но при этом не задан ID
if
(
threadcreate
)
{
uinfo
<<
myname
<<
": ?? не задан ObjectId...("
<<
"myid="
<<
myid
<<
" threadcreate="
<<
threadcreate
<<
")"
<<
endl
;
}
thread
(
false
);
}
activateObject
();
uinfo
<<
myname
<<
": activate ok."
<<
endl
;
return
true
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
work
()
{
uinfo
<<
myname
<<
": thread processing messages running..."
<<
endl
;
msgpid
=
thr
?
thr
->
getTID
()
:
Poco
::
Process
::
id
();
{
std
::
unique_lock
<
std
::
mutex
>
locker
(
m_working
);
a_working
=
true
;
}
while
(
isActive
()
)
callback
();
uinfo
<<
myname
<<
": thread processing messages stopped..."
<<
endl
;
{
std
::
unique_lock
<
std
::
mutex
>
locker
(
m_working
);
a_working
=
false
;
}
cv_working
.
notify_all
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
callback
()
{
// При реализации с использованием waitMessage() каждый раз при вызове askTimer() необходимо
// проверять возвращаемое значение на UniSetTimers::WaitUpTime и вызывать termWaiting(),
// чтобы избежать ситуации, когда процесс до заказа таймера 'спал'(в функции waitMessage()) и после
// заказа продолжит спать(т.е. обработчик вызван не будет)...
try
{
auto
m
=
waitMessage
(
sleepTime
);
if
(
m
)
processingMessage
(
m
.
get
());
if
(
!
isActive
()
)
return
;
sleepTime
=
checkTimers
(
this
);
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ucrit
<<
myname
<<
"(callback): "
<<
ex
<<
endl
;
}
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
processingMessage
(
const
uniset
::
VoidMessage
*
msg
)
{
try
{
switch
(
msg
->
type
)
{
case
Message
:
:
SensorInfo
:
sensorInfo
(
reinterpret_cast
<
const
SensorMessage
*>
(
msg
)
);
break
;
case
Message
:
:
Timer
:
timerInfo
(
reinterpret_cast
<
const
TimerMessage
*>
(
msg
)
);
break
;
case
Message
:
:
SysCommand
:
sysCommand
(
reinterpret_cast
<
const
SystemMessage
*>
(
msg
)
);
break
;
case
Message
:
:
TextMessage
:
{
TextMessage
tm
(
msg
);
onTextMessage
(
&
tm
);
break
;
}
default
:
break
;
}
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ucrit
<<
myname
<<
"(processingMessage): CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(processingMessage): CORBA::Exception: "
<<
ex
.
_name
()
<<
endl
;
}
catch
(
omniORB
::
fatalException
&
fe
)
{
if
(
ulog
()
->
is_crit
()
)
{
ulog
()
->
crit
()
<<
myname
<<
"(processingMessage): Caught omniORB::fatalException:"
<<
endl
;
ulog
()
->
crit
()
<<
myname
<<
"(processingMessage): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ucrit
<<
myname
<<
"(processingMessage): "
<<
ex
<<
endl
;
}
catch
(
const
std
::
exception
&
ex
)
{
ucrit
<<
myname
<<
"(processingMessage): "
<<
ex
.
what
()
<<
endl
;
}
/*
catch( ... )
{
std::exception_ptr p = std::current_exception();
ucrit <<(p ? p.__cxa_exception_type()->name() : "null") << std::endl;
}
*/
}
// ------------------------------------------------------------------------------------------
timeout_t
UniSetObject
::
askTimer
(
TimerId
timerid
,
timeout_t
timeMS
,
clock_t
ticks
,
Message
::
Priority
p
)
{
timeout_t
tsleep
=
LT_Object
::
askTimer
(
timerid
,
timeMS
,
ticks
,
p
);
if
(
tsleep
!=
UniSetTimer
::
WaitUpTime
)
termWaiting
();
return
tsleep
;
}
// ------------------------------------------------------------------------------------------
uniset
::
SimpleInfo
*
UniSetObject
::
getInfo
(
const
char
*
userparam
)
{
ostringstream
info
;
info
.
setf
(
ios
::
left
,
ios
::
adjustfield
);
info
<<
"("
<<
myid
<<
")"
<<
setw
(
40
)
<<
myname
<<
" date: "
<<
uniset
::
dateToString
()
<<
" time: "
<<
uniset
::
timeToString
()
<<
"
\n
===============================================================================
\n
"
<<
"pid="
<<
setw
(
10
)
<<
Poco
::
Process
::
id
()
<<
" tid="
<<
setw
(
10
);
if
(
threadcreate
)
{
if
(
thr
)
{
msgpid
=
thr
->
getTID
();
// заодно(на всякий) обновим и внутреннюю информацию
info
<<
msgpid
;
}
else
info
<<
"не запущен"
;
}
else
info
<<
"откл."
;
info
<<
"
\t
count="
<<
countMessages
()
<<
"
\t
medium: "
<<
" maxMsg="
<<
mqueueMedium
.
getMaxQueueMessages
()
<<
" qFull("
<<
mqueueMedium
.
getMaxSizeOfMessageQueue
()
<<
")="
<<
mqueueMedium
.
getCountOfLostMessages
()
<<
"
\t
hi: "
<<
" maxMsg="
<<
mqueueHi
.
getMaxQueueMessages
()
<<
" qFull("
<<
mqueueHi
.
getMaxSizeOfMessageQueue
()
<<
")="
<<
mqueueHi
.
getCountOfLostMessages
()
<<
"
\t
low: "
<<
" maxMsg="
<<
mqueueLow
.
getMaxQueueMessages
()
<<
" qFull("
<<
mqueueLow
.
getMaxSizeOfMessageQueue
()
<<
")="
<<
mqueueLow
.
getCountOfLostMessages
();
SimpleInfo
*
res
=
new
SimpleInfo
();
res
->
info
=
info
.
str
().
c_str
();
// CORBA::string_dup(info.str().c_str());
res
->
id
=
myid
;
return
res
;
// ._retn();
}
// ------------------------------------------------------------------------------------------
SimpleInfo
*
UniSetObject
::
apiRequest
(
const
char
*
request
)
{
// ------------------------------------------------------------------------------------------
ObjectPtr
UniSetObject
::
getRef
()
const
{
uniset
::
uniset_rwmutex_rlock
lock
(
refmutex
);
return
(
uniset
::
ObjectPtr
)
CORBA
::
Object
::
_duplicate
(
oref
);
}
// ------------------------------------------------------------------------------------------
size_t
UniSetObject
::
countMessages
()
{
return
(
mqueueMedium
.
size
()
+
mqueueLow
.
size
()
+
mqueueHi
.
size
());
}
// ------------------------------------------------------------------------------------------
size_t
UniSetObject
::
getCountOfLostMessages
()
const
{
return
(
mqueueMedium
.
getCountOfLostMessages
()
+
mqueueLow
.
getCountOfLostMessages
()
+
mqueueHi
.
getCountOfLostMessages
()
);
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
activateObject
()
{
return
true
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
deactivateObject
()
{
return
true
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
uterminate
()
{
//
setActive(false);
auto
act
=
UniSetActivator
::
Instance
();
act
->
terminate
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
thread
(
bool
create
)
{
threadcreate
=
create
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
offThread
()
{
threadcreate
=
false
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
onThread
()
{
threadcreate
=
true
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
deactivate
()
{
if
(
!
isActive
()
)
{
try
{
deactivateObject
();
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
.
what
()
<<
endl
;
}
return
true
;
}
setActive
(
false
);
// завершаем поток обработки сообщений
if
(
tmr
)
tmr
->
terminate
();
try
{
uinfo
<<
myname
<<
"(deactivate): ..."
<<
endl
;
auto
m
=
mymngr
.
lock
();
if
(
m
)
{
PortableServer
::
POA_var
poamngr
=
m
->
getPOA
();
if
(
!
PortableServer
::
POA_Helper
::
is_nil
(
poamngr
)
)
{
try
{
deactivateObject
();
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
.
what
()
<<
endl
;
}
unregistration
();
PortableServer
::
ObjectId_var
oid
=
poamngr
->
servant_to_id
(
static_cast
<
PortableServer
::
ServantBase
*>
(
this
));
poamngr
->
deactivate_object
(
oid
);
uinfo
<<
myname
<<
"(deactivate): finished..."
<<
endl
;
waitFinish
();
return
true
;
}
}
uwarn
<<
myname
<<
"(deactivate): manager already destroyed.."
<<
endl
;
}
catch
(
const
CORBA
::
TRANSIENT
&
)
{
uwarn
<<
myname
<<
"(deactivate): isExist: нет связи..."
<<
endl
;
}
catch
(
CORBA
::
SystemException
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
"поймали CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
"поймали CORBA::Exception."
<<
endl
;
}
catch
(
const
uniset
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
<<
endl
;
}
catch
(
std
::
exception
&
ex
)
{
uwarn
<<
myname
<<
"(deactivate): "
<<
ex
.
what
()
<<
endl
;
}
return
false
;
}
// ------------------------------------------------------------------------------------------
bool
UniSetObject
::
activate
()
{
uinfo
<<
myname
<<
": activate..."
<<
endl
;
auto
m
=
mymngr
.
lock
();
if
(
!
m
)
{
ostringstream
err
;
err
<<
myname
<<
"(activate): mymngr=NULL!!! activate failure..."
;
ucrit
<<
err
.
str
()
<<
endl
;
throw
SystemError
(
err
.
str
());
}
PortableServer
::
POA_var
poa
=
m
->
getPOA
();
if
(
poa
==
NULL
||
CORBA
::
is_nil
(
poa
)
)
{
string
err
(
myname
+
": не задан менеджер"
);
throw
ORepFailed
(
err
);
}
bool
actOK
=
false
;
auto
conf
=
uniset_conf
();
for
(
size_t
i
=
0
;
i
<
conf
->
getRepeatCount
();
i
++
)
{
try
{
if
(
conf
->
isTransientIOR
()
)
{
// activate witch generate id
poa
->
activate_object
(
static_cast
<
PortableServer
::
ServantBase
*>
(
this
));
actOK
=
true
;
break
;
}
else
{
// А если myid==uniset::DefaultObjectId
// то myname = noname. ВСЕГДА!
if
(
myid
==
uniset
::
DefaultObjectId
)
{
uwarn
<<
myname
<<
"(activate): Не задан ID!!! IGNORE ACTIVATE..."
<<
endl
;
// вызываем на случай если она переопределена в дочерних классах
// Например в UniSetManager, если здесь не вызвать, то не будут инициализированы подчинённые объекты.
// (см. UniSetManager::activateObject)
activateObject
();
return
false
;
}
// Always use the same object id.
PortableServer
::
ObjectId_var
oid
=
PortableServer
::
string_to_ObjectId
(
myname
.
c_str
());
// Activate object...
poa
->
activate_object_with_id
(
oid
,
this
);
actOK
=
true
;
break
;
}
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
if
(
string
(
ex
.
_name
())
!=
"ObjectAlreadyActive"
)
{
ostringstream
err
;
err
<<
myname
<<
"(activate): ACTIVATE ERROR: "
<<
ex
.
_name
();
ucrit
<<
myname
<<
"(activate): "
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
uwarn
<<
myname
<<
"(activate): IGNORE.. catch "
<<
ex
.
_name
()
<<
endl
;
}
msleep
(
conf
->
getRepeatTimeout
()
);
}
if
(
!
actOK
)
{
ostringstream
err
;
err
<<
myname
<<
"(activate): DON`T ACTIVATE.."
;
ucrit
<<
myname
<<
"(activate): "
<<
err
.
str
()
<<
endl
;
throw
uniset
::
SystemError
(
err
.
str
());
}
{
uniset
::
uniset_rwmutex_wrlock
lock
(
refmutex
);
oref
=
poa
->
servant_to_reference
(
static_cast
<
PortableServer
::
ServantBase
*>
(
this
)
);
}
registration
();
// Запускаем поток обработки сообщений
setActive
(
true
);
if
(
myid
!=
uniset
::
DefaultObjectId
&&
threadcreate
)
{
thr
=
unisetstd
::
make_unique
<
ThreadCreator
<
UniSetObject
>
>
(
this
,
&
UniSetObject
::
work
);
//thr->setCancel(ost::Thread::cancelDeferred);
std
::
unique_lock
<
std
::
mutex
>
locker
(
m_working
);
a_working
=
true
;
thr
->
start
();
}
else
{
// выдаём предупреждение только если поток не отключён, но при этом не задан ID
if
(
threadcreate
)
{
uinfo
<<
myname
<<
": ?? не задан ObjectId...("
<<
"myid="
<<
myid
<<
" threadcreate="
<<
threadcreate
<<
")"
<<
endl
;
}
thread
(
false
);
}
activateObject
();
uinfo
<<
myname
<<
": activate ok."
<<
endl
;
return
true
;
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
work
()
{
uinfo
<<
myname
<<
": thread processing messages running..."
<<
endl
;
msgpid
=
thr
?
thr
->
getTID
()
:
Poco
::
Process
::
id
();
{
std
::
unique_lock
<
std
::
mutex
>
locker
(
m_working
);
a_working
=
true
;
}
while
(
isActive
()
)
callback
();
uinfo
<<
myname
<<
": thread processing messages stopped..."
<<
endl
;
{
std
::
unique_lock
<
std
::
mutex
>
locker
(
m_working
);
a_working
=
false
;
}
cv_working
.
notify_all
();
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
callback
()
{
// При реализации с использованием waitMessage() каждый раз при вызове askTimer() необходимо
// проверять возвращаемое значение на UniSetTimers::WaitUpTime и вызывать termWaiting(),
// чтобы избежать ситуации, когда процесс до заказа таймера 'спал'(в функции waitMessage()) и после
// заказа продолжит спать(т.е. обработчик вызван не будет)...
try
{
auto
m
=
waitMessage
(
sleepTime
);
if
(
m
)
processingMessage
(
m
.
get
());
if
(
!
isActive
()
)
return
;
sleepTime
=
checkTimers
(
this
);
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ucrit
<<
myname
<<
"(callback): "
<<
ex
<<
endl
;
}
}
// ------------------------------------------------------------------------------------------
void
UniSetObject
::
processingMessage
(
const
uniset
::
VoidMessage
*
msg
)
{
try
{
switch
(
msg
->
type
)
{
case
Message
:
:
SensorInfo
:
sensorInfo
(
reinterpret_cast
<
const
SensorMessage
*>
(
msg
)
);
break
;
case
Message
:
:
Timer
:
timerInfo
(
reinterpret_cast
<
const
TimerMessage
*>
(
msg
)
);
break
;
case
Message
:
:
SysCommand
:
sysCommand
(
reinterpret_cast
<
const
SystemMessage
*>
(
msg
)
);
break
;
case
Message
:
:
TextMessage
:
{
TextMessage
tm
(
msg
);
onTextMessage
(
&
tm
);
break
;
}
default
:
break
;
}
}
catch
(
const
CORBA
::
SystemException
&
ex
)
{
ucrit
<<
myname
<<
"(processingMessage): CORBA::SystemException: "
<<
ex
.
NP_minorString
()
<<
endl
;
}
catch
(
const
CORBA
::
Exception
&
ex
)
{
uwarn
<<
myname
<<
"(processingMessage): CORBA::Exception: "
<<
ex
.
_name
()
<<
endl
;
}
catch
(
omniORB
::
fatalException
&
fe
)
{
if
(
ulog
()
->
is_crit
()
)
{
ulog
()
->
crit
()
<<
myname
<<
"(processingMessage): Caught omniORB::fatalException:"
<<
endl
;
ulog
()
->
crit
()
<<
myname
<<
"(processingMessage): file: "
<<
fe
.
file
()
<<
" line: "
<<
fe
.
line
()
<<
" mesg: "
<<
fe
.
errmsg
()
<<
endl
;
}
}
catch
(
const
uniset
::
Exception
&
ex
)
{
ucrit
<<
myname
<<
"(processingMessage): "
<<
ex
<<
endl
;
}
catch
(
const
std
::
exception
&
ex
)
{
ucrit
<<
myname
<<
"(processingMessage): "
<<
ex
.
what
()
<<
endl
;
}
/*
catch( ... )
{
std::exception_ptr p = std::current_exception();
ucrit <<(p ? p.__cxa_exception_type()->name() : "null") << std::endl;
}
*/
}
// ------------------------------------------------------------------------------------------
timeout_t
UniSetObject
::
askTimer
(
TimerId
timerid
,
timeout_t
timeMS
,
clock_t
ticks
,
Message
::
Priority
p
)
{
timeout_t
tsleep
=
LT_Object
::
askTimer
(
timerid
,
timeMS
,
ticks
,
p
);
if
(
tsleep
!=
UniSetTimer
::
WaitUpTime
)
termWaiting
();
return
tsleep
;
}
// ------------------------------------------------------------------------------------------
uniset
::
SimpleInfo
*
UniSetObject
::
getInfo
(
const
char
*
userparam
)
{
ostringstream
info
;
info
.
setf
(
ios
::
left
,
ios
::
adjustfield
);
info
<<
"("
<<
myid
<<
")"
<<
setw
(
40
)
<<
myname
<<
" date: "
<<
uniset
::
dateToString
()
<<
" time: "
<<
uniset
::
timeToString
()
<<
"
\n
===============================================================================
\n
"
<<
"pid="
<<
setw
(
10
)
<<
Poco
::
Process
::
id
()
<<
" tid="
<<
setw
(
10
);
if
(
threadcreate
)
{
if
(
thr
)
{
msgpid
=
thr
->
getTID
();
// заодно(на всякий) обновим и внутреннюю информацию
info
<<
msgpid
;
}
else
info
<<
"не запущен"
;
}
else
info
<<
"откл."
;
info
<<
"
\t
count="
<<
countMessages
()
<<
"
\t
medium: "
<<
" maxMsg="
<<
mqueueMedium
.
getMaxQueueMessages
()
<<
" qFull("
<<
mqueueMedium
.
getMaxSizeOfMessageQueue
()
<<
")="
<<
mqueueMedium
.
getCountOfLostMessages
()
<<
"
\t
hi: "
<<
" maxMsg="
<<
mqueueHi
.
getMaxQueueMessages
()
<<
" qFull("
<<
mqueueHi
.
getMaxSizeOfMessageQueue
()
<<
")="
<<
mqueueHi
.
getCountOfLostMessages
()
<<
"
\t
low: "
<<
" maxMsg="
<<
mqueueLow
.
getMaxQueueMessages
()
<<
" qFull("
<<
mqueueLow
.
getMaxSizeOfMessageQueue
()
<<
")="
<<
mqueueLow
.
getCountOfLostMessages
();
SimpleInfo
*
res
=
new
SimpleInfo
();
res
->
info
=
info
.
str
().
c_str
();
// CORBA::string_dup(info.str().c_str());
res
->
id
=
myid
;
return
res
;
// ._retn();
}
// ------------------------------------------------------------------------------------------
SimpleInfo
*
UniSetObject
::
apiRequest
(
const
char
*
request
)
{
#ifdef DISABLE_REST_API
return
getInfo
(
request
);
return
getInfo
(
request
);
#else
SimpleInfo
*
ret
=
new
SimpleInfo
();
ret
->
id
=
getId
();
ostringstream
err
;
try
{
Poco
::
URI
uri
(
request
);
if
(
ulog
()
->
is_level9
()
)
ulog
()
->
level9
()
<<
myname
<<
"(apiRequest): request: "
<<
request
<<
endl
;
ostringstream
out
;
std
::
string
query
=
""
;
// Пока не будем требовать обязательно использовать формат /api/vesion/query..
// но если указан, то проверяем..
std
::
vector
<
std
::
string
>
seg
;
uri
.
getPathSegments
(
seg
);
size_t
qind
=
0
;
if
(
seg
.
size
()
>
0
&&
seg
[
0
]
==
"api"
)
{
// проверка: /api/version/query[?params]..
if
(
seg
.
size
()
<
2
||
seg
[
1
]
!=
UHttp
::
UHTTP_API_VERSION
)
{
Poco
::
JSON
::
Object
jdata
;
jdata
.
set
(
"error"
,
Poco
::
Net
::
HTTPServerResponse
::
getReasonForStatus
(
Poco
::
Net
::
HTTPResponse
::
HTTP_BAD_REQUEST
));
jdata
.
set
(
"ecode"
,
(
int
)
Poco
::
Net
::
HTTPResponse
::
HTTP_BAD_REQUEST
);
jdata
.
set
(
"message"
,
"BAD REQUEST STRUCTURE"
);
jdata
.
stringify
(
out
);
ret
->
info
=
out
.
str
().
c_str
();
// CORBA::string_dup(..)
return
ret
;
}
if
(
seg
.
size
()
>
2
)
qind
=
2
;
}
else
if
(
seg
.
size
()
==
1
)
qind
=
0
;
query
=
seg
.
empty
()
?
""
:
seg
[
qind
];
// обработка запроса..
if
(
query
==
"help"
)
{
// запрос вида: /help?params
auto
reply
=
httpHelp
(
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
if
(
query
==
"configure"
)
{
// запрос вида: /configure/query?params
string
qconf
=
(
seg
.
size
()
>
(
qind
+
1
)
)
?
seg
[
qind
+
1
]
:
""
;
auto
reply
=
request_configure
(
qconf
,
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
if
(
query
==
"params"
)
{
// запрос вида: /params/query?params
string
qconf
=
(
seg
.
size
()
>
(
qind
+
1
)
)
?
seg
[
qind
+
1
]
:
""
;
auto
reply
=
request_params
(
qconf
,
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
if
(
!
query
.
empty
()
)
{
// запрос вида: /cmd?params
auto
reply
=
httpRequest
(
query
,
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
{
// запрос без команды /?params
auto
reply
=
httpGet
(
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
ret
->
info
=
out
.
str
().
c_str
();
// CORBA::string_dup(..)
return
ret
;
}
catch
(
Poco
::
SyntaxException
&
ex
)
{
err
<<
ex
.
displayText
();
}
catch
(
uniset
::
SystemError
&
ex
)
{
err
<<
ex
;
}
catch
(
std
::
exception
&
ex
)
{
err
<<
ex
.
what
();
}
Poco
::
JSON
::
Object
jdata
;
jdata
.
set
(
"error"
,
err
.
str
());
jdata
.
set
(
"ecode"
,
(
int
)
Poco
::
Net
::
HTTPResponse
::
HTTP_INTERNAL_SERVER_ERROR
);
//
jdata.set("ename", Poco::Net::HTTPResponse::getReasonForStatus(Poco::Net::HTTPResponse::HTTP_INTERNAL_SERVER_ERROR));
ostringstream
out
;
jdata
.
stringify
(
out
);
ret
->
info
=
out
.
str
().
c_str
();
// CORBA::string_dup(..)
return
ret
;
SimpleInfo
*
ret
=
new
SimpleInfo
();
ret
->
id
=
getId
();
ostringstream
err
;
try
{
Poco
::
URI
uri
(
request
);
if
(
ulog
()
->
is_level9
()
)
ulog
()
->
level9
()
<<
myname
<<
"(apiRequest): request: "
<<
request
<<
endl
;
ostringstream
out
;
std
::
string
query
=
""
;
// Пока не будем требовать обязательно использовать формат /api/vesion/query..
// но если указан, то проверяем..
std
::
vector
<
std
::
string
>
seg
;
uri
.
getPathSegments
(
seg
);
size_t
qind
=
0
;
if
(
seg
.
size
()
>
0
&&
seg
[
0
]
==
"api"
)
{
// проверка: /api/version/query[?params]..
if
(
seg
.
size
()
<
2
||
seg
[
1
]
!=
UHttp
::
UHTTP_API_VERSION
)
{
Poco
::
JSON
::
Object
jdata
;
jdata
.
set
(
"error"
,
Poco
::
Net
::
HTTPServerResponse
::
getReasonForStatus
(
Poco
::
Net
::
HTTPResponse
::
HTTP_BAD_REQUEST
));
jdata
.
set
(
"ecode"
,
(
int
)
Poco
::
Net
::
HTTPResponse
::
HTTP_BAD_REQUEST
);
jdata
.
set
(
"message"
,
"BAD REQUEST STRUCTURE"
);
jdata
.
stringify
(
out
);
ret
->
info
=
out
.
str
().
c_str
();
// CORBA::string_dup(..)
return
ret
;
}
if
(
seg
.
size
()
>
2
)
qind
=
2
;
}
else
if
(
seg
.
size
()
==
1
)
qind
=
0
;
query
=
seg
.
empty
()
?
""
:
seg
[
qind
];
// обработка запроса..
if
(
query
==
"help"
)
{
// запрос вида: /help?params
auto
reply
=
httpHelp
(
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
if
(
query
==
"configure"
)
{
// запрос вида: /configure/query?params
string
qconf
=
(
seg
.
size
()
>
(
qind
+
1
)
)
?
seg
[
qind
+
1
]
:
""
;
auto
reply
=
request_configure
(
qconf
,
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
if
(
query
==
"params"
)
{
// запрос вида: /params/query?params
string
qconf
=
(
seg
.
size
()
>
(
qind
+
1
)
)
?
seg
[
qind
+
1
]
:
""
;
auto
reply
=
request_params
(
qconf
,
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
if
(
!
query
.
empty
()
)
{
// запрос вида: /cmd?params
auto
reply
=
httpRequest
(
query
,
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
else
{
// запрос без команды /?params
auto
reply
=
httpGet
(
uri
.
getQueryParameters
());
reply
->
stringify
(
out
);
}
ret
->
info
=
out
.
str
().
c_str
();
// CORBA::string_dup(..)
return
ret
;
}
catch
(
Poco
::
SyntaxException
&
ex
)
{
err
<<
ex
.
displayText
();
}
catch
(
uniset
::
SystemError
&
ex
)
{
err
<<
ex
;
}
catch
(
std
::
exception
&
ex
)
{
err
<<
ex
.
what
();
}
Poco
::
JSON
::
Object
jdata
;
jdata
.
set
(
"error"
,
err
.
str
());
jdata
.
set
(
"ecode"
,
(
int
)
Poco
::
Net
::
HTTPResponse
::
HTTP_INTERNAL_SERVER_ERROR
);
//
jdata.set("ename", Poco::Net::HTTPResponse::getReasonForStatus(Poco::Net::HTTPResponse::HTTP_INTERNAL_SERVER_ERROR));
ostringstream
out
;
jdata
.
stringify
(
out
);
ret
->
info
=
out
.
str
().
c_str
();
// CORBA::string_dup(..)
return
ret
;
#endif
}
// ------------------------------------------------------------------------------------------
ostream
&
operator
<<
(
ostream
&
os
,
UniSetObject
&
obj
)
{
SimpleInfo_var
si
=
obj
.
getInfo
();
return
os
<<
si
->
info
;
}
// ------------------------------------------------------------------------------------------
}
// ------------------------------------------------------------------------------------------
ostream
&
operator
<<
(
ostream
&
os
,
UniSetObject
&
obj
)
{
SimpleInfo_var
si
=
obj
.
getInfo
();
return
os
<<
si
->
info
;
}
// ------------------------------------------------------------------------------------------
#undef CREATE_TIMER
}
// end of namespace uniset
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment