mirror of https://github.com/lianthony/NT4.0
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
720 lines
20 KiB
720 lines
20 KiB
/*++
|
|
|
|
Copyright (c) 1992-1993 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
ImpConf.c
|
|
|
|
Abstract:
|
|
|
|
This file contains structures, function prototypes, and definitions
|
|
for the replicator import directory worker routines.
|
|
|
|
Author:
|
|
|
|
John Rogers (JohnRo) 09-Jan-1992
|
|
|
|
Environment:
|
|
|
|
User Mode - Win32
|
|
Portable to any flat, 32-bit environment. (Uses Win32 typedefs.)
|
|
Requires ANSI C extensions: slash-slash comments, long external names.
|
|
|
|
Revision History:
|
|
|
|
09-Jan-1992 JohnRo
|
|
Created.
|
|
23-Jan-1992 JohnRo
|
|
Clarify units for time parameters.
|
|
27-Jan-1992 JohnRo
|
|
ImportDirReadConfigData() should return NERR_UnknownDevDir.
|
|
Changed to use LPTSTR etc.
|
|
10-Feb-1992 JohnRo
|
|
ImportDirReadConfigData() should handle section not found.
|
|
13-Feb-1992 JohnRo
|
|
Moved section name equates to ConfName.h.
|
|
21-Feb-1992 JohnRo
|
|
Fixed bugs handling UNC master.
|
|
Added support for REPL_STATE_NOT_STARTED.
|
|
Added ImportDirDeleteConfigData() and ImportDirConfigDataExists().
|
|
27-Feb-1992 JohnRo
|
|
Changed state not started to state never replicated.
|
|
25-Mar-1992 JohnRo
|
|
Avoid obsolete state values.
|
|
Get rid of old config helpers.
|
|
26-Mar-1992 JohnRo
|
|
Fixed bug parsing UncMaster.
|
|
10-Jul-1992 JohnRo
|
|
RAID 10503: srv mgr: repl dialog doesn't come up.
|
|
Use PREFIX_ equates.
|
|
23-Jul-1992 JohnRo
|
|
RAID 2274: repl svc should impersonate caller.
|
|
29-Sep-1992 JohnRo
|
|
Fix remote repl admin.
|
|
01-Dec-1992 JohnRo
|
|
RAID 3844: remote NetReplSetInfo uses local machine type.
|
|
21-Jan-1993 JohnRo
|
|
RAID 7717: Repl assert if not logged on correctly. (Also do event
|
|
logging for real.)
|
|
Made changes suggested by PC-LINT 5.0
|
|
30-Apr-1993 JohnRo
|
|
Use NetpKdPrint() where possible.
|
|
|
|
--*/
|
|
|
|
|
|
// These must be included first:
|
|
|
|
#include <windef.h> // Win32 type definitions
|
|
#include <lmcons.h> // LAN Manager common definitions
|
|
|
|
// These may be included in any order:
|
|
|
|
#include <config.h> // NetpConfig helpers.
|
|
#include <confname.h> // SECT_NT_ equates.
|
|
#include <dirname.h> // ReplIsDirNameValid().
|
|
#include <impdir.h> // My prototypes.
|
|
#include <lmapibuf.h> // NetApiBufferFree().
|
|
#include <lmerr.h> // NO_ERROR, ERROR_, and NERR_ equates.
|
|
#include <lmerrlog.h> // NELOG_ equates.
|
|
#include <lmrepl.h> // REPL_STATE_ equates.
|
|
#include <names.h> // NetpIsUncComputerNameValid().
|
|
#include <netdebug.h> // NetpAssert(), etc.
|
|
#include <netlib.h> // NetpPointerPlusSomeBytes().
|
|
#include <prefix.h> // PREFIX_ equates.
|
|
#include <replconf.h> // ReplConfigReportBadParmValue().
|
|
#include <repldefs.h> // IF_DEBUG(), DWORDLEN, ReplErrorLog().
|
|
#include <tstr.h> // STRCPY(), ATOL().
|
|
|
|
|
|
#define IMPORT_VALUE_ARRAY_LEN \
|
|
(STATE_LEN /* state */ \
|
|
+ 1 /* , */ \
|
|
+ UNCLEN /* master */ \
|
|
+ 1 /* , */ \
|
|
+ DWORDLEN /* last_update_time (seconds since 1970) */ \
|
|
+ 1 /* , */ \
|
|
+ DWORDLEN /* lockcount */ \
|
|
+ 1 /* , */ \
|
|
+ DWORDLEN ) /* locktime (seconds since 1970) */
|
|
|
|
#define OPTIONAL_LPTSTR( tstr ) \
|
|
( (tstr) ? (tstr) : (LPTSTR) TEXT("<noname>") )
|
|
|
|
|
|
// Tells whether or not config data for this directory exists.
|
|
// Callable even if the replicator service is not started.
|
|
BOOL
|
|
ImportDirConfigDataExists (
|
|
IN LPTSTR UncServerName OPTIONAL,
|
|
IN LPTSTR DirName // Caller must check dir name syntax.
|
|
)
|
|
{
|
|
NET_API_STATUS ApiStatus;
|
|
LPNET_CONFIG_HANDLE Handle;
|
|
LPTSTR Value;
|
|
|
|
//
|
|
// Check for caller's errors.
|
|
//
|
|
NetpAssert( ReplIsDirNameValid( DirName ) );
|
|
|
|
//
|
|
// Open the right section of the config file/whatever.
|
|
//
|
|
ApiStatus = NetpOpenConfigDataEx(
|
|
& Handle,
|
|
UncServerName,
|
|
(LPTSTR) SECT_NT_REPLICATOR, // section
|
|
(LPTSTR) SECT_NT_REPLICATOR_IMPORTS, // area (instead of parameters)
|
|
TRUE); // read-only
|
|
|
|
if (ApiStatus != NO_ERROR) {
|
|
|
|
// Log error on server we were trying to access.
|
|
ReplErrorLog(
|
|
UncServerName,
|
|
NELOG_ReplSysErr,
|
|
ApiStatus,
|
|
NULL,
|
|
NULL );
|
|
|
|
return (FALSE); // section doesn't exist, so dir data doesn't.
|
|
}
|
|
|
|
//
|
|
// Read the value from the config file/whatever.
|
|
//
|
|
ApiStatus = NetpGetConfigValue(
|
|
Handle,
|
|
DirName, // keyword is dir name
|
|
& Value); // alloc and set ptr
|
|
|
|
//
|
|
// We're done with this, so close the config data and toss the buffer we
|
|
// got. But remember the status from NetpGetConfigValue!
|
|
//
|
|
if (Value != NULL) {
|
|
(void) NetApiBufferFree( Value );
|
|
}
|
|
(void) NetpCloseConfigData( Handle );
|
|
|
|
//
|
|
// Now check the status of the Get.
|
|
//
|
|
if (ApiStatus == NERR_CfgParamNotFound) {
|
|
return (FALSE); // doesn't exist
|
|
} else if (ApiStatus == NO_ERROR) {
|
|
return (TRUE); // exists
|
|
} else {
|
|
// Log error on server we were trying to access.
|
|
ReplErrorLog(
|
|
UncServerName,
|
|
NELOG_ReplSysErr,
|
|
ApiStatus,
|
|
NULL,
|
|
NULL );
|
|
|
|
return (FALSE); // Say it doesn't exist, since we don't know.
|
|
}
|
|
|
|
/*NOTREACHED*/
|
|
|
|
} // ImportDirConfigDataExists
|
|
|
|
|
|
// Delete config data for this directory.
|
|
// Returns NERR_UnknownDevDir if config data doesn't exist for this dir.
|
|
// Callable even if the replicator service is not started.
|
|
NET_API_STATUS
|
|
ImportDirDeleteConfigData (
|
|
IN LPTSTR UncServerName OPTIONAL,
|
|
IN LPTSTR DirName // Caller must check dir name syntax.
|
|
)
|
|
{
|
|
NET_API_STATUS ApiStatus;
|
|
LPNET_CONFIG_HANDLE Handle = NULL;
|
|
|
|
//
|
|
// Check for caller's errors.
|
|
//
|
|
if ( ! ReplIsDirNameValid( DirName ) ) {
|
|
ApiStatus = ERROR_INVALID_PARAMETER;
|
|
goto Cleanup; // Log error below.
|
|
}
|
|
|
|
//
|
|
// Open the right section of the config file/whatever.
|
|
//
|
|
ApiStatus = NetpOpenConfigDataEx(
|
|
& Handle,
|
|
UncServerName,
|
|
(LPTSTR) SECT_NT_REPLICATOR, // section
|
|
(LPTSTR) SECT_NT_REPLICATOR_IMPORTS, // area (instead of parameters)
|
|
FALSE ); // not read-only
|
|
if (ApiStatus == NERR_CfgCompNotFound) {
|
|
ApiStatus = NERR_UnknownDevDir;
|
|
goto Cleanup; // Log error below.
|
|
} else if (ApiStatus != NO_ERROR) {
|
|
goto Cleanup; // Log error below.
|
|
}
|
|
|
|
//
|
|
// Delete this keyword from this section.
|
|
//
|
|
ApiStatus = NetpDeleteConfigKeyword(
|
|
Handle,
|
|
DirName ); // keyword is dir name
|
|
|
|
IF_DEBUG(EXPAPI) {
|
|
NetpKdPrint(( PREFIX_REPL
|
|
"ImportDirDeleteConfigData: conf del ret " FORMAT_API_STATUS
|
|
".\n", ApiStatus ));
|
|
}
|
|
|
|
if (ApiStatus == NERR_CfgParamNotFound) {
|
|
ApiStatus = NERR_UnknownDevDir;
|
|
goto Cleanup; // Log error below.
|
|
} else if (ApiStatus != NO_ERROR) {
|
|
goto Cleanup; // Log error below.
|
|
}
|
|
|
|
//
|
|
// All done.
|
|
//
|
|
Cleanup:
|
|
|
|
if ( Handle != NULL ) {
|
|
NET_API_STATUS CloseStatus;
|
|
|
|
CloseStatus = NetpCloseConfigData( Handle );
|
|
|
|
// Return this error iff it is first error we've gotten.
|
|
if ( (ApiStatus == NO_ERROR) && (CloseStatus != NO_ERROR) ) {
|
|
ApiStatus = CloseStatus;
|
|
}
|
|
}
|
|
|
|
if (ApiStatus != NO_ERROR) {
|
|
// Log error on server we were trying to access.
|
|
ReplErrorLog(
|
|
UncServerName,
|
|
NELOG_ReplSysErr,
|
|
ApiStatus,
|
|
NULL,
|
|
NULL );
|
|
}
|
|
|
|
|
|
return (ApiStatus);
|
|
|
|
} // ImportDirDeleteConfigData
|
|
|
|
|
|
// Parse config data for a single import directory. Callable whether or not
|
|
// the replicator service is started.
|
|
NET_API_STATUS
|
|
ImportDirParseConfigData (
|
|
IN LPTSTR UncServerName OPTIONAL,
|
|
IN LPTSTR ValueString,
|
|
OUT LPDWORD StatePtr,
|
|
OUT LPTSTR UncMasterPtr,
|
|
OUT LPDWORD LastUpdateTimePtr, // Seconds since 1970.
|
|
OUT LPDWORD LockCountPtr,
|
|
OUT LPDWORD LockTimePtr // Seconds since 1970.
|
|
)
|
|
{
|
|
LPTSTR CurrentValuePtr = ValueString;
|
|
|
|
//
|
|
// Check for caller's errors.
|
|
//
|
|
NetpAssert( ValueString != NULL);
|
|
if (STRLEN( ValueString ) > IMPORT_VALUE_ARRAY_LEN) {
|
|
goto ReportBadConfigLine;
|
|
}
|
|
|
|
//
|
|
// Start parsing the value, which begins with a string containing the
|
|
// state.
|
|
//
|
|
|
|
#define TRY_STATE( StateEquate, StateString ) \
|
|
{ \
|
|
DWORD HopefulStringLength = STRLEN(StateString); \
|
|
if (STRNCMP( CurrentValuePtr, (StateString), HopefulStringLength) == 0) { \
|
|
*StatePtr = (StateEquate); \
|
|
CurrentValuePtr = (LPTSTR) (LPVOID) \
|
|
NetpPointerPlusSomeBytes( CurrentValuePtr, \
|
|
HopefulStringLength * sizeof(TCHAR) ); \
|
|
goto DoneState; \
|
|
} \
|
|
}
|
|
|
|
TRY_STATE( REPL_STATE_OK, OK_RP )
|
|
|
|
TRY_STATE( REPL_STATE_NO_SYNC, NO_SYNC_RP )
|
|
|
|
TRY_STATE( REPL_STATE_NO_MASTER, NO_MASTER_RP )
|
|
|
|
TRY_STATE( REPL_STATE_NEVER_REPLICATED, NEVER_REPLICATED_RP )
|
|
|
|
goto ReportBadConfigLine;
|
|
|
|
DoneState:
|
|
|
|
//
|
|
// Parse the rest of the value string.
|
|
//
|
|
|
|
#define PARSE_CHAR(AsciiChar) \
|
|
{ \
|
|
if (*CurrentValuePtr == MAKE_TCHAR(AsciiChar)) { \
|
|
++CurrentValuePtr; \
|
|
} else { \
|
|
goto ReportBadConfigLine; \
|
|
} \
|
|
}
|
|
|
|
#define PARSE_COMMA( ) PARSE_CHAR(',')
|
|
|
|
PARSE_COMMA();
|
|
|
|
//
|
|
// Parse the (optional) UNC master name.
|
|
//
|
|
if (*CurrentValuePtr == MAKE_TCHAR('\\')) {
|
|
LPTSTR StringAfterMasterName;
|
|
|
|
StringAfterMasterName = STRCHR( CurrentValuePtr, MAKE_TCHAR(',') );
|
|
if (StringAfterMasterName == NULL) {
|
|
goto ReportBadConfigLine;
|
|
}
|
|
|
|
*StringAfterMasterName = TCHAR_EOS; // changes master to its own str.
|
|
if ( !NetpIsUncComputerNameValid( CurrentValuePtr ) ) {
|
|
goto ReportBadConfigLine;
|
|
}
|
|
|
|
(void) STRCPY( UncMasterPtr, CurrentValuePtr );
|
|
*StringAfterMasterName = MAKE_TCHAR(','); // put line back as is was
|
|
CurrentValuePtr = StringAfterMasterName; // skip to the comma.
|
|
} else if (*CurrentValuePtr == MAKE_TCHAR(',')) {
|
|
if (UncMasterPtr != NULL) {
|
|
*UncMasterPtr = TCHAR_EOS;
|
|
}
|
|
} else {
|
|
goto ReportBadConfigLine;
|
|
}
|
|
|
|
PARSE_COMMA();
|
|
|
|
//
|
|
// Parse the numbers on the rest of the line.
|
|
//
|
|
|
|
#define PARSE_DWORD( NumberPtr ) \
|
|
{ \
|
|
if ( ! ISDIGIT( *CurrentValuePtr ) ) { \
|
|
goto ReportBadConfigLine; \
|
|
} \
|
|
NetpAssert( NumberPtr != NULL ); \
|
|
* NumberPtr = (DWORD) ATOL( CurrentValuePtr ); \
|
|
while ( ISDIGIT( *CurrentValuePtr ) ) { \
|
|
++CurrentValuePtr; \
|
|
} \
|
|
}
|
|
|
|
PARSE_DWORD( LastUpdateTimePtr ); // Seconds since 1970.
|
|
|
|
PARSE_COMMA();
|
|
|
|
PARSE_DWORD( LockCountPtr );
|
|
|
|
PARSE_COMMA();
|
|
|
|
PARSE_DWORD( LockTimePtr ); // Seconds since 1970.
|
|
|
|
IF_DEBUG(IMPAPI) {
|
|
NetpKdPrint(( PREFIX_REPL
|
|
"ImportDirParseConfigValue: Value = '" FORMAT_LPTSTR "',\n",
|
|
ValueString ));
|
|
NetpKdPrint((
|
|
" State = " FORMAT_DWORD
|
|
", UncMaster = '" FORMAT_LPTSTR "'.\n",
|
|
*StatePtr, OPTIONAL_LPTSTR(UncMasterPtr) ));
|
|
NetpKdPrint((
|
|
" last update time (secs since 1970) = " FORMAT_DWORD
|
|
", lock count = " FORMAT_DWORD
|
|
", lock time (secs since 1970) = " FORMAT_DWORD ".\n",
|
|
*LastUpdateTimePtr, *LockCountPtr, *LockTimePtr ));
|
|
}
|
|
|
|
if ( ! ReplIsStateValid( *StatePtr ) ) {
|
|
goto ReportBadConfigLine;
|
|
}
|
|
|
|
return (NO_ERROR);
|
|
|
|
ReportBadConfigLine:
|
|
|
|
// BUGBUG: Sure would be nice if we could include dirname here.
|
|
|
|
ReplConfigReportBadParmValue(
|
|
UncServerName,
|
|
(LPTSTR) SECT_NT_REPLICATOR_IMPORTS,
|
|
ValueString );
|
|
|
|
return (ERROR_INVALID_DATA);
|
|
|
|
} // ImportDirParseConfigData
|
|
|
|
|
|
// Read config data for a single import directory. Callable whether or not
|
|
// the replicator service is started. Returns NERR_UnknownDevDir if there
|
|
// is no config data for this directory.
|
|
NET_API_STATUS
|
|
ImportDirReadConfigData (
|
|
IN LPTSTR UncServerName OPTIONAL,
|
|
IN LPTSTR DirName,
|
|
OUT LPDWORD StatePtr,
|
|
OUT LPTSTR UncMasterPtr,
|
|
OUT LPDWORD LastUpdateTimePtr, // Seconds since 1970.
|
|
OUT LPDWORD LockCountPtr,
|
|
OUT LPDWORD LockTimePtr // Seconds since 1970.
|
|
)
|
|
{
|
|
NET_API_STATUS ApiStatus;
|
|
LPNET_CONFIG_HANDLE Handle = NULL;
|
|
LPTSTR Value = NULL;
|
|
|
|
//
|
|
// Check for caller's errors.
|
|
//
|
|
if ( ! ReplIsDirNameValid( DirName ) ) {
|
|
ApiStatus = ERROR_INVALID_PARAMETER;
|
|
goto Cleanup; // go log error
|
|
}
|
|
|
|
//
|
|
// Open the right section of the config file/whatever.
|
|
//
|
|
ApiStatus = NetpOpenConfigDataEx(
|
|
& Handle,
|
|
UncServerName,
|
|
(LPTSTR) SECT_NT_REPLICATOR, // section
|
|
(LPTSTR) SECT_NT_REPLICATOR_IMPORTS, // area (instead of parameters)
|
|
TRUE); // read-only
|
|
if (ApiStatus == NERR_CfgCompNotFound) {
|
|
ApiStatus = NERR_UnknownDevDir;
|
|
goto Cleanup; // go log error
|
|
} else if (ApiStatus != NO_ERROR) {
|
|
goto Cleanup; // go log error
|
|
}
|
|
|
|
//
|
|
// Read the value from the config file/whatever.
|
|
//
|
|
ApiStatus = NetpGetConfigValue(
|
|
Handle,
|
|
DirName, // keyword is dir name
|
|
& Value); // alloc and set ptr
|
|
if (ApiStatus == NERR_CfgParamNotFound) {
|
|
ApiStatus = NERR_UnknownDevDir;
|
|
goto Cleanup; // go log error
|
|
} else if (ApiStatus != NO_ERROR) {
|
|
goto Cleanup; // go log error
|
|
}
|
|
NetpAssert( Value != NULL );
|
|
|
|
IF_DEBUG(IMPAPI) {
|
|
NetpKdPrint(( PREFIX_REPL
|
|
"ImportDirReadConfigValue( " FORMAT_LPTSTR "): '"
|
|
FORMAT_LPTSTR "' = '" FORMAT_LPTSTR "'.\n",
|
|
(UncServerName!=NULL) ? UncServerName : (LPTSTR) TEXT("local"),
|
|
DirName, Value ));
|
|
}
|
|
|
|
//
|
|
// Parse the value string...
|
|
//
|
|
ApiStatus = ImportDirParseConfigData (
|
|
UncServerName,
|
|
Value,
|
|
StatePtr,
|
|
UncMasterPtr,
|
|
LastUpdateTimePtr, // Seconds since 1970.
|
|
LockCountPtr,
|
|
LockTimePtr); // Seconds since 1970.
|
|
// Fall through and log error if this failed.
|
|
|
|
Cleanup:
|
|
//
|
|
// All done.
|
|
//
|
|
if ( Handle != NULL ) {
|
|
NET_API_STATUS CloseStatus;
|
|
|
|
CloseStatus = NetpCloseConfigData( Handle );
|
|
|
|
// Return this error iff it is first error we've gotten.
|
|
if ( (ApiStatus == NO_ERROR) && (CloseStatus != NO_ERROR) ) {
|
|
ApiStatus = CloseStatus;
|
|
}
|
|
}
|
|
|
|
if (Value != NULL) {
|
|
(VOID) NetApiBufferFree( Value );
|
|
}
|
|
|
|
if (ApiStatus != NO_ERROR) {
|
|
// Log error on server we were trying to access.
|
|
ReplErrorLog(
|
|
UncServerName,
|
|
NELOG_ReplSysErr,
|
|
ApiStatus,
|
|
NULL,
|
|
NULL );
|
|
}
|
|
|
|
return (ApiStatus);
|
|
|
|
} // ImportDirReadConfigData
|
|
|
|
|
|
|
|
|
|
|
|
// Write config data for a single import directory. Callable whether or not
|
|
// the replicator service is started.
|
|
NET_API_STATUS
|
|
ImportDirWriteConfigData (
|
|
IN LPTSTR UncServerName OPTIONAL,
|
|
IN LPTSTR DirName,
|
|
IN DWORD State,
|
|
IN LPTSTR UncMaster OPTIONAL,
|
|
IN DWORD LastUpdateTime, // Seconds since 1970.
|
|
IN DWORD LockCount,
|
|
IN DWORD LockTime // Seconds since 1970.
|
|
)
|
|
{
|
|
NET_API_STATUS ApiStatus;
|
|
LPNET_CONFIG_HANDLE Handle = NULL;
|
|
TCHAR ValueArray[IMPORT_VALUE_ARRAY_LEN+1];
|
|
|
|
IF_DEBUG(IMPAPI) {
|
|
NetpKdPrint(( PREFIX_REPL
|
|
"ImportDirWriteConfigValue:( " FORMAT_LPTSTR " ): DirName = "
|
|
FORMAT_LPTSTR ".\n",
|
|
(UncServerName!=NULL) ? UncServerName : (LPTSTR) TEXT("local"),
|
|
DirName ));
|
|
NetpKdPrint((
|
|
" State = " FORMAT_DWORD
|
|
", UncMaster = '" FORMAT_LPTSTR "'.\n",
|
|
State, OPTIONAL_LPTSTR(UncMaster) ));
|
|
NetpKdPrint((
|
|
" last update time (secs since 1970) = " FORMAT_DWORD
|
|
", lock count = " FORMAT_DWORD
|
|
", lock time (secs since 1970) = " FORMAT_DWORD ".\n",
|
|
LastUpdateTime, LockCount, LockTime ));
|
|
}
|
|
//
|
|
// Check for caller's errors.
|
|
//
|
|
if ( ! ReplIsDirNameValid( DirName ) ) {
|
|
ApiStatus = ERROR_INVALID_PARAMETER;
|
|
goto Cleanup; // go log error
|
|
}
|
|
if ( ! ReplIsStateValid( State ) ) {
|
|
ApiStatus = ERROR_INVALID_PARAMETER;
|
|
goto Cleanup; // go log error
|
|
}
|
|
if (UncMaster != NULL) {
|
|
if ( ! NetpIsUncComputerNameValid( UncMaster ) ) {
|
|
ApiStatus = ERROR_INVALID_PARAMETER;
|
|
goto Cleanup; // go log error
|
|
}
|
|
}
|
|
|
|
//
|
|
// Open the right section of the config file/whatever.
|
|
//
|
|
ApiStatus = NetpOpenConfigDataEx(
|
|
& Handle,
|
|
UncServerName,
|
|
(LPTSTR) SECT_NT_REPLICATOR, // section
|
|
(LPTSTR) SECT_NT_REPLICATOR_IMPORTS, // area (instead of parameters)
|
|
FALSE); // not read-only
|
|
if (ApiStatus != NO_ERROR) {
|
|
goto Cleanup; // go log error
|
|
}
|
|
|
|
//
|
|
// Start building the value, which begins with a string containing the
|
|
// state.
|
|
//
|
|
switch (State) {
|
|
case REPL_STATE_OK:
|
|
|
|
(void) STRCPY( ValueArray, OK_RP);
|
|
break;
|
|
|
|
case REPL_STATE_NO_SYNC:
|
|
|
|
(void) STRCPY( ValueArray, NO_SYNC_RP);
|
|
break;
|
|
|
|
case REPL_STATE_NO_MASTER:
|
|
|
|
(void) STRCPY( ValueArray, NO_MASTER_RP);
|
|
break;
|
|
|
|
case REPL_STATE_NEVER_REPLICATED:
|
|
|
|
(void) STRCPY( ValueArray, NEVER_REPLICATED_RP);
|
|
break;
|
|
|
|
default:
|
|
NetpAssert( FALSE );
|
|
ApiStatus = ERROR_INVALID_PARAMETER;
|
|
goto Cleanup; // go log error
|
|
}
|
|
|
|
//
|
|
// Build the rest of the value string.
|
|
//
|
|
(void) STRCAT( ValueArray, (LPTSTR) TEXT(",") );
|
|
|
|
if (UncMaster != NULL) {
|
|
(void) STRCAT( ValueArray, UncMaster );
|
|
}
|
|
|
|
/*lint -save -e767 */ // Don't complain about different definitions
|
|
#define WRITE_COMMA( ) \
|
|
(void) STRCAT( ValueArray, (LPTSTR) TEXT(",") )
|
|
/*lint -restore */ // Resume checking for different macro definitions
|
|
|
|
/*lint -save -e767 */ // Don't complain about different definitions
|
|
#define WRITE_DWORD( Number ) \
|
|
{ \
|
|
LPTSTR StrEnd = & ValueArray[ STRLEN( ValueArray ) ]; \
|
|
(void) ULTOA( (Number), StrEnd, /* radix */ 10 ); \
|
|
}
|
|
/*lint -restore */ // Resume checking for different macro definitions
|
|
|
|
WRITE_COMMA();
|
|
|
|
WRITE_DWORD( LastUpdateTime ); // Seconds since 1970.
|
|
|
|
WRITE_COMMA();
|
|
|
|
WRITE_DWORD( LockCount );
|
|
|
|
WRITE_COMMA();
|
|
|
|
WRITE_DWORD( LockTime ); // Seconds since 1970.
|
|
|
|
IF_DEBUG(IMPAPI) {
|
|
NetpKdPrint(( PREFIX_REPL
|
|
"ImportDirWriteConfigValue: '" FORMAT_LPTSTR "' = '"
|
|
FORMAT_LPTSTR "'.\n", DirName, ValueArray ));
|
|
}
|
|
|
|
//
|
|
// Write this value out to the config file/whatever.
|
|
//
|
|
ApiStatus = NetpSetConfigValue(
|
|
Handle,
|
|
DirName, // keyword is dir name
|
|
ValueArray);
|
|
// Fall through and log error if one happened.
|
|
|
|
Cleanup:
|
|
//
|
|
// All done.
|
|
//
|
|
if ( Handle != NULL ) {
|
|
NET_API_STATUS CloseStatus;
|
|
|
|
CloseStatus = NetpCloseConfigData( Handle );
|
|
|
|
// Return this error iff it is first error we've gotten.
|
|
if ( (ApiStatus == NO_ERROR) && (CloseStatus != NO_ERROR) ) {
|
|
ApiStatus = CloseStatus;
|
|
}
|
|
}
|
|
|
|
if (ApiStatus != NO_ERROR) {
|
|
// Log error on server we were trying to access.
|
|
ReplErrorLog(
|
|
UncServerName,
|
|
NELOG_ReplSysErr,
|
|
ApiStatus,
|
|
NULL,
|
|
NULL );
|
|
}
|
|
|
|
return (ApiStatus);
|
|
|
|
} // ImportDirWriteConfigData
|