Merge 3.15 branch into 7.0

This commit is contained in:
Andrew Johnson
2021-09-17 11:44:04 -05:00
6 changed files with 59 additions and 72 deletions
+1 -1
View File
@@ -455,7 +455,7 @@ $(COMMON_DIR)/%.html: ../%.pl
$(PODTOHTML) -s -o $(notdir $@) $<
@$(MV) $(notdir $@) $@
.PRECIOUS: $(COMMON_DIR)/%.html %.html
.PRECIOUS: $(COMMON_DIR)/%.html
#---------------------------------------------------------------
# DB files
+4 -4
View File
@@ -563,6 +563,10 @@ $(INSTALL_DOC)/%: ../%
$(ECHO) "Installing doc $@"
@$(INSTALL) -d -m $(INSTALL_PERMISSIONS) $< $(INSTALL_DOC)
$(INSTALL_HTML)/$(HTMLS_DIR)/%: $(COMMON_DIR)/%
$(ECHO) "Installing generated html $@"
@$(INSTALL) -d -m $(INSTALL_PERMISSIONS) $< $(@D)
$(INSTALL_HTML)/$(HTMLS_DIR)/%: %
$(ECHO) "Installing html $@"
@$(INSTALL) -d -m $(INSTALL_PERMISSIONS) $< $(@D)
@@ -571,10 +575,6 @@ $(INSTALL_HTML)/$(HTMLS_DIR)/%: ../%
$(ECHO) "Installing html $@"
@$(INSTALL) -d -m $(INSTALL_PERMISSIONS) $< $(@D)
$(INSTALL_HTML)/$(HTMLS_DIR)/%: $(COMMON_DIR)/%
$(ECHO) "Installing generated html $@"
@$(INSTALL) -d -m $(INSTALL_PERMISSIONS) $< $(@D)
$(INSTALL_TEMPLATES_SUBDIR)/%: ../%
$(ECHO) "Installing $@"
@$(INSTALL) -d -m $(INSTALL_PERMISSIONS) $< $(@D)
+7
View File
@@ -1927,6 +1927,13 @@ header and removed the need for dbScan.c to reach into the internals of its
## Changes from the 3.15 branch since 3.15.9
### Fix timers on MS Windows for non-EPICS threads
The waitable timer changes in 3.15.9 broke calls to `epicsThreadSleep()` and
similar routines that used timers (including `ca_pend_event()`) when made from
threads that were not started using the epicsThread APIs.
[This problem](https://github.com/epics-base/epics-base/pull/200)
[has now been fixed](https://github.com/epics-base/epics-base/pull/201).
## Changes made between 3.15.8 and 3.15.9
@@ -71,22 +71,23 @@ SELM is a menu, with three choices:
=menu dfanoutSELM
If SELM=="All", then all output links are used, and the values of
If SELM is C<All>, then all output links are used, and the values of
SELL and SELN are ignored.
If SELM=="Specified", then the value of SELN is used to specify a single
If SELM is C<Specified>, then the value of SELN is used to specify a single
link which will be used. If SELN==0, then no link will be used; if SELN==1,
then OUTA will be used, and so on.
SELN can either have its value set directly, or have its values retrieved
from another EPICS PV. If SELL is a valid PV link, then SELN will be set to
the values of the linked PV.
SELN can either have its value set directly, or have it retrieved from
another EPICS PV. If SELL is a valid PV link, then SELN will be read from
the linked PV.
If SELM=="Mask", then SELN will be treated as a bit mask. If bit one of
SELN is set, then OUTA will be used, if bit two is set, OUTB will be used.
Thus if SELN==5, OUTC and OUTA will be used.
If SELM is C<Mask>, then SELN will be treated as a bit mask. If bit zero
(the LSB) of SELN is set, then OUTA will be written to; if bit one is set,
OUTB will be written to, and so on. Thus when SELN==5, both OUTC and OUTA
will be written to.
=fields OUTA, OUTB, OUTC, OUTD, OUTE, OUTF, OUTG, OUTH
=fields SELL, SELM, SELN, OUTA, OUTB, OUTC, OUTD, OUTE, OUTF, OUTG, OUTH
=head3 Operator Display Parameters
+29 -47
View File
@@ -674,21 +674,34 @@ void epicsThreadMustJoin(epicsThreadId id)
}
/*
* epicsThreadSuspendSelf ()
* getMyWin32ThreadParam ()
*/
LIBCOM_API void epicsStdCall epicsThreadSuspendSelf ()
static void* getMyWin32ThreadParam ( win32ThreadGlobal * pGbl )
{
win32ThreadGlobal * pGbl = fetchWin32ThreadGlobal ();
win32ThreadParam * pParm;
DWORD stat;
assert ( pGbl );
if ( ! pGbl ) {
pGbl = fetchWin32ThreadGlobal ();
assert ( pGbl );
}
pParm = ( win32ThreadParam * )
TlsGetValue ( pGbl->tlsIndexThreadLibraryEPICS );
if ( ! pParm ) {
pParm = epicsThreadImplicitCreate ();
}
return pParm;
}
/*
* epicsThreadSuspendSelf ()
*/
LIBCOM_API void epicsStdCall epicsThreadSuspendSelf ()
{
DWORD stat;
win32ThreadGlobal * pGbl = fetchWin32ThreadGlobal ();
win32ThreadParam * pParm = getMyWin32ThreadParam ( pGbl );
if ( pParm ) {
EnterCriticalSection ( & pGbl->mutex );
pParm->isSuspended = 1;
@@ -732,17 +745,9 @@ LIBCOM_API unsigned epicsStdCall epicsThreadGetPriority (epicsThreadId id)
* epicsThreadGetPrioritySelf ()
*/
LIBCOM_API unsigned epicsStdCall epicsThreadGetPrioritySelf ()
{
win32ThreadGlobal * pGbl = fetchWin32ThreadGlobal ();
win32ThreadParam * pParm;
{
win32ThreadParam * pParm = getMyWin32ThreadParam ( NULL );
assert ( pGbl );
pParm = ( win32ThreadParam * )
TlsGetValue ( pGbl->tlsIndexThreadLibraryEPICS );
if ( ! pParm ) {
pParm = epicsThreadImplicitCreate ();
}
if ( pParm ) {
return pParm->epicsPriority;
}
@@ -803,15 +808,12 @@ LIBCOM_API int epicsStdCall epicsThreadIsSuspended ( epicsThreadId id )
*/
HANDLE osdThreadGetTimer()
{
win32ThreadGlobal * pGbl = fetchWin32ThreadGlobal ();
win32ThreadParam * pParm;
assert ( pGbl );
pParm = ( win32ThreadParam * )
TlsGetValue ( pGbl->tlsIndexThreadLibraryEPICS );
return pParm->timer;
win32ThreadParam * pParm = getMyWin32ThreadParam ( NULL );
if (pParm) {
return pParm->timer;
} else {
return NULL;
}
}
/*
@@ -892,17 +894,8 @@ double epicsStdCall epicsThreadSleepQuantum ()
*/
LIBCOM_API epicsThreadId epicsStdCall epicsThreadGetIdSelf (void)
{
win32ThreadGlobal * pGbl = fetchWin32ThreadGlobal ();
win32ThreadParam * pParm;
assert ( pGbl );
pParm = ( win32ThreadParam * ) TlsGetValue (
pGbl->tlsIndexThreadLibraryEPICS );
if ( ! pParm ) {
pParm = epicsThreadImplicitCreate ();
assert ( pParm ); /* very dangerous to allow non-unique thread id into use */
}
win32ThreadParam * pParm = getMyWin32ThreadParam ( NULL );
assert ( pParm ); /* Don't return a NULL thread id */
return ( epicsThreadId ) pParm;
}
@@ -939,18 +932,7 @@ LIBCOM_API epicsThreadId epicsStdCall epicsThreadGetId ( const char * pName )
*/
LIBCOM_API const char * epicsStdCall epicsThreadGetNameSelf (void)
{
win32ThreadGlobal * pGbl = fetchWin32ThreadGlobal ();
win32ThreadParam * pParm;
if ( ! pGbl ) {
return "thread library not initialized";
}
pParm = ( win32ThreadParam * )
TlsGetValue ( pGbl->tlsIndexThreadLibraryEPICS );
if ( ! pParm ) {
pParm = epicsThreadImplicitCreate ();
}
win32ThreadParam * pParm = getMyWin32ThreadParam ( NULL );
if ( pParm ) {
if ( pParm->pName ) {
+8 -11
View File
@@ -109,17 +109,14 @@ inline double delayVerify::delay () const
double delayVerify::checkError () const
{
const double messageThresh = 5.0; // percent
double actualDelay = this->expireStamp - this->beginStamp;
double measuredError = actualDelay - this->expectedDelay;
double percentError = 100.0 * fabs ( measuredError ) / this->expectedDelay;
if(testImpreciseTiming())
testTodoBegin("imprecise");
testOk ( percentError < messageThresh, "%f < %f, delay = %f s, error = %f s (%.1f %%)",
percentError, messageThresh,
this->expectedDelay, measuredError, percentError );
if(testImpreciseTiming())
testTodoEnd();
const double minError = testImpreciseTiming() ? 0.25 : 0.05;
double measuredDelay = this->expireStamp - this->beginStamp;
double measuredError = measuredDelay - this->expectedDelay;
double absoluteError = fabs(measuredError);
double percentError = 100.0 * measuredError / this->expectedDelay;
testOk(absoluteError < minError,
"Delay %.3f s, error = %+.6f ms (%+.3f %%)",
this->expectedDelay, measuredError * 1000, percentError);
return measuredError;
}