This repository has been archived on 2024-04-08. You can view files and clone it, but cannot push or open issues or pull requests.
tsmpipe/lib/dsmsession.c
2015-09-23 15:19:59 +10:00

396 lines
12 KiB
C

/*
* This function will set up a session to the TSM server and return the
* session handler
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "dsmrc.h"
#include "dsmapitd.h"
#include "dsmapifp.h"
#include "../tsmpipe.h"
dsBool_t compressEnabled=bFalse; // Is compression enabled
/* Print out TSM Error Code */
char *tsm_printerr(dsUint32_t dsmHandle, dsInt16_t rc) {
char rcStr[DSM_MAX_RC_MSG_LENGTH];
char *s;
s = malloc(sizeof(rcStr));
if (rc == DSM_RC_WILL_ABORT) {
dsUint16_t reason;
rc = dsmEndTxn(dsmHandle, DSM_VOTE_COMMIT, &reason);
if (rc == DSM_RC_CHECK_REASON_CODE)
rc = reason;
}
dsmRCMsg(dsmHandle,rc,rcStr);
strtok(rcStr, "\n");
sprintf(s,"[rc=%s]",rcStr);
return s;
}
/* Check the TSM API Version */
int tsm_checkapi(void) {
dsmApiVersionEx apiLibVer;
dsUint32_t apiVersion;
dsUint32_t applVersion = (10000 * DSM_API_VERSION) + (1000 * DSM_API_RELEASE) + (100 * DSM_API_LEVEL) + DSM_API_SUBLEVEL;
memset(&apiLibVer,0x00,sizeof(dsmApiVersionEx));
apiLibVer.stVersion = apiVersionExVer;
dsmQueryApiVersionEx(&apiLibVer);
apiVersion = (10000 * apiLibVer.version) + (1000 * apiLibVer.release) + (100 * apiLibVer.level) + apiLibVer.subLevel;
if (apiVersion < applVersion) {
printf("The Tivoli Storage Manager API library Version (%d.%d.%d.%d) is at a lower version than the application version (%d.%d.%d.%d)\n",
apiLibVer.version,
apiLibVer.release,
apiLibVer.level,
apiLibVer.subLevel,
DSM_API_VERSION,
DSM_API_RELEASE,
DSM_API_LEVEL,
DSM_API_SUBLEVEL);
printf("Please upgrade the API accordingly.\n");
return 0;
}
return 1;
}
/* Initialise a session to the TSM server */
dsUint32_t tsm_initsess(char *options) {
dsInt16_t rc=0;
dsUint32_t dsmHandle=0;
dsmApiVersionEx applApi;
dsmInitExIn_t initIn;
dsmInitExOut_t initOut;
optStruct dsmOpt;
ApiSessInfo dsmSessInfo;
if (! tsm_checkapi()) {
exit(2);
}
memset(&applApi,0x00,sizeof(dsmApiVersionEx));
applApi.stVersion = apiVersionExVer;
applApi.version = DSM_API_VERSION;
applApi.release = DSM_API_RELEASE;
applApi.level = DSM_API_LEVEL;
applApi.subLevel = DSM_API_SUBLEVEL;
memset(&initIn,0x00,sizeof(dsmInitExIn_t));
initIn.stVersion = dsmInitExInVersion;
initIn.apiVersionExP = &applApi;
initIn.clientNodeNameP = NULL;
initIn.clientOwnerNameP = NULL;
initIn.clientPasswordP = NULL;
initIn.applicationTypeP = NULL;
initIn.configfile = NULL;
initIn.options = options;
initIn.userNameP = NULL;
initIn.userPasswordP = NULL;
//initIn.dirDelimiter = dirDelimiter;
//initIn.useUnicode = useUnicode;
//initIn.bEncryptKeyEnabled = encrypt;
//initIn.encryptionPasswordP = encryptKey;
memset(&initOut,0x00,sizeof(dsmInitExOut_t));
initOut.stVersion = dsmInitExOutVersion;
rc = dsmInitEx(&dsmHandle, &initIn, &initOut);
/* If the TSM password has expired, change it. */
if (rc == DSM_RC_REJECT_VERIFIER_EXPIRED) {
rc = dsmChangePW(dsmHandle,NULL,NULL);
if (rc != DSM_RC_OK) {
printf("%s: dsmChangePW() failed %s\n",__func__,tsm_printerr(dsmHandle,rc));
return 0;
}
} else if (rc != DSM_RC_OK) {
printf("%s: dsmInitEx() failed %s\n",__func__,tsm_printerr(dsmHandle, rc));
dsmTerminate(dsmHandle);
return 0;
}
// Make sure if we have compression enabled, that we also have COMPRESSAlways YES
memset(&dsmOpt,0x00,sizeof(dsmOpt));
rc = dsmQuerySessOptions(dsmHandle, &dsmOpt);
memset(&dsmSessInfo,0x00,sizeof(ApiSessInfo));
dsmSessInfo.stVersion = ApiSessInfoVersion; /* Init struct version */
rc = dsmQuerySessInfo(dsmHandle, &dsmSessInfo);
rc = 1;
switch (dsmSessInfo.compression) {
case COMPRESS_YES : compressEnabled = bTrue; break;
case COMPRESS_NO : compressEnabled = bFalse; break;
case COMPRESS_CD : compressEnabled = dsmOpt.compression; break;
default: rc=0;
}
if (!rc || (compressEnabled && ! dsmOpt.compressalways)) {
debugLog(0,__func__,!rc ? "ERROR: Error Querying Session Capabilities" : "ERROR: COMPRESSion is ENABLED, but not COMPRESSAlways Yes",1);
}
return dsmHandle;
}
/* List objects that are in TSM */
int tsm_sessioninfo(dsUint32_t dsmHandle) {
extern int verbose;
dsInt16_t rc=0;
optStruct dsmOpt;
ApiSessInfo dsmSessInfo;
dsmApiVersionEx apiLibVer;
char t[50];
memset(&apiLibVer,0x00,sizeof(dsmApiVersionEx));
apiLibVer.stVersion = apiVersionExVer;
dsmQueryApiVersionEx(&apiLibVer);
printf("Application Version:\n");
printf(" TSMPIPE Version: %s\n",
_TSMPIPE_VERSION);
printf(" TSMPIPE API Version: %d.%d.%d.%d\n",
DSM_API_VERSION,
DSM_API_RELEASE,
DSM_API_LEVEL,
DSM_API_SUBLEVEL);
printf(" TSM Library: %d.%d.%d.%d\n",
apiLibVer.version,
apiLibVer.release,
apiLibVer.level,
apiLibVer.subLevel);
printf("\n");
memset(&dsmOpt,0x00,sizeof(dsmOpt));
rc = dsmQuerySessOptions(dsmHandle, &dsmOpt);
if (rc)
printf("%s: ERROR dsmQuerySessOptions() unable to query Session Options. RC = %d\n",__func__,rc);
else {
printf("dsmQuerySessOptions:\n");
printf(" DSMI_DIR: %s\n",dsmOpt.dsmiDir);
printf(" DSMI_CONFIG: %s\n",dsmOpt.dsmiConfig);
printf(" SErvername: %s\n",dsmOpt.serverName);
switch (dsmOpt.commMethod) {
case DSM_COMM_TCP : strcpy(t,"TCP/IP"); break;
case DSM_COMM_NAMEDPIPE : strcpy(t,"NAMED PIPE"); break;
case DSM_COMM_SHM : strcpy(t,"SHARED MEMORY"); break;
case DSM_COMM_TCPIP6 : strcpy(t,"TCP/IP v6"); break;
default: strcpy(t,"UNKNOWN");
}
printf(" COMMmethod: %s\n",t);
if (verbose)
fprintf(stderr,"%s: commMethod: [%d]\n",__func__,dsmOpt.commMethod);
printf(" TCPServerAddress: %s\n",dsmOpt.serverAddress);
if (verbose)
fprintf(stderr,"%s: serverAddress: [%s]\n",__func__,dsmOpt.serverAddress);
printf(" NODEName: %s\n",dsmOpt.nodeName);
printf(" COMPRESSIon: %s\n",dsmOpt.compression ? "YES" : "NO");
printf(" COMPRESSAlways: %s\n",dsmOpt.compressalways ? "YES" : "NO");
printf(" PASSWORDAccess: %s\n",dsmOpt.passwordAccess ? "GENERATE" : "PROMPT");
}
memset(&dsmSessInfo,0x00,sizeof(ApiSessInfo));
dsmSessInfo.stVersion = ApiSessInfoVersion; /* Init struct version */
rc = dsmQuerySessInfo(dsmHandle, &dsmSessInfo);
if (rc)
printf("%s: ERROR dsmQuerySessInfo() unable to query Session Info. RC = %d\n",__func__,rc);
else {
printf("\n");
printf("dsmQuerySessInfo:\n");
printf(" Server Information:\n");
printf(" Name: %s\n",dsmSessInfo.adsmServerName);
printf(" Host: %s\n",dsmSessInfo.serverHost);
printf(" Port: %u\n",dsmSessInfo.serverPort);
printf(" Date: %s\n",dsmDateToStr(dsmSessInfo.serverDate));
printf(" Type: %s\n",dsmSessInfo.serverType);
printf(" Version: %i.%i.%i.%i\n",
dsmSessInfo.serverVer,
dsmSessInfo.serverRel,
dsmSessInfo.serverLev,
dsmSessInfo.serverSubLev);
printf(" Archive Retention Protection : %s\n",dsmSessInfo.archiveRetentionProtection ? "YES" : "NO");
printf("\n");
printf(" Client Information:\n");
printf(" Node: %s\n",dsmSessInfo.id);
printf(" Node Type: %s\n",dsmSessInfo.nodeType);
printf(" Filespace delimiter: %c\n",dsmSessInfo.fsdelim);
printf(" HL & LL delimiter: %c\n",dsmSessInfo.hldelim);
switch (dsmSessInfo.compression) {
case COMPRESS_YES : strcpy(t,"ON"); break;
case COMPRESS_NO : strcpy(t,"OFF"); break;
case COMPRESS_CD : strcpy(t,"CLIENT"); break;
default: strcpy(t,"UNKNOWN");
}
printf(" Client compression: %s\n",t);
switch (dsmSessInfo.archDel) {
case ARCHDEL_YES : strcpy(t,"YES"); break;
case ARCHDEL_NO : strcpy(t,"NO"); break;
default: strcpy(t,"UNKNOWN");
}
printf(" ARCHIVE Delete: %s\n",t);
switch (dsmSessInfo.backDel) {
case BACKDEL_YES : strcpy(t,"YES"); break;
case ARCHDEL_NO : strcpy(t,"NO"); break;
default: strcpy(t,"UNKNOWN");
}
printf(" BACKUP delete: %s\n",t);
printf(" MAX objects per transactions: %u\n", dsmSessInfo.maxObjPerTxn);
printf(" LAN FREE Enabled: %s\n",dsmSessInfo.lanFreeEnabled ? "YES" : "NO");
printf(" Deduplication: %s\n",dsmSessInfo.dedupType == dedupClientOrServer ? "Client Or Server" : "Server Only");
printf("\n");
printf(" General session info:\n");
printf(" Owner: %s\n",dsmSessInfo.owner);
printf(" API Config file: %s\n",dsmSessInfo.confFile);
printf("\n");
printf(" Policy Information:\n");
printf(" Domain name: %s\n",dsmSessInfo.domainName);
printf(" Policyset name: %s\n",dsmSessInfo.policySetName);
printf(" Policy activation date: %s\n",dsmDateToStr(dsmSessInfo.polActDate));
printf(" Default management class: %s\n",dsmSessInfo.dfltMCName);
printf(" BACKUP retention grace: %u days\n",dsmSessInfo.gpBackRetn);
printf(" ARCHIVE retention grace: %u days\n",dsmSessInfo.gpArchRetn);
printf("\n");
}
return 1;
}
/*
* Query TSM for a list of objects.
*
* We use a callback to process the list, the callback should return:
* -1 upon error condition, application should exit.
* 0 if tsm_queryfile() should skip processing the remaining matches.
* 1 otherwise.
*/
dsInt16_t tsm_queryfile(dsUint32_t dsmHandle, dsmQueryType qType, tsm_query_callback usercb, void *userdata, qryArchiveData qaData, qryBackupData qbData, dsBool_t friendly) {
extern int verbose;
dsInt16_t rc=0;
dsmQueryBuff *qDataP;
DataBlk qResp;
memset(&qResp,0x00,sizeof(DataBlk));
qResp.stVersion = DataBlkVersion;
switch (qType) {
case qtArchive:
qDataP = &qaData;
if (verbose)
fprintf(stderr,"%s: Query filespace %s\n",__func__,dsmObjnameToStr(*qaData.objName));
qryRespArchiveData qaResp;
qaResp.stVersion = qryRespArchiveDataVersion;
qResp.bufferPtr = (char *) &qaResp;
qResp.bufferLen = sizeof(qaResp);
break;
case qtBackup:
qDataP = &qbData;
if (verbose)
fprintf(stderr,"%s: Query filespace %s\n",__func__,dsmObjnameToStr(*qbData.objName));
if (verbose > 1) {
fprintf(stderr,"%s: PIT Date: %s\n",__func__,dsmDateToStr(qbData.pitDate));
fprintf(stderr,"%s: OBJSTATE : %s\n",__func__,qbData.objState==DSM_ACTIVE ? "DSM_ACTIVE" : "DSM_ANY_MATCH");
}
qryRespBackupData qbResp;
qbResp.stVersion = qryRespBackupDataVersion;
qResp.bufferPtr = (char *) &qbResp;
qResp.bufferLen = sizeof(qbResp);
break;
default:
fprintf(stderr,"%s: UNKNOWN Type %d\n",__func__,qType);
exit(1);
}
rc = dsmBeginQuery(dsmHandle, qType, qDataP);
if (rc != DSM_RC_OK) {
printf("%s: dsmBeginQuery() failed %s\n",__func__,tsm_printerr(dsmHandle,rc));
return rc;
}
/* Loop and apply our callback to the result */
while ((rc = dsmGetNextQObj(dsmHandle, &qResp)) == DSM_RC_MORE_DATA) {
int cbret;
if(verbose > 1) {
dsmObjName *rObjName;
if (qType == qtArchive) {
qryRespArchiveData *qr = (void *) qResp.bufferPtr;
rObjName = &(qr->objName);
} else if (qType == qtBackup) {
qryRespBackupData *qr = (void *) qResp.bufferPtr;
rObjName = &(qr->objName);
} else {
fprintf(stderr,"%s: UNKNOWN Type %d\n",__func__,qType);
return DSM_RC_UNKNOWN_ERROR;
}
fprintf(stderr,"%s: Match file %s\n",__func__,dsmObjnameToStr(*rObjName));
}
if (usercb == NULL)
continue;
cbret = usercb(qType,&qResp,userdata,friendly);
if (cbret < 0) {
return DSM_RC_UNKNOWN_ERROR;
} else if(cbret == 0) {
break;
}
}
if (rc != DSM_RC_FINISHED && rc != DSM_RC_MORE_DATA) {
printf("%s: dsmGetNextObj() failed %s\n",__func__,tsm_printerr(dsmHandle,rc));
return rc;
}
rc = dsmEndQuery(dsmHandle);
if (rc != DSM_RC_OK) {
printf("%s: dsmEndQuery() failed %s\n",__func__,tsm_printerr(dsmHandle,rc));
return rc;
}
return DSM_RC_OK;
}